我正在尝试将我的一个数据库表从 utf8_general_ci 切换到 utf8mb4。
ALTER TABLE d4b80le1jha CONVERT TO CHARACTER SET utf8mb4 COLLATE utf8mb4_bin
这会引发以下错误:
1071 - Specified key was too long; max key length is 1000 bytes
我已经阅读了很多关于此错误消息的答案,但似乎无法解决我的问题。他们中的大多数人都在谈论定义新索引,而不是如何处理现有索引。
我还尝试运行以下命令,如 recommended here , 这没有区别:
SET @@global.innodb_large_prefix = 1;
一个复杂的因素可能是我使用 varchar 散列作为主键。这是我无法控制的遗留功能。我没有为我的索引设置明确的大小 - 我想知道这是否是我应该查看的内容。
表:
Field Type Null Key Default
-------------------------------------------------------
id varchar(11) NO PRI NULL
link varchar(255) NO NULL
title varchar(255) NO NULL
description varchar(255) YES NULL
pubdate datetime NO NULL
img_url varchar(255) YES NULL
team_id varchar(11) NO MUL NULL
source_id varchar(11) NO NULL
hits int(11) YES NULL
索引:
Keyname Type Unique Packed Column Cardinality Collation Null
--------------------------------------------------------------------------------
PRIMARY BTREE Yes No id 13407 A No
Unique combo BTREE Yes No team_id A No
source_id A No
link 13407 A No
最佳答案
这可能是你的 Unique combo
索引引起麻烦,我的意思是你在 (team_id, source_id, link)
上的索引.该索引的字符总长度为 277,因此它的最大字节总长度是 1108 的四倍。
对此你能做什么?
减少
link
的字符长度列到 228,因此索引的最大字符长度为 250。只要您的值仍然适合,这可能是最简单的。重新创建索引并提及
link(228)
而不仅仅是link
仅索引link
的前导字符.我不知道这是不是个好主意;索引的目的是定义一个唯一约束。如果您不索引link
的整个值你并没有完全那样做。而不是将表中的所有字符列都转换为
utfmb4
字符编码,只需转换title
和description
列。这可能对你有用。为什么?你的_id
哈希可能使用有限的字符集,根本不需要 unicode。你的link
列值可能是 URLS,也可以使用有限的 (latin1) 字符集。所以,只是title
和description
可能需要用希伯来语或中文书写或包含表情符号或其他内容。这可能是您的最佳解决方案。
(注意字符编码实际上是逐列指定的。转换整个表格的能力是为了方便而提供的。)
所以你可以这样做
ALTER TABLE d4b80le1jha
MODIFY title VARCHAR(255)
CHARACTER SET utf8mb4
COLLATE utf8mb4_bin;
ALTER TABLE d4b80le1jha
MODIFY description VARCHAR(255)
CHARACTER SET utf8mb4
COLLATE utf8mb4_bin;
最后,因为这两列是人类可读的文本,您可能想要使用 utf8mb4_general_ci
用于整理这些列而不是 utf8mb4_bin
.搜索和订购可能会更好地满足用户的期望。
关于MySQL - 错误 1071、 "specified key was too long..."阻止更改字符集/归类,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/49095673/