專案原使用 Microsoft 官方 JDBC 驅動(com.microsoft.jdbc.base.BaseDatabaseMetaData),單獨測試連線正常,但整合 Hibernate 後拋出:
java.lang.AbstractMethodError: com.microsoft.jdbc.base.BaseDatabaseMetaData.getJDBCMajorVersion()I
// 或
java.lang.AbstractMethodError: com.microsoft.jdbc.base.BaseDatabaseMetaData.supportsGetGeneratedKeys()Z
根因:Microsoft 早期 JDBC 驅動未完整實作 JDBC 3.0/4.0 介面,Hibernate 內部呼叫 DatabaseMetaData 進階方法時觸發 AbstractMethodError。
jTDS 是開源、輕量、完整實作 JDBC 4.0 的 SQL Server / Sybase 驅動,廣泛用於 Hibernate、Spring、Tomcat 等生態系。
<dependency>
<groupId>net.sourceforge.jtds</groupId>
<artifactId>jtds</artifactId>
<version>1.3.1</version> <!-- JDK 8+ 使用 1.3.1;JDK 6/7 請用 1.2.x -->
</dependency>
<property name="connection.driver_class">net.sourceforge.jtds.jdbc.Driver</property>
<property name="connection.url">jdbc:jtds:sqlserver://<host>:<port>/<dbName>;instance=<instanceName>;charset=utf8</property>
<property name="connection.username">your_user</property>
<property name="connection.password">your_pwd</property>
<property name="dialect">org.hibernate.dialect.SQLServerDialect</property> <!-- 依版本調整:SQLServer2012Dialect 等 -->
| 參數 | 說明 | 建議值 |
|---|---|---|
| instance | 命名執行個體名稱(若為預設執行個體可省略) | MSSQLSERVER 或自訂名稱 |
| charset | 字元編碼 | utf8 |
| domain | Windows 網域驗證時指定網域 | CORP |
| useNTLMv2 | 啟用 NTLMv2 驗證(較安全) | true |
| ssl | 強制加密傳輸 | request / true |
| jTDS 版本 | 最低 JDK | 支援 SQL Server | 備註 |
|---|---|---|---|
| 1.2.x | JDK 1.5 | 2000 ~ 2012 | JDK 6/7 專案常用 |
| 1.3.0 | JDK 1.6 | 2005 ~ 2014 | 修正若干 Bug |
| 1.3.1 | JDK 1.7 | 2008 ~ 2019 | 建議生產環境版本 |
| 1.4.x (SNAPSHOT) | JDK 1.8+ | 2012 ~ 2022 | 尚未正式發布,慎用 |
1.2.8;升級 JDK 8 後務必同步升級 jTDS 至 1.3.1,否則會出現 UnsupportedClassVersionError: major.minor version 52.0/55.0。
sqljdbc.jar 與 jtds.jar,類別載入器可能優先載入舊驅動 → 徹底移除 Microsoft 驅動。jtds.jar 放入 $CATALINA_HOME/lib,避免 Webapp 類別載入器隔離導致重複載入。port 略過 Browser。lobBuffer=524288(512KB)或更大。SessionFactory 建立無誤)。validationQuery=SELECT 1)。