Sql – NHibernate Conversation per Business Transaction and Identity Keys

nhibernatesql server

I would like to implement the conversation per business transaction pattern in a WPF application as described here. Unfortunately this application has a large existing database using SQL Server generated identity keys in all tables.

I know that adding a new object to an NHibernate session will cause it to be inserted if it has an identity key. Fabio has the pattern commiting the current transaction at the end of each request, even though we haven't necesarily finished the entire unit of work yet.

If I understand correctly, this means that my objects are going to be inserted into the database and not removed even if I abandon the unit of work. So:

  • Is this pattern incompatible with identity keys?
  • Are there any reasonable work arounds?
  • Is there a better pattern I can use in this case?

Edit #1:

Some additional comments from Fabio are here.

Edit #2:

Exploring further has lead me to the persist(…) method which is similar to save(…) but just different enough to be confusing. This statement taken from the hibernate FAQs is interesting:

The persist() method also guarantees
that it will not execute an INSERT
statement if it is called outside of
transaction boundaries. This is useful
in long-running conversations with an
extended Session/persistence context.

Surely if it guaranteed the same inside a transaction boundary it would be more useful? I was under the impression not using transactions was frowned upon anyway.

Best Answer

One workaround - you can hold off on your ISession.Saves until you're ready to commit your unit of work, perhaps as a collection of transient instances in your unit of work class.

Also, if your entities are referenced by an existing entity (and it makes sense to), you can cascade the inserts - done consistently, this means you should only need to explicitly insert your aggregate root objects. This is the approach I normally use in this situation.

Related Topic