11

JDBC を使用してデータベース サーバーに接続しています。接続はワイヤレスネットワークを介しており、時々危険な場合があります. 接続が失われた瞬間に、アプリケーションを閉じて再起動する必要があります。

最後のクエリを自動的に再接続して再実行するための何らかのラッパーを記述できるコードの例はありますか? これにより、多くの手間が省けます。

どのように実装すべきか/実装できるかわかりません。たぶん、すでに利用可能なものがありますか?

4

3 に答える 3

7

アプリケーション サーバーが提供する JDBC 接続プールまたは apache commons プーリングを使用する場合でも、再試行ロジックをコーディングする価値があります。アプリケーション サーバーの構成に基づいて、アプリケーション サーバーはプールされたすべての接続を消去し、新しい接続セットを再作成します。以下にサンプルを示します。

Connection conn = null;
Statement stmt = null;
ResultSet rs = null;
//
// How many times do you want to retry the transaction
// (or at least _getting_ a connection)?
//
int retryCount = 5;
boolean transactionCompleted = false;
do {

  try {
    conn = getConnection(); // assume getting this from a
    // javax.sql.DataSource, or the
    // java.sql.DriverManager

    retryCount = 0;
    stmt = conn.createStatement();
    String query = "Some sample SQL";
    rs = stmt.executeQuery(query);
    while (rs.next()) {
    }
    rs.close();
    rs = null;
    stmt.close();
    stmt = null;

    conn.close();
    conn = null;
    transactionCompleted = true;
  } catch (SQLException sqlEx) {
    //
    // The two SQL states that are 'retry-able' 
    // for a communications error.
    //
    // Only retry if the error was due to a stale connection,
    // communications problem 
    //
    String sqlState = sqlEx.getSQLState();
    if ("Substitute with Your DB documented sqlstate number for stale connection".equals(sqlState) ) {
      retryCount--;
    } else {
      retryCount = 0;
    }
  } finally {
    if (rs != null) {
      try {
        rs.close();
      } catch (SQLException sqlEx) {
        // log this
      }
    }
    if (stmt != null) {
      try {
        stmt.close();
      } catch (SQLException sqlEx) {
        // log this
      }
    }
    if (conn != null) {
      try {
        //
        // If we got here, and conn is not null, the
        // transaction should be rolled back, as not
        // all work has been done
        try {
          conn.rollback();
        } finally {

          conn.close();
        }
      } catch (SQLException sqlEx) {
        //
        // If we got an exception here, something
        // pretty serious is going on, so we better
        // pass it up the stack, rather than just
        // logging it. . .
        throw sqlEx;
      }
    }
  }
} while (!transactionCompleted && (retryCount > 0));
于 2009-10-13T22:13:10.397 に答える
3

接続プールにこれを処理させてください。それらの多くは接続を検証できます。接続が使用される前に、すべての接続で健全性チェックを強制するパラメータを持つDBCPも同様です。testOnBorrowこのパラメータのデフォルト値は です。効果を得るには、null 以外の文字列に設定するtrue必要があります。validationQueryを設定してvalidationQueryください。ドキュメントを確認してください。

于 2009-10-13T21:48:43.520 に答える
1

Oracle の Universal Connection Pool (UCP) ライブラリを確認してください。これらは JDBC 4.0 に完全に準拠しておりisValid()、接続が有効かどうかを確認する呼び出しを実装しています。このチェックを行うのは簡単です。再接続が失敗した場合は、クエリを実行します。

Oracle UCP ダウンロード ページ

あなたが接続プールについて尋ねていないことは知っていますが、おそらく接続プールを使用しているはずなので、これは 2 つの助けになります。

于 2009-10-13T21:30:58.053 に答える