我正试图编写一个脚本,用于在我们的合并复制快照代理程序完成将快照应用于订户后恢复对存储过程的权限。这个SQL需要有些动态。SQL Server - 使用WHILE循环问题执行语句
目前,我正在选择我们所有存储过程的列表,并将它们与字符串语句一起插入到临时表中以用于“授予”权限。我试图遍历该表上的所有行,使用EXEC()命令逐个执行语句。我不断收到
只有一个表达式可以在选择列表时,子查询不引入指定的错误EXISTS
但我的SQL语句看起来像他们应该罚款。也许我不理解WHILE在SQL Server中的工作原理。
这里是我的代码:
BEGIN
CREATE TABLE sqltemp (id int IDENTITY(1, 1) , Stmt1 varchar(max), Stmt2 varchar(max), Stmt3 varchar(max))
INSERT INTO sqltemp
SELECT
'GRANT EXECUTE ON OBJECT::' as Stmt1, name as Stmt2, 'TO edoc_only_execute' as Stmt3
FROM sys.sysobjects
WHERE
type = 'P' AND name NOT LIKE 'MSMerge%'
DECLARE @counter int = 1
WHILE (@counter < (SELECT COUNT(*) FROM sqltemp))
BEGIN
DECLARE @sqlrun varchar(max)
SET @sqlrun = (SELECT Stmt1, Stmt2, Stmt3 FROM sqltemp WHERE id = @counter)
EXEC(@sqlrun)
SET @counter = @counter + 1
END
END
GO
DROP TABLE sqltemp
两个问题:
我怎样才能做到在执行上面的脚本为每个项目在我的临时表?
是否有更好的方式来编写脚本,以便在应用快照后为我的数据库中的每个存储过程恢复权限(注意:我必须能够使用SQL系统表来提取存储过程名称)?
谢谢......好奇的寿。进一步解释为什么我的SET @sqlrun =(SELECT ....)不被sql服务器接受?只是想了解,所以我不会再犯同样的错误,并遵循最佳实践。 – Encryption
@Encryption - SQL Server中的变量是标量,它们只能包含单个数据类型的单个值。另一种方法是使用一个表变量,但在这种情况下,这并不会带给你任何地方。因此,您需要将三个值推入三个不同的变量,或者将它们连接起来,以便它们可以进入单个变量。 – MatBailie
因此,使用SELECT @@ sql提供了一个字符串,其中SET @SQL没有提供字符串类型? – Encryption