この記事は、主にJavaプログラミングの詳細な説明を再試行メカニズムの例と共有する関連コードの例を研究しています。編集者は、それが非常に良いと考えており、特定の参照値を持っています。それを必要とする友達はそれを参照できます。
アプリケーションに関数を実装する必要があります。データはリモートストレージサービスにアップロードする必要があり、返品処理が成功したときにその他の操作が実行されます。この関数は複雑ではなく、2つのステップに分かれています。最初のステップは、リモートレストサービスロジックラッパーを呼び出して処理結果を処理方法に返すことです。 2番目のステップは、最初のステップの結果を取得するか、例外をキャッチすることです。エラーまたは例外が発生した場合、アップロードロジックが再試行されます。そうしないと、論理操作が継続されます。
通常のアップロードロジックに基づいて、関数ロジックは、戻り結果が結果であるか、例外決定を聞いているかを判断することにより実行されます。同時に、即時再試行の無効な実行を解決するために(例外が外部実行の不安定性によって引き起こされると仮定して)、関数ロジックは特定の遅延時間の再測定です。
public void commonretry(map <string、object> datamap)arturtedexception {map <string、object> parammap = maps.newhashmap(); parammap.put( "tablename"、 "creativetable"); parammap.put( "ds"、 "20160220"); parammap.put( "datamap"、datamap); boolean result = false; try {result = uploadtoodps(parammap); if(!result){thread.sleep(1000); uploadtoodps(parammap); //一度試してください}} catch(例外e){thread.sleep(1000); uploadtoodps(parammap); //一度試してみてください}}上記のソリューションは、再試行に対してまだ無効である可能性があります。この問題を解決するために、再試行カウントと再試行間隔を増やして、再試行を有効にする可能性を達成するようにしてください。
public void commonretry(map <string、object> datamap)arturtedexception {map <string、object> parammap = maps.newhashmap(); parammap.put( "tablename"、 "creativetable"); parammap.put( "ds"、 "20160220"); parammap.put( "datamap"、datamap); boolean result = false; try {result = uploadtoodps(parammap); if(!result){reuploadtoodps(parammap、1000l、10); //多重retry}} catch(例外e){reuploadtoodps(parammap、1000l、10); //多重retry}}}}}}ソリューション1とソリューション2には問題があります。通常のロジックと再試行ロジックが強く結合されています。 Retry Logicは、通常のロジックの実行結果に非常に依存しており、通常のロジックの予想される結果のパッシブ再試行がトリガーされます。再試行の根本原因は、しばしば複雑なロジックに圧倒され、その後の運用とメンテナンスのために解決する問題の一貫性のない理解につながる可能性があります。再試行を保証することは困難であり、動作とメンテナンスを助長しません。これは、再試行設計は通常の論理例外に依存しているか、推測の根本原因を再試行するからです。
したがって、通常のロジックを分離してロジックを再試行するために使用できるソリューションはありますか?同時に、retryロジックに標準化されたソリューションを与えることができますか?答えは次のとおりです。つまり、エージェントの設計パターンに基づいた再試行ツールです。対応するツールを使用して、上記のシナリオを再構築しようとします。
コマンド設計パターンの特定の定義は説明されていません。主な理由は、コマンドパターンがオブジェクトを実行してインターフェイス操作ロジックを完了できることであり、同時に、再試行ロジックの内部カプセル化が実装の詳細にさらされないことです。発信者にとって、それは通常のロジックの実行であり、デカップリングの目標を達成します。特定の関数実装をご覧ください。 (クラス図構造)
IRETRYは、OdpsTretryのようなカプセル化を実装するアップロードおよび再試行インターフェイスに同意し、ODPのアップロードロジックをカプセル化し、再試行メカニズムと再試行戦略を同時にカプセル化します。同時に、回復方法を使用して、最後に回復操作を実行します。
発信者の論理clientは、再試行に注意を払う必要はありません。 Retryer Retryerを介してコンベンションインターフェイス機能を実装します。同時に、再生者は応答してRetryロジックを処理する必要があります。リトライヤーの特定の再試行処理は、実際のIrry Interface実装クラスodpsretryに引き渡されます。コマンドモードを採用することにより、通常のロジックとリトリーロジックはエレガントに分離され、同時に、再生者の役割を構築することにより、通常のロジックとリトイロジックが分離され、再試行がより良いスケーラビリティを備えています。
Spring-Retryはオープンソースのツールキットで、現在利用可能なバージョン1.1.2.Releaseであり、再試行操作テンプレートをカスタマイズし、再試行ポリシーとフォールバックポリシーを設定できます。同時に、スレッドの安全性を確保するために実行インスタンスを再試行します。特定の操作の例は次のとおりです。
public void upload(final Map <string、object> map)Strows Exception {// Retry TemplateインスタンスRetryTemplate retryTemplate = new RetryTemplate(); // retryポリシーを設定し、主にretries simpleretrypolicyポリシーの数を設定します= new simpleretrypolicy(3、collections。<class <?extends throwable>、boolean> singletonmap(exception.class、true)); //再試行フォールバック操作ポリシーを設定し、主に再試行間隔を設定しましたfixedbackoffpolicy sixedbackoffpolicy = new sixedbackoffpolicy(); sixedbackoffpolicy.setbackoffperiod(100); retrytemplate.setretrypolicy(ポリシー); retrytemplate.setbackOffpolicy(fixedbackoffpolicy); // retryCallbackコールバックインスタンスを再試行して通常のロジックロジックをラップすると、最初の実行と再試行の実行はすべてこのロジックであり、最終的なRetryCallback <オブジェクト、例外> retryCallback = new retrycallback <オブジェクト、例外>() system.out.println( "do sonthing");例外e = uploadtoodps(map); system.out.println(context.getRetryCount()); e; //この点に特に注意を払ってください。再試行のルートは、例外によって返されます}}; //再試行プロセスを取得すると、通常は上限が再制限されるか、到達します。 final RecoveryCallback <Object> RecoveryCallback = new RecoveryCallback <Object>(){public Object Recover(RetryContextコンテキスト)スロー{System.out.println( "Do Recovery操作"); nullを返します。 }}; try {// retryTemplateで実行メソッドを実行して、retrytemplate.executeの論理実行を開始します(retrycallback、RecoveryCallback); } catch(Exception e){e.printstacktrace(); }}ケースコードの簡単な分析の後、RetryTemplateは再生執行者の役割を引き受けます。 SimpleretryPolicy(再試行ポリシー、上限の再制限を設定し、ルートエンティティを再試行)、固定BackOffpolicy(Fixed Fallbackポリシー、再試行フォールバックの時間間隔を設定)を設定できます。 RetryTemplateは実行を通じて操作を実行し、2つのクラスのインスタンス、RecryCallbackの2つのクラスインスタンスが2つのクラスインスタンスを準備する必要があります。前者は、再試行コールバックロジックインスタンスに対応し、通常の機能操作をラップします。 RecoveryCallbackは、実行操作全体の終了時に回復操作インスタンスを実装します。
retryTemplateの実行はスレッドセーフであり、実装ロジックはthreadlocalを使用して、各実行インスタンスのretrycontext実行コンテキストを保存します。
Spring-Retry ToolはRetryをエレガントに実装できますが、2つの非友好的なデザインがあります。1つは、Retryエンティティがスロー可能なサブクラスに限定されていることを示しています。もう1つは、根本原因を再試行するアサーションオブジェクトです。これは、通常の内部アサーションのリターンデザインに準拠していないDowithretryの例外インスタンスを使用します。
Spring Retryは、注釈の再試行方法を支持します。再試行ロジックは同期的に実行されます。再試行の「失敗」は、スロー可能なものです。返品値の特定の状態に基づいて再試行する必要があるかどうかを判断したい場合は、返品値を自分で判断し、例外を明示的に投げることができる場合があります。
再試行のための春の抽象化
「要約」は、すべてのプログラマーにとって必要な品質です。平凡な資格を持っている私にとっては、優れたソースコードを模倣して理解するよりも改善するためのより良い方法はありません。これを行うには、そのコアロジックを書き直します...「再試行」のためのSpring Retryの抽象化を見てみましょう。
春の再試行関連インターフェイス
Guava Retryerツールは、Spring-Retryに似ています。再生者の役割を定義することにより、通常の論理再試行をラップします。ただし、Guava Retryerにはより良いポリシー定義があります。再試行時間の数と再試行周波数制御をサポートすることに基づいて、複数の例外またはカスタムエンティティオブジェクトをサポートする再生ソース定義と互換性があり、再試行機能により柔軟性が向上します。 Guava Retryerもスレッドセーフです。エントリコールロジックは、java.util.concurrent.callableの呼び出し方式を使用します。サンプルコードは次のとおりです。
public void uploadodps(最終マップ<string、object> map){// retryerbuilder retryerbuilder build a retry instance retryer、複数の再試行ソースをサポートすることができます。また、再試行時間の数を構成するか、タイムアウト時間を再試行できます。 .retryifexception()。 .withStopStrategy(stopstrategies.stopafterattempt(5))// retryを5回設定すると、retryタイムアウト時間を設定することもできます。 java.util.concurrent.callable <v>、したがって、実行はスレッドセーフboolean result = retryer.call(new callable <boolean>(){@override public boolean call()try {// special note:return false statement nectry retry retry retry retry retry retry retry retry retry retry retry retry retry retry retry retry retry retry excuntion extry neection(例外(e);}}); } catch(executionexception e){} catch(retryexception ex){}}サンプルコード原則分析:
Retryerbuilderは、再試行ソースをカスタマイズできる工場作成者であり、複数の再試行ソースをサポートし、再試行時間の数を構成したり、タイムアウトを再試行したり、順番時間間隔を構成して再生者の再生インスタンスを作成できます。
RetryerBuilderのRetryソースは、例外オブジェクトとカスタムアサーションオブジェクトをサポートし、RetryifexceptionとRetryifresultを通じて設定されているため、複数をサポートし、同時に互換性があります。
RetryerBuilderの待機時間とRetry制限構成は、異なるポリシークラスを使用して実装され、待機時間機能は介入および固定インターバルモードをサポートできます。
RetryerはRetryerのインスタンスであり、コールメソッドを介して操作ロジックを実行し、Retryソース操作をカプセル化します。
エレガントな再試行の共通性と原則
正常で再retryエレガントにデカップされているため、条件付きインスタンスまたは論理例外インスタンスが2つの間の通信の媒体であると主張して再試行します。
再試行間隔、差別的な再試行戦略、および再試行タイムアウト時間を設定して、再試行の有効性と再試行プロセスの安定性をさらに確保することに同意します。
すべてがコマンド設計パターンを使用し、対応する論理操作はRetryオブジェクトを委任することで完了し、Retryロジックは内部的に実装されます。
Spring-TryerとGuava-Tryerツールはどちらもスレッドセーフ再試行であり、同時ビジネスシナリオでの再試行ロジックの正確性をサポートできます。
優雅に再試行するための適用可能なシナリオ
機能ロジックには不安定な依存関係シナリオがあり、再試行を使用して予想される結果を取得するか、すぐに終了せずにロジックを再測定しようとする必要があります。たとえば、リモートインターフェイスアクセス、データロードアクセス、データのアップロード検証など。
例外シナリオのために再試行する必要があるシナリオがあり、同時に、通常のロジックと再試行ロジックを分離することが望まれます。
データメディアに基づいた相互作用の場合、再試行スキームは、実行ロジックを検出するために投票を再試行する必要があるシナリオでも考慮することができます。
上記は、Javaプログラミング再試行メカニズムの例のすべての詳細な説明です。私はそれが誰にでも役立つことを願っています。興味のある友人は、このサイトの他の関連トピックを引き続き参照できます。欠点がある場合は、それを指摘するためにメッセージを残してください。このサイトへのご支援をありがとうございました!