侧边栏壁纸
博主头像
落叶人生博主等级

走进秋风,寻找秋天的落叶

  • 累计撰写 130562 篇文章
  • 累计创建 28 个标签
  • 累计收到 9 条评论
标签搜索

目 录CONTENT

文章目录

SpringBoot+Mysql 无法保存emoj表情?

2022-07-04 星期一 / 0 评论 / 0 点赞 / 35 阅读 / 14170 字

尤记得很久以前,想存 emoj 表情到 mysql 中,需要额外的将 emoj 表情转码之后保存,每次读取时,再解码还原成一下;每次这种 sb 的操作,真心感觉心塞,那么有没有办法直接存呢?mysql

尤记得很久以前,想存 emoj 表情到 mysql 中,需要额外的将 emoj 表情转码之后保存,每次读取时,再解码还原成一下;每次这种 sb 的操作,真心感觉心塞,那么有没有办法直接存呢?

mysql 本身可以通过选择编码集(如 utfbmb4)来支持 emoj 表情,然而今天遇到了一个相当鬼畜的问题,表中可以直接写入 emoj 表情,但是通过 spring boot 代码塞入的 emoj 时,却抛出异常:

Caused by: java.sql.SQLException: Incorrect string value: '/xF0/x9F/x98/x9D/xE6/xB1...' for column 'nick' at row 1	at com.mysql.jdbc.SQLError.createSQLException(SQLError.java:1084) ~[mysql-connector-java-5.1.30.jar:na]	at com.mysql.jdbc.MysqlIO.checkErrorPacket(MysqlIO.java:4232) ~[mysql-connector-java-5.1.30.jar:na]	at com.mysql.jdbc.MysqlIO.checkErrorPacket(MysqlIO.java:4164) ~[mysql-connector-java-5.1.30.jar:na]	at com.mysql.jdbc.MysqlIO.sendCommand(MysqlIO.java:2615) ~[mysql-connector-java-5.1.30.jar:na]	at com.mysql.jdbc.MysqlIO.sqlQueryDirect(MysqlIO.java:2776) ~[mysql-connector-java-5.1.30.jar:na]	at com.mysql.jdbc.ConnectionImpl.execSQL(ConnectionImpl.java:2838) ~[mysql-connector-java-5.1.30.jar:na]	at com.mysql.jdbc.PreparedStatement.executeInternal(PreparedStatement.java:2082) ~[mysql-connector-java-5.1.30.jar:na]

接下来演示一下正确的使用姿势,以及导致上面问题的错误 case,避免大家重复采坑

I. Emoj 表情支持之旅

接下来我们的目标是可以直接向 mysql 中读取或写入 emoj 表情

1. 表字符集

首先针对 mysql 表,需要指定字符集为utfbmb4

CREATE TABLE `Subscribe` (  `id` int(11) unsigned NOT NULL AUTO_INCREMENT,  `email` varchar(140) NOT NULL DEFAULT '',  `nick` varchar(30) NOT NULL DEFAULT '昵称',  `status` tinyint(4) NOT NULL DEFAULT '0' COMMENT '0 订阅未激活, 1 订阅已激活 , 2 取消订阅',  `created` int(13) NOT NULL DEFAULT '0' COMMENT '创建时间',  `updated` int(13) NOT NULL DEFAULT '0' COMMENT '更新时间'  PRIMARY KEY (`id`),  UNIQUE KEY `email` (`email`)) ENGINE=InnoDB AUTO_INCREMENT=1 DEFAULT CHARSET=utf8mb4;

上面直接设置表的字符集为utf8mb4,如果某个表已经存在,但是字符集不是 utf8mb4,这种 case 下我们也可以单独的设置某个列的编码如下

ALTER TABLE `Subscribe` CHANGE `nick` `nick` VARCHAR(30)  CHARACTER SET utf8mb4 NOT NULL  DEFAULT '';

如上设置之后,我们可以直接在这个表中添加 emoj

2. SpringBoot 支持

接下来进入正题,springboot 项目,如何支持 emoj 的插入;首先看一下项目依赖

<parent>    <groupId>org.springframework.boot</groupId>    <artifactId>spring-boot-starter-parent</artifactId>    <version>2.2.1.RELEASE</version>    <relativePath/> <!-- lookup parent from repository --></parent><properties>    <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>    <project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>    <java.version>1.8</java.version></properties><dependencies>    <dependency>        <groupId>org.springframework.boot</groupId>        <artifactId>spring-boot-starter-jdbc</artifactId>    </dependency>    <dependency>        <groupId>mysql</groupId>        <artifactId>mysql-connector-java</artifactId>    </dependency></dependencies><build>    <pluginManagement>        <plugins>            <plugin>                <groupId>org.springframework.boot</groupId>                <artifactId>spring-boot-maven-plugin</artifactId>            </plugin>        </plugins>    </pluginManagement></build><repositories>    <repository>        <id>spring-snapshots</id>        <name>Spring Snapshots</name>        <url>https://repo.spring.io/libs-snapshot-local</url>        <snapshots>            <enabled>true</enabled>        </snapshots>    </repository>    <repository>        <id>spring-milestones</id>        <name>Spring Milestones</name>        <url>https://repo.spring.io/libs-milestone-local</url>        <snapshots>            <enabled>false</enabled>        </snapshots>    </repository>    <repository>        <id>spring-releases</id>        <name>Spring Releases</name>        <url>https://repo.spring.io/libs-release-local</url>        <snapshots>            <enabled>false</enabled>        </snapshots>    </repository></repositories>

我们使用的是2.2.1.RELEASE版本,请确保引入了依赖spring-boot-starter-jdbcmysql-connector-java

然后配置 db 相关属性, application.properties

## DataSourcespring.datasource.url=jdbc:mysql://127.0.0.1:3306/story?useUnicode=true&characterEncoding=UTF-8&useSSL=falsespring.datasource.username=rootspring.datasource.password=

然后就可以愉快的进行测试了

@Slf4j@SpringBootApplicationpublic class Application {    public Application(JdbcTemplate jdbcTemplate) {        log.warn("application start!!!");        // 插入emoj 表情        jdbcTemplate.update("insert into Subscribe (`email`, `nick`) values (?, ?)",                UUID.randomUUID().toString() + "@t.com", "

广告 广告

评论区