#c# #.net-core #entity-framework-core
Вопрос:
У меня есть коллекция сущностей, на которые ссылается моя Company
сущность, как это
public sealed class Company
{
private readonly List<CompanyJobCategory> _jobCategories = new();
public IReadOnlyCollection<CompanyJobCategory> JobCategories => _jobCategories.AsReadOnly();
}
public sealed class CompanyJobCategory
{
public CompanyJobCategory(int jobCategoryId, Guid companyId)
{
JobCategoryId = jobCategoryId;
CompanyId = companyId;
}
public int JobCategoryId { get; private set; }
public JobCategory JobCategory { get; private set; }
public Guid CompanyId { get; private set; }
}
public sealed class JobCategory
{
// the stuff I need is here
}
Все работает нормально, но теперь мне нужно убедиться, что JobCategory
эти свойства навигации доступны в какой-то момент, прежде чем звонить DbContext.SaveChanges()
Я хватаю сущность вот так
var entry = DbContext.ChangeTracker
.Entries<Company>()
.FirstOrDefault(entry => entry.Entity.Id == id)!;
Но могу видеть , что для каждого entry.Entity.JobCategories
JobCategory
из них всегда равно нулю (из-за того, как я инициализировал сущность)
Я думал, что смогу сделать что-то вроде
DbContext.ChangeTracker.Entries<Company>().First().Collection(x => x.JobCategories).Load();
но это не заполняет дочерние навигационные реквизиты
Я также попытался установить IsLoaded
значение false перед вызовом Load()
, но это не помогло
Самое странное, что я заметил, это то, что иногда некоторые из этих дочерних сущностей будут полностью загружены, если я загляну внутрь записи.Коллекции(x => x.Категории заданий)[0].Категория заданий> но нет никакой разницы в том, как я их добавляю. Как это возможно?
Я также попробовал следующее, которое, похоже, загружает большинство JobCategory
ссылок, но все равно некоторые из них отображаются как нулевые — возможно ли это?
entry.Collection(x => x.JobCategories)
.Query()
.Include(y => y.JobCategory)
.Load();
Комментарии:
1.«ссылается на другую сущность под названием JobCategory» — отдельную
JobCategory
или совокупностьJobCategory
? Я предполагаю, что коллекция из чтения вашего вопроса, но она может оказаться полезной, чтобы сделать ее более понятной, пожалуйста.2. @ErmiyaEskandary
CompanyJobCategory
содержит ссылку на одинJobCategory
— это в основном таблица соединений m2m3. Последний фрагмент (с
Query().Include(...).Load()
) — это предполагаемый способ выполнить то, о чем вы просите.4. @IvanStoev Спасибо, Иван, есть идеи, почему 1 или 2 навигационных реквизита все еще не заполнены? В основном это работает, но некоторые все равно приходят как null, хотя я вижу, что do ссылается на реальную строку во внешней таблице… Хотя это кажется невозможным
Ответ №1:
Вот как я заставил это работать
// get the entity which is about to be persisted
var entry = DbContext.ChangeTracker
.Entries<Company>()
.FirstOrDefault(x => x.Entity.Id == id)!;
// select the ids for the referenced entities I need to load
var jobCategoryIds = entry.Entity.JobCategories
.Select(x => x.JobCategoryId);
// load them into into DbContext
await DbContext.Set<JobCategory>()
.Where(x => jobCategoryIds.Contains(x.Id))
.LoadAsync();
Вместо того, чтобы просто вызывать LoadAsync()
отслеживаемую коллекцию, мне нужно загрузить нужные мне ссылочные объекты прямо в DbContext