importo 3.0.21 → 3.0.22

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: bcca807f9c6f4ca09145b27128b1df2564b226bae7ff922618d399298cf8c231
4
- data.tar.gz: b63912b0490807c5f99dc6928dd69b189cfcd0b92611ac6982d27c45a64b33e4
3
+ metadata.gz: d68cd0c105d04f8338c6eeecf55032d1f6a31cb6fa825787e0c4b43859a1fd6f
4
+ data.tar.gz: 6c64470c728960afac588aeeadd59f219062254bb07d14d1fd02751ec6271baf
5
5
  SHA512:
6
- metadata.gz: 9b01d49b3e56b5823331572c42cccf441325aae495699bc7d52ecb1fb7aaf6468f685ffbfe3412ebc0f64c9d0c34b99f7340f21f420ce655d7804a0aad5beeaa
7
- data.tar.gz: 553dadb41cbe13aae4857265964fd3cf449c641f0bc199938b22db259bc3ce897ea7a34b340f2bb4bf7380647ec5f6a216e4efc0a378d15714bb89f38669e0ce
6
+ metadata.gz: 716af97a98a787f7491a53df4099efba5d5eac4693ad375fbd36609c3dec86e930b7ac9dff38dc5d49afdc9d240ec581e7a7b0bb0ca7304b6a7b6d9f1eaddc4a
7
+ data.tar.gz: 04c57bf751390e916f996c5d3684277041f4f68d1e562a4aff0aee5595c0d1a07d86d93537ecac88eda996bc977bd4cd53374e1891fa4d646981f018ea30c0cc
@@ -126,7 +126,7 @@ module Importable
126
126
  def import!
127
127
  raise ArgumentError, "Invalid data structure" unless structure_valid?
128
128
 
129
- batch = Importo::SidekiqBatchAdapter.new
129
+ batch = Importo.config.batch_adapter.new
130
130
  batch.description = "#{import.original.filename} - #{import.kind}"
131
131
  batch.properties = {import_id: import.id}
132
132
  batch.on_success("Importo::ImportJobCallback")
@@ -7,13 +7,10 @@ module Importo
7
7
  import = Import.find(options["import_id"])
8
8
  if import.present?
9
9
  results_file = import.importer.results_file
10
- if results_file.is_a?(StringIO)
11
- import.result.attach(io: results_file, filename: import.importer.file_name("results"),
12
- content_type: "application/vnd.openxmlformats-officedocument.spreadsheetml.sheet")
13
- else
14
- import.result.attach(io: File.open(results_file), filename: import.importer.file_name("results"),
15
- content_type: "application/vnd.openxmlformats-officedocument.spreadsheetml.sheet")
16
- end
10
+ results_file = results_file.is_a?(StringIO) ? results_file : File.open(results_file)
11
+
12
+ import.result.attach(io: results_file, filename: import.importer.file_name("results"),
13
+ content_type: "application/vnd.openxmlformats-officedocument.spreadsheetml.sheet")
17
14
 
18
15
  ActiveRecord::Base.uncached do
19
16
  import.result_message = I18n.t("importo.importers.result_message",
@@ -1,24 +1,6 @@
1
1
  module Importo
2
- class ImportJob
3
- include Sidekiq::Job
4
- sidekiq_options retry: 5
5
- # queue_as :integration
6
- queue_as Importo.config.queue_name
7
-
8
- sidekiq_retries_exhausted do |msg, _e|
9
- attributes = msg["args"][0]
10
- index = msg["args"][1]
11
- import_id = msg["args"][2]
12
-
13
- execute_row(attributes, index, import_id, true, msg["bid"])
14
- end
15
-
16
- sidekiq_retry_in do |_count, exception, _jobhash|
17
- case exception
18
- when Importo::RetryError
19
- exception.delay
20
- end
21
- end
2
+ class ImportJob < Importo.config.import_job_base_class.safe_constantize
3
+ # No options here, gets added from the adapter
22
4
 
23
5
  def perform(attributes, index, import_id)
24
6
  self.class.execute_row(attributes, index, import_id, false, bid)
@@ -28,12 +10,18 @@ module Importo
28
10
  attributes = JSON.load(attributes).deep_symbolize_keys if attributes.is_a?(String)
29
11
 
30
12
  import = Import.find(import_id)
31
- record = import.importer.process_data_row(attributes, index, last_attempt: last_attempt)
32
-
33
- batch = Importo::SidekiqBatchAdapter.find(bid)
34
-
35
- if !import.completed? && import.can_complete? && batch.finished?
36
- ImportJobCallback.new.on_complete(batch.status, {import_id: import.id})
13
+ import.importer.process_data_row(attributes, index, last_attempt: last_attempt)
14
+
15
+ # Between sidekiq and good job, there's a big difference:
16
+ # - Sidekiq calls on_complete callback when all jobs ran at least once.
17
+ # - GoodJob calls on_complete callback when all jobs are done (including retries).
18
+ # i.e. this logic is only needed for sidekiq
19
+ if Importo.config.batch_adapter == Importo::SidekiqBatchAdapter
20
+ batch = Importo::SidekiqBatchAdapter.find(bid)
21
+
22
+ if !import.completed? && import.can_complete? && batch.finished?
23
+ ImportJobCallback.new.on_complete("success", {import_id: import.id})
24
+ end
37
25
  end
38
26
  end
39
27
  end
@@ -0,0 +1,79 @@
1
+ if !defined?(Sidekiq::Batch)
2
+ module Sidekiq
3
+ class Batch
4
+ def self.new(*)
5
+ raise NotImplementedError, "Sidekiq::Batch is not available. Please install the sidekiq-pro or sidekiq-batch gem."
6
+ end
7
+ end
8
+ end
9
+ end
10
+
11
+ require_relative "../../../app/jobs/importo/import_job"
12
+
13
+ module Importo
14
+ class SidekiqBatchAdapter
15
+ attr_reader :description
16
+ attr_accessor :properties
17
+ attr_writer :instance
18
+
19
+ delegate :description=, to: :@instance
20
+
21
+ def initialize
22
+ @instance = Sidekiq::Batch.new
23
+ end
24
+
25
+ def on_success(job)
26
+ @instance.on(:complete, job.constantize, properties)
27
+ end
28
+
29
+ def add
30
+ @instance.jobs do
31
+ yield
32
+ end
33
+ end
34
+
35
+ def finished?
36
+ status = Sidekiq::Batch::Status.new( @instance.bid)
37
+ status.complete?
38
+ end
39
+
40
+ class << self
41
+ def import_job_base_class
42
+ Object
43
+ end
44
+
45
+ def find(id)
46
+ instance = new
47
+ instance.instance = Sidekiq::Batch.new(id)
48
+ instance
49
+ end
50
+ end
51
+
52
+ module ImportJobIncludes
53
+ extend ActiveSupport::Concern
54
+
55
+ included do
56
+ queue_as Importo.config.queue_name
57
+ sidekiq_options retry: 5
58
+
59
+ sidekiq_retries_exhausted do |msg, _e|
60
+ attributes = msg["args"][0]
61
+ index = msg["args"][1]
62
+ import_id = msg["args"][2]
63
+
64
+ execute_row(attributes, index, import_id, true, msg["bid"])
65
+ end
66
+
67
+ sidekiq_retry_in do |_count, exception, _jobhash|
68
+ case exception
69
+ when Importo::RetryError
70
+ exception.delay
71
+ end
72
+ end
73
+ end
74
+ end
75
+ end
76
+ end
77
+
78
+ Importo::ImportJob.send(:include, Sidekiq::Job)
79
+ Importo::ImportJob.send(:include, Importo::SidekiqBatchAdapter::ImportJobIncludes)
@@ -3,9 +3,19 @@
3
3
  module Importo
4
4
  module Options
5
5
  module ClassMethods
6
- def option(name, default: nil)
7
- attr_accessor(name)
8
- schema[name] = default
6
+ def option(name, default: nil, proc: false)
7
+ attr_writer(name)
8
+ schema[name] = {default: default, proc: proc}
9
+ if schema[name][:proc]
10
+ define_method(name) do |*params|
11
+ value = instance_variable_get(:"@#{name}")
12
+ instance_exec(*params, &value)
13
+ end
14
+ else
15
+ define_method(name) do
16
+ instance_variable_get(:"@#{name}")
17
+ end
18
+ end
9
19
  end
10
20
 
11
21
  def schema
@@ -14,8 +24,8 @@ module Importo
14
24
  end
15
25
 
16
26
  def set_defaults!
17
- self.class.schema.each do |name, default|
18
- instance_variable_set(:"@#{name}", default)
27
+ self.class.schema.each do |name, options|
28
+ instance_variable_set(:"@#{name}", options[:default])
19
29
  end
20
30
  end
21
31
 
@@ -41,6 +51,10 @@ module Importo
41
51
  false
42
52
  end)
43
53
 
54
+ # You can either use GoodJob::Batch or Importo::SidekiqBatchAdapter
55
+ option :batch_adapter, default: lambda { Importo::SidekiqBatchAdapter }, proc: true
56
+ option :import_job_base_class, default: "Object"
57
+
44
58
  # Extra links relevant for this import: { link_name: { icon: 'far fa-..', url: '...' } }
45
59
  option(:admin_extra_links,
46
60
  default: lambda do |import|
@@ -18,6 +18,9 @@ module Importo
18
18
  config.after_initialize do
19
19
  ActiveSupport.on_load(:active_record) do
20
20
  Importo::Import.include(ImportHelpers)
21
+
22
+ # For now put this here to ensure compatibility
23
+ require "importo/adapters/sidekiq_batch_adapter"
21
24
  end
22
25
  end
23
26
  end
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module Importo
4
- VERSION = "3.0.21"
4
+ VERSION = "3.0.22"
5
5
  end
metadata CHANGED
@@ -1,15 +1,15 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: importo
3
3
  version: !ruby/object:Gem::Version
4
- version: 3.0.21
4
+ version: 3.0.22
5
5
  platform: ruby
6
6
  authors:
7
7
  - Andre Meij
8
8
  - Tom de Grunt
9
- autorequire:
9
+ autorequire:
10
10
  bindir: bin
11
11
  cert_chain: []
12
- date: 2024-10-02 00:00:00.000000000 Z
12
+ date: 2025-02-19 00:00:00.000000000 Z
13
13
  dependencies:
14
14
  - !ruby/object:Gem::Dependency
15
15
  name: caxlsx
@@ -25,6 +25,20 @@ dependencies:
25
25
  - - "~>"
26
26
  - !ruby/object:Gem::Version
27
27
  version: 3.0.1
28
+ - !ruby/object:Gem::Dependency
29
+ name: csv
30
+ requirement: !ruby/object:Gem::Requirement
31
+ requirements:
32
+ - - "~>"
33
+ - !ruby/object:Gem::Version
34
+ version: '3.3'
35
+ type: :runtime
36
+ prerelease: false
37
+ version_requirements: !ruby/object:Gem::Requirement
38
+ requirements:
39
+ - - "~>"
40
+ - !ruby/object:Gem::Version
41
+ version: '3.3'
28
42
  - !ruby/object:Gem::Dependency
29
43
  name: rails
30
44
  requirement: !ruby/object:Gem::Requirement
@@ -302,7 +316,6 @@ files:
302
316
  - MIT-LICENSE
303
317
  - README.md
304
318
  - Rakefile
305
- - app/adapters/importo/sidekiq_batch_adapter.rb
306
319
  - app/assets/config/importo_manifest.js
307
320
  - app/assets/javascripts/importo/application.js
308
321
  - app/assets/stylesheets/importo/application.css
@@ -357,6 +370,7 @@ files:
357
370
  - lib/generators/satis/templates/config/initializers/satis.rb
358
371
  - lib/importo.rb
359
372
  - lib/importo/acts_as_import_owner.rb
373
+ - lib/importo/adapters/sidekiq_batch_adapter.rb
360
374
  - lib/importo/configuration.rb
361
375
  - lib/importo/engine.rb
362
376
  - lib/importo/import_column.rb
@@ -367,7 +381,7 @@ homepage: https://github.com/entdec/importo
367
381
  licenses:
368
382
  - MIT
369
383
  metadata: {}
370
- post_install_message:
384
+ post_install_message:
371
385
  rdoc_options: []
372
386
  require_paths:
373
387
  - lib
@@ -383,7 +397,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
383
397
  version: '0'
384
398
  requirements: []
385
399
  rubygems_version: 3.4.10
386
- signing_key:
400
+ signing_key:
387
401
  specification_version: 4
388
402
  summary: Rails engine allowing uploads and imports
389
403
  test_files: []
@@ -1,35 +0,0 @@
1
- module Importo
2
- class SidekiqBatchAdapter
3
- attr_reader :description
4
- attr_accessor :properties
5
- attr_writer :instance
6
-
7
- def initialize
8
- @instance = Sidekiq::Batch.new
9
- end
10
-
11
- delegate :description=, :status, to: :@instance
12
-
13
- def on_success(job)
14
- @instance.on(:complete, job.constantize, properties)
15
- end
16
-
17
- def add
18
- @instance.jobs do
19
- yield
20
- end
21
- end
22
-
23
- def finished?
24
- @instance.status.complete?
25
- end
26
-
27
- class << self
28
- def find(id)
29
- instance = new
30
- instance.instance = Sidekiq::Batch.new(id)
31
- instance
32
- end
33
- end
34
- end
35
- end