Comments (17)
Hey thanks :)
I was hoping to add support for this. I think the best way is to update the current RelationshipManager class to support it.
Do you have any thoughts on how the api would look? We could specify the properties during connect?
class Person(StructuredNode):
lived_in = RelationshipTo('LIVED_IN', 'Town')
bristol = Town(..)
jim = Person(...)
jim.lived_in.connect(bristol, {'from': 123434, 'to': 23423})
As far a search goes we could either add a separate method to RelationshipManager maybe 'search_by_rel' or we could extend the existing search method to provide rel properties.
There currently isn't the concept of a relationship object in neomodel... it's probably about time I added one.
R
from neomodel.
Actually, since you went through all the effort to define ORM for Node, I'd think it would be even easier to re-use it for Relationship.
Something like this:
class MyRel(RelationShipTo):#OR maybe just deriving from RelationShip)
....name=StringProperty()
....size=IntegrerProperty()
....reltype="FRIEND" #??? either here, or in the __call function, passed below
....Direction="OUTGOING"# Again, may not be used if deriving from RelationShipTo
class OneNode(StructuredNode):
....pass
class MyNode(StructuredNode):
....name=StringProperty()
....other= MyRel('OneNode','FRIEND)
What do you think ?
Sorry, I do no know the format/way to insert code in these comments...
from neomodel.
Also, no matter how you define this, but there should be a way to retrieve & update these informations after creation time.
After looking tourhgh the code, it seems that, indeed, RelationshipManager is the way to go.
Then, it is just a matter of changing the usage of RelationShipTo/RelationShipFrom from function call to proper class usage.
from neomodel.
You can now create properties in a connect operation. Search support to come.
from neomodel.
Thanks for the great work! Looking forward to test neomodel more thoroughly.
On first sight (the README..), I'd like to second opqopqs request here.
It would be really nice to deal with the properties in the same structured manner as with nodes.
A example for this could be bulbflow.
There you have
class Person(Node)
...
relates_to = Relationship('Person', 'Relation')
and
class Relation(Relationship)
strength = StringProperty(default='low')
start_date =
type =
... all the relationship attributes....
If you had that in neomodel, the impact to the API could probably be minimal
rel = jim.relates_to.connect(john) # creates Relationship defaults such as "strength = 'low' "
rel.strength = 'high'
rel.save() # validate
The cool thing would be that you'd have the same level of validation on relationships as on nodes.
I love putting properties into relationships, I think there are many use-cases for this (like the above where the relation attributes are not attributes of the related persons) so it would be nice to make them "first class citizens".
What do you think?
from neomodel.
That's a good idea :)
Currently you can create properties via:
jim.knows.connect(john, {'since': 1365002257})
This allows us to do it in a single operation. returning the relation object on connect is a nice idea!
But as you mentioned this doesn't (currently) provide validation. How about something like this?
class Knows(StructuredRel):
since=DateTimeProperty()
class Person(StructuredNode):
name=StringProperty()
knows=RelationshipTo('Person', 'KNOWS', rel_class='Knows')
jim = Person(name='Jim').save()
bob = Person(name='Bob').save()
jim.knows.connect(bob, {'since': datetime.utcnow()})
I don't think we should specify the relationship type on the relationship class as this prevents re-use of the rel class.
Any ideas on the api on retrieving the rels between two nodes?
R
from neomodel.
I don't think we should specify the relationship type on the relationship class as this prevents re-use of the rel class.
OK got it, there's of course a difference to node handling.
I don't see the need to make the relation class independent of the relationship type. The only reason I can construct is that the same relation class is associated with a different type when used between a different node class. Then your suggestion seems the simplest.
Any ideas on the api on retrieving the rels between two nodes?
My prevailing need is returning relations based on a node, followed by the need to filter and sort the resulting based on a relation attributes.
(I experience that relations of the same type originating from 1 node seem to often have a mutual relation, such as in 'among those I know, who do I know best' - therefore the sorting/filtering)
So, I think a new rel has to be returned on its creation. Also, finding a (filtered/sorted) set of edges from a node is important. I feel that rels = findrel(nodeA, nodeB)
would be less important and could be derived from above. Would be interested in your thoughts about this.
Coming from bulbflows, the api is:
rels = node.outE(), or node.inE(), or node.bothE(). This is inspired by gremlin, the return value is a generator. They can be chained and filtered on type: node.outE('KNOWS').inE(). (where chaining is probably not a good idea if every call is a single cypher query roundtrip - but discussing this goes likely beyond my expertise.)
To adapt to your previous commands, maybe something like:
from_rels = germany.relationship_to('IS_FROM')
?
from neomodel.
Hmm it's a difficult one. I guess with nodes we inflate to objects based on their incoming category node relationship. We also name our category node and outgoing relationships via the class name of our node definition.
Should the relationship class and relationship type have the same kind of mapping?
I am just thinking if you have a large schema, you may end up with relationships of the same neo4j relationship 'type' but used in different contexts. i.e you may not want to share the same relationship class for all relationships of the same type.
Any particular reason you don't like specifying the class whilst defining the relationship on the node class?
Interesting you mention chaining and filtering based on relationship properties, there is a new feature in master allowing more advanced traversing. It's currently undocumented but if you check out my slides (towards the end).
https://github.com/robinedwards/slides/raw/master/sharehoods_skillsmatter.pdf
from neomodel.
@nigelsmall any thoughts on this?
from neomodel.
Traversal: here we go!! this is very cool.. now there's just a need to differentiate whether the return value is to be a rel or a node. The gremlin way's obviously something like node.outRels(type1).inNodes().inRels(type2) but any other thing with more focus on nodes could easily apply.
With your recent addition, how about something as simple as adding a function .return_rels()
which returns the relations traversed between chain elements LAST and LAST-1?
Should the relationship class and relationship type have the same kind of mapping?
I think yes. I would propose a relation_category node. This looks more or less the same like a category node. Since from there you can't have a relation to a relation, you can use the relation type to index the node needed for validation. You may not even need an index, just follow the origin node -> 'category nodes' -> rel_category_node
to find the validator. - Relating to this, I don't see a need for a requirement to "retrieve all relations of type X" because a relation seems to be of interest purely in the context of known nodes. (And technically, relations don't exist per se in neo4j anyway.)
If you wanted to separate rel class and type, another option would be a fixed property name in the relation class. That's similar to the bulbflow way - in bulbflow, there's
class Knows(Relationship):
label = "knows"
...
graph.add_proxy("knows", Knows)
The API is then graph.knows.create(node1, node2)
, and the neo4j level rel type is "knows"
.
Any particular reason you don't like specifying the class whilst defining the relationship on the node class?
nothing really, except DRY if they're the same. (Specifying both the relation class and type in the node class seems to suggest doing both again in every node class that connects with the same relation type.)
from neomodel.
Yea I think something like return_rels() or just 'rels' would do the trick.
I think we need a word other than label as labels is a new feature being introduced in neo4j 2.0. You've sold me on putting the type in the class definition :)
class Knows(Relationship):
__type__ = 'KNOWS'
Rel types with out a type definition can inflate directly to Relationship I guess.
from neomodel.
this looks beautiful! :)
from neomodel.
hey! how is this coming along, are you making any progress on this front? Unfortunately I'm not an expert coder, but if you give me clear pointers I might be able to help?
from neomodel.
I am hoping to get some time over the next few weeks to work on this.
I've been very busy at work on none neo stuff so haven't been able to
commit yet.
I am hoping to make a release to pypi soon which uses py2neo 1.5 (giving
python 3 support).
The next thing I look at will be relationship classes. However if you want
to give it a shot I am happy to provide pointers.
The first thing that comes to mind is the property mechanism is currently
tied to nodes, this needs abstracting slightly.
On 24 May 2013 20:30, bebbi [email protected] wrote:
hey! how is this coming along, are you making any progress on this front?
Unfortunately I'm not an expert coder, but if you give me clear pointers I
might be able to help?—
Reply to this email directly or view it on GitHubhttps://github.com//issues/20#issuecomment-18425098
.
from neomodel.
Guys finally in master you will see support for relationship properties sorry for the delay and thanks for your patience.
I decided against inflating them purely by relationship type as it makes code a lot modular. You may also traverse relationships and filter by their properties (still experimental)
from neomodel.
@robinedwards I like that connect
supports defining properties on the relationship being created. However, I have noticed that disconnect
does not support filtering by properties to narrow down which relationship should be deleted.
As such, when I define multiple instances of a relationship type between two nodes, calling disconnect
on that relationship type deletes all relationships between the two nodes, whereas what I really want is to select and delete only one specific relationship.
Is there any way to do this through the ORM that I've overlooked? I can't find it in the docs.
from neomodel.
Hi @gchorn there currently isn't but patches would be greatly appreciated. perhaps something like delete_where(**filters)?
from neomodel.
Related Issues (20)
- Fix flaky Aura tests in the build pipeline HOT 1
- Relying on Driver's destructor to close the session is deprecated. HOT 1
- Handling multiple labels where class inheritance is not appropriate HOT 10
- Refactor independent `db` functions into `Database`
- Extract the driver out of the library HOT 7
- Use of batch create_or_update raises Exception HOT 2
- Discussion : Do we want to add Property type constraints ?
- Database introspection HOT 1
- Support for Vector indexes HOT 2
- Autocomplete not recognizing parameters of an instance of "StructuredNode". HOT 1
- Failed creating nodes to neo4j aura HOT 1
- Db version parsing in Aura
- Provide "light" options for inspection script HOT 1
- Incorrect query for count of objects HOT 2
- AttributeError: 'SpecificNode' object has no attribute 'unique_relation' HOT 2
- Relationship properties marked with db_property are skipped during inflation HOT 1
- Structured Node `__eq__` works incorrectly for non-persisted nodes.
- Unable to access property values on nodes that inherit from SemiStructuredNode HOT 1
- neomodel_inspect_database - Only writes first relationship HOT 2
- Missing import in contrib __init__ HOT 1
Recommend Projects
-
React
A declarative, efficient, and flexible JavaScript library for building user interfaces.
-
Vue.js
🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
-
Typescript
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
-
TensorFlow
An Open Source Machine Learning Framework for Everyone
-
Django
The Web framework for perfectionists with deadlines.
-
Laravel
A PHP framework for web artisans
-
D3
Bring data to life with SVG, Canvas and HTML. 📊📈🎉
-
Recommend Topics
-
javascript
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
-
web
Some thing interesting about web. New door for the world.
-
server
A server is a program made to process requests and deliver data to clients.
-
Machine learning
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
-
Visualization
Some thing interesting about visualization, use data art
-
Game
Some thing interesting about game, make everyone happy.
Recommend Org
-
Facebook
We are working to build community through open source technology. NB: members must have two-factor auth.
-
Microsoft
Open source projects and samples from Microsoft.
-
Google
Google ❤️ Open Source for everyone.
-
Alibaba
Alibaba Open Source for everyone
-
D3
Data-Driven Documents codes.
-
Tencent
China tencent open source team.
from neomodel.