2012-01-23 116 views
9

我使用import.sql將我的開發數據寫入數據庫。我使用的MySQL Server 5.5和我的persistence.xml是在這裏:Hibernate/JPA import.sql utf8字符損壞

<?xml version="1.0" encoding="UTF-8"?> 
<persistence version="2.0" 
xmlns="http://java.sun.com/xml/ns/persistence" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" 
xsi:schemaLocation="http://java.sun.com/xml/ns/persistence http://java.sun.com/xml/ns/persistence/persistence_2_0.xsd"> 
<persistence-unit name="MobilHM" transaction-type="RESOURCE_LOCAL"> 
    <provider>org.hibernate.ejb.HibernatePersistence</provider> 
    <class>tr.com.stigma.db.entity.Doctor</class> 
    <class>tr.com.stigma.db.entity.Patient</class> 
    <class>tr.com.stigma.db.entity.Record</class> 
    <class>tr.com.stigma.db.entity.User</class> 
    <properties> 
     <property name="hibernate.hbm2ddl.auto" value="create" /> 
     <property name="hibernate.show_sql" value="true" /> 
     <property name="hibernate.format_sql" value="true" /> 
     <!-- Auto detect annotation model classes --> 
     <property name="hibernate.archive.autodetection" value="class" /> 
     <!-- Datasource --> 
     <property name="hibernate.connection.driver_class" value="com.mysql.jdbc.Driver" /> 
     <property name="hibernate.connection.username" value="mobilhm" /> 
     <property name="hibernate.connection.password" value="mobilhm" /> 
     <property name="hibernate.connection.url" value="jdbc:mysql://localhost/mobilhm" /> 
     <property name="hibernate.dialect" value="org.hibernate.dialect.MySQLDialect" /> 
    </properties> 
</persistence-unit> 

某些字符在我import.sql沒有在DB正確顯示。例如,字符ü變成以db爲單位。在MySQL默認字符集是UTF-8,我創建表像

CREATE TABLE doctor (doctorId int unsigned NOT NULL AUTO_INCREMENT, name varchar(45) NOT NULL, surname varchar(45) NOT NULL, PRIMARY KEY (doctorId)) ENGINE=InnoDB DEFAULT CHARSET=utf8; 

這是奇怪的,如果我輸入使用MySQL導入/導出管理器數據是正確的,但使用hibernate.hbm2ddl.auto =創建使得亂碼。

我該如何解決這個問題?

編輯: 還有我嘗試添加

<property name="hibernate.connection.useUnicode" value="true" /> 
<property name="hibernate.connection.characterEncoding" 
      value="UTF-8" /> 
<property name="hibernate.connection.charSet" value="UTF-8" /> 

到persistence.xml中。但它沒有幫助。

修復: 我最終解決了它。我使用的是Tomcat,這是不是休眠或者mysql的腐敗點。我已經開始設置JAVA_OPTS = -Dfile.encoding = UTF-8命令,我的問題消失了。

問題的標題現在變得令人誤解。對不起。

回答

10

爲該文件創建閱讀器時,Hibernate直接使用new InputStreamReader(stream);,而沒有顯式編碼(假設/使用默認的執行平臺charset編碼)。

因此,換句話說,您的import.sql文件必須在默認執行平臺字符集編碼。

有一個古老的(2006)開放式問題對於這一點,萬一有希望發送補丁:https://hibernate.atlassian.net/browse/HBX-711


選項來解決:

  • 添加-Dfile.encoding=UTF-8JAVA_OPTS環境變量,如:

    # Linux/Unix 
    export JAVA_OPTS=-Dfile.encoding=UTF-8 
    # Windows 
    set JAVA_OPTS=-Dfile.encoding=UTF-8 
    
    # Attention, check before if your JAVA_OPTS doesnt already have a value. If so, 
    # then it should be 
    export JAVA_OPTS=$JAVA_OPTS -Dfile.encoding=UTF-8 
    # or 
    set JAVA_OPTS=%JAVA_OPTS% -Dfile.encoding=UTF-8 
    
  • 在您的Maven插件中設置一個屬性(可能是surefire,failsafe或其他,取決於您如何運行導入休眠文件的代碼)。舉例surefire

    <plugin> 
        <groupId>org.apache.maven.plugins</groupId> 
        <artifactId>maven-surefire-plugin</artifactId> 
        <configuration> 
         <argLine>-Dfile.encoding=UTF8</argLine> 
        </configuration> 
    </plugin> 
    
+2

+1由於正確的原因,但假設是不正確的,因爲那麼你的測試將是平臺相關的。如果使用Maven作爲@Jaroslav Frolikov已經說過,最簡單的解決方案是將文本文件編碼設置爲IDE中的「UTF-8」或「 -Dfile.encoding = UTF8」。 –

+0

它在2017年仍然不起作用 – gstackoverflow

2

這是可靠解決方案,無需設置任何系統屬性

我們假設導入文件使用UTF-8編碼,但Java默認字符集不同,比如說latin1

1)定義的自定義類爲import_files_sql_extractor hibernate.hbm2ddl.import_files_sql_extractor = com.pragmasphere.hibernate.CustomSqlExtractor

2)固定由休眠在執行讀出的無效的字符串

package com.pragmasphere.hibernate; 

import org.hibernate.tool.hbm2ddl.MultipleLinesSqlCommandExtractor; 

import java.io.IOError; 
import java.io.Reader; 
import java.io.UnsupportedEncodingException; 
import java.nio.charset.Charset; 

public class CustomSqlExtractor extends MultipleLinesSqlCommandExtractor { 

    private final String SOURCE_CHARSET = "UTF-8"; 

    @Override 
    public String[] extractCommands(final Reader reader) { 
     String[] lines = super.extractCommands(reader); 

     Charset charset = Charset.defaultCharset(); 
     if (!charset.equals(Charset.forName(SOURCE_CHARSET))) { 
      for (int i = 0; i < lines.length; i++) { 
       try { 
        lines[i] = new String(lines[i].getBytes(), SOURCE_CHARSET); 
       } catch (UnsupportedEncodingException e) { 
        throw new IOError(e); 
       } 
      } 
     } 

     return lines; 
    } 
} 

您可以通過導入文件中使用的另一種編碼改變SOURCE_CHARSET值。