【问题标题】:same key value for is already being tracked相同的键值已经被跟踪
【发布时间】:2018-06-23 19:13:22
【问题描述】:
System.InvalidOperationException: The instance of entity type 'ProjectAssignment' cannot be tracked because another instance with the same key value for {'ProjectID'} is already being tracked. When attaching existing entities, ensure that only one entity instance with a given key value is attached. Consider using 'DbContextOptionsBuilder.EnableSensitiveDataLogging' to see the conflicting key values.
   at Microsoft.EntityFrameworkCore.ChangeTracking.Internal.IdentityMap`1.Add(TKey key, InternalEntityEntry entry)
   at Microsoft.EntityFrameworkCore.ChangeTracking.Internal.StateManager.St

我制作了一个项目,其中包含 Worker(ID 和其他列)和 Project(ID 和其他列)实体和 ProjectAssignment(许多项目 ID 到许多 Worker)Crossbound。但是当我尝试获取 ProjectAssignment 数据时,Application Insights 中出现错误。奇怪的是 id 没有更早出现。

这里是https://github.com/Streamc/ContosoObserve1/tree/master/Proj_s

 context.Database.EnsureCreated();

  var ProjectAssignments = new ProjectAssignment[]
             {
                    new ProjectAssignment
                    {
                        ProjectID = Projects.Single( i => i.ID == 1).ID,
                        WorkerID = Workers.Single( i => i.ID == 1).ID,
                    },
                     new ProjectAssignment
                    {
                        ProjectID = Projects.Single( i => i.ID == 1).ID,
                        WorkerID = Workers.Single( i => i.ID == 2).ID,
                    },
                     new ProjectAssignment
                    {
                        ProjectID = Projects.Single( i => i.ID == 1).ID,
                        WorkerID = Workers.Single( i => i.ID == 3).ID,
                    },
                    new ProjectAssignment
                    {
                        ProjectID = Projects.Single( i => i.ID == 2).ID,
                        WorkerID = Workers.Single( i => i.ID == 1).ID,
                    },
                    new ProjectAssignment
                    {
                        ProjectID = Projects.Single( i => i.ID == 3).ID,
                        WorkerID = Workers.Single( i => i.ID == 1).ID,
                    },
                    new ProjectAssignment
                    {
                        ProjectID = Projects.Single( i => i.ID == 4).ID,
                        WorkerID = Workers.Single( i => i.ID == 1).ID,
                    },
                    new ProjectAssignment
                    {
                        ProjectID = Projects.Single( i => i.ID == 2).ID,
                        WorkerID = Workers.Single( i => i.ID == 2).ID,
                    },
                    new ProjectAssignment
                    {
                        ProjectID = Projects.Single( i => i.ID == 2).ID,
                        WorkerID = Workers.Single( i => i.ID == 3).ID,
                    },
                    new ProjectAssignment
                    {
                        ProjectID = Projects.Single( i => i.ID == 2).ID,
                        WorkerID = Workers.Single( i => i.ID == 4).ID,
                    }

             };
            foreach (ProjectAssignment ss in ProjectAssignments)
            {
                context.ProjectAssignments.Add(ss);
            }
            context.SaveChanges();



 public class ProjectAssignment
    {
        [Key]
        public int ProjectID { get; set; }
        public int WorkerID { get; set; }


        public Project Project { get; set; }
        public Worker Worker { get; set; }

    }
   public class Worker
    {
        public int ID { get; set; }
        public string Firstname { get; set; }
        public string Lastname { get; set; }
        public string Fathername { get; set; }
        public string email { get; set; }    
        public string Company_name { get; set; }
        public ICollection<ProjectAssignment> ProjectAssignment { get; set; }

    }
    public class Project
    {
        public int ID { get; set; }
        public string Name { get; set; }
        public string Customer_Company { get; set; }
        public string Executive_Company { get; set; }
        public int ManagerID { get; set; }    
        public int WorkerID { get; set; }    
        public DateTime Begin_date { get; set; }
        public DateTime End_date { get; set; }
        public int Priority { get; set; }    
        public string Test_comment { get; set; }    
        public ICollection<ProjectAssignment> ProjectAssignment { get; set; }
    }

【问题讨论】:

标签: c# entity-framework-6


【解决方案1】:

仔细阅读错误信息:

无法跟踪实体类型“ProjectAssignment”的实例,因为已经在跟踪另一个与 {'ProjectID'} 键值相同的实例。

所以问题是我们有两个或多个ProjectAssignment 和相同的ProjectID。

如果我们查看代码,我们会发现我们分配了相同的 ProjectID 两次:

 var ProjectAssignments = new ProjectAssignment[] {
     new ProjectAssignment {
         ProjectID = Projects.Single( i => i.ID == 1).ID, // ID == "1"
         WorkerID = Workers.Single( i => i.ID == 1).ID,
     },
     new ProjectAssignment {
         ProjectID = Projects.Single( i => i.ID == 1).ID, // ID == "1", again
         WorkerID = Workers.Single( i => i.ID == 2).ID,
     },
     // ...
 }

根本原因似乎是 ProjectID 被建模为主键而不是外键。主键必须是唯一的。您可能想要的是由ProjectID 和WorkerID 组成的composite primary key。

查看你的 Github 项目中的ProjectContext,这个复合键已经到位:

modelBuilder.Entity<ProjectAssignment>().HasKey(c => new { c.ProjectID, c.WorkerID });

但它与ProjectAssignment.ProjectID 上的[Key] 注释冲突。删除这个[Key] 属性!

【讨论】:

  • 我发现的比较早。我修好了。是的,逻辑是 2 列键。我刚刚测试了 keyattribute 并错过了我没有擦除行。问题实际上在于关键属性。感谢您的回答!
  • 我认为应该删除问题。
猜你喜欢
  • 2021-11-24
  • 2020-10-16
  • 2018-12-01
  • 2021-08-27
  • 1970-01-01
  • 1970-01-01
  • 2016-09-14
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多