实体框架代码优先多对多不使用 GUID 加载相关实体

Posted

技术标签:

【中文标题】实体框架代码优先多对多不使用 GUID 加载相关实体【英文标题】:Entity Framework Code First Many-To-Many not loading related entities using GUID 【发布时间】:2011-07-07 20:06:55 【问题描述】:

我在用户和经理之间有一个自我引用的多对多关系,如下所示:

 public class User
    
        public virtual Guid UserId  get; set; 
        public virtual string Username  get; set;     
        public virtual ICollection<UsersManagers> Managers  get; set; 
    

public class UsersManagers

    public int UsersManagersId  get; set; 
    public virtual Guid ManagerId  get; set; 
    public virtual Guid UserId  get; set; 
    public int ManagerRank  get; set; 

    [ForeignKey("ManagerId")]
    public virtual User Manager  get; set; 

因此,用户可以拥有多个可以按等级排序的经理。当我为我的数据库和具有几个经理的用户播种时,如下所示:

        var user = u.All.Where(e => e.Username == "Neil").FirstOrDefault(); 

        UsersManagers c = new UsersManagers ManagerRank = 1, ManagerId = manager1.UserId, UserId = user.UserId;
        UsersManagers c1 = new UsersManagers  ManagerRank = 2, ManagerId = manager2.UserId, UserId = user.UserId ;

一切都在数据库中正确创建。 UsersManagers 表中有 3 个条目具有正确的 UserId、ManagerId 和 ManagerRank。

当我从存储库加载用户并尝试访问 Managers 属性时,集合为空。我能做些什么来解决这个问题?

任何帮助将不胜感激。

更新:

我在加载用户时添加了包括经理,如下所示。 EF 现在为错误的用户返回错误的管理器。这是来自 UsersManagers 表的数据,它应该为 1 个用户返回 4 个经理,但它为 4 个用户返回 1 个经理。

UsersManagersId        ManagerId            UserId                       ManagerRank
1   2157B648-7FE3-4784-A742-687682672EE8    F603EB04-FF22-4E8E-8FB2-3AA12F3F6C8F    1
2   862C2E56-8DF2-4110-B6E4-534B8C0E8F75    F603EB04-FF22-4E8E-8FB2-3AA12F3F6C8F    2
3   A95AD9A2-6475-4B4C-925A-6C0522E9B004    F603EB04-FF22-4E8E-8FB2-3AA12F3F6C8F    3
4   A6D37381-2507-46E8-B84D-059A1B4F1020    F603EB04-FF22-4E8E-8FB2-3AA12F3F6C8F    4

解决方案

解决方案是在 UsersManagers 中将 Manager 的 ForeignKey 注释更改为使用“UserID”。

【问题讨论】:

我不是 EF 专家,但我使用了“包含”功能,传入与我在存储库中加载的内容相关的实体名称... 谢谢 - 我曾尝试使用 include,但它仍然无法正常工作。在返回包括经理在内的所有用户并查看结果集后,似乎它正在为用户加载不正确的经理......将进行更多测试以查看导致该问题的原因 这是一个可能有用的链接...***.com/questions/5270721/… 尝试添加注释但没有成功。数据库中的数据正确,表设置正确。我会用一些数据截图更新问题。 【参考方案1】:

这是一个示例代码位,它为我的存储库中的程序加载所有会话和相关跟踪。

public Program GetById(int id)

    var entity = _context.Programs
        .Include(p => p.Sessions.Select(s => s.Trackings))
        .Single(p => p.ID == id);

     return entity;

【讨论】:

以上是关于实体框架代码优先多对多不使用 GUID 加载相关实体的主要内容,如果未能解决你的问题,请参考以下文章

实体框架代码优先,同一张表上的多对多关系

实体框架代码优先的多对多关系的最佳方法

多对多关系实体框架核心db优先

多对多(自相关)特定订单实体框架

实体框架 CTP5,代码优先。多对多级联删除

多对多实体框架和存储库模式插入/更新