需先确认MySQL版本≥5.5.3且InnoDB启用innodb_large_prefix=ON、innodb_file_format=Barracuda,再用ALTER TABLE ... CONVERT TO CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci逐表转换,并修正连接层字符集与SQL文件中的排序规则。

确认 MySQL 版本和 InnoDB 配置是否支持 utf8mb4
低于 MySQL 5.5.3 的版本根本不认识 utf8mb4,执行 ALTER TABLE ... CONVERT TO CHARACTER SET utf8mb4 会直接报 Unknown character set: utf8mb4。即使版本达标(推荐 ≥ 5.7.7),若未启用 innodb_large_prefix 或 innodb_file_format 不是 Barracuda,后续转换可能在索引上失败,报错 Specified key was too long。
先执行:
SELECT VERSION();
再查配置:
SHOW VARIABLES LIKE 'innodb_large_prefix';<br>SHOW VARIABLES LIKE 'innodb_file_format';
- 若
innodb_large_prefix是OFF,需在my.cnf的[mysqld]段加innodb_large_prefix = ON并重启 MySQL - 若
innodb_file_format不是Barracuda,同样需在配置中加innodb_file_format = Barracuda并重启
只改表默认字符集是无效的,必须用 CONVERT TO
仅执行 ALTER TABLE tbl_name DEFAULT CHARSET=utf8mb4 只改了表级默认值,字段、索引、生成列、注释里的字符集全没动,导入/插入时仍可能乱码或截断。真正安全的做法是用 CONVERT TO —— 它会递归更新所有列、索引、存储过程依赖项。
立即学习“PHP免费学习笔记(深入)”;
生成语句前,先定位要转的表:
SELECT table_schema, table_name FROM information_schema.tables<br>WHERE table_schema = 'your_db'<br> AND table_collation LIKE 'utf8%';
然后生成批量语句(注意替换 your_db):
SELECT CONCAT('ALTER TABLE `', table_schema, '`.`', table_name,<br> '` CONVERT TO CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci;')<br>FROM information_schema.tables<br>WHERE table_schema = 'your_db'<br> AND table_collation LIKE 'utf8%';
- 逐条执行生成的
ALTER TABLE,别拼成一条大语句 —— 单表失败不影响其余 - 执行前务必运行
SET FOREIGN_KEY_CHECKS = 0;,避免外键中断 - 每条执行后检查是否报错,尤其留意
Row size too large(说明有 TEXT + 长索引组合,需先缩索引)
导入 SQL 文件时 utf8mb4_0900_ai_ci 报错怎么修
如果导出源是 MySQL 8.0+,SQL 文件里大概率含 utf8mb4_0900_ai_ci 这类排序规则,而目标 MySQL 是 5.7 或更早版本,就会报 Unknown collation: 'utf8mb4_0900_ai_ci'。这不是文件损坏,是纯版本不兼容。
别信“SET NAMES utf8mb4”能救——它对建表语句里的硬编码 COLLATE 完全无效。唯一可靠方式是改文件:
- MySQL 5.7:全局替换
utf8mb4_0900_ai_ci→utf8mb4_unicode_ci - MySQL 5.6 或更早:必须同步把
CHARACTER SET utf8mb4改成CHARACTER SET utf8,再把COLLATE换成utf8_general_ci - 用
grep -n "utf8mb4_0900" your.sql先定位范围,避免误伤注释或字符串内容
转换后中文仍乱码?重点查连接层和旧数据编码
表和字段都已是 utf8mb4,但 phpMyAdmin 页面显示问号或方块,问题几乎一定出在连接层或历史数据本身。执行:
SELECT @@character_set_client, @@character_set_connection, @@character_set_results;
三项必须全是 utf8mb4。如果不是,说明 phpMyAdmin 连接没生效,要改 config.inc.php:
$cfg['Servers'][$i]['charset'] = 'utf8mb4';$cfg['Servers'][$i]['connection_charset'] = 'utf8mb4';$cfg['DefaultCharset'] = 'utf8mb4';
改完必须重启 Web 服务(Apache/Nginx)和 MySQL 服务。
如果是旧表转换后乱码,别直接 CONVERT TO。先用 SELECT HEX(column_name) FROM tbl LIMIT 1; 看原始字节:若返回 E4B8ADE69687(即“中文”的 UTF-8 编码),说明数据本就是 UTF-8,只是被当 latin1 解释了——此时该用 MODIFY 声明修正,而非 CONVERT 二次转码。



















