【问题标题】:What's the proper design for a one-to-one relationship using Fluent NHibernate?使用 Fluent NHibernate 的一对一关系的正确设计是什么?
【发布时间】:2014-01-02 20:52:31
【问题描述】:

我有一张食谱表。每个配方在表RecipeMetadata 中只有一行,其中包含关于配方的各种数据,出于各种原因我不想存储在Recipes 表中。因此,RecipesRecipeMetadata 具有一对一的映射关系。我的Recipes表如下:

public partial class RecipesMap : ClassMap<Recipes>
{
   public RecipesMap()
   {
      Id(x => x.RecipeId);

      // Map() various columns here

      HasMany(x => x.Ingredients).KeyColumn("RecipeId");
      HasOne(x => x.Metadata);
   }
}

这是我的RecipeMetadata 表:

public partial class RecipeMetadataMap : ClassMap<RecipeMetadata>
{
   public RecipeMetadataMap()
   {
      Id(x => x.RecipeMetadataId);

      // Map() various columns here

      References<Recipes>(x => x.Recipe).Column("RecipeId").Not.Nullable();
   }
}

但是,当我加载Recipe 并访问Metadata 属性时,它会尝试在RecipeMetadata 中找到Recipes.RecipeId = RecipeMetadata.RecipeMetadataId 中的一行。换句话说,它使用两个表上的主键进行连接。

对于我的表架构,RecipeMetadataId 是唯一的一个键,只对那个表,与RecipeId 无关。 RecipeMetadata 有另一列,也称为RecipeId,它对“Recipes”有一个外键约束。 JOIN 应该作为:

Recipes.RecipeId = RecipeMetadata.RecipeId

我的问题:

  1. 我希望 RecipeMetadata 拥有自己的唯一 ID 并使用单独的列将其链接到 Recipes 是不是错了?显然,我有一个 FK 约束以及 RecipeMetadata.RecipeId 上的唯一索引,所以没有性能影响。是的,磁盘上有一些额外的字节用于在这个表上存储一个可以说是不必要的 ID。

  2. 我从未见过一个表,其主键 对另一个表也有外键约束。这是合法的做法吗?这似乎是 nHibernate 喜欢 默认行为的方式。我应该屈服并让它顺其自然吗?

  3. 如果我不想更改数据库(尽管如果有正当理由,我可以说服我这样做),如何使用此模型创建所需的一对一映射?

【问题讨论】:

    标签: c# sql nhibernate fluent-nhibernate


    【解决方案1】:

    NHibernate 对一对一关系有严格的定义。严格但公平。在 NHibernate 中,一对一关系是指 A 表中的 a 行在 B 表中总是有匹配的行。

    1. 对或错,这不适用于 NHibernate 的一对一映射。请注意,您提出的模型与一对多关系的建模方式相同。
    2. 它是合法的,并强制执行一对一的关系。
    3. 由于您希望配方始终具有关联的元数据行,因此我将使用 NHibernate 的一对一映射对其进行建模。或者,您可以将其映射为一对多,但仅将一个实例作为属性公开。

    另请参阅:Ayende's post on the topic

    【讨论】:

    • 那么,您是说 NHibernate 将一对一关系定义为共享 主键 的两个表?
    • 是的,没错,我应该这样说。我应该提到另一种选择,从配方方面将其映射为多对一(引用)。这应该可行,因为您不太可能从元数据导航或查询到配方。
    • 谢谢!这就说得通了。我更喜欢按照 NHibernate 推荐的方式做事,因为这样会减少未来的问题。更改架构有点麻烦(我有一些视图必须重新修改),但现在一切正常。
    • 小提示:使用 NHibernate 有 one-to-one 一个 副作用 :Reciepe 的任何选择 - 将加入两个表中的数据。总是。这就是 NHibernate 的工作原理。 one-to-many here 更难应用,但最终会更灵活。 stackoverflow.com/a/20788642/1679310 的简化方法。总之,不错的Q和A
    • @RadimKöhler - 谢谢。看起来我可能会更好地使用一对多,如果性能变得至关重要..我会在代码中记下这一点。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2011-04-10
    • 2012-09-22
    • 2012-06-28
    • 1970-01-01
    相关资源
    最近更新 更多