Entity Framework 核心关系并使用代码优先方法中的查找获取详细信息

Entity Framework Core relationship and get the details using lookup in code-first approach

我下面有三个 table。我如何找到实体上下文为 UserNotifications 的给定用户的业务列表?可能吗?

在我的 DTO 中你可以看到这个 属性, public string SenderUserPrimaryBusinessName { get;放; },我正在寻找如何填充驻留在 BusinessInfo Table 中的这个值,因此查找如下,Notification --> User --> UserBusinessInfo --> BuinsessInfo (Name 属性 is这里)

我认为唯一的选择是使用 UserNotifications 上下文加载所有用户,因为它与 User table 有关系,然后从 UserBusiness 迭代。

它需要大量的数据库往返,寻找一个查询来一次加载所有这些信息。感谢您的帮助。

User
    id

UserBusiness
    user_id (multiple records for the same user_id)

Notifications
    user_id

有关 class 详细信息和我在通知上下文中尝试的查询的更多信息 class

public abstract class BaseEntity : BaseExEntity
{
    public BaseEntity()
    {
        Id = System.Guid.NewGuid();
    }
    [Key]
    public Guid Id { get; set; }
    public bool IsDeleted { get; set; } = false;
}

public class User : BaseEntity
{
    [MaxLength(50)]
    public string FullName { get; set; }      

}

public class UserBusinessInfo : BaseEntity
{ 
    public Guid UserId { get; set; }
    
    public Guid BusinessInfoId { get; set; }

    public User User { get; set; }

    public BusinessInfo BusinessInfo { get; set; }

    public bool IsPrimary { get; set; }

}

public class Notification : BaseEntity
{
    public Guid RecieverUserId { get; set; }

    public User RecieverUser { get; set; }

    public bool ViewStatus { get; set; }

    public NotificationType NotificationType { get; set; }
    public string EventType { get; set; }

    public Guid SenderUserId { get; set; }
    public User SenderUser { get; set; }

    [Column(TypeName = "jsonb")]
    public string NotificationData { get; set; }
}

 public class BusinessInfo : BaseEntity
    {
      
        [Required]     
        public string Name { get; set; }

       
    }
  public class NotificationExistingDto : BaseEntity
{        
    public bool ViewStatus { get; set; }
    public NotificationType NotificationType { get; set; }
    public string EventType { get; set; }
    public Guid SenderUserId { get; set; }
    public string SenderUserProfilePictureUrl { get; set; }
    public string SenderUserFullName { get; set; }
    public string SenderUserName { get; set; }
    public string SenderUserPrimaryBusinessName { get; set; }
    public Guid RecieverUserId { get; set; }
    public string RecieverUserProfilePictureUrl { get; set; }
    public string RecieverUserFullName { get; set; }
    public string RecieverUserName { get; set; }
    public string NotificationData { get; set; }
    public ProfileType SenderUserProfileType { get; set; }
}
IQueryable<Notification> notifications;
var pagedData = await notifications
        .Select( n => new NotificationExistingDto()
        {
            Id = n.Id,
            CreatedAt = n.CreatedAt,
            EventType = n.EventType,
            IsDeleted = n.IsDeleted,
            ModifiedAt = n.ModifiedAt,
            NotificationType = n.NotificationType,
            NotificationData = n.NotificationData,
            RecieverUserId = n.RecieverUserId,
            RecieverUserFullName = n.RecieverUser.FullName,
            RecieverUserName = n.RecieverUser.UserName,
            RecieverUserProfilePictureUrl = n.RecieverUser.ProfilePictureUrl,
            SenderUserFullName = n.SenderUser.FullName,
            SenderUserId = n.SenderUserId,
            SenderUserName = n.SenderUser.UserName,
            SenderUserProfilePictureUrl = n.SenderUser.ProfilePictureUrl,
            //SenderUserPrimaryBusinessName = n.SenderUserBusinessInfo.Where(b => b.IsPrimary && b.UserId == n.SenderUserId).FirstOrDefault().BusinessInfo.Name,
            ViewStatus = n.ViewStatus,
            SenderUserProfileType = n.SenderUser.ProfileType

        })
        .Skip((validFilter.PageNumber - 1) * validFilter.PageSize)
        .Take(validFilter.PageSize)
        .ToListAsync();

大概是这样:

new NotificationExistingDto()
{
   ...
   SenderUserPrimaryBusinessName = context.UserBusinessInfo
      .FirstOrDefault(b => n.SenderUser.Id == b.UserId && b.IsPrimary && b.UserId == n.SenderUserId).BusinessInfo.Name,
   ...            
}

您可以改进代码优先模型中的导航。

public class User : BaseEntity
{
    [MaxLength(50)]
    public string FullName { get; set; }      

    // new navigation collection
    public ICollection<UserBusinessInfo> Infos { get; set; }
}

那么你可以

SenderUserPrimaryBusinessName = n.SenderUser.Infos.FirstOrDefault(b => b.IsPrimary).BusinessInfo.Name,

在您的查询中。 (或者可能 SingleOrDefault 如果保证单个主)