3
votes

I have three tables - Context, Session and User. And below are their simplified structure.

User:
UserId (Int, PK)
Email (Varchar(100))

Context:
ContextId (Int, PK)
UserId (Int, FK from User table)
CurrentSessionId (Int, Nullable, FK from Session table)

Session:
SessionId (Int, PK)
UserId (Int, FK from User table)
ContextId (Int, FK from Context table)

Below is the sequence in my code to delete a user entity.

1) Update CurrentSessionId of Context table to null where UserId = UserId to be deleted.
2) Delete all Sessions corresponding to the User
3) Delete all Contexts corresponding to the User
4) Finally Delete User.
5) Call ObjectContext.SaveChanges()

Upon calling ObjectContext.SaveChanges() I get the following exception -

Unable to determine a valid ordering for dependent operations. Dependencies may exist due to foreign key constraints, model requirements, or store-generated values.

I guess EF4 gets confused determining the execution order of first 3 statements. Is it possible to tell EF4 what statements to execute first and what to execute next?

One way I can work around is to call SaveChanges() after step one and then call it again after step four. But I would love to know if there are any other elegant solution than that.

2

2 Answers

4
votes

Based on this MSDN link the order of execution cannot be forced in EF4. I had to call SaveChanges() twice once after step one and then again after step four.

0
votes

I think the issue lies with the circular reference between Session and Context; if you get rid of Context.CurrentSessionId then your generated Context object will still have a Sessions property you can use, but EF shouldn't get upset trying to negotiate the dependencies. You could manually add a CurrentSession property to Context like this:

public Session CurrentSession
{
    get { return this.Sessions.FirstOrDefault(); }
}

Also, if you set the User -> Context and User -> Session relationships in your EF model to cascade delete (or even better in the database), then deleting a User becomes just two lines:

objectContext.Users.DeleteObject(user);
objectContext.SaveChanges();