以下の説明は、説明のみを目的としていることに注意してください。問題は、akka でのイベント ストリーム処理のパターンに関するものであり、例示的な例を別の設計で解決する方法に関する問題ではありません。
イベント ルールがアクターによってモデル化されている、Akka で記述された複雑なイベント処理エンジンを想像してみてください。メッセージのイベント フローは、注文、注文内のアイテムのフルフィルメント、注文に対する支払いに似ています。ビジネス ルール アクターは、顧客への請求書発行と完了までの支払いの追跡に似た作業を行っています。ビジネス ルールが対象とするデータは本質的に非常に動的であり、どのルールがメッセージ ストリームのどの部分を追跡しているかを知ることはできません。
単純に、ボードキャスト ルーター スタイルのアプローチを使用できます。すべてのビジネス ルール アクターは、すべてのデータを確認し、追跡対象のデータでない場合はメッセージを無視します。ただし、すべてのルール アクターがすべてのデータにかなりの割合で関心を持っているわけではないため、これにはスケーラビリティの問題があります。これは、メッセージ内の複雑なビジネス識別子によって、どのルール アクターがどのタイプのメッセージを追跡しているかのインデックスを使用することを意味します。次に、ルール アクターに、彼らが探しているデータのみを送信できます。どのメッセージがどのアクターに送信されるかを示すこのインデックスは、アクター内のビジネス ルールに応じて変化します。これをルーティング アクターの観点から見ると、ルート先は動的にルートを変更したいと考えています。
これにより、タイミングの問題が発生します。ルーティング アクターが多くのルートをビジー状態に保つのに十分な速さで実行されている場合、特定のルートがメッセージ {A} を取得するまでに、{A,B,C} などのメッセージ ストリームを渡します。その後、そのルートがメッセージ {B} が必要であると判断した場合、メッセージ {A} を見てメッセージ {B} が必要であることを最近発見したルートのメールボックスにはルーティングされていません。変更されたルートは、{C} の後、またはルーティング アクターが特定のルートからの応答メッセージを処理するようになるずっと後のメッセージに対してのみ有効になります。
これに対する 1 つの解決策は、ルーティング アクターでメッセージをバッファリングすることです。その後、ルートがメッセージに応答して関心のあるものを変更した場合、ルーティング アクターは古いメッセージのバッファをスキャンし、必要に応じて一部を再送信できます。これは、メッセージのバッファーをできるだけ小さくして、メッセージをできるだけ効率的に再送信できるようにするための多くのコードを意味します。Akka 内で動的ルーティングを解決するための、より標準的なパターンまたはより自然なアプローチがあるかどうか疑問に思っています。
[脚注: コメントで説明されている別の解決策は、メッセージのキャッシュを使用し、ルール アクターにキャッシュをヒットさせることですが、メインの jdbc ストアで IO または 2 フェーズ コミットを強制するためにキャッシュが非常に大きくなる必要があると仮定します。回避できる場合、キャッシュは望ましくありません。質問は、ルーティング ルールが非常に動的な方法で変更される akka のイベント ストリーミング パターンに関するものです。上記のようなシステムのおおよその説明は単純化されており、説明のみを目的としています。重要なパラグラフは、メッセージ ストリーム {A,B,C} に関するものであり、{A} を読み取ったルートに、上流のルーターによって既にディスパッチされたメッセージ {B} が必要であると判断させることです。]