我正在尝试使我的数据库名称可配置为能够运行这样的内容:
declare @x nvarchar(MAX)
declare @y nvarchar(MAX)
set @x = 'database1'
set @y = 'database2'
select * from @x.table1 INNER JOIN @y.table2 ON ....
有没有办法在SQL Server 2016上实现它? 非常感谢。
答案 0 :(得分:5)
一种方法是使用SQLCMD变量:
:SETVAR x "database1"
:SETVAR y "database2"
SELECT * FROM $(x).dbo.table1 INNER JOIN $(y).dbo.table2 ON ....
要在SSMS中运行SQLCMD脚本,请从“查询”菜单中启用SQLCMD模式。
如果使用SQLCMD
实用程序从命令行运行脚本,则可以省略SETVAR
命令并将值作为命令行参数传递。
答案 1 :(得分:2)
您无法在SQL中参数化标识符 您唯一的选择是使用动态SQL。 (顺便说一句,您的代码示例表明您正在讨论的是表,而不是数据库)
declare @x sysname, @sysname, @sql nvarchar(max)
SELECT @x = 'table1',
@y = 'table2'
SET @SQL = 'SELECT * FROM '+ @x +' INNER JOIN '+ @y +' ON ....'
EXEC(@SQL)
但是,由于这是动态SQL,因此您正在为SQL注入攻击打开一扇门。 还有两件事要做,以保护自己:
quotename
所以更好的代码就是这样:
declare @x sysname, @sysname, @sql nvarchar(max)
SELECT @x = 'table1',
@y = 'table2'
IF
(
SELECT COUNT(*)
FROM InformationSchema.Tables
WHERE TABLE_NAME IN(@x, @y)
) = 2
BEGIN
SET @SQL = 'SELECT * FROM quotename('+ @x +') INNER JOIN quotename('+ @y +') ON ....'
EXEC(@SQL)
END
答案 2 :(得分:0)
使用SYNONYMs
create SYNONYM YourTableReference FOR YourDatabaseName.dbo.YourTable;
create SYNONYM YourTableRefernce2 FOR YourDatabaseNameNumber2.dbo.YourTable;
select * from YourTableReference r
inner join YourTableRefernce2 r2 on r.Id=r2.Id -- etc . . . .