updated documentation for spring data neo4j 2.0

This commit is contained in:
Michael Hunger
2011-12-19 10:24:43 +01:00
parent d806ce15af
commit c9996cff44
13 changed files with 146 additions and 35 deletions

View File

@@ -3,7 +3,7 @@
<chapter id="reference:aspectj-details">
<title>AspectJ details</title>
<para>
The object graph mapper of Spring Data Neo4j relies heavily on AspectJ. AspectJ is a Java implementation
The advanced mapping mode of Spring Data Neo4j relies heavily on AspectJ. AspectJ is a Java implementation
of the <ulink url="https://secure.wikimedia.org/wikipedia/en/wiki/Aspect-oriented_programming">aspect-oriented
programming</ulink> paradigm that allows easy extraction and controlled application of so-called
cross-cutting concerns. Cross-cutting concerns are typically repetitive tasks in a system (e.g. logging,

Binary file not shown.

After

Width:  |  Height:  |  Size: 121 KiB

View File

@@ -3,7 +3,8 @@
<chapter id="reference:cross-store">
<title>Cross-store persistence</title>
<para>
The Spring Data Neo4j project support cross-store persistence, which allows for parts of the data to be
The Spring Data Neo4j project support cross-store persistence for the advanced mapping mode,
which allows for parts of the data to be
stored in a traditional JPA data store (RDBMS), and other parts in a graph store. This means that an entity
can be partially stored in e.g. MySQL, and partially stored in Neo4j.
</para>
@@ -23,7 +24,7 @@
A backing node in the graph store is only created when the entity has been assigned a JPA ID. Only
then will the association between the two stores be established. Until the entity has been persisted,
its state is just kept inside the POJO (in detached state), and then flushed to the backing graph
database on <code>persist()</code>.
database on the persist operation.
</para>
<para>
The association between the two entities is maintained via a FOREIGN_ID field in the node, that

View File

@@ -8,7 +8,7 @@
of using Spring Data Neo4j instead of the Neo4j API directly.
</para>
<section>
<title>When is Spring Data Neo4j right</title>
<title>When to use Spring Data Neo4j</title>
<para>
The focus of Spring Data Neo4j is to add a convenience layer on top of the Neo4j API. This enables
developers to get up and running with a graph database very quickly, having their domain objects
@@ -16,23 +16,38 @@
more efficient ways to explore and process the graph - if the performance requirements demand it.
</para>
<para>
Like any other object mapping framework, the domain entities that are created, read, or persisted
Like with any other object mapping framework, the domain entities that are created, read, or persisted
represent only a small fraction of the data stored in the database. This is the set needed for a
certain use-case to be displayed, edited or processed in a low throughput fashion. The main advantages
of using an object mapper in this case are the ease of use of real domain objects in your business
logic and also with existing
logic and also the integration with existing
frameworks and libraries that expect Java POJOs as input or create them as results.
</para>
<para>
Spring Data Neo4j, however, was not designed with a major focus on performance. It does add some overhead
to pure graph operations. Something to keep in mind is that any access of properties and relationships
will in general read through down to the database. To avoid multiple reads, it is sensible to store the
result in a local variable in suitable scope (e.g. method, class or jsp).
</para>
to pure graph operations.
</para>
<para>
Most of the overhead comes from the use of the Java Reflection API, which is used to provide
information about annotations, fields and constructors. Some of the information is already cached
by the JVM and the library, so that only the first access gets a performance penalty.
by the JVM and the library infrastructure from Spring-Data-Commons, so that only the first access gets a performance penalty.
Other reflection penalties like field or method access will occur all the time.
</para>
<para>
For the <emphasis>simple mapping</emphasis> it is important to be aware of the size graph of data that is pulled out of the
graph database in a single read and copied to domain entities. That's why Spring Data Neo4j loads
related data not by default. You have to provide an indicator (<code>@Fetch</code>) to do so. Alternatively
the <code>Neo4jTemplate.fetch</code> method offers means of of loading entities and collections of those.
</para>
<para>
For the <emphasis>advanced mapping mode</emphasis> keep in mind that any access of properties and relationships
will in general read through down to the database. To avoid multiple reads, it is sensible to store the
result in a local variable in suitable scope (e.g. method, class or jsp).
</para>
<para>
To evaluate if the performance of Spring Data Neo4j impacts a certain use-case it is sensible to define
performance requirements and measure the actual time in realistic test scenarios for the use-case. Only if
Spring Data Neo4j doesn't perform as fast as required it is recommended to drop down to the native Neo4j API.
</para>
</section>
</chapter>

View File

@@ -1,24 +1,35 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE section PUBLIC "-//OASIS//DTD DocBook XML V4.4//EN" "http://www.oasis-open.org/docbook/xml/4.4/docbookx.dtd">
<section id="reference:programming-model:lifecycle">
<title>Detached node entities</title>
<title>Detached node entities in advanced mapping mode</title>
<para>
This section only applies to the advanced mapping (AspectJ-backed). The simple mapping always detaches entities on
load as it copies the data out of the graph into the entities and stores it back fully too.
</para>
<para>
Node entities can be in two different persistence states: attached or detached. By default, newly created node
entities are in the detached state. When <code>persist()</code> is called on the entity, it becomes
entities are in the detached state. When <code>persist() or template.save()</code> is called on the entity, it becomes
attached to the graph, and its properties and relationships are stores in the database. If
<code>persist()</code> is not called within a transaction, it automatically creates an implicit
transaction for the operation.
the save operation is not called within a transaction, it automatically creates an implicit
transaction only for the operation.
</para>
<para>
Changing an attached entity inside a transaction will immediately write through the changes to
the datastore. Whenever an entity is changed outside of a transaction it becomes detached. The
changes are stored in the entity itself until the next call to <code>persist()</code>.
changes are stored in the entity (its fields) itself until the next call to a save operation.
</para>
<para>
All entities returned by library functions are initially in an attached state.
Just as with any other entity, changing them outside of a transaction detaches them, and they
must be reattached with <code>persist()</code> for the data to be saved.
</para>
<mediaobject>
<imageobject>
<imagedata fileref="attachdetach.png" scalefit="1" contentwidth="15cm"/>
</imageobject>
</mediaobject>
<!--<para>-->
<!--Persisting an entity not only persists that single entity but will traverse its existing and new relationships-->
<!--and persist the cluster of detached entities that it is part of. The borders of this cluster are formed by-->
@@ -82,7 +93,7 @@ movie.setTopActor(actor);
It is a matter of Java references and is not related to the data model in the database.
</para>
<para>
The persist operation (merge) stores all properties of the entity to the graph database
The save operation (merge) stores all properties of the entity to the graph database
and puts the entity in attached mode. There is no need to update the reference to the Java
POJO as the underlying backing node handles the read-through transparently. If multiple
object instances that point to the same node are persisted, the ordering is not important

View File

@@ -3,11 +3,12 @@
<section id="reference:programming-model:validation">
<title>Bean validation (JSR-303)</title>
<para>
Spring Data Neo4j supports property-based validation support. When a property is changed, it is
Spring Data Neo4j supports property-based validation support. When a property is changed and persisted, it is
checked against the annotated constraints, e.g. <code>@Min</code>, <code>@Max</code>,
<code>@Size</code>, etc. Validation errors throw a <code>ValidationException</code>. The validation
support that comes with Spring is used for evaluating the constraints. To use this feature, a validator
has to be registered with the <code>GraphDatabaseContext</code>.
has to be registered with the <code>Neo4jTemplate</code>, which is done automatically by the <code>Neo4jConfiguration</code>
if one is present in the Spring Config.
</para>
<example>
<title>Bean validation</title>

View File

@@ -39,6 +39,26 @@ public class Movie {
</example>
</section>
<section>
<title>@GraphId: Neo4j -id field</title>
<para>
For the simple mapping this is a required field which must be of type <code>Long</code>. It is used
by Spring Data Neo4j to store the node or relationship-id to re-connect the entity to the graph.
</para>
<note>
<para>
It must not be a primitive type because then the "non-attached" case can not be represented as the
default value 0 would point to the reference node. Please make also sure that
an <code>equals()</code> and <code>hashCode()</code> method have to be provided which take the <code>id</code>
field into account (and also handle the "non-attached", null case).
</para>
</note>
<para>
For the advanced mapping such a field is optional. Only if the underlying id has to be accessed, it is
needed.
</para>
</section>
<section>
<title>@GraphProperty: Optional annotation for property fields</title>
<para>

View File

@@ -314,7 +314,7 @@ Iterable<Person> davesFriends = repo.findAllByTraversal(dave,
<title>Composing repositories</title>
<programlisting language="java"><![CDATA[public interface PersonRepository extends GraphRepository<Person>, PersonRepositoryExtension {}
// configure the repositories, preferably via the datagraph:repositories namespace
// configure the repositories, preferably via the neo4j:repositories namespace
// (template reference is optional)
<neo4j:repositories base-package="org.example.repository"
graph-database-context-ref="template"/>

View File

@@ -30,6 +30,13 @@
for classes. Both <code>Neo4jPersistentEntitity</code> as well as <code>Neo4jPersistentProperty</code> provide access to that
information on their scope.
</para>
<note>
<para>
Please note that if you have two collections in an entity pointing to the same relationship and one of them has data and the other is
empty due to the nature of persisting it, one will override the other in the graph so that you might end up with no data. If you want
a relationship-collection to be ignored on save set it to null.
</para>
</note>
<para>
<example>
<title>Examples for loading entities from the graph</title>

View File

@@ -82,7 +82,7 @@
</example>
<para>
One can also configure a stock XA transaction manager (e.g. Atomikos, JOTM, App-Server-TM) to be
used with Neo4j and the other resources. For a bit less secure but fast 1 phase commit best effort,
used with Neo4j and the other resources. For a bit less secure but fast 1-phase-commit-best-effort,
use <code>ChainedTransactionManager</code>, which comes bundled with Spring Data Neo4j. It takes a
list of transaction managers as constructor params and will handle them in order for transaction
start and commit (or rollback) in the reverse order.

View File

@@ -8,16 +8,16 @@
this type information is saved in the graph database.
</para>
<para>
Implementations of <code>TypeRepresentationStrategy</code> take care of persisting this information on entity instance
Implementations of <code>TypeRepresentationStrategy</code> take care of persisting this information during entity instance
creation. They also provide the repository methods that use this type information to perform their operations,
like findAll and count.
like <code>findAll</code> and <code>count</code>. The derived finderMethods also use the type information for graph global queries.
</para>
<para>
There are three available implementations for node entities to choose from.
<itemizedlist>
<listitem>
<para>
<code>IndexingNodeTypeRepresentationStrategy</code>
<code>IndexingNodeTypeRepresentationStrategy</code> this is the default strategy used.
</para>
<para>
Stores entity types in the integrated index. Each entity node gets indexed with its type and
@@ -25,7 +25,7 @@
is called<code>__types__</code>. Additionally, in order to get the type of an entity node, each
node has a property
<code>__type__</code>
with the type of that entity.
with the fully qualified type of that entity.
</para>
</listitem>
<listitem>

View File

@@ -24,6 +24,10 @@
The unit tests demonstrate some other features of Spring Data Neo4j as well. The sample comes
with a minimal configuration for Maven and Spring to get up and running quickly.
</para>
<para>
The Hello Worlds application is available both for the simple mapping (<code>hello-worlds</code>)
and for the advanced mapping (<code>hello-world-aspects</code>).
</para>
<para>
Executing the application creates the following graph in the graph database:
</para>
@@ -42,7 +46,7 @@
roles in different movies. It also uses graph traversal operations to calculate the
<ulink url="http://en.wikipedia.org/wiki/Bacon_number">Bacon number</ulink> of any given actor.
This sample application shows the usage of Spring Data Neo4j in a more complex setting, using several
annotated entities and relationships as well as indexes and graph traversals.
annotated entities and relationships as well as indexes and in-graph indexes and graph traversals.
</para>
<para>
See the readme file for instructions on how to compile and run the application.
@@ -98,5 +102,33 @@
</imageobject>
</mediaobject>
</section>
<section id="samples:cineasts">
<title>Cineasts social movie database</title>
<para>
The cineasts.net application was introduced extensively in the first part of this guide, the
tutorial. The tutorial covers the development of the simple mapping version of cineasts.
</para>
<para>
To document the differences, versions for the advanced mapping (<code>cineasts-aspects</code>)
and accessing the remote server (<code>cineasts-rest</code>) are also available.
</para>
<para>
A online version of cineasts can be found on <ulink url="http://cineasts.net">cineasts.net</ulink>.
A sample dataset of the cineasts databse is available at the neo4j <ulink url="http://sample-data.neo4j.org">sample-data page</ulink>.
</para>
<para>
This is a subset of the visualization of the cineasts graph for the "Matrix" movie.
</para>
<mediaobject>
<imageobject>
<imagedata fileref="../tutorial/cineasts_graph.png" contentwidth="15cm" scalefit="1"/>
</imageobject>
</mediaobject>
<mediaobject>
<imageobject>
<imagedata fileref="../tutorial/cineasts_main.png" contentwidth="15cm" scalefit="1"/>
</imageobject>
</mediaobject>
</section>
</chapter>

View File

@@ -17,15 +17,15 @@
<section>
<title>Dependencies for Spring Data Neo4j Simple Mapping</title>
<para>
For the POJO mapping it is enough to add the <code>org.springframework.data:spring-data-neo4j:2.0.0.RC1</code> dependency
to your project. If you want to use the Cypher query language please add <code>org.neo4j:neo4j-cypher:1.5</code>
For the simple POJO mapping it is enough to add the <code>org.springframework.data:spring-data-neo4j:2.0.0.RELEASE</code> dependency
to your project. If you want to use the Cypher query language please add <code>org.neo4j:neo4j-cypher:1.6.M02</code>
</para>
<example>
<title>Maven dependencies for Spring Data Neo4j</title>
<programlisting language="xml"><![CDATA[<dependency>
<groupId>org.springframework.data</groupId>
<artifactId>spring-data-neo4j</artifactId>
<version>2.0.0.RC1</version>
<version>2.0.0.RELEASE</version>
</dependency>
]]></programlisting>
</example>
@@ -43,8 +43,8 @@
<programlisting language="java"><![CDATA[sourceCompatibility = 1.6
targetCompatibility = 1.6
springVersion = "3.0.6.RELEASE"
springDataNeo4jVersion = "2.0.0.RC1"
springVersion = "3.0.7.RELEASE"
springDataNeo4jVersion = "2.0.0.RELEASE"
aspectjVersion = "1.6.12"
apply from:'https://github.com/SpringSource/spring-data-neo4j/raw/master/build/
@@ -128,7 +128,7 @@ repositories {
<programlisting language="xml"><![CDATA[<dependency>
<groupId>org.springframework.data</groupId>
<artifactId>spring-data-neo4j-aspects</artifactId>
<version>2.0.0.RC1</version>
<version>2.0.0.RELEASE</version>
</dependency>
<dependency>
@@ -139,7 +139,7 @@ repositories {
[<dependency>
<groupId>org.neo4j</groupId>
<artifactId>neo4j-cypher</artifactId>
<version>1.5</version>
<version>1.6.M02</version>
</dependency>]
]]></programlisting>
</example>
@@ -272,6 +272,29 @@ repositories {
]]></programlisting>
</example>
</section>
<section>
<title>Repository Configuration</title>
<para>
Spring Data Neo4j repositories are configured using the <code>&lt;neo4j:repositories></code>
element which defines the base-package (or packages) for the repositories.
A reference to an existing <code>Neo4jTemplate</code> bean reference can be passed in as well.
</para>
<para>
As Spring Data Neo4j repositories build upon the infrastructure provided by
<ulink url="http://static.springsource.org/spring-data/data-commons/docs/current/reference/html/#repositories.create-instances">
Spring Data Commons</ulink>,
the configuration options for repositories described there work here as well.
</para>
<example>
<title>XML configuration for repositories</title>
<programlisting language="xml"><![CDATA[
<neo4j:repositories base-package="org.example.repository"/>
<!-- with template bean reference -->
<neo4j:repositories base-package="org.example.repository" graph-database-context-ref="template"/>
]]></programlisting>
</example>
</section>
<section>
<title>Java-based bean configuration</title>
<para>
@@ -279,7 +302,7 @@ repositories {
</para>
<note>
<para>
For those not familiar with Java-based bean metadata in Spring, we recommend that you
For those not familiar with Java-based bean configuration in Spring, we recommend that you
read up on it first. The Spring documentation has a
<ulink url="http://static.springsource.org/spring/docs/3.1.x/spring-framework-reference/html/new-in-3.0.html#new-java-configuration">high-level introduction</ulink>
as well as
@@ -316,7 +339,8 @@ repositories {
</para>
<para>
Additional beans can be configured to be included in the Neo4j-Configuration. ConversionService for custom conversions,
Additional beans can be configured to be included in the Neo4j-Configuration just by defining them in the Spring context.
ConversionService for custom conversions,
Validators for bean validation, TypeRepresentationStrategyFactory for configuring the in graph type representation,
IndexProviders for custom index handling (e.g. for multi-tenancy),
Entity-Instantiators (with their config) to have more control over the creation of entity instances and much more.