如何附加不是来自数据库的Entity Framework对象?
我完全分离了我的Entity Framework对象和我的POCO对象,我只是来回翻译它们……
即:
// poco public class Author { public Guid Id { get; set; } public string UserName { get; set; } }
然后我有一个EF对象“作者”具有相同的属性..
所以我有我的业务对象
var author = new Author { UserName="foo", Id="Guid thats in the db" };
我想保存此对象,所以我执行以下操作:
var dbAuthor = new dbAuthor { Id=author.Id, UserName=author.UserName }; entities.Attach(dbAuthor); entities.SaveChanges();
但这给了我以下错误:
具有null EntityKey值的对象无法附加到对象上下文。
编辑:看起来我必须使用entities.AttachTo(“作者”,dbAuthor); 没有EntityKey附加,但后来我有硬编码的魔术字符串,如果我改变我的实体集名称将破坏我不会有任何编译时检查…有没有一种方法可以附加,保持编译时间检查?
我希望我能够做到这一点,因为硬编码字符串会导致编译时间validation失败=)
您是否尝试过使用AttachTo并指定实体集?
entities.AttachTo("Authors", dbAuthor);
其中"Authors"
将是您的实际实体集名称。
编辑:
是的,有更好的方法(应该有)。 设计人员应该为ObjectContext生成“添加”方法 ,转换为上面的调用..所以你应该能够做到:
entities.AddToAuthors(dbAuthor);
这应该是:
public void AddToAuthors(Authors authors) { base.AddObject("Authors", authors); }
在whateverobjectcontext.designer.cs文件中定义。
刚看到这个。 如果你想Attach()到ObjectContext,即说服entity framework已经存在数据库中的实体,并且你想避免使用魔术字符串,即
ctx.AttachTo("EntitySet", entity);
您可以尝试基于扩展方法的两种可能性,这两种方法都可以让生活变得更加可以忍受。
第一个选项允许您编写:
ctx.AttachToDefault(entity);
并在此处介绍: 技巧13 – 如何以简单的方式附加实体
第二个选项允许您编写:
ctx.EntitySet.Attach(entity);
并在此处介绍: 技巧16 – 今天如何模仿.NET 4.0的ObjectSet
正如您所看到的,两者都非常易于使用并完全避免使用字符串。
希望这可以帮助
亚历克斯
如果您不想使用EntitySet名称编写字符串,请尝试此操作
entities.AttachTo(entities.CreateObjectSet().EntitySet.Name, entity);
如果您不知道要对哪个实体进行操作,则可以采用以下方法:
string className = entityObject.GetType().Name; var container = _DbContext.MetadataWorkspace.GetEntityContainer(_DbContext.DefaultContainerName, DataSpace.CSpace); string setName = (from meta in container.BaseEntitySets where meta.ElementType.Name == className select meta.Name).First(); _DbContext.AttachTo(setName, entityObject);
你能试试吗?
entities.AddToAuthors(dbAuthor);
为了我,
Context.Authors.AddObject(new Author())
工作得很好。 想知道我是否遗漏了什么? 或者这不是正确的方法?