2

我有两个实体密码和密码哈希。Password 有一组 PasswordHashes(这些是具有不同掩码的哈希)。

当我删除密码时,我希望所有关联的 PasswordHash 也被删除。

我做了这样的映射:

mapping.HasMany(x => x.PasswordHashes)
            .Cascade
            .All()
            .Inverse()
            .ReferencedBy(x => x.Password);

我希望生成两个查询:

DELETE FROM "PasswordHash" WHERE "IdPassword" = :p0

显然

DELETE FROM "Password" WHERE "IdPassword" = :p0

相反,NHibernate 生成了 N+1 个查询,如下所示:

DELETE FROM "PasswordHash" WHERE "IdPasswordHash" = :p0 (N)

DELETE FROM "Password" WHERE "IdPassword" = :p0 (1)

如何将这种行为更改为更优化?

编辑:删除代码:

session.Delete(password);
session.Flush();
4

1 回答 1

2

DELETE根据我的研究,在当前版本的 NHibernate (3.3) 中,使用诸如password.hashes.Clear()session.Delete(password)在您的域对象上的操作似乎无法使用单个语句删除子集合。NHibernate 文档提到了一次删除,但我无法通过单向或双向一对多关联的反向和级联的任何组合来完成这项工作。

一种替代方法是使用on-delete="cascade"它禁用 NHibernate 中的级联功能,并将其留给数据库来强制级联删除。更多信息可以在这个nh 用户谷歌小组讨论中找到。

Rippo 在评论部分提到的另一个选项是使用 HQL。您将需要两个语句,因此最好将它们包装在事务中,即

using (var transaction = session.BeginTransaction()
{
   session.Query("delete from PasswordHash h where h.Password = :password")
                   .SetParameter("password", password)
                   .ExecuteUpdate();
   session.Delete(password);
   transaction.Commit();
}
于 2013-03-21T23:23:18.487 回答