You need to enable JavaScript to run this app.
最新活动
大模型
产品
解决方案
定价
生态与合作
支持与服务
开发者
了解我们

无需添加引号使PostgreSQL标识符区分大小写:MySQL迁移至PostgreSQL的SQL查询适配求助

解决PostgreSQL中混合大小写标识符查询的非手动方案

我之前迁移MySQL到PostgreSQL时也踩过这个大小写的坑,完全手动加引号确实太折磨人了,给你几个相对高效的方案:

方案1:批量脚本自动给查询标识符加引号

不用手动逐个修改查询,可以写个简单的脚本自动识别SQL里的表名、列名,给它们加上双引号。比如用Python的sqlparse库来解析SQL语句,遍历所有标识符节点,自动包裹引号。

举个简单的示例代码:

import sqlparse
from sqlparse.tokens import Token

def quote_identifiers(sql):
    parsed = sqlparse.parse(sql)[0]
    for token in parsed.flatten():
        if token.ttype == Token.Name and not token.value.startswith('"'):
            token.value = f'"{token.value}"'
    return str(parsed)

# 测试示例
old_sql = "SELECT Table.Column FROM Table WHERE Table.Id = 1"
new_sql = quote_identifiers(old_sql)
print(new_sql)  # 输出: SELECT "Table"."Column" FROM "Table" WHERE "Table"."Id" = 1

这个脚本能处理大部分常规查询,复杂的嵌套查询或特殊别名可能需要微调,但比手动修改效率高太多。你可以把所有旧查询批量跑一遍这个脚本,直接生成适配PostgreSQL的版本。

方案2:创建小写视图映射大写表

如果不想修改任何查询语句,可以在PostgreSQL里给每个带混合大小写的表创建一个小写的视图,把查询里的小写标识符映射到真实的大写表/列。

比如真实表是"Table",列是"Column",你可以创建视图:

CREATE VIEW table AS
SELECT "Column" AS column, "Id" AS id
FROM "Table";

这样旧查询SELECT table.column FROM table WHERE table.id = 1就能正常执行了。

如果表和列数量很多,完全可以批量生成创建视图的SQL,比如从information_schema里查询生成:

SELECT 'CREATE VIEW ' || lower(table_name) || ' AS SELECT ' ||
       string_agg('"' || column_name || '" AS ' || lower(column_name), ', ') ||
       ' FROM "' || table_name || '";'
FROM information_schema.columns
WHERE table_schema = 'public'  -- 替换成你的实际schema
GROUP BY table_name;

执行这个查询会生成所有表的视图创建语句,直接运行就能批量搞定。这个方案的好处是查询完全不用改,但要注意后续表结构变更时,视图也要同步更新。

方案3:检查pgloader的迁移配置(若未完成迁移)

如果你还在使用pgloader迁移数据,可以看看它的参数是否能帮你提前规避这个问题。pgloader有--quote-identifiers参数,迁移时会自动给表和列名加上双引号,不过你提到已经无法转换表列名为小写,应该已经完成了这一步,但如果迁移还没结束,可以确认下这个配置是否正确。

需要注意的是,PostgreSQL的标识符大小写规则是硬编码的:未加引号的标识符会被自动转换为小写,加引号的则保留原大小写。所以没有官方模块或配置能让PostgreSQL默认保留未加引号标识符的大小写,上面的方案都是绕开这个规则的实用办法。

内容的提问来源于stack exchange,提问作者Janne Annala

火山引擎 最新活动