我想使用 ICU 系统不敏感的排序规则,以避免 postgres11-on-mac 与 postgres11-on-Ubuntu 之间的排序差异。我的第一个测试是转储现有的
Collate=en_US.UTF-8
并将它们 pg_restore 到使用 Collate=en-US-x-icu
创建的数据库中
创建数据库文档有这样的说法:
创建具有不同语言环境的数据库音乐:
创建数据库音乐 LC_COLLATE 'sv_SE.utf8' LC_CTYPE 'sv_SE.utf8' 模板模板0;
select collname, collprovider from pg_collation where collname like 'en_US%';
collname | collprovider
------------------------+--------------
en_US.UTF-8 | c
en_US | c
en_US.ISO8859-15 | c
en_US.ISO8859-1 | c
en_US | c
en_US | c
en-US-x-icu | i 👈
en-US-u-va-posix-x-icu | i 👈
(8 rows)
但是使用任一 icu 语言环境创建数据库时都没有运气。
CREATE DATABASE test LC_COLLATE = 'en-US-x-icu' TEMPLATE template0;
ksysdb=# CREATE DATABASE test LC_COLLATE = 'en-US-x-icu' TEMPLATE template0;
ERROR: invalid locale name: "en-US-x-icu"
LC_COLLATE
用于其他语言环境:LC_COLLATE
子句似乎确实附带了一些附加条件,例如观察您的编码并指定适当的模板。但它似乎给出了非 ICU 语言环境的错误提示。
这有效,例如:
CREATE DATABASE test LC_COLLATE = 'en_US' TEMPLATE template0;
这个给出了一条有用的用户消息:
ksysdb=# CREATE DATABASE test LC_COLLATE = 'en_US.ISO8859-15' TEMPLATE template0;
ERROR: encoding "UTF8" does not match locale "en_US.ISO8859-15"
DETAIL: The chosen LC_COLLATE setting requires encoding "LATIN9".
注意:一个相关的问题,Linux 上的 PostgreSQL 10 - LC_COLLATE locale en_US.utf-8 not valid,似乎并不那么相关,因为答案谈到了生成操作系统级别的语言环境来解决问题。据我了解,ICU 区域设置明确旨在与底层操作系统分离。
这可以从 PostgreSQL v15 开始实现:
CREATE DATABASE test
LOCALE_PROVIDER icu
ICU_LOCALE "en-US"
LOCALE "en_US.utf8"
TEMPLATE template0;
您仍然需要提供 libc 语言环境,但 ICU 库用于排序。