다음 문자열 값이 있습니다. “walmart obama ??”
MySQL과 Java를 사용하고 있습니다.
다음 예외가 발생합니다.`java.sql.SQLException : 잘못된 문자열 값 : ‘\ xF0 \ x9F \ x91 \ xBD \ xF0 \ x9F …’
삽입하려는 변수는 다음과 같습니다.
var1 varchar(255) CHARACTER SET utf8 COLLATE utf8_general_ci NOT NULL`
“walmart obama ??”를 삽입하려는 Java 코드가 준비된 상태입니다. 그래서 나는 setString()
방법을 사용하고 있습니다.
문제는 ?? 값의 인코딩 인 것 같습니다. 이 문제를 어떻게 해결할 수 있습니까? 이전에는 Derby SQL을 사용했고 ?? 값은 2 sqaures로 끝났습니다 (나는 이것이 널 문자의 표현이라고 생각합니다)
모든 도움에 감사드립니다!
답변
당신이 가진 것은 EXTRATERRESTRIAL ALIEN (U+1F47D)
하고 BROKEN HEART (U+1F494)
있는 기본 다국어 평면에 있지 않습니다. 그들은 자바에서 하나의 문자로 표현 될 수도 없습니다 "??".length() == 4
. 확실히 null 문자가 아니며 지원하는 글꼴을 사용하지 않으면 사각형이 표시됩니다.
MySQL utf8
은 기본 다국어 평면 만 지원하며 utf8mb4
대신 다음 을 사용해야 합니다 .
보충 문자의 경우 utf8은 문자를 전혀 저장할 수 없지만 utf8mb4는이를 저장하는 데 4 바이트가 필요합니다. utf8은 문자를 전혀 저장할 수 없기 때문에 utf8 열에 보충 문자가 없으며 이전 버전의 MySQL에서 utf8 데이터를 업그레이드 할 때 문자 변환이나 데이터 손실에 대해 걱정할 필요가 없습니다.
따라서 이러한 문자를 지원하려면 MySQL이 5.5 이상이어야하며 utf8mb4
모든 곳 에서 사용해야 합니다. 연결 인코딩은이어야 utf8mb4
하고 문자 세트는이어야 utf8mb4
하며 조합은이어야 utf8mb4
합니다. Java의 경우 여전히 "utf-8"
이지만 MySQL에는 구별이 필요합니다.
어떤 드라이버를 사용하고 있는지 모르겠지만 드라이버에 구애받지 않는 연결 문자 집합을 설정하는 방법은 쿼리를 보내는 것입니다.
SET NAMES 'utf8mb4'
연결 직후.
Connector / J에 대한 내용도 참조하십시오 .
14.14 : Connector / J에서 4 바이트 UTF8, utf8mb4를 어떻게 사용할 수 있습니까?
Connector / J에서 4 바이트 UTF8을 사용하려면 character_set_server = utf8mb4로 MySQL 서버를 구성합니다. Connector / J는 연결 문자열에 characterEncoding이 설정 되지 않은 한 해당 설정을 사용
합니다 . 이것은 문자 집합의 자동 감지와 동일합니다.
열과 데이터베이스도 조정하십시오.
var1 varchar(255) CHARACTER SET utf8mb4 COLLATE utf8mb4_general_ci NOT NULL
다시 말하지만, MySQL 버전은 utf8mb4 지원을 위해 비교적 최신 버전이어야합니다.
답변
대체로 4 바이트가 필요한 기호를 저장하려면 characher-set 및 collation을 업데이트해야합니다 utf8mb4
.
- 데이터베이스 테이블 / 열 :
alter table <some_table> convert to character set utf8mb4 collate utf8mb4_unicode_ci
- 데이터베이스 서버 연결 ( 참조 )
# 2의 개발 환경에서 서버를 시작할 때 명령 줄에 매개 변수를 설정하는 것을 선호합니다.
mysqld --character-set-server=utf8mb4 --collation-server=utf8mb4_unicode_ci
BTW에주의를 기울 커넥터 / J 행동 과 SET NAMES 'utf8mb4'
:
커넥터 / J를 사용하여 쿼리 세트 이름을 발행하지 마십시오. 드라이버는 문자 세트가 변경되었음을 감지하지 않고 초기 연결 설정 중에 감지 된 문자 세트를 계속 사용합니다.
characterEncoding
연결된 서버 인코딩을 재정의하므로 연결 URL에서 매개 변수를 설정하지 마십시오 .
클라이언트 측에서 자동으로 감지 된 인코딩을 재정의하려면 서버에 연결하는 데 사용되는 URL에서 characterEncoding 속성을 사용합니다.
답변
이상하게, 나는 제거하기 것을 발견 &characterEncoding=UTF-8
으로부터 것은 JDBC url
유사한 문제로 나를 위해 트릭을했다.
내 속성에 따라
jdbc_url=jdbc:mysql://localhost:3306/dbName?useUnicode=true
나는 이것이 @Esailija가 위에서 말한 것을 지원한다고 생각합니다. 즉, 실제로 5.5 인 내 MySQL은 UTF-8 인코딩의 가장 좋아하는 맛을 파악하고 있습니다.
(참고, 나는 또한 InputStream
내가 읽고 UTF-8
있는 자바 코드를 지정하고 있는데, 아마 아프지 않을 것입니다) …
답변
내 문제를 어떻게 해결했는지.
나는 가지고 있었다
?useUnicode=true&characterEncoding=UTF-8
내 최대 절전 모드 jdbc 연결 URL에서 문자열 데이터 유형을 이전에 varchar였던 데이터베이스의 longtext로 변경했습니다.
답변
useUnicode=true&characterEncoding=UTF-8
jdbc URL에 줄 을 추가하십시오 .
귀하의 경우 데이터는 UTF-8
인코딩을 사용하여 전송되지 않습니다 .
답변
나는 같은 문제에 직면하고 각 열에 대해 Collation 을 utf8_general_ci 로 설정하여 해결했습니다 .
답변
MySQL은 이것이 유효한 UTF8 텍스트라고 믿지 않는다고 생각합니다. 동일한 열 정의 (mysql 클라이언트 연결도 UTF8)로 테스트 테이블에 삽입을 시도했지만 삽입했지만 MySQL CLI 클라이언트와 JDBC로 검색 한 데이터는 값을 올바르게 검색하지 못했습니다. UTF8이 올바르게 작동하는지 확인하기 위해 오바마에 “o”대신 “ö”를 삽입했습니다.
johan@maiden:~$ mysql -vvv test < insert.sql
--------------
insert into utf8_test values(_utf8 "walmart öbama ??")
--------------
Query OK, 1 row affected, 1 warning (0.12 sec)
johan@maiden:~$ file insert.sql
insert.sql: UTF-8 Unicode text
테스트 할 작은 Java 애플리케이션 :
package test.sql;
import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
public class Test
{
public static void main(String[] args)
{
System.out.println("test string=" + "walmart öbama ??");
String url = "jdbc:mysql://hostname/test?useUnicode=true&characterEncoding=UTF-8";
try
{
Class.forName("com.mysql.jdbc.Driver").newInstance();
Connection c = DriverManager.getConnection(url, "username", "password");
PreparedStatement p = c.prepareStatement("select * from utf8_test");
p.execute();
ResultSet rs = p.getResultSet();
while (!rs.isLast())
{
rs.next();
String retrieved = rs.getString(1);
System.out.println("retrieved=\"" + retrieved + "\"");
}
}
catch (Exception e)
{
e.printStackTrace();
}
}
}
산출:
johan@appel:~/workspaces/java/javatest/bin$ java test.sql.Test
test string=walmart öbama ??
retrieved="walmart öbama "
또한 JDBC 연결로 동일한 삽입을 시도했으며 동일한 예외가 발생했습니다. 나는 이것이 MySQL 버그라고 생각합니다. 이미 그런 상황에 대한 버그 리포트가 있을지도 ..