Dbset.Add(entity) assigns an ID and this results in a exception

c# dbset entity-framework entity-framework-6

Question

For the following classes :

public Car 
{
    public int ID { get; set; }
    public string Brand {get; set; }
}

Normally when we do :

Car c = new Car { Brand = "Jaguar" } ; // Point A
context.Cars.Add(c); // Point B
context.SaveChanges() // Point C

At point B, the ID should remain 0, and an ID should only be assigned at point C. However, I have found that for one of my classes, an ID is assigned at point B and this results in this exception being thrown :

Cannot insert explicit value for identity column in table 'Cars' when IDENTITY_INSERT is set to OFF.

I have played with Fluent API and I'm 99% sure my relationships are correctly defined. I can't figure out why this DbSet tries to assign an ID for this entity.

Update

Thank you for your help, so here is a more detailed illustration of my situation :

public Car 
{
    public int ID { get; set; }
    public string Brand {get; set; }
    public int Driver1ID {get; set;}
    public Person Driver1 {get; set;}
    public int Driver2ID {get; set;}
    public Person Driver2 {get; set;}
}

public Person
{
   public int ID { get; set; }
   public string Name { get; set; }
}

And here is my fluent configuration :

modelBuilder.Entity<Car>().HasKey(x => x.ID);
            modelBuilder.Entity<Car>().Property(x => x.ID).HasDatabaseGeneratedOption(DatabaseGeneratedOption.Identity); // Added following Igor's suggestion
            modelBuilder.Entity<Car>().HasRequired(x => x.Driver1).WithOptional().WillCascadeOnDelete(false);
            modelBuilder.Entity<Car>().HasRequired(x => x.Driver2).WithOptional().WillCascadeOnDelete(false);

Edit 2

Well, I have found that actually Migrations messed up. For some reason EF put the 2nd foreign key (Driver2), on the primary key column. This is why, DbSet.Add() was populating the ID column with a value that was actually the Driver 2 ID.

I really don't know why EF got confused like that. And the weird thing is that I didn't see this FK when I looked in SQL Management Studio. It looks like EF applied some relashionships that were not actually in the DB.

I reset the whole migrations (deleted the migration folder and the _migrationhistory table, then executed Enable-Migrations and Add-Migration Init in PowerShell), and I have been able to see the problematic lines in the initial migration file.

Or course I have modified them and It seems to have solved the problem.

1
0
2/20/2015 3:15:06 PM

Popular Answer

In your fluent (and also declaritivly) mapping you can do specify if the ID is assigned by the database using Identity or if its not. If you specify that it IS assigned your code should not also assign it because you will get an exception. In fluent you can do it like this:

public Car 
{
    public int ID { get; set; }
    public string Brand {get; set; }
    public int Driver1ID {get; set;}
    public Person Driver1 {get; set;}
    public int Driver2ID {get; set;}
    public Person Driver2 {get; set;}
}

public Person
{
   public int ID { get; set; }
   public string Name { get; set; }
}


protected override void OnModelCreating(DbModelBuilder modelBuilder) { 
// ....
modelBuilder.Entity<Car>().HasKey(x => x.ID);
modelBuilder.Entity<Car>().Property(x => x.ID).HasDatabaseGeneratedOption(DatabaseGeneratedOption.Identity); // set it on
modelBuilder.Entity<Car>().HasRequired(x => x.Driver1).WithMany().HasForeignKey(x => x.Driver1ID).WillCascadeOnDelete(false);
modelBuilder.Entity<Car>().HasRequired(x => x.Driver2).WithMany().HasForeignKey(x => x.Driver2ID).WillCascadeOnDelete(false);
// ....
}
0
2/20/2015 11:57:05 AM


Related Questions





Related

Licensed under: CC-BY-SA with attribution
Not affiliated with Stack Overflow
Licensed under: CC-BY-SA with attribution
Not affiliated with Stack Overflow