SQL动态拼接表名和日期参数的EXEC查询报语法错误如何解决?
报错原因
- 动态SQL拼接时,
DATETIME类型的@date变量会被隐式转换为字符串后再和SQL语句拼接,转换后的日期值没有被单引号包裹,最终拼接出的SQL语法非法,就会触发2022附近语法错误的提示。 - 直接拼接变量生成动态SQL还有SQL注入的安全隐患,属于不推荐的写法。
解决方案
优先使用sp_executesql实现参数化动态查询,仅表名做动态拼接,筛选条件的参数通过参数传递的方式传入,既解决语法问题,也避免注入风险,还不用处理日期转义、格式兼容问题:
DECLARE @table_name NVARCHAR(255); SET @table_name = 'dba.hello'; DECLARE @date DATETIME; SET @date = '09/01/2022'; DECLARE @sql NVARCHAR(MAX); -- 用QUOTENAME包裹表名、schema名,避免特殊字符或注入风险 SET @sql = N'SELECT * FROM ' + QUOTENAME(PARSENAME(@table_name,2)) + N'.' + QUOTENAME(PARSENAME(@table_name,1)) + N' WHERE datum = @date'; -- 执行动态SQL,传入参数定义和对应参数值 EXEC sp_executesql @stmt = @sql, @params = N'@date DATETIME', @date = @date;
如果你一定要用字符串拼接的方式实现,需要手动把日期转成字符串,并且前后加转义后的单引号,该写法不推荐,仅做参考:
DECLARE @table_name NVARCHAR(255); SET @table_name = 'dba.hello'; DECLARE @date DATETIME; SET @date = '09/01/2022'; -- 转义单引号、指定日期转换格式避免兼容性问题 EXEC('SELECT * FROM '+@table_name+' WHERE datum = '''+ CONVERT(VARCHAR(10),@date,120) +'''')
内容的提问来源于stack exchange,提问作者MedvidekPu
相关产品推荐
相关产品推荐

