java - 动态加载 JDBC 驱动程序

标签 java jdbc classloader

我正在尝试使用这种代码动态加载 JDBC 驱动程序:

        try{
        URL[] url={new URL("file:libs/mysql-connector-java-5.1.21.jar")};
        URLClassLoader loader = new URLClassLoader(url, System.class.getClassLoader());
        loader.loadClass(drivername);
        Enumeration<Driver> drivers = DriverManager.getDrivers();
        while(drivers.hasMoreElements()){
            Driver driver = drivers.nextElement();
            System.out.println("driver:"+driver);
        }
        Class.forName(drivername, true, loader);
        drivers = DriverManager.getDrivers();
        while(drivers.hasMoreElements()){
            Driver driver = drivers.nextElement();
            System.out.println("driver:"+driver);
        }
        Connection connect = DriverManager.getConnection(jdbcurl, user,
                password);

        return connect;
    }
    catch (MalformedURLException e){
        e.printStackTrace();
        return null;
    }

第一个 while 循环显示类路径的驱动程序:

driver:sun.jdbc.odbc.JdbcOdbcDriver@35712651
driver:oracle.jdbc.OracleDriver@58df0438
driver:com.ibm.db2.jcc.DB2Driver@525c7734
driver:SQLServerDriver:1

第二个循环显示相同的驱动程序,但没有 MySQL 驱动程序。

我的问题是为什么?我错过了什么吗?

我读了in the JavaDoc of DriverManager如果驱动程序已加载,每个驱动程序都会尝试通过驱动程序管理器注册自己。在我的代码中,这应该是 loader.loadClass(drivername);。我认为这段代码应该调用静态部分,例如:

static {
  try {
      java.sql.DriverManager.registerDriver(new Driver());
  } catch (SQLException E) {
      throw new RuntimeException("Can't register driver!");
  }
}

the Driver class .

最佳答案

这是 DriverManager 和类加载器的一个已知问题,请参阅:

http://www.kfu.com/~nsayer/Java/dyn-jdbc.html

驱动程序定义(基本上是委托(delegate)):

class DriverShim implements Driver {
    private Driver driver;
    DriverShim(Driver d) { this.driver = d; }
    public boolean acceptsURL(String u) throws SQLException {
        return this.driver.acceptsURL(u);
    }
    public Connection connect(String u, Properties p) throws SQLException {
        return this.driver.connect(u, p);
    }
    // and so on....

使用示例:

URL u = new URL("jar:file:/path/to/pgjdbc2.jar!/");
String classname = "org.postgresql.Driver";
URLClassLoader ucl = new URLClassLoader(new URL[] { u });
Driver d = (Driver)Class.forName(classname, true, ucl).newInstance();
DriverManager.registerDriver(new DriverShim(d));
DriverManager.getConnection("jdbc:postgresql://host/db", "user", "pw");

关于java - 动态加载 JDBC 驱动程序,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/14478870/

相关文章:

java - Lifefay freemarker ADT : methods unavailable?

java.sql.SQLException : [Microsoft][ODBC Microsoft Access Driver] Number of query values and destination fields are not the same 异常

java - 在 Android 应用程序中使用 Jar 时读取我自己的 Jar 的 list

plugins - 什么是Gradle插件生命周期

Java thread.getContext().getClassLoader() 唯一性

java - Java 中的 boolean 值

Java将数组切割成不均匀矩阵的最快方法

java - 单击时如何播放Listview项目的特定声音

java - 无法创建表 'basque30.newreferral'(错误号 : 150)

java - JPA 和服务器时区错误