RE: 非同期ジョブキューのアーキテクチャ設計、どうしてますか?

http://d.hatena.ne.jp/a666666/20101027/1288117907

少しだけ言及されてたので、自分の回答を書いておきますね。

刺身さんのエントリは、

  • 非同期リクエストへの非同期の応答の仕方
  • 非同期処理のキャンセルの仕方

の二つの問題を話しているように思うので、問題を少し分けてみます。

非同期リクエストへの非同期の応答の仕方

1つ目の問題は、リサイズと顔認識が十分に早いという前提に立てば、1つのworkerで処理をするのがいいでしょうね。で、Web App側がブロックしないように、Web App側からは非同期でタスクを登録するのがいいんじゃないかなと。それで、処理結果を別のキュー(またはmemcached)にいれてから、クライアント側(jsなど)でポーリングして、キューから取り出して結果表示するのがいいんじゃないでしょうか。こうするとで、Web App側はブロックせずに次の処理をすることができます。

これは非同期のrequest-reply patternといわれるもので、Enterprise Integration Patternに書かれています。 http://www.eaipatterns.com/RequestReply.html
Enterprise Integration Patternsは、非同期処理の基本的なパターンをまとめている良書なので、興味があればぜひ。

ただ、1番目の問題も、これは要求される応答性能次第でいろいろな設計方法がありえて、リサイズと顔画像認識の処理が両方遅い場合には、workerを分けて処理する必要があると思うんですが、これはまた話が膨らみそうなので、また別の機会に。

非同期処理のキャンセルの仕方

続いて、2番目の問題の非同期処理のキャンセルです。これはgearmanの機能不足の問題なので、gearmanに手をいれるか、はたまた別のキュー実装を使うのがいいんじゃないでしょうか。

ただ、一般に非同期job ququeからキャンセルしようとすると、結構コードが複雑になります。 キャンセルしようと思ったら、既にキューにはなくて、クライアントにレスポンス返す寸前だったりなどの、入れ違いがおこりうるからです。この問題についても、Enterprise Integration Patternはいくつか設計のパターンを示してくれているので、参考にされるといいんじゃないかと思います。

# 僕の感想では、あまりSEDAの話とは関係がないかな?という気もするんですが、一応自分の回答を書いてみました