postgresql 如何更改postgres数据库的字符编码?

s2j5cfk0  于 2023-01-13  发布在  PostgreSQL
关注(0)|答案(6)|浏览(558)

我有一个使用默认字符集SQL_ASCII设置的数据库。我想将它切换到UNICODE。有简单的方法吗?

nkcskrwz

nkcskrwz1#

首先,丹尼尔的答案是正确的,安全的选择。
对于从SQL_ASCII更改为其他数据库的特定情况,您可以欺骗并简单地戳pg_database目录来重新分配数据库编码,这假设您已经以预期的编码存储了任何非ASCII字符(或者您根本没有使用任何非ASCII字符)。
然后您可以:

update pg_database set encoding = pg_char_to_encoding('UTF8') where datname = 'thedb'

这不会改变数据库的排序规则,只会改变编码字节转换为字符的方式(所以length('£123')将返回4而不是5)。如果数据库使用'C'排序规则,ASCII字符串的排序应该不会改变。不过,您可能需要重新构建包含非ASCII字符的索引。
注意清空者。转储和重新加载提供了一种方法来检查数据库内容实际上是在你期望的编码中,而这不是。如果结果是你确实在数据库中有一些错误编码的数据,那么拯救将是困难的。所以如果你可能的话,转储和重新初始化。

soat7uwm

soat7uwm2#

要更改数据库的编码:
1.转储数据库
1.删除数据库,
1.使用不同的编码创建新数据库
1.重新加载数据。
确保在此过程中正确设置了客户端编码。
来源:http://archives.postgresql.org/pgsql-novice/2006-03/msg00210.php

qnakjoqk

qnakjoqk3#

转储具有特定编码的数据库并尝试在具有不同编码的另一个数据库上还原该数据库可能会导致数据损坏。必须在将任何数据插入数据库之前设置数据编码。
检查this:* 复制任何其他数据库时,不能更改源数据库的编码和区域设置,因为这可能导致数据损坏。*
以及this:* 某些区域设置类别的值必须在创建数据库时固定。您可以对不同的数据库使用不同的设置,但一旦创建了数据库,就不能再更改该数据库的设置。* LC_COLLATE和LC_CTYPE就是这些类别。* 它们影响索引的排序顺序,因此必须保持固定。或文本列上的索引将损坏。 但是您可以使用排序规则来减轻这种限制,如第22. 2节所述。 这些类别的默认值是在运行initdb时确定的,并且在创建新数据库时使用这些值,除非在CREATE DATABASE命令中另有指定。*
我宁愿在您的debian操作系统上使用正确的本地编码从头开始正确地重建所有内容,如here所述:

su root

重新配置本地设置:

dpkg-reconfigure locales

选择您的区域设置(例如瑞士的法语:帧_通道. UTF8)
卸载并正确清理postgresql:

apt-get --purge remove postgresql\*
rm -r /etc/postgresql/
rm -r /etc/postgresql-common/
rm -r /var/lib/postgresql/
userdel -r postgres
groupdel postgres

重新安装postgresql:

aptitude install postgresql-9.1 postgresql-contrib-9.1 postgresql-doc-9.1

现在,任何新数据库都将自动创建为具有正确的编码、LC_TYPE(字符分类)和LC_COLLATE(字符串排序顺序)。

8fsztsew

8fsztsew4#

Daniel Kutik的答案是正确的,但它可以更安全,数据库重命名
所以,真正安全的方法是:
1.使用不同的编码和名称创建新数据库
1.转储数据库
1.将转储恢复到新数据库
1.测试您的应用程序是否可以在新DB中正常运行
1.将旧数据库重命名为有意义的名称
1.重命名新数据库
1.再次测试应用程序
1.删除旧数据库
在紧急情况下,只需重新命名数据库

dfddblmv

dfddblmv5#

# dump into file
pg_dump myDB > /tmp/myDB.sql

# create an empty db with the right encoding (on older versions the escaped single quotes are needed!)
psql -c 'CREATE DATABASE "tempDB" WITH OWNER = "myself" LC_COLLATE = '\''de_DE.utf8'\'' TEMPLATE template0;'

# import in the new DB
psql -d tempDB -1 -f /tmp/myDB.sql

# rename databases
psql -c 'ALTER DATABASE "myDB" RENAME TO "myDB_wrong_encoding";' 
psql -c 'ALTER DATABASE "tempDB" RENAME TO "myDB";'

# see the result
psql myDB -c "SHOW LC_COLLATE"
kknvjkwl

kknvjkwl6#

我在postgres 11中遇到了同样的问题,我确实使用以下步骤更改了数据库编码,
更新所有编码列表
1#SET客户端编码="UTF8";
2#UPDATE pg_database设置数据整理="en_US. UTF-8",数据类型="en_US. UTF-8",其中数据名称="postgres";
3#更新pg_数据库集编码= pg_char_to_encoding('UTF8 '),其中数据名='数据库名';
确保在template0和template1以及postgres数据库中应用updaet语句
postgres =#更新pg_database设置数据整理='en_US. UTF-8',数据类型='en_US. UTF-8'其中数据名称='postgres';更新1 postgres =#UPDATE pg_database设置数据整理='en_US. UTF-8',数据类型='en_US. UTF-8'其中数据名称='template0';更新1 postgres =#更新pg_database设置数据整理='en_US. UTF-8',数据类型='en_US. UTF-8'其中数据名称='template1';更新1
enter image description hereenter image description here

相关问题