/** * Copyright (c) 2002-2010 "Neo Technology," * Network Engine for Objects in Lund AB [http://neotechnology.com] * * This file is part of Neo4j. * * Neo4j is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as * published by the Free Software Foundation, either version 3 of the * License, or (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU Affero General Public License for more details. * * You should have received a copy of the GNU Affero General Public License * along with this program. If not, see <http://www.gnu.org/licenses/>. */ package org.neo4j.graphdb; /** * A relationship between two nodes in the graph. A relationship has a start * node, an end node and a {@link RelationshipType type}. You can attach * properties to relationships with the API specified in * {@link PropertyContainer}. * <p> * Relationships are created by invoking the * {@link Node#createRelationshipTo(Node, RelationshipType) * Node.createRelationshipTo()} method on a node as follows: * <p> * <code> * Relationship rel = node.{@link Node#createRelationshipTo(Node, RelationshipType) createRelationshipTo}( otherNode, MyRels.REL_TYPE ); * </code> * <p> * <em>Neo4j doesn't support relationships where the start node and end node are the * same.</em> * <p> * The fact that the relationship API gives meaning to {@link #getStartNode() * start} and {@link #getEndNode() end} nodes implicitly means that all * relationships have a direction. In the example above, <code>rel</code> would * be directed <i>from</i> <code>node</code> <i>to</i> <code>otherNode</code>. A * relationship's start node and end node and their relation to * {@link Direction#OUTGOING} and {@link Direction#INCOMING} are defined so that * the assertions in the following code are <code>true</code>: * * <pre> * <code> * {@link Node} a = graphDb.{@link GraphDatabaseService#createNode() createNode}(), b = graphDb.{@link GraphDatabaseService#createNode() createNode}(); * {@link Relationship} rel = a.{@link Node#createRelationshipTo(Node, RelationshipType) createRelationshipTo}( b, {@link RelationshipType MyRels.REL_TYPE} ); * // Now we have: (a) --- REL_TYPE ---> (b) * * assert rel.{@link Relationship#getStartNode() getStartNode}().equals( a ); * assert rel.{@link Relationship#getEndNode() getEndNode}().equals( b ); * assert rel.{@link Relationship#getNodes() getNodes}()[0].equals( a ) && rel.{@link Relationship#getNodes() getNodes}()[1].equals( b ); * </code> * </pre> * * Even though all relationships have a direction they are equally well * traversed in both directions so there's no need to create duplicate * relationships in the opposite direction (with regard to traversal or * performance). * <p> * Furthermore, Neo4j guarantees that a relationship is never "hanging freely," * i.e. {@link #getStartNode()}, {@link #getEndNode()}, * {@link #getOtherNode(Node)} and {@link #getNodes()} are guaranteed to always * return valid, non-null nodes. * <p> * The id of a relationship is unique, but may not be unique over time since * neo4j reuses deleted ids. See http://wiki.neo4j.org/content/Id_Reuse */ public interface Relationship extends PropertyContainer { /** * Returns the unique id of this relationship. Ids are garbage collected * over time so they are only guaranteed to be unique during a specific time * span: if the relationship is deleted, it's likely that a new relationship * at some point will get the old id. This makes relationship ids brittle as * public APIs. * * @return the id of this node */ public long getId(); /** * Deletes this relationship. Invoking any methods on this relationship * after <code>delete()</code> has returned is invalid and will lead to * unspecified behavior. */ public void delete(); // Node accessors /** * Returns the start node of this relationship. For a definition of how * start node relates to {@link Direction directions} as arguments to the * {@link Node#getRelationships() relationship accessors} in Node, see the * class documentation of Relationship. * * @return the start node of this relationship */ public Node getStartNode(); /** * Returns the end node of this relationship. For a definition of how end * node relates to {@link Direction directions} as arguments to the * {@link Node#getRelationships() relationship accessors} in Node, see the * class documentation of Relationship. * * @return the end node of this relationship */ public Node getEndNode(); /** * A convenience operation that, given a node that is attached to this * relationship, returns the other node. For example if <code>node</code> is * a start node, the end node will be returned, and vice versa. This is a * very convenient operation when you're manually traversing the node space * by invoking one of the {@link Node#getRelationships() getRelationships()} * operations on a node. For example, to get the node "at the other end" of * a relationship, use the following: * <p> * <code> * Node endNode = node.getSingleRelationship( MyRels.REL_TYPE ).getOtherNode( node ); * </code> * <p> * This operation will throw a runtime exception if <code>node</code> is * neither this relationship's start node nor its end node. * * @param node the start or end node of this relationship * @return the other node * @throws RuntimeException if the given node is neither the start nor end * node of this relationship */ public Node getOtherNode( Node node ); /** * Returns the two nodes that are attached to this relationship. The first * element in the array will be the start node, the second element the end * node. * * @return the two nodes that are attached to this relationship */ public Node[] getNodes(); /** * Returns the type of this relationship. A relationship's type is an * immutable attribute that is specified at Relationship * {@link Node#createRelationshipTo creation}. Remember that relationship * types are semantically equivalent if their * {@link RelationshipType#name() names} are {@link Object#equals(Object) * equal}. This is NOT the same as checking for identity equality using the * == operator. If you want to know whether this relationship is of a * certain type, use the {@link #isType(RelationshipType) isType()} * operation. * * @return the type of this relationship */ public RelationshipType getType(); /** * Indicates whether this relationship is of the type <code>type</code>. * This is a convenience method that checks for equality using the contract * specified by RelationshipType, i.e. by checking for equal * {@link RelationshipType#name() names}. * * @param type the type to check * @return <code>true</code> if this relationship is of the type * <code>type</code>, <code>false</code> otherwise or if * <code>null</code> */ public boolean isType( RelationshipType type ); }