在会话中使用太多对象来改善NHibernate性能

时间:2011-03-03 01:36:28

标签: performance nhibernate

我们的应用程序最初是使用NHibernate构建的,并且考虑到批处理的局限性。然而,随着时间的推移,它已经转变为数据处理器,我们正在观察到显着的性能衰退。

会议最终必须维护大约1000个或更多对象,我们的分析显示自动刷新和脏检查是这里最大的违规者。我们尝试关闭自动刷新并在保存/更新操作中自行管理,但这导致批量保存/更新的灾难性能。 我们现在正在考虑从会话中驱逐不需要的对象的选项。

  1. 我遇到了第二级缓存逐出方法(sessionFactory.Evict(typeof(Cat));),它允许我们按类型逐出,但我们不使用二级缓存。我仍然可以使用此方法从第一级缓存中驱逐对象吗?
  2. 我还阅读了一个获取对象的模式,从会话中逐出它们,然后根据需要通过调用Update()对会话重新关联它们。这是一个推荐和接受的模式因为我还读到NH3已经为此设置了一道墙吗? (我们仍然可以使用它,因为我们还没有升级到NH3)
  3. 虽然我们意识到我们没有以最佳方式使用NHibernate,但我们只是想以某种方式改善当前的情况。非常感谢上述问题和任何其他建议/建议的答案。感谢。

    更新
    在查看NH文档和代码之后,我意识到1可能是不可能的。我仍在关注使用Evict()的一些指示或提示。我能够大大减少会话中的对象数量。但是仍然不知道在更新或删除被驱逐的对象时是否需要付出代价。感谢您的帮助。

3 个答案:

答案 0 :(得分:3)

如果不了解您的要求,很难说,但也许您可以使用IStatelessSession。它没有担心的第一级缓存。

Ayende在使用它进行批量操作方面有很好的帖子 here

答案 1 :(得分:0)

为什么不使用更多会话而不是一个大会话?那个,与关闭autoflush一起帮助了我。此外,如果可能,您应该考虑使用HQL进行批量更新。

答案 2 :(得分:0)

我知道这是旧的,但我只是在寻找其他东西时遇到了这个 - 刚解决了这个问题。通过使用多个会话,我确实解决了Trent提到的问题。我会创建一个会话来获取我想要的所有对象,然后关闭该会话。我遇到的情况是迭代列表并对每个对象进行操作并尝试在每次迭代时提交。然后我会在我的列表上创建foreach,在循环中创建和处理一个新会话,将我的对象从列表重新连接到新会话。这需要一个大约2.5小时到2分40秒的过程!

请参阅这篇文章,了解我如何解决它的灵感 - 虽然不完全是因为我有NHibernate的工作包装单元:

http://weblogs.asp.net/ricardoperes/archive/2013/03/21/attaching-disconnected-entities-in-nhibernate-without-going-to-the-database.aspx