次の方法で共有


パフォーマンスの高いアダプターをデザインする方法

アダプターのパフォーマンスを確保するには、すべてのアダプターを、メッセージのバッチの送信、バッチの転送、およびバッチ単位での一般的なメッセージ操作を実行可能なバッチ対応にしておく必要があります。 また、アダプターのパフォーマンス関連の属性 (バッチのサイズやバッチ内のバイト数など) をできる限り構成可能な属性として公開し、アダプターのデザイン時ユーザー インターフェイスで構成できるようにします。

前述したように、送信ホストのパフォーマンス低下を避けるため、送信アダプターは常に非ブロッキング送信を行う必要があります。 メッセージング エンジン API をさらにブロックすることはお勧めしません。

メッセージ コンテキストの書き込みと読み取りは、実行時のパフォーマンスに影響します。 通常は、アダプターでメッセージ コンテキスト プロパティの読み取り、書き込み、および昇格が発生しすぎないようにする必要があります。 プロパティを昇格させると、昇格させたプロパティごとに実行時にサブスクリプションの評価が行われるため、パフォーマンスがさらに低下します。 アダプターで昇格させるプロパティの数が膨大にならない限りパフォーマンスに著しい影響が及ぶことはありませんが、 昇格の必要なプロパティに限定して昇格させることをお勧めします。

送信と受信の制限

BizTalk エンジンの負荷がしきい値の構成値を超えると、最適なパフォーマンスを確保するためにエンジンによってアダプターとオーケストレーションが制限されます。 受信側では、エンジンのワークロードが特定のしきい値を超えると、負荷が十分に減少するまで、アダプターの IBTTransportBatch.Done の呼び出しがブロックされます。 これにより、アダプターからエンジンに新しい作業が送信されるのは、エンジンが使用可能な場合に限られることになります。 送信側では、アダプターによる送信メッセージの送信がエンジンによって制限されている場合は、負荷が減少するまで、エンジンから新たな送信メッセージが配信されなくなります。

このため、バックエンド システムへの接続数を制限するなどの必要が生じない限り、アダプターでの制限を考慮する必要はありません。 このようなシナリオについて、エンジンおよびアダプター フレームワークにおけるサポートは提供されていません。

カスタム送信アダプターから送信されるメッセージの数を制限するには、アダプターのソース コードを制御するかどうかに応じていくつかの方法があります。

送信側の制限によるパフォーマンス向上

アダプターのソース コードを制御する場合は、いつでも送信できるようキューに格納するメッセージの最大数をヒューリスティックによって決定できます。 メッセージング エンジンが メソッドをTransmitMessage呼び出して送信アダプターに新しいメッセージを渡す場合は、スレッドをブロックするか、チェックを選択して、キュー内のメッセージの数が前に決定した最大値より大きいかどうかを確認できます。 メッセージの最大数を超えた場合は、 メソッドを Resubmit 使用してメッセージをメッセージング エンジンに再送信できます。 同期アダプターの場合、メッセージはそれ以前にブロックされます。

アダプターのソース コードを制御しない場合は、BizTalk 管理データベースのAdm_serviceclass テーブルの Highwatermark 値を変更することで、キューに登録されたメッセージの数を変更できます。 Highwatermark プロパティの最大値は 200 です。 Lowwatermark プロパティの値を小さい値に変更することもできます。

非同期アダプターの Highwatermark プロパティの値は、メッセージング エンジンがアダプターに渡したメッセージの数を占める点に注意してください。 メッセージング エンジンは、 メソッドを介してTransmitMessageアダプターに渡します。これらのメッセージは、アダプターが、または Microsoft.BizTalk.TransportProxy.Interop.BatchOperationType.MoveToSuspendQ メソッドにDeleteMessageResubmitMoveToNextTransport対応する呼び出しを行っていない場合など、送信で未処理のままである可能性があります。 同期アダプターの場合、 Highwatermark プロパティは、この呼び出しが同期的に処理され、呼び出し元のメッセージング エンジン スレッドをブロックするため、 TransmitMessage メソッドを使用してメッセージング エンジンがアダプターに渡したメッセージの数のみを考慮します。

本質的に低速なプロトコル (HTTP、FTP、双方向の SOAP など) の送信アダプターを作成する場合は、次の点を考慮してください。

  • BizTalk メッセージング エンジンから送信されるメッセージをアダプターで受信する速度が、送信可能な速度を上回る可能性があります。 この速度の差は、さまざまなレベルの問題の原因になります。 送信中のメッセージがメモリに残って仮想メモリが占有され、システム全体の処理速度が低下します。

  • アダプターがプロトコル固有のリソースを占有する場合があります。 たとえば、サーバーに対して多数のコンカレント接続が行われると、リモート サーバーの処理が低下することがあります。

  • 他のアダプターにも影響が生じる可能性があります。 たとえば、特定のアダプターに対する多数のメッセージがキューに保存されると、メッセージング エンジンはそのプロセスの他の送信アダプターに対する要求の発行を停止します。

    解決方法としては、低速のアダプターと高速のアダプターを異なる BizTalk ホストに配置し、"High Watermark" および "Low Watermark" の設定を使用してメッセージの数を制御する方法があります。

受信側の制限によるパフォーマンス向上

受信アダプターのメッセージ受信速度が、システムの他の部分におけるメッセージ処理速度を上回る状況は多数存在します。 このような状況では、メッセージ ボックス データベースでバックログが発生します。 この場合、システム全体のパフォーマンスが大幅に低下します。

アダプターでこの現象が発生した場合は、次のいずれかの方法で受信アダプターの速度を下げることができます。

  • メッセージング エンジンのスレッド プールのサイズを小さくします。 メッセージをメッセージ ボックスに公開するためにメッセージング エンジンが使用するスレッドの数を制御することができます。 スレッドの数を減らすことで、受信アダプターがメッセージ ボックスにメッセージを取り込む速度を下げることができます。 この設定を適用する必要があるのは、アダプターの受信ハンドラーに対応するホストのみです。 送信アダプターの速度も下げる必要がある場合を除き、アダプターの送信ハンドラーに対応するホストにはこの設定を適用しないでください。

  • アダプターのバッチ サイズを小さくします。 高速の受信アダプターの大多数は、メッセージをバッチ単位でメッセージ ボックスに公開します。 通常、これらのバッチのサイズは受信場所のプロパティ ページで構成できます。 バッチ サイズを小さくすることで、システムに入ってくるメッセージ全体のスループットを下げることができます。

  • その他のアダプター固有の設定を変更します。 上記の 2 つの手順が完了したら、アダプターの他のパラメーターを調整することでスループットをさらに下げられるかどうか試してみます。 アダプターの中には、スループットを下げるために使用できる内部パラメーターを公開しているものがあります。 たとえば、MQSeries アダプターには "順次配送" に関する設定があります。 順次配送とは、アダプターがメッセージのバッチを 1 つずつ公開し、1 つのバッチの処理が完了するのを待って次のバッチを公開することを示します。 この設定を有効にすると、該当する受信アダプターでは実質的に並列処理が行われなくなります。 逆に、パラメーターを逆方向に調整することで、受信アダプターの受信速度を上げることもできます。

    アダプターは、必要な数だけバッチをトランスポート プロキシに送信できます。 システムに大きな負荷がかかっている場合、IBTTransportBatch インターフェイスの Done メソッドを呼び出すと、必要なリソースがシステムに解放されるまでメッセージがブロックされます。

非同期の送受信への対応

BizTalk Server メッセージング API には、非同期プログラミングをサポートするさまざまな機能があります。 スケーラブルなアダプターを作成するには、当初からコンカレンシーの高い非同期モデルの使用を検討してください。

受信側では、アダプターが ( IBTTransportBatch::D one を呼び出して) BizTalk メッセージング エンジンにメッセージのバッチを送信すると、メッセージング エンジンは内部スレッド プールを使用して作業をキューに入れ、直ちに返します。 エンジンはメッセージを別のスレッドで処理するため、アダプターはソースからさらにメッセージを読み取って、前のメッセージの処理が完了するのを待たずに送信することができます。

送信側のアダプターは非同期でも同期でもかまいません。 ただし、プロトコルで非同期操作がサポートされている場合は、そのサポートを利用してスケーラブルなアダプターを作成するようにしてください。 たとえば、ファイル送信アダプターと HTTP 送信アダプターは完全に非同期であり、ブロック操作や同期操作はほとんど実行されません。

非同期操作では、メッセージング エンジンとアダプターの両方の作業が並行して続行されるようになっており、通常のメッセージ処理で相互の作業完了を待機することはありません。

バッチ処理によるパフォーマンス向上

スケーラブルなアダプターを作成するには、まずバッチ処理から取り組むのが最も有効です。 これは、送信側と受信側の両方のアダプターに該当します。 アダプターが非トランザクション アダプターであっても、各バッチは BizTalk Server 内のデータベース トランザクションで処理されます。 トランザクションごとに一定の遅延が発生するため、複数の操作を 1 つのバッチにまとめることによってトランザクションの数を最小限に抑える必要があります。

.NET スレッド プールの枯渇の回避

BizTalk アダプターの作成は .NET ランタイム コードの記述の一環であり、.NET ランタイム コードの記述は常に非同期プログラミングの一環です。

.NET における非同期プログラミングには .NET スレッド プールの枯渇のリスクが生じます。このリスクを回避することは BizTalk アダプターのプログラマにとって特に重要です。

.NET スレッド プールは、限られたリソースでありながら広く共有されています。 .NET スレッド プールのスレッドの 1 つを使用して長時間保持し、他の作業項目の実行をブロックするコードを書くのは簡単です。

BeginInvoke を使用するか、タイマーを使用するたびに、.NET スレッド プール スレッドを使用します。 複数の作業がある場合 (たとえば、MQSeries からメッセージをBizTalk Serverにコピーする場合)、1 つの作業項目 (BizTalk Serverへのメッセージの 1 つのバッチ) を実行し、さらに作業が必要な場合はスレッド プールでキューに入れ直す必要があります。 スレッド上の while ループに座ってはいけません。

具体的には、これはループを BeginInvoke への繰り返し呼び出しに置き換えることをwhile意味します。 この単純な変更により、実装全体の応答性と拡張性が大幅に向上する可能性があります。

バッチ サイズの制限に適した単位の選択

メッセージをバッチ単位で BizTalk Server に送信する場合、メッセージ数のみに基づいてバッチ サイズを制限しないようにしてください。 メッセージ数のみに基づいてバッチ処理するようにアダプターが構成されている場合の動作を検討してください。バッチ サイズが 2 で、アダプターがそれぞれサイズ 4 KB、8 KB、1 MB、5 MB の 4 つのメッセージを取得する場合、最初のバッチはサイズ 12 KB、2 番目のバッチはサイズ 6 MB になります。

BizTalk メッセージング エンジンは各バッチのすべてのメッセージを順に処理するため、この例の 2 つ目のバッチの処理速度は 1 つ目のバッチに比べて大幅に低下します。 これは実質的にスループットの低下をもたらします。 このような問題への対処としては、バッチのメッセージ数と合計バイト数 (バイト単位のバッチ サイズ) の両方に基づくバッチ処理の方が優れています。 適切な合計バイト数は場合によって異なりますが、 通常の処理シナリオでは、バッチ サイズが 1 MB を超えるとコンカレンシーとスループットの低下が始まります。

一般に、アダプターではメッセージは区別されず、実稼働環境でのメッセージのサイズは認識されません。 通常、受信メッセージによってサイズは大幅に異なります。 このため、常にメッセージ数と合計バイト数に基づいてバッチを作成するようにしてください。