C# 更新通用存储库中的实体时出错

C# 更新通用存储库中的实体时出错,c#,asp.net-mvc,automapper,C#,Asp.net Mvc,Automapper,我正在构建一个通用存储库,所有其他方法都可以使用,更新方法除外。代码如下: public void Update(T1 obj) { T2 item = Mapper.Map<T1, T2>(obj); //db.Entry(item).State = EntityState.Modified; //db.Set<T2>().Attach(item); db.Entry<T2>(item

我正在构建一个通用存储库,所有其他方法都可以使用,更新方法除外。代码如下:

 public void Update(T1 obj)
    {
        T2 item = Mapper.Map<T1, T2>(obj);
        //db.Entry(item).State = EntityState.Modified;
        //db.Set<T2>().Attach(item);
        db.Entry<T2>(item).State = EntityState.Modified;
        db.SaveChanges();

    }
该模型工作得很好,它的活动值为False。但它给了我以下错误:

Attaching an entity of type 'Data.UserIdentification' failed because 
another entity of the same type already has the same primary key value. 
 This can happen when using the 'Attach' method or setting the state of 
 an entity to 'Unchanged' or 'Modified' if any entities in the graph 
have conflicting key values. This may be because some entities are new 
and have not yet received database-generated key values. In this case 
 use the 'Add' method or the 'Added' entity state to track the graph and 
 then set the state of non-new entities to 'Unchanged' or 'Modified' as 
appropriate.
我怎样才能解决这个问题?我试过几种方法都没有成功。 新增通用回购代码:

public class GenericRepository<T1, T2>:IGenericRepository<T1> 
    where T1 : class
    where T2: class

{
    private Data.Entities db = null;
    private DbSet<T2> table = null;

    public GenericRepository()
    {
        this.db = new Data.Entities();
        table = db.Set<T2>();
    }

    public GenericRepository(Entities db)
    {
        this.db = db;
        table = db.Set<T2>();
    }

    public IQueryable<T1> SelectAll()
    {
        return table.ToList().AsQueryable().Select(x => Mapper.Map<T2, T1>(x));
    }

    public T1 SelectByID(object id)
    {
        return Mapper.Map<T2, T1>(table.Find(id));
    }

    public void Insert(T1 obj)
    {
        T2 item = Mapper.Map<T1, T2>(obj);
        table.Add(item);
    }

    public void Update(T1 obj)
    {
        //T2 item = Mapper.Map<T1, T2>(obj);
        //table.Attach(item);
        //db.Entry<T2>(item).State = EntityState.Modified;
        //db.SaveChanges();
        T2 item = Mapper.Map<T1, T2>(obj);
        db.Set<T2>().Attach(item);
        db.Entry<T2>(item).State = EntityState.Modified;
        db.SaveChanges();




    }

    public void Delete(object id)
    {
        T2 existing = table.Find(id);
        table.Remove(existing);
    }

    public void Save()
    {
        db.SaveChanges();
    }
公共类GenericRepository:IGenericRepository
其中T1:class
其中T2:类
{
私有数据。实体db=null;
私有DbSet表=null;
公共通用存储库()
{
this.db=新数据.Entities();
table=db.Set();
}
公共一般报告(实体数据库)
{
这个.db=db;
table=db.Set();
}
公共IQueryable SelectAll()
{
return table.ToList().AsQueryable().Select(x=>Mapper.Map(x));
}
公共T1 SelectByID(对象id)
{
返回Mapper.Map(table.Find(id));
}
公共空白插入(T1 obj)
{
T2项=映射器映射(obj);
表.增加(项目);
}
公共作废更新(T1 obj)
{
//T2项=映射器映射(obj);
//表.附件(项目);
//db.Entry(item).State=EntityState.Modified;
//db.SaveChanges();
T2项=映射器映射(obj);
db.Set().Attach(项目);
db.Entry(item).State=EntityState.Modified;
db.SaveChanges();
}
公共无效删除(对象id)
{
T2 existing=table.Find(id);
表2.移除(现有);
}
公共作废保存()
{
db.SaveChanges();
}
EDIT2:添加了UserIdentification实体

 public partial class UserIdentification
{
    public System.Guid id { get; set; }
    public System.Guid user_id { get; set; }
    public int id_type { get; set; }
    public System.DateTime expiration_date { get; set; }
    public System.DateTime Created { get; set; }
    public Nullable<bool> Active { get; set; }

    public virtual IdentificationType IdentificationType { get; set; }
    public virtual UserInfo UserInfo { get; set; }
}
公共部分类用户标识
{
public System.Guid id{get;set;}
public System.Guid用户\u id{get;set;}
公共int id_类型{get;set;}
public System.DateTime过期\u date{get;set;}
public System.DateTime已创建{get;set;}
公共可空活动{get;set;}
公共虚拟标识类型标识类型{get;set;}
公共虚拟用户信息用户信息{get;set;}
}
编辑3:商业模式

    public Guid id { get; set; }
    public System.Guid user_id { get; set; }
    public int id_type { get; set; }
    public System.DateTime expiration_date { get; set; }
    public System.DateTime Created { get; set; }
    public Nullable<bool> Active { get; set; }
    public virtual IdentificationType IdentificationType { get; set; }
公共Guid id{get;set;}
public System.Guid用户\u id{get;set;}
公共int id_类型{get;set;}
public System.DateTime过期\u date{get;set;}
public System.DateTime已创建{get;set;}
公共可空活动{get;set;}
公共虚拟标识类型标识类型{get;set;}

如果对检索和更新操作使用相同的
DbContext
,则更新时,您的上下文已跟踪您的实体(具有此主键的实体)。从:

更改被跟踪实体的状态

您可以通过在实体条目上设置state属性来更改已被跟踪实体的状态。例如:

请注意,为已跟踪的实体调用Add或Attach 也可用于更改实体状态。例如,调用 当前处于“添加”状态的实体的“附加”将更改 它的状态保持不变

我想你错过了
Attach
呼叫(你已注释掉)。请再试一次

public void Update(T1 obj)
{
    T2 item = Mapper.Map<T1, T2>(obj);
    db.Set<T2>().Attach(item);
    db.Entry<T2>(item).State = EntityState.Modified;
    db.SaveChanges();
}
公共作废更新(T1 obj)
{
T2项=映射器映射(obj);
db.Set().Attach(项目);
db.Entry(item).State=EntityState.Modified;
db.SaveChanges();
}

我只想把这个留在这里:


我有完全相同的问题,所有其他方法(添加、删除、获取)都可以正常工作,但更新除外。 当dbContext尝试附加实体时,出现错误:

    public virtual void Update(T entity)
    {
        dbSet.Attach(entity);
        dataContext.Entry(entity).State = EntityState.Modified;
    }
此存储库方法“studentRepository.Update(student);”是从服务层调用的

    public StudentAdapterModel SaveStudent(StudentAdapterModel studentAdapterModel)
    {
        try
        {
            Student student = null;
            if (studentAdapterModel.EventId == 0)
            {
                student = new Student();
                student = Mapper.Map<StudentAdapterModel, Student>(studentAdapterModel);
                studentRepository.Add(student);
            }
            else
            {
                //student = studentRepository.GetById(studentAdapterModel.EventId);
                student = studentRepository.Get(e => e.EventId == studentAdapterModel.EventId);
                try
                {
                    student = Mapper.Map<StudentAdapterModel, Student>(studentAdapterModel);

                }
                catch (Exception ex2)
                {
                    string errMess = ex2.ToString().Trim();
                }

                auctionEventRepository.Update(auctionEvent);

            }
            unitOfWork.Commit();
            studentAdapterModel.EventId = student.EventId;
            return studentAdapterModel;
        }
        catch (Exception ex)
        {
            string errMess = ex.ToString().Trim();
        }
        return null;
    }
public StudentAdapterModel SaveStudent(StudentAdapterModel StudentAdapterModel)
{
尝试
{
Student=null;
if(studentAdapterModel.EventId==0)
{
学生=新学生();
student=Mapper.Map(studentAdapterModel);
studentRepository.Add(学生);
}
其他的
{
//student=studentRepository.GetById(studentAdapterModel.EventId);
student=studentRepository.Get(e=>e.EventId==studentAdapterModel.EventId);
尝试
{
student=Mapper.Map(studentAdapterModel);
}
捕获(异常ex2)
{
字符串errMess=ex2.ToString().Trim();
}
auctionEventRepository.Update(auctionEvent);
}
unitOfWork.Commit();
studentAdapterModel.EventId=student.EventId;
返回学生daptermodel;
}
捕获(例外情况除外)
{
字符串errMess=ex.ToString().Trim();
}
返回null;
}
但如果我不使用Mapper,效果很好

    //student = studentRepository.GetById(studentAdapterModel.EventId);
            student = studentRepository.Get(e => e.EventId == studentAdapterModel.EventId);
            try
            {
                //student = Mapper.Map<StudentAdapterModel, Student>(studentAdapterModel);
                student.Name = StudentAdapterModel.Name;
            }
            catch (Exception ex2)
            {
                string errMess = ex2.ToString().Trim();
            }
//student=studentRepository.GetById(studentAdapterModel.EventId);
student=studentRepository.Get(e=>e.EventId==studentAdapterModel.EventId);
尝试
{
//student=Mapper.Map(studentAdapterModel);
student.Name=StudentAdapterModel.Name;
}
捕获(异常ex2)
{
字符串errMess=ex2.ToString().Trim();
}

您是否使用相同的
DbContext
来检索实体和更新实体?虽然我不喜欢通用存储库,但我可以推荐这篇关于如何构建一个存储库的文章:。您是否也可以发布您的
User
实体(您尝试更新的那个)。当然。添加了实体模型和业务模型。嗨,尼古拉,谢谢你提供的信息性回复。我尝试了你的更新方法,但我得到了相同的异常,特别是在这一点上:db.Set().Attach(item);我将发布我完整的通用存储库,以防出现问题。一个技巧是使用 public StudentAdapterModel SaveStudent(StudentAdapterModel studentAdapterModel) { try { Student student = null; if (studentAdapterModel.EventId == 0) { student = new Student(); student = Mapper.Map<StudentAdapterModel, Student>(studentAdapterModel); studentRepository.Add(student); } else { //student = studentRepository.GetById(studentAdapterModel.EventId); student = studentRepository.Get(e => e.EventId == studentAdapterModel.EventId); try { student = Mapper.Map<StudentAdapterModel, Student>(studentAdapterModel); } catch (Exception ex2) { string errMess = ex2.ToString().Trim(); } auctionEventRepository.Update(auctionEvent); } unitOfWork.Commit(); studentAdapterModel.EventId = student.EventId; return studentAdapterModel; } catch (Exception ex) { string errMess = ex.ToString().Trim(); } return null; }
    //student = studentRepository.GetById(studentAdapterModel.EventId);
            student = studentRepository.Get(e => e.EventId == studentAdapterModel.EventId);
            try
            {
                //student = Mapper.Map<StudentAdapterModel, Student>(studentAdapterModel);
                student.Name = StudentAdapterModel.Name;
            }
            catch (Exception ex2)
            {
                string errMess = ex2.ToString().Trim();
            }