65.9K
CodeProject 正在变化。 阅读更多。
Home

EF Code First:添加外键关系

starIconstarIconstarIconstarIcon
emptyStarIcon
starIcon

4.79/5 (17投票s)

2012年1月24日

CPOL

3分钟阅读

viewsIcon

249299

展示如何使用 Entity Framework Code First 添加外键约束。

引言

我们在第一篇文章 EF Code First: 让我们试试中看到了如何使用 EF Code First 生成表。在本文中,我们将了解如何定义外键约束。

使用代码

我们想添加一个新表来使用外键。让我们添加一个新的 Project 类,如下所示

public class Project
{
    public int ProjectId { get; set; }
    public string Name { get; set; }
    public int ManagerId { get; set; }
    public Person Manager { get; set; }
}

您可以看到 Manager 属性的类型是 Person,并且我添加了 ManagerId 属性作为两个表之间的键。

现在像对 Person 一样添加 ProjectDbSet

public DbSet Projects { get; set; }

运行应用程序。您应该会收到一个 InvalidOperationException: 自创建数据库以来,'MyContext' 上下文的模型已更改。手动删除/更新数据库,或者使用 IDatabaseInitializer 实例调用 Database.SetInitializer。 例如,DropCreateDatabaseIfModelChanges 策略将自动删除并重新创建数据库,并可选择使用新数据填充它。

这是因为我们所做的更改对数据库的影响太大,应该删除它。但是,EF 上下文无法自行决定是否可以删除数据库以重新创建它。 解决方案是什么? 有两种解决方案

  • 您可以自己删除数据库并重新运行应用程序。
  • 您可以使用 SetInitializer 使用 DropCreateDatabaseIfModelChanges

我不会解释第一个解决方案。关于第二个解决方案,这是 Code First 允许的功能。您可以要求上下文在模型更改时自动删除并重新创建数据库。您应该非常小心此选项,因为在生产环境中,您可能会丢失所有数据。因为我们不想自己删除数据库,所以我们将看到如何告诉上下文为我们这样做。

在文件 MyContext.cs 中,添加一个新类: MyInitializer

public class MyInitializer : DropCreateDatabaseIfModelChanges
{
}

如您所见,每次模型更改时,数据库都会被删除并重新创建。您可以在初始化程序中做更多的事情,但我们将在本文后面看到这一点。

现在我们将设置初始化程序。返回到 Program.cs 并在 Main 方法的开头添加以下行

Database.SetInitializer(new MyInitializer());

现在您可以运行我们的应用程序了。

发生了什么? 上下文检测到模型中的更改,因此数据库已被删除并重新创建。如果检查数据库中的表,您应该看到两个表: PeopleProjectMain 方法中的 person 已在 People 表中创建。该项目仅出现一次,因为该表被重新创建,因此,之前的记录被删除,并未备份。

如果我们仔细观察,我们可以看到一列名为 ManagerId 和另一列名为 Manager_PersonId。

Project table with FK auto generated

第一个是由于我们的属性 ManagerId 而创建的。第二个是由于我们的导航属性到 Person 列表而创建的。

EF Code First 为我们创建了一个外键,这很棒,但我们想要的是使用 ManagerId 属性。因此,让我们修改我们的 Project 类以使用此属性,而不是让 Code First 为我们创建它。

要配置 Code First 及其生成数据库的方式,有两种方法: DataAnnotationFluent API

让我们使用 DataAnnotation。像这样修改您的类

public class Project
{
    public int ProjectId { get; set; }
    public string Name { get; set; }
    public int ManagerId { get; set; }
    [ForeignKey("ManagerId")]
    public Person Manager { get; set; }
}

您应该添加 System.ComponentModel.DataAnnotations 命名空间。 添加 ForeignKey 属性,我们告诉 Code First 我们希望将 ManagerId 属性用作到 Person 表的外键。

运行应用程序并检查您的数据库模式。 Manager_PersonId 列不再存在,只有 ManagerId 列,并且它被声明为到 People 表的外键。

Project columns with FK

我们刚刚使用 EF Code First 创建了我们的第一个一对多关系。正如我们所看到的,我们可以在类中声明 FK,或者让 Code First 为我们管理它。在下一篇文章中,我们将讨论 Data Annotation 和 Code Fluent。

历史

  • 2012 年 1 月:第一篇文章。
© . All rights reserved.