iphone的表情保存到数据库失败-- utf8 ——utf8mb4

来源:互联网 发布:外国语大学网络教育 编辑:程序博客网 时间:2024/05/20 03:05

iphone的表情保存到数据库失败,抛出异常:
org.hibernate.exception.GenericJDBCException: Incorrect string value: ‘\xF0\x9F\x98\x9B\xF0\x9F…’

使用的数据库是:mysqld 5.6.25,而从5.5.3开始支持utf8mb4
原因是UTF-8编码有可能是两个、三个、四个字节。Emoji表情或者某些特殊字符是4个字节,而Mysql的utf8编码最多3个字节,所以数据插不进去。

参考http://bbs.csdn.net/topics/390193026

另:关于utf8 和utf8mb4的区别:
http://dev.mysql.com/doc/refman/5.5/en/charset-unicode-utf8mb4.html
10.1.10.6 The utf8mb4 Character Set (4-Byte UTF-8 Unicode Encoding)
The character set named utf8 uses a maximum of three bytes per character and contains only BMP characters. As of MySQL 5.5.3, the utf8mb4 character set uses a maximum of four bytes per character supports supplemental characters:

For a BMP character, utf8 and utf8mb4 have identical storage characteristics: same code values, same encoding, same length.

For a supplementary character, utf8 cannot store the character at all, while utf8mb4 requires four bytes to store it. Since utf8 cannot store the character at all, you do not have any supplementary characters in utf8 columns and you need not worry about converting characters or losing data when upgrading utf8 data from older versions of MySQL.

utf8mb4 is a superset of utf8, so for an operation such as the following concatenation, the result has character set utf8mb4 and the collation of utf8mb4_col:

SELECT CONCAT(utf8_col, utf8mb4_col);
Similarly, the following comparison in the WHERE clause works according to the collation of utf8mb4_col:

SELECT * FROM utf8_tbl, utf8mb4_tbl
WHERE utf8_tbl.utf8_col = utf8mb4_tbl.utf8mb4_col;
Tip: To save space with UTF-8, use VARCHAR instead of CHAR. Otherwise, MySQL must reserve three (or four) bytes for each character in a CHAR CHARACTER SET utf8 (or utf8mb4) column because that is the maximum possible length. For example, MySQL must reserve 40 bytes for a CHAR(10) CHARACTER SET utf8mb4 column.

以往mysql里的utf8一个字符最多3字节,只支持BMP这部分的unicode编码区,
BMP是从哪到哪,到http://en.wikipedia.org/wiki/Mapping_of_Unicode_characters这里看,基本就是0000~FFFF这一区。
而utf8mb4则扩展到一个字符最多能有4字节,所以能支持更多的字符集。
SQL code
1
utf8mb4 is a superset of utf8

utf8mb4兼容utf8,且比utf8能表示更多的字符。
至于什么时候用,看你的做什么项目了,到
http://witmax.cn/unicode-list.html
看unicode编码区
从1 ~ 126就属于传统utf8区,当然utf8mb4也兼容这个区,126行以下就是utf8mb4扩充区,什么时候你需要存储那些字符,你才用utf8mb4,否则只是浪费空间。

==========================================================

操作步骤:1
修改相应的列的属性
alter TABLE tbtask MODIFY requirement TEXT CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci ;

操作步骤:2
修改表的属性
ALTER TABLE tbtask DEFAULT CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci

操作步骤:3
从/etc/my.cnf 中修改或增加服务端的属性
[root@iZ25v1b90qhZ home]# cd /etc/
[root@iZ25v1b90qhZ etc]# vi my.cnf

[mysqld]
——-》
[mysqld]
character-set-server=utf8mb4
[mysql]
default-character-set=utf8mb4

操作步骤:4
然后重启下mysql
[root@iZ25v1b90qhZ etc]# service mysqld restart
Shutting down MySQL…. [ OK ]
Starting MySQL. [ OK ]

下面是修改前的日志:
2015-07-31 18:47:00.275 [http-8080-2] INFO com.hcyg.media.core.controller.TaskController.publishTask - 发布任务接口,接收到的参数:{“token”:”cf1e632817324717881952dee8918d74”,”task”:{“type”:2,”criterion”:”sy\n\n”,”cost”:2334,”author”:{“headimgUrl”:”http://dn-hcyg2014.qbox.me/814adb3c5c3a4fdd8344602bc2bc8dd5“,”userId”:”8a2bb8164ecec7a7014ececa0550000a”,”nickName”:”张平”},”deadline”:”1442851199000”,”location”:”吉林省 白城市”,”requirement”:””,”title”:””},”userId”:”8a2bb8164ecec7a7014ececa0550000a”}
2015-07-31 18:47:00.297 [http-8080-2] ERROR com.hcyg.media.core.service.TaskService.publishTask -
org.springframework.orm.jpa.JpaSystemException: org.hibernate.exception.GenericJDBCException: Incorrect string value: ‘\xF0\x9F\x98\x9B\xF0\x9F…’ for column ‘title’ at row 1; nested exception is javax.persistence.PersistenceException: org.hibernate.exception.GenericJDBCException: Incorrect string value: ‘\xF0\x9F\x98\x9B\xF0\x9F…’ for column ‘title’ at row 1
at org.springframework.orm.jpa.EntityManagerFactoryUtils.convertJpaAccessExceptionIfPossible(EntityManagerFactoryUtils.java:318) ~[spring-orm-3.2.0.RELEASE.jar:3.2.0.RELEASE]
at org.springframework.orm.jpa.DefaultJpaDialect.translateExceptionIfPossible(DefaultJpaDialect.java:120) ~[spring-orm-3.2.0.RELEASE.jar:3.2.0.RELEASE]
at org.springframework.orm.jpa.JpaTransactionManager.doCommit(JpaTransactionManager.java:516) ~[spring-orm-3.2.0.RELEASE.jar:3.2.0.RELEASE]
at org.springframework.transaction.support.AbstractPlatformTransactionManager.processCommit(AbstractPlatformTransactionManager.java:754) ~[spring-tx-3.2.0.RELEASE.jar:3.2.0.RELEASE]
at org.springframework.transaction.support.AbstractPlatformTransactionManager.commit(AbstractPlatformTransactionManager.java:723) ~[spring-tx-3.2.0.RELEASE.jar:3.2.0.RELEASE]
at org.springframework.transaction.interceptor.TransactionAspectSupport.commitTransactionAfterReturning(TransactionAspectSupport.java:392) ~[spring-tx-3.2.0.RELEASE.jar:3.2.0.RELEASE]
at org.springframework.transaction.interceptor.TransactionInterceptor.invoke(TransactionInterceptor.java:120) ~[spring-tx-3.2.0.RELEASE.jar:3.2.0.RELEASE]
at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:172) ~[spring-aop-3.2.0.RELEASE.jar:3.2.0.RELEASE]
at org.springframework.aop.framework.CglibAopProxy$DynamicAdvisedInterceptor.intercept(CglibAopProxy.java:631) ~[spring-aop-3.2.0.RELEASE.jar:3.2.0.RELEASE]

。。。。。
2015-07-31 18:47:00.305 [http-8080-2] INFO com.hcyg.media.core.controller.TaskController.publishTask - 发布任务接口,返回结果:{“result”:”1”,”errorMessage”:”请求失败”}

这里是修改后的日志:

2015-07-31 18:48:06.986 [http-8080-2] INFO com.hcyg.media.core.controller.TaskController.publishTask - 发布任务接口,接收到的参数:{“token”:”cf1e632817324717881952dee8918d74”,”task”:{“type”:2,”criterion”:”sy\n\n”,”cost”:2334,”author”:{“headimgUrl”:”http://dn-hcyg2014.qbox.me/814adb3c5c3a4fdd8344602bc2bc8dd5“,”userId”:”8a2bb8164ecec7a7014ececa0550000a”,”nickName”:”张平”},”deadline”:”1442851199000”,”location”:”吉林省 白城市”,”requirement”:””,”title”:””},”userId”:”8a2bb8164ecec7a7014ececa0550000a”}
2015-07-31 18:48:06.996 [http-8080-2] INFO com.hcyg.media.core.service.TaskService.publishTask - 任务发布成功,taskId为8a2bb8164ee2f949014ee3b9e24d03c2。
2015-07-31 18:48:07.003 [http-8080-2] INFO com.hcyg.media.core.controller.TaskController.publishTask - 发布任务接口,返回结果:{“taskId”:”8a2bb8164ee2f949014ee3b9e24d03c2”,”result”:”0”,”errorMessage”:”请求成功”}

0 0