【问题标题】:Converting in-place a Postgresql database from SQL_ASCII to UTF8将 Postgresql 数据库从 SQL_ASCII 就地转换为 UTF8
【发布时间】:2011-03-10 20:04:34
【问题描述】:

(不是4079956的重复)

我有一个SQL_ASCII 数据库,LC_CTYPE=LC_COLLATION="C",其中主要包含 ASCII 数据以及来自某些代码页的一些非 ASCII 字符,例如 LATIN1

我想就地(没有pg_dump/pg-restore)将LATIN1代码页中的所有非ASCII代码点转码为UTF-8,然后将数据库编码更改为UTF-8,例如:

-- change encoding first, transcode data after
UPDATE pg_database SET encoding=pg_char_to_encoding('UTF8')
  WHERE datname='sqlasciidb';
UPDATE tbl SET str=convert_from(str::bytea, 'LATIN1')
  WHERE str::bytea<>convert_from(str::bytea, 'LATIN1')::bytea;

-- transcode data first, change encoding after
CREATE DOMAIN my_varlena AS bytea;
CREATE CAST (my_varlena AS text) WITHOUT FUNCTION;
UPDATE tbl SET str=convert(str::bytea, 'LATIN1','UTF8')::my_varlena::text
  WHERE str::bytea<>convert(str::bytea, 'LATIN1', 'UTF8');
DROP DOMAIN my_varlena CASCADE;
UPDATE pg_database SET encoding=pg_char_to_encoding('UTF8')
  WHERE datname='sqlasciidb';

上述方法有什么问题(如果有的话)?

我可以看到一些问题:

  • pg_database 更新后,所有与数据库的连接都应关闭并重新打开,以便后端考虑新的编码
  • 应重建基于更改列的所有索引

还有什么?

【问题讨论】:

    标签: postgresql unicode internationalization


    【解决方案1】:

    看起来你已经掌握了它的主要要点。我假设您已经使用测试数据库尝试过这个?在向某人推荐它时,我确实对其进行了快速测试,它似乎对我来说还可以,尽管这远非彻底的测试。

    我的直觉是先转码,然后再更改编码,因为虽然数据库仍在 SQL_ASCII 中,但您不必处理来自 postgresql 尝试解释尚未转码或不正确转码数据的错误,并且可以相对不受惩罚地查看数据。 OTOH 首先更改编码保证只有随后连接的后端才会以 UTF8 写入数据...

    还要检查可能需要转码的函数体、视图定义、约束定义等? (你希望不是,但是......)

    【讨论】:

    • 原来并不真正支持通过域进行投射。无论如何都要颁奖。 :)
    猜你喜欢
    • 1970-01-01
    • 2012-02-07
    • 2022-11-12
    • 2013-06-06
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2010-09-11
    • 1970-01-01
    相关资源
    最近更新 更多