#sql-server #sqltransaction
#sql-сервер #sqltransaction
Вопрос:
У меня есть транзакция и две таблицы, в которые я вставляю некоторые данные, могу ли я выполнить частичную фиксацию в SQL Server
BEGIN TRANSACTION tran1
BEGIN TRY
--Insert into Table1
--Insert into Table2
COMMIT TRANSACTION tran1
END TRY
BEGIN CATCH
ROLLBACK TRANSACTION tran1
END CATCH
Приведенный выше код откатит данные обеих таблиц, есть ли способ, которым мы можем зафиксировать таблицу 1, если в вставке таблицы 1 нет ошибки, но откат таблицы 2, если произошла какая-либо ошибка.
Ответ №1:
Ответ — да, хотя транзакции действительно являются атомарными, вы могли бы использовать точку сохранения. Итак, в вашем случае код может выглядеть следующим образом (непроверенный):
BEGIN TRY
BEGIN TRANSACTION
--Insert into Table1
-- savepoint
SAVE TRANSACTION tran1
--Insert into Table2
-- commit the whole transaction
COMMIT TRANSACTION
END TRY
BEGIN CATCH
-- rollback to savepoint
IF @@TRANCOUNT > 0 ROLLBACK TRANSACTION tran1
END CATCH
Возможно, вам придется изменить порядок вставки.
Ответ №2:
Нет, ты не можешь. Транзакция является атомарной. То есть все шаги выполняются как один, фиксируются вместе или откатываются. Если вы помещаете обе вставки в одну транзакцию, вы не сможете зафиксировать их в одной таблице. Вы можете использовать различные транзакции, если это возможно.
Комментарии:
1. можете ли вы взглянуть на приведенный выше ответ, видите ли вы какую-либо проблему с вышеуказанным подходом
2. На самом деле выглядит нормально. Эта точка сохранения является функцией MSSQL. В этом случае это почти то же самое, что иметь 2 транзакции, за исключением того, что при первом сбое 2-я не будет работать
3. Чего вы пытаетесь достичь здесь?
4. Нет, я просто изучаю, существует ли эта функция в MSSQL или не более того, в любом случае спасибо, что помогли мне
5. NP, еще один метод, о котором я могу подумать, заключается в том, чтобы поместить try catch внутри транзакции. Таким образом, он попробует обе таблицы