camel_snake_keys 0.0.3 → 0.0.7
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 +5 -5
- data/.gitignore +1 -0
- data/.rubocop.yml +96 -1164
- data/.ruby-version +1 -0
- data/.travis.yml +31 -0
- data/CHANGELOG.md +13 -0
- data/Gemfile +4 -3
- data/README.md +18 -7
- data/Rakefile +0 -1
- data/camel_snake.gemspec +13 -12
- data/lib/camel_snake_keys.rb +40 -35
- data/lib/version.rb +1 -1
- data/spec/lib/camel_snake_keys_spec.rb +84 -20
- metadata +26 -11
data/.ruby-version
ADDED
@@ -0,0 +1 @@
|
|
1
|
+
3.0.1
|
data/.travis.yml
ADDED
@@ -0,0 +1,31 @@
|
|
1
|
+
language: ruby
|
2
|
+
before_install:
|
3
|
+
- gem install bundler -v 1.17.3
|
4
|
+
- gem install rspec
|
5
|
+
install: bundle install --jobs=1 --retry=1
|
6
|
+
script:
|
7
|
+
- bundle install
|
8
|
+
- bundle exec rspec
|
9
|
+
|
10
|
+
rvm:
|
11
|
+
- 2.3.1
|
12
|
+
# - 2.4.0
|
13
|
+
# - 2.5.0
|
14
|
+
# - ruby-head
|
15
|
+
# - jruby-head
|
16
|
+
|
17
|
+
matrix:
|
18
|
+
allow_failures:
|
19
|
+
- rvm: ruby-head
|
20
|
+
- rvm: jruby-head
|
21
|
+
|
22
|
+
env:
|
23
|
+
global:
|
24
|
+
- JRUBY_OPTS="-J-Xmx1024m --debug"
|
25
|
+
|
26
|
+
notifications:
|
27
|
+
email:
|
28
|
+
recipients:
|
29
|
+
- buermann@gmail.com
|
30
|
+
on_success: change
|
31
|
+
on_failure: always
|
data/CHANGELOG.md
CHANGED
data/Gemfile
CHANGED
data/README.md
CHANGED
@@ -1,20 +1,31 @@
|
|
1
1
|
# camel_snake_keys
|
2
2
|
|
3
|
-
|
3
|
+
[![Gem Version][GV img]][Gem Version]
|
4
|
+
[![Build Status][BS img]][Build Status]
|
5
|
+
[![Coverage Status][CS img]][Coverage Status]
|
4
6
|
|
5
|
-
|
7
|
+
[Gem Version]: https://rubygems.org/gems/camel_snake_keys
|
8
|
+
[Build Status]: https://travis-ci.org/buermann/camel_snake_keys
|
9
|
+
[travis pull requests]: https://travis-ci.org/buermann/camel_snake_keys/pull_requests
|
10
|
+
[Coverage Status]: https://coveralls.io/r/buermann/camel_snake_keys
|
11
|
+
|
12
|
+
[GV img]: https://badge.fury.io/rb/camel_snake_keys.png
|
13
|
+
[BS img]: https://travis-ci.org/buermann/camel_snake_keys.png
|
14
|
+
[CS img]: https://coveralls.io/repos/buermann/camel_snake_keys/badge.png?branch=master
|
6
15
|
|
7
|
-
Add gem 'camel_snake_keys' to your gemfile or gem install camel_snake_keys.
|
8
16
|
|
9
|
-
|
17
|
+
Add recursive with_snake_keys and with_camel_keys refinements to Array and Hash. Preserve strings and symbols and treat hash descendents such as ActiveSupport::HashWithIndifferentAccess and Hashie::Mash agnostically.
|
10
18
|
|
11
|
-
|
12
|
-
|
19
|
+
## Documentation
|
20
|
+
|
21
|
+
Add `gem 'camel_snake_keys'` to your Gemfile or gem install camel_snake_keys. Where you want to add `with_snake_keys` and `with_camel_keys` to your objects invoke `using CamelSnakeKeys`, or invoke the class methods, `CamelSnakeKeys.camel_keys(object, with_indifference)` and `CamelSnakeKeys.snake_keys(object, with_indifference)`.
|
13
22
|
|
14
23
|
If with_indifference is set to a true value hashes will be returned as ActiveSupport's HashWithIndifferentAccess.
|
15
24
|
|
16
25
|
```
|
17
|
-
require '
|
26
|
+
require 'camel_snake_keys'
|
27
|
+
|
28
|
+
using CamelSnakeKeys
|
18
29
|
|
19
30
|
{fooBar: "Frob"}.with_snake_keys
|
20
31
|
=> {:foo_bar=>"Frob"}
|
data/Rakefile
CHANGED
data/camel_snake.gemspec
CHANGED
@@ -1,24 +1,25 @@
|
|
1
|
-
|
1
|
+
$LOAD_PATH.push File.expand_path('lib', __dir__)
|
2
2
|
|
3
3
|
# Maintain your gem's version:
|
4
|
-
require
|
4
|
+
require 'version'
|
5
5
|
|
6
6
|
# Describe your gem and declare its dependencies:
|
7
7
|
Gem::Specification.new do |s|
|
8
|
-
s.name =
|
8
|
+
s.name = 'camel_snake_keys'
|
9
9
|
s.version = CamelSnakeKeys::VERSION
|
10
|
-
s.authors = [
|
11
|
-
s.email = [
|
12
|
-
s.homepage =
|
13
|
-
s.summary =
|
14
|
-
s.description =
|
15
|
-
s.license =
|
10
|
+
s.authors = ['Josh Buermann']
|
11
|
+
s.email = ['buermann@gmail.com']
|
12
|
+
s.homepage = 'https://github.com/buermann/camel_snake_keys'
|
13
|
+
s.summary = 'Convert nested data structure hash keys between camel and snake case.'
|
14
|
+
s.description = ''
|
15
|
+
s.license = 'MIT'
|
16
16
|
|
17
17
|
s.files = `git ls-files`.split("\n").sort
|
18
18
|
s.test_files = `git ls-files -- spec/*`.split("\n")
|
19
19
|
|
20
|
-
s.required_ruby_version = '
|
21
|
-
s.add_dependency
|
20
|
+
s.required_ruby_version = '> 2.0'
|
21
|
+
s.add_dependency 'activesupport'
|
22
22
|
|
23
|
-
s.add_development_dependency
|
23
|
+
s.add_development_dependency 'rspec'
|
24
|
+
s.add_development_dependency 'activesupport'
|
24
25
|
end
|
data/lib/camel_snake_keys.rb
CHANGED
@@ -1,61 +1,66 @@
|
|
1
|
-
require 'active_support
|
2
|
-
require 'active_support/core_ext
|
3
|
-
require 'hashie/mash'
|
1
|
+
require 'active_support'
|
2
|
+
require 'active_support/core_ext'
|
4
3
|
|
5
4
|
module CamelSnakeKeys
|
5
|
+
[Hash, Array].each do |klass|
|
6
|
+
refine klass do
|
7
|
+
def with_camel_keys(indifference=false)
|
8
|
+
CamelSnakeKeys.camel_keys(self, indifference)
|
9
|
+
end
|
10
|
+
|
11
|
+
def with_snake_keys(indifference=false)
|
12
|
+
CamelSnakeKeys.snake_keys(self, indifference)
|
13
|
+
end
|
14
|
+
end
|
15
|
+
end
|
16
|
+
|
6
17
|
class << self
|
7
|
-
def if_underscore(
|
8
|
-
|
9
|
-
|
10
|
-
|
11
|
-
|
18
|
+
def if_underscore(obj)
|
19
|
+
case obj
|
20
|
+
when Symbol
|
21
|
+
obj.to_s.underscore.to_sym
|
22
|
+
when String
|
23
|
+
obj.underscore
|
12
24
|
else
|
13
|
-
|
25
|
+
obj
|
14
26
|
end
|
15
27
|
end
|
16
28
|
|
17
|
-
def if_camelize(
|
18
|
-
|
19
|
-
|
20
|
-
|
21
|
-
|
29
|
+
def if_camelize(obj)
|
30
|
+
case obj
|
31
|
+
when Symbol
|
32
|
+
obj.to_s.camelize(:lower).to_sym
|
33
|
+
when String
|
34
|
+
obj.camelize(:lower)
|
22
35
|
else
|
23
|
-
|
36
|
+
obj
|
24
37
|
end
|
25
38
|
end
|
26
39
|
|
27
40
|
def snake_keys(data, indifference=false)
|
28
|
-
|
29
|
-
|
30
|
-
|
31
|
-
|
41
|
+
case data
|
42
|
+
when Array
|
43
|
+
data.map { |v| snake_keys(v, indifference) }
|
44
|
+
when Hash
|
45
|
+
hash = data.sort_by {|k, _v| k =~ /_/ ? 0 : 1 }.map {|k, v| [if_underscore(k), snake_keys(v, indifference)] }.to_h
|
32
46
|
hash = hash.with_indifferent_access if indifference
|
33
|
-
data.
|
47
|
+
data.instance_of?(Hash) ? hash : data.class.new(hash)
|
34
48
|
else
|
35
49
|
data
|
36
50
|
end
|
37
51
|
end
|
38
52
|
|
39
53
|
def camel_keys(data, indifference=false)
|
40
|
-
|
41
|
-
|
42
|
-
|
43
|
-
|
54
|
+
case data
|
55
|
+
when Array
|
56
|
+
data.map { |v| camel_keys(v, indifference) }
|
57
|
+
when Hash
|
58
|
+
hash = data.sort_by {|k, _v| k =~ /_/ ? 1 : 0 }.map {|k, v| [if_camelize(k), camel_keys(v, indifference)] }.to_h
|
44
59
|
hash = hash.with_indifferent_access if indifference
|
45
|
-
data.
|
60
|
+
data.instance_of?(Hash) ? hash : data.class.new(hash)
|
46
61
|
else
|
47
62
|
data
|
48
63
|
end
|
49
64
|
end
|
50
65
|
end
|
51
66
|
end
|
52
|
-
|
53
|
-
module Enumerable
|
54
|
-
def with_camel_keys(indifference=false)
|
55
|
-
CamelSnakeKeys.camel_keys(self, indifference)
|
56
|
-
end
|
57
|
-
|
58
|
-
def with_snake_keys(indifference=false)
|
59
|
-
CamelSnakeKeys.snake_keys(self, indifference)
|
60
|
-
end
|
61
|
-
end
|
data/lib/version.rb
CHANGED
@@ -1,4 +1,7 @@
|
|
1
1
|
require 'test_helper'
|
2
|
+
require 'hashie/mash'
|
3
|
+
|
4
|
+
using CamelSnakeKeys
|
2
5
|
|
3
6
|
RSpec.describe Enumerable do
|
4
7
|
|
@@ -13,6 +16,7 @@ RSpec.describe Enumerable do
|
|
13
16
|
it "should camel case keys of hashes" do
|
14
17
|
snaked.with_camel_keys.should eq camelized
|
15
18
|
end
|
19
|
+
|
16
20
|
end
|
17
21
|
|
18
22
|
context "hashes" do
|
@@ -21,94 +25,154 @@ RSpec.describe Enumerable do
|
|
21
25
|
|
22
26
|
it "should snake case keys of hashes" do
|
23
27
|
hash = camelized.with_snake_keys
|
24
|
-
hash.class.should
|
28
|
+
hash.class.should eq Hash
|
25
29
|
hash.should eq snaked
|
26
30
|
end
|
27
31
|
|
28
32
|
it "should camel case keys of hashes" do
|
29
33
|
hash = snaked.with_camel_keys
|
30
|
-
hash.class.should
|
34
|
+
hash.class.should eq Hash
|
31
35
|
hash.should eq camelized
|
32
36
|
end
|
33
37
|
|
38
|
+
it "should preserve symbol keys" do
|
39
|
+
camelized.with_snake_keys[:foo_bar].should_not be_nil
|
40
|
+
camelized.with_snake_keys['foo_bar'].should be_nil
|
41
|
+
snaked.with_camel_keys[:fooBar].should be_present
|
42
|
+
snaked.with_camel_keys['fooBar'].should be_nil
|
43
|
+
end
|
44
|
+
|
45
|
+
it "should preserve string keys" do
|
46
|
+
camelized.with_snake_keys['dark_matter'].should be_present
|
47
|
+
camelized.with_snake_keys[:dark_matter].should be_nil
|
48
|
+
snaked.with_camel_keys['darkMatter'].should be_present
|
49
|
+
snaked.with_camel_keys[:darkMatter].should be_nil
|
50
|
+
end
|
51
|
+
|
34
52
|
it "should snake case keys of hashes with indifference" do
|
35
53
|
hash = camelized.with_snake_keys(true)
|
36
|
-
hash.class.should
|
54
|
+
hash.class.should eq HashWithIndifferentAccess
|
37
55
|
hash.should eq snaked.with_indifferent_access
|
38
56
|
hash[:foo_bar].should eq hash["foo_bar"]
|
39
57
|
end
|
40
58
|
|
41
59
|
it "should camel case keys of hashes with indifference" do
|
42
60
|
hash = snaked.with_camel_keys(true)
|
43
|
-
hash.class.should
|
61
|
+
hash.class.should eq HashWithIndifferentAccess
|
44
62
|
hash.should eq camelized.with_indifferent_access
|
45
63
|
hash["fooBar"].should eq hash[:fooBar]
|
46
64
|
end
|
47
65
|
|
48
66
|
end
|
49
67
|
|
50
|
-
context "hashes with indifferent access" do
|
68
|
+
context "hashes with indifferent access" do
|
51
69
|
let(:snaked) { {1.2=>1, 1=>1.2, nil=>2, :foo_bar=>1, "dark_matter"=>[{:dark_energy=>"aBc", "baz_qux"=>"Frob."}]}.with_indifferent_access }
|
52
70
|
let(:camelized) { { 1.2=>1, 1=>1.2, nil=>2, :fooBar=>1, "darkMatter"=>[{:darkEnergy=>"aBc", "bazQux"=>"Frob."}]}.with_indifferent_access }
|
53
71
|
|
54
72
|
it "should snake case keys of hashes" do
|
55
73
|
hash = camelized.with_snake_keys
|
56
|
-
hash.class.should
|
74
|
+
hash.class.should eq HashWithIndifferentAccess
|
57
75
|
hash.should eq snaked
|
58
76
|
end
|
59
77
|
|
60
78
|
it "should camel case keys of hashes" do
|
61
79
|
hash = snaked.with_camel_keys
|
62
|
-
hash.class.should
|
80
|
+
hash.class.should eq HashWithIndifferentAccess
|
63
81
|
hash.should eq camelized
|
64
82
|
end
|
65
83
|
|
66
84
|
it "should snake case keys of hashes with indifference" do
|
67
85
|
hash = camelized.with_snake_keys(true)
|
68
|
-
hash.class.should
|
86
|
+
hash.class.should eq HashWithIndifferentAccess
|
69
87
|
hash.should eq snaked
|
70
88
|
end
|
71
89
|
|
72
90
|
it "should camel case keys of hashes with indifference" do
|
73
91
|
hash = snaked.with_camel_keys(true)
|
74
|
-
hash.class.should
|
92
|
+
hash.class.should eq HashWithIndifferentAccess
|
75
93
|
hash.should eq camelized
|
76
94
|
end
|
77
95
|
|
78
96
|
end
|
79
97
|
|
80
|
-
context "mashes" do
|
98
|
+
context "mashes" do
|
81
99
|
let(:snaked) { Hashie::Mash.new({1.2=>1, 1=>1.2, nil=>2, :foo_bar=>1, "dark_matter"=>[{:dark_energy=>"aBc", "baz_qux"=>"Frob."}]}) }
|
82
100
|
let(:camelized) { Hashie::Mash.new({ 1.2=>1, 1=>1.2, nil=>2, :fooBar=>1, "darkMatter"=>[{:darkEnergy=>"aBc", "bazQux"=>"Frob."}]}) }
|
83
101
|
|
84
102
|
it "should snake case keys of hashes" do
|
85
103
|
hash = camelized.with_snake_keys
|
86
|
-
hash.class.should
|
104
|
+
hash.class.should eq Hashie::Mash
|
87
105
|
hash.should eq snaked
|
88
|
-
hash["fooBar"].should
|
106
|
+
hash["fooBar"].should eq hash[:fooBar]
|
89
107
|
end
|
90
108
|
|
91
109
|
it "should camel case keys of hashes" do
|
92
110
|
hash = snaked.with_camel_keys
|
93
|
-
hash.class.should
|
111
|
+
hash.class.should eq Hashie::Mash
|
94
112
|
hash.should eq camelized
|
95
|
-
hash["foo_bar"].should
|
113
|
+
hash["foo_bar"].should eq hash[:foo_bar]
|
96
114
|
end
|
97
|
-
|
115
|
+
|
98
116
|
it "should snake case keys of hashes with redundant indifference" do
|
99
117
|
hash = camelized.with_snake_keys(true)
|
100
|
-
hash.class.should
|
118
|
+
hash.class.should eq Hashie::Mash
|
101
119
|
hash.should eq snaked
|
102
|
-
hash["foo_bar"].should
|
120
|
+
hash["foo_bar"].should eq hash[:foo_bar]
|
103
121
|
end
|
104
122
|
|
105
123
|
it "should camel case keys of hashes with redundant indifference" do
|
106
124
|
hash = snaked.with_camel_keys(true)
|
107
|
-
hash.class.should
|
125
|
+
hash.class.should eq Hashie::Mash
|
108
126
|
hash.should eq camelized
|
109
|
-
hash["foo_bar"].should
|
127
|
+
hash["foo_bar"].should eq hash[:foo_bar]
|
110
128
|
end
|
111
|
-
|
129
|
+
|
112
130
|
end
|
113
131
|
|
132
|
+
context "hash merge conflicts should be resolved predictably" do
|
133
|
+
it "should give camel case key values priority when snake casing" do
|
134
|
+
hash = { foo_bar: 1, fooBar: 2 }
|
135
|
+
result = { foo_bar: 2 }
|
136
|
+
hash.with_snake_keys.should eq result
|
137
|
+
|
138
|
+
hash = { fooBar: 2, foo_bar: 1 }
|
139
|
+
hash.with_snake_keys.should eq result
|
140
|
+
end
|
141
|
+
|
142
|
+
it "should give snake case key values priority when camel casing" do
|
143
|
+
hash = { foo_bar: 1, fooBar: 2 }
|
144
|
+
result = { fooBar: 1 }
|
145
|
+
hash.with_camel_keys.should eq result
|
146
|
+
|
147
|
+
hash = { fooBar: 2, foo_bar: 1 }
|
148
|
+
hash.with_camel_keys.should eq result
|
149
|
+
end
|
150
|
+
end
|
151
|
+
|
152
|
+
context "it should pass indifference down deeply nested structures" do
|
153
|
+
it "camelizing an array of hashes" do
|
154
|
+
camelized = [ a: { b: [{c: :d}] } ].with_camel_keys(true)
|
155
|
+
camelized.first[:a].is_a?(HashWithIndifferentAccess).should be_truthy
|
156
|
+
camelized.first[:a][:b].first.is_a?(HashWithIndifferentAccess).should be_truthy
|
157
|
+
end
|
158
|
+
|
159
|
+
it "cazemlizing a hashes of arrays" do
|
160
|
+
camelized = { a: [{b: {c: :d}}]}.with_camel_keys(true)
|
161
|
+
camelized.is_a?(HashWithIndifferentAccess).should be_truthy
|
162
|
+
camelized[:a].first[:b].is_a?(HashWithIndifferentAccess).should be_truthy
|
163
|
+
end
|
164
|
+
|
165
|
+
it "snaking an array of hashes" do
|
166
|
+
snaked = [ a: { b: [{c: :d}] } ].with_snake_keys(true)
|
167
|
+
snaked.first[:a].is_a?(HashWithIndifferentAccess).should be_truthy
|
168
|
+
snaked.first[:a][:b].first.is_a?(HashWithIndifferentAccess).should be_truthy
|
169
|
+
end
|
170
|
+
|
171
|
+
it "snaking a hashes of arrays" do
|
172
|
+
snaked = { a: [{b: {c: :d}}]}.with_snake_keys(true)
|
173
|
+
snaked.is_a?(HashWithIndifferentAccess).should be_truthy
|
174
|
+
snaked[:a].first[:b].is_a?(HashWithIndifferentAccess).should be_truthy
|
175
|
+
end
|
176
|
+
|
177
|
+
end
|
114
178
|
end
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: camel_snake_keys
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.0.
|
4
|
+
version: 0.0.7
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Josh Buermann
|
8
|
-
autorequire:
|
8
|
+
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date:
|
11
|
+
date: 2022-02-08 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: activesupport
|
@@ -25,19 +25,33 @@ dependencies:
|
|
25
25
|
- !ruby/object:Gem::Version
|
26
26
|
version: '0'
|
27
27
|
- !ruby/object:Gem::Dependency
|
28
|
-
name: rspec
|
28
|
+
name: rspec
|
29
29
|
requirement: !ruby/object:Gem::Requirement
|
30
30
|
requirements:
|
31
31
|
- - ">="
|
32
32
|
- !ruby/object:Gem::Version
|
33
|
-
version: '
|
33
|
+
version: '0'
|
34
|
+
type: :development
|
35
|
+
prerelease: false
|
36
|
+
version_requirements: !ruby/object:Gem::Requirement
|
37
|
+
requirements:
|
38
|
+
- - ">="
|
39
|
+
- !ruby/object:Gem::Version
|
40
|
+
version: '0'
|
41
|
+
- !ruby/object:Gem::Dependency
|
42
|
+
name: activesupport
|
43
|
+
requirement: !ruby/object:Gem::Requirement
|
44
|
+
requirements:
|
45
|
+
- - ">="
|
46
|
+
- !ruby/object:Gem::Version
|
47
|
+
version: '0'
|
34
48
|
type: :development
|
35
49
|
prerelease: false
|
36
50
|
version_requirements: !ruby/object:Gem::Requirement
|
37
51
|
requirements:
|
38
52
|
- - ">="
|
39
53
|
- !ruby/object:Gem::Version
|
40
|
-
version: '
|
54
|
+
version: '0'
|
41
55
|
description: ''
|
42
56
|
email:
|
43
57
|
- buermann@gmail.com
|
@@ -48,6 +62,8 @@ files:
|
|
48
62
|
- ".coveralls.yml"
|
49
63
|
- ".gitignore"
|
50
64
|
- ".rubocop.yml"
|
65
|
+
- ".ruby-version"
|
66
|
+
- ".travis.yml"
|
51
67
|
- CHANGELOG.md
|
52
68
|
- Gemfile
|
53
69
|
- README.md
|
@@ -61,13 +77,13 @@ homepage: https://github.com/buermann/camel_snake_keys
|
|
61
77
|
licenses:
|
62
78
|
- MIT
|
63
79
|
metadata: {}
|
64
|
-
post_install_message:
|
80
|
+
post_install_message:
|
65
81
|
rdoc_options: []
|
66
82
|
require_paths:
|
67
83
|
- lib
|
68
84
|
required_ruby_version: !ruby/object:Gem::Requirement
|
69
85
|
requirements:
|
70
|
-
- - "
|
86
|
+
- - ">"
|
71
87
|
- !ruby/object:Gem::Version
|
72
88
|
version: '2.0'
|
73
89
|
required_rubygems_version: !ruby/object:Gem::Requirement
|
@@ -76,9 +92,8 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
76
92
|
- !ruby/object:Gem::Version
|
77
93
|
version: '0'
|
78
94
|
requirements: []
|
79
|
-
|
80
|
-
|
81
|
-
signing_key:
|
95
|
+
rubygems_version: 3.2.15
|
96
|
+
signing_key:
|
82
97
|
specification_version: 4
|
83
98
|
summary: Convert nested data structure hash keys between camel and snake case.
|
84
99
|
test_files:
|