mysql - 在 Web 应用程序中通过 JDBC 连接到数据库时,何时需要 Class.forName?

标签 mysql tomcat jdbc

根据 this tutorial ,对于 JDBC 4.0+ 驱动程序,不再需要调用 Class.forName。对于使用 MySQL 的独立程序,我成功地遵循了示例中的方法(仅调用 DriverManager.getConnection),但是当我尝试从属于在 Tomcat 7 上运行的 Web 应用程序无法运行;相反,我得到了一个 No suitable driver found 异常。

mysql-connector-java-5.1.18-bin.jar 文件在 tomcat\webapps\DatabaseProject\WEB-INF\lib 中,我检查了三次,但它没有用,所以我开始尝试。我添加了对 Class.forName 的调用,它起作用了。这是唯一发生变化的事情。

无论如何,我的问题是,有人知道为什么这有效或这里发生了什么吗?我唯一的理论是,我在 tomcat\lib 中也有用于另一个项目的 hsqldb.jar,也许驱动程序不知何故感到困惑?但我的印象是 DriverManager 应该能够自动判断要使用哪个驱动程序,所以这不应该成为问题......无论如何,如果有人能告诉我这里发生了什么,我真的很感激

最佳答案

JDBC4 驱动程序包含一个文件:

META-INF/services/java.sql.Driver

在使用 ServiceProvider 机制向 JVM 注册驱动程序实现的 jar 中(参见 java.util.ServiceLoader 的 javadocs)。这就是不再需要 Class.forName 的原因。

我猜这是一个类加载器问题。 ServiceLoader javadoc 提到:

The provider must be accessible from the same class loader that was initially queried to locate the configuration file; note that this is not necessarily the class loader from which the file was actually loaded.

我会尝试将您的驱动程序放在 tomcat\lib 目录中,而不是您的 Web 应用程序目录中,看看这是否会有所不同(不同的类加载器?)。

如果您通过 IDE 启动 Web 应用程序并设置断点,一旦遇到断点,您可以使用“评估表达式”功能来执行:ServiceLoader.load(Driver.class) .这将为您提供一个 ServiceLoader 类,您可以查看其中注册了哪些驱动程序。您可以检查 mysql 驱动程序是否存在,它在列表中的位置等,这可能有助于找出此处的行为。

关于mysql - 在 Web 应用程序中通过 JDBC 连接到数据库时,何时需要 Class.forName?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/21666909/

相关文章:

java - 对在 amazon Linux 上为 tomcat7 设置 CATALINA_OPTS 的位置感到困惑

oracle - Tomcat session 复制:java.io.NotSerializableException : oracle. jdbc.driver.T4CConnection

ios - HTTP 状态 404 Tomcat/Intellij

java - 将值写入文本文件,读取它并在db中显示

java - 使用 LEFT JOIN 更新不适用于 UCanAccess

php - 使用 PHP 将网页中的重音符号从 MySQL 转换为无重音符号

MySQL + htaccess mod_rewrite?

PHP 仅获取所有数据 1 否

Java/SQL : return an average from a specific column problem

asp.net - 单声道 + mysql = 慢?