实体框架加载相关实体

杜威·沃泽尔(Dewey Vozel)

我使用的是代码优先的Entity Framework,其基本上下文仅由标准IDbSet集合组成,其中T只是POCO类。就我而言,我已禁用了延迟加载。虽然我的模型类中有“导航属性”,但是我从它们中删除了virtual关键字。

存储库中的“全部获取”方法执行一些自定义筛选,以确保当前用户仅看到他们拥有的数据,除非他们是管理员。我遇到一个特别的问题,我以管理员身份登录,该管理员也与某些记录相关联。由于我登录时所使用的实体是在上下文中加载的,因此即使禁用了延迟加载,删除了虚拟且未使用“包含”或“加载”,结果中与我的配置文件相关联的对象仍具有导航属性自动设置。

这不是我的项目中的代码,仅是一个示例,用以说明我在做什么。它可能存在拼写错误和语法错误。

public class Record
{
    public Guid Id { get; set; }
    public string Name { get; set; }
    public Owner Owner { get; set; } //No virtual keyword
    public Guid OwnerId { get; set; }
}

public class Owner
{
    public Guid Id { get; set; }
    public string Name { get; set; }
    public Collection<Record> Records { get; set; } //No virtual keyword
}

public class Context : DbContext
{
    IDbSet<Owner> Owners { get; set; }
    IDbSet<Record> Records { get; set; }
    public static Context Create()
    {
        Context context = new Context();
        context.Configuration.LazyLoadingEnabled = false; //Lazy loading disabled
        return context;
    }
}

public class Repository
{
    private Context Context { get; set; }
    public Owner CurrentOwner { get; private set; }
    public Repository()
    {
        Context = Context.Create();

        //Code here to get the application user and look up an associated "owner"
        //entity if the user is an "owner" (they could just be an administrator)
        //but the GetCurrentOwnerOrNull uses the Context to find the user
        CurrentOwner = GetCurrentOwnerOrNull();
    }

    public IQueryable<Record> GetRecords(bool asAdmin)
    {
        IQueryable<Record> records = Context.Records; //Not including or loading Owner
        if (asAdmin)
        {
           //Verify that the application user is an admin and throw exception otherwise
        }
        else
        {
            if (CurrentOwner == null)
            {
                //Throw a security exception
            }
            records = records.Where(r => r.OwnerId == CurrentOwner.Id);
        }
        return records;
    }
}

同样,上述问题是,如果我以所有者(无论是否是管理员)的身份运行该代码,则我拥有的那些记录将设置Owner属性,而不是null。我希望实体框架脱离我的业务,​​而不是自动设置。这会在下游引起问题,尤其是在以管理员和所有者身份运行代码时,因此您会获得一些带有Owner = null的记录和一些带有Owner设置的记录。它很烦人。请让我停下来。

埃里克·飞利浦(Erik Philips)

错误实际上是一个功能。实体框架将自动在同一上下文中关联关联,即使这些实体彼此独立地加载也是如此。

让我们假设以下内容:

public class Person
{
  public Person()
  {
    this.Pets = new List<Pet>();
  }

  public int Id { get; set; }
  public string Name { get; set; }

  public virtual ICollection<Pet> Pets { get; set; }
}

public class Pet
{
  public int Id { get; set; }
  public string Name { get; set; }
  public int PersonId { get; set; }

  public virtual Person Owner { get; set; }
}

我们还假设它们是正确关联的DB-First或Attributes / Fluent API代码优先。

数据库:

Persons
Id Name
1  Erik Philips

Pets
Id Name PersonId
1  Joe  1

将会发生以下情况:

var pet = DbContext.Pets.FirstOrDefault(id => id == 1);
var person = DbContext.Persons.FirstOrDefault(id => id == 1);

Assert.AreEqual(person.Pets.Count(), 1);
Assert.IsNotNull(pet.Person);
Assert.AreEqual(pet.Person, person);

发生这种情况的原因是,上下文将保留其缓存中的对象。如果您不关心持有这些对象的上下文,则需要使用AsNoTracking()

本文收集自互联网,转载请注明来源。

如有侵权,请联系[email protected] 删除。

编辑于
0

我来说两句

0条评论
登录后参与评论

相关文章

来自分类Dev

实体框架加载相关实体

来自分类Dev

实体框架 - 用相关对象加载对象

来自分类Dev

为什么实体框架会自动加载相关实体

来自分类Dev

为什么实体框架会自动加载相关实体

来自分类Dev

实体框架多对多不加载相关实体

来自分类Dev

如何使用实体框架显式加载特定实体的特定相关实体?

来自分类Dev

加载相关实体

来自分类Dev

加载相关对象时发生异常。实体框架

来自分类Dev

实体框架-长链相关对象的高效渴望加载?

来自分类Dev

实体框架核心:查询对象后加载相关数据

来自分类Dev

实体框架核心未从参考表加载相关数据

来自分类Dev

如何为实体框架已经跟踪的记录加载相关数据

来自分类Dev

加载相关对象时发生异常。实体框架

来自分类Dev

渴望加载实体框架

来自分类Dev

使用.Include时,实体框架不会加载相关实体,除非上下文知道相关实体

来自分类Dev

相关实体查询实体框架

来自分类Dev

实体框架入口负载相关实体

来自分类Dev

实体框架无需加载即可将对象添加到相关实体

来自分类Dev

当实体不公开时,实体框架不会加载相关数据

来自分类Dev

实体框架数据库首先发布加载相关实体(ASP.NET Web API)

来自分类Dev

实体框架5-使用“包括”应用与过滤器加载相关的实体

来自分类Dev

当不访问导航属性时,实体框架会延迟加载相关实体

来自分类Dev

当实体不公开时,实体框架不会加载相关数据

来自分类Dev

如何使用实体框架从数据库视图加载相关实体?

来自分类Dev

实体框架6,加载实体异步/等待

来自分类Dev

实体框架仅加载父实体

来自分类Dev

实体框架6,加载实体异步/等待

来自分类Dev

实体框架未正确加载子实体

来自分类Dev

实体框架实体加载如何工作?

Related 相关文章

  1. 1

    实体框架加载相关实体

  2. 2

    实体框架 - 用相关对象加载对象

  3. 3

    为什么实体框架会自动加载相关实体

  4. 4

    为什么实体框架会自动加载相关实体

  5. 5

    实体框架多对多不加载相关实体

  6. 6

    如何使用实体框架显式加载特定实体的特定相关实体?

  7. 7

    加载相关实体

  8. 8

    加载相关对象时发生异常。实体框架

  9. 9

    实体框架-长链相关对象的高效渴望加载?

  10. 10

    实体框架核心:查询对象后加载相关数据

  11. 11

    实体框架核心未从参考表加载相关数据

  12. 12

    如何为实体框架已经跟踪的记录加载相关数据

  13. 13

    加载相关对象时发生异常。实体框架

  14. 14

    渴望加载实体框架

  15. 15

    使用.Include时,实体框架不会加载相关实体,除非上下文知道相关实体

  16. 16

    相关实体查询实体框架

  17. 17

    实体框架入口负载相关实体

  18. 18

    实体框架无需加载即可将对象添加到相关实体

  19. 19

    当实体不公开时,实体框架不会加载相关数据

  20. 20

    实体框架数据库首先发布加载相关实体(ASP.NET Web API)

  21. 21

    实体框架5-使用“包括”应用与过滤器加载相关的实体

  22. 22

    当不访问导航属性时,实体框架会延迟加载相关实体

  23. 23

    当实体不公开时,实体框架不会加载相关数据

  24. 24

    如何使用实体框架从数据库视图加载相关实体?

  25. 25

    实体框架6,加载实体异步/等待

  26. 26

    实体框架仅加载父实体

  27. 27

    实体框架6,加载实体异步/等待

  28. 28

    实体框架未正确加载子实体

  29. 29

    实体框架实体加载如何工作?

热门标签

归档