2

Azure 環境で一時的なエラーから回復するための再試行ロジックを実装しようとしています。

長時間実行されるセッションを使用して、アプリケーション トランザクション (複数の Web リクエストにまたがる可能性があります) の最後に一連の変更を追跡およびコミットしています。途中で、データベースから追​​加のデータを取得する必要があります。私たちの主な問題は、すべてのユーザー アクションを「再生」できないため、db エラーから簡単に回復できないことです。

ここまでは、単純な回復アルゴリズムを使用しました。

  • 実行時間の長いセッションで操作を実行してみてください
  • エラーが発生した場合は、セッションを閉じ、新しいセッションを開いてエンティティをマージします
  • 操作を再試行してください

これは、時間の点で非常にコストのかかるアプローチです (大きなエンティティ階層の場合、マージは非常に長くなります)。そこで、少し最適化を行いたいと思います。

別のセッションでクエリ操作を実行し (長時間実行されているものを手付かずで安全に保つため)、成功したら結果を長時間実行セッションにマージしたいと考えています。ここでの再試行は比較的簡単です。新しいセッションを開いてクエリをもう一度実行するだけです。ただし、このアプローチでは、遅延プロパティ/コレクションの初期化に問題があります。

  • これを別のセッションで行う場合、結果 (多数のエンティティ) をマージして戻す必要がありますが、マージが失敗し、実行時間の長いセッションが中断される可能性があります
  • 元のエンティティを別のセッションに「移動」し、詳細をロードして元に戻すさまざまな方法を試しましたが、成功しませんでした (エビクト、複製など)。

例外が発生した場合にセッションを破棄する必要があるという既知のステートメントがあります。ただし、例は書き込み動作を示しています。読んだものにはまだ当てはまりますか?データベースにデータが書き戻されないことを保証する場合、同じセッションを再利用してクエリを再度実行できますか?

長時間実行されるセッションでの再試行ロジックについて他に何か提案はありますか?

4

1 に答える 1

1

IMO あなたの問題を解決する方法はありません。すべてをコミットするには多くの時間がかかるか、小さなセッションに分割してマージ中に発生する可能性のあるすべてのエラーを処理するために多くの作業を行う必要があります。

例外後のセッションの使用に関する質問に答えるには、このセッション内では何も信頼できず、読み込まれたエンティティでさえも信頼できません。

セッションで例外が発生した場合の復旧計画を備えた単純な todo アプリの構築に関するAyende の記事から、次の段落をお読みください。

次に、エラー処理の問題があります。例外 (同時実行の競合による StaleObjectStateException など) が発生した場合、NHibernate では、セッションからスローされた例外がそのセッションを未定義の状態に移動するため、セッションとその読み込まれたエンティティは乾杯します。そのセッションまたは読み込まれたエンティティは使用できなくなります。グローバル セッションが 1 つしかない場合は、おそらくアプリケーションを再起動する必要があることを意味しますが、これはおそらく良い考えではありません。

于 2013-06-12T07:26:50.560 に答える