我需要使用公共EXEC
命令从另一个执行存储过程。
我需要确定,所有sql语句都将在事务中。
BEGIN TRANSACTION
BEGIN TRY
SET @Esercizio = (SELECT ESERCIZIO_OBIETTIVI_CONSUNTIVARE from TB_SCHEDE WHERE MATRICOLA = @iMATRICOLA and COD_VALUTAZIONE = @iCOD_VALUTAZIONE)
SET @TipoProcesso = (SELECT ISNULL(TipoProcesso, 'middle') from TB_SCHEDE WHERE MATRICOLA = @iMATRICOLA and COD_VALUTAZIONE = @iCOD_VALUTAZIONE)
DELETE FROM TB_SCHEDE WHERE MATRICOLA = @iMATRICOLA and COD_VALUTAZIONE = @iCOD_VALUTAZIONE
DELETE FROM TB_SCHEDE_AUTOVAL WHERE MATRICOLA = @iMATRICOLA and COD_VALUTAZIONE = @iCOD_VALUTAZIONE
DELETE FROM TB_OBIETTIVI WHERE MATRICOLA = @iMATRICOLA and ESERCIZIO = @Esercizio
DELETE FROM TB_OBIETTIVI_AUTOVAL WHERE MATRICOLA = @iMATRICOLA and ESERCIZIO = @Esercizio
EXEC AnotherStore @iCOD_VALUTAZIONE, @iMATRICOLA, @TipoProcesso
COMMIT TRANSACTION
END TRY
BEGIN CATCH
ROLLBACK TRANSACTION
END CATCH
如果AnotherStore
过程抛出异常,数据库引擎是否确保从调用者存储过程回滚?
希望明确。
答案 0 :(得分:2)
有关事务存在时异常处理的示例,请参阅Exception handling and nested transactions:
create procedure [usp_my_procedure_name]
as
begin
set nocount on;
declare @trancount int;
set @trancount = @@trancount;
begin try
if @trancount = 0
begin transaction
else
save transaction usp_my_procedure_name;
-- Do the actual work here
lbexit:
if @trancount = 0
commit;
end try
begin catch
declare @error int, @message varchar(4000), @xstate int;
select @error = ERROR_NUMBER(), @message = ERROR_MESSAGE(), @xstate = XACT_STATE();
if @xstate = -1
rollback;
if @xstate = 1 and @trancount = 0
rollback
if @xstate = 1 and @trancount > 0
rollback transaction usp_my_procedure_name;
raiserror ('usp_my_procedure_name: %d: %s', 16, 1, @error, @message) ;
end catch
end
答案 1 :(得分:1)
简单的答案是肯定的是它将回滚调用者存储过程的更改,但是如果你在其他存储过程中有事务,那就考虑一下,如果是这种情况,有可能事情不像你期望的那样。 ROLLBACK
会影响所有交易,尽管这可能是您想要的。您可以在捕获中使用@@TRANCOUNT
并确定是否要回滚整个内容,Savepoints.
BEGIN TRANSACTION
和COMMIT
或ROLLBACK
之间的所有到数据库都是事务的一部分,如果有任何行出错,请控制将被路由到将回滚事务的CATCH
块。 像表变量这样的东西将超出此范围而不会回滚。正如@David Brabant所说,BEGIN TRANSACTION
应该在BEGIN TRY
块中。