使用正则表达式将注释格式字符串自动转换为 SQL WHERE 子句

6次阅读

使用正则表达式将注释格式字符串自动转换为 SQL WHERE 子句

本文介绍一种健壮的正则表达式方案,结合 JavaScript 的 String.prototype.replace() 与回调函数,可将形如 /* Col1: ABC, Col2: 123 */ 的注释字符串精准解析并转换为标准 sql WHERE 子句(如 WHERE Col1 = ‘ABC’ AND Col2 = ‘123’),支持多字段、含空格及省略号的值。

本文介绍一种健壮的正则表达式方案,结合 javascript 的 `string.prototype.replace()` 与回调函数,可将形如 `/* col1: abc, col2: 123 */` 的注释字符串精准解析并转换为标准 sql where 子句(如 `where col1 = ‘abc’ and col2 = ‘123’`),支持多字段、含空格及省略号的值。

在实际开发中,尤其在动态 SQL 构建或低代码查询配置场景下,常需将结构化注释(如文档化标记)自动转为可执行的 SQL 条件片段。本方案不依赖外部解析器,仅用原生正则与字符串处理即可完成语义提取与格式组装。

核心思路是:一次性匹配注释中的所有语法单元(起始标记 /*、字段键值对、分隔符 ,、结束标记 */),再通过 replace() 的回调函数按匹配类型分别生成对应 SQL 片段。

以下是完整可运行的实现:

function commentToWhereClause(data) {   return data.replace(     //*|,|s*([^:]+):s+(.*?)(?=,|s+*/)|s+*//g,     (match, key, value) => {       if (match === '/*') {         return 'WHERE ';       } else if (match.endsWith('*/')) {         return '';       } else if (match === ',') {         return ' AND ';       } else if (key && value !== undefined) {         // 对 value 进行基础 SQL 字符串转义(防止单引号破坏语法)         const escapedValue = value.replace(/'/g, "''");         return `${key.trim()} = '${escapedValue}'`;       }       return '';     }   ); }  // 示例调用 const input = '/* Col1: ABC, Col2: 123, ColN: Bla bla... */'; console.log(commentToWhereClause(input)); // 输出:WHERE Col1 = 'ABC' AND Col2 = '123' AND ColN = 'Bla bla...'

关键特性说明

  • 正则 //*|,|s*([^:]+):s+(.*?)(?=,|s+*/)|s+*//g 使用交替(|)精确捕获四类目标:
    • /* → 起始标记
    • , → 字段分隔符
    • s*([^:]+):s+(.*?)(?=,|s+*/) → 键([^:]+ 非冒号字符)与值(惰性匹配至下一个 , 或 */ 前)
    • s+*/ → 结束标记
  • 回调中通过 match 值判断上下文类型,避免歧义(例如单独匹配到 Col1: 不会误判为独立 Token
  • 值内单引号自动转义为 ”(符合 ANSI SQL 标准),提升安全性与兼容性

⚠️ 注意事项

  • 该方案不处理嵌套括号、引号包裹的复杂值或 SQL 注入防护;若输入来自不可信源,建议额外校验字段名白名单(如 /^[a-zA-Z_][a-zA-Z0-9_]*$/)并使用参数化查询替代拼接。
  • 值中换行符、制表符等空白字符会被保留;如需规范化空格(如将 “Bla bla…” → “Bla bla…”),可在 value 处理前添加 .replace(/s+/g, ‘ ‘).trim()。
  • 若字段值本身含逗号(如 /* Name: “Smith, John”, Age: 30 */),当前正则会错误切分——此时应改用更严格的语法(如 json 或带引号的键值对),而非纯正则解析。

总结而言,此正则+回调方案在保持简洁性的同时具备良好可读性与扩展性,适用于预定义格式的轻量级转换需求;对于更复杂的 DSL 场景,建议升级为专用词法分析器。

text=ZqhQzanResources