darthjee-core_ext 1.5.6 → 1.6.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 (68) hide show
  1. checksums.yaml +4 -4
  2. data/.circleci/config.yml +14 -0
  3. data/.rubocop.yml +17 -0
  4. data/.rubocop_todo.yml +12 -0
  5. data/Gemfile +2 -1
  6. data/Rakefile +2 -0
  7. data/core_ext.gemspec +6 -3
  8. data/lib/darthjee/core_ext/array/hash_builder.rb +21 -13
  9. data/lib/darthjee/core_ext/array.rb +4 -2
  10. data/lib/darthjee/core_ext/date.rb +2 -0
  11. data/lib/darthjee/core_ext/enumerable.rb +5 -3
  12. data/lib/darthjee/core_ext/hash/chain_fetcher.rb +33 -0
  13. data/lib/darthjee/core_ext/hash/deep_hash_constructor.rb +62 -60
  14. data/lib/darthjee/core_ext/hash/key_changer.rb +64 -54
  15. data/lib/darthjee/core_ext/hash/keys_sorter.rb +31 -0
  16. data/lib/darthjee/core_ext/hash/squasher.rb +31 -0
  17. data/lib/darthjee/core_ext/hash/to_hash_mapper.rb +21 -0
  18. data/lib/darthjee/core_ext/hash/value_changer.rb +48 -44
  19. data/lib/darthjee/core_ext/hash.rb +28 -58
  20. data/lib/darthjee/core_ext/math.rb +4 -2
  21. data/lib/darthjee/core_ext/numeric.rb +5 -3
  22. data/lib/darthjee/core_ext/object/default_value.rb +2 -1
  23. data/lib/darthjee/core_ext/object.rb +2 -0
  24. data/lib/darthjee/core_ext/symbol.rb +2 -0
  25. data/lib/darthjee/core_ext/time.rb +2 -0
  26. data/lib/darthjee/core_ext/version.rb +3 -1
  27. data/lib/darthjee/core_ext.rb +2 -0
  28. data/lib/darthjee.rb +2 -1
  29. data/spec/lib/array_spec.rb +27 -19
  30. data/spec/lib/date_spec.rb +2 -0
  31. data/spec/lib/enumerable_spec.rb +10 -8
  32. data/spec/lib/hash/chain_fetcher_spec.rb +11 -0
  33. data/spec/lib/hash/deep_hash_constructor_spec.rb +3 -1
  34. data/spec/lib/hash/key_changer_spec.rb +19 -5
  35. data/spec/lib/hash/keys_sorter_spec.rb +10 -0
  36. data/spec/lib/hash/squasher_spec.rb +9 -0
  37. data/spec/lib/hash/to_hash_mapper_spec.rb +10 -0
  38. data/spec/lib/hash_spec.rb +16 -46
  39. data/spec/lib/math_spec.rb +2 -0
  40. data/spec/lib/numeric_spec.rb +2 -0
  41. data/spec/lib/object/default_value_spe.rb +2 -0
  42. data/spec/lib/object_spec.rb +2 -0
  43. data/spec/lib/symbol_spec.rb +2 -0
  44. data/spec/lib/time_spec.rb +2 -0
  45. data/spec/spec_helper.rb +2 -1
  46. data/spec/support/models/default_value.rb +2 -0
  47. data/spec/support/models/hash/value_changer/dummy.rb +19 -13
  48. data/spec/support/models/hash/value_changer/dummy_iteractor.rb +13 -8
  49. data/spec/support/shared_examples/{array_random.rb → array/array_random.rb} +5 -2
  50. data/spec/support/shared_examples/clean.rb +14 -2
  51. data/spec/support/shared_examples/date.rb +2 -0
  52. data/spec/support/shared_examples/expected.rb +2 -1
  53. data/spec/support/shared_examples/{chain_fetch.rb → hash/chain_fetch.rb} +9 -7
  54. data/spec/support/shared_examples/{chain_hash_keys_changer.rb → hash/chain_hash_keys_changer.rb} +14 -11
  55. data/spec/support/shared_examples/{hash_keys_changer.rb → hash/hash_keys_changer.rb} +7 -5
  56. data/spec/support/shared_examples/hash/hash_squasher.rb +23 -0
  57. data/spec/support/shared_examples/{hash_transpose.rb → hash/hash_transpose.rb} +8 -6
  58. data/spec/support/shared_examples/hash/keys_appender.rb +69 -0
  59. data/spec/support/shared_examples/{keys_camelizer.rb → hash/keys_camelizer.rb} +6 -4
  60. data/spec/support/shared_examples/hash/keys_sorter.rb +67 -0
  61. data/spec/support/shared_examples/{keys_underscorer.rb → hash/keys_underscorer.rb} +4 -3
  62. data/spec/support/shared_examples/{map_to_hash.rb → hash/map_to_hash.rb} +16 -16
  63. data/spec/support/shared_examples/{remap.rb → hash/remap.rb} +16 -13
  64. data/spec/support/shared_examples/hash/value_changer.rb +192 -0
  65. metadata +76 -30
  66. data/circle.yml +0 -10
  67. data/spec/support/shared_examples/keys_appender.rb +0 -43
  68. data/spec/support/shared_examples/value_changer.rb +0 -147
@@ -1,3 +1,5 @@
1
+ # frozen_string_literal: true
2
+
1
3
  require 'spec_helper'
2
4
 
3
5
  describe Hash do
@@ -8,54 +10,22 @@ describe Hash do
8
10
  it_behaves_like 'a class with append_keys method'
9
11
  it_behaves_like 'a class with change_values method'
10
12
  it_behaves_like 'a class with remap method'
11
- it_behaves_like 'an object with chain_fetch method'
12
- it_behaves_like 'a hash with map_to_hash method'
13
13
  it_behaves_like 'a class with transpose methods'
14
14
 
15
- describe :squash do
16
- let(:hash) { { a: { b: 1, c: { d: 2 } } } }
17
-
18
- it 'flattens the hash' do
19
- expect(hash.squash).to eq('a.b' => 1, 'a.c.d' => 2)
20
- end
21
-
22
- it { expect { hash.squash }.not_to change { hash } }
15
+ it_behaves_like 'an object with capable of performing chain fetch' do
16
+ let(:result) { hash.chain_fetch(*keys, &block) }
17
+ end
23
18
 
24
- context 'with array value' do
25
- let(:hash) { { a: { b: [1, { x: 3, y: { z: 4 } }] } } }
19
+ it_behaves_like 'a class that has a method to squash a hash' do
20
+ let(:squashed) { hash.squash }
21
+ end
26
22
 
27
- it 'flattens the hash' do
28
- expect(hash.squash).to eq('a.b' => [1, { x: 3, y: { z: 4 } }])
29
- end
30
- end
23
+ it_behaves_like 'a hash with map_to_hash method' do
24
+ let(:mapped) { hash.map_to_hash(&mapping_block) }
31
25
  end
32
26
 
33
- describe :sort_keys do
34
- it 'sorts keys as symbols' do
35
- expect({ b: 1, a: 2 }.sort_keys).to eq(a: 2, b: 1)
36
- end
37
- it 'sorts keys as string' do
38
- expect({ 'b' => 1, 'a' => 2 }.sort_keys).to eq('a' => 2, 'b' => 1)
39
- end
40
- it 'sorts keys recursively' do
41
- expect({ b: 1, a: { d: 3, c: 4 } }.sort_keys).to eq(a: { c: 4, d: 3 }, b: 1)
42
- end
43
- it 'sorts keys recursively when argumen is passed' do
44
- expect({ b: 1, a: { d: 3, c: 4 } }.sort_keys(recursive: true)).to eq(a: { c: 4, d: 3 }, b: 1)
45
- end
46
- it 'does not sorts keys recursively when argumen is passed' do
47
- expect({ b: 1, a: { d: 3, c: 4 } }.sort_keys(recursive: false)).to eq(a: { d: 3, c: 4 }, b: 1)
48
- end
49
- it 'sort recursevely on many levels' do
50
- hash = { b: 1, a: { d: 2, c: { e: 3, f: 4 } } }
51
- expected = { a: { c: { f: 4, e: 3 }, d: 2 }, b: 1 }
52
- expect(hash.sort_keys(recursive: true)).to eq(expected)
53
- end
54
- it 'applies to arrays as well' do
55
- hash = { b: 1, a: { d: 2, c: [{ e: 3, f: 4 }] } }
56
- expected = { a: { c: [{ f: 4, e: 3 }], d: 2 }, b: 1 }
57
- expect(hash.sort_keys(recursive: true)).to eq(expected)
58
- end
27
+ it_behaves_like 'a class with a keys sort method' do
28
+ let(:result) { hash.sort_keys(**options) }
59
29
  end
60
30
 
61
31
  describe :exclusive_merge do
@@ -67,7 +37,7 @@ describe Hash do
67
37
  end
68
38
 
69
39
  it 'does not change the original hash' do
70
- expect { subject.exclusive_merge(other) }.not_to change { subject }
40
+ expect { subject.exclusive_merge(other) }.not_to(change { subject })
71
41
  end
72
42
  end
73
43
 
@@ -80,7 +50,7 @@ describe Hash do
80
50
  end
81
51
 
82
52
  it 'does not change the original hash' do
83
- expect { subject.exclusive_merge!(other) }.to change { subject }
53
+ expect { subject.exclusive_merge!(other) }.to(change { subject })
84
54
  end
85
55
  end
86
56
 
@@ -126,7 +96,7 @@ describe Hash do
126
96
  { 'name' => 'First person', 'age' => 22 },
127
97
  { 'name' => 'Second person', 'age' => 27 }
128
98
  ],
129
- 'device' => %w(GEAR_LOCK GPS),
99
+ 'device' => %w[GEAR_LOCK GPS],
130
100
  'zipCode' => '122345-123'
131
101
  }
132
102
  end
@@ -317,7 +287,7 @@ describe Hash do
317
287
  context 'when block returns the key and not the value' do
318
288
  let(:block) { proc { |k, v| v > 1 && k } }
319
289
 
320
- it { expect(list).to eq([:b, :c, :d]) }
290
+ it { expect(list).to eq(%i[b c d]) }
321
291
  end
322
292
 
323
293
  context 'but not for the first value' do
@@ -1,3 +1,5 @@
1
+ # frozen_string_literal: true
2
+
1
3
  require 'spec_helper'
2
4
 
3
5
  describe Math do
@@ -1,3 +1,5 @@
1
+ # frozen_string_literal: true
2
+
1
3
  require 'spec_helper'
2
4
 
3
5
  describe Numeric do
@@ -1,3 +1,5 @@
1
+ # frozen_string_literal: true
2
+
1
3
  require 'spec_helper'
2
4
 
3
5
  describe Object do
@@ -1,3 +1,5 @@
1
+ # frozen_string_literal: true
2
+
1
3
  require 'spec_helper'
2
4
 
3
5
  describe Object do
@@ -1,3 +1,5 @@
1
+ # frozen_string_literal: true
2
+
1
3
  require 'spec_helper'
2
4
 
3
5
  describe Symbol do
@@ -1,3 +1,5 @@
1
+ # frozen_string_literal: true
2
+
1
3
  require 'spec_helper'
2
4
 
3
5
  describe Time do
data/spec/spec_helper.rb CHANGED
@@ -1,3 +1,5 @@
1
+ # frozen_string_literal: true
2
+
1
3
  require 'simplecov'
2
4
 
3
5
  SimpleCov.profiles.define 'gem' do
@@ -20,7 +22,6 @@ require 'darthjee/core_ext'
20
22
  Dir['./spec/support/**/*.rb'].each { |f| require f }
21
23
 
22
24
  RSpec.configure do |config|
23
- config.treat_symbols_as_metadata_keys_with_true_values = true
24
25
  config.run_all_when_everything_filtered = true
25
26
  config.filter_run :focus
26
27
 
@@ -1,3 +1,5 @@
1
+ # frozen_string_literal: true
2
+
1
3
  class DefaultValue
2
4
  default_value :x, 10
3
5
  default_values :y, :z, 20
@@ -1,19 +1,25 @@
1
- class Hash::ValueChanger::Dummy
2
- attr_reader :value
1
+ # frozen_string_literal: true
3
2
 
4
- delegate :+, to: :value
3
+ class Hash
4
+ class ValueChanger
5
+ class Dummy
6
+ attr_reader :value
5
7
 
6
- def initialize(value)
7
- @value = value
8
- end
8
+ delegate :+, to: :value
9
9
 
10
- def as_json
11
- { val: value }
12
- end
10
+ def initialize(value)
11
+ @value = value
12
+ end
13
+
14
+ def as_json
15
+ { val: value }
16
+ end
13
17
 
14
- def eql?(other)
15
- return true if equals?(other)
16
- return false unless other.is_a?(self.class)
17
- a.value == value
18
+ def eql?(other)
19
+ return true if equals?(other)
20
+ return false unless other.is_a?(self.class)
21
+ a.value == value
22
+ end
23
+ end
18
24
  end
19
25
  end
@@ -1,12 +1,17 @@
1
- class Hash::ValueChanger::DummyIteractor
2
- def initialize(*array)
3
- @array = array
4
- end
1
+ # frozen_string_literal: true
5
2
 
6
- delegate :each, :map, :to_a, to: :array
3
+ class Hash
4
+ class ValueChanger
5
+ class DummyIteractor
6
+ def initialize(*array)
7
+ @array = array
8
+ end
7
9
 
8
- private
10
+ delegate :each, :map, :to_a, to: :array
9
11
 
10
- attr_reader :array
11
- end
12
+ private
12
13
 
14
+ attr_reader :array
15
+ end
16
+ end
17
+ end
@@ -1,11 +1,14 @@
1
+ # frozen_string_literal: true
2
+
1
3
  shared_examples 'a method that returns a random element' do |method|
2
- let(:array) { [ 7, 5, 3 ] }
4
+ let(:array) { [7, 5, 3] }
3
5
 
4
6
  (0..2).each do |index|
5
7
  context "when random returns #{index}" do
6
8
  let!(:expected) { array[index] }
7
9
  before do
8
- allow_any_instance_of(Array).to receive(:rand).with(array.size) { index }
10
+ allow_any_instance_of(Array).to receive(:rand)
11
+ .with(array.size) { index }
9
12
  end
10
13
 
11
14
  it 'returns the randomized index of the array' do
@@ -1,3 +1,5 @@
1
+ # frozen_string_literal: true
2
+
1
3
  shared_examples 'a hash clean method' do |method|
2
4
  context 'when hash has one level' do
3
5
  let(:subject) do
@@ -29,7 +31,11 @@ shared_examples 'a hash clean method' do |method|
29
31
 
30
32
  context 'when hash has many levels' do
31
33
  let(:subject) do
32
- { a: 1, d: { e: { k: { l: { m: { n: 1 } } } } }, f: { g: { h: { i: { j: { c: '' } } } } } }
34
+ {
35
+ a: 1,
36
+ d: { e: { k: { l: { m: { n: 1 } } } } },
37
+ f: { g: { h: { i: { j: { c: '' } } } } }
38
+ }
33
39
  end
34
40
 
35
41
  let(:expected) do
@@ -129,7 +135,13 @@ shared_examples 'an array clean method' do |method|
129
135
 
130
136
  context 'when array has many levels' do
131
137
  let(:subject) do
132
- [1, nil, '', {}, [[[{ a: [[[[[[[]]]]]]] }]]], [[[[[[[2]]]]]]], [{ a: [2] }]]
138
+ [
139
+ 1,
140
+ nil,
141
+ '',
142
+ {},
143
+ [[[{ a: [[[[[[[]]]]]]] }]]], [[[[[[[2]]]]]]], [{ a: [2] }]
144
+ ]
133
145
  end
134
146
 
135
147
  let(:expected) do
@@ -1,3 +1,5 @@
1
+ # frozen_string_literal: true
2
+
1
3
  shared_examples 'an object that knows how to calculate days between' do
2
4
  let(:other_date) { subject.to_date + difference }
3
5
  let(:difference) { 1.year }
@@ -1,6 +1,7 @@
1
+ # frozen_string_literal: true
2
+
1
3
  shared_examples 'result is as expected' do
2
4
  it 'is as expected' do
3
5
  expect(result).to eq(expected)
4
6
  end
5
7
  end
6
-
@@ -1,6 +1,10 @@
1
- shared_examples 'an object with chain_fetch method' do
2
- describe :chain_fetch do
1
+ # frozen_string_literal: true
2
+
3
+ shared_examples 'an object with capable of performing chain fetch' do
4
+ describe '#chain_fetch' do
3
5
  let(:value) { 10 }
6
+ let(:keys) { %i[a b c d] }
7
+ let(:block) { nil }
4
8
  let(:hash) do
5
9
  {
6
10
  b: 1, c: 2, d: 3, a: {
@@ -12,8 +16,6 @@ shared_examples 'an object with chain_fetch method' do
12
16
  }
13
17
  }
14
18
  end
15
- let(:keys) { [:a, :b, :c, :d] }
16
- let(:result) { hash.chain_fetch(*keys) }
17
19
 
18
20
  context 'when fetching existing keys' do
19
21
  it 'returns the value' do
@@ -22,7 +24,7 @@ shared_examples 'an object with chain_fetch method' do
22
24
  end
23
25
 
24
26
  context 'when fetching non existing keys keys' do
25
- let(:keys) { [:a, :x, :y] }
27
+ let(:keys) { %i[a x y] }
26
28
 
27
29
  context 'when there is no default value' do
28
30
  it 'raises fetch error' do
@@ -50,7 +52,7 @@ shared_examples 'an object with chain_fetch method' do
50
52
 
51
53
  context 'but a default value block is given' do
52
54
  let(:default_value) { 100 }
53
- let(:result) { hash.chain_fetch(*keys) { default_value } }
55
+ let(:block) { proc { default_value } }
54
56
 
55
57
  it 'returns the default_value' do
56
58
  expect(result).to eq(default_value)
@@ -68,7 +70,7 @@ shared_examples 'an object with chain_fetch method' do
68
70
  end
69
71
 
70
72
  context 'and the block uses the key for the return' do
71
- let(:result) { hash.chain_fetch(*keys) { |k| "returned #{k}" } }
73
+ let(:block) { proc { |k| "returned #{k}" } }
72
74
  it 'hnadles the missing keys' do
73
75
  expect(result).to eq('returned x')
74
76
  end
@@ -1,25 +1,28 @@
1
+ # frozen_string_literal: true
2
+
1
3
  shared_examples 'a class with chain_change_key method' do
2
4
  let(:hash) do
3
5
  { 'a' => 1, b: 2, c: { d: 3, e: 4 }, f: [{ g: 5 }, { h: 6 }] }
4
6
  end
5
7
 
6
8
  describe :chain_change_keys do
7
-
8
- it_behaves_like 'a method that is able to chain change keys', :chain_change_keys
9
+ it_behaves_like 'a method that is able to chain change keys',
10
+ :chain_change_keys
9
11
  it 'does not affects the original hash' do
10
12
  expect do
11
13
  hash.chain_change_keys(:to_s, :upcase)
12
- end.not_to change { hash }
14
+ end.not_to(change { hash })
13
15
  end
14
16
  end
15
17
 
16
18
  describe :ichain_change_keys! do
17
- it_behaves_like 'a method that is able to chain change keys', :chain_change_keys!
19
+ it_behaves_like 'a method that is able to chain change keys',
20
+ :chain_change_keys!
18
21
 
19
22
  it 'affects the original hash' do
20
23
  expect do
21
24
  hash.chain_change_keys!(:to_s, :upcase)
22
- end.to change { hash }
25
+ end.to(change { hash })
23
26
  end
24
27
  end
25
28
  end
@@ -27,13 +30,13 @@ end
27
30
  shared_examples 'a method that is able to chain change keys' do |method|
28
31
  let(:result) { hash.public_send(method, *transformations, options) }
29
32
  let(:options) { {} }
30
- let(:transformations) { [ :to_s ] }
33
+ let(:transformations) { [:to_s] }
31
34
 
32
35
  context 'with simple level hash' do
33
36
  let(:hash) { { 'a' => 1, b: 2 } }
34
37
 
35
38
  context 'with symbol transformation' do
36
- let(:transformations) { [ :to_sym ] }
39
+ let(:transformations) { [:to_sym] }
37
40
  let(:expected) { { a: 1, b: 2 } }
38
41
  it_behaves_like 'result is as expected'
39
42
  end
@@ -45,9 +48,9 @@ shared_examples 'a method that is able to chain change keys' do |method|
45
48
  end
46
49
 
47
50
  context 'with recursive hash' do
48
- let(:hash) { { 'a' => 1, b: { c: 3, 'd' => 4 } } }
51
+ let(:hash) { { 'a' => 1, b: { c: 3, 'd' => 4 } } }
49
52
  let(:expected) do
50
- { 'a' => 1, 'b' => { 'c' => 3, 'd' => 4 } }
53
+ { 'a' => 1, 'b' => { 'c' => 3, 'd' => 4 } }
51
54
  end
52
55
 
53
56
  context 'when no options are given' do
@@ -64,7 +67,7 @@ shared_examples 'a method that is able to chain change keys' do |method|
64
67
 
65
68
  context 'without recursion' do
66
69
  let(:recursive) { false }
67
- let(:expected) { { 'a' => 1, 'b' => { c: 3, 'd' => 4 } } }
70
+ let(:expected) { { 'a' => 1, 'b' => { c: 3, 'd' => 4 } } }
68
71
  it_behaves_like 'result is as expected'
69
72
  end
70
73
  end
@@ -79,7 +82,7 @@ shared_examples 'a method that is able to chain change keys' do |method|
79
82
  end
80
83
 
81
84
  context 'calling with chained transformations' do
82
- let(:transformations) { [ :to_s, :upcase, :to_sym ] }
85
+ let(:transformations) { %i[to_s upcase to_sym] }
83
86
 
84
87
  let(:hexpected) do
85
88
  { A: 1, B: 2, C: { D: 3, E: 4 }, F: [{ G: 5 }, { H: 6 }] }
@@ -1,3 +1,5 @@
1
+ # frozen_string_literal: true
2
+
1
3
  shared_examples 'a class with change_key method' do
2
4
  let(:hash) do
3
5
  { 'a' => 1, b: 2, c: { d: 3, e: 4 }, f: [{ g: 5 }, { h: 6 }] }
@@ -8,7 +10,7 @@ shared_examples 'a class with change_key method' do
8
10
  it 'does not affects the original hash' do
9
11
  expect do
10
12
  hash.change_keys(recursive: true) { |k| "foo_#{k}" }
11
- end.not_to change { hash }
13
+ end.not_to(change { hash })
12
14
  end
13
15
  end
14
16
 
@@ -18,7 +20,7 @@ shared_examples 'a class with change_key method' do
18
20
  it 'affects the original hash' do
19
21
  expect do
20
22
  hash.change_keys!(recursive: true) { |k| "foo_#{k}" }
21
- end.to change { hash }
23
+ end.to(change { hash })
22
24
  end
23
25
  end
24
26
  end
@@ -47,10 +49,10 @@ shared_examples 'a method that is able to change keys' do |method|
47
49
  end
48
50
 
49
51
  context 'with recursive hash' do
50
- let(:hash) { { 'a' => 1, b: { c: 3, 'd' => 4 } } }
52
+ let(:hash) { { 'a' => 1, b: { c: 3, 'd' => 4 } } }
51
53
  let(:result) { hash.public_send(method, options) { |k| "foo_#{k}" } }
52
54
  let(:expected) do
53
- { 'foo_a' => 1, 'foo_b' => { 'foo_c' => 3, 'foo_d' => 4 } }
55
+ { 'foo_a' => 1, 'foo_b' => { 'foo_c' => 3, 'foo_d' => 4 } }
54
56
  end
55
57
 
56
58
  context 'when no options are given' do
@@ -68,7 +70,7 @@ shared_examples 'a method that is able to change keys' do |method|
68
70
 
69
71
  context 'without recursion' do
70
72
  let(:recursive) { false }
71
- let(:expected) { { 'foo_a' => 1, 'foo_b' => { c: 3, 'd' => 4 } } }
73
+ let(:expected) { { 'foo_a' => 1, 'foo_b' => { c: 3, 'd' => 4 } } }
72
74
  it_behaves_like 'result is as expected'
73
75
  end
74
76
  end
@@ -0,0 +1,23 @@
1
+ # frozen_string_literal: true
2
+
3
+ require 'spec_helper'
4
+
5
+ shared_examples 'a class that has a method to squash a hash' do
6
+ describe '#squash' do
7
+ let(:hash) { { a: { b: 1, c: { d: 2 } } } }
8
+
9
+ it 'flattens the hash' do
10
+ expect(squashed).to eq('a.b' => 1, 'a.c.d' => 2)
11
+ end
12
+
13
+ it { expect { hash.squash }.not_to(change { hash }) }
14
+
15
+ context 'with array value' do
16
+ let(:hash) { { a: { b: [1, { x: 3, y: { z: 4 } }] } } }
17
+
18
+ it 'flattens the hash' do
19
+ expect(squashed).to eq('a.b' => [1, { x: 3, y: { z: 4 } }])
20
+ end
21
+ end
22
+ end
23
+ end
@@ -1,3 +1,5 @@
1
+ # frozen_string_literal: true
2
+
1
3
  shared_examples 'a class with transpose method' do |method|
2
4
  let(:hash) { { a: 1 } }
3
5
 
@@ -61,7 +63,7 @@ shared_examples 'a class with transpose method' do |method|
61
63
  end
62
64
 
63
65
  context 'when there is a clash of keys' do
64
- let(:hash) { { a: :b, c: :b} }
66
+ let(:hash) { { a: :b, c: :b } }
65
67
 
66
68
  it 'uses the last key for value' do
67
69
  expect(hash.public_send(method)).to eq(b: :c)
@@ -69,7 +71,7 @@ shared_examples 'a class with transpose method' do |method|
69
71
  end
70
72
 
71
73
  context 'when there is a key which alreay has been defined' do
72
- let(:hash) { { a: :b, b: :c} }
74
+ let(:hash) { { a: :b, b: :c } }
73
75
 
74
76
  it 'does not override values' do
75
77
  expect(hash.public_send(method)).to eq(b: :a, c: :b)
@@ -83,18 +85,18 @@ shared_examples 'a class with transpose method' do |method|
83
85
  end
84
86
 
85
87
  shared_examples 'a class with transpose methods' do
86
- it_behaves_like 'a class with transpose method', :transpose do
88
+ it_behaves_like 'a class with transpose method', :transpose do
87
89
  it do
88
90
  expect do
89
91
  hash.transpose
90
- end.not_to change { hash }
92
+ end.not_to(change { hash })
91
93
  end
92
94
  end
93
- it_behaves_like 'a class with transpose method', :transpose! do
95
+ it_behaves_like 'a class with transpose method', :transpose! do
94
96
  it do
95
97
  expect do
96
98
  hash.transpose!
97
- end.to change { hash }
99
+ end.to(change { hash })
98
100
  end
99
101
  end
100
102
  end
@@ -0,0 +1,69 @@
1
+ # frozen_string_literal: true
2
+
3
+ shared_examples 'a class with append_keys method' do
4
+ describe '#prepend_to_keys' do
5
+ it 'accepts block to change the keys' do
6
+ hash = { a: 1, 'b' => 2 }
7
+ expected = { foo_a: 1, 'foo_b' => 2 }
8
+ expect(hash.prepend_to_keys('foo_')).to eq(expected)
9
+ end
10
+ it 'applies the block recursively' do
11
+ hash = { 'a' => 1, b: { c: 3, 'd' => 4 } }
12
+ expected = { 'foo_a' => 1, foo_b: { foo_c: 3, 'foo_d' => 4 } }
13
+ expect(hash.prepend_to_keys('foo_')).to eq(expected)
14
+ end
15
+ it 'changes type when type option is passed' do
16
+ hash = { 'a' => 1, b: 2 }
17
+ expected = { 'foo_a' => 1, 'foo_b' => 2 }
18
+ expect(hash.prepend_to_keys('foo_', type: :string)).to eq(expected)
19
+ end
20
+ it 'changes type when type option is passed' do
21
+ hash = { 'a' => 1, b: 2 }
22
+ expected = { foo_a: 1, foo_b: 2 }
23
+ expect(hash.prepend_to_keys('foo_', type: :symbol)).to eq(expected)
24
+ end
25
+ it 'keep type when type option is passed as keep' do
26
+ hash = { 'a' => 1, b: 2 }
27
+ expected = { 'foo_a' => 1, foo_b: 2 }
28
+ expect(hash.prepend_to_keys('foo_', type: :keep)).to eq(expected)
29
+ end
30
+ it 'applies to array as well' do
31
+ hash = { 'a' => 1, b: [{ c: 2 }, { d: 3 }] }
32
+ expected = { 'foo_a' => 1, foo_b: [{ foo_c: 2 }, { foo_d: 3 }] }
33
+ expect(hash.prepend_to_keys('foo_', type: :keep)).to eq(expected)
34
+ end
35
+ end
36
+
37
+ describe '#append_to_keys' do
38
+ it 'accepts block to change the keys' do
39
+ hash = { a: 1, 'b' => 2 }
40
+ expected = { a_bar: 1, 'b_bar' => 2 }
41
+ expect(hash.append_to_keys('_bar')).to eq(expected)
42
+ end
43
+ it 'applies the block recursively' do
44
+ hash = { 'a' => 1, b: { c: 3, 'd' => 4 } }
45
+ expected = { 'a_bar' => 1, b_bar: { c_bar: 3, 'd_bar' => 4 } }
46
+ expect(hash.append_to_keys('_bar')).to eq(expected)
47
+ end
48
+ it 'changes type when type option is passed' do
49
+ hash = { 'a' => 1, b: 2 }
50
+ expected = { 'a_bar' => 1, 'b_bar' => 2 }
51
+ expect(hash.append_to_keys('_bar', type: :string)).to eq(expected)
52
+ end
53
+ it 'changes type when type option is passed' do
54
+ hash = { 'a' => 1, b: 2 }
55
+ expected = { a_bar: 1, b_bar: 2 }
56
+ expect(hash.append_to_keys('_bar', type: :symbol)).to eq(expected)
57
+ end
58
+ it 'keep type when type option is passed as keep' do
59
+ hash = { 'a' => 1, b: 2 }
60
+ expected = { 'a_bar' => 1, b_bar: 2 }
61
+ expect(hash.append_to_keys('_bar', type: :keep)).to eq(expected)
62
+ end
63
+ it 'applies to array as well' do
64
+ hash = { 'a' => 1, b: [{ c: 2 }, { d: 3 }] }
65
+ expected = { 'a_bar' => 1, b_bar: [{ c_bar: 2 }, { d_bar: 3 }] }
66
+ expect(hash.append_to_keys('_bar', type: :keep)).to eq(expected)
67
+ end
68
+ end
69
+ end
@@ -1,3 +1,5 @@
1
+ # frozen_string_literal: true
2
+
1
3
  shared_examples 'a class with camlize_keys method' do
2
4
  describe :lower_camelize_keys do
3
5
  let(:expected) { { inputKey: 'value' } }
@@ -10,7 +12,7 @@ shared_examples 'a class with camlize_keys method' do
10
12
  end
11
13
 
12
14
  it 'does not change original hash' do
13
- expect { hash.lower_camelize_keys }.not_to change { hash }
15
+ expect { hash.lower_camelize_keys }.not_to(change { hash })
14
16
  end
15
17
  end
16
18
 
@@ -81,7 +83,7 @@ shared_examples 'a class with camlize_keys method' do
81
83
  end
82
84
 
83
85
  it 'does not change original hash' do
84
- expect { hash.lower_camelize_keys! }.to change { hash }
86
+ expect { hash.lower_camelize_keys! }.to(change { hash })
85
87
  end
86
88
  end
87
89
 
@@ -152,7 +154,7 @@ shared_examples 'a class with camlize_keys method' do
152
154
  end
153
155
 
154
156
  it 'does not change original hash' do
155
- expect { hash.camelize_keys }.not_to change { hash }
157
+ expect { hash.camelize_keys }.not_to(change { hash })
156
158
  end
157
159
  end
158
160
 
@@ -223,7 +225,7 @@ shared_examples 'a class with camlize_keys method' do
223
225
  end
224
226
 
225
227
  it 'does not change original hash' do
226
- expect { hash.camelize_keys! }.to change { hash }
228
+ expect { hash.camelize_keys! }.to(change { hash })
227
229
  end
228
230
  end
229
231