【问题标题】:Conditionally Include() in Entity Framework在实体框架中有条件地包含()
【发布时间】:2012-08-30 14:30:13
【问题描述】:

我正在使用带有 DbContext 的 EF4.3。

我有一个存储在缓存中的实体,因此在转换为列表并将其弹出缓存之前,我需要预先加载必要的数据。

我的数据库已标准化,因此数据分布在多个表中。基本实体是“用户”,用户可能是也可能不是“订阅者”,订阅者可以是“贡献者”、“成员”或“管理员”三种类型之一

由于我缺乏 EF、Linq 等方面的知识,目前整个 fetch 不是很优雅。

    public static User Get(Guid userId)
    {
        Guard.ThrowIfDefault(userId, "userId");

        var r = new CrudRepo<User>(Local.Items.Uow.Context);

        var u = r.FindBy(x => x.UserId == userId)
            .Include("BookmarkedDeals")
            .Include("BookmarkedStores")
            .SingleOrDefault();

        if (u.IsNotNull() && u.IsActive)
        {
            if (u.IsAdmin)
            {
                u.GetAdministrator();
            }
            else if (u.IsContributor)
            {
                u.GetContributor();
            }
            else if (u.IsMember)
            {
                u.GetMember();
            }
            else
            {
                string.Format("Case {0} not implemented", u.UserRoleId)
                    .Throw<NotImplementedException>();
            }
        }

        return u;
    }

每个“Get”方法都获取一个订阅者实体以及角色类型的相关 Include() 实体。

我很确定它可以做得比这更优雅,但在最初的思考过程中遇到了困难。

有人帮忙吗?

更新了 Get 方法之一的示例

    public static void GetMember(this User user)
    {
        Guard.ThrowIfNull(user, "user");

        var r = new ReadRepo<Subscriber>(Local.Items.Uow.Context);

        user.Subscriber = r.FindBy(x => x.UserId == user.UserId)
            .Include("Kudos")
            .Include("Member.DrawEntries")
            .Include("Member.FavouriteCategories")
            .Include("Member.FavouriteStores")
            .Single();
    }

【问题讨论】:

  • 就个人而言,我不介意这一点。我不知道我有多喜欢实体上可以获取其他实体的方法。我个人不会这样做,因为我喜欢我的实体纯净和干净的数据存储。我不会写这个作为答案,因为这是意见。我认为如果它对你有用,而且它的可读性很好,那很好。我始终牢记这一点:根据需要更改功能代码。不只是因为你觉得它看起来很丑吗?那里总是有更大的鱼要炸。
  • 您能否展示其中一种“Get...”方法,它们究竟做了什么?
  • @Slauma 添加了一个示例
  • @RyanBennett 我之所以称其为另一个是因为它们实际上是一个单一的实体——一个“用户”。只有对 db 表进行规范化才能将它们分开。
  • 恕我直言,您的代码适合这种情况。我认为您不能将其压缩为单个数据库查询。但也许其他人有一个想法(也许使用投影而不是包含)。

标签: c# .net entity-framework


【解决方案1】:

如果您的“用户”实体连接到您的其他实体,您可以使用连接实体集合的 Load 方法来获取相关实体。例如,如果您的“用户”实体具有属性“订阅者”,您可以调用 u.Subscriber.Load() 来获取相关实体。这是相关的MSDN article

【讨论】:

    【解决方案2】:
    var u = r.FindBy(x => x.UserId == userId)
            .Include("BookmarkedDeals")
            .Include("BookmarkedStores")
            .SingleOrDefault();
    
    if(someCondition)
    {
        u = u.Include("something");
    }
    

    没有地方可以测试这个,但你试过吗?

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2015-12-21
      • 1970-01-01
      • 2022-02-15
      • 2018-12-07
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2010-11-08
      相关资源
      最近更新 更多