如果我们有一个混合字符集和排序规则的数据库,是否会有问题?

问题描述 投票:0回答:3

我们目前正在将 MySQL 服务器中的 latin1 数据库迁移到 UTF8。

我们正在研究什么是最好的方法,希望不会造成任何停机。

我的问题是,我们是否会将 latin1 数据库中的表迁移到 UTF8,例如,我们有一个查询对这两个表执行操作(例如,联接)

由于不同的排序规则/字符集,我们是否有可能开始得到预期之外的结果?

我想迁移整个数据库会更安全,但会涉及停机时间。

谢谢你。

编辑:

我们正在查看我们的数据,我们发现 99% 的数据是 windows cp1252 编码的数据,这意味着将表从 latin1 转换为 utf8 是安全的,而不必担心损坏它。

所以在我看来,我们有三个选择:

  1. 停机并转换整个数据库
  2. 无需停机并转换每个表,但存在性能风险和生产中的一些错误(由于联接查询和不兼容的排序规则)
  3. 使用
    pt-online-schema-change
    (或类似的东西)
mysql database utf-8 database-migration iso-8859-1
3个回答
1
投票

是和不是。

中的单独的可以有不同的字符集和排序规则。不能分开

是独立的,直到您

JOIN
。此时,如果您要加入的列没有相同的字符集 排序规则,性能就会受到影响。

插入/获取数据时,您的客户端有一个字符集。如果是 utf8mb4,那么 MySQL 会很乐意在该字符与表列中的字符之间进行动态转换。当然,有些字符是不能转换的;例如,latin1 的不同字符比 utf8mb4 少得多。

您提到了移民。您将需要转储并重新加载(较慢)或执行大量更改(更快,但对于大型表来说不是“快”)或执行其他操作。请说明您可以接受的参数。速度、简单性等之间存在权衡。

很多人在更改字符集时都会遇到麻烦。大约有 7 种不同的 ALTER 可供人们使用。如果你执行错误,就会造成一团糟,很难解决。

如果您在更改数据库时尝试保持数据库“活动”,则可能会遇到上面提到的 JOIN 性能问题。

如果您已经设置了复制,则可能有一些利用“故障转移”的技术。

请随身携带以下问答,以防遇到乱码: UTF-8 字符出现问题;我看到的不是我存储的

您使用的 MySQL 版本是什么?如果是 8.0,那么默认字符集 (utf8mb4) 及其默认排序规则可能是最好的。


0
投票

您不应该得到意想不到的结果。

如果字符集完全不兼容,那么根本无法进行字符串比较。你会得到一个错误。

如果字符集兼容,但排序规则不同,您应该得到相同的结果,但不会通过索引查找进行优化。您可以使用 EXPLAIN 来验证这一点,您将在其中看到连接的表 使用表扫描,并且在额外列中可能有“使用连接缓冲区”。

为了解决停机问题,我使用了pt-online-schema-change来执行

ALTER TABLE <name> CONVERT TO CHARACTER SET utf8mb4 COLLATE utf8mb4_0900_ai_ci;
(假设您使用的是MySQL 8.0,这对于字符集/排序规则来说是一个不错的选择),同时继续读写原始表。我们每周多次执行此操作(或其他 ALTER TABLE 更改),甚至在高峰时段也是如此。


0
投票

考虑使用 pt-online-schema-change 似乎是一个安全的选择。我唯一不喜欢的是它会更改 FK 的名称,将 _ 前缀为“FK_NAME”。 2 个问题: #1 有办法解决这个问题吗?

#2 测试列是否正确转换的简单方法是什么?

谢谢。

© www.soinside.com 2019 - 2024. All rights reserved.