NHibernate poor performance on auto flush events?
Let me start by saying that I know that NH doesn't recommend using bulk operations. But as a bit of interest, I was wondering why this is so expensive. For 200 objects in m开发者_运维百科y system, it takes 4 minutes, for which 90+% of the time is spent in DefaultAutoFlushEventListener.OnAutoFlush (Thanks to RedGate Profiler). That's insane. I wonder if anyone has written a custom DefaultAutoFlushEventListener that temporarily works around this hinderence for large repetitive updates.
Update: Actually not an issue with bulk update so much as it is with transactions and FlushMode for queries. But still, what the hell is NH doing when it flushes?
This was a good one. I had each update in a transaction, and within that transaction was a query, that was 2nd level cached, but caused a flush. If you have queries in a transaction, and FlushMode=Auto (basically not turned off) you get a flush. Which is extremely expensive, especially if you have lots of objects in session cache, which we do. Moving this query out of the transaction, increased the query time by a factor of 5. Further more, making the whole thing a transaction, instead of individual transactions was a another big boost because each transaction.commit causes a flush. Updating 1000's of objects takes less than 30 seconds, and I'm too embarassed to say how long that was before. Ahh legacy code.
Update: On further investigation, I have set the FlushMode to Commit for our specific nested transaction model. Without going into too much detail, we have a specific transaction model that accounts for nested transactions when using nested 'Logic' calls. For legacy applications we don't want to set this across the board. The specific issue in this case is the combination of using Transactions and setting the FlushMode to Auto (or Always).
While the standard ISession is not recommended for bulk operations, you can use either a stateless session or DML instead.
精彩评论