I am experiencing the pain in the A** of EF and according too google, I am not the only one with this issue. I Have a list of object that I got from EF and then I set this list as the DataContext (WPF) of an itemscontrol. Since, after the "using" block the context is destroyed, I would have to make a new query and object with the same ID When wishing to save the changes. I try to attach it to the Context, I try saving the changes, but they are not stored.
Some people have tried several things, but does maybe someone know of a handy and smart solution for this problem?
I tried Attach()
, AttachTo()
, nothing worked
P.S. It's EF 4.0
EDITED - SOLVED
Adding the following line of code between attaching and saving solved everything in EF 4.0
_context.ObjectStateManager.ChangeObjectState(modifiedEntity, System.Data.EntityState.Modified);
in EF 4.1
_context.Entry(modifiedEntity).State = System.Data.EntityState.Modified;
When you do an Attach()
of an Entity Framework object to a new DbContext
, it is entered with State EntityState.Unchanged. This happens regardless of whether or not the properties of the object have actually been changed since it was originally fetched from the DB (in a different context).
To tell EF about changes that happened outside of the current DbContext, you simply need to set the State of the object to EntityState.Modified before calling DbContext.SaveChanges()
.
Foo foo=null;
using (var db = new MyContext())
{
db.Foos.Add( new Foo { MyValue = OLD_VALUE } );
db.SaveChanges(); // foo written to DB with MyValue = OLD_VALUE
foo = db.Foos.FirstOrDefault(); // grab foo
}
// leave context and update foo...
foo.MyValue = NEW_VALUE;
using (var db = new MyContext())
{
db.Foos.Attach(foo); // foo is attached in the 'unchanged' state...
db.SaveChanges(); // ...so this statement has no effect
// At this point, db.Foos.FirstOrDefault().MyValue will be NEW_VALUE, yet
// the "real" value of the object in the DB is OLD_VALUE.
db.Entry(foo).State = EntityState.Modified; // setting foo to "Modified" will cause...
db.SaveChanges(); // ...foo to be written out with NEW_VALUE
}