【问题标题】:Nhibernate (and ORMs in General): work with Objects or ObjectIds?Nhibernate(和一般的 ORM):使用 Objects 或 ObjectIds?
【发布时间】:2010-07-29 08:47:45
【问题描述】:

这件事一直困扰着我。考虑使用 ORM(例如 Nhiberate)作为数据访问层的(MVC 类型)Web 应用程序。

一方面 - OOP/富域模型方面 - 我觉得我应该传递(引用)我正在谈论的真实对象。

另一方面 - DB/Web App 手 - 我觉得只传递对象的整数 Id 而不是传递反对自己。

考虑一个电子商务目录类型的应用程序:

  • 用户已登录并导航到产品页面。
  • 他们发表评论。
  • 负责保存此评论的控制器操作包含 3 条信息:a) 用户 ID(来自 auth cookie 或任何地方),b) 产品 ID(可能来自查询字符串),以及 c) 评论文本。
  • 现在,这里的最佳做法是什么?当我们知道它们的全部用途是为了让 ORM 可以读取它们的 ID 并设置适当的外部对象时,是否真的值得夸大用户和产品对象(例如,通过从存储库中获取它们,以及所需的所有数据库工作)存储 cmets 的 DB 表中的键?

人们对此有何看法?由于 Web 应用程序的无状态特性,也许应该比其他应用程序给予更多的余地?我想会有“视情况而定”的答案,但也许有些人是这个问题的纯粹主义者。

这是一个可能适用于许多平台的一般问题,但如果给出示例,我希望它们尽可能使用 ASP.NET MVC

谢谢。

【问题讨论】:

  • 如何更容易“只是”传递 id 而不是引用?另外,除了从数据库中获取一个额外的实体之外,这是否在任何方面都更具性能?
  • @Apollodude:当然,一旦你拥有对象,它就不再具有更高的性能——这不是我的意思。但是两次不必要的数据库提取让我畏缩。看看 Daniel Auger 的解决方案,大家都满意。
  • 我同意性能问题是非常有效的。我想了解您追求的其他好处。

标签: asp.net-mvc nhibernate oop orm


【解决方案1】:

正是由于这个原因,NHibernate 才具有加载操作(而不是执行获取)。

session.Save(
  new Comment
      {
         Text = commentTextFromScreen,
         User = session.Load<User>(userID),
         Product = session.Load<Product>(productID)
      }
};

在上面的例子中,你告诉 NHibernate:我知道这些已经存在于数据库中,所以现在不要费心去选择它们。 NHibernate 将为它们返回代理对象,只要您不尝试访问对象的任何属性,就不会对数据库进行选择。

有关更多信息,请查看 Ayende 的博文:The difference between Get, Load, and query by id.

【讨论】:

  • 太棒了!谢谢。我想知道我之前怎么没有注意到这一点:0
  • 更一般地说(在其他情况下),延迟加载和缓存将有助于防止从数据库中获取过多的数据。比起将 id 暴露给大型应用程序,更喜欢这些技术。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2013-02-10
  • 1970-01-01
  • 1970-01-01
  • 2018-08-25
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多