rails-archiver 0.1.8 → 0.2.0

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 22767f51d1fefb73fd2d17b703a0ee846509bb99fc4dd2bed27c06a28fcdfc60
4
- data.tar.gz: d04f42ec798d1df81fc3ee76575d4e1658563b73e4087f1e1639553b489b52b6
3
+ metadata.gz: 3b31d762ea01d15091eebffd02a581b9ae2a20fba31005ec2669b4cf0d350125
4
+ data.tar.gz: 6f553c01c3a2d02062c74384c09a8e220845907544009f8d64ea97313afba6af
5
5
  SHA512:
6
- metadata.gz: a9b6176a12fd8fd673ebb726dcaa4dd08f2a3e561718685693870f78d0661b863e7ca03b2ea8a9da8f8e18e73f1128115c20af17f65aee08e070911584473958
7
- data.tar.gz: 176e5169d8d4756fdae4ff8fcbe5e8f5bcde4395a262a332321e7cbbdf1e61530e7373b1fd389217d5c747190d4dbb0023aa1aab48c29df5128ac7827a7a502d
6
+ metadata.gz: 11961ec8a0cacd1101792d3beade62fa79eb224a3c254edcb42a67a0a0f16ce423f7fefec0a5adb1b535ee5a33864e6dd5e02d8e8df22b83f1f490925741e9ae
7
+ data.tar.gz: 3f37961ca490f99900f3de97e0e76d4b6ae83e9fa7977ebadedfb55784102b8d33dc8975aead38af477d3732350774212b8b11f323ae3a093a05aaca34a4811f
data/.gitignore ADDED
@@ -0,0 +1,3 @@
1
+ ### Ruby template
2
+ *.gem
3
+ .idea
data/CHANGELOG.md ADDED
@@ -0,0 +1,13 @@
1
+ # Changelog
2
+
3
+ All notable changes to this project will be documented in this file.
4
+
5
+ The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/)
6
+ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
7
+
8
+ ## UNRELEASED
9
+
10
+ # [0.2.0] - 2025-01-20
11
+ - Added support for enum columns - should be able to handle both keys and values.
12
+ - Refactored the `unarchiver` method to more easily subclass `Unarchiver`.
13
+ - For `belongs_to` associations, replace foreign key attributes with actual reference to the relevant object while archiving to avoid issues with validation.
@@ -128,9 +128,18 @@ module RailsArchiver
128
128
  @logger.info("Finished deleting from #{table}")
129
129
  end
130
130
 
131
+ # @return [Class]
132
+ def unarchiver_class
133
+ RailsArchiver::Unarchiver
134
+ end
135
+
131
136
  # @return [RailsArchiver::Unarchiver]
132
- def unarchiver
133
- unarchiver = RailsArchiver::Unarchiver.new(@model, :logger => @logger)
137
+ # @param crash_on_errors [Boolean]
138
+ def unarchiver(crash_on_errors: false)
139
+ unarchiver = unarchiver_class.new(@model,
140
+ logger: @logger,
141
+ crash_on_errors: crash_on_errors
142
+ )
134
143
  unarchiver.transport = self.transport
135
144
  unarchiver
136
145
  end
@@ -11,18 +11,24 @@ module RailsArchiver
11
11
  attr_accessor :errors, :transport
12
12
 
13
13
  # @param model [ActiveRecord::Base]
14
- # @param options [Hash]
15
- # * logger [Logger]
16
- # * new_copy [Boolean] if true, create all new objects instead of
17
- # replacing existing ones.
18
- # * crash_on_errors [Boolean] if true, do not do any imports if any
19
- # models' validations failed.
20
- def initialize(model, options={})
14
+ # @param logger [Logger]
15
+ # @param new_copy [Boolean] if true, create all new objects instead of
16
+ # replacing existing ones.
17
+ # @param crash_on_errors [Boolean] if true, do not do any imports if any
18
+ # models' validations failed.
19
+ # @param transport [Symbol|RailsArchiver::Transport::Base]
20
+ def initialize(model,
21
+ transport: :in_memory,
22
+ logger: Logger.new(STDOUT),
23
+ new_copy: false, crash_on_errors: false)
21
24
  @model = model
22
- @logger = options.delete(:logger) || Logger.new(STDOUT)
23
- @options = options
25
+ @logger = logger
26
+ @options = {
27
+ new_copy: new_copy,
28
+ crash_on_errors: crash_on_errors
29
+ }
24
30
  # Transport for downloading
25
- self.transport = _get_transport(options.delete(:transport) || :in_memory)
31
+ self.transport = _get_transport(transport)
26
32
  self.errors = []
27
33
  end
28
34
 
@@ -58,7 +64,7 @@ module RailsArchiver
58
64
  end
59
65
  end
60
66
  if @options[:crash_on_errors] && self.errors.any?
61
- raise ImportError.new("Errors occurred during load - please see 'errors' method for more details")
67
+ raise ImportError.new("Errors occurred during load: #{self.errors.join("\n")}")
62
68
  end
63
69
  end
64
70
 
@@ -114,13 +120,52 @@ module RailsArchiver
114
120
  end
115
121
 
116
122
  model
123
+ rescue => e
124
+ self.errors << "Error importing class #{klass.name}: #{e.message}"
117
125
  end
118
126
 
119
127
  private
120
128
 
129
+ # @param model [ActiveRecord::Base]
130
+ # @param field [String]
131
+ # @param attrs [Hash]
132
+ def assign_enum_value(model, field, attrs)
133
+ entries = model.class.public_send(field.pluralize)
134
+ is_integer = entries.values.first.is_a?(Integer)
135
+ value = attrs[field]
136
+ valid = if entries.keys.include?(value)
137
+ true
138
+ elsif is_integer && entries.values.include?(value.to_i)
139
+ true
140
+ else
141
+ entries.values.include?(value)
142
+ end
143
+
144
+ return if valid
145
+
146
+ @logger.warn("Invalid value for #{field}: #{attrs[field]}")
147
+ new_value = model.class.columns.find { |a| a.name == field }.default
148
+ new_value = new_value.to_i if is_integer && new_value
149
+ attrs[field] = new_value
150
+ end
151
+
121
152
  # @param model [ActiveRecord::Base]
122
153
  # @param attrs [Hash]
123
154
  def _assign_attributes(model, attrs)
155
+ # Handle integer enum values that were turned into strings
156
+ if model.class.respond_to?(:attribute_types)
157
+ enums = model.class.attribute_types.select { |_, v| v.is_a?(ActiveRecord::Enum::EnumType) }
158
+ enums.keys.each do |field|
159
+ assign_enum_value(model, field, attrs)
160
+ end
161
+ end
162
+ model.class.reflect_on_all_associations(:belongs_to).each do |assoc|
163
+ if attrs[assoc.foreign_key].present?
164
+ record = assoc.klass.find_by(assoc.association_primary_key => attrs[assoc.foreign_key])
165
+ attrs[assoc.name] = record if record
166
+ end
167
+ end
168
+
124
169
  if model.method(:attributes=).arity == 1
125
170
  model.attributes = attrs
126
171
  else
@@ -1,8 +1,8 @@
1
1
  Gem::Specification.new do |s|
2
2
  s.name = 'rails-archiver'
3
3
  s.require_paths = %w(. lib lib/rails-archiver)
4
- s.version = '0.1.8'
5
- s.date = '2024-07-03'
4
+ s.version = '0.2.0'
5
+ s.date = '2025-01-20'
6
6
  s.summary = 'Fully archive a Rails model'
7
7
  s.description = <<-EOF
8
8
  EOF
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: rails-archiver
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.1.8
4
+ version: 0.2.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Daniel Orner
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2024-07-03 00:00:00.000000000 Z
11
+ date: 2025-01-20 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: rails
@@ -44,6 +44,8 @@ executables: []
44
44
  extensions: []
45
45
  extra_rdoc_files: []
46
46
  files:
47
+ - ".gitignore"
48
+ - CHANGELOG.md
47
49
  - README.md
48
50
  - lib/rails-archiver.rb
49
51
  - lib/rails-archiver/archiver.rb