我应该如何监听从 ObjectContext 添加/删除的实体?

Posted

技术标签:

【中文标题】我应该如何监听从 ObjectContext 添加/删除的实体?【英文标题】:How should I listen for entities being added/deleted from an ObjectContext? 【发布时间】:2012-01-08 15:22:31 【问题描述】:

据我所知,ObjectContext 没有公开任何直接监听添加/删除项目的方法。您可以连接到SavingChanges 事件,并查询ObjectStateManager 中添加或删除了哪些项目。但这有几个问题:

通知将在项目实际添加到上下文之前发生。 只要保存任何项更改(即使没有添加/删除任何项目),都会发出通知。 SavingChanges 的用途似乎并非如此——它更多的是用于验证数据而不是通知更改。 这是主观的,但我只是觉得错了。

我已经通过实现一个有限版本的存储库模式来解决这个问题——它处理创建、读取和删除,但更新仍然是通过直接操作实体本身的属性来执行的(然后从我的存储库)。

出于以下几个原因,我对此感到有些不安:

我认为ObjectContext 应该从存储库模式中替换存储库。感觉就像我在重复实体框架应该为我做的工作。 使用不完整版本的存储库模式(CRUD 中的 C、R 和 D)似乎有点奇怪。存储库不应该用于所有 4 种 CRUD 操作,还是不应该? 实体框架不支持添加/删除通知一定是有原因的。无论如何选择实现它们,是否会造成实体框架开发人员选择避免的设计难题?

作为参考,这里是我的存储库的粗略轮廓:

public class EntityArgs<T> : EventArgs
    where T : EntityObject

    ....

    public T Entity
    
        get  return this.entity; 
    


public delegate void EntityEventHandler<T>(object sender, EntityArgs<T> args) where T: EntityObject;

public class EntityRepository

    public event EntityEventHandler<Foo> FooAdded;
    public event EntityEventHandler<Foo> FooDeleted;

    ...

    public EntityRepository()
    
        this.entities = new Entities();
    

    public IEnumerable<Foo> Foos
    
        get  return this.entities.Foos; 
    

    public void AddFoo(Foo foo)
    
        this.entities.Foos.AddObject(foo);
        this.entities.SaveChanges();
        this.OnFooAdded(foo);
    

    public void DeleteFoo(Foo foo)
    
        this.entities.Foos.DeleteObject(foo);
        this.entities.SaveChanges();
        this.OnFooDeleted(foo);
    

    public void SaveChanges()
    
        this.entities.SaveChanges();
    

    ...

我对实体框架很陌生,所以如果我的方法完全错误,请告诉我。

编辑:响应 Erix 使用 ObjectStateManager 的建议,它几乎解决了我的问题,但并不完全。问题是我想在entities.Foos 反映更改时收到通知。 ObjectStateManager.ObjectStateManagerChanged 发生在 AddObject 被调用时,但在 SaveChanges 被调用之前。所以:

entities.ObjectStateManager.ObjectStateManagerChanged += (s, e) =>
    Console.WriteLine("Action: 0, Object: 1, Count: 2", e.Action, e.Element, entities.Foos.Count());
var foo = ...
Console.WriteLine("Count: 0", entities.Foos.Count());
entities.Foos.AddObject(foo);
entities.Foos.SaveChanged();
Console.WriteLine("Count: 0", entities.Foos.Count());

// Output:
// Count: 0
// Action: Add, Object: ..., Count: 0
// Count: 1

【问题讨论】:

您对哪些活动感兴趣,为什么?从上下文中添加/删除对象,或者从数据库中插入或删除记录? @ProgrammingHero:从上下文中添加/删除的对象。 @ProgrammingHero:至于为什么,我感兴趣的原因有很多。一个简单的例子是,我可以知道何时更新符合某些条件的显示的实体列表。 目前还不清楚你在找什么。您的 cmets 和您编辑的问题看起来相反。 你的问题让我想起了这些:***.com/questions/2714857/… 和 ***.com/questions/2716359/… 【参考方案1】:

你能用ObjectStateManager吗? 它应该在添加对象后引发事件。

显示在 MSDN 中,看起来是正确的方法:

http://msdn.microsoft.com/en-us/library/ee705449.aspx

【讨论】:

这几乎是我需要的,但不完全是。查看我对原始问题的修改。

以上是关于我应该如何监听从 ObjectContext 添加/删除的实体?的主要内容,如果未能解决你的问题,请参考以下文章

n 层项目中的实体框架 ObjectContext 生命周期

如何修复“ObjectContext 实例已被处置”

如果将新对象添加到 ObjectSet,则 ObjectContext.SaveChanges() 永远不会返回。有没有人经历过这个?

使用 ObjectContext 获取关系记录的主键

ObjectContext.Refresh()?

iOS 上的 DeviceEventEmitter