简体   繁体   English

使用具有实体框架6的存储库模式更新记录

[英]Updating records using a Repository Pattern with Entity Framework 6

I'm writing a simple blog application and trying to establish CRUD operations in my generic repository pattern but I'm getting an error on my update method that says: 我正在编写一个简单的博客应用程序,并尝试在我的通用存储库模式中建立CRUD操作,但我的更新方法出现错误,该错误说:

'System.Data.Entity.DbSet' does not contain a definition for 'Entry' and no extension method 'Entry' accepting a first argument of type 'System.Data.Entity.DbSet' could be found (are you missing a using directive or an assembly reference?) 'System.Data.Entity.DbSet'不包含'Entry'的定义,并且没有扩展方法'Entry'可以找到接受类型'System.Data.Entity.DbSet'的第一个参数(你是否缺少using指令)或汇编参考?)

I followed a post that explained how to 'fake' Entry() by adding additional level of indirection over DbContext. 我跟着一篇帖子解释了如何通过在DbContext上添加额外的间接级别来“伪造”Entry()。 However in MVC 5 we're inheriting from: IdentityDbContext and not DbContext. 但是在MVC 5中我们继承自: IdentityDbContext而不是DbContext。 I did try implementing the authors fix but the error persists. 我确实试过实现作者修复,但错误仍然存​​在。

My Question 我的问题

How can I add an update method to my repository in Entity Framework 6 using IdentityDbContext? 如何使用IdentityDbContext将更新方法添加到Entity Framework 6中的存储库? If we aren't supposed to do it this way then how do I update a record with this pattern? 如果我们不应该这样做,那么如何使用这种模式更新记录?

I should note that all other the other methods work as expected. 我应该注意到其他所有方法都按预期工作。

My generic Repository: 我的通用存储库:

public class BlogEngineRepository<T> : IRepository<T> where T : class
    {
        protected DbSet<T> DbSet;

        public BlogEngineRepository(DbContext dataContext)
        {
            DbSet = dataContext.Set<T>();
        }

        #region IRepository<T> Members

        public void Insert(T entity)
        {
            DbSet.Add(entity);
        }

        public void Delete(T entity)
        {
            DbSet.Remove(entity);
        }

        public void Update(T entity)
        { 

           DbSet.Entry(entity).State = System.Data.Entity.EntityState.Modified;

        }

        public IQueryable<T> SearchFor(Expression<Func<T, bool>> predicate)
        {
            return DbSet.Where(predicate);
        }

        public IQueryable<T> GetAll()
        {
            return DbSet;
        }

        public T GetById(int id)
        {
            return DbSet.Find(id);
        }

        #endregion
    }

Ok, I figured this out. 好的,我想通了。 The reason why there isn't an Update method in new repository patterns (Entity Framework 6) is because there's no need for one . 新存储库模式(实体框架6)中没有Update方法的原因是因为不需要一个 You simply fetch your record by id, make your changes and then commit/save. 您只需按ID获取记录,进行更改然后提交/保存。

For example, this is my edit POST method from my postController: 例如,这是我的postController中的编辑POST方法:

[HttpPost]
[ValidateAntiForgeryToken]
[ValidateInput(false)]
public ActionResult Edit([Bind(Include = "Id,Title,IntroText,Body,Modified,Author")] Post post)
{
    using (UnitOfWork uwork = new UnitOfWork())
    {
        Post edit = uwork.PostRepository.GetById(post.Id);
        edit.Title = post.Title;
        edit.IntroText = post.IntroText;
        edit.Body = post.Body;
        edit.Modified = DateTime.Now;

        uwork.Commit();

        return RedirectToAction("Index");
    }
}

RepositoryPattern looks like this: RepositoryPattern看起来像这样:

public class BlogEngineRepository<T> : IRepository<T> where T : class
{
    protected DbSet<T> DbSet;

    public BlogEngineRepository(DbContext dataContext)
    {
        DbSet = dataContext.Set<T>();
    } 

    public void Insert(T entity)
    {
        DbSet.Add(entity);
    }

    public void Delete(T entity)
    {
        DbSet.Remove(entity); 
    }

    public IQueryable<T> SearchFor(Expression<Func<T, bool>> predicate)
    {
        return DbSet.Where(predicate);
    }

    public IQueryable<T> GetAll()
    {
        return DbSet;
    }

    public T GetById(int id)
    {
        return DbSet.Find(id);
    } 
}

Update should look like ( expanding on Dan Beaulieu's answer ) : 更新应该是这样的( 扩展Dan Beaulieu的回答 ):

[HttpPost]
[ValidateAntiForgeryToken]
[ValidateInput(false)]
public ActionResult Edit([Bind(Include = "Id,Title,IntroText,Body,Modified,Author")] Post post)
{
    using (UnitOfWork uwork = new UnitOfWork())
    {
        post.Modified = DateTime.Now;
        uwork.PostRepository.Update(post);

        uwork.Commit();

        return RedirectToAction("Index");
    }
}

RepositoryPattern looks like this: RepositoryPattern看起来像这样:

public class BlogEngineRepository<T> : IRepository<T> where T : class
{
  public BlogEngineRepository(DbContext dataContext)
  {
    DbSet = dataContext.Set<T>();
    Context = dataContext;
  }

  public T Update(T entity)
  {
     DbSet.Attach(entity);
     var entry = Context.Entry(entity);
     entry.State = System.Data.EntityState.Modified;
  }
}

You can view a full explaination to the answer for Efficient way of updating list of entities for more information on the details of just an update. 您可以查看有关更新实体列表的有效方法的答案的完整说明,以获取有关更新详细信息的更多信息。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

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