active_admin_import 4.1.0 → 5.0.0
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 +4 -4
- data/.gitignore +4 -1
- data/.travis.yml +10 -4
- data/CHANGELOG.md +17 -0
- data/Gemfile +3 -2
- data/active_admin_import.gemspec +4 -4
- data/lib/active_admin_import/dsl.rb +5 -1
- data/lib/active_admin_import/exception.rb +5 -0
- data/lib/active_admin_import/import_result.rb +4 -1
- data/lib/active_admin_import/importer.rb +16 -10
- data/lib/active_admin_import/model.rb +2 -1
- data/lib/active_admin_import/version.rb +1 -1
- data/lib/active_admin_import.rb +1 -0
- data/spec/fixtures/files/authors.csv +3 -3
- data/spec/import_result_spec.rb +11 -10
- data/spec/import_spec.rb +57 -8
- data/spec/spec_helper.rb +1 -0
- data/tasks/test.rake +1 -1
- metadata +15 -15
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: ba919b0429b44accf46af4dcdc52ef1ddcf691a446cddf1bc434b38982c6b0c2
|
4
|
+
data.tar.gz: b54c35f3d81a3b170a8a27b657f1c0b8137c49716fab6b1ba0717845f1b15649
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: d949ae03350ff838eb97856d4c34afb610708dde36bee45d32b56de0bd1bf48a5e0adb4e67aaa549e1e35393cca146be755258fbc213422ab9a91b299769688e
|
7
|
+
data.tar.gz: 4ddc52d5273f06837f54a3806e56ebdad52c2a60581aa452b196de25885697348b13af8f56e27716ed2234b3771072f3f93e365035cdfc02b1539e7aa8385fb1
|
data/.gitignore
CHANGED
data/.travis.yml
CHANGED
data/CHANGELOG.md
CHANGED
@@ -1,4 +1,21 @@
|
|
1
1
|
# Changelog
|
2
|
+
## [5.0.0] - 2021-11-16
|
3
|
+
- Ruby 3 compatibility added #190 | @clinejj
|
4
|
+
- Support for a non UTF-8 file when zip uploading #185| @naokirin
|
5
|
+
- Rails 6 supported #183 | @pnghai
|
6
|
+
- Drop ruby 2.4 support #192 | @Fivell
|
7
|
+
|
8
|
+
|
9
|
+
## [4.2.0] - 2020-02-05
|
10
|
+
- generic exception for import added #175 | @linqueta
|
11
|
+
|
12
|
+
## [4.1.2] - 2019-12-16
|
13
|
+
- allow application/octet-stream content-type #172 | @dmitry-sinina
|
14
|
+
- Allow activerecord-import >= 0.27 #171 | @sagium
|
15
|
+
|
16
|
+
## [4.1.1] - 2019-09-20
|
17
|
+
- Fix column slicing #168 | @doredesign
|
18
|
+
- Handle errors on base #163
|
2
19
|
|
3
20
|
## [4.1.0] - 2019-01-15
|
4
21
|
- Upgrade dependencies: `activerecord-import` to >=0.27.1 | @jkowens
|
data/Gemfile
CHANGED
@@ -6,12 +6,13 @@ gemspec
|
|
6
6
|
|
7
7
|
|
8
8
|
group :test do
|
9
|
-
default_rails_version = "~> 5.
|
9
|
+
default_rails_version = "~> 5.2.4"
|
10
10
|
rails_version = ENV['RAILS'] || default_rails_version
|
11
|
+
gem 'sassc-rails'
|
11
12
|
gem 'rails', rails_version
|
12
13
|
gem 'rspec-rails'
|
13
14
|
gem 'coveralls', require: false # Test coverage website. Go to https://coveralls.io
|
14
|
-
gem
|
15
|
+
gem "sqlite3", "~> 1.4.0"
|
15
16
|
gem 'launchy'
|
16
17
|
gem 'database_cleaner'
|
17
18
|
gem 'capybara'
|
data/active_admin_import.gemspec
CHANGED
@@ -15,8 +15,8 @@ Gem::Specification.new do |gem|
|
|
15
15
|
gem.name = 'active_admin_import'
|
16
16
|
gem.require_paths = ['lib']
|
17
17
|
gem.version = ActiveAdminImport::VERSION
|
18
|
-
gem.add_runtime_dependency 'activerecord-import', '
|
19
|
-
gem.add_runtime_dependency 'rchardet', '
|
20
|
-
gem.add_runtime_dependency 'rubyzip', '
|
21
|
-
gem.add_dependency 'activeadmin', '>= 1.0.0
|
18
|
+
gem.add_runtime_dependency 'activerecord-import', '>= 0.27'
|
19
|
+
gem.add_runtime_dependency 'rchardet', '>= 1.6'
|
20
|
+
gem.add_runtime_dependency 'rubyzip', '>= 1.2'
|
21
|
+
gem.add_dependency 'activeadmin', '>= 1.0.0'
|
22
22
|
end
|
@@ -92,7 +92,11 @@ module ActiveAdminImport
|
|
92
92
|
else
|
93
93
|
instance_exec result, options, &DEFAULT_RESULT_PROC
|
94
94
|
end
|
95
|
-
rescue ActiveRecord::Import::MissingColumnError,
|
95
|
+
rescue ActiveRecord::Import::MissingColumnError,
|
96
|
+
NoMethodError,
|
97
|
+
ActiveRecord::StatementInvalid,
|
98
|
+
CSV::MalformedCSVError,
|
99
|
+
ActiveAdminImport::Exception => e
|
96
100
|
Rails.logger.error(I18n.t('active_admin_import.file_error', message: e.message))
|
97
101
|
Rails.logger.error(e.backtrace.join("\n"))
|
98
102
|
flash[:error] = I18n.t('active_admin_import.file_error', message: e.message[0..200])
|
@@ -33,7 +33,10 @@ module ActiveAdminImport
|
|
33
33
|
limit = options[:limit] || failed.count
|
34
34
|
failed.first(limit).map do |record|
|
35
35
|
errors = record.errors
|
36
|
-
|
36
|
+
failed_values = errors.keys.map do |key|
|
37
|
+
key == :base ? nil : record.public_send(key)
|
38
|
+
end
|
39
|
+
errors.full_messages.zip(failed_values).map { |ms| ms.compact.join(' - ') }.join(', ')
|
37
40
|
end.join(' ; ')
|
38
41
|
end
|
39
42
|
end
|
@@ -37,7 +37,7 @@ module ActiveAdminImport
|
|
37
37
|
end
|
38
38
|
|
39
39
|
def cycle(lines)
|
40
|
-
@csv_lines = CSV.parse(lines.join,
|
40
|
+
@csv_lines = CSV.parse(lines.join, **@csv_options)
|
41
41
|
import_result.add(batch_import, lines.count)
|
42
42
|
end
|
43
43
|
|
@@ -70,7 +70,7 @@ module ActiveAdminImport
|
|
70
70
|
end
|
71
71
|
end
|
72
72
|
|
73
|
-
# Use
|
73
|
+
# Use this method when CSV file contains unnecessary columns
|
74
74
|
#
|
75
75
|
# Example:
|
76
76
|
#
|
@@ -81,16 +81,22 @@ module ActiveAdminImport
|
|
81
81
|
# end
|
82
82
|
#
|
83
83
|
def batch_slice_columns(slice_columns)
|
84
|
-
use_indexes
|
85
|
-
|
86
|
-
|
84
|
+
# Only set @use_indexes for the first batch so that @use_indexes are in correct
|
85
|
+
# position for subsequent batches
|
86
|
+
unless defined?(@use_indexes)
|
87
|
+
@use_indexes = []
|
88
|
+
headers.values.each_with_index do |val, index|
|
89
|
+
@use_indexes << index if val.in?(slice_columns)
|
90
|
+
end
|
91
|
+
return csv_lines if @use_indexes.empty?
|
92
|
+
|
93
|
+
# slice CSV headers
|
94
|
+
@headers = headers.to_a.values_at(*@use_indexes).to_h
|
87
95
|
end
|
88
|
-
|
89
|
-
# slice CSV headers
|
90
|
-
@headers = headers.to_a.values_at(*use_indexes).to_h
|
96
|
+
|
91
97
|
# slice CSV values
|
92
98
|
csv_lines.map! do |line|
|
93
|
-
line.values_at(
|
99
|
+
line.values_at(*@use_indexes)
|
94
100
|
end
|
95
101
|
end
|
96
102
|
|
@@ -109,7 +115,7 @@ module ActiveAdminImport
|
|
109
115
|
batch_size = options[:batch_size].to_i
|
110
116
|
File.open(file.path) do |f|
|
111
117
|
# capture headers if not exist
|
112
|
-
prepare_headers { CSV.parse(f.readline,
|
118
|
+
prepare_headers { CSV.parse(f.readline, **@csv_options).first }
|
113
119
|
f.each_line do |line|
|
114
120
|
lines << line if line.present?
|
115
121
|
if lines.size == batch_size || f.eof?
|
@@ -21,6 +21,7 @@ module ActiveAdminImport
|
|
21
21
|
application/csv
|
22
22
|
application/vnd.ms-excel
|
23
23
|
application/vnd.msexcel
|
24
|
+
application/octet-stream
|
24
25
|
text/tsv
|
25
26
|
text/x-tsv
|
26
27
|
text/tab-separated-values
|
@@ -109,7 +110,7 @@ module ActiveAdminImport
|
|
109
110
|
|
110
111
|
def unzip_file
|
111
112
|
Zip::File.open(file_path) do |zip_file|
|
112
|
-
self.file = Tempfile.new(CONST::TMP_FILE)
|
113
|
+
self.file = Tempfile.new(CONST::TMP_FILE, binmode: true)
|
113
114
|
data = zip_file.entries.select(&:file?).first.get_input_stream.read
|
114
115
|
file << data
|
115
116
|
file.close
|
data/lib/active_admin_import.rb
CHANGED
@@ -3,6 +3,7 @@ require 'activerecord-import'
|
|
3
3
|
require 'active_admin'
|
4
4
|
require 'active_admin_import/version'
|
5
5
|
require 'active_admin_import/engine'
|
6
|
+
require 'active_admin_import/exception'
|
6
7
|
require 'active_admin_import/import_result'
|
7
8
|
require 'active_admin_import/options'
|
8
9
|
require 'active_admin_import/dsl'
|
@@ -1,3 +1,3 @@
|
|
1
|
-
Name,Last name
|
2
|
-
|
3
|
-
|
1
|
+
Birthday,Name,Last name
|
2
|
+
1986-05-01,John,Doe
|
3
|
+
1988-11-16,Jane,Roe
|
data/spec/import_result_spec.rb
CHANGED
@@ -5,17 +5,18 @@ describe ActiveAdminImport::ImportResult do
|
|
5
5
|
context 'failed_message' do
|
6
6
|
let(:import_result) { ActiveAdminImport::ImportResult.new }
|
7
7
|
|
8
|
-
before do
|
9
|
-
Author.create(name: 'John', last_name: 'Doe')
|
10
|
-
Author.create(name: 'Jane', last_name: 'Roe')
|
11
8
|
|
9
|
+
let(:failed_instances) do
|
10
|
+
[
|
11
|
+
Author.new(last_name: 'Doe').tap {|r| r.errors.add(:last_name, :taken) },
|
12
|
+
Author.new(name: "", last_name: 'Doe').tap {|r| r.errors.add(:name, :blank); r.errors.add(:last_name, :taken) },
|
13
|
+
Author.new.tap {|r| r.errors.add(:base, 'custom') }
|
14
|
+
]
|
15
|
+
end
|
16
|
+
|
17
|
+
before do
|
12
18
|
@result = double \
|
13
|
-
failed_instances:
|
14
|
-
# {:last_name=>["has already been taken"]}
|
15
|
-
Author.create(name: 'Jim', last_name: 'Doe'),
|
16
|
-
# {:name=>["can't be blank"], :last_name=>["has already been taken"]}
|
17
|
-
Author.create(name: nil, last_name: 'Doe')
|
18
|
-
]
|
19
|
+
failed_instances: failed_instances
|
19
20
|
end
|
20
21
|
|
21
22
|
it 'should work without any failed instances' do
|
@@ -26,7 +27,7 @@ describe ActiveAdminImport::ImportResult do
|
|
26
27
|
import_result.add(@result, 4)
|
27
28
|
expect(import_result.failed_message)
|
28
29
|
.to eq(
|
29
|
-
"Last name has already been taken - Doe ; Name can't be blank - , Last name has already been taken - Doe"
|
30
|
+
"Last name has already been taken - Doe ; Name can't be blank - , Last name has already been taken - Doe ; custom"
|
30
31
|
)
|
31
32
|
end
|
32
33
|
|
data/spec/import_spec.rb
CHANGED
@@ -371,6 +371,20 @@ describe 'import', type: :feature do
|
|
371
371
|
end
|
372
372
|
end
|
373
373
|
end
|
374
|
+
|
375
|
+
context 'when zipped with Win1251 file' do
|
376
|
+
let(:options) do
|
377
|
+
attributes = { force_encoding: :auto }
|
378
|
+
{ template_object: ActiveAdminImport::Model.new(attributes) }
|
379
|
+
end
|
380
|
+
it 'should import file' do
|
381
|
+
with_zipped_csv(:authors_win1251_win_endline) do
|
382
|
+
upload_file!(:authors_win1251_win_endline, :zip)
|
383
|
+
expect(page).to have_content 'Successfully imported 2 authors'
|
384
|
+
expect(Author.count).to eq(2)
|
385
|
+
end
|
386
|
+
end
|
387
|
+
end
|
374
388
|
end
|
375
389
|
|
376
390
|
context 'with different header attribute names' do
|
@@ -430,15 +444,40 @@ describe 'import', type: :feature do
|
|
430
444
|
upload_file!(:authors)
|
431
445
|
expect(Author.count).to eq(2)
|
432
446
|
end
|
447
|
+
|
448
|
+
context 'when the option before_import raises a ActiveAdminImport::Exception' do
|
449
|
+
let(:options) { { before_import: ->(_) { raise ActiveAdminImport::Exception, 'error message' } } }
|
450
|
+
|
451
|
+
before { upload_file!(:authors) }
|
452
|
+
|
453
|
+
it 'should show error' do
|
454
|
+
expect(page).to have_content I18n.t('active_admin_import.file_error', message: 'error message')
|
455
|
+
expect(Author.count).to eq(0)
|
456
|
+
end
|
457
|
+
end
|
458
|
+
|
459
|
+
context 'when the option before_batch_import raises a ActiveAdminImport::Exception' do
|
460
|
+
let(:options) { { before_batch_import: ->(_) { raise ActiveAdminImport::Exception, 'error message' } } }
|
461
|
+
|
462
|
+
before { upload_file!(:authors) }
|
463
|
+
|
464
|
+
it 'should show error' do
|
465
|
+
expect(page).to have_content I18n.t('active_admin_import.file_error', message: 'error message')
|
466
|
+
expect(Author.count).to eq(0)
|
467
|
+
end
|
468
|
+
end
|
433
469
|
end
|
434
470
|
end
|
435
471
|
|
436
472
|
context "with slice_columns option" do
|
473
|
+
let(:batch_size) { 2 }
|
474
|
+
|
437
475
|
before do
|
438
476
|
add_author_resource template_object: ActiveAdminImport::Model.new,
|
439
477
|
before_batch_import: lambda { |importer|
|
440
478
|
importer.batch_slice_columns(slice_columns)
|
441
|
-
}
|
479
|
+
},
|
480
|
+
batch_size: batch_size
|
442
481
|
visit "/admin/authors/import"
|
443
482
|
upload_file!(:authors)
|
444
483
|
end
|
@@ -446,13 +485,23 @@ describe 'import', type: :feature do
|
|
446
485
|
context "slice last column and superfluous column" do
|
447
486
|
let(:slice_columns) { %w(name last_name not_existing_column) }
|
448
487
|
|
449
|
-
|
450
|
-
|
451
|
-
|
452
|
-
[
|
453
|
-
|
454
|
-
|
455
|
-
|
488
|
+
shared_examples_for "birthday column removed" do
|
489
|
+
it "should not fill `birthday` column" do
|
490
|
+
expect(Author.pluck(:name, :last_name, :birthday)).to match_array(
|
491
|
+
[
|
492
|
+
["Jane", "Roe", nil],
|
493
|
+
["John", "Doe", nil]
|
494
|
+
]
|
495
|
+
)
|
496
|
+
end
|
497
|
+
end
|
498
|
+
|
499
|
+
it_behaves_like "birthday column removed"
|
500
|
+
|
501
|
+
context "when doing more than one batch" do
|
502
|
+
let(:batch_size) { 1 }
|
503
|
+
|
504
|
+
it_behaves_like "birthday column removed"
|
456
505
|
end
|
457
506
|
end
|
458
507
|
|
data/spec/spec_helper.rb
CHANGED
@@ -20,6 +20,7 @@ system 'rake setup' unless File.exist?(ENV['RAILS_ROOT'])
|
|
20
20
|
require 'active_model'
|
21
21
|
# require ActiveRecord to ensure that Ransack loads correctly
|
22
22
|
require 'active_record'
|
23
|
+
require 'action_view'
|
23
24
|
require 'active_admin'
|
24
25
|
ActiveAdmin.application.load_paths = [ENV['RAILS_ROOT'] + '/app/admin']
|
25
26
|
require ENV['RAILS_ROOT'] + '/config/environment.rb'
|
data/tasks/test.rake
CHANGED
@@ -3,5 +3,5 @@ desc 'Creates a test rails app for the specs to run against'
|
|
3
3
|
task :setup do
|
4
4
|
require 'rails/version'
|
5
5
|
system('mkdir spec/rails') unless File.exist?('spec/rails')
|
6
|
-
system "bundle exec rails new spec/rails/rails-#{Rails::VERSION::STRING} -m spec/support/rails_template.rb --skip-spring --skip-turbolinks"
|
6
|
+
system "bundle exec rails new spec/rails/rails-#{Rails::VERSION::STRING} -m spec/support/rails_template.rb --skip-spring --skip-turbolinks --skip-bootsnap"
|
7
7
|
end
|
metadata
CHANGED
@@ -1,55 +1,55 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: active_admin_import
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version:
|
4
|
+
version: 5.0.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Igor Fedoronchuk
|
8
|
-
autorequire:
|
8
|
+
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date:
|
11
|
+
date: 2021-11-17 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: activerecord-import
|
15
15
|
requirement: !ruby/object:Gem::Requirement
|
16
16
|
requirements:
|
17
|
-
- - "
|
17
|
+
- - ">="
|
18
18
|
- !ruby/object:Gem::Version
|
19
19
|
version: '0.27'
|
20
20
|
type: :runtime
|
21
21
|
prerelease: false
|
22
22
|
version_requirements: !ruby/object:Gem::Requirement
|
23
23
|
requirements:
|
24
|
-
- - "
|
24
|
+
- - ">="
|
25
25
|
- !ruby/object:Gem::Version
|
26
26
|
version: '0.27'
|
27
27
|
- !ruby/object:Gem::Dependency
|
28
28
|
name: rchardet
|
29
29
|
requirement: !ruby/object:Gem::Requirement
|
30
30
|
requirements:
|
31
|
-
- - "
|
31
|
+
- - ">="
|
32
32
|
- !ruby/object:Gem::Version
|
33
33
|
version: '1.6'
|
34
34
|
type: :runtime
|
35
35
|
prerelease: false
|
36
36
|
version_requirements: !ruby/object:Gem::Requirement
|
37
37
|
requirements:
|
38
|
-
- - "
|
38
|
+
- - ">="
|
39
39
|
- !ruby/object:Gem::Version
|
40
40
|
version: '1.6'
|
41
41
|
- !ruby/object:Gem::Dependency
|
42
42
|
name: rubyzip
|
43
43
|
requirement: !ruby/object:Gem::Requirement
|
44
44
|
requirements:
|
45
|
-
- - "
|
45
|
+
- - ">="
|
46
46
|
- !ruby/object:Gem::Version
|
47
47
|
version: '1.2'
|
48
48
|
type: :runtime
|
49
49
|
prerelease: false
|
50
50
|
version_requirements: !ruby/object:Gem::Requirement
|
51
51
|
requirements:
|
52
|
-
- - "
|
52
|
+
- - ">="
|
53
53
|
- !ruby/object:Gem::Version
|
54
54
|
version: '1.2'
|
55
55
|
- !ruby/object:Gem::Dependency
|
@@ -58,14 +58,14 @@ dependencies:
|
|
58
58
|
requirements:
|
59
59
|
- - ">="
|
60
60
|
- !ruby/object:Gem::Version
|
61
|
-
version: 1.0.0
|
61
|
+
version: 1.0.0
|
62
62
|
type: :runtime
|
63
63
|
prerelease: false
|
64
64
|
version_requirements: !ruby/object:Gem::Requirement
|
65
65
|
requirements:
|
66
66
|
- - ">="
|
67
67
|
- !ruby/object:Gem::Version
|
68
|
-
version: 1.0.0
|
68
|
+
version: 1.0.0
|
69
69
|
description: The most efficient way to import for Active Admin
|
70
70
|
email:
|
71
71
|
- fedoronchuk@gmail.com
|
@@ -99,6 +99,7 @@ files:
|
|
99
99
|
- lib/active_admin_import/authorization.rb
|
100
100
|
- lib/active_admin_import/dsl.rb
|
101
101
|
- lib/active_admin_import/engine.rb
|
102
|
+
- lib/active_admin_import/exception.rb
|
102
103
|
- lib/active_admin_import/import_result.rb
|
103
104
|
- lib/active_admin_import/importer.rb
|
104
105
|
- lib/active_admin_import/model.rb
|
@@ -133,7 +134,7 @@ homepage: http://github.com/Fivell/active_admin_import
|
|
133
134
|
licenses:
|
134
135
|
- MIT
|
135
136
|
metadata: {}
|
136
|
-
post_install_message:
|
137
|
+
post_install_message:
|
137
138
|
rdoc_options: []
|
138
139
|
require_paths:
|
139
140
|
- lib
|
@@ -148,9 +149,8 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
148
149
|
- !ruby/object:Gem::Version
|
149
150
|
version: '0'
|
150
151
|
requirements: []
|
151
|
-
|
152
|
-
|
153
|
-
signing_key:
|
152
|
+
rubygems_version: 3.1.6
|
153
|
+
signing_key:
|
154
154
|
specification_version: 4
|
155
155
|
summary: ActiveAdmin import based on activerecord-import gem.
|
156
156
|
test_files:
|