Newbie questions - finding and sorting

49 views
Skip to first unread message

Peter Ehrlich

unread,
Jan 20, 2012, 1:59:01 PM1/20/12
to neo...@googlegroups.com
Hello!

I'm just getting started w/ my first neo4j Rails app.  I'm running in to some questions sorting.

# Why doesn't find work?
jruby-1.6.5 :029 > Goal.all('title: p*').count
 => 0 
jruby-1.6.5 :030 > Goal.find(4).title
 => "play games" 


# Why doesn't sort work?
jruby-1.6.5 :009 > Goal.find(:all, :sort => { :title => :desc }).map &:title
 => ["play games", "play games", "play games", "play games", "play games", "play games", "eat beer"] 
jruby-1.6.5 :010 > Goal.find(:all, :sort => { :title => :asc }).map &:title
 => ["play games", "play games", "play games", "play games", "play games", "play games", "eat beer"] 


I'm running rails 3.1 on webrick, mac osx.  Latest Neo4j (community 1.6 M03) and gem verion 1.3.1.  I haven't done anything for lucene, etc.

Finally, is there any equivalent to the AcitveRecord named scope? (I see there are rules, but those are made on write, and can't accept arguments).

Thanks!
--Peter

Andreas Ronge

unread,
Jan 20, 2012, 3:36:40 PM1/20/12
to neo...@googlegroups.com

Hi
Sort only works with lucene queries, exampels
https://github.com/andreasronge/neo4j/blob/master/spec/rails/finders_spec.rb

The all method use neo traversals.
Try use an index and wildcard query instead.
Regarding scope, what do you want to find ?

sent from my phone

--
You received this message because you are subscribed to the Google Groups "neo4jrb" group.
To view this discussion on the web visit https://groups.google.com/d/msg/neo4jrb/-/iZ0rW0zaWIAJ.
To post to this group, send email to neo...@googlegroups.com.
To unsubscribe from this group, send email to neo4jrb+u...@googlegroups.com.
For more options, visit this group at http://groups.google.com/group/neo4jrb?hl=en.

Andreas Ronge

unread,
Jan 20, 2012, 3:36:40 PM1/20/12
to neo...@googlegroups.com

What do you mean running 1.6 community? No server is needed.

sent from my phone

On Jan 20, 2012 7:59 PM, "Peter Ehrlich" <peter.i...@gmail.com> wrote:
--

Peter Ehrlich

unread,
Jan 24, 2012, 12:04:28 AM1/24/12
to neo...@googlegroups.com
Hm.  Sever turned off and it still works, like you say. ok!

Got the lucene sort going, thanks.  Some new questions though:

 - A node must be indexed to be search.  How can an index be rebuilt, to include already existing nodes?

 - I want to pass in a hash, and have a node and relationship made.  Normally one would use accepts_nested_attributes_for, but this does not allow control over the more complicated case of find_or_create_by(:location_id => '123').  I tried to put my own handling in a before filter, but no callback seems to fire before "add_incoming_rel" does.  I could alias_method_chain the #create method to handle it, but that seems just silly.  Perhaps the only way is to pass in fully fledged locations?

Thanks,
--Peter

Peter Ehrlich

unread,
Jan 24, 2012, 1:41:27 AM1/24/12
to neo...@googlegroups.com
Such a callback would also be useful for automatic serialization.. (status quo afaik here: http://stackoverflow.com/questions/7656397/storing-serialized-data-in-an-object-in-neo4j)

Andreas Ronge

unread,
Jan 24, 2012, 2:16:06 AM1/24/12
to neo...@googlegroups.com
Hi

On Tue, Jan 24, 2012 at 6:04 AM, Peter Ehrlich
<peter.i...@gmail.com> wrote:
> Hm.  Sever turned off and it still works, like you say. ok!
>
> Got the lucene sort going, thanks.  Some new questions though:
>
>  - A node must be indexed to be search.  How can an index be rebuilt, to
> include already existing nodes?

If you already have data that you don't want to lose then have a look
at migrations -
http://neo4j.rubyforge.org/guides/migrations.html#add-index

>
>  - I want to pass in a hash, and have a node and relationship made.
>  Normally one would use accepts_nested_attributes_for, but this does not
> allow control over the more complicated case of
> find_or_create_by(:location_id => '123').  I tried to put my own handling in
> a before filter, but no callback seems to fire before "add_incoming_rel"
> does.  I could alias_method_chain the #create method to handle it, but that
> seems just silly.  Perhaps the only way is to pass in fully fledged
> locations?

Not sure I understand. You want a callback for adding/deleting relationships ?
Maybe a callback for the relationship would help.
Create your own relationship class instead of using the default
Neo4j::Rails::Relationship class.

E.g:
class MyRel < Neo4j::Rails::Relationship
before_create :do_stuff
def do_stuff
puts "start_node #{start_node.attributes.inspect}"
puts "end_node #{end_node.attributes.inspect}"
end
end

class Person
has_n(:friends).relationship(MyRel)
end

Cheers
Andreas

>
> Thanks,


> --Peter
>
> --
> You received this message because you are subscribed to the Google Groups
> "neo4jrb" group.
> To view this discussion on the web visit

> https://groups.google.com/d/msg/neo4jrb/-/7Be5gbRPM1QJ.

Peter Ehrlich

unread,
Jan 24, 2012, 2:59:29 AM1/24/12
to neo...@googlegroups.com
thanks again

The goal is to be able to run this:
User.create(:location => {:location_id => '1234'})

And have this be unobtrusively (ie, in the background) run in the context of the user model, before validations:

self.location = Location.find('location_id: 1234') || Location.new({:location_id => '1234'})

Will think on this more tomorrow..!

Dmytrii Nagirniak

unread,
Jan 24, 2012, 6:35:07 AM1/24/12
to neo...@googlegroups.com, neo...@googlegroups.com
I think you are trying to adopt the tool for something that is specific for your particular case only.
And I think it is partially supported if you'll use accept_nested_attributes (if the hash comes from HTTP like it does in Rails).

Why not just creat a method like User.create_for_location and handle that inside?
Simple, easy and clearly shows the intent.

I would honestly try to avoid callbacks as much as possible (not only with neo4j, but with other ORMs too) simply because they couple things too tightly and make unit testing harder.

Peter Ehrlich

unread,
Jan 25, 2012, 1:04:04 AM1/25/12
to neo...@googlegroups.com
Ok!  Have a look at this gist: https://gist.github.com/1674994

        # This allows anything to be thrown at a relationship and understood.
        # usage:
        #
        # has_one(:location).to(Location)
        # accepts_hash_for :location
        #
        # Will run Location.new with the passed in :location hash.
        # You can also give it a block which returns a location node:
        #
        # accepts_hash_for :location do |location_attributes|
        # Location.find_or_create_by(:name => location_attributes[:name])
        # end

I also created an easy serializer, here: https://gist.github.com/1674551

I really like being able to throw any thing at a model, without so much as a second thought.

Any practicality in looking to include these in neo4j proper, with a little work?  (I don't know how indexing works, but how easy would it be to index on serialized properties, like mongoid?)


A couple side questions:

The migration docs seem out of date.  They call for this, although MigrationMixin can't be found there:

class Person
  include Neo4j::NodeMixin # does also work for Neo4j::Rails::Model
  include Neo4j::MigrationMixin

I fixed it like so, but haven't updated the docs, not knowing if my fix is a hack:

class Goal < Neo4j::Rails::Model 
  include Neo4j::Migrations::NodeMixin

Cheers

Andreas Ronge

unread,
Jan 25, 2012, 7:15:42 AM1/25/12
to neo...@googlegroups.com
Hi

Yes, it looks like a nice feature ! How about having that as a separate gem ?
Maybe that gem is not even specific to Neo4j.rb but could also work for Active Record.
Btw, does it exist  a gem for AR which support this already ?
I would rather remove features from neo4j.rb (we already done this - the  will_paginate support has been moved to a separate gem).

Regarding indexing - it might be possible
The index method will by default index the value of the given property name -
You could for example use a before_save callback and read the property and add an index manually
, e.g. self.add_index(:foo, value_of_serialized properties)).
Not sure about transaction rollback and lucene index in that case. It would be nice to know if it was possible. 


Yes, the migration docs are old and the Neo4j::MigrationMixin has moved.
"include Neo4j::Migrations::NodeMixin " looks correct.

Cheers

--
You received this message because you are subscribed to the Google Groups "neo4jrb" group.
To view this discussion on the web visit https://groups.google.com/d/msg/neo4jrb/-/NR6NUBxvjBcJ.

Peter Ehrlich

unread,
Jan 25, 2012, 12:37:22 PM1/25/12
to neo...@googlegroups.com
Here's the gem: https://github.com/pehrlich/neo4j_helper

I know AR does serialization automatically, but I know nothing about automatic object creation... its been a while time since I made any project with it ;)

I'm going to hold off on indexing right now, I think that's something of a bigger project, and I don't have an immediate need.  It would need a finder syntax, which then begins to touch on all sorts of things.  One of which being an argument that 'key: value' search syntax should be deprecated, in favor of the likes of this: Person.visible.where(last_name: "Jordan").and(first_name: /^d/i).order(:created_at).limit(2) # mongoid query

Presumably, add_index is called automatically in a callback somewhere?

I'll update the docs

Cheers,
--Peter

Peter Ehrlich

unread,
Jan 25, 2012, 8:07:39 PM1/25/12
to neo...@googlegroups.com
Just found the Hashie Clash, which does method chaining.  I like.
Reply all
Reply to author
Forward
0 new messages