У меня есть такая ситуация: регулирование может быть изменено другим регламентом и может изменить другие регламенты.Или оно может быть отменено другим правилом и может отменить другие правила.
public class Regulation
{
public int Id { get; set; }
public int? AmendedByRegulationId { get; set; }
public virtual Regulation AmendedByRegulation { get; set; }
readonly HashSet<Regulation> amendedRegulations = new HashSet<Regulation>();
public virtual IReadOnlyCollection<Regulation> AmendedRegulations => amendedRegulations.ToList();
readonly HashSet<Regulation> repealedRegulations = new HashSet<Regulation>();
public virtual IReadOnlyCollection<Regulation> RepealedRegulations => repealedRegulations.ToList();
public void MergeAmendedRegulations(HashSet<Regulation> incomingAmendedRegulations)
{
if (incomingAmendedRegulations.IsNullOrEmpty())
return;
foreach (var dbAmendedRegulation in AmendedRegulations)
{
if (!incomingAmendedRegulations.Contains(dbAmendedRegulation))
{
amendedRegulations.Remove(dbAmendedRegulation);
dbAmendedRegulation.AmendedByRegulationId = null;
}
}
foreach (var amendedRegulationToAdd in incomingAmendedRegulations)
{
if (!amendedRegulations.Contains(amendedRegulationToAdd))
{
amendedRegulations.Add(amendedRegulationToAdd);
amendedRegulationToAdd.AmendedByRegulationId = Id;
}
}
}
}
/// mapping
builder.HasOne(r => r.AmendedByRegulation)
.WithMany(r => r.AmendedRegulations)
.HasForeignKey(r => r.AmendedByRegulationId);
Таким образом, таблица правил содержит Id [int] not null, AmendedByRegulationId [int] null
столбцы.Столбец AmendByRegulationId заполняется идентификатором поправки к Регламенту.
Регламент также загружен .Include(r => r.AmendedRegulations);
Метод MergeAededRegulations () получает данные, сопоставленные с DTO, а для параметра входящего в составRegulations имеется только список идентификаторов, выбранныйиз списка.
Когда я пытаюсь сохранить, EF Core пытается вставить измененное правило, что неправильно.Он должен обновлять только свойство / столбец AmendByRegulationId.
public async Task UpdateAsync(Regulation regulation)
{
await updateAmendedRegulations(dbContext, regulation);
await updateRepealedRegulations(dbContext, regulation);
await dbContext.SaveChangesAsync();
}
async Task updateAmendedRegulations(DbContext dbContext, Regulation regulation)
{
if (regulation.AmendedRegulations.Any())
{
foreach (var ar in regulation.AmendedRegulations)
{
dbContext.Entry(ar).Property(e => e.AmendedByRegulationId).IsModified = true;
}
// ... other code
}
}
Когда я вручную отмечаю свойство AmendByRegulationId как измененное, оно работает, однако
dbContext.Entry(ar)
создает исключение, если объект являетсяуже присутствует в коллекции RepealedRegulations.
Мои вопросы:
Является ли это моделирование стандартным?
Правильно ли сопоставление EF?
Как я могу исправить эти отношения с EF Core?