.net 实体框架手动数据库更改

.net 实体框架手动数据库更改,.net,entity-framework,.net,Entity Framework,我正在学习一门关于构建.net和mvc5项目的课程。本项目涉及使用数据库的代码优先设计理念。在练习之后,我把一些事情搞混了,所以我去了tutors github代码库并下载了一些类。在其中一节课上,他在一个电影课上有一个名为“流派Id”的栏目,而我把我的版本命名为GenreId。因此,我愚蠢地进入了电影类,调用了列Genre_Id,并进入数据库,手动将列重命名为Genre_Id。这种手动更改立即开始在我的应用程序中引发异常 当我尝试构建我的应用程序时,会抛出系统异常。我做了一些研究,发现一篇文章

我正在学习一门关于构建.net和mvc5项目的课程。本项目涉及使用数据库的代码优先设计理念。在练习之后,我把一些事情搞混了,所以我去了tutors github代码库并下载了一些类。在其中一节课上,他在一个电影课上有一个名为“流派Id”的栏目,而我把我的版本命名为GenreId。因此,我愚蠢地进入了电影类,调用了列Genre_Id,并进入数据库,手动将列重命名为Genre_Id。这种手动更改立即开始在我的应用程序中引发异常

当我尝试构建我的应用程序时,会抛出系统异常。我做了一些研究,发现一篇文章建议重新初始化迁移可以解决异常。因此,我删除了我的migrations文件夹,断开了数据库连接并删除了数据库,以便从头开始重新创建迁移和数据库架构。我似乎不明白的是,当我的电影类不包含该列名时,为什么VisualStudio仍在使用流派Id1创建迁移,而流派Id1是外键

在我从头开始重建整个解决方案之前,有人能帮我吗。我遇到的异常是内部异常:列名“Genre_Id1”无效。我在整个解决方案中搜索了Genre_Id1,检查了我的类,确保在更新数据库之前删除了包含Genre_Id1的add migration InitialMigration,并将其替换为Genre_Id,但我不太确定它在何处定义或拾取此列名,因为构建过程似乎在查找它

在我废弃项目并重新启动之前,我可以尝试其他任何东西


谢谢

您遇到的问题源于EF(而不是您)在EF Core之前选择了错误的默认约定

当您有一个具有navigation属性但没有Explicit FK属性的类时:

public class Movie
{
    // ...
    public Genre Genre { get; set; }
}
隐含的shadow FK属性和列名是
Genre\u Id

但是显式FK属性名称的默认约定是
GenreId
(无下划线)。如果提供,也会更改隐含的列名:

public class Movie
{
    // ...
    public int GenreId { get; set; }
    public Genre Genre { get; set; }
}
public class Movie
{
    // ...
    [Column("Genre_Id")]
    public int GenreId { get; set; }
    public Genre Genre { get; set; }
}
当您命名属性时
Genre\u Id

public class Movie
{
    // ...
    public int Genre_Id { get; set; }
    public Genre Genre { get; set; }
}
按照约定,EF将不会将其识别为FK属性,并将尝试使用默认名称
Genre\u Id
创建隐藏(阴影)属性。由于名称由属性保留,EF会附加一个后缀以使其唯一,因此在生成的SQL中会看到
Genre_Id1

有几种方法可以修复它。我个人更喜欢fluent配置,因为它更干净,但以下是如何使用数据注释解决它:

如果要将FK属性命名为
Genre\u Id
,请使用[
ForeignKey
]属性将其映射为FK:

public class Movie
{
    // ...
    [ForeignKey("Genre")]
    public int Genre_Id { get; set; }
    public Genre Genre { get; set; }
}

如果希望属性名为
GenreId
,请使用[
Column
]属性指定列名:

public class Movie
{
    // ...
    public int GenreId { get; set; }
    public Genre Genre { get; set; }
}
public class Movie
{
    // ...
    [Column("Genre_Id")]
    public int GenreId { get; set; }
    public Genre Genre { get; set; }
}

我建议您总是创建一个显式迁移,看看它包含什么。如果您看到未指定的列,则表明某些不正确的配置导致与EF默认约定冲突。

感谢您的解释,非常有用,现在我了解了这些阴影列的来源。我让它工作了。