简体   繁体   中英

Using Entity Framework (Code First) to update/change an entity with a nullable association to null

I have an association (virtual, lazyloaded one-to-one-or-null) and I want to set it to null. I've found that it's not possible unless you load this association first, and then set it to null.

someEntity.AnotherEntity.ToString(); // Needs to be done in order to force a load since im using a service that wraps a generic repository
someEntity.AnotherEntity = null; // Now this works because i loaded above.

I google around a lot and it seems that eager-loading someEntity is an option, or adding a new property to the SomeEntity that is:

[ForeignKey("AnotherEntity")] // With this annotation
int? AnotherEntity_Id // Added this property

And then work with the nullable AnotherEntityId instead of the association property AnotherEntity .

I for now use the second approach, and it bloats the Entity a bit, but seem more solid because you also don't need the extra SQL calls.

  1. Why can't I set associations to null and have EF understand this?

  2. What about the second approach i'm using. Is it a good practice or is there something better?

1 Why can't I set associations to null and have EF understand this?

It's because of the nature of your entity with lazy loading enabled. With lazy loading, the entity does not materialize in the property until you call the get method on the navigation property. If you call set , sure this can set a property's backing field to null, but EF will ignore it because it was null to begin with. The property's backing field does not get populated until you call get unless you eager load.

2 What about the second approach i'm using. Is it a good practice or is there something better?

One easy workaround is to force lazy loading if you haven't already eager loaded, by doing this:

if (someEntity.AnotherEntity != null) // this will lazy load the instance
    someEntity.AnotherEntity = null; // now tell EF to remove the association

The statement in the if block will invoke the get method on the property and lazy load it if it hasn't already been eager loaded. Now the EF context knows this entity is being tracked, so when you set it to null in the next line, EF will remember that you want to null it out when you go to save changes.

Also, as you noted, if you are exposing a nullable foreign key property for the association, you can just set it. Since it is not virtual, changing it to null will also have the same effect of telling your EF context that you want to remove the association.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM