最近我遇到Tomcat停止后在Oracle数据库中有活动会话的问题。我决定重现这种情况并尝试找到解决方案。测试代码:
import lombok.extern.slf4j.Slf4j;
import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.SQLException;
import java.sql.Statement;
@Slf4j
public class ClosingActiveOracleSession {
public static void main(String[] args) throws SQLException, InterruptedException {
final Connection connection = DriverManager.getConnection("jdbc:oracle:thin:@//...", "username", "password");
final Statement statement = connection.createStatement();
new Thread(() -> {
try {
statement.execute("BEGIN\n"
+ " LOOP\n"
+ " dbms_lock.sleep(5);\n"
+ " END LOOP;\n"
+ "END;");
} catch (SQLException e) {
throw new RuntimeException("PL/SQL execution error", e);
}
}).start();
log.info("[main] will sleep");
Thread.sleep(10000);
log.info("[main] awoke");
statement.cancel();
log.info("statement canceled");
statement.close();
log.info("statement closed");
connection.close();
log.info("[main] connection closed");
}
}
我收到一条消息,说明该语句已被取消,但未发生有关其关闭的消息。我怀疑关闭语句被互斥锁(连接)阻止。 Oracle数据库中的会话仍然存在。
要检查是否可以取消此查询,我在PL / SQL Developer中运行此PL / SQL块并单击“中断”按钮:
BEGIN
LOOP
dbms_lock.sleep(5);
END LOOP;
END;
经过一段时间后,我有ORA-01013取消了PL / SQL块的执行。 Oracle数据库中的会话状态变为非活动状态。
有人知道Oracle JDBC Driver出了什么问题吗?
Oracle驱动程序版本:ojdbc7-12.1.0.2
Oracle数据库版本:Oracle Database 12c企业版12.1.0.2.0版
但是这段代码很好用:
import lombok.extern.slf4j.Slf4j;
import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Statement;
@Slf4j
public class ClosingActiveOracleSession {
public static void main(String[] args) throws SQLException, InterruptedException {
final Connection connection = DriverManager.getConnection("jdbc:oracle:thin:@//...", "username", "password");
final Statement statement = connection.createStatement();
new Thread(() -> {
try {
final ResultSet resultSet = statement.executeQuery("SELECT * FROM some_table WHERE some_condition = 21332112");
while (resultSet.next()) {
// Ignore
}
} catch (SQLException e) {
throw new RuntimeException("Processing ResultSet failed", e);
}
}).start();
log.info("[main] will sleep");
Thread.sleep(10000);
log.info("[main] awoke");
statement.cancel();
log.info("statement cancelled");
statement.close();
log.info("statement closed");
connection.close();
log.info("[main] connection closed");
}
}
当声明取消时我得到了:
java.sql.SQLException:关闭结果集:下一个
和
java.sql.SQLException:ORA-12592:TNS:坏包
感谢帮助。
p.s:抱歉我的英文