[Neo] Read Transactions? Really?
Ryan Levering
rrlevering at gmail.com
Tue Jan 12 06:41:55 CET 2010
I know this has come up a couple of times and that transactions are
being worked on it Traversers, but I just can't get my head around how
people use neo4j transactions in general. When I started writing
neo4j code a couple days ago, I was amazed at two things: 1) how
efficient and fast it was and 2) how easy it was to write. It
remained that way until I started writing more interesting, deep, and
large models.
Now, after several days of working with it, I am fed up with
transaction management in Neo. I feel that the implementation and
strict reliance on transactions ruins those two things that I loved
about it. I understand transaction management in general and have
implemented several systems that relied on SQL transaction management,
but when the simplest read requires a transaction, it makes the code
very cumbersome. In addition, my profiling shows that a lot of
program time is being spent on transaction management in very simple
reading code.
I'm hoping that the reason is that I just haven't figured out the
correct usage pattern for working on nodes and, very importantly,
encapsulating the transaction management in my model. I'm really
looking for a solution here, not just criticizing neo4j. Let's say I
have a User object, for purposes of example. Here are two basic
things I want to do:
1. User.getName()
I want a property off the node. I assume I encapsulate the single
internal getProperty call in a transaction? My accessor code has just
quadrupled in size, even if I am ok with this silly, time-consuming
transaction. Leaving it out means every piece of code in my system
has to understand to start a neo4j transaction just to get the user's
name.
2: for (User user : getUsers())
I want to do something to all the users in the system. There are A
LOT of them and they are all linked to a UserFactory or whatever. I
can't create an internal list, because they won't all fit in memory.
So I wrap the Iterable<Relationship/Node> in an Iterable that wraps
the nodes in POJOs. Only there is no way to do this without enclosing
that loop in a transaction.
Do people just create giant transactions that wrap their entire
programs since they don't work with large graphs/models? Or is your
code entirely littered with transaction = service.beginTx();
transaction.success(); transaction.finish()?
I've looked around on the wiki and site and I can't find good answers
to these questions. The IMDB example transactionalizes things at a
very high level. In a sense, wrapping the entire program (web
request) in a single transaction. I guess that's fine if you have
small operations and use Spring injection, but what if you don't?
More information about the User
mailing list