Cae*_*sar 38 c# foreign-keys entity-framework-4
我正在使用Entity Framework 4.0并且有一个我无法弄清楚的愚蠢问题.
我有两张桌子:
实体框架创建了以下两个实体:
我正在使用以下代码获取联系人并更新该特定联系人的联系人类型:
Contact contact = dbContext.Contacts.Single(c => c.Id == 12345);
contact.ContactType.Id = 3;
Run Code Online (Sandbox Code Playgroud)
引发以下异常:
The property 'Id' is part of the object's key information and cannot be modified.
Run Code Online (Sandbox Code Playgroud)
看起来很简单!我不明白!
AL-*_*imi 26
出现此问题的原因是您多次引用同一对象.这不是EF的限制,而是一种安全功能,可确保您不会插入具有两个不同ID的同一对象.因此,要实现您要执行的操作,只需创建一个新对象并将新创建的对象添加到数据库中.
**这个问题经常发生在循环中.如果您使用while或foreach循环,请确保将新创建的对象INSIDE循环体.
试试这个:
Contact contact = dbContext.Contacts.Single(c => c.contactTypeId == 1234);
contact.contactTypeId = 4;
dbContext.AddObject(contact);
dbContext.SaveChanges();
Run Code Online (Sandbox Code Playgroud)
Cae*_*sar 16
框架创建的实体没有contact.ContactTypeId属性.它会自动删除它并在Contact实体中创建ContactType关联.
正如您所建议的那样,让它工作的方法是通过查询数据库并将其分配给contact.ContactType来创建ContactType对象.例如:
Contact contact = dbContext.Contacts.Single(c => c.Id == 12345);
ContactType contactType = dbContext.ContactType.Single(c => c.Id == 3);
contact.ContactType = contactType;
Run Code Online (Sandbox Code Playgroud)
当我同时从两个不同的上下文编辑相关对象时,就发生了这种情况。例子:
DataContext ctxA = new DataContext();
DataContext ctxB = new DataContext();
Author orwell = new Author {Name = "George Orwell" };
ctxA.Add(orwell);
ctxB.Add(new Book {Name = "1984", Author = orwell});
ctxA.SaveChanges();
ctxB.SaveChanges();
Run Code Online (Sandbox Code Playgroud)
我的情况有点复杂(因为这显然很愚蠢),但本质上这导致了我的情况的错误。
小智 6
你应该添加
db.Entry(contact).State = EntityState.Detached;
Run Code Online (Sandbox Code Playgroud)
在 .SaveChanges(); 之后
尝试
contact.ContactType = differentContactType;
Run Code Online (Sandbox Code Playgroud)
要么
contact.ContactTypeId = 3;
Run Code Online (Sandbox Code Playgroud)
您正尝试将ContactType(联系人)的ID设置为3.