如果我有以下SQL查询
CREATE TABLE #t1
(a INT NOT NULL PRIMARY KEY);
SET XACT_ABORT ON
go
BEGIN TRANSACTION
INSERT INTO #t1 VALUES (1);
INSERT INTO #t1 VALUES (2);
INSERT INTO #t1 VALUES (3);
INSERT INTO #t1 VALUES (2); -- PK violation error
go
INSERT INTO #t1 VALUES (4);
go
COMMIT TRANSACTION
SET XACT_ABORT OFF
当我运行查询时,我得到了这个输出
(1行受影响)
(1行受影响)
(1行(s)受影响)Msg 2627,Level 14,State 1,Line 7违反 PRIMARY KEY约束'PK_ #t1 _ __ _ _ _66D536B1'。无法插入 对象'dbo中的重复键。#t1'。
(1行(s)受影响)消息102,级别15,状态1,行8不正确 '#t1'附近的语法。
#t1的值是
a
-----------
4
我需要做什么才能使脚本中止而不运行第二批?
编辑:
尝试过JNK的解决方案
begin try
BEGIN TRANSACTION
INSERT INTO #t1 VALUES (1)
INSERT INTO #t1 VALUES (2)
INSERT INTO #t1 VALUES (3)
INSERT INTO #t1 VALUES (2) -- PK violation error
go
INSERT INTO #t1 VALUES (4)
go
COMMIT TRANSACTION
end try
begin catch
IF @@trancount > 0 Rollback
END catch
select * from #t1
truncate table #t1
但是我得到了这个输出
Msg 102, Level 15, State 1, Line 6
Incorrect syntax near ')'.
(1 row(s) affected)
Msg 102, Level 15, State 1, Line 5
Incorrect syntax near 'begin'.
Msg 102, Level 15, State 1, Line 8
Incorrect syntax near 'END'.
表格中仍然包含4个
EDIT2:
try catch的错误是因为GO语句,我需要为我的真实脚本而不是这个测试用例。所以看起来try / catch对于这种情况不起作用。
答案 0 :(得分:1)
添加错误处理:
BEGIN TRY
<your query>
END TRY
BEGIN CATCH
IF @@TRANCOUNT > 0 ROLLBACK
<other error reporting processes>
END CATCH
ROLLBACK
是可选的,将撤消在发生错误之前完成的所有插入。您还可以添加多个事务,因此如果前三个插入与以后的某些其他内容无关,请将它们包装在事务中并提交它,然后再为其进行另一个转换。
答案 1 :(得分:0)
begin try
begin transaction
INSERT INTO #t1 VALUES (1);
INSERT INTO #t1 VALUES (2);
INSERT INTO #t1 VALUES (3);
INSERT INTO #t1 VALUES (2);
INSERT INTO #t1 VALUES (4);
commit
end try
begin catch
if @@trancount > 0
rollback
declare @errmsg nvarchar(4000), @errseverity int
select @errmsg = error_message(), @errseverity = error_severity()
raiserror(@errmsg, @errseverity, 1)
end catch
来自MSDN: “ 将GO解释为他们应该将当前批处理的Transact-SQL语句发送到SQL Server实例的信号。当前一批语句由自上次GO以来输入的所有语句组成,或者自ad hoc会话或脚本开始以来(如果这是第一个GO )。
Transact-SQL语句不能与GO命令占用同一行。但是,该行可以包含注释。 “