Other methods of optimistic concurrency
In addition to integer version fields, NHibernate also allows you to use DateTime-based version fields. However, Micorosoft SQL Server has a datetime resolution of about three milliseconds. This may fail when two updates occur almost simultaneously. It’s also possible to use SQL Server 2008’s DateTime2 data type, which has a resolution of 100 nanoseconds, or even SQL Server’s timestamp data type for the version field.
NHibernate allows you to use the more traditional form of optimistic concurrency through the mapping attribute optimistic-lock. A simple example would look like the following code:
<class name="Product" dynamic-update="true"
optimistic-lock=”dirty”>In this case, changing a Product name from Stuff to Junk would generate SQL as shown
in the following code:
UPDATE Product SET Name = 'Junk' /* @p0 */ WHERE Id = '741bd189-78b5-400c-97bd-9db80159ef79' /* @p1 */
AND Name = ‘Stuff’ /* @p2 */This ensures that the Name value hasn’t been changed by another user because this user
read the value. Another user may have changed other properties of this entity.
Another alternative is to set optimistic-lock to all. In this case, a Product update would generate SQL like this:
UPDATE Product SET Name = 'Junk' /* @p0 */ WHERE Id = 'd3458d6e-fa28-4dcb-9130-9db8015cc5bb' /* @p1 */
AND Name = 'Stuff' /* @p2 */ AND Description = 'Cool' /* @p3 */ AND UnitPrice = 100 /* @p4 */
As you might have guessed, in this case, we check the values of all properties.
When optimistic-lock is set to dirty, dynamic-update must be true. Dynamic update simply means that the update statement only updates dirty properties, or properties with changed values, instead of explicitly setting all properties.