How to make the NHibernate property always considered dirty when using dynamic update or insert?

I am looking for help with a problem with NHibernate that has been listening to me for a while. Shortly speaking:

I am looking for a way, in the first level cache, to "reset" a property for an object every time I do an update or insert.

What I want to achieve is that the property in question will always be considered polluted by NHibernate when using dynamic update or insert.

The source of this is that I know that if the transaction was successful, the column I want to โ€œresetโ€ will be set to Null in the database using a trigger. On the other hand, the first level cache does not know this, and therefore NHibernate will think that the property was not updated when I set it to the same value as in the previous update / insert. The catch is that my trigger depends on the value set. As a result, the mess is that if I want to use dynamic update or insert Im, I can only update / insert the object once without updating it after that (which I really don't want to do).

Advice or help would be greatly appreciated because Ive really hit the wall here.

+4
source share
1 answer

NHibernate provides many places to expand. Among them is the IInterceptor session. There is documentation with many details:

http://nhibernate.info/doc/nh/en/index.html#objectstate-interceptors

In this case, we can create our custom one, which will observe our object (for example, Client ) and a property that needs to be updated every time (for example, Code ). Thus, our implementation may look like this:

 public class MyInterceptor : EmptyInterceptor { public override int[] FindDirty(object entity, object id, object[] currentState, object[] previousState, string[] propertyNames, NHibernate.Type.IType[] types) { var result = new List<int>(); // we do not care about other entities here if(!(entity is Client)) { return null; } var length = propertyNames.Length; // iterate all properties for(var i = 0; i < length; i++) { var areEqual = currentState[i].Equals(previousState[i]); var isResettingProperty = propertyNames[i] == "Code"; if (!areEqual || isResettingProperty) { result.Add(i); // the index of "Code" property will be added always } } return result.ToArray(); } } 

NOTE. This is just an example! Apply your own logic to check dirty properties.

And we have to wrap Session as follows:

 var interceptor = new MyInterceptor() _configuration.SetInterceptor(interceptor); 

And this is it. If the Client is marked as dynamic update, the Code property will always be set as dirty.

 <class name="Client" dynamic-update="true" ... 
+3
source

Source: https://habr.com/ru/post/1446933/


All Articles