traipse 0.5.0 → 0.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.
- data/lib/traipse.rb +37 -0
- data/lib/traipse/version.rb +1 -1
- data/test/traipse_test.rb +89 -0
- metadata +5 -3
data/lib/traipse.rb
CHANGED
@@ -10,6 +10,10 @@ module Traipse
|
|
10
10
|
return _find( object, path.split( SEPARATOR ) )
|
11
11
|
end
|
12
12
|
|
13
|
+
def self.find_with_keys( object, path )
|
14
|
+
_find_with_keys( object, path.split( SEPARATOR ) )
|
15
|
+
end
|
16
|
+
|
13
17
|
def self._find( object, path, results=[] ) # :nodoc:
|
14
18
|
key, *rest = path
|
15
19
|
|
@@ -43,4 +47,37 @@ module Traipse
|
|
43
47
|
return results
|
44
48
|
end
|
45
49
|
|
50
|
+
def self._find_with_keys( object, path, full_path=[], results={} ) # :nodoc:
|
51
|
+
key, *rest = path
|
52
|
+
full_path << key unless key == "*"
|
53
|
+
|
54
|
+
# Handle wildcard hash keys
|
55
|
+
if key == '*'
|
56
|
+
object.keys.each do |subkey|
|
57
|
+
results.merge! _find_with_keys( object, [ subkey, *rest ], full_path.dup )
|
58
|
+
end
|
59
|
+
return results.reject { |k,v| v.nil? }
|
60
|
+
end
|
61
|
+
|
62
|
+
# This is the end of the line, megatron.
|
63
|
+
return { full_path.join(".") => object[key] } if rest.empty?
|
64
|
+
|
65
|
+
# Traverse hashes and arrays
|
66
|
+
case object[ key ]
|
67
|
+
when Hash
|
68
|
+
return _find_with_keys( object[ key ], rest, full_path )
|
69
|
+
when Array
|
70
|
+
if rest.first =~ /^\d+$/
|
71
|
+
index = rest.shift.to_i
|
72
|
+
results.merge! _find_with_keys( object[key][index], rest, full_path + [index] )
|
73
|
+
else
|
74
|
+
object[ key ].each_with_index do |obj, index|
|
75
|
+
results.merge! _find_with_keys( obj, rest, full_path + [index] )
|
76
|
+
end
|
77
|
+
end
|
78
|
+
end
|
79
|
+
|
80
|
+
return results
|
81
|
+
end
|
82
|
+
|
46
83
|
end
|
data/lib/traipse/version.rb
CHANGED
@@ -0,0 +1,89 @@
|
|
1
|
+
require "../lib/traipse"
|
2
|
+
require "test/unit"
|
3
|
+
|
4
|
+
|
5
|
+
|
6
|
+
class TraipseTest < Test::Unit::TestCase
|
7
|
+
|
8
|
+
DATA = {
|
9
|
+
"name" => "Percival",
|
10
|
+
"board" => {
|
11
|
+
"name" => "cats"
|
12
|
+
},
|
13
|
+
"categories" => [
|
14
|
+
{ "name" => "animals" },
|
15
|
+
{ "name" => "kitties" },
|
16
|
+
{ "name" => "robots" },
|
17
|
+
],
|
18
|
+
"products" => {
|
19
|
+
"shoes" => {
|
20
|
+
"brands" => [
|
21
|
+
{ "name" => "converse" },
|
22
|
+
{ "name" => "adidas" },
|
23
|
+
{ "name" => "nike" }
|
24
|
+
]
|
25
|
+
},
|
26
|
+
"apparel" => {
|
27
|
+
"brands" => [
|
28
|
+
{ "name" => "Calvin Klein" },
|
29
|
+
{ "name" => "Diesel" },
|
30
|
+
{ "name" => "Betsey Johnson" },
|
31
|
+
{ "name" => [ "Marc", "Ecko" ] },
|
32
|
+
{ "caltrops" => 'Yes Please' }
|
33
|
+
]
|
34
|
+
}
|
35
|
+
}
|
36
|
+
}
|
37
|
+
|
38
|
+
def test_can_find_top_level_values
|
39
|
+
assert_equal ['Percival'], Traipse.find( DATA, 'name' )
|
40
|
+
end
|
41
|
+
|
42
|
+
def test_can_return_key_names_too
|
43
|
+
matches = Traipse.find_with_keys( DATA, 'name' )
|
44
|
+
assert_equal matches.keys, ["name"]
|
45
|
+
assert_equal matches.values, ["Percival"]
|
46
|
+
end
|
47
|
+
|
48
|
+
def test_can_get_to_nested_values
|
49
|
+
matches = Traipse.find_with_keys( DATA, 'board.name' )
|
50
|
+
assert_equal matches.keys, ["board.name"]
|
51
|
+
assert_equal matches.values, ["cats"]
|
52
|
+
end
|
53
|
+
|
54
|
+
def test_can_traverse_arrays
|
55
|
+
matches = Traipse.find_with_keys( DATA, 'categories.name' )
|
56
|
+
assert_equal ["categories.0.name", "categories.1.name", "categories.2.name"], matches.keys
|
57
|
+
assert_equal ["animals", "kitties", "robots"], matches.values
|
58
|
+
end
|
59
|
+
|
60
|
+
def test_can_traverse_arrays_to_get_to_nested_values
|
61
|
+
matches = Traipse.find_with_keys( DATA, 'products.shoes.brands.name' )
|
62
|
+
assert_equal ["products.shoes.brands.0.name", "products.shoes.brands.1.name", "products.shoes.brands.2.name"], matches.keys
|
63
|
+
assert_equal [ "converse", "adidas", "nike" ], matches.values
|
64
|
+
end
|
65
|
+
|
66
|
+
def test_can_handle_key_wildcards
|
67
|
+
matches = Traipse.find_with_keys( DATA, 'products.*.brands.name' )
|
68
|
+
assert_equal [ "converse", "adidas", "nike", "Calvin Klein", "Diesel", "Betsey Johnson", [ "Marc", "Ecko" ] ], matches.values
|
69
|
+
assert_equal "products.shoes.brands.0.name", matches.keys.first
|
70
|
+
assert_equal "products.apparel.brands.3.name", matches.keys.last
|
71
|
+
|
72
|
+
matches = Traipse.find_with_keys( DATA, '*.name' )
|
73
|
+
assert_equal [ "cats", "animals", "kitties", "robots" ], matches.values
|
74
|
+
assert_equal "board.name", matches.keys.first
|
75
|
+
assert_equal "categories.2.name", matches.keys.last
|
76
|
+
end
|
77
|
+
|
78
|
+
def test_can_do_multiple_wildcards
|
79
|
+
matches = Traipse.find_with_keys( DATA, "products.*.brands.*" )
|
80
|
+
assert_equal [ "converse", "adidas", "nike", "Calvin Klein", "Diesel", "Betsey Johnson", [ "Marc", "Ecko" ], 'Yes Please' ], matches.values
|
81
|
+
assert_equal "products.shoes.brands.0.name", matches.keys.first
|
82
|
+
assert_equal "products.apparel.brands.4.caltrops", matches.keys.last
|
83
|
+
end
|
84
|
+
|
85
|
+
def test_can_match_array_indexed_paths
|
86
|
+
assert_equal [ "Marc", "Ecko" ], Traipse.find_with_keys( DATA, "products.apparel.brands.3.name").values.first
|
87
|
+
assert_equal 'Yes Please', Traipse.find_with_keys( DATA, "products.apparel.brands.4.caltrops").values.first
|
88
|
+
end
|
89
|
+
end
|
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: traipse
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.
|
4
|
+
version: 0.6.0
|
5
5
|
prerelease:
|
6
6
|
platform: ruby
|
7
7
|
authors:
|
@@ -9,7 +9,7 @@ authors:
|
|
9
9
|
autorequire:
|
10
10
|
bindir: bin
|
11
11
|
cert_chain: []
|
12
|
-
date: 2012-
|
12
|
+
date: 2012-08-15 00:00:00.000000000 Z
|
13
13
|
dependencies: []
|
14
14
|
description: ! 'Traipse is a library that allows you to address a data structure of
|
15
15
|
Hashes & Arrays using a dot notated string & wildcards. ex: ''categories.*.name''.
|
@@ -28,6 +28,7 @@ files:
|
|
28
28
|
- lib/traipse/version.rb
|
29
29
|
- spec/spec_helper.rb
|
30
30
|
- spec/traipse_spec.rb
|
31
|
+
- test/traipse_test.rb
|
31
32
|
- traipse.gemspec
|
32
33
|
homepage: https://github.com/makenai/traipse
|
33
34
|
licenses: []
|
@@ -49,10 +50,11 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
49
50
|
version: '0'
|
50
51
|
requirements: []
|
51
52
|
rubyforge_project: traipse
|
52
|
-
rubygems_version: 1.8.
|
53
|
+
rubygems_version: 1.8.24
|
53
54
|
signing_key:
|
54
55
|
specification_version: 3
|
55
56
|
summary: Traverse data structures with a dot notated string.
|
56
57
|
test_files:
|
57
58
|
- spec/spec_helper.rb
|
58
59
|
- spec/traipse_spec.rb
|
60
|
+
- test/traipse_test.rb
|