使用EFCore,模型有一个带有外键约束的表,它引用另一个表,但此列是可空。像这样的模型:
public class Order
{
[Key]
public int Id { get; set; }
public int Code { get; set; }
public int Amount { get; set; }
... // other fields
}
public class OrderCode
{
[Key]
public int Id { get; set; }
public int Code { get; set; }
public string Description { get; set; }
}
Order o = new Order { Amount = 1 }; // Code is not set and default NULL in DB
orders.Add(o);
db.SaveChanges(); // failure
因此,在某些情况下,Code
是空的,它是数据库中的默认NULL
,但当我通过DbSet.Add
添加对象时,它抛出了一个异常:
Microsoft.EntityFrameworkCore.DbUpdateException:更新条目时出错。有关详细信息,请参见内部异常。---> System.Data.SqlClient.SqlException:INSERT语句与FOREIGN KEY约束“FK_Orders_Code”冲突。数据库“Store”、表“dbo.OrderCode”、列“Id”发生冲突。
看起来EFCore会尝试在insert语句中添加此字段,即使它没有设置,那么有什么方法可以避免这种情况呢?
2条答案
按热度按时间jv4diomz1#
我想你应该使用int。在模型中的代码。int的默认值为0,因此实体框架为“代码”字段设置该值。
ekqde3dh2#
默认情况下,EF Core在INSERT语句中包含所有属性,即使它们没有显式设置。要解决这个问题,你有几个选择:
1.在
Order
类中使Code
属性为空:1.使
Order
和OrderCode
之间的关系可选:通过将
[ForeignKey("Code")]
属性添加到OrderCode
导航属性中,您可以让EF Core知道该关系是可选的。这样,EF Core就不会尝试为外键列插入空值。1.如果您正在寻找一种避免在任何地方修改代码的替代方法,您可以考虑使用
Code
属性的默认值,而不是将其设为空。通过这样做,您可以在Code
属性未显式设置时为其分配一个默认值,确保它不违反外键约束。下面是一个例子:通过使用这种方法,您不需要在任何地方修改代码来处理可空属性。但是,请记住,这种方法假设0是
OrderCode
表中的有效值,并且它可能不适合所有场景。