我有一个应用程序,其目的是支持jdbc:hive://
和jdbc:hive2://
协议的JDBC连接。以下代码为两个协议加载相应的JDBC驱动程序:
private void setDriverClass() ... {
...
Class.forName("org.apache.hadoop.hive.jdbc.HiveDriver"); // acceptsURL -> jdbc:hive://
Class.forName("org.apache.hive.jdbc.HiveDriver"); // acceptsURL -> jdbc:hive2://
}
据我所知,当调用客户端连接时,DriverManager调用accepstURL()方法来验证索引中的当前驱动程序是否可以处理连接。 acceptsURL()通常使用jdbcURL.startsWith方法来匹配字符串。
有时我的客户端连接使用jdbc:hive2://
前缀未建立,因为“无效的jdbcURL”错误。似乎org.apache.hadoop.hive.jdbc.HiveDriver
接受jdbc:hive2://
前缀并抛出异常 - org.apache.hadoop.hive.jdbc.HiveDriver
显示在stacktrace--中,这是正确的,因为它的acceptsURL返回false(因为我已经验证)。
我的问题是:除了acceptsURL之外,还有其他任何方法,DriverManager用来选择创建连接时使用的JDBC驱动程序吗?并且,它仅依赖于DriverManager或底层JDBC驱动程序除了acceptURL()和jdbc的基础之外还需要实现支持代码。
答案 0 :(得分:1)
DriverManager依赖于JDBC规范(以及驱动程序对它的遵从性),其中注意到:
如果驱动程序意识到连接到给定URL的驱动程序类型错误,则应返回“null”。这很常见,因为当要求JDBC驱动程序管理器连接到给定的URL时,它会依次将URL传递给每个加载的驱动程序。
Hive的JDBC驱动程序违反了合同并抛出异常而不是由DriverManager解释为“驱动程序理解URL,但由于某种原因无法建立连接”。如果DriverManager调用驱动程序acceptsURL()
不仅作为getDriver(url)
的一部分,而且作为getConnection(url)
方法的一部分,那也没关系,但事实并非如此。
答案 1 :(得分:0)
使用较新版本的JDBC,您不必将JDBC驱动程序加载到内存中。 JDBC代码将扫描您的类路径以查找驱动程序。
这使您的setDriverClass
方法变得不必要。只需确保在类路径中将驱动程序包含为JAR。
在以前的JDBC版本中,要获得连接,首先必须通过调用Class.forName方法来初始化JDBC驱动程序。此方法需要java.sql.Driver类型的对象。每个JDBC驱动程序都包含一个或多个实现接口java.sql.Driver的类。 [...]
自动加载在类路径中找到的任何JDBC 4.0驱动程序。 (但是,必须使用方法Class.forName手动加载JDBC 4.0之前的任何驱动程序。)
(来自JDBC Java Trail)