2

我正在创建一个部署包,它将运行 VSS 中的存储过程。我能够做到这一点,但我的问题是这个。我需要部署到或多或少 30 个数据库,而我只有两个不需要获取更新的数据库。有了这个,我在批处理文件运行的 .sql 文件中包含了以下代码:

IF OBJECT_ID('CONFIG') IS NULL OR  DB_NAME() LIKE '%SampleDB%'
BEGIN
    PRINT 'This is not a store database. Skipping this database.'
    SET NOEXEC ON
    RETURN
END

IF EXISTS (SELECT * FROM dbo.sysobjects WHERE ID = OBJECT_ID(N'[dbo].[sp_ThisIsMySampleProcedure]'))
     DROP PROCEDURE [dbo].[sp_ThisIsMySampleProcedure]
GO

SET QUOTED_IDENTIFIER OFF 
GO
SET ANSI_NULLS OFF 
GO

CREATE PROCEDURE [dbo].[sp_ThisIsMySampleProcedure]
-- Everything else follows...

此 sql 代码在 SQL Server 上完美运行。每当我对 Sample DB 运行它时,它都会自动跳过检查过程是否存在以及之后的所有内容。

但是,每当我尝试使用我的批处理文件对 SampleDB 运行它时,它都会提示错误消息,但会继续运行该过程而忽略我的RETURN关键字。所以消息看起来像这样:

这不是商店数据库。跳过此数据库。
消息 3701,级别 11,状态 5,第 8 行
无法删除过程“sp_ThisIsMySampleProcedure”,因为它不存在或您没有权限。

我知道错误消息是正确的,因为我的 SampleDB 上确实不存在该过程。但是,为什么RETURN在它满足跳过运行整个脚本的条件后,当我在那里有关键字时它仍然继续运行?

谢谢!

编辑:

好吧,我认为人们并不完全理解我。这是场景:我的过程(见上文)在 SQL Server Management Studio 上运行良好。我的意思是,每当我尝试在 SampleDB 上运行它时,它都会给我消息This is not a store database. Skipping this database.

但是,每当我尝试运行执行此存储过程的批处理文件时,我都会在命令提示符下收到此消息:

这不是商店数据库。跳过此数据库。
消息 3701,级别 11,状态 5,第 8 行
无法删除过程“sp_ThisIsMySampleProcedure”,因为它不存在或您没有权限。

这基本上意味着无论第一个条件是否满足,批处理文件都会继续执行整个 SQL 脚本。

我的问题是如何让批处理文件知道每当 SQL Server 抛出消息This is not a store database. Skipping this database.时,批处理文件将立即停止执行 sql 文件。

4

1 回答 1

1

第一的。关键字GO将文件分成单独的请求。每个请求都由服务器单独处理。RETURN仅从第一个请求退出,将运行其他请求。

尝试这个:

select 1
RETURN
select 2
go
select 3
go

其次,SET NOEXEC ON是危险的事情,它会阻止所有后续执行。尝试这个:

select 1
SET NOEXEC ON
RETURN
select 2
go
select 3
go
SET NOEXEC OFF
go

您可以在所有服务器上创建过程,但如果数据库名称类似某些东西,则在开始时从它返回。或者您可以使用动态 SQL 删除GO和创建存储过程:

IF DB_NAME() like '%mydb%'
BEGIN
    EXEC dbo.sp_executesql @statement = N'
    CREATE PROCEDURE [dbo].[my proc]
    AS 
    BEGIN 
        select 1
    END'
END
于 2013-06-21T15:41:51.067 回答