entity framework迁移中必填字段的默认值?

我在ASP.NET MVC应用程序中添加了[Required]数据注释。 创build迁移后,运行update-database resuilts,出现以下错误:

无法将值NULL插入到'Director'列中,'MOVIES_cf7bad808fa94f89afa2e5dae1161e78.dbo.Movies'; 列不允许空值。 更新失败。 该语句已终止。

这是由于一些logging在其Director列中有NULL。 我该如何自动将这些值改变为默认值(如“John Doe”)导演?

这是我的模型:

  public class Movie { public int ID { get; set; } [Required] public string Title { get; set; } [DataType(DataType.Date)] public DateTime ReleaseDate { get; set; } [Required] public string Genre { get; set; } [Range(1,100)] [DataType(DataType.Currency)] public decimal Price { get; set; } [StringLength(5)] public string Rating { get; set; } [Required] /// <--- NEW public string Director { get; set; } } 

这是我最近的迁移:

 public partial class AddDataAnnotationsMig : DbMigration { public override void Up() { AlterColumn("dbo.Movies", "Title", c => c.String(nullable: false)); AlterColumn("dbo.Movies", "Genre", c => c.String(nullable: false)); AlterColumn("dbo.Movies", "Rating", c => c.String(maxLength: 5)); AlterColumn("dbo.Movies", "Director", c => c.String(nullable: false)); } public override void Down() { AlterColumn("dbo.Movies", "Director", c => c.String()); AlterColumn("dbo.Movies", "Rating", c => c.String()); AlterColumn("dbo.Movies", "Genre", c => c.String()); AlterColumn("dbo.Movies", "Title", c => c.String()); } } 

如果我没有记错的话,应该这样做:

 AlterColumn("dbo.Movies", "Director", c => c.String(nullable: false, defaultValueSql: "John Doe")); 

除了来自@webdeveloper和@Pushpendra的回答之外,您还需要手动将更新添加到迁移中以更新现有的行。 例如:

 public override void Up() { Sql("UPDATE [dbo].[Movies] SET Title = 'No Title' WHERE Title IS NULL"); AlterColumn("dbo.Movies", "Title", c => c.String(nullable: false,defaultValue:"MyTitle")); } 

这是因为AlterColumn生成DDL来将列的默认值设置为表规范中的某个特定值。 DDL不影响数据库中的现有行。

你实际上是同时进行了两个改变(设置默认值,使列不为NULL),并且每个都是单独有效的,但是由于你同时做了这两个,你可以期望系统'智能地“实现你的意图,并将所有的NULL值设置为默认值,但这不是所有的预期。

假设你只是设置列的默认值,而不是使它不为NULL。 你显然不希望所有的NULLlogging都用你提供的默认值进行更新。

所以,在我看来,这不是一个错误,我不希望EF以我没有明确告诉它做的方式更新我的数据。 开发者负责指导系统如何处理数据。

 public partial class AddDataAnnotationsMig : DbMigration { public override void Up() { AlterColumn("dbo.Movies", "Title", c => c.String(nullable: false,defaultValue:"MyTitle")); AlterColumn("dbo.Movies", "Genre", c => c.String(nullable: false,defaultValue:"Genre")); AlterColumn("dbo.Movies", "Rating", c => c.String(maxLength: 5)); AlterColumn("dbo.Movies", "Director", c => c.String(nullable: false,defaultValue:"Director")); } public override void Down() { AlterColumn("dbo.Movies", "Director", c => c.String()); AlterColumn("dbo.Movies", "Rating", c => c.String()); AlterColumn("dbo.Movies", "Genre", c => c.String()); AlterColumn("dbo.Movies", "Title", c => c.String()); } } 

不知道这个选项总是在附近,但刚刚遇到类似的问题,发现我可以设置默认值,而不需要使用以下任何手动更新

defaultValueSql: "'NY'"

当提供的值是"NY"时,我得到了一个错误,然后我意识到他们正在期待一个像"GETDATE()"的SQL值,所以我尝试了"'NY'" ,并做了这个把戏

整条线看起来像这样

AddColumn("TABLE_NAME", "State", c => c.String(maxLength: 2, nullable: false, defaultValueSql: "'NY'"));

感谢这个答案 ,让我走上正轨

我发现只要在实体属性上使用Auto-Property Initializer就足以完成工作。

例如:

 public class Thing { public bool IsBigThing { get; set; } = false; }