セロリ食べたい

とりあえず作りました

Kue をつかってみた

node.js でペロペロと遊んでいるのですが、以下のようなことをやりたいと思いました。

  • バックグラウンドで行いたい処理をキューに追加していって、それを順次実行したい
  • それをきれいに管理したい
  • 指定した時間が経過したあとに、遅れて処理を実行したい(5秒後にほにゃらら、みたいな)

パッケージでそんなものがないかと探してみると、Kue というものが見つかったので使ってみました。Kue ってなんて読むんだろう。くえ?きゅー?くー?

Kue は npm をつかって簡単にインストールできます。

npm install kue

Kue ではひとつの処理を job と呼んでいるみたいです。job の管理に redis を使うようなので、redis も使えるように設定しておく必要があります。homebrew なり MacPorts なりでインストールするとよいでしょう*1。ここではその手順は省略します。

僕は node.js のアプリケーションを coffeescript で書いているので、以下の例はすべて coffeescript のコードです。

まず、自分のアプリケーションで Kue を使えるようにモジュールを読み込み、createQueue関数でキューを作ります。さらに、'kue.app.listen 3000' と記述しておくと、ポート3000で Web インターフェイスが起動します。キューに追加した job や実行中の job の一覧がブラウザで確認できるので便利です。

kue = require 'kue'
jobs = kue.createQueue()

kue.app.listen 3000

Kue では job の実際の処理をキュー(jobs)の process という関数で設定します。process 関数では第一引数に job の名前を、最後の引数に処理内容を定義した関数を指定します。0.1秒ごとに100までカウントを増やす hoge job と fuga job を設定しました。この job はカウントをひとつ増やすたびに job に設定された値を console.log で出力します。job を設定するときには、一度にそのjobをいくつまで並行に動かしてよいか指定することができます。以下の例では、 fuga job を3つまで並行に動かしてよいと指定しています。

process = (job, done) ->
    progressMax = 100
    next = (i) ->
        console.log "#{job.data.title}(#{job.data.id}) [#{i}/#{progressMax}]"
        job.progress i, progressMax
        if i == progressMax
            done()
        else
            setTimeout ->
                next i+1
            , 100
    next 0

jobs.process 'hoge', process
jobs.process 'fuga', 3, process

以下のようにして job を登録します。キューの create 関数の引数には、作成する job の名前とそれに与える値をオブジェクトで指定します。job に起きたイベントに応じて実行したい処理を設定することもできます。以下の例では job が終了したら 'complete hoge' と標準出力に出力するようにしました。最後に save 関数を呼ぶことで、job が redis に登録されます。以下の例では hoge job を5つ登録しています。

jobs.create('hoge',
    title: 'hogehoge'
    id: i
).on('complete', ->
    console.log 'complete hoge'
).save() for i in [1..5]

遅れて実行したい job は以下のようにして登録できます。delay(5000) のようにdelay関数でミリ秒単位の遅延時間を指定するだけです。以下の例では、fuga job は5秒待ってから処理を実行します。遅延実行する job を登録した際は、遅延 job の確認を何ミリ秒おきに行うか、キューの promote 関数で指定する必要があります。引数に何も指定しないと5秒おきに確認します。以下の例では 100ミリ秒おきに確認するように指定しました。

jobs.create('fuga',
    title: 'fugafuga'
    id: i
).on('complete', ->
    console.log 'complete fuga'
).delay(5000).save() for i in [1..5]

jobs.promote 100 # default 5000(ms)

以上、簡単に Kue を使ってみたの例でした。コードは github においてあります。https://github.com/slightair/hello-kue

*1:関係ないですが僕はまだ MacPorts をつかっています。クリーンインストールをするタイミングで homebrew に移行するんだ!とずっと思っているのですが、なかなかその機会はやってきません。