0

我正在尝试制作JDBC连接池组件,但遇到了问题。即:如何检测java.sql.SQLException. 据说国家应该遵循SQL2003惯例和文件中的XOPEN SQL惯例JDK。但是我找不到关于这两个公约的任何文件。有人可以为我提供吗?

我想知道每个状态代表什么,所以我可以决定何时完全关闭连接或重新连接。

我参考了BoneCP. 这是发生 SQLException 时将激活的部分:

    ImmutableSet<String> sqlStateDBFailureCodes = ImmutableSet.of("08001", "08007", "08S01", "57P01", "HY000"); 
    String state = e.getSQLState();
        ConnectionState connectionState = this.getConnectionHook() != null ? this.getConnectionHook().onMarkPossiblyBroken(this, state, e) : ConnectionState.NOP; 
        if (state == null){ // safety;
            state = "08999"; 
        }

        if (((sqlStateDBFailureCodes.contains(state) || connectionState.equals(ConnectionState.TERMINATE_ALL_CONNECTIONS)) && this.pool != null) && this.pool.getDbIsDown().compareAndSet(false, true) ){
            logger.error("Database access problem. Killing off all remaining connections in the connection pool. SQL State = " + state);
            this.pool.connectionStrategy.terminateAllConnections();
            this.pool.poisonAndRepopulatePartitions();
        }
char firstChar = state.charAt(0);
        if (connectionState.equals(ConnectionState.CONNECTION_POSSIBLY_BROKEN) || state.equals("40001") || 
                state.startsWith("08") ||  (firstChar >= '5' && firstChar <='9') /*|| (firstChar >='I' && firstChar <= 'Z')*/){
            this.possiblyBroken = true;
        }

        // Notify anyone who's interested
        if (this.possiblyBroken  && (this.getConnectionHook() != null)){
            this.possiblyBroken = this.getConnectionHook().onConnectionException(this, state, e);
        }

根据这些代码,boneCP当 SQLException 的状态等于“08001”、“08007”、“08S01”、“57P01”、“HY000”之一时,将其视为数据库服务器崩溃。

但是为什么,这些州代表什么?

4

3 回答 3

5

前 2 个字符在SQL92 规范的“Table_23-SQLSTATE_class_and_subclass_values”中指定。

这是相关性的摘录:

00  success completion
01  warning
02  no data
07  dynamic SQL error
08  connection exception
0A  feature not supported
21  cardinality violation
22  data exception
23  integrity constraint violation
24  invalid cursor state
25  invalid transaction state
26  invalid SQL statement name
27  triggered data change violation
28  invalid authorization specification
2A  direct SQL syntax error or access rule violation
2B  dependent privilege descriptors still exist
2C  invalid character set name
2D  invalid transaction termination
2E  invalid connection name
33  invalid SQL descriptor name
34  invalid cursor name
35  invalid condition number
37  dynamic SQL syntax error or access rule violation
3C  ambiguous cursor name
3D  invalid catalog name
3F  invalid schema name
40  transaction rollback
42  syntax error or access rule violation
44  with check option violation
HZ  remote database access

其余字符取决于数据库供应商。所以一般建议只进行startsWith()检查。

于 2013-01-18T18:30:47.470 回答
2

SQL 标准 (ISO/IEC-9075),特别是书 2 Foundation 定义了 SQL 状态。它们是一个 2 个字符的类值,后跟一个 3 个字符的子类值。

以数字“0”、“1”、“2”、“3”或“4”之一或简单的拉丁大写字母“A”、“B”、“C”之一开头的类值, “D”、“E”、“F”、“G”或“H”仅在 ISO/IEC 9075 或任何其他国际标准中定义的条件下返回。[...] 与同样以这 13 个字符之一开头的此类相关的子类值仅针对 ISO/IEC 9075 或其他一些国际标准中定义的条件返回。[...] 与以数字“5”、“6”、“7”、“8”或“9”之一或简单的拉丁大写字母“I”之一开头的此类相关的子类值, 'J', 'K', 'L', 'M', 'N', 'O', 'P',

以数字“5”、“6”、“7”、“8”或“9”之一或简单的拉丁大写字母“I”、“J”、“K”之一开头的类值, 'L'、'M'、'N'、'O'、'P'、'Q'、'R'、'S'、'T'、'U'、'V'、'W'、'X '、'Y' 或 'Z' 保留用于实现定义的异常条件,称为实现定义的类。除了“000”(表示没有子类)之外的所有子类值,与此类关联的所有子类值都保留用于实现定义的条件,并称为实现定义的子类。

(来自 SQL:2011 第 2 册)

这些标准类(和标准定义的子类)列在第 2(基础)、3(CLI)、4(PSM)、9(MED)、10(OLB)、13(JRT)和 14(XML)中。它还列出了某事是异常、警告、成功完成条件还是无数据完成条件(并非所有 SQL 状态都是错误!)

例如,您的问题中列出的 sqlstates 是:

  • 08001: 类: 连接异常, 子类: SQL-client 无法建立 SQL-connection
  • 08007:类:连接异常,子类:事务解析未知
  • 08S01: 类:连接异常,子类:以S开头,所以是实现定义的子类(在ODBC中定义为通信链路故障)
  • 57P01:class: 以5开头,所以是实现定义类,好像是PostgreSQL sqlstate for ADMIN SHUTDOWN
  • HY000: 类:CLI 特定条件(在第 3 本书 CLI 中定义),子类:(无子类)

HY000是一个非常通用的错误,因为某些数据库或驱动程序会为任何没有特定 sqlstate 的错误返回它,因此它通常被视为致命错误。我这样做是为了将 BoneCP 的行为视为杀死整个连接池的原因,这有点矫枉过正,HY000因为相对良性的错误也可能会被抛出。其他 sqlstates 通常表示连接到数据库有问题 ( 08001, 08S01) 或数据库不可用 ( 57P01) 或数据库本身有问题 ( 08007)。

于 2013-01-19T09:28:06.180 回答
0

状态代码解释的链接实际上与您提到的代码块相同: https ://github.com/wwadge/bonecp/blob/master/bonecp/src/main/java/com/jolbox/bonecp/ConnectionHandle.java #L163

于 2013-01-28T15:01:24.590 回答