T-SQL中如何在OPENQUERY里使用STRING_AGG生成的NVARCHAR做WHERE IN查询
可行实现方案
方案1:预转义拼接IN参数(全版本兼容)
核心逻辑是先把逗号分隔的@THE_DDT处理成符合IN语法要求的带单引号格式,再处理多层嵌套的单引号转义:
- 先处理
@THE_DDT得到符合IN要求的参数格式:
-- 原始生成逻辑不变的前提下,额外处理格式 DECLARE @IN_PART NVARCHAR(MAX) = '''' + REPLACE(@THE_DDT, ',', ''',''') + '''' -- 处理OPENQUERY双层嵌套的单引号转义:单个单引号转义为4个单引号 DECLARE @ESCAPED_IN NVARCHAR(MAX) = REPLACE(@IN_PART, '''', '''''')
- 替换原OPENQUERY的WHERE条件:
SELECT @MY_QUERY = 'SELECT * FROM OPENQUERY(HYPER_CONN, '' SELECT COALESCE(SUM(QUANT_RIGA),0) FROM DDT_CLI_RIGHE WHERE DOC_RIGA_ID IN (' + @ESCAPED_IN + ') '')'
也可以直接在生成@THE_DDT的时候就完成格式处理,减少后续转义步骤:
DECLARE @THE_DDT nvarchar(MAX) = ( SELECT '''' + STRING_AGG(DOC_RIGA_ID, ''',''') + '''' FROM 你的原查询表 )
方案2:用字符串拆分函数实现(更安全,避免SQL注入)
如果HYPER_CONN连接的目标数据库支持STRING_SPLIT同类函数(SQL Server 2016及以上、PostgreSQL、MySQL 8.0等均支持),可以直接传递原始逗号分隔字符串,在远程查询内拆分后匹配,无需处理复杂的单引号转义:
SELECT @MY_QUERY = 'SELECT * FROM OPENQUERY(HYPER_CONN, '' SELECT COALESCE(SUM(QUANT_RIGA),0) FROM DDT_CLI_RIGHE WHERE DOC_RIGA_ID IN (SELECT value FROM STRING_SPLIT(''''' + @THE_DDT + ''''', '','')) '')'
注意事项
- 如果
DOC_RIGA_ID是数值类型,无需拼接单引号,直接把逗号分隔的数值串放到IN括号内即可 - 动态拼接SQL需注意防范SQL注入风险,确保
@THE_DDT的数据源可控,优先选择方案2规避注入风险
内容的提问来源于stack exchange,提问作者user222137
相关产品推荐
相关产品推荐

