詳解在Hibernate中配置數據庫方言的作用和好處以及各種數據庫的方言連接


Hibernate底層依然使用SQL語句來執行數據庫操作,雖然所有關系型數據庫都支持使用標准SQL語句,但所有數據庫都對標准SQL進行了一些擴展,所以在語法細節上存在一些差異,因此Hibernate需要根據數據庫來識別這些差異。

舉例來說,我們在MySQL數據庫里進行分頁查詢,只需使用limit關鍵字就可以了;而標准SQL並不支持limit關鍵字,例如Oracle則需要使用行內視圖的方式來進行分頁。同樣的應用程序,當我們在不同數據庫之間遷移時,底層數據庫的訪問細節會發生改變,而Hibernate也為這種改變做好了准備,現在我們需要做的是:告訴Hibernate應用程序的底層即將使用哪種數據庫——這就是數據庫方言。

一旦我們為Hibernate設置了合適的數據庫方言,Hibernate將可以自動應付底層數據庫訪問所存在的細節差異。

不同數據庫所應使用的方言如表5.1所示。

表 不同數據庫及其對應方言

關系數據庫

方 言

DB2

org.hibernate.dialect.DB2Dialect

DB2 AS/400

org.hibernate.dialect.DB2400Dialect

DB2 OS390

org.hibernate.dialect.DB2390Dialect

PostgreSQL

org.hibernate.dialect.PostgreSQLDialect

MySQL

org.hibernate.dialect.MySQLDialect

MySQL with InnoDB

org.hibernate.dialect.MySQLInnoDBDialect

MySQL with MyISAM

org.hibernate.dialect.MySQLMyISAMDialect

Oracle(any version)

org.hibernate.dialect.OracleDialect

Oracle 9i

org.hibernate.dialect.Oracle9iDialect

Oracle 10g

org.hibernate.dialect.Oracle10gDialect

 

 

Sybase

org.hibernate.dialect.SybaseDialect

Sybase Anywhere

org.hibernate.dialect.SybaseAnywhereDialect

Microsoft SQL Server

org.hibernate.dialect.SQLServerDialect

SAP DB

org.hibernate.dialect.SAPDBDialect

Informix

org.hibernate.dialect.InformixDialect

HypersonicSQL

org.hibernate.dialect.HSQLDialect

Ingres

org.hibernate.dialect.IngresDialect

Progress

org.hibernate.dialect.ProgressDialect

Mckoi SQL

org.hibernate.dialect.MckoiDialect

Interbase

org.hibernate.dialect.InterbaseDialect

Pointbase

org.hibernate.dialect.PointbaseDialect

FrontBase

org.hibernate.dialect.FrontbaseDialect

Firebird

org.hibernate.dialect.FirebirdDialect

如果一個系統可能運行於多種數據庫,或者同時使用多種數據庫,那么,使用Hibernate將會給你帶來很多的方便,想信很多接觸Hibernate的人都會體會到。Hibernate底層是通過dialect包來對各種數據庫的差異進行抽象的。Dialect類中實現每種數據庫相同的東西,而不同數據庫對應會有該類的一個擴展實現,最終通過DialectFactory來決定創建哪一個類。通常我們都會指定hibernate.dialect屬性,那直接創建該屬性對應的類。如果我們沒有指定該屬性,那么由Hibernate自己決定選擇合適的方言。在DialectFactory中初始化各種數據庫對應的方言的Map,以數據庫產品名為key,以方言的包裝對象為value。Hibernate自動選擇方言時,會通過JDBC的DatabaseMetadata取得數據庫的產品名稱,根據名稱取得對應的方言。DialectFactory中對該Map的初始化的部分代碼如下:

  1. // TODO : this is the stuff it'd be nice to move to a properties file or some other easily user-editable place
  2. private static final Map MAPPERS = new HashMap();
  3. static {
  4. // detectors...
  5. MAPPERS.put( "HSQL Database Engine", new VersionInsensitiveMapper( "org.hibernate.dialect.HSQLDialect" ) );
  6. MAPPERS.put( "H2", new VersionInsensitiveMapper( "org.hibernate.dialect.H2Dialect" ) );
  7. MAPPERS.put( "MySQL", new VersionInsensitiveMapper( "org.hibernate.dialect.MySQLDialect" ) );
  8. MAPPERS.put( "PostgreSQL", new VersionInsensitiveMapper( "org.hibernate.dialect.PostgreSQLDialect" ) );
  9. MAPPERS.put( "Apache Derby", new VersionInsensitiveMapper( "org.hibernate.dialect.DerbyDialect" ) );
  10. <SPAN>...</SPAN> 原本上,這種自動選擇的方式,會給我們帶來方便,只可惜,從以上的代碼的注釋中可以知道,目前這一部分的初始化是通過硬編碼的,只有在以后的版本才會移動到配置文件或其他容易用戶編譯的地方,否則,我們可以非常容易的添加我們的配置供Hibernate進行自動選擇。而經常我們所使用的數據庫驅動程序所取到的數據庫產品名稱會跟以上硬編碼的不同,所以最終我們還是得自己配置數據庫方言。

    由於我們的系統中用到了好幾個數據源,經常也是對應不同類型的數據庫,並且數據源都是由容器提供的,在首次部署時經常因為數據庫類型變了而忘了修改對應的數據庫方言,而出了問題,這給實施人員帶來了很多的不便。不過目前除了對各種數據庫提供與以上硬編碼相同的數據庫產品名稱的驅動程序外,我們就只能自己動手了

  11. Hibernate對各數據庫的連接方言

  12.  

    <session-factory>
    <property name="connection.driver_class">net.sourceforge.jtds.JDBC.Driver</property>
    <property name="connection.url">jdbc:jtds:sqlserver://ALEX:1134/News</property>
    <!--for Oracle 9
    <property name="dialect">org.Hibernate.dialect.Oracle9Dialect</property>
    -->
    <!--for MySQL
    <property name="dialect">org.hibernate.dialect.MySQLDialect</property>
    -->
    <!--for Ms SQL Server-->
    <property name="dialect">org.hibernate.dialect.SQLServerDialect</property>
    <property name="connection.username">sa</property>
    <property name="connection.password">sa</property>
    <property name="show_sql">true</property>
    </session-factory>
    
    ?
    
    
    <!--MySql 驅動程序 eg. mysql-connector-java-5.0.4-bin.jar-->
    <property name="dialect">org.hibernate.dialect.MySQLDialect</property>
    <property name="connection.driver_class">com.mysql.jdbc.Driver</property>
    
    <!-- JDBC URL -->
    <property name="connection.url">jdbc:mysql://localhost/dbname?characterEncoding=gb2312</property>
    
    <!-- 數據庫用戶名-->
    <property name="connection.username">root</property>
    
    <!-- 數據庫密碼-->
    <property name="connection.password">root</property>
    
    
    <!--Sql Server 驅動程序 eg. jtds-1.2.jar-->
    <property name="dialect">org.hibernate.dialect.SQLServerDialect</property>
    <property name="connection.driver_class">net.sourceforge.jtds.jdbc.Driver</property>
    
    <!-- JDBC URL -->
    <property name="connection.url">jdbc:jtds:sqlserver://localhost:1433;DatabaseName=dbname</property>
    
    <!-- 數據庫用戶名-->
    <property name="connection.username">sa</property>
    
    <!-- 數據庫密碼-->
    <property name="connection.password"></property>
    
    
    
    <!--Oracle 驅動程序 ojdbc14.jar-->
    <property name="dialect">org.hibernate.dialect.OracleDialect</property>
    <property name="connection.driver_class">oracle.jdbc.driver.OracleDriver</property>
    
    <!-- JDBC URL -->
    <property name="connection.url">jdbc:oracle:thin:@localhost:1521:dbname</property>
    
    <!-- 數據庫用戶名-->
    <property name="connection.username">test</property>
    
    <!-- 數據庫密碼-->
    <property name="connection.password">test</property>
    
    
    
    如果出現如下錯誤,則可能是Hibernate SQL方言 (hibernate.dialect)設置不正確。
    Caused by: java.sql.SQLException: [Microsoft][SQLServer 2000 Driver for JDBC][SQLServer]'last_insert_id' 不是可以識別的 函數名。
    
    ?
    
    
    RDBMS 方言 
    DB2 org.hibernate.dialect.DB2Dialect 
    DB2 AS/400 org.hibernate.dialect.DB2400Dialect 
    DB2 OS390 org.hibernate.dialect.DB2390Dialect 
    PostgreSQL org.hibernate.dialect.PostgreSQLDialect 
    MySQL org.hibernate.dialect.MySQLDialect 
    MySQL with InnoDB org.hibernate.dialect.MySQLInnoDBDialect 
    MySQL with MyISAM org.hibernate.dialect.MySQLMyISAMDialect 
    Oracle (any version) org.hibernate.dialect.OracleDialect 
    Oracle 9i/10g org.hibernate.dialect.Oracle9Dialect 
    Sybase org.hibernate.dialect.SybaseDialect 
    Sybase Anywhere org.hibernate.dialect.SybaseAnywhereDialect 
    Microsoft SQL Server org.hibernate.dialect.SQLServerDialect 
    SAP DB org.hibernate.dialect.SAPDBDialect 
    Informix org.hibernate.dialect.InformixDialect 
    HypersonicSQL org.hibernate.dialect.HSQLDialect 
    Ingres org.hibernate.dialect.IngresDialect 
    Progress org.hibernate.dialect.ProgressDialect 
    Mckoi SQL org.hibernate.dialect.MckoiDialect 
    Interbase org.hibernate.dialect.InterbaseDialect 
    Pointbase org.hibernate.dialect.PointbaseDialect 
    FrontBase org.hibernate.dialect.FrontbaseDialect 
    Firebird org.hibernate.dialect.FirebirdDialect
     
    

      


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM