neography 0.0.1 → 0.0.2

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/README.rdoc CHANGED
@@ -1,9 +1,10 @@
1
1
  == Welcome to Neography
2
2
 
3
- Neography is a thin ruby wrapper to the Neo4j Rest API, for more information:
3
+ Neography is a thin Ruby wrapper to the Neo4j Rest API, for more information:
4
4
  * {Getting Started with Neo4j Server}[http://wiki.neo4j.org/content/Getting_Started_with_Neo4j_Server]
5
5
  * {Neo4j Rest API Reference}[http://components.neo4j.org/neo4j-rest/]
6
6
 
7
+ If you want to the full power of Neo4j, you will want to use JRuby and the excellent Neo4j.rb gem at https://github.com/andreasronge/neo4j
7
8
 
8
9
  === Installation
9
10
 
@@ -78,17 +79,42 @@ To Use:
78
79
  @neo.get_path(from, to, relationships, depth=4, algorithm="shortestPath") # finds the shortest path between two nodes
79
80
  @neo.get_paths(from, to, relationships, depth=3, algorithm="allPaths") # finds all paths between two nodes
80
81
 
82
+ nodes = @neo.traverse(id, # the id of the node where the traversal starts
83
+ "nodes", # return_type (can be "nodes", "relationships" or "paths"
84
+ {"order" => "breadth first", # "breadth first" or "depth first" traversal order
85
+ "uniqueness" => "node global", # See Uniqueness in API documentation for options.
86
+ "relationships" => [{"type"=> "roommates", # A hash containg a description of the traversal
87
+ "direction" => "all"}, # two relationships.
88
+ {"type"=> "friends", #
89
+ "direction" => "out"}], #
90
+ "prune evaluator" => {"language" => "javascript", # A prune evaluator (when to stop traversing)
91
+ "body" => "position.endNode().getProperty('age') < 21;"
92
+ "return filter" => {"language" => "builtin", # "all" or "all but start node"
93
+ "name" => "all"},
94
+ "depth" => 4})
95
+
96
+ # "depth" is a short-hand way of specifying a prune evaluator which prunes after a certain depth.
97
+ # If not specified a depth of 1 is used and if a "prune evaluator" is specified instead of a depth, no depth limit is set.
98
+
99
+ Please see the specs for more examples.
100
+
101
+ See Neo4j API for:
102
+ * {Order}[http://components.neo4j.org/neo4j-examples/1.2.M04/apidocs/org/neo4j/graphdb/Traverser.Order.html]
103
+ * {Uniqueness}[http://components.neo4j.org/neo4j-examples/1.2.M04/apidocs/org/neo4j/kernel/Uniqueness.html]
104
+ * {Prune Evaluator}[http://components.neo4j.org/neo4j-examples/1.2.M04/apidocs/org/neo4j/graphdb/StopEvaluator.html]
105
+ * {Return Filter}[http://components.neo4j.org/neo4j-examples/1.2.M04/apidocs/org/neo4j/graphdb/ReturnableEvaluator.html]
106
+
81
107
  === To Do
82
108
 
83
- Path tests
84
- Traverse tests
85
- @neo.traverse()
86
- examples
109
+ * More tests
110
+ * examples
111
+ * batch import with typhoeus ?
112
+ * create proper objects for Node and Relationship
87
113
 
88
114
  === License
89
115
 
90
116
  * Neography - MIT, see the LICENSE file http://github.com/maxdemarzi/neography/tree/master/LICENSE.
91
117
  * Lucene - Apache, see http://lucene.apache.org/java/docs/features.html
92
- * Neo4j - Dual free software/commercial license, see http://neo4j.org/
118
+ * Neo4j - Dual free software/commercial license, see http://neo4j.org
93
119
 
94
120
 
@@ -161,6 +161,16 @@ module Neography
161
161
  index
162
162
  end
163
163
 
164
+ def traverse(id, return_type, description)
165
+ options = { :body => {"order" => get_order(description["order"]),
166
+ "uniqueness" => get_uniqueness(description["uniqueness"]),
167
+ "relationships" => description["relationships"],
168
+ "prune evaluator" => description["prune evaluator"],
169
+ "return filter" => description["return filter"],
170
+ "max depth" => get_depth(description["depth"]), }.to_json, :headers => {'Content-Type' => 'application/json'} }
171
+ traversal = post("/node/#{id}/traverse/#{get_type(return_type)}", options) || Array.new
172
+ end
173
+
164
174
  def get_path(from, to, relationships, depth=1, algorithm="shortestPath")
165
175
  options = { :body => {"to" => self.configuration + "/node/#{to}", "relationships" => relationships, "max depth" => depth, "algorithm" => get_algorithm(algorithm) }.to_json, :headers => {'Content-Type' => 'application/json'} }
166
176
  path = post("/node/#{from}/path", options) || Hash.new
@@ -237,5 +247,49 @@ module Neography
237
247
  end
238
248
  end
239
249
 
250
+ def get_order(order)
251
+ case order
252
+ when :breadth, "breadth", "breadth first", "breadthFirst", :wide, "wide"
253
+ "breadth first"
254
+ else
255
+ "depth first"
256
+ end
257
+ end
258
+
259
+ def get_type(type)
260
+ case type
261
+ when :node, "nodes", :nodes, "nodes"
262
+ "node"
263
+ when :relationship, "relationship", :relationships, "relationships"
264
+ "relationship"
265
+ else
266
+ "path"
267
+ end
268
+ end
269
+
270
+ def get_uniqueness(uniqueness)
271
+ case uniqueness
272
+ when :nodeglobal, "node global", "nodeglobal", "node_global"
273
+ "node global"
274
+ when :nodepath, "node path", "nodepath", "node_path"
275
+ "node path"
276
+ when :noderecent, "node recent", "noderecent", "node_recent"
277
+ "node recent"
278
+ when :relationshipglobal, "relationship global", "relationshipglobal", "relationship_global"
279
+ "relationship global"
280
+ when :relationshippath, "relationship path", "relationshippath", "relationship_path"
281
+ "relationship path"
282
+ when :relationshiprecent, "relationship recent", "relationshiprecent", "relationship_recent"
283
+ "relationship recent"
284
+ else
285
+ "none"
286
+ end
287
+ end
288
+
289
+ def get_depth(depth)
290
+ return 1 if depth.to_i == 0
291
+ depth.to_i
292
+ end
293
+
240
294
  end
241
295
  end
@@ -1,3 +1,3 @@
1
1
  module Neography
2
- VERSION = "0.0.1"
2
+ VERSION = "0.0.2"
3
3
  end
@@ -19,41 +19,235 @@ describe Neography::Rest do
19
19
  end
20
20
 
21
21
  it "can get the shortest path between two nodes" do
22
- pending
22
+ new_node1 = @neo.create_node
23
+ new_node1[:id] = new_node1["self"].split('/').last
24
+ new_node2 = @neo.create_node
25
+ new_node2[:id] = new_node2["self"].split('/').last
26
+ new_node3 = @neo.create_node
27
+ new_node3[:id] = new_node3["self"].split('/').last
28
+ new_node4 = @neo.create_node
29
+ new_node4[:id] = new_node4["self"].split('/').last
30
+ new_node5 = @neo.create_node
31
+ new_node5[:id] = new_node5["self"].split('/').last
32
+ @neo.create_relationship("friends", new_node1[:id], new_node2[:id])
33
+ @neo.create_relationship("friends", new_node2[:id], new_node3[:id])
34
+ @neo.create_relationship("friends", new_node3[:id], new_node4[:id])
35
+ @neo.create_relationship("friends", new_node4[:id], new_node5[:id])
36
+ @neo.create_relationship("friends", new_node3[:id], new_node5[:id])
37
+ path = @neo.get_path(new_node1[:id], new_node5[:id], {"type"=> "friends", "direction" => "out"}, depth=3, algorithm="shortestPath")
38
+ path["start"].should == new_node1["self"]
39
+ path["end"].should == new_node5["self"]
40
+ path["nodes"].should == [new_node1["self"], new_node2["self"], new_node3["self"], new_node5["self"]]
23
41
  end
24
42
 
25
43
  it "can get a simple path between two nodes" do
26
- pending
44
+ new_node1 = @neo.create_node
45
+ new_node1[:id] = new_node1["self"].split('/').last
46
+ new_node2 = @neo.create_node
47
+ new_node2[:id] = new_node2["self"].split('/').last
48
+ new_node3 = @neo.create_node
49
+ new_node3[:id] = new_node3["self"].split('/').last
50
+ new_node4 = @neo.create_node
51
+ new_node4[:id] = new_node4["self"].split('/').last
52
+ new_node5 = @neo.create_node
53
+ new_node5[:id] = new_node5["self"].split('/').last
54
+ @neo.create_relationship("friends", new_node1[:id], new_node2[:id])
55
+ @neo.create_relationship("friends", new_node2[:id], new_node3[:id])
56
+ @neo.create_relationship("friends", new_node3[:id], new_node4[:id])
57
+ @neo.create_relationship("friends", new_node4[:id], new_node5[:id])
58
+ @neo.create_relationship("friends", new_node3[:id], new_node5[:id])
59
+ path = @neo.get_path(new_node1[:id], new_node5[:id], {"type"=> "friends", "direction" => "out"}, depth=3, algorithm="simplePaths")
60
+ path["start"].should == new_node1["self"]
61
+ path["end"].should == new_node5["self"]
62
+ path["nodes"].should == [new_node1["self"], new_node2["self"], new_node3["self"], new_node5["self"]]
27
63
  end
28
64
 
29
- it "can get a path between two nodes of max depth 3" do
30
- pending
65
+ it "fails to get a path between two nodes 3 nodes apart when using max depth of 2" do
66
+ new_node1 = @neo.create_node
67
+ new_node1[:id] = new_node1["self"].split('/').last
68
+ new_node2 = @neo.create_node
69
+ new_node2[:id] = new_node2["self"].split('/').last
70
+ new_node3 = @neo.create_node
71
+ new_node3[:id] = new_node3["self"].split('/').last
72
+ new_node4 = @neo.create_node
73
+ new_node4[:id] = new_node4["self"].split('/').last
74
+ new_node5 = @neo.create_node
75
+ new_node5[:id] = new_node5["self"].split('/').last
76
+ @neo.create_relationship("friends", new_node1[:id], new_node2[:id])
77
+ @neo.create_relationship("friends", new_node2[:id], new_node3[:id])
78
+ @neo.create_relationship("friends", new_node3[:id], new_node4[:id])
79
+ @neo.create_relationship("friends", new_node4[:id], new_node5[:id])
80
+ @neo.create_relationship("friends", new_node3[:id], new_node5[:id])
81
+ path = @neo.get_path(new_node1[:id], new_node5[:id], {"type"=> "friends", "direction" => "out"}, depth=2, algorithm="shortestPath")
82
+ path["start"].should be_nil
83
+ path["end"].should be_nil
31
84
  end
32
85
 
33
86
  it "can get a path between two nodes of a specific relationship" do
34
- pending
87
+ new_node1 = @neo.create_node
88
+ new_node1[:id] = new_node1["self"].split('/').last
89
+ new_node2 = @neo.create_node
90
+ new_node2[:id] = new_node2["self"].split('/').last
91
+ new_node3 = @neo.create_node
92
+ new_node3[:id] = new_node3["self"].split('/').last
93
+ new_node4 = @neo.create_node
94
+ new_node4[:id] = new_node4["self"].split('/').last
95
+ new_node5 = @neo.create_node
96
+ new_node5[:id] = new_node5["self"].split('/').last
97
+ @neo.create_relationship("classmates", new_node1[:id], new_node2[:id])
98
+ @neo.create_relationship("classmates", new_node2[:id], new_node5[:id])
99
+ @neo.create_relationship("friends", new_node1[:id], new_node2[:id])
100
+ @neo.create_relationship("friends", new_node2[:id], new_node3[:id])
101
+ @neo.create_relationship("friends", new_node3[:id], new_node4[:id])
102
+ @neo.create_relationship("friends", new_node4[:id], new_node5[:id])
103
+ path = @neo.get_path(new_node1[:id], new_node5[:id], {"type"=> "friends", "direction" => "out"}, depth=4, algorithm="shortestPath")
104
+ path["start"].should == new_node1["self"]
105
+ path["end"].should == new_node5["self"]
106
+ path["nodes"].should == [new_node1["self"], new_node2["self"], new_node3["self"], new_node4["self"], new_node5["self"]]
35
107
  end
36
108
  end
37
109
 
38
110
  describe "get paths" do
39
111
  it "can get the shortest paths between two nodes" do
40
- pending
112
+ new_node1 = @neo.create_node
113
+ new_node1[:id] = new_node1["self"].split('/').last
114
+ new_node2 = @neo.create_node
115
+ new_node2[:id] = new_node2["self"].split('/').last
116
+ new_node3 = @neo.create_node
117
+ new_node3[:id] = new_node3["self"].split('/').last
118
+ new_node4 = @neo.create_node
119
+ new_node4[:id] = new_node4["self"].split('/').last
120
+ new_node5 = @neo.create_node
121
+ new_node5[:id] = new_node5["self"].split('/').last
122
+ @neo.create_relationship("friends", new_node1[:id], new_node2[:id])
123
+ @neo.create_relationship("friends", new_node2[:id], new_node5[:id])
124
+ @neo.create_relationship("friends", new_node1[:id], new_node3[:id])
125
+ @neo.create_relationship("friends", new_node3[:id], new_node4[:id])
126
+ @neo.create_relationship("friends", new_node4[:id], new_node5[:id])
127
+ @neo.create_relationship("friends", new_node3[:id], new_node5[:id])
128
+ paths = @neo.get_paths(new_node1[:id], new_node5[:id], {"type"=> "friends", "direction" => "out"}, depth=4, algorithm="shortestPath")
129
+ paths.length.should == 2
130
+ paths[0]["length"].should == 2
131
+ paths[0]["start"].should == new_node1["self"]
132
+ paths[0]["end"].should == new_node5["self"]
133
+ paths[1]["length"].should == 2
134
+ paths[1]["start"].should == new_node1["self"]
135
+ paths[1]["end"].should == new_node5["self"]
41
136
  end
42
137
 
43
138
  it "can get all paths between two nodes" do
44
- pending
139
+ new_node1 = @neo.create_node
140
+ new_node1[:id] = new_node1["self"].split('/').last
141
+ new_node2 = @neo.create_node
142
+ new_node2[:id] = new_node2["self"].split('/').last
143
+ new_node3 = @neo.create_node
144
+ new_node3[:id] = new_node3["self"].split('/').last
145
+ new_node4 = @neo.create_node
146
+ new_node4[:id] = new_node4["self"].split('/').last
147
+ new_node5 = @neo.create_node
148
+ new_node5[:id] = new_node5["self"].split('/').last
149
+ @neo.create_relationship("friends", new_node1[:id], new_node2[:id])
150
+ @neo.create_relationship("friends", new_node2[:id], new_node5[:id])
151
+ @neo.create_relationship("friends", new_node1[:id], new_node3[:id])
152
+ @neo.create_relationship("friends", new_node3[:id], new_node4[:id])
153
+ @neo.create_relationship("friends", new_node4[:id], new_node5[:id])
154
+ @neo.create_relationship("friends", new_node3[:id], new_node5[:id])
155
+ paths = @neo.get_paths(new_node1[:id], new_node5[:id], {"type"=> "friends", "direction" => "out"}, depth=4, algorithm="allPaths")
156
+ paths.length.should == 3
157
+ paths[0]["length"].should == 2
158
+ paths[0]["start"].should == new_node1["self"]
159
+ paths[0]["end"].should == new_node5["self"]
160
+ paths[1]["length"].should == 3
161
+ paths[1]["start"].should == new_node1["self"]
162
+ paths[1]["end"].should == new_node5["self"]
163
+ paths[2]["length"].should == 2
164
+ paths[2]["start"].should == new_node1["self"]
165
+ paths[2]["end"].should == new_node5["self"]
45
166
  end
46
167
 
47
168
  it "can get all simple paths between two nodes" do
48
- pending
169
+ new_node1 = @neo.create_node
170
+ new_node1[:id] = new_node1["self"].split('/').last
171
+ new_node2 = @neo.create_node
172
+ new_node2[:id] = new_node2["self"].split('/').last
173
+ new_node3 = @neo.create_node
174
+ new_node3[:id] = new_node3["self"].split('/').last
175
+ new_node4 = @neo.create_node
176
+ new_node4[:id] = new_node4["self"].split('/').last
177
+ new_node5 = @neo.create_node
178
+ new_node5[:id] = new_node5["self"].split('/').last
179
+ @neo.create_relationship("friends", new_node1[:id], new_node2[:id])
180
+ @neo.create_relationship("friends", new_node2[:id], new_node1[:id])
181
+ @neo.create_relationship("friends", new_node2[:id], new_node5[:id])
182
+ @neo.create_relationship("friends", new_node1[:id], new_node3[:id])
183
+ @neo.create_relationship("friends", new_node3[:id], new_node4[:id])
184
+ @neo.create_relationship("friends", new_node4[:id], new_node5[:id])
185
+ @neo.create_relationship("friends", new_node3[:id], new_node5[:id])
186
+ paths = @neo.get_paths(new_node1[:id], new_node5[:id], {"type"=> "friends", "direction" => "out"}, depth=4, algorithm="allSimplePaths")
187
+ paths.length.should == 3
188
+ paths[0]["length"].should == 2
189
+ paths[0]["start"].should == new_node1["self"]
190
+ paths[0]["end"].should == new_node5["self"]
191
+ paths[1]["length"].should == 3
192
+ paths[1]["start"].should == new_node1["self"]
193
+ paths[1]["end"].should == new_node5["self"]
194
+ paths[2]["length"].should == 2
195
+ paths[2]["start"].should == new_node1["self"]
196
+ paths[2]["end"].should == new_node5["self"]
49
197
  end
50
198
 
51
- it "can get paths between two nodes of max depth 3" do
52
- pending
53
- end
199
+ it "can get paths between two nodes of max depth 2" do
200
+ new_node1 = @neo.create_node
201
+ new_node1[:id] = new_node1["self"].split('/').last
202
+ new_node2 = @neo.create_node
203
+ new_node2[:id] = new_node2["self"].split('/').last
204
+ new_node3 = @neo.create_node
205
+ new_node3[:id] = new_node3["self"].split('/').last
206
+ new_node4 = @neo.create_node
207
+ new_node4[:id] = new_node4["self"].split('/').last
208
+ new_node5 = @neo.create_node
209
+ new_node5[:id] = new_node5["self"].split('/').last
210
+ @neo.create_relationship("friends", new_node1[:id], new_node2[:id])
211
+ @neo.create_relationship("friends", new_node2[:id], new_node5[:id])
212
+ @neo.create_relationship("friends", new_node1[:id], new_node3[:id])
213
+ @neo.create_relationship("friends", new_node3[:id], new_node4[:id])
214
+ @neo.create_relationship("friends", new_node4[:id], new_node5[:id])
215
+ @neo.create_relationship("friends", new_node3[:id], new_node5[:id])
216
+ paths = @neo.get_paths(new_node1[:id], new_node5[:id], {"type"=> "friends", "direction" => "out"}, depth=2, algorithm="allPaths")
217
+ paths.length.should == 2
218
+ paths[0]["length"].should == 2
219
+ paths[0]["start"].should == new_node1["self"]
220
+ paths[0]["end"].should == new_node5["self"]
221
+ paths[1]["length"].should == 2
222
+ paths[1]["start"].should == new_node1["self"]
223
+ paths[1]["end"].should == new_node5["self"] end
54
224
 
55
225
  it "can get paths between two nodes of a specific relationship" do
56
- pending
226
+ new_node1 = @neo.create_node
227
+ new_node1[:id] = new_node1["self"].split('/').last
228
+ new_node2 = @neo.create_node
229
+ new_node2[:id] = new_node2["self"].split('/').last
230
+ new_node3 = @neo.create_node
231
+ new_node3[:id] = new_node3["self"].split('/').last
232
+ new_node4 = @neo.create_node
233
+ new_node4[:id] = new_node4["self"].split('/').last
234
+ new_node5 = @neo.create_node
235
+ new_node5[:id] = new_node5["self"].split('/').last
236
+ @neo.create_relationship("classmates", new_node1[:id], new_node2[:id])
237
+ @neo.create_relationship("classmates", new_node2[:id], new_node5[:id])
238
+ @neo.create_relationship("friends", new_node1[:id], new_node2[:id])
239
+ @neo.create_relationship("friends", new_node2[:id], new_node3[:id])
240
+ @neo.create_relationship("friends", new_node3[:id], new_node4[:id])
241
+ @neo.create_relationship("friends", new_node4[:id], new_node5[:id])
242
+ @neo.create_relationship("classmates", new_node1[:id], new_node3[:id])
243
+ @neo.create_relationship("classmates", new_node3[:id], new_node5[:id])
244
+ paths = @neo.get_paths(new_node1[:id], new_node5[:id], {"type"=> "classmates", "direction" => "out"}, depth=4, algorithm="allPaths")
245
+ paths[0]["length"].should == 2
246
+ paths[0]["start"].should == new_node1["self"]
247
+ paths[0]["end"].should == new_node5["self"]
248
+ paths[1]["length"].should == 2
249
+ paths[1]["start"].should == new_node1["self"]
250
+ paths[1]["end"].should == new_node5["self"]
57
251
  end
58
252
 
59
253
  end
@@ -0,0 +1,230 @@
1
+ require File.join(File.dirname(__FILE__), '..', 'spec_helper')
2
+
3
+ describe Neography::Rest do
4
+ before(:each) do
5
+ @neo = Neography::Rest.new
6
+ end
7
+
8
+ describe "traverse" do
9
+ it "can traverse the graph and return nodes" do
10
+ new_node1 = @neo.create_node
11
+ new_node1[:id] = new_node1["self"].split('/').last
12
+ new_node2 = @neo.create_node
13
+ new_node2[:id] = new_node2["self"].split('/').last
14
+ new_node3 = @neo.create_node
15
+ new_node3[:id] = new_node3["self"].split('/').last
16
+ new_node4 = @neo.create_node
17
+ new_node4[:id] = new_node4["self"].split('/').last
18
+ new_node5 = @neo.create_node
19
+ new_node5[:id] = new_node5["self"].split('/').last
20
+ @neo.create_relationship("friends", new_node1[:id], new_node2[:id])
21
+ @neo.create_relationship("friends", new_node2[:id], new_node3[:id])
22
+ @neo.create_relationship("friends", new_node3[:id], new_node4[:id])
23
+ @neo.create_relationship("friends", new_node4[:id], new_node5[:id])
24
+ @neo.create_relationship("friends", new_node3[:id], new_node5[:id])
25
+ nodes = @neo.traverse(new_node1[:id], "nodes", {"relationships" => {"type"=> "friends", "direction" => "out"}, "depth" => 4} )
26
+ nodes.should_not be_nil
27
+ nodes[0]["self"].should == new_node2["self"]
28
+ nodes[1]["self"].should == new_node3["self"]
29
+ nodes[2]["self"].should == new_node4["self"]
30
+ nodes[3]["self"].should == new_node5["self"]
31
+ end
32
+
33
+ it "can traverse the graph and return relationships" do
34
+ new_node1 = @neo.create_node
35
+ new_node1[:id] = new_node1["self"].split('/').last
36
+ new_node2 = @neo.create_node
37
+ new_node2[:id] = new_node2["self"].split('/').last
38
+ new_node3 = @neo.create_node
39
+ new_node3[:id] = new_node3["self"].split('/').last
40
+ new_node4 = @neo.create_node
41
+ new_node4[:id] = new_node4["self"].split('/').last
42
+ new_node5 = @neo.create_node
43
+ new_node5[:id] = new_node5["self"].split('/').last
44
+
45
+ new_relationship1= @neo.create_relationship("friends", new_node1[:id], new_node2[:id])
46
+ new_relationship2= @neo.create_relationship("friends", new_node2[:id], new_node3[:id])
47
+ new_relationship3= @neo.create_relationship("friends", new_node3[:id], new_node4[:id])
48
+ new_relationship4= @neo.create_relationship("friends", new_node4[:id], new_node5[:id])
49
+ new_relationship5= @neo.create_relationship("friends", new_node3[:id], new_node5[:id])
50
+
51
+ relationships = @neo.traverse(new_node1[:id], "relationships", {"relationships" => {"type"=> "friends", "direction" => "out"}, "depth" => 4} )
52
+ relationships.should_not be_nil
53
+
54
+ relationships[0]["self"].should == new_relationship1["self"]
55
+ relationships[1]["self"].should == new_relationship2["self"]
56
+ relationships[2]["self"].should == new_relationship3["self"]
57
+ relationships[3]["self"].should == new_relationship4["self"]
58
+ end
59
+
60
+ it "can traverse the graph and return paths" do
61
+ new_node1 = @neo.create_node
62
+ new_node1[:id] = new_node1["self"].split('/').last
63
+ new_node2 = @neo.create_node
64
+ new_node2[:id] = new_node2["self"].split('/').last
65
+ new_node3 = @neo.create_node
66
+ new_node3[:id] = new_node3["self"].split('/').last
67
+ new_node4 = @neo.create_node
68
+ new_node4[:id] = new_node4["self"].split('/').last
69
+ new_node5 = @neo.create_node
70
+ new_node5[:id] = new_node5["self"].split('/').last
71
+
72
+ new_relationship1= @neo.create_relationship("friends", new_node1[:id], new_node2[:id])
73
+ new_relationship2= @neo.create_relationship("friends", new_node2[:id], new_node3[:id])
74
+ new_relationship3= @neo.create_relationship("friends", new_node3[:id], new_node4[:id])
75
+ new_relationship4= @neo.create_relationship("friends", new_node4[:id], new_node5[:id])
76
+ new_relationship5= @neo.create_relationship("friends", new_node3[:id], new_node5[:id])
77
+
78
+ paths = @neo.traverse(new_node1[:id], "paths", {"relationships" => {"type"=> "friends", "direction" => "out"}, "depth" => 4} )
79
+ paths.should_not be_nil
80
+
81
+ paths[0]["nodes"].should == [new_node1["self"], new_node2["self"]]
82
+ paths[1]["nodes"].should == [new_node1["self"], new_node2["self"], new_node3["self"]]
83
+ paths[2]["nodes"].should == [new_node1["self"], new_node2["self"], new_node3["self"], new_node4["self"]]
84
+ paths[3]["nodes"].should == [new_node1["self"], new_node2["self"], new_node3["self"], new_node4["self"], new_node5["self"]]
85
+ end
86
+
87
+ it "can traverse the graph up to a certain depth" do
88
+ new_node1 = @neo.create_node
89
+ new_node1[:id] = new_node1["self"].split('/').last
90
+ new_node2 = @neo.create_node
91
+ new_node2[:id] = new_node2["self"].split('/').last
92
+ new_node3 = @neo.create_node
93
+ new_node3[:id] = new_node3["self"].split('/').last
94
+ new_node4 = @neo.create_node
95
+ new_node4[:id] = new_node4["self"].split('/').last
96
+ new_node5 = @neo.create_node
97
+ new_node5[:id] = new_node5["self"].split('/').last
98
+
99
+ new_relationship1= @neo.create_relationship("friends", new_node1[:id], new_node2[:id])
100
+ new_relationship2= @neo.create_relationship("friends", new_node2[:id], new_node3[:id])
101
+ new_relationship3= @neo.create_relationship("friends", new_node3[:id], new_node4[:id])
102
+ new_relationship4= @neo.create_relationship("friends", new_node4[:id], new_node5[:id])
103
+ new_relationship5= @neo.create_relationship("friends", new_node3[:id], new_node5[:id])
104
+
105
+ paths = @neo.traverse(new_node1[:id], "paths", {"relationships" => {"type"=> "friends", "direction" => "out"}, "depth" => 3} )
106
+ paths.should_not be_nil
107
+
108
+ paths[0]["nodes"].should == [new_node1["self"], new_node2["self"]]
109
+ paths[1]["nodes"].should == [new_node1["self"], new_node2["self"], new_node3["self"]]
110
+ paths[2]["nodes"].should == [new_node1["self"], new_node2["self"], new_node3["self"], new_node4["self"]]
111
+ paths[3]["nodes"].should == [new_node1["self"], new_node2["self"], new_node3["self"], new_node5["self"]]
112
+ end
113
+
114
+ it "can traverse the graph in a certain order" do
115
+ new_node1 = @neo.create_node
116
+ new_node1[:id] = new_node1["self"].split('/').last
117
+ new_node2 = @neo.create_node
118
+ new_node2[:id] = new_node2["self"].split('/').last
119
+ new_node3 = @neo.create_node
120
+ new_node3[:id] = new_node3["self"].split('/').last
121
+ new_node4 = @neo.create_node
122
+ new_node4[:id] = new_node4["self"].split('/').last
123
+ new_node5 = @neo.create_node
124
+ new_node5[:id] = new_node5["self"].split('/').last
125
+
126
+ new_relationship1= @neo.create_relationship("friends", new_node1[:id], new_node2[:id])
127
+ new_relationship2= @neo.create_relationship("friends", new_node2[:id], new_node3[:id])
128
+ new_relationship3= @neo.create_relationship("friends", new_node3[:id], new_node4[:id])
129
+ new_relationship4= @neo.create_relationship("friends", new_node4[:id], new_node5[:id])
130
+ new_relationship5= @neo.create_relationship("friends", new_node3[:id], new_node5[:id])
131
+
132
+ paths = @neo.traverse(new_node1[:id], "paths", {"order" => "breadth first", "relationships" => {"type"=> "friends", "direction" => "out"}, "depth" => 4} )
133
+ paths.should_not be_nil
134
+
135
+ paths[0]["nodes"].should == [new_node1["self"], new_node2["self"]]
136
+ paths[1]["nodes"].should == [new_node1["self"], new_node2["self"], new_node3["self"]]
137
+ paths[2]["nodes"].should == [new_node1["self"], new_node2["self"], new_node3["self"], new_node4["self"]]
138
+ paths[3]["nodes"].should == [new_node1["self"], new_node2["self"], new_node3["self"], new_node5["self"]]
139
+ end
140
+
141
+ it "can traverse the graph with a specific uniqueness" do
142
+ new_node1 = @neo.create_node
143
+ new_node1[:id] = new_node1["self"].split('/').last
144
+ new_node2 = @neo.create_node
145
+ new_node2[:id] = new_node2["self"].split('/').last
146
+ new_node3 = @neo.create_node
147
+ new_node3[:id] = new_node3["self"].split('/').last
148
+ new_node4 = @neo.create_node
149
+ new_node4[:id] = new_node4["self"].split('/').last
150
+ new_node5 = @neo.create_node
151
+ new_node5[:id] = new_node5["self"].split('/').last
152
+
153
+ new_relationship1= @neo.create_relationship("roommates", new_node1[:id], new_node2[:id])
154
+ new_relationship2= @neo.create_relationship("roommates", new_node2[:id], new_node3[:id])
155
+ new_relationship1= @neo.create_relationship("friends", new_node3[:id], new_node2[:id])
156
+ new_relationship2= @neo.create_relationship("friends", new_node2[:id], new_node5[:id])
157
+ new_relationship3= @neo.create_relationship("friends", new_node3[:id], new_node4[:id])
158
+ new_relationship4= @neo.create_relationship("friends", new_node4[:id], new_node5[:id])
159
+ new_relationship5= @neo.create_relationship("friends", new_node3[:id], new_node5[:id])
160
+
161
+ paths = @neo.traverse(new_node1[:id], "paths", {"order" => "breadth first", "uniqueness" => "node global", "relationships" => [{"type"=> "roommates", "direction" => "all"},{"type"=> "friends", "direction" => "out"}], "depth" => 4} )
162
+ paths.should_not be_nil
163
+
164
+ paths[0]["nodes"].should == [new_node1["self"], new_node2["self"]]
165
+ paths[1]["nodes"].should == [new_node1["self"], new_node2["self"], new_node3["self"]]
166
+ paths[2]["nodes"].should == [new_node1["self"], new_node2["self"], new_node5["self"]]
167
+ paths[3]["nodes"].should == [new_node1["self"], new_node2["self"], new_node3["self"], new_node4["self"]]
168
+ end
169
+
170
+ it "can traverse the graph with a prune evaluator" do
171
+ new_node1 = @neo.create_node("age" => 31, "name" => "Max")
172
+ new_node1[:id] = new_node1["self"].split('/').last
173
+ new_node2 = @neo.create_node("age" => 30, "name" => "Helene")
174
+ new_node2[:id] = new_node2["self"].split('/').last
175
+ new_node3 = @neo.create_node("age" => 17, "name" => "Alex")
176
+ new_node3[:id] = new_node3["self"].split('/').last
177
+ new_node4 = @neo.create_node("age" => 24, "name" => "Eric")
178
+ new_node4[:id] = new_node4["self"].split('/').last
179
+ new_node5 = @neo.create_node("age" => 32, "name" => "Leslie")
180
+ new_node5[:id] = new_node5["self"].split('/').last
181
+
182
+ new_relationship1= @neo.create_relationship("friends", new_node1[:id], new_node2[:id])
183
+ new_relationship2= @neo.create_relationship("friends", new_node2[:id], new_node3[:id])
184
+ new_relationship3= @neo.create_relationship("friends", new_node3[:id], new_node4[:id])
185
+ new_relationship4= @neo.create_relationship("friends", new_node4[:id], new_node5[:id])
186
+ new_relationship5= @neo.create_relationship("friends", new_node3[:id], new_node5[:id])
187
+
188
+ paths = @neo.traverse(new_node1[:id],
189
+ "paths",
190
+ {"relationships" => {"type"=> "friends", "direction" => "out"},
191
+ "depth" => 3,
192
+ "prune evaluator" => {"language" => "javascript", "body" => "position.endNode().getProperty('age') < 21;"
193
+ }} )
194
+ paths.should_not be_nil
195
+ paths[0]["nodes"].should == [new_node1["self"], new_node2["self"]]
196
+ paths[1]["nodes"].should == [new_node1["self"], new_node2["self"], new_node3["self"]]
197
+ paths[2].should be_nil
198
+ end
199
+
200
+ it "can traverse the graph with a return filter" do
201
+ new_node1 = @neo.create_node
202
+ new_node1[:id] = new_node1["self"].split('/').last
203
+ new_node2 = @neo.create_node
204
+ new_node2[:id] = new_node2["self"].split('/').last
205
+ new_node3 = @neo.create_node
206
+ new_node3[:id] = new_node3["self"].split('/').last
207
+ new_node4 = @neo.create_node
208
+ new_node4[:id] = new_node4["self"].split('/').last
209
+ new_node5 = @neo.create_node
210
+ new_node5[:id] = new_node5["self"].split('/').last
211
+ @neo.create_relationship("friends", new_node1[:id], new_node2[:id])
212
+ @neo.create_relationship("friends", new_node2[:id], new_node3[:id])
213
+ @neo.create_relationship("friends", new_node3[:id], new_node4[:id])
214
+ @neo.create_relationship("friends", new_node4[:id], new_node5[:id])
215
+ @neo.create_relationship("friends", new_node3[:id], new_node5[:id])
216
+ nodes = @neo.traverse(new_node1[:id], "nodes", {"relationships" => {"type"=> "friends", "direction" => "out"},
217
+ "return filter" => {"language" => "builtin", "name" => "all"},
218
+ "depth" => 4} )
219
+ nodes.should_not be_nil
220
+ nodes[0]["self"].should == new_node1["self"]
221
+ nodes[1]["self"].should == new_node2["self"]
222
+ nodes[2]["self"].should == new_node3["self"]
223
+ nodes[3]["self"].should == new_node4["self"]
224
+ nodes[4]["self"].should == new_node5["self"]
225
+ end
226
+
227
+
228
+ end
229
+
230
+ end
metadata CHANGED
@@ -5,8 +5,8 @@ version: !ruby/object:Gem::Version
5
5
  segments:
6
6
  - 0
7
7
  - 0
8
- - 1
9
- version: 0.0.1
8
+ - 2
9
+ version: 0.0.2
10
10
  platform: ruby
11
11
  authors:
12
12
  - Max De Marzi
@@ -108,7 +108,6 @@ files:
108
108
  - README.rdoc
109
109
  - Rakefile
110
110
  - lib/neography.rb
111
- - lib/neography/config.rb
112
111
  - lib/neography/rest.rb
113
112
  - lib/neography/version.rb
114
113
  - neography.gemspec
@@ -116,6 +115,7 @@ files:
116
115
  - spec/integration/rest_node_spec.rb
117
116
  - spec/integration/rest_path_spec.rb
118
117
  - spec/integration/rest_relationship_spec.rb
118
+ - spec/integration/rest_traverse_spec.rb
119
119
  - spec/spec_helper.rb
120
120
  - spec/support/fake_root_spec.rb
121
121
  has_rdoc: true
@@ -1,152 +0,0 @@
1
- module Neography
2
-
3
- # == Keeps configuration for neography
4
- #
5
- # The most important configuration options are <tt>Neograophy::Config[:server]</tt> and <tt>Neograophy::Config[:port]</tt> which are
6
- # used to locate where the neo4j database and is stored on the network.
7
- # If these options are not supplied then the default of localhost:9999 will be used.
8
- #
9
- # ==== Default Configurations
10
- # <tt>:protocol</tt>:: default <tt>http://</tt> protocol to use (can be https://)
11
- # <tt>:server</tt>:: default <tt>localhost</tt> where the database is stored on the network
12
- # <tt>:port</tt>:: default <tt>7474</tt> what port is listening
13
- #
14
- class Config
15
- # This code is copied from merb-core/config.rb.
16
- class << self
17
- # Returns the hash of default config values for neography
18
- #
19
- # ==== Returns
20
- # Hash:: The defaults for the config.
21
- def defaults
22
- @defaults ||= {
23
- :protocol => 'http://',
24
- :server => 'localhost',
25
- :port => '7474'
26
- }
27
- end
28
-
29
-
30
- # Yields the configuration.
31
- #
32
- # ==== Block parameters
33
- # c :: The configuration parameters, a hash.
34
- #
35
- # ==== Examples
36
- # Neography::Config.use do |config|
37
- # config[:server] = '192.168.1.13'
38
- # end
39
- #
40
- # ==== Returns
41
- # nil
42
- def use
43
- @configuration ||= {}
44
- yield @configuration
45
- nil
46
- end
47
-
48
-
49
- # Set the value of a config entry.
50
- #
51
- # ==== Parameters
52
- # key :: The key to set the parameter for.
53
- # val :: The value of the parameter.
54
- #
55
- def []=(key, val)
56
- (@configuration ||= setup)[key] = val
57
- end
58
-
59
-
60
- # Gets the the value of a config entry
61
- #
62
- # ==== Parameters
63
- # key:: The key of the config entry value we want
64
- #
65
- def [](key)
66
- (@configuration ||= setup)[key]
67
- end
68
-
69
-
70
- # Remove the value of a config entry.
71
- #
72
- # ==== Parameters
73
- # key<Object>:: The key of the parameter to delete.
74
- #
75
- # ==== Returns
76
- # The value of the removed entry.
77
- #
78
- def delete(key)
79
- @configuration.delete(key)
80
- end
81
-
82
-
83
- # Remove all configuration. This can be useful for testing purpose.
84
- #
85
- #
86
- # ==== Returns
87
- # nil
88
- #
89
- def delete_all
90
- @configuration = nil
91
- end
92
-
93
-
94
- # Retrieve the value of a config entry, returning the provided default if the key is not present
95
- #
96
- # ==== Parameters
97
- # key:: The key to retrieve the parameter for.
98
- # default::The default value to return if the parameter is not set.
99
- #
100
- # ==== Returns
101
- # The value of the configuration parameter or the default.
102
- #
103
- def fetch(key, default)
104
- @configuration.fetch(key, default)
105
- end
106
-
107
- # Sets up the configuration
108
- #
109
- # ==== Returns
110
- # The configuration as a hash.
111
- #
112
- def setup()
113
- @configuration = {}
114
- @configuration.merge!(defaults)
115
- @configuration
116
- end
117
-
118
-
119
- # Returns the configuration as a hash.
120
- #
121
- # ==== Returns
122
- # The config as a hash.
123
- #
124
- def to_hash
125
- @configuration
126
- end
127
-
128
- # Returns the config as YAML.
129
- #
130
- # ==== Returns
131
- # The config as YAML.
132
- #
133
- def to_yaml
134
- require "yaml"
135
- @configuration.to_yaml
136
- end
137
-
138
- # Returns the configuration as a string.
139
- #
140
- # ==== Returns
141
- # The config as a string.
142
- #
143
- def to_s
144
- setup
145
- @configuration[:protocol] + @configuration[:server].to_s + ':' + @configuration[:port].to_s
146
- end
147
-
148
-
149
- end
150
- end
151
-
152
- end