拥有2个具有相同模式的独立数据库,我需要使用Entity Framework 4将实体(记录)从一个数据库复制到另一个数据库。
我正在创建2个上下文,但是当我向第二个上下文添加一个实体时,我收到以下错误:
An entity object cannot be referenced by multiple instances of IEntityChangeTracker.
我知道如果我使用Detach方法可以避免该错误,但在这种情况下相关实体会丢失!
示例代码:
var cx = new MyEntities();
//eager load related tables
var allEntities = from x in cx.Reservation.Include("Detail.MoreDetail")
select x;
// new instance of context but connected to a second database
var cx2 = new MyEntities( new ConnectionString...);
foreach (var e in allEntities)
{
//cx.Detach(reservation); // can't detach, or related entities will be lost
cx2.AddToReservation(reservation); // error happens here!
cx2.SaveChanges();
}
我该如何进行此类操作? 或者,如何在不丢失相关实体的情况下分离实体?
答案 0 :(得分:8)
一旦错误消息有用 - 实体一次只能属于一个上下文。为了做你想要的事情,你需要在第一个上下文中Detatch
每个实体,然后再添加到第二个实体。
就像你说的那样,这会杀死相关实体。不幸的是,你必须处理Detach
的这个(恼人的)方面。
答案 1 :(得分:6)
答案 2 :(得分:0)
我可以节省时间的好的解决方案: http://lorifpeterson.com/?p=75
禁用EF跟踪
从数据集中检索一个或多个实体时,可以 告诉实体框架不要跟踪您所做的任何更改 制作该对象,然后将该实体作为新实体添加到 数据集。使用.AsNoTracking,上下文一无所知 关于现有实体。
var entity = context.MyDataSet .AsNoTracking() .FirstOrDefault(e => e.Id == 1); context.MyDataSet.Add(entity); context.SaveChanges(); You can also include child entities as well var entity = context.MyDataSet .AsNoTracking() .Including(ds => ds.MyChildEntities) .FirstOrDefault(e => e.Id == 1); context.MyDataSet.Add(entity); context.SaveChanges(); // creates a new object graph in the database
EF复制当前值
使用此技术,您可以从现有的设备中获取当前值 实体对象,并将值设置为新创建的实体对象。
var originalEntity = context.MyDataSet .FirstOrDefault(e => e.Id == 1); var entity = new MyDataSetEntity(); context.MyDataSet.Add(entity); //Create and add new entity object to context before setting its values var originalEntityValues = Context.Entry(originalEntity).CurrentValues; Context.Entry(entity).CurrentValues.SetValues(originalEntityValues); //Copy values from original entity to new entity entity.MyProperty1 = "Changed value"; // make any changes to the new entity entity.MyProperty2 = "Another changed value"; context.SaveChanges();