控制台报错:Failed to obtain JDBC Connection; nested exception is java.sql.SQLException: Connections could

背景

控制台提示报错:

Failed to obtain JDBC Connection; nested exception is java.sql.SQLException: Connections could not be acquired from the underlying database!

后台日志报错中出现:com.mysql.cj.exceptions.WrongArgumentException: Malformed database URL, failed to parse the connection string near '=utf-8;serverTimezone=Asia/Shanghai'.

解决办法

这一段数据库的连接本身是没有什么问题,将原来mysql-connector-java jar版本从8.0.11换成8.0.15就解决了

原因分析

我在想jar版本换了就能解决问题,那不同版本之间肯定有比较大的差距。后来看到

mysql-connector-java的版本在8.0.12也有这个问题,到8.0.13才解决,那到底是什么原因导致的呢?通过调试jar包程序,发现在解析url时用到的正则表达式发生了调整,具体差异如下:

这两个正则表达式非常相似,都用于解析查询字符串或者HTTP请求参数格式的键值对,比如key=value&another_key=value2这样的形式。两者主要区别在于对“值”部分(<value>组)的定义上。
共同点:
(?<key>[\w.\-\s%]*) 部分都是一样的,用来捕获键名,允许包含字母、数字、下划线、点、破折号和空白字符(包括空格)。
区别:
第一个正则表达式:[^&=]*
这个片段表示“值”的部分可以包含除&和=之外的任何字符的任意次数,这意味着它可以匹配到不包含&和=的值,即使值中包含了特殊字符。
第二个正则表达式:[^&]*
这个片段表示“值”的部分可以包含除&之外的任何字符的任意次数,但不禁止=的存在。因此,在这个表达式下,值可以包含=, 但它不能包含&,因为一旦遇到&,正则表达式就会停止匹配值部分。
总结起来,第一个表达式更严格地限制了值的部分,不允许出现=作为值的一部分;而第二个表达式则允许值中包含=符号,但不允许值中包含&。在处理URL查询字符串时,通常值中是可以包含=的,因为它用于分隔键和值,所以第二个表达式可能更适合用于解析实际的HTTP查询字符串参数。

补充说明

mysql官方对上面的问题做了如下解释说明:

https://dev.mysql.com/doc/relnotes/connector-j/8.0/en/news-8-0-13.html

这段话的意思大致是:

当连接属性的值本身包含等号(“=”)时,会引发异常(“WrongArgumentException:数据库URL格式不正确”)。这是由于连接URL的解析程序中出现错误,此修复程序已更正该错误。

  • 10
    点赞
  • 10
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
启动报错"Failed to obtain JDBC Connection; nested exception is java.sql.SQLException: interrupt"通常是由于数据库连接池耗尽导致的。这个错误表示应用程序无法从连接池中获取到数据库连接。 解决这个问题的方法有以下几种: 1. 增加连接池的大小:可以通过增加连接池的最大连接数来解决连接耗尽的问题。可以在连接池配置文件中修改`maxActive`属性的值,增加连接池的大小。 2. 检查数据库连接是否正确关闭:确保在使用完数据库连接后,及时关闭连接。如果连接没有正确关闭,会导致连接池中的连接无法释放,最终导致连接耗尽。 3. 检查数据库连接超时设置:检查数据库连接超时的设置,确保连接在一定时间内没有被使用时会被释放回连接池。 4. 检查数据库服务器的负载:如果数据库服务器的负载过高,可能会导致连接池中的连接无法及时释放。可以通过监控数据库服务器的负载情况,及时调整服务器资源。 5. 检查数据库连接配置:检查数据库连接配置是否正确,包括数据库的URL、用户名、密码等信息。 6. 检查数据库驱动版本:有些数据库驱动存在bug,可能会导致连接池无法正常工作。可以尝试升级或更换数据库驱动版本。 以下是一个示例代码,演示如何使用连接池获取数据库连接: ```java import org.apache.commons.dbcp.BasicDataSource; public class ConnectionPoolExample { public static void main(String[] args) { BasicDataSource dataSource = new BasicDataSource(); dataSource.setDriverClassName("com.mysql.jdbc.Driver"); dataSource.setUrl("jdbc:mysql://localhost:3306/mydb"); dataSource.setUsername("username"); dataSource.setPassword("password"); try (Connection connection = dataSource.getConnection()) { // 使用数据库连接进行操作 } catch (SQLException e) { e.printStackTrace(); } } } ```
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值