【问题标题】:How do I use Fluent Nhibernate many-to-many for optimal performance?如何使用 Fluent Nhibernate 多对多以获得最佳性能?
【发布时间】:2010-07-14 19:09:38
【问题描述】:

我有一个与自身具有多对多关系的产品表(使用两列多对多表),并且我在 Fluent NHibernate 中使用以下代码对其进行了设置:

public class ProductConfiguration : ClassMap<Product>
{
    public ProductConfiguration()
    {
        Table("Product");
        Id(p => p.Id).GeneratedBy.Guid();

        Map(p => p.Name).Not.Nullable().Length(254);
        Map(p => p.Description).Not.Nullable().Length(1000);
        Map(p => p.CreatedAt).Not.Nullable();

        HasManyToMany(p => p.CrossSell)
            .Table("ProductCrossSell")
            .ParentKeyColumn("Id")
            .ChildKeyColumn("ProductId"); 
    }
}

我的 MVC 应用程序有两个使用此设置的页面:

  • 索引 - 使用通用存储库 GetAll 方法显示所有产品。
  • 详细信息 - 使用通用存储库 GetById 方法以多对多的形式显示一个产品和任何相关的交叉销售产品设置。

看起来 NHibernate 默认设置为 LazyLoad 多对多,所以当我启动应用程序并在分析器中观察它时,我可以看到它使用以下警报执行 LazyLoad 多对多“使用不鼓励隐式交易”。

  1. 如何消除此警报?我找不到有关如何将 LazyLoad 包装在事务中以消除警报的任何信息。有可能吗?
  2. 有没有办法通过告诉 NHibernate 每当我要求 GetById 时确保加入表并在一个查询中获取所有内容来避免延迟加载?我尝试在多对多映射中使用 .Fetch.Join() ,但这也影响了我的 GetAll 查询,该查询现在也显示连接的结果集,这是不正确的。

这种简单场景的最佳方法是什么?

谢谢

【问题讨论】:

    标签: nhibernate fluent-nhibernate nhibernate-mapping


    【解决方案1】:
    1. 消除警告的方法是访问对象图并在单个事务中完全填充 UI 元素。

    2. 不是通过配置。您可以创建一个 HQL 查询,该查询渴望获取关联并将该查询用于特定视图。我会坚持延迟加载,除非需要,否则不会进行优化。 HQL 将是:


    return session.CreateQuery("from ProductionConfiguration pc join fetch pc.CrossSell where pc.Id = ?")
        .SetGuid(0, id)
        .List<ProductConfiguration>();
    

    【讨论】:

    • Jamie,你会说“不鼓励使用隐式事务”警报在这种情况下不是什么大问题吗?在视图之前我不会开始遍历关联,因此延迟加载将始终在事务范围之外触发​​。解决它的唯一方法是像你说的那样在事务中急切加载。
    • 我不会担心它,尤其是在读取操作中。在几乎所有情况下,我认为您可以放心地忽略它。毕竟这只是一个警告。 :-)
    【解决方案2】:

    默认情况下,NHibernate 中的所有集合都是延迟加载的。

    您必须通过某种调用触发加载(甚至可能使用调试器监视)

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2015-05-17
      • 1970-01-01
      • 1970-01-01
      • 2011-03-16
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多