我正在使用EF Core,并且尝试在三个表(Car,ElectricCar和PetrolCar)之间创建一对一关系
public class Car
{
public int Id { get; set; }
public string RegistrationNumber { get; set; }
public ElectricCar Company { get; set; }
public PetrolCar Trust { get; set; }
}
public class ElectricCar
{
public int ElectricCarId { get; set; }
public double BatteryCapacityWattage{ get; set; }
public int CarId { get; set; }
public Car Car { get; set; }
}
public class PetrolCar
{
public int PetrolCarId { get; set; }
public double TankCapacity { get; set; }
public int CarId { get; set; }
public Car Car { get; set; }
}
public partial class CarDbContext : Microsoft.EntityFrameworkCore.DbContext
{
public CarDbContext()
{
}
public CarDbContext(DbContextOptions<CarDbContext> options)
: base(options)
{
}
public DbSet<ElectricCar> ElectricCar { get; set; }
public DbSet<Car> Car { get; set; }
public DbSet<PetrolCar> PetrolCar { get; set; }
protected override void OnConfiguring(DbContextOptionsBuilder optionsBuilder)
{
if (!optionsBuilder.IsConfigured)
{
optionsBuilder.UseSqlServer("Server=DESKTOP-PC\\SQLLOCAL;Database=OneToOneEFCoreCar;Trusted_Connection=True;");
}
}
}
以及插入数据的代码:
CarDbContext context = new CarDbContext();
context.Car.Add(new Car
{
RegistrationNumber = "EL123",
Company = new ElectricCar() { BatteryCapacityWattage = 2000 }
});
context.Car.Add(new Car
{
RegistrationNumber = "PETR123",
Trust = new PetrolCar() { TankCapacity = 50 }
});
context.SaveChanges();
当我去PetrolCar时,我插入了CarId = 1的新行,尽管CarId在ElectricCar表中用作CarId,但它接受了该行而没有给出任何错误。 有什么方法可以限制这一点吗?
答案 0 :(得分:0)
如果要完全保持对象模型/数据结构与上面相同,那么在两个表之间唯一的约束实际上是无法实现的。
代码解决方案中的一种可能(尽管它不是特别干净,所以我建议以此为基础来重组数据,尽管这似乎是您希望避免的事情)是重写SaveChanges
方法。
类似的东西:
public override SaveChanges()
{
var petrolCars = ChangeTracker.Entries().Where(e is PetrolCar).ToList();
foreach(var pCar in petrolCars)
{
if(query the database for electric cars to see if car id exists)
{
do some sort of error processing and avoid saving;
}
}
base.SaveChanges();
}
的确意味着创建一个从默认上下文继承的上下文类,尽管这样做可以增加灵活性(显然,您也需要处理ID中具有相同ID的汽车的其他情况)。其他方向)