使用 JDBC 连接器 5.1 从 Java 读取/写入 MySQL 中的 UTF-8 数据时出现问题

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/730359/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-11 18:47:53  来源:igfitidea点击:

Problems reading/writing UTF-8 data in MySQL from Java using JDBC connector 5.1

javamysqljdbcutf-8

提问by

I have a scenario with two MySQL databases (in UTF-8), a Java code (a Timer Service) that synchronize both databases (reading form first of them and writing/updating to second) and a Web application that lets modify data loaded in the second database.

我有一个包含两个 MySQL 数据库(UTF-8 格式)的场景,一个同步两个数据库的 Java 代码(一个定时器服务)(首先读取它们的表单,然后写入/更新到第二个)和一个允许修改加载的数据的 Web 应用程序第二个数据库。

All database access is made using IBATIS (but I detect that I have the same problem using JDBC, PreparedStatements and ResultSets)

所有数据库访问都是使用 IBATIS 进行的(但我检测到我使用 JDBC、PreparedStatements 和ResultSets有同样的问题)

When my java code reads data from first database, I obtain characters like '?3'when really it must be 'ó'. This data is wroten without modifications to the second database.

当我的 Java 代码从第一个数据库读取数据时,我获得的字符'?3'实际上必须是'ó'. 该数据是在不修改第二个数据库的情况下写入的。

Later, when I see the loaded data in my web application, I see the extrange character despite the <meta http-equiv="Content-Type" content="text/html; charset=utf-8" />.

后来,当我在 Web 应用程序中看到加载的数据时,尽管<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />.

If I decode the data using ...

如果我使用...解码数据

new String(data.getBytes("UTF-8"));

... I visualize correctly the character (ó). But I can not use this solution as a general rule because when I modify data using web application form, the data is not updated in UTF-8 in my second database (despite the database is UTF-8 and my connection string is using characterEncoding, characterSetResults and useUnicode parameters).

...我正确地形象化了字符 (ó)。但是我不能将此解决方案用作一般规则,因为当我使用 Web 应用程序表单修改数据时,我的第二个数据库中的数据不会以 UTF-8 更新(尽管数据库是 UTF-8 并且我的连接字符串使用的是字符编码, characterSetResults 和 useUnicode 参数)。

From my Java code I obtain the following Database settings:

从我的 Java 代码中,我获得了以下数据库设置:

character_set_client-->utf8 
character_set_connection-->utf8 
character_set_database-->utf8 
character_set_filesystem-->binary 
character_set_results-->utf8 
character_set_server-->latin1 
character_set_system-->utf8 
character_sets_dir-->/usr/local/mysql51/share/mysql/charsets/ 

the character_set_server setting can't be changed and I don't know what I am doing wrong!!

character_set_server 设置无法更改,我不知道我做错了什么!!

How can I read UTF-8 data from MySQL using JDBC connector (mysql-connector-java-5.1.5-bin.jar)?

如何使用 JDBC 连接器 ( mysql-connector-java-5.1.5-bin.jar)从 MySQL 读取 UTF-8 数据?

Is the problem with reading data from the first database or writing to the second database?

是从第一个数据库读取数据还是写入第二个数据库的问题?

回答by chburd

You can set the file.encodingproperty of your JVM to UTF-8 so all locale/encoding sensitive API will consider decoded Strings as UTF8.

您可以将file.encodingJVM的属性设置为 UTF-8,这样所有区域设置/编码敏感的 API 都会将解码后的字符串视为 UTF8。

For example, you can set it in your command line that launches your Java app:

例如,您可以在启动 Java 应用程序的命令行中设置它:

java -Dfile.encoding=UTF-8 ....

You can also refer to this SO questionfor a complete explanation of Tomcat setup.

您还可以参考此 SO 问题以获取有关 Tomcat 设置的完整说明。

回答by erickson

At some point in the chain, UTF-8–encoded bytes are being decoded with Latin1. From the list of your settings, it appears this is happening at "character_set_server". Without knowing how these values were obtained, it is hard to interpret them.

在链中的某个点,UTF-8 编码的字节正在使用 Latin1 进行解码。从您的设置列表中,这似乎发生在“character_set_server”上。如果不知道这些值是如何获得的,就很难解释它们。

Check the value of the system property"file.encoding". If that is not "UTF-8", then you need to explicitly specify "UTF-8" as the character encoding whenever you decode bytes to characters. For example, when you call a Stringconstructor with a byte[], or use an InputStreamReader.

检查系统属性“file.encoding”的值。如果这不是“UTF-8”,那么每当您将字节解码为字符时,您都需要明确指定“UTF-8”作为字符编码。例如,当您使用 调用String构造函数时byte[],或使用InputStreamReader.

It is best to explicitly specify character encodings, rather than rely on the default platform encoding.

最好明确指定字符编码,而不是依赖默认的平台编码。

回答by Doua Beri

A little late but this will help you:

有点晚了,但这会帮助你:

DriverManager.getConnection(
           "jdbc:mysql://" + host + "/" + dbName 
           + "?useUnicode=true&characterEncoding=UTF-8", user, pass);