java.sql.SQLException:连接已关闭 [POOL-HikariCP]

Posted

技术标签:

【中文标题】java.sql.SQLException:连接已关闭 [POOL-HikariCP]【英文标题】:java.sql.SQLException: Connection is closed [POOL-HikariCP] 【发布时间】:2016-07-01 20:03:03 【问题描述】:

您好,我的连接有问题,它在执行查询时正在关闭连接。我不知道会发生什么 D: 这是配置:

private static HikariDataSource Hikari;
public static String ID_Usuario;

public void connectToDatabase()        

    Hikari = new HikariDataSource();       
    Hikari.setDriverClassName("com.mysql.jdbc.Driver");
    Hikari.setJdbcUrl("jdbc:mysql://localhost:3306/bank");
    Hikari.setUsername("root");
    Hikari.setPassword(""); 
    Hikari.setMaximumPoolSize(5);
    Hikari.setConnectionTimeout(300000);
    Hikari.addDataSourceProperty("cachePrepStmts", "true");
    Hikari.addDataSourceProperty("prepStmtCacheSize", "250");
    Hikari.addDataSourceProperty("prepStmtCacheSqlLimit", "2048");
    Hikari.setConnectionTestQuery("SELECT 1");


public HikariDataSource getHikari()
    return Hikari;

现在,这是我使用池的类,首先我收到了来自 Hikari.getConnection() 的连接。然后我把它保存在“连接”中

Pool HikariPool;
HikariDataSource Hikari;
Connection connection;

  public SQL() 
    initComponents();
  

    public void initComponents()
        HikariPool= new Pool();
        HikariPool.connectToDatabase();

    Hikari=HikariPool.getHikari();

    try
       connection= Hikari.getConnection();
    catch(SQLException e)
        e.printStackTrace();
    

我在 validateLogin() 中使用“连接”

public int validateLogin(String nip)
   int validation=0;
   String SQL="SELECT * FROM bank.account WHERE No_Account='"+account+"'   
    AND NIP='"+nip+"'";
    try
        Statement stm=Conexion.createStatement();
        ResultSet rs= stm.executeQuery(SQL);
...

在“语句 stm=connection.createStatement();”行发生错误

上面写着:

[AWT-EventQueue-0] INFO com.zaxxer.hikari.HikariDataSource - HikariPool-0  
- is starting.
java.sql.SQLException: Connection is closed at   
com.zaxxer.hikari.pool.ProxyConnection$ClosedConnection$1.invoke
(ProxyConnection.java:468)
at com.sun.proxy.$Proxy0.createStatement(Unknown Source)...

为什么要关闭连接?

【问题讨论】:

您使用连接池的方式是非典型的。大多数连接池会在连接打开到 long 时撤销连接,因为它通常表明代码忘记调用 close(将其返回到池中)。 不要连接查询字符串中的值,使用带有参数占位符的准备好的语句。您当前的代码容易受到 SQL 注入的攻击。 我知道这是不同的,我是新手,但感谢您的建议。 【参考方案1】:

您的代码结构对我来说还不是很清楚。但我认为您不想在initComponents() 中分配连接。当您需要运行查询时,您应该获取一个 Connection,然后将其关闭以将其返回到池中。

类似...

public int validateLogin(String nip) 
   int validation=0;
   String SQL="SELECT * FROM bank.account WHERE No_Account='"+account+"'   
    AND NIP='"+nip+"'";
    try (Connection conn = SQL.getConnection();
         Statement stm = conn.createStatement()) 
       ResultSet rs = stm.executeQuery(SQL);
       ...
    
    catch (SQLException e) 
       ...
    

“try with resources”会自动关闭连接和语句。

SQL.getConnection() 在哪里做了类似的事情:

public Connection getConnection() throws SQLException 
   return Hikari.getConnection();

【讨论】:

我知道你的意思,但为什么你不能在需要运行查询之前打开连接。为什么会发生?

以上是关于java.sql.SQLException:连接已关闭 [POOL-HikariCP]的主要内容,如果未能解决你的问题,请参考以下文章

java连接Oracle数据库,从ResultSet中提取数据出现java.sql.sqlException结果集已耗尽

java.sql.SQLException: TNS:listener 目前不知道连接描述符中给出的 SID

Java 异常 java.sql.SQLException: HikariDataSource HikariDataSource (HikariPool-1) 已关闭

java.sql.SQLException:打开连接时出错

spark - 线程“main”java.sql.SQLException 中的异常:没有合适的驱动程序

java.sql.SQLException:Io 异常:套接字读取超时与关闭连接