特定のフローで非同期にデータを消費および生成する必要がある分散処理ワーカーのセットを必要とするアプリケーションを設計しています。例えば:
- コンポーネント A はページをフェッチします。
- コンポーネント B は、A のページを分析します。
- コンポーネント C は、B からの分析された断片を保存します。
明らかに、関連するコンポーネントは 3 つだけではありません。
その他の要件:
- 各コンポーネントは、個別のプロセス (または一連のプロセス) である必要があります。
- 生産者は消費者について何も知りません。つまり、コンポーネント A はデータを生成するだけで、どのコンポーネントがそのデータを消費するかはわかりません。
これは、 Stormのようなトポロジ指向のシステムによって解決される一種のデータ フローです。Storm は良さそうに見えますが、私は懐疑的です。これは Java システムであり、Thrift をベースにしていますが、どちらも好きではありません。
私は現在、AMQP をデータ トランスポートとして使用し、HTTP をデータ共有/ストレージのプロトコルとして使用するパブ/サブ スタイルのアプローチに傾いています。これは、AMQP キュー モデルがパブリック API になることを意味します。つまり、コンシューマーは、プロデューサーが使用する AMQP ホストとキューを知る必要があります。これについては特に満足しているわけではありませんが、妥協する価値はあるかもしれません。
AMQP アプローチのもう 1 つの問題は、各コンポーネントが次のように非常に類似したロジックを持つ必要があることです。
- キューへの接続
- 接続エラーの処理
- データを共通の形式にシリアライズ/デシリアライズする
- 実際のワーカーの実行 (ゴルーチンまたはフォーク サブプロセス)
- ワーカーの動的スケーリング
- 耐障害性
- ノード登録
- 処理指標
- キューのスロットリング
- キューの優先順位付け (一部のワーカーは他のワーカーよりも重要度が低い)
…そして、各コンポーネントが必要とする他の多くの詳細。
コンシューマーが論理的に非常に単純であっても (MapReduce ジョブ、テキストをトークンに分割するようなものを考えてください)、ボイラープレートがたくさんあります。確かに、私はこれらすべてを自分で行うことができます — 私は AMQP やキュー、その他すべてに精通しています — すべてのコンポーネントで共有される共通のパッケージにこれらすべてをラップしますが、その場合はすでにフレームワークを発明する途中です。
この種のもののための良いフレームワークは存在しますか?
Goについて具体的に尋ねていることに注意してください。Hadoop と Java スタック全体を避けたい。
編集:明確にするためにいくつかのポイントを追加しました。