neo4j-core 0.0.9-java → 0.0.10-java

Sign up to get free protection for your applications and to get access to all the features.
@@ -64,4 +64,4 @@ require 'neo4j-core/cypher/result_wrapper'
64
64
  require 'neo4j/algo'
65
65
  require 'neo4j/cypher'
66
66
  require 'neo4j/node'
67
- require 'neo4j/relationship'
67
+ require 'neo4j/relationship'
@@ -170,6 +170,24 @@ module Neo4j
170
170
  MatchNode.new(self, other, expressions, :outgoing)
171
171
  end
172
172
 
173
+ def outgoing(rel_type)
174
+ node = NodeVar.new(@expressions, @variables)
175
+ MatchRelLeft.new(self, ":`#{rel_type}`", expressions, :outgoing) > node
176
+ node
177
+ end
178
+
179
+ def incoming(rel_type)
180
+ node = NodeVar.new(@expressions, @variables)
181
+ MatchRelLeft.new(self, ":`#{rel_type}`", expressions, :incoming) < node
182
+ node
183
+ end
184
+
185
+ def both(rel_type)
186
+ node = NodeVar.new(@expressions, @variables)
187
+ MatchRelLeft.new(self, ":`#{rel_type}`", expressions, :both) < node
188
+ node
189
+ end
190
+
173
191
  # Incoming relationship to other node
174
192
  # @param [Symbol, #var_name] other either a node (Symbol, #var_name)
175
193
  # @return [MatchRelLeft, MatchNode]
@@ -665,6 +683,7 @@ module Neo4j
665
683
  def initialize(expressions, variables)
666
684
  @var_name = "v#{variables.size}"
667
685
  variables << self
686
+ @variables = variables
668
687
  @expressions = expressions
669
688
  end
670
689
 
@@ -21,18 +21,7 @@ module Neo4j
21
21
  # trigger_on :ntype => 'foo', :name => ['bar', 'foobar']
22
22
  #
23
23
  # prefix_index_name do
24
- # return "" unless Neo4j.running?
25
- # return "" unless @indexer_for.respond_to?(:ref_node_for_class)
26
- # ref_node = @indexer_for.ref_node_for_class.wrapper
27
- # prefix = ref_node.send(:_index_prefix) if ref_node.respond_to?(:_index_prefix)
28
- # prefix ||= ref_node[:name] # To maintain backward compatiblity
29
- # prefix.blank? ? "" : prefix + "_"
30
- # end
31
- #
32
- #
33
- # numeric do
34
- # type = decl_props && decl_props[field.to_sym] && decl_props[field.to_sym][:type]
35
- # type && !type.is_a?(String)
24
+ # "Foo" # this is used for example in multitenancy to let each domain have there own index files
36
25
  # end
37
26
  # end
38
27
  # end
@@ -64,6 +53,17 @@ module Neo4j
64
53
  @_indexer ||= IndexerRegistry.instance.register(Indexer.new(index_config))
65
54
  end
66
55
 
56
+ # You can specify which nodes should be triggered.
57
+ # The index can be triggered by one or more properties having one or more values.
58
+ # This can also be done using the #node_indexer or #rel_indexer methods.
59
+ #
60
+ # @example trigger on property :type being 'MyType1'
61
+ # Neo4j::NodeIndex.trigger_on(:type => 'MyType1')
62
+ #
63
+ def trigger_on(hash)
64
+ _config.trigger_on(hash)
65
+ end
66
+
67
67
 
68
68
  class << self
69
69
  private
@@ -2,7 +2,7 @@ module Neo4j
2
2
  module Core
3
3
 
4
4
  # A mixin which adds indexing behaviour to your own Ruby class
5
- # You are expected to implement the method `wrapped_entity` returning the underlying Neo4j Node or Relationship
5
+ # You are expected to implement the method `java_entity` returning the underlying Neo4j Node or Relationship.
6
6
  module Index
7
7
 
8
8
  # Adds an index on the given property
@@ -16,7 +16,7 @@ module Neo4j
16
16
  # @see Neo4j::Core::Index::ClassMethods#add_index
17
17
  #
18
18
  def add_index(field, value=self[field])
19
- self.class.add_index(wrapped_entity, field.to_s, value)
19
+ self.class.add_index(java_entity, field.to_s, value)
20
20
  end
21
21
 
22
22
  # Removes an index on the given property.
@@ -26,7 +26,7 @@ module Neo4j
26
26
  # @see Neo4j::Core::Index::ClassMethods#rm_index
27
27
  #
28
28
  def rm_index(field, value=self[field])
29
- self.class.rm_index(wrapped_entity, field.to_s, value)
29
+ self.class.rm_index(java_entity, field.to_s, value)
30
30
  end
31
31
 
32
32
  end
@@ -60,7 +60,7 @@ module Neo4j
60
60
 
61
61
  # same as #_java_rel
62
62
  # Used so that we have same method for both relationship and nodes
63
- def wrapped_entity
63
+ def java_entity
64
64
  self
65
65
  end
66
66
 
@@ -29,7 +29,7 @@ module Neo4j
29
29
  iter = iterator
30
30
  while (iter.has_next())
31
31
  rel = iter.next
32
- yield rel.wrapper if match_to_other?(rel)
32
+ yield rel.wrapper if match_between?(rel)
33
33
  end
34
34
  end
35
35
 
@@ -44,27 +44,29 @@ module Neo4j
44
44
  end
45
45
 
46
46
  # @return [true,false] true if it match the specified other node
47
- # @see #to_other
48
- def match_to_other?(rel)
49
- if @to_other.nil?
47
+ # @see #between
48
+ def match_between?(rel)
49
+ if @between.nil?
50
50
  true
51
51
  elsif @dir == :outgoing
52
- rel._end_node == @to_other
52
+ rel._end_node == @between
53
53
  elsif @dir == :incoming
54
- rel._start_node == @to_other
54
+ rel._start_node == @between
55
55
  else
56
- rel._start_node == @to_other || rel._end_node == @to_other
56
+ rel._start_node == @between || rel._end_node == @between
57
57
  end
58
58
  end
59
59
 
60
60
  # Specifies that we only want relationship to the given node
61
- # @param [Neo4j::Node] to_other a node or an object that implements the Neo4j::Core::Equal mixin
61
+ # @param [Neo4j::Node] between a node or an object that implements the Neo4j::Core::Equal mixin
62
62
  # @return self
63
- def to_other(to_other)
64
- @to_other = to_other
63
+ def between(between)
64
+ @between = between
65
65
  self
66
66
  end
67
67
 
68
+ alias_method :to_other, :between
69
+
68
70
  # Deletes all the relationships
69
71
  def del
70
72
  each { |rel| rel.del }
@@ -2,6 +2,54 @@ module Neo4j
2
2
  module Core
3
3
  module Traversal
4
4
 
5
+ class CypherQuery
6
+ include Enumerable
7
+ attr_accessor :query, :return_variable
8
+
9
+ def initialize(start_id, dir, types, query_hash=nil, &block)
10
+ this = self
11
+
12
+ rel_type = ":#{types.map{|x| "`#{x}`"}.join('|')}"
13
+
14
+ @query = Neo4j::Cypher.new do
15
+ default_ret = node(:default_ret)
16
+ n = node(start_id)
17
+ case dir
18
+ when :outgoing then
19
+ n > rel_type > default_ret
20
+ when :incoming then
21
+ n < rel_type < default_ret
22
+ when :both then
23
+ n - rel_type - default_ret
24
+ end
25
+
26
+ # where statement
27
+ ret_maybe = block && self.instance_exec(default_ret, &block)
28
+ ret = ret_maybe.respond_to?(:var_name) ? ret_maybe : default_ret
29
+ if query_hash
30
+ expr = []
31
+ query_hash.each{|pair| expr << (ret[pair[0]] == pair[1])}.to_a
32
+ expr.each_with_index do |obj, i|
33
+ Neo4j::Core::Cypher::ExprOp.new(obj, expr[i+1], "and") if i < expr.size - 1
34
+ end
35
+ end
36
+
37
+ this.return_variable = ret.var_name.to_sym
38
+ ret
39
+ end.to_s
40
+ end
41
+
42
+ def to_s
43
+ @query
44
+ end
45
+
46
+ def each
47
+ Neo4j._query(query).each do |r|
48
+ yield r[return_variable]
49
+ end
50
+ end
51
+ end
52
+
5
53
  # By using this class you can both specify traversals and create new relationships.
6
54
  # This object is return from the Neo4j::Core::Traversal methods.
7
55
  # @see Neo4j::Core::Traversal#outgoing
@@ -17,14 +65,27 @@ module Neo4j
17
65
  if type.nil?
18
66
  raise "Traversing all relationship in direction #{dir.inspect} not supported, only :both supported" unless dir == :both
19
67
  @td = Java::OrgNeo4jKernelImplTraversal::TraversalDescriptionImpl.new.breadth_first()
68
+ elsif (dir == :both)
69
+ both(type)
70
+ elsif (dir == :incoming)
71
+ incoming(type)
72
+ elsif (dir == :outgoing)
73
+ outgoing(type)
20
74
  else
21
- @type = type_to_java(type)
22
- @dir = dir_to_java(dir)
23
- @td = Java::OrgNeo4jKernelImplTraversal::TraversalDescriptionImpl.new.breadth_first().relationships(@type, @dir)
75
+ raise "Illegal direction #{dir.inspect}, expected :outgoing, :incoming or :both"
24
76
  end
25
77
  end
26
78
 
27
79
 
80
+ def query(query_hash = nil, &block)
81
+ # only one direction is supported
82
+ rel_types = [@outgoing_rel_types, @incoming_rel_types, @both_rel_types].find_all { |x| !x.nil? }
83
+ raise "Only one direction is allowed, outgoing:#{@outgoing_rel_types}, incoming:#{@incoming_rel_types}, @both:#{@both_rel_types}" if rel_types.count != 1
84
+ start_id = @from.neo_id
85
+ dir = (@outgoing_rel_types && :outgoing) || (@incoming_rel_types && :incoming) || (@both_rel_types && :both)
86
+ CypherQuery.new(start_id, dir, rel_types.first, query_hash, &block)
87
+ end
88
+
28
89
  # Sets traversing depth first.
29
90
  #
30
91
  # The <tt>pre_or_post</tt> parameter parameter can have two values: :pre or :post
@@ -112,11 +173,19 @@ module Neo4j
112
173
  end
113
174
 
114
175
  def to_s
115
- "NodeTraverser [from: #{@from.neo_id} depth: #{@depth} type: #{@type} dir:#{@dir}"
176
+ "NodeTraverser [from: #{@from.neo_id} depth: #{@depth}"
116
177
  end
117
178
 
118
179
 
119
180
  # Creates a new relationship between given node and self
181
+ # It can create more then one relationship
182
+ #
183
+ # @example One outgoing relationships
184
+ # node.outgoing(:foo) << other_node
185
+ #
186
+ # @example Two outgoing relationships
187
+ # node.outgoing(:foo).outgoing(:bar) << other_node
188
+ #
120
189
  # @param [Neo4j::Node] other_node the node to which we want to create a relationship
121
190
  # @return (see #new)
122
191
  def <<(other_node)
@@ -130,25 +199,49 @@ module Neo4j
130
199
  end
131
200
 
132
201
  # Creates a new relationship between self and given node.
202
+ # It can create more then one relationship
203
+ # This method is used by the <tt><<</tt> operator.
204
+ #
205
+ # @example create one relationship
206
+ # node.outgoing(:bar).new(other_node, rel_props)
207
+ #
208
+ # @example two relationships
209
+ # node.outgoing(:bar).outgoing(:foo).new(other_node, rel_props)
210
+ #
211
+ # @example both incoming and outgoing - two relationships
212
+ # node.both(:bar).new(other_node, rel_props)
213
+ #
214
+ # @see #<<
133
215
  # @param [Hash] props properties of new relationship
134
216
  # @return [Neo4j::Relationship] the created relationship
135
217
  def new(other_node, props = {})
136
- case @dir
137
- when Java::OrgNeo4jGraphdb::Direction::OUTGOING
138
- @from.create_relationship_to(other_node, @type).update(props)
139
- when Java::OrgNeo4jGraphdb::Direction::INCOMING
140
- other_node.create_relationship_to(@from, @type).update(props)
141
- else
142
- raise "Only allowed to create outgoing or incoming relationships (not #@dir)"
143
- end
218
+ @outgoing_rel_types && @outgoing_rel_types.each { |type| _new_out(other_node, type, props) }
219
+ @incoming_rel_types && @incoming_rel_types.each { |type| _new_in(other_node, type, props) }
220
+ @both_rel_types && @both_rel_types.each { |type| _new_both(other_node, type, props) }
221
+ end
222
+
223
+ # @private
224
+ def _new_out(other_node, type, props)
225
+ @from.create_relationship_to(other_node, type_to_java(type)).update(props)
226
+ end
227
+
228
+ # @private
229
+ def _new_in(other_node, type, props)
230
+ other_node.create_relationship_to(@from, type_to_java(type)).update(props)
231
+ end
232
+
233
+ # @private
234
+ def _new_both(other_node, type, props)
235
+ _new_out(other_node, type, props)
236
+ _new_in(other_node, type, props)
144
237
  end
145
238
 
146
239
  # @param (see Neo4j::Core::Traversal#both)
147
240
  # @see Neo4j::Core::Traversal#both
148
241
  def both(type)
149
- @type = type_to_java(type) if type
150
- @dir = dir_to_java(:both)
151
- @td = @td.relationships(type_to_java(type), @dir)
242
+ @both_rel_types ||= []
243
+ @both_rel_types << type
244
+ _add_rel(:both, type)
152
245
  self
153
246
  end
154
247
 
@@ -165,9 +258,9 @@ module Neo4j
165
258
  # @return self
166
259
  # @see Neo4j::Core::Traversal#outgoing
167
260
  def outgoing(type)
168
- @type = type_to_java(type) if type
169
- @dir = dir_to_java(:outgoing)
170
- @td = @td.relationships(type_to_java(type), @dir)
261
+ @outgoing_rel_types ||= []
262
+ @outgoing_rel_types << type
263
+ _add_rel(:outgoing, type)
171
264
  self
172
265
  end
173
266
 
@@ -176,12 +269,19 @@ module Neo4j
176
269
  # @return self
177
270
  # @see Neo4j::Core::Traversal#incoming
178
271
  def incoming(type)
179
- @type = type_to_java(type) if type
180
- @dir = dir_to_java(:incoming)
181
- @td = @td.relationships(type_to_java(type), @dir)
272
+ @incoming_rel_types ||= []
273
+ @incoming_rel_types << type
274
+ _add_rel(:incoming, type)
182
275
  self
183
276
  end
184
277
 
278
+ # @private
279
+ def _add_rel(dir, type)
280
+ t = type_to_java(type)
281
+ d = dir_to_java(dir)
282
+ @td = @td ? @td.relationships(t, d) : Java::OrgNeo4jKernelImplTraversal::TraversalDescriptionImpl.new.breadth_first().relationships(t, d)
283
+ end
284
+
185
285
  # Cuts of of parts of the traversal.
186
286
  # @yield [path]
187
287
  # @yieldparam [Java::OrgNeo4jGraphdb::Path] path the path which can be used to filter nodes
@@ -289,6 +389,7 @@ module Neo4j
289
389
  end
290
390
 
291
391
  end
392
+
292
393
  end
293
394
  end
294
395
  end
@@ -1,5 +1,5 @@
1
1
  module Neo4j
2
2
  module Core
3
- VERSION = "0.0.9"
3
+ VERSION = "0.0.10"
4
4
  end
5
5
  end
@@ -8,6 +8,13 @@ module Neo4j
8
8
  def wrapper
9
9
  self.class.wrapper(self)
10
10
  end
11
+
12
+ # This can be implemented by a wrapper to returned the underlying java node or relationship.
13
+ # You can override this method in your own wrapper class.
14
+ # @return self
15
+ def java_entity
16
+ self
17
+ end
11
18
  end
12
19
  end
13
20
  end
@@ -9,9 +9,26 @@ module Neo4j
9
9
  # *org.neo4j.kernel.impl.core.NodeProxy* object. This java object includes the same mixin as this class. The #class method on the java object
10
10
  # returns Neo4j::Node in order to make it feel like an ordinary Ruby object.
11
11
  #
12
+ # @example Create a node with one property (see {Neo4j::Core::Node::ClassMethods})
13
+ # Neo4j::Node.new(:name => 'andreas')
14
+ #
15
+ # @example Create a relationship (see {Neo4j::Core::Traversal})
16
+ # Neo4j::Node.new.outgoing(:friends) << Neo4j::Node.new
17
+ #
18
+ # @example Finding relationships (see {Neo4j::Core::Rels})
19
+ # node.rels(:outgoing, :friends)
20
+ #
21
+ # @example Lucene index (see {Neo4j::Core::Index})
22
+ # Neo4j::Node.trigger_on(:typex => 'MyTypeX')
23
+ # Neo4j::Node.index(:name)
24
+ # a = Neo4j::Node.new(:name => 'andreas', :typex => 'MyTypeX')
25
+ # # finish_tx
26
+ # Neo4j::Node.find(:name => 'andreas').first.should == a
27
+ #
12
28
  class Node
13
29
  extend Neo4j::Core::Node::ClassMethods
14
30
  extend Neo4j::Core::Wrapper::ClassMethods
31
+ extend Neo4j::Core::Index::ClassMethods
15
32
 
16
33
  include Neo4j::Core::Property
17
34
  include Neo4j::Core::Rels
@@ -20,6 +37,11 @@ module Neo4j
20
37
  include Neo4j::Core::Node
21
38
  include Neo4j::Core::Wrapper
22
39
  include Neo4j::Core::Property::Java # for documentation purpose only
40
+ include Neo4j::Core::Index
41
+
42
+ node_indexer do
43
+ index_names :exact => 'default_node_index_exact', :fulltext => 'default_node_index_fulltext'
44
+ end
23
45
 
24
46
  class << self
25
47
 
@@ -33,6 +55,7 @@ module Neo4j
33
55
  include Neo4j::Core::Equal
34
56
  include Neo4j::Core::Node
35
57
  include Neo4j::Core::Wrapper
58
+ include Neo4j::Core::Index
36
59
  end
37
60
  end
38
61
  end
@@ -29,17 +29,26 @@ module Neo4j
29
29
  #
30
30
  # node.outgoing(:friends) << other_node << yet_another_node
31
31
  #
32
+ # @example lucene index
33
+ # Neo4j::Relationship.trigger_on(:typey => 123)
34
+ # Neo4j::Relationship.index(:name)
35
+ # a = Neo4j::Relationship.new(:friends, Neo4j::Node.new, Neo4j::Node.new, :typey => 123, :name => 'kalle')
36
+ # # Finish tx
37
+ # Neo4j::Relationship.find(:name => 'kalle').first.should be_nil
38
+ #
32
39
  # @see http://api.neo4j.org/current/org/neo4j/graphdb/Relationship.html
33
40
  #
34
41
  class Relationship
35
42
  extend Neo4j::Core::Relationship::ClassMethods
36
43
  extend Neo4j::Core::Wrapper::ClassMethods
44
+ extend Neo4j::Core::Index::ClassMethods
37
45
 
38
46
  include Neo4j::Core::Property
39
47
  include Neo4j::Core::Equal
40
48
  include Neo4j::Core::Relationship
41
49
  include Neo4j::Core::Wrapper
42
50
  include Neo4j::Core::Property::Java # for documentation purpose only
51
+ include Neo4j::Core::Index
43
52
 
44
53
 
45
54
  # (see Neo4j::Core::Relationship::ClassMethods#new)
@@ -47,6 +56,10 @@ module Neo4j
47
56
  end
48
57
 
49
58
 
59
+ rel_indexer do
60
+ index_names :exact => 'default_rel_index_exact', :fulltext => 'default_rel_index_fulltext'
61
+ end
62
+
50
63
  class << self
51
64
  def extend_java_class(java_clazz) #:nodoc:
52
65
  java_clazz.class_eval do
@@ -54,6 +67,7 @@ module Neo4j
54
67
  include Neo4j::Core::Equal
55
68
  include Neo4j::Core::Relationship
56
69
  include Neo4j::Core::Wrapper
70
+ include Neo4j::Core::Index
57
71
  end
58
72
  end
59
73
 
metadata CHANGED
@@ -2,7 +2,7 @@
2
2
  name: neo4j-core
3
3
  version: !ruby/object:Gem::Version
4
4
  prerelease:
5
- version: 0.0.9
5
+ version: 0.0.10
6
6
  platform: java
7
7
  authors:
8
8
  - Andreas Ronge
@@ -10,7 +10,7 @@ autorequire:
10
10
  bindir: bin
11
11
  cert_chain: []
12
12
 
13
- date: 2012-04-15 00:00:00 Z
13
+ date: 2012-04-17 00:00:00 Z
14
14
  dependencies:
15
15
  - !ruby/object:Gem::Dependency
16
16
  name: neo4j-community