SQL SERVER 2008动态查询问题

时间:2009-09-21 10:37:11

标签: sql sql-server

我有一个动态查询,如下所示

Alter PROCEDURE dbo.mySP 
    -- Add the parameters for the stored procedure here
    (
        @DBName varchar(50),
        @tblName varchar(50)

    )

AS
BEGIN
-- SET NOCOUNT ON added to prevent extra result sets from
-- interfering with SELECT statements.
SET NOCOUNT ON;

-- Insert statements for procedure here
declare @string as varchar(50)
declare @string1 as varchar(50)

set @string1  = '[' + @DBName + ']' + '.[dbo].' + '[' + @tblName + ']'

set @string = 'select * from ' + @string1   

exec @string

END

我这样打电话

dbo.mySP 'dbtest1','tblTest'

我遇到了错误

"Msg 203, Level 16, State 2, Procedure mySP, Line 27
The name 'select * from [dbtest1].[dbo].[tblTest]' is not a valid identifier."

有什么问题?以及如何克服?

提前致谢

4 个答案:

答案 0 :(得分:5)

它认为@string的内容是指存储过程名称。你需要把

EXEC (@string)

或更好地使用存储过程sp_executesql

您还应该设置一些保护代码,以检查传入的值是真实表和数据库的名称。您可以在INFORMATION_SCHEMA中查询视图以验证输入。

您可以在我的博客上阅读safer dynamic SQL上的更多内容。

答案 1 :(得分:4)

更改

exec @string

exec(@string)

这是我刚刚测试的一个正在运行的SP:

CREATE PROCEDURE [dbo].[test] 
    @DBName varchar(50),
    @tblName varchar(50)
AS
BEGIN
    SET NOCOUNT ON;

    DECLARE @string AS VARCHAR(50)
    DECLARE @string1 AS VARCHAR(50)

    SET @string1 = '[' + @DBName + '].[dbo].[' + @tblName + ']'
    SET @string = 'select * from ' + @string1

    EXEC(@string)
END

答案 2 :(得分:1)

如果您使用EXEC:

EXEC @String

它正在尝试运行一个名称包含在@String变量中的过程。尝试一下:

create procedure TestProc
as
print 'you called TestProc!'
go

declare @string varchar(20)
set @string='TestProc'

exec @string

如果您使用EXEC:

EXEC (@Query)

你在@Query变量中运行sql,试试看:

DECLARE @Query  varchar(50)
set @Query='Print ''just ran it!'''

EXEC (@Query)

答案 3 :(得分:0)

ALTER PROCEDURE test_sp
    -- Add the parameters for the stored procedure here
    (
        @DBName varchar(50),
        @tblName varchar(50)

    )

AS
BEGIN
-- SET NOCOUNT ON added to prevent extra result sets from
-- interfering with SELECT statements.
SET NOCOUNT ON

-- Insert statements for procedure here
declare @string as varchar(100)
declare @string1 as varchar(50)

set @string1  = '[' + @DBName + ']' + '.[dbo].' + '[' + @tblName + ']'
Print @string1
set @string = 'select * from'  + @string1       
Print @string
exec (@string)
SET NOCOUNT OFF  
END