cascade-rb 0.2.3 → 0.3.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.
Files changed (53) hide show
  1. checksums.yaml +4 -4
  2. data/.hound.yml +1 -1
  3. data/.rubocop.yml +11 -0
  4. data/.travis.yml +11 -0
  5. data/Gemfile +3 -1
  6. data/README.md +2 -25
  7. data/Rakefile +7 -4
  8. data/cascade.gemspec +22 -21
  9. data/lib/cascade.rb +6 -7
  10. data/lib/cascade/columns_matching.rb +14 -13
  11. data/lib/cascade/complex_fields.rb +5 -3
  12. data/lib/cascade/complex_fields/array_processor.rb +2 -0
  13. data/lib/cascade/complex_fields/boolean.rb +3 -1
  14. data/lib/cascade/complex_fields/currency.rb +8 -4
  15. data/lib/cascade/concerns/statistics_collectible.rb +3 -1
  16. data/lib/cascade/data_parser.rb +4 -2
  17. data/lib/cascade/error_handler.rb +4 -7
  18. data/lib/cascade/exceptions.rb +5 -3
  19. data/lib/cascade/exceptions/unknown_presenter_type.rb +2 -0
  20. data/lib/cascade/exceptions/unsupported_component.rb +3 -1
  21. data/lib/cascade/exceptions/wrong_mapping_format.rb +2 -0
  22. data/lib/cascade/helpers/hash.rb +2 -0
  23. data/lib/cascade/registry.rb +6 -3
  24. data/lib/cascade/row_processor.rb +23 -22
  25. data/lib/cascade/statistics.rb +4 -2
  26. data/lib/cascade/statistics_stores.rb +5 -3
  27. data/lib/cascade/statistics_stores/abstract_store.rb +2 -0
  28. data/lib/cascade/statistics_stores/array_store.rb +2 -0
  29. data/lib/cascade/statistics_stores/counter_store.rb +2 -0
  30. data/lib/cascade/version.rb +3 -1
  31. data/spec/integration_spec.rb +70 -0
  32. data/spec/lib/columns_matching_spec.rb +18 -26
  33. data/spec/lib/complex_fields/array_processor_spec.rb +6 -4
  34. data/spec/lib/complex_fields/boolean_spec.rb +8 -6
  35. data/spec/lib/complex_fields/currency_spec.rb +11 -9
  36. data/spec/lib/concerns/statistics_collectible_spec.rb +6 -4
  37. data/spec/lib/data_parser_spec.rb +14 -11
  38. data/spec/lib/error_handler_spec.rb +21 -15
  39. data/spec/lib/exceptions/unknown_presenter_type_spec.rb +5 -3
  40. data/spec/lib/exceptions/unsupported_component_spec.rb +10 -8
  41. data/spec/lib/exceptions/wrong_mapping_format_spec.rb +5 -3
  42. data/spec/lib/helpers/hash_spec.rb +7 -5
  43. data/spec/lib/registry_spec.rb +9 -8
  44. data/spec/lib/row_processor_spec.rb +33 -33
  45. data/spec/lib/statistics_spec.rb +14 -12
  46. data/spec/lib/statistics_stores/abstract_store_spec.rb +7 -5
  47. data/spec/lib/statistics_stores/array_store_spec.rb +8 -6
  48. data/spec/lib/statistics_stores/counter_store_spec.rb +8 -6
  49. data/spec/spec_helper.rb +16 -15
  50. metadata +28 -28
  51. data/.ruby-style.yml +0 -1063
  52. data/lib/cascade/helpers/configuration.rb +0 -32
  53. data/spec/lib/helpers/configuration_spec.rb +0 -36
@@ -1,5 +1,7 @@
1
- require "singleton"
2
- require "cascade/statistics_stores"
1
+ # frozen_string_literal: true
2
+
3
+ require 'singleton'
4
+ require 'cascade/statistics_stores'
3
5
 
4
6
  module Cascade
5
7
  class Statistics
@@ -1,3 +1,5 @@
1
- require "cascade/statistics_stores/abstract_store"
2
- require "cascade/statistics_stores/counter_store"
3
- require "cascade/statistics_stores/array_store"
1
+ # frozen_string_literal: true
2
+
3
+ require 'cascade/statistics_stores/abstract_store'
4
+ require 'cascade/statistics_stores/counter_store'
5
+ require 'cascade/statistics_stores/array_store'
@@ -1,3 +1,5 @@
1
+ # frozen_string_literal: true
2
+
1
3
  module Cascade
2
4
  module StatisticsStores
3
5
  class AbstractStore
@@ -1,3 +1,5 @@
1
+ # frozen_string_literal: true
2
+
1
3
  module Cascade
2
4
  module StatisticsStores
3
5
  class ArrayStore < AbstractStore
@@ -1,3 +1,5 @@
1
+ # frozen_string_literal: true
2
+
1
3
  module Cascade
2
4
  module StatisticsStores
3
5
  class CounterStore < AbstractStore
@@ -1,4 +1,6 @@
1
+ # frozen_string_literal: true
2
+
1
3
  module Cascade
2
4
  # current gem version
3
- VERSION = "0.2.3"
5
+ VERSION = '0.3.0'
4
6
  end
@@ -0,0 +1,70 @@
1
+ # frozen_string_literal: true
2
+
3
+ require 'spec_helper'
4
+
5
+ describe Cascade do
6
+ let(:date_parser) { ->(value) { Date.parse(value) } }
7
+ let(:int_parser) { ->(value) { Integer(value) } }
8
+
9
+ class ExampleDateSaver
10
+ def initialize
11
+ @result = []
12
+ end
13
+
14
+ attr_reader :result
15
+
16
+ def call(row_description, _row_number)
17
+ @result << row_description.values
18
+ end
19
+ end
20
+
21
+ let(:data_provider) do
22
+ [
23
+ ['2000-01-01', '1000', 'uno'],
24
+ ['2001-01-01', '2000', 'dos'],
25
+ ['2002-01-01', '3000', 'tres']
26
+ ]
27
+ end
28
+
29
+ let(:columns_matching) do
30
+ Cascade::ColumnsMatching.new(content: {
31
+ date: :date,
32
+ points: :integer,
33
+ spanish: :string
34
+ })
35
+ end
36
+
37
+ let(:row_processor) do
38
+ Cascade::RowProcessor.new(
39
+ columns_matching: columns_matching,
40
+ ext_presenters: { date: date_parser, integer: int_parser }
41
+ )
42
+ end
43
+
44
+ let(:data_saver) { ExampleDateSaver.new }
45
+
46
+ let(:expected_result) do
47
+ [
48
+ [Date.new(2000, 1, 1), 1000, 'uno'],
49
+ [Date.new(2001, 1, 1), 2000, 'dos'],
50
+ [Date.new(2002, 1, 1), 3000, 'tres']
51
+ ]
52
+ end
53
+
54
+ it 'works with empty example' do
55
+ Cascade::DataParser.new(
56
+ data_provider: data_provider,
57
+ data_saver: ->(*_any) {}
58
+ ).call
59
+ end
60
+
61
+ it 'checks main cascade work-flow' do
62
+ Cascade::DataParser.new(
63
+ data_provider: data_provider,
64
+ row_processor: row_processor,
65
+ data_saver: data_saver
66
+ ).call
67
+
68
+ assert_equal expected_result, data_saver.result
69
+ end
70
+ end
@@ -1,49 +1,41 @@
1
- require "spec_helper"
2
- require "cascade/columns_matching"
1
+ # frozen_string_literal: true
2
+
3
+ require 'spec_helper'
4
+ require 'cascade/columns_matching'
3
5
 
4
6
  describe Cascade::ColumnsMatching do
5
7
  def described_class
6
8
  Cascade::ColumnsMatching
7
9
  end
8
- subject { described_class.new }
9
10
 
10
- context "on settings file parsing" do
11
- subject { described_class.new(filepath: "config/columns_match.yml") }
11
+ context 'on settings file parsing' do
12
+ subject { described_class.new(filepath: 'config/columns_match.yml') }
12
13
 
13
- it "raise error if columns matching file doesnt contain mapping key" do
14
- mock(YAML).load_file("config/columns_match.yml") { {} }
14
+ it "raise error if columns matching file doesn't contain mapping key" do
15
+ mock(YAML).load_file('config/columns_match.yml') { {} }
15
16
  assert_raises(Cascade::WrongMappingFormat) { subject }
16
17
  end
17
18
 
18
- it "raise error if columns matching file doesnt contain any info" do
19
- mock(YAML).load_file("config/columns_match.yml") { nil }
19
+ it "raise error if columns matching file doesn't contain any info" do
20
+ mock(YAML).load_file('config/columns_match.yml') { nil }
20
21
  assert_raises(Cascade::WrongMappingFormat) { subject }
21
22
  end
22
23
  end
23
24
 
24
- context "after file parsed" do
25
- before do
26
- stub(YAML).load_file do
27
- {
28
- "mapping" => {
29
- "name" => "string",
30
- "class" => "string"
31
- }
32
- }
33
- end
34
- end
25
+ context 'after file parsed' do
26
+ subject { described_class.new(content: { name: 'string' }) }
35
27
 
36
- context "#supported_keys" do
28
+ context '#supported_keys' do
37
29
  it { subject.must_respond_to(:supported_keys) }
38
- it "return array" do
30
+
31
+ it 'return array' do
39
32
  subject.supported_keys.must_be_kind_of Array
40
33
  end
41
34
  end
42
35
 
43
- context "#column_type" do
44
- it "return curresponding value for passed column value" do
45
- assert_equal :string,
46
- described_class.new(content: { name: "string" }).column_type(:name)
36
+ context '#column_type' do
37
+ it 'return curresponding value for passed column value' do
38
+ assert_equal :string, subject.column_type(:name)
47
39
  end
48
40
  end
49
41
  end
@@ -1,15 +1,17 @@
1
- require "spec_helper"
2
- require "cascade/complex_fields/array_processor"
1
+ # frozen_string_literal: true
2
+
3
+ require 'spec_helper'
4
+ require 'cascade/complex_fields/array_processor'
3
5
 
4
6
  describe Cascade::ComplexFields::ArrayProcessor do
5
7
  def described_class
6
8
  Cascade::ComplexFields::ArrayProcessor
7
9
  end
8
10
 
9
- let(:processor) { -> (value) { value + 1 } }
11
+ let(:processor) { ->(value) { value + 1 } }
10
12
  let(:subject) { described_class.new(processor) }
11
13
 
12
- it "return processed array" do
14
+ it 'return processed array' do
13
15
  assert_equal subject.call([1, 2, 3]), [2, 3, 4]
14
16
  end
15
17
  end
@@ -1,5 +1,7 @@
1
- require "spec_helper"
2
- require "cascade/complex_fields/boolean"
1
+ # frozen_string_literal: true
2
+
3
+ require 'spec_helper'
4
+ require 'cascade/complex_fields/boolean'
3
5
 
4
6
  describe Cascade::ComplexFields::Boolean do
5
7
  def described_class
@@ -8,14 +10,14 @@ describe Cascade::ComplexFields::Boolean do
8
10
 
9
11
  let(:subject) { described_class.new }
10
12
 
11
- it "return true value for values that seems like true" do
12
- ["True", "true", "x", "+", true].each do |value|
13
+ it 'return true value for values that seems like true' do
14
+ ['True', 'true', 'x', '+', true].each do |value|
13
15
  assert subject.call(value)
14
16
  end
15
17
  end
16
18
 
17
- it "return false value for values that cant be true" do
18
- ["false", false, nil, "", "some value"].each do |value|
19
+ it 'return false value for values that cant be true' do
20
+ ['false', false, nil, '', 'some value'].each do |value|
19
21
  refute subject.call(value)
20
22
  end
21
23
  end
@@ -1,5 +1,7 @@
1
- require "spec_helper"
2
- require "cascade/complex_fields/currency"
1
+ # frozen_string_literal: true
2
+
3
+ require 'spec_helper'
4
+ require 'cascade/complex_fields/currency'
3
5
 
4
6
  describe Cascade::ComplexFields::Currency do
5
7
  def described_class
@@ -8,18 +10,18 @@ describe Cascade::ComplexFields::Currency do
8
10
 
9
11
  subject { described_class.new }
10
12
 
11
- describe "parse" do
13
+ describe 'parse' do
12
14
  it "return nil if input string isn't number" do
13
- assert_nil subject.call("0o")
15
+ assert_nil subject.call('0o')
14
16
  end
15
17
 
16
- it "prepare string to use it as bignum" do
17
- assert_kind_of BigDecimal, subject.call("1 123 123 45")
18
- assert_kind_of BigDecimal, subject.call("1 123, 123 45")
18
+ it 'prepare string to use it as bignum' do
19
+ assert_kind_of BigDecimal, subject.call('1 123 123 45')
20
+ assert_kind_of BigDecimal, subject.call('1 123, 123 45')
19
21
  end
20
22
 
21
- it "return zero if field is empty" do
22
- assert_nil subject.call("")
23
+ it 'return zero if field is empty' do
24
+ assert_nil subject.call('')
23
25
  assert_nil subject.call(nil)
24
26
  end
25
27
  end
@@ -1,15 +1,17 @@
1
- require "spec_helper"
2
- require "cascade/concerns/statistics_collectible"
1
+ # frozen_string_literal: true
2
+
3
+ require 'spec_helper'
4
+ require 'cascade/concerns/statistics_collectible'
3
5
 
4
6
  describe Cascade::StatisticsCollectible do
5
7
  class ExtendableClass; include Cascade::StatisticsCollectible; end
6
8
  subject { ExtendableClass.new }
7
9
 
8
- it "defines helper for access to statics class" do
10
+ it 'defines helper for access to statics class' do
9
11
  assert_instance_of Cascade::Statistics, subject.statistics
10
12
  end
11
13
 
12
- it "delegates register_action method to statistics" do
14
+ it 'delegates register_action method to statistics' do
13
15
  assert_respond_to subject, :register_action
14
16
  end
15
17
  end
@@ -1,5 +1,7 @@
1
- require "spec_helper"
2
- require "cascade/data_parser"
1
+ # frozen_string_literal: true
2
+
3
+ require 'spec_helper'
4
+ require 'cascade/data_parser'
3
5
 
4
6
  describe Cascade::DataParser do
5
7
  def described_class
@@ -7,29 +9,30 @@ describe Cascade::DataParser do
7
9
  end
8
10
 
9
11
  class FakeDataProvider
10
- def self.open(_)
12
+ def self.open(_any)
11
13
  [
12
- ["Sally Whittaker", "2018", "McCarren House", "312",
13
- "3.75", "France", "+", "123.123"],
14
- ["Jeff Smith", "2018", "Prescott House", "17-D", "3.20",
15
- "Austria", "45.12"]
14
+ ['Sally Whittaker', '2018', 'McCarren House', '312',
15
+ '3.75', 'France', '+', '123.123'],
16
+ ['Jeff Smith', '2018', 'Prescott House', '17-D', '3.20',
17
+ 'Austria', '45.12']
16
18
  ]
17
19
  end
18
20
  end
19
21
 
20
- let(:filename) { "spec/examples/data_test.txt" }
22
+ let(:filename) { 'spec/examples/data_test.txt' }
21
23
  let(:data_provider) { FakeDataProvider.open(filename) }
22
24
 
23
25
  before do
24
26
  @processor_calls_count = 0
25
27
  @data_saves_count = 0
26
28
  row_processor = ->(_row) { @processor_calls_count += 1 }
27
- data_saver = ->(*) { @data_saves_count += 1 }
29
+ data_saver = ->(*) { @data_saves_count += 1 }
28
30
  @parser = described_class.new(row_processor: row_processor,
29
- data_saver: data_saver, data_provider: data_provider)
31
+ data_saver: data_saver,
32
+ data_provider: data_provider)
30
33
  end
31
34
 
32
- it "calls row processor for each file line" do
35
+ it 'calls row processor for each file line' do
33
36
  @parser.call
34
37
  assert_equal @processor_calls_count, 2
35
38
  assert_equal @data_saves_count, 2
@@ -1,5 +1,7 @@
1
- require "spec_helper"
2
- require "cascade/error_handler"
1
+ # frozen_string_literal: true
2
+
3
+ require 'spec_helper'
4
+ require 'cascade/error_handler'
3
5
 
4
6
  describe Cascade::ErrorHandler do
5
7
  def described_class
@@ -14,27 +16,31 @@ describe Cascade::ErrorHandler do
14
16
  end
15
17
  let(:row) { Struct.new(:fields) }
16
18
 
17
- subject { described_class.new(error_store: error_store) }
19
+ context 'when raise_parse_errors setting is false' do
20
+ subject { described_class.new(error_store: error_store) }
21
+
22
+ it 'catches handling exceptions and send info to error store' do
23
+ subject.with_errors_handling(row) { raise IndexError }
24
+ assert_includes @errors, [row, IndexError.to_s]
25
+ end
26
+ end
18
27
 
19
- Cascade::ErrorHandler::HANDLING_EXCEPTIONS.each do |exception|
20
- it "catch #{exception} and send info to error store" do
21
- subject.with_errors_handling(row) { raise exception }
22
- assert_includes @errors, [row, exception.to_s]
28
+ context 'when raise_parse_errors setting is true' do
29
+ subject do
30
+ described_class.new(error_store: error_store, raise_parse_errors: true)
23
31
  end
24
32
 
25
- it "raises #{exception} if raise_parse_errors setting is true" do
26
- described_class.stub(:raise_parse_errors, true) do
27
- assert_raises(exception) do
28
- subject.with_errors_handling(row) { raise exception }
29
- end
33
+ it 'raises for handling exceptions' do
34
+ assert_raises(IndexError) do
35
+ subject.with_errors_handling(row) { raise IndexError }
30
36
  end
31
37
  end
32
38
  end
33
39
 
34
- describe "DEFAULT_ERROR_STORE" do
35
- it "create new array and push row with reason" do
40
+ describe 'DEFAULT_ERROR_STORE' do
41
+ it 'create new array and push row with reason' do
36
42
  result = Cascade::ErrorHandler::DEFAULT_ERROR_STORE.call(:row, :reason)
37
- assert_includes result, [:row, "reason"]
43
+ assert_includes result, [:row, 'reason']
38
44
  end
39
45
  end
40
46
  end
@@ -1,9 +1,11 @@
1
- require "spec_helper"
2
- require "cascade/exceptions/unknown_presenter_type"
1
+ # frozen_string_literal: true
2
+
3
+ require 'spec_helper'
4
+ require 'cascade/exceptions/unknown_presenter_type'
3
5
 
4
6
  describe Cascade::UnknownPresenterType do
5
7
  subject { Cascade::UnknownPresenterType.new }
6
- it "exception raisable" do
8
+ it 'exception raisable' do
7
9
  assert_respond_to subject, :exception
8
10
  end
9
11
  end
@@ -1,19 +1,21 @@
1
- require "spec_helper"
2
- require "cascade/exceptions/unsupported_component"
1
+ # frozen_string_literal: true
2
+
3
+ require 'spec_helper'
4
+ require 'cascade/exceptions/unsupported_component'
3
5
 
4
6
  describe Cascade::UnsupportedComponent do
5
7
  subject { Cascade::UnsupportedComponent.new }
6
- it "exception raisable" do
8
+ it 'exception raisable' do
7
9
  assert_respond_to subject, :exception
8
10
  end
9
11
 
10
- context "#message" do
11
- it "uses passed message" do
12
- subject = Cascade::UnsupportedComponent.new("custom_message")
13
- assert_equal subject.message, "custom_message"
12
+ context '#message' do
13
+ it 'uses passed message' do
14
+ subject = Cascade::UnsupportedComponent.new('custom_message')
15
+ assert_equal subject.message, 'custom_message'
14
16
  end
15
17
 
16
- it "uses default message if not passed" do
18
+ it 'uses default message if not passed' do
17
19
  assert_equal subject.message, Cascade::UnsupportedComponent::MESSAGE
18
20
  end
19
21
  end