1

I am trying to simplify my code and am moving some of the core logic on to the Entity Framework entities themselves (Seems like that is why we have entities that model business logic). Presently entities are pretty much just a bunch of properties and collections.

I am looking at having a function on the entity that removes an item from a collection and adds it to another collection on the entity.

Now the add to the other collection function works perfectly. However the remove - removes the item from the collection however it doesn't delete.

I get:

The operation failed: The relationship could not be changed because one or more of the foreign-key properties is non-nullable.

I understand that this is because removing from collection doesn't actually mark for delete and when context save changes occurs it is upset by the key being nulled but not marked for removal. As I am not in a repository and have no access to the context within. How am I supposed to let the context know that this item needs to be deleted?

I thought I was supposed to make sure domain entities encapsulated appropriate business logic. Is this just the wrong thing to be doing? How can I get around this? Should I get around this?

If I use the extension method:

public static ObjectContext GetContext(this IEntityWithRelationships entity)
{
    if (entity == null)
        throw new ArgumentNullException("entity");

    var relationshipManager = entity.RelationshipManager;

    var relatedEnd = relationshipManager.GetAllRelatedEnds()
                                        .FirstOrDefault();

    if (relatedEnd == null)
        throw new Exception("No relationships found");

    var query = relatedEnd.CreateSourceQuery() as ObjectQuery;

    if (query == null)
        throw new Exception("The Entity is Detached");

    return query.Context;
}

I can access the context within the entity like this:

var context = this.GetContext() as Entities;
context.events.DeleteObject(event);

This seems hideous but does work. Surely doing this can't be the right way?

Gert Arnold
  • 105,341
  • 31
  • 202
  • 291
GraemeMiller
  • 11,973
  • 8
  • 57
  • 111
  • 1
    Pursuing domain-driven design is a good thing (+1), but you are confusing DDD and data layer responsibilities. Your domain classes should be oblivious of persistence logic (well, with EF model-first they aren't, but we can keep that below the hood). So if just adding and removing objects on the domain level does not work, I would make a persistence-aware service for this kind of logic. – Gert Arnold Mar 07 '12 at 19:59
  • Yeah I don't normally end up in the situation. Inserting and updating is handled by repository. However one of my domain concepts seemed to require removing a current event from a collection and moving it to another collection. I wanted to model the concept of clear current event. – GraemeMiller Mar 07 '12 at 20:13
  • 1
    What if you change the parent of the event? Anyway, as soon as marking for delete is involved and most certainly when the object context is required I would leave that to a service. – Gert Arnold Mar 07 '12 at 20:39
  • Yeah thinking that because EF requires me to use the context to mark for deleted I will just have to keep this functionality in a service that handles it for me. Thanks for the advice – GraemeMiller Mar 07 '12 at 22:05

1 Answers1

0

I changed the models to make the relationships between parent and child identities identifying relationships by using a composite key containing the parents key. This means that removing the entity from the child collection removes it without requiring access to the context. See this question Is it possible to remove child from collection and resolve issues on SaveChanges?

Community
  • 1
  • 1
GraemeMiller
  • 11,973
  • 8
  • 57
  • 111