【问题标题】:How to get sp_executesql to accept parameter values that are not nvarchar如何让 sp_executesql 接受不是 nvarchar 的参数值
【发布时间】:2015-07-24 01:07:30
【问题描述】:

我正在尝试在存储过程中构建动态 SQL 语句。这是它的简化版本:

CREATE PROC dbo.GetOrders
    @UserID INT = 2
AS
    DECLARE @SQLString NVARCHAR(MAX)

    SET @SQLString = N'(
                 SELECT * FROM dbo.Orders WHERE UserID = '+@UserID+'
                 )
    EXEC sys.sp_executesql @SQLString

我遇到的问题是 sp_executesql 仅适用于 Unicode 数据。所以我在@UserID 参数上得到一个转换错误,它是一个整数:

转换 nvarchar 值时转换失败 'SELECT * FROM dbo.Orders WHERE UserID = '

我必须在存储过程开始时声明我的参数并让用户提供这些值。到目前为止,我看到的使用sp_executesql 的示例显示了在sp_executesql 运行时定义的参数及其值。这对我不起作用,因为我需要在同一存储过程的其他区域重用参数。

如果不将所有参数指定为nvarchar 类型,我该如何解决这个问题?

【问题讨论】:

    标签: sql-server stored-procedures sql-server-2012 dynamic-sql sp-executesql


    【解决方案1】:

    试试这个...

    CREATE PROC dbo.GetOrders
    @UserID INT = 2
    AS
    BEGIN
      SET NOCOUNT ON;
      DECLARE @SQLString NVARCHAR(MAX);
    
        SET @SQLString = N' SELECT * FROM dbo.Orders ' 
                       + N' WHERE UserID = @UserID '
    
    
    EXEC sp_executesql @SQLString
                       ,N'@UserID INT'
                       ,@UserID
    END
    

    或者干脆用下面的

    CREATE PROC dbo.GetOrders
    @UserID INT = 2
    AS
    BEGIN
      SET NOCOUNT ON;
    
     SELECT * FROM dbo.Orders 
     WHERE UserID = @UserID 
    END
    

    【讨论】:

    • 所以每次我想运行 sp_executesql 我都必须重新声明参数并再次设置它们的值?我将示例简化到最低限度。真正的存储过程大约有10-15个参数。并且 sp_executesql 命令驻留在许多地方(由于 IF/ELSE 分支)
    • 是的,您需要单独重新定义 sp_executesql 的参数,因为它有自己的范围,在其范围之外声明的任何内容对 sp_executesql 都不可见。
    • 我明白了。作为一种解决方法,我将参数定义存储在一个变量中,例如@SQLParamDef = N'@UserID int, @OrderID int, etc',并在 sp_executesql 需要的任何地方重新使用该变量。似乎工作!
    【解决方案2】:

    不清楚您为什么在这里使用动态 SQL,但这是正确的方法。

    CREATE PROC dbo.GetOrders
    @UserID INT = 2
    AS
    DECLARE @SQLString NVARCHAR(MAX)
    SET @SQLString = N'SELECT * FROM dbo.Orders WHERE UserID = @UserID'
    
    EXEC sys.sp_executesql @SQLString, N'@UserID int', @UserID= @UserID
    

    【讨论】:

    • 所以每次我想运行 sp_executesql 我都必须重新声明参数并再次设置它们的值?我将示例简化到最低限度。真正的存储过程大约有10-15个参数。并且 sp_executesql 命令驻留在许多地方(由于 IF/ELSE 分支)。
    猜你喜欢
    • 1970-01-01
    • 2013-01-27
    • 1970-01-01
    • 2016-06-11
    • 1970-01-01
    • 2018-03-01
    • 2012-10-22
    • 1970-01-01
    • 2015-10-23
    相关资源
    最近更新 更多