看起来像Entity Framework 7,虽然不支持/实现延迟加载,但是在不使用Include(...)
方法的情况下返回给定实体的所有关系。
我不确定在此情况下我应遵循预期的行为。请参阅下面的复制品。请注意,this github branch/commit会重现这一点。
添加DbContext
和存储库提供商:
// In ConfigureServices
services.AddDbContext<PouarfDbContext>(options => options.UseInMemoryDatabase());
services.AddScoped<IContactProvider, ContactProvider>();
种子申请数据:
// In Configure
// CreateSampleData() adds a bunch of `People` objects to a list,
// and then loops through them, adding each one to the DbContext
// through the `ContactProvider`
Task.Run(async () =>
await new
MockPeople(app
.ApplicationServices
.GetService<IContactProvider>()).CreateSampleData());
ContactProvider
实施中的几个例子:
public async Task AddPerson(Person person)
{
await Task.Run(() => _dbContext.Add(person));
}
public async Task<IEnumerable<Person>> GetPeople()
{
// Notice no Include(...)
return await _dbContext.People.ToListAsync();
}
人物对象:
public class Person : ContactInformationBase // Contains Id
{
...
public virtual ICollection<PhoneNumber> PhoneNumbers { get; set; }
}
然后在我的控制器操作中,我从EF获得了人员:
public async Task<IActionResult> Index()
{
// Contains a populated list of `PhoneNumbers`, even though
// they should only be included if I explicitly asked EF7 to load them.
var people = await _contactProvider.GetPeople();
..
}
基本上,EF7提供了来自我的主对象的映射实体,即使它们只应在我明确要求时通过Include(p => p.PhoneNumbers)
包含。
我正在使用带有Entity Framework 7的ASP.NET Core 1 RC2
修改
刚刚向我的控制器添加了一个API动作,结果是......奇怪。
[Route("api/[action]")]
public async Task<IEnumerable<Person>> People()
{
// True adds all the Includes off the DbSet as needed.
return await _contactProvider.GetPeople(true);
}
现在我没有通过此调用返回任何映射实体。如果我删除或添加Include()
来电,则不会对结果产生影响。仅返回核心Person
实体,所有映射实体均为null
。
答案 0 :(得分:1)
正如我所提到的here,问题是我自己的错。
问题在于在DbSet上使用Include
模式。
我有这个,错误:
var people = _dbContext.People;
if (includeRelationships)
{
people.Include(p => p.PhoneNumbers)
.Include(p => p.EmailAddresses)
.Include(p => p.StreetAddresses);
}
return await people.FirstOrDefaultAsync(p => p.Id.Equals(id));
并将其更改为此,请注意此处Include
的实际应用, RIGHT :
IQueryable<Person> people = _dbContext.People;
if (includeRelationships)
{
people = people
.Include(p => p.EmailAddresses)
.Include(p => p.PhoneNumbers)
.Include(p => p.StreetAddresses);
}
return await people.FirstOrDefaultAsync(p => p.Id.Equals(id));