EntityFramework 5.0中的虚拟删除

时间:2012-12-30 21:30:28

标签: c# sql-server-2012 .net-4.5 entity-framework-5

我的问题是......

我会问我的用户,他是否要删除记录。如果他说是的话,

我不会实际删除表中的行,但会使用true更新表的Deleted列。但在执行此操作之前,我想检查外键约束,就像我们在Delete行情况中那样,意味着该值是否被其他表使用。我应该说我的用户该行被其他表使用,所以无法删除?

有什么想法我能做到这一点。

Currenly我这样做是为了删除..

public bool Delete(dynamic entity)
{
    try
    {
        //here I want to check, whether this is being used by some other table or not. Foreign key constaint
        entity.Deleted = true;
        this.SaveChanges();
        return true;
    }
    catch { return false; }
}

3 个答案:

答案 0 :(得分:1)

我的回答适用于实体框架5.0和Code First。 该解决方案需要两个部分。首先,每个数据类必须实现一个暴露“已删除”属性的接口(让我们称之为IVirtualDelete)。

public interface IVirtualDelete{
  bool Deleted {get; set;}
}

其次,您需要覆盖DBContext中的SaveChanges方法。

调用SaveChanges时,请查看context.ChangeTracker.Entities(),查看状态为System.Data.EntityState.Deleted且实体实现IVirtualDelete接口的那些。在对象上设置已删除,并将实体状态更改为已修改。

public override int SaveChanges() {
  foreach (var item in this.ChangeTracker.Entries().Where(x=> x.EntityState == EntityState.Deleted)){
    var entity = item.Entity as IVirtualDelete;
    if(entity != null){
      entity.Deleted = true;
      item.EntityState = EntityState.Modified;
    }
  }
  return base.SaveChanges();
}

答案 1 :(得分:0)

这就是“关于它”。 EF没有方法可以将删除重写为更新,最后可以认为这不好,因为机制可能会有所不同(删除的时间戳等)。所以,你所做的就是人们在这种情况下所做的事情。

答案 2 :(得分:0)

您可以尝试更改实体的主键值并保存。

如果存在任何子记录 - 您将收到某种级联更新错误并返回false。

如果更新成功 - 您没有子记录,您可以将主键值更改回原始值,设置Deleted = true并重新保存。

当然,如果您将身份作为主键或具有“删除级联”用户可见场景的子表,则不适用。