EF Core 3.0 добавил несколько новых значений в перечисление DeleteBehavior
- ClientCascade
, NoAction
, ClientNoAction
. К сожалению, документация не обновляется (за исключением значений enum в справочнике по API), и только 3 ClientNoAction
упомянуто в 3.0 Breaking Changes - DeleteBehavior.Restrict имеет более чистую семантику :
Старое поведение
До версии 3.0 DeleteBehavior.Restrict
создавал внешние ключи в базе данных с семантикой Restrict
, но также изменял внутреннюю фиксацию неочевидным способом.
Новое поведение
Начиная с 3.0, DeleteBehavior.Restrict
обеспечивает создание внешних ключей с семантикой Restrict
, то есть без каскадов; выбросить при нарушении ограничения - без влияния на внутреннюю фиксацию EF.
Почему
Это изменение было сделано для улучшения опыта использования DeleteBehavior
в интуитивно понятном виде, без неожиданных побочных эффектов.
Смягчения
Предыдущее поведение можно восстановить с помощью DeleteBehavior.ClientNoAction
.
Дополнительная информация содержится в связанной с этим проблеме отслеживания - 12661: обновите DeleteBehavior, чтобы он был более последовательным и понятным
Честно говоря, даже после прочтения всего этого я не нахожу это чище, но еще более запутанно. Restrict
кажется устаревшим и заменен на NoAction
, который независимо от того, что было сказано на самом деле устанавливает свойство навигации для загруженных связанных объектов / FK в null
, таким образом вызывая поведение базы данных SET NULL
как вы уже испытали.
После попытки всех из них, единственный вариант, который делает то, что вы ожидаете, это вышеупомянутый ClientNoAction :
Примечание: это необычно для используйте это значение. Попробуйте вместо этого использовать ClientSetNull
, чтобы сопоставить поведение EF6 с отключенным каскадным удалением.
Для объектов, отслеживаемых DbContext
, значения свойств внешнего ключа в зависимых объектах не изменяются, когда связанный основной объект удален Это может привести к несогласованности графа сущностей, где значения свойств внешнего ключа не соответствуют отношениям в графе.
Если база данных была создана из модели с использованием Entity Framework Migrations или метода EnsureCreated()
тогда поведение в базе данных - генерировать ошибку, если ограничение внешнего ключа нарушено.
независимо от их примечания в начале.
С учетом всего сказанного просто замените Restrict
на ClientNoAction
, и проблема будет решена. Миграция базы данных не требуется, поскольку это изменение влияет только на поведение клиента.