首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 編程語言 >  >> Java 程式設計 >> Java 相關知識

JDBC 連接 Access 資料庫三種方案詳解:ODBC 橋接、免 DSN 連線字串、原生驅動

     編輯:Java 相關知識

雖然 Access 已非主流生產資料庫,但在輕量級桌面應用、遷移專案、單元測試替身中仍常見。JDBC 連接 Access 主要有三條路徑,本文詳細對比優劣、提供可直接複製的連線代碼,並解決「找不到資料源」、「架構不匹配 (32/64 位)」等經典坑。

方案一:JDBC-ODBC Bridge + 系統 DSN (JDK 8 移除,僅歷史參考)

已廢棄:JDK 8 起移除 sun.jdbc.odbc.JdbcOdbcDriver。若維護極舊系統 (JDK 7-):

  1. 控制台 → 管理工具 → ODBC 資料來源 (32/64 位對應 JDK 位數) → 系統 DSN → 新增 → Microsoft Access Driver (*.mdb, *.accdb)
  2. 資料源名稱:MyAccessDSN,選擇 .mdb/.accdb 檔案。
  3. 代碼:
Class.forName("sun.jdbc.odbc.JdbcOdbcDriver");
Connection conn = DriverManager.getConnection("jdbc:odbc:MyAccessDSN", "", "");

⚠ 致命缺陷:效能差、非跨平台、JDK 8+ 無法使用、需管理員配置 DSN、部署麻煩。

方案二:JDBC-ODBC Bridge + 免 DSN 連線字串 (JDK 7- 適用,推薦舊專案)

在連線字串內直接指定驅動與檔案路徑,無需建立系統 DSN,部署極簡:

// .mdb (Access 2003-)
String url = "jdbc:odbc:Driver={Microsoft Access Driver (*.mdb)};DBQ=C:/data/test.mdb";

// .accdb (Access 2007+)
String url = "jdbc:odbc:Driver={Microsoft Access Driver (*.mdb, *.accdb)};DBQ=C:/data/test.accdb";

Class.forName("sun.jdbc.odbc.JdbcOdbcDriver");
Connection conn = DriverManager.getConnection(url, "", ""); // Access 預設無密碼或僅資料庫密碼

關鍵點:

  • DBQ 使用正斜線 或雙反斜線 C:\\data\\test.mdb。
  • 若資料庫有密碼:;PWD=your_password。
  • 32/64 位陷阱:JdbcOdbcDriver 僅 32 位。64 位 JDK 無法載入。解決:安裝 32 位 JDK/JRE 運行應用,或升級方案三。

方案三:UCanAccess 純 Java 驅動 (JDK 8+ 唯一推薦、跨平台、無 ODBC 依賴)

現代標準解法:UCanAccess 基於 Jackcess 實現純 Java 讀寫 Access,無需 ODBC、無需 Access 安裝、支援 .mdb/.accdb、Maven 中央倉庫可用。

Maven 依賴

<dependency>
    <groupId>net.sf.ucanaccess</groupId>
    <artifactId>ucanaccess</artifactId>
    <version>5.0.1</version> <!-- 檢查最新版 -->
</dependency>

傳遞依賴:jackcess, commons-lang3, commons-logging, hsqldb (內嵌用於複雜查詢)。

連線代碼

// .accdb
String url = "jdbc:ucanaccess://C:/data/test.accdb";
// .mdb
String url = "jdbc:ucanaccess://C:/data/test.mdb";

// 可選參數
// 單獨連線 (預設共享 hsqldb 快取)
String url = "jdbc:ucanaccess://C:/data/test.accdb;singleConnection=true";
// 忽略大小寫
String url = "jdbc:ucanaccess://C:/data/test.accdb;ignoreCase=true";
// 記憶體模式 (唯讀、極快)
String url = "jdbc:ucanaccess://C:/data/test.accdb?memory=true";

Connection conn = DriverManager.getConnection(url); // 自動載入驅動 (JDBC 4.0+)

完整 CRUD 範例

try (Connection conn = DriverManager.getConnection("jdbc:ucanaccess://C:/data/test.accdb");
     Statement stmt = conn.createStatement()) {
    
    // 建表
    stmt.execute("CREATE TABLE users (id COUNTER PRIMARY KEY, name TEXT(50), age INT)");
    
    // 插入
    try (PreparedStatement ps = conn.prepareStatement("INSERT INTO users(name, age) VALUES(?, ?)")) {
        ps.setString(1, "Alice");
        ps.setInt(2, 25);
        ps.executeUpdate();
    }
    
    // 查詢
    try (ResultSet rs = stmt.executeQuery("SELECT * FROM users")) {
        while (rs.next()) {
            System.out.printf("ID:%d Name:%s Age:%d%n", 
                rs.getInt("id"), rs.getString("name"), rs.getInt("age"));
        }
    }
} catch (SQLException e) {
    e.printStackTrace();
}

方案對比總結表

維度方案一: 系統 DSN方案二: 免 DSN ODBC方案三: UCanAccess
JDK 版本≤ 7≤ 78 - 21+
平台僅 Windows僅 Windows跨平台 (Win/Linux/Mac)
架構32 位限制32 位限制32/64 位通用
部署需配置 DSN僅需檔案路徑僅需 JAR 包
效能低低中 (純 Java、Jackcess 優化)
功能支援完整完整大多數 SQL、部分複雜查詢轉 hsqldb
維護狀態已移除已移除活躍維護

常見問題 FAQ

No suitable driver found for jdbc:ucanaccess://...
JAR 未在 classpath、版本衝突 (多版本 ucanaccess/jackcess)、未用 DriverManager.getConnection 觸發 SPI 載入。
java.lang.UnsatisfiedLinkError (方案二)
64 位 JDK 嘗試載入 32 位 ODBC 驅動。改用 32 位 JRE 或遷移 UCanAccess。
寫入效能極慢
Access 非事務型資料庫,批次寫入用 conn.setAutoCommit(false) + 批次 executeBatch() + 定期 commit()。
並發存取衝突
Access 檔案鎖機制簡單,多進程寫入極易損壞。**嚴禁高併發寫入**,改用 SQLite (單檔) 或 H2/Derby (嵌入式) 替代。
遷移建議
新專案**直接選擇 H2 / SQLite / PostgreSQL**,僅在「必須讀寫現有 .accdb」時用 UCanAccess 做遷移過渡。

總結

JDK 8+ 環境下,**UCanAccess 是連接 Access 的唯一正解**:純 Java、跨平台、無配置、Maven 化。方案一、二僅供維護 JDK 7 以下遺留系統參考。長遠規劃應將 Access 視為「遷移來源」而非「運行時依賴」,盡早導出資料至標準關係型資料庫。

  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved