Tsql 什么';当我们绕过SQL Server';UDF中副作用操作的限制?

Tsql 什么';当我们绕过SQL Server';UDF中副作用操作的限制?,tsql,Tsql,今天,我使用这种方法取得了巨大成功,根据数据中的“测试”/“生产”标志,在同一数据库模式的多个实例中使用随机垃圾替换名称、保险号和地址 背景:尝试做什么 CREATE FUNCTION dbo.FailsToCreate() RETURNS uniqueidentifier AS BEGIN RETURN NEWID() END 不可避免地以失败告终 Msg 443,16级,状态1,程序FailsToCreate,第6行[批次开始第27行] 在函数中使用副作用运算符“newid”无

今天,我使用这种方法取得了巨大成功,根据数据中的“测试”/“生产”标志,在同一数据库模式的多个实例中使用随机垃圾替换名称、保险号和地址

背景:尝试做什么

CREATE FUNCTION dbo.FailsToCreate() 
RETURNS uniqueidentifier 
AS 
BEGIN 
  RETURN NEWID()
END
不可避免地以失败告终

Msg 443,16级,状态1,程序FailsToCreate,第6行[批次开始第27行] 在函数中使用副作用运算符“newid”无效。

现在我们可以做个大坏蛋了

CREATE VIEW dbo.vwGuessWhat AS SELECT NEWID() Fooled
这让我们很惊讶地发现它可以与

CREATE FUNCTION dbo.SuddenlyWorks() 
RETURNS uniqueidentifier 
AS 
BEGIN 
  RETURN (SELECT Fooled FROM vwGuessWhat)
END
他对后果保持沉默。它只列出了不能使用的函数,没有提到绕过限制的可能性


我是否可以安全地继续在生产代码中使用此方法,或者绕过SQL Server的验证是否存在导致其出现故障的危险?

本身没有风险。您提供了一种有趣的方法来规避SQL函数的限制

另一方面,标量UDF的许多问题之一是它们破坏了并行性。换句话说,使用dbo.SuddenlyWorks()的查询将始终连续运行,即使使用Adam Machanic的make_parallel()或traceflag 8649


如果您想要一个并行计划,您需要使dbo.SuddenlyWorks()成为一个内联表值函数。

文档中怎么说?为什么你会相信一个随机的人对官方文件的意见呢?他对后果保持沉默。它只列出了不能使用的函数,没有提到绕过限制的可能性。为什么你认为这个问题会吸引固执己见的答案?我希望看到确凿的事实,比如“在场景X中,它会因为Y而发生故障”。@dlatikay我实际上同意这是一个合理的问题;但是,我认为答案是“它没有定义,或者:它被定义为非法”(取决于您对它的解释)——唯一能够回答这个问题的人是SQL Server开发人员。无论哪种方式,我个人都不会在行为未定义或定义为非法的情况下使用。在这种情况下,您不是从UDF内部调用非确定性函数,而是从视图中选择一个值,这不是同一件事,即使视图提供了您想要的。我个人的意见(嗯,这似乎在某种程度上是基于观点的…):我会使用
视图
方法。许多人这样做是为了创建一个随机数(例如,取
NEWID()
的前4个字节,并将它们转换为
INT
。这是因为重复调用
RAND()
会返回所有调用的结果相同…)如果微软能修复这一问题,大量高效的代码将被破坏。。。