是否有一种方法可以立即停止SQL服务器中SQL脚本的执行,如“break”或“exit”命令?

我有一个脚本,它在开始插入之前执行一些验证和查找,我希望它在任何验证或查找失败时停止。


当前回答

我用一个事务成功地扩展了noexec开/关解决方案,以全有或全无的方式运行脚本。

set noexec off

begin transaction
go

<First batch, do something here>
go
if @@error != 0 set noexec on;

<Second batch, do something here>
go
if @@error != 0 set noexec on;

<... etc>

declare @finished bit;
set @finished = 1;

SET noexec off;

IF @finished = 1
BEGIN
    PRINT 'Committing changes'
    COMMIT TRANSACTION
END
ELSE
BEGIN
    PRINT 'Errors occured. Rolling back changes'
    ROLLBACK TRANSACTION
END

显然,编译器“理解”IF中的@finished变量,即使有一个错误并且执行被禁用。但是,只有在未禁用执行时,该值才会设置为1。因此,我可以很好地提交或回滚事务。

其他回答

进一步细化Sglasses方法,上面的代码行强制使用SQLCMD模式,如果不使用SQLCMD模式,则终止脚本,或者使用:on error exit在出现任何错误时退出 CONTEXT_INFO用于跟踪状态。

SET CONTEXT_INFO  0x1 --Just to make sure everything's ok
GO 
--treminate the script on any error. (Requires SQLCMD mode)
:on error exit 
--If not in SQLCMD mode the above line will generate an error, so the next line won't hit
SET CONTEXT_INFO 0x2
GO
--make sure to use SQLCMD mode ( :on error needs that)
IF CONTEXT_INFO()<>0x2 
BEGIN
    SELECT CONTEXT_INFO()
    SELECT 'This script must be run in SQLCMD mode! (To enable it go to (Management Studio) Query->SQLCMD mode)\nPlease abort the script!'
    RAISERROR('This script must be run in SQLCMD mode! (To enable it go to (Management Studio) Query->SQLCMD mode)\nPlease abort the script!',16,1) WITH NOWAIT 
    WAITFOR DELAY '02:00'; --wait for the user to read the message, and terminate the script manually
END
GO

----------------------------------------------------------------------------------
----THE ACTUAL SCRIPT BEGINS HERE-------------

非常感谢这里的其他人以及我读过的其他帖子。 但没有什么能满足我所有的需求,直到@jaraics回答。

我所见过的大多数答案都忽略了具有多个批处理的脚本。他们忽略了SSMS和SQLCMD的双重用法。我的脚本在SSMS中是完全可运行的——但我想要F5预防,这样他们就不会在意外中删除现有的对象集。

SET PARSEONLY ON工作得很好,可以防止不必要的F5。但是你不能用SQLCMD运行。

另一件让我慢下来的事情是Batch在出现错误时如何跳过任何进一步的命令-所以我的SET NOCOUNT ON被跳过,因此脚本仍然运行。

不管怎样,我稍微修改了一下jaraics的答案:(在这种情况下,我还需要一个数据库从命令行激活)

-----------------------------------------------------------------------
-- Prevent accidental F5
-- Options:
--     1) Highlight everything below here to run
--     2) Disable this safety guard
--     3) or use SQLCMD
-----------------------------------------------------------------------
set NOEXEC OFF                             -- Reset in case it got stuck ON
set CONTEXT_INFO  0x1                      -- A 'variable' that can pass batch boundaries
GO                                         -- important !
if $(SQLCMDDBNAME) is not null
    set CONTEXT_INFO 0x2                   -- If above line worked, we're in SQLCMD mode
GO                                         -- important !
if CONTEXT_INFO()<>0x2 
begin
    select 'F5 Pressed accidentally.'
    SET NOEXEC ON                          -- skip rest of script
END
GO                                         -- important !
-----------------------------------------------------------------------

< rest of script . . . . . >


GO
SET NOEXEC OFF
print 'DONE'

如果你只是在Management Studio中执行一个脚本,并且想要在第一个错误时停止执行或回滚事务(如果使用),那么我认为最好的方法是使用try catch block (SQL 2005以后)。 如果您正在执行脚本文件,这在Management studio中工作得很好。 Stored proc也总是可以使用这个。

这就是我的解决方案:

...

BEGIN
    raiserror('Invalid database', 15, 10)
    rollback transaction
    return
END

在过去,我们使用了以下语句:效果最好:

RAISERROR ('Error! Connection dead', 20, 127) WITH LOG