Skip to content

Commit

Permalink
Add HashUtils.deep_transform_keys
Browse files Browse the repository at this point in the history
  • Loading branch information
locawebemailmarketing authored and fabioperrella committed Jul 14, 2020
1 parent eaa644f commit 6f4ef24
Show file tree
Hide file tree
Showing 3 changed files with 62 additions and 0 deletions.
1 change: 1 addition & 0 deletions lib/format_parser.rb
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@
# top-level methods of the library.
module FormatParser
require_relative 'format_parser/version'
require_relative 'hash_utils'
require_relative 'attributes_json'
require_relative 'image'
require_relative 'audio'
Expand Down
19 changes: 19 additions & 0 deletions lib/hash_utils.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
# based on https://github.com/rails/rails/blob/master/activesupport/lib/active_support/core_ext/hash/keys.rb#L116
# I chose to copy this method instead of adding activesupport as a dependency
# because we want to have the least number of dependencies
module FormatParser
class HashUtils
def self.deep_transform_keys(object, &block)
case object
when Hash
object.each_with_object({}) do |(key, value), result|
result[yield(key)] = deep_transform_keys(value, &block)
end
when Array
object.map { |e| deep_transform_keys(e, &block) }
else
object
end
end
end
end
42 changes: 42 additions & 0 deletions spec/hash_utils_spec.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,42 @@
require 'spec_helper'

describe FormatParser::HashUtils do
describe '.deep_transform_keys' do
it 'transforms all the keys in a hash' do
hash = { aa: 1, 'bb' => 2 }
result = described_class.deep_transform_keys(hash, &:to_s)

expect(result).to eq('aa' => 1, 'bb' => 2)
end

it 'transforms all the keys in a array of hashes' do
array = [{ aa: 1, bb: 2 }, { cc: 3, dd: [{c: 2, d: 3}] }]
result = described_class.deep_transform_keys(array, &:to_s)

expect(result).to eq(
[{'aa' => 1, 'bb' => 2}, {'cc' => 3, 'dd' => [{'c' => 2, 'd' => 3}]}]
)
end

it 'transforms all the keys in a hash recursively' do
hash = { aa: 1, bb: { cc: 22, dd: 3 } }
result = described_class.deep_transform_keys(hash, &:to_s)

expect(result).to eq('aa' => 1, 'bb' => { 'cc' => 22, 'dd' => 3})
end

it 'does nothing for an non array/hash object' do
object = Object.new
result = described_class.deep_transform_keys(object, &:to_s)

expect(result).to eq(object)
end

it 'returns the last value if different keys are transformed into the same one' do
hash = { aa: 0, 'bb' => 2, bb: 1 }
result = described_class.deep_transform_keys(hash, &:to_s)

expect(result).to eq('aa' => 0, 'bb' => 1)
end
end
end

0 comments on commit 6f4ef24

Please sign in to comment.