2016-12-07 142 views
3

我知道我们对这个问题有很多答案,但是我仍然不明白这个错误的真正原因。必须声明标量变量“@serverName”

我已经创建了这样的存储过程。

CREATE PROCEDURE [dbo].[storedProc_dataPull] 
    @serverName nvarchar(30), 
    @dbName nvarchar (30), 
    @tblName nvarchar(30) 
AS BEGIN 
    DECLARE @sql nvarchar(500) 
    DECLARE @ds nvarchar(500) 

    SET @ds = 'Data Source=phmnldb16\eaudit;user id=YYYY;password=XXXX' 
    SET @sql = 'SELECT @serverName, @dbName, sdb1.* from 
       OPENDATASOURCE(''SQLOLEDB'', '+Char(39)+ @ds +Char(39)+ ').AUDIT_FSA_170_001.AUD170.Workflow sdb1)' 
    INSERT INTO sampleDatabase.dbo.WorkFlowCopy 
     ([ServerName] 
     ,[DBName] 
     ,[ID] 
     ,[ActivityDefinitionID] 
     ,[ParentID] 
     ,[Caption] 
     ,[Description] 
     ,[ShortDescription] 
     ,[Name] 
     ,[Order] 
     ,[ReferenceNumber] 
     ,[ShowOnNavigation] 
     ,[Status] 
     ,[InUseBy]) 

    EXEC (@sql) 

,当我试图执行它..

EXEC storedProc_dataPull 'serverName', 'dbName', 'tblName' 

我总是得到这个错误:

Msg 137, Level 15, State 2, Line 1
Must declare the scalar variable "serverName"

+0

您不能从'EXEC(@sql)'内部访问'@ serverName'(或任何其他变量),因为它们是在它之外声明的。动态SQL不能像那样工作。 – Blorgbeard

+0

请参阅:http://stackoverflow.com/questions/28481189/exec-sp-executesql-with-multiple-parameters – Blorgbeard

+0

如果我不能从EXEC(@sql)访问@serverName,那么什么是最好的解决方案那? – Jhe

回答

1

您使用@serverName作为字符串的一部分。尝试

SET @sql = 'SELECT ' + @serverName + ',' + @dbName + ', sdb1.* from 
      OPENDATASOURCE(''SQLOLEDB'','+Char(39)+ @ds + Char(39)+ ').AUDIT_FSA_170_001.AUD170.Workflow sdb1' 

,而不是

SET @sql = 'SELECT @serverName, @dbName, sdb1.* from 
      OPENDATASOURCE(''SQLOLEDB'', '+Char(39)+ @ds +Char(39)+ ').AUDIT_FSA_170_001.AUD170.Workflow sdb1)' 

我已经在@sql年底将额外的支架为好。

3

使用SP_EXECUTESQL将值传递给参数的动态SQL

SET @sql = 'SELECT @serverName, @dbName, sdb1.* from 
       OPENDATASOURCE(''SQLOLEDB'', ' 
      + Char(39) + @ds + Char(39) 
      + ').AUDIT_FSA_170_001.AUD170.Workflow sdb1' -- unwanted close parenthesis 

INSERT INTO sampleDatabase.dbo.WorkFlowCopy 
      ([ServerName], 
      [DBName], 
      [ID], 
      [ActivityDefinitionID], 
      [ParentID], 
      [Caption], 
      [Description], 
      [ShortDescription], 
      [Name], 
      [Order], 
      [ReferenceNumber], 
      [ShowOnNavigation], 
      [Status], 
      [InUseBy]) -- Missing close parenthesis 
EXEC Sp_executesql 
    @sql, 
    N'@serverName nvarchar(30), @dbName nvarchar (30)', 
    @[email protected], 
    @[email protected] 

注意里面:

  • Select列表你已经使用,*确保选择列表返回相同的列数为Insert列表顺序相同
  • 有一个缺失关闭括号末尾的Insert列列表和不需要的右括号末尾的OPENDATASOURCE查询
  • @tblName输入参数未在过程中使用。