有没有办法只在定义更改时替换 SQL Server 存储过程?

ber*_*d_k 4 sql-server stored-procedures

我知道以下两种模式来编写创建存储过程的脚本,可以重复执行而不抛出错误。

if object_id('my_proc') > 0 drop procedure my_proc
go
create procedure dbo.my_proc as Print 'This is not a dummy';
Run Code Online (Sandbox Code Playgroud)

另一个保留权限

if object_id('my_proc') is null
    EXEC ('create procedure dbo.my_proc as Print ''This is a dummy''');
go
ALTER PROCEDURE dbo.my_proc as Print 'This is not a dummy';
    
Run Code Online (Sandbox Code Playgroud)

我猜当该过程存在并且其哈希码与新版本的哈希码相同时,就不需要删除并重新创建或更改该过程。

我的问题是HashBytes被限制为最多 8000 个字节,我不能像这样使用它

if object_id('my_proc') is null
    EXEC ('create procedure dbo.my_proc as Print ''This is a dummy''');
go
if object_Id('my_proc') > 0
and
(
Select HashBytes('MD5',definition) MD5
from sys.sql_modules m
join sysobjects o on o.id = m.object_id
where o.name = 'my_proc'
) <> 0x9028A1B9D93AC7592EC939CCABF9D3DE
begin
    print 'definition has changed';
    EXEC ('ALTER PROCEDURE dbo.my_proc as Print ''This is not a dummy''');
end 
Run Code Online (Sandbox Code Playgroud)

对于定义超过 4000 个字符的过程。有没有以类似方式处理这些案件的建议?

编辑:

我不仅要避免刷新缓存计划。

我还必须应对拥有不同版本存储过程的不同客户,在这些客户中,我只想用更新版本替换这些变体之一。

gbn*_*gbn 6

不应将权限分配给存储过程

您的存储过程应该位于架构中,权限在架构上(授予角色)。这样,该架构中的新对象将自动拥有权限。任何单个对象都不应具有权限

所以无论哪种方式都可以。

查看其他 DBA 问题:

仅供参考,object_id 被签名为 int所以使用“不等于”

if object_id('my_proc') <> 0 drop procedure my_proc
Run Code Online (Sandbox Code Playgroud)

编辑,nvarchar(max) 可以直接比较

if object_Id('my_proc') <> 0
    drop proc ThenewProc
GO
CREATE PROC ThenewProc
...
GO

IF object_definition(object_id('my_proc')) <> 
         object_definition(object_id('ThenewProc')) <> 0
BEGIN
    drop procedure my_proc
    drop proc ThenewProc
END
GO
CREATE PROC my_proc
...
GO
Run Code Online (Sandbox Code Playgroud)