Представьте, как бы вы это реализовали.
Если решение по внешнему ключу будет отложено до фиксации транзакции, то при фиксации потребуется выполнить все операции поиска / проверки / каскада, которые не выполнялись во время вставки / удаления / обновления. Подумайте, что на самом деле означает ограничение FK: ваш план выполнения вставки «аннотируется» дополнительной операцией для проверки и применения ограничения FK. Если вы отложите ограничение, дополнительная логика в плане запроса должна быть не связана с моментом выполнения и помещена в некоторый контекст транзакции, чтобы он выполнялся во время принятия. Внезапная фиксация превращается из операции «короткая транзакция зафиксирована в журнале» в операцию, которая выполняет все, что было пропущено во время реальной транзакции. Хуже всего то, что ограничение может потерпеть неудачу, и подумать , как приложение обработает ошибку ? Если в момент выполнения вставки введено ограничение, приложение может отловить ошибку и предпринять корректирующие действия: оно точно знает, что не удалось. Но если вы отложите это до фиксации, вы попытаетесь зафиксировать и поймать исключение, теперь вам нужно как-то выяснить, из-за исключения, что не удалось. Подумайте, насколько сложна жизнь разработчиков приложений в этом случае.
Вторая причина, по которой это не сработало, заключается в том, что вы все еще не решили проблему. У вас есть таблица A с ограничением FK в B. Вы начинаете транзакцию, вставляете в B, затем вставляете в A, затем удаляете из A, затем удаляете из B, затем фиксируете. Все операции удовлетворяли FK в момент их возникновения, база данных удовлетворяла FK во время фиксации. Тем не менее, если вы отложите проверку ограничений, они будут терпеть неудачу во время фиксации !!
Так что я бы сказал, что ссылочная целостность работает нормально, как есть, но она разработана для каскадной иерархии, свободной от циклов. Как и многие структуры данных CS и алгоритмы, он ломается, когда вводятся циклы. Лучшим решением было бы проанализировать схему и посмотреть, действительно ли циклы неизбежны. Если не считать этого, вставка NULL и обновление пост-вставки - лучшее решение.
К сожалению, отключение ограничения и включение возврата - это большая проблема: нет, повторное включение должно проверять каждую строку в таблице, чтобы проверить ограничение, и будет длиться вечно. В противном случае ограничение помечается как «ненадежное» в метаданных базы данных, и оптимизатор в основном игнорирует его (все равно будет применено, но вы не получите от него преимуществ оптимизации плана).