记一个Emoji造成的数据库插入异常

版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/Mr_Megamind/article/details/84661620

前提

这次仍然是在我的日报系统上遇到的异常崩溃,关于日报系统的简要说明请参阅《记一次重构》.


异常信息

Incorrect string value: ‘\xF0\x9F\x8C\xB8’ for column ‘Content’ at row 49
就是说在第49行的Content这一列插入了不正确的字符串值\xF0\x9F\x8C\xB8


问题所在

这个问题倒是很好查,看来很多人都遇到过。简而言之,问题在于向数据库中插入了emoji表情。

然而问题并不是下面这种图片格式的Emoji造成的:
Emoji
因为我在解析HTML时会过滤掉<img>标签。

又经过一番搜索和验证,我发现了如下图的这种东西:
文本Emoji
表面上看,只是和上面的Emoji风格不同,实际上另有玄机!!!


真相——文本格式的Emoji

我从网站上复制了这些Emoji的一部分放到文本文档里,想看看这些东西是不是图片(图片是不能复制进文本文档的),结果看到了惊掉下巴的东西:
文本格式的Emoji
没错,这些是上述那些看似彩色图片的Emoji的真身,文本格式。


原因

那么,既然这种东西也算是一个一个的字符,为什么会出现数据库插入异常呢?
原因在于:

普通的字符串或者表情都是占位3个字节,所以utf8足够用了,但是移动端的表情符号占位是4个字节,普通的utf8就不够用了,为了应对无线互联网的机遇和挑战、避免 emoji 表情符号带来的问题、涉及无线相关的 MySQL 数据库建议都提前采用utf8mb4字符集,这必须要作为移动互联网行业的一个技术选型的要点。[1]

总之,这种字符存在于扩展之后的每个字符占4个字节的utf8mb4字符集中,转换为每个字符为3个字节的utf8就出错了。

关于utf8mb4,请移步《浅谈MySQL中utf8和utf8mb4的区别》


解决方案

根据查到的解决方案,亲测有效但是描述上有错误,我再赘述一下。

第一步——修改MySQL配置

①打开mysql的配置文件,windows下的为my.ini(linux下的为my.cnf);
②找到[client],在下面添加一行
default-character-set = utf8mb4
③找到[mysqld],在下面添加两行
character-set-server = utf8mb4
collation-server = utf8mb4_unicode_ci
④找到[mysql],在下面添加一行
default-character-set = utf8mb4
特别要注意的是,小心不要把这些写在以#开头的注释里。

第二步——修改字段的字符集

在数据库中,修改相应字段(我这里是text类型的Content字段)的字符集为utf8mb4,排序规则为utf8mb4_general_ci
修改字符集

第三步——修改代码中数据库连接字符串

去掉数据库连接字符串中的?characterEncoding=utf-8

因为怕出现汉字乱码的问题,我就没有做这一步试了一下,亲测是可以的。因此这一步不像网上说的必须要做,视情况而定。


后记

后来查明,是一位同学的日报中出现了这个:
导致崩溃的元凶
我问他的时候,他自己都没有意识到发了这个东西过来。可能是误触了输入法提供的这个吧。


  1. 摘自《【Mysql】存储emoji表情报错(Incorrect string value: ‘\xF0\x9F\x98\x82\xF0\x9F…’)的解决方案》 ↩︎

猜你喜欢

转载自blog.csdn.net/Mr_Megamind/article/details/84661620
今日推荐