While the first-level cache in NHibernate is great for production, it can be super annoying for integration tests. Basically I just want to make sure my mapping works and that when I save an entity it goes to the database.
1 2 3 4 5 6 7 8 9 10 11 12 13 |
|
The problem is the next time I call FindById()
I get my object back from the first level cache ISession
, so the Assert passes but looking at the SQL output by NHibernate I can see that no INSERT statement is happening. There are two things that NHibernate needs to do in order for the integration test to work as expected.
- There needs to be an explicit transaction and it needs to be committed in order to actually send the INSERT statements to the database.
- The entity needs to be evicted from the session in order to ensure that the next call to
FindById()
actually goes to the database.
It’s the job of the application to manage the scope of the unit of work. Typically this is per web request in a web app. In a test, it’s per test. This turns into a bunch of boiler-plate noise. Also, this business about evicting the session is an NHibernate specific thing and doesn’t belong in a test that is dealing with an IRepository abstraction.
Since I solve all my problems with a pipeline or decorator, I figured I’d decorate the ISession
and commit and evict on the operations I care about:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 |
|
Then I just work it into a test fixture like this:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 |
|