Kestrel は Message Queue (MQ) の実装のひとつです。一般に MQ はアプリケーション間やプロセス間、スレッド間で非同期に通信するために用いられます。メッセージの送信側は MQ に書き込めば受信側の応答を待たずに次の処理に非同期に進むことができます。Kestrel はわずか 2500 行程の Scala で実装されており JVM で動作します。MQ 自体はメモリ上に存在するため高速にアクセスでき、永続化のためジャーナルファイルにも同じ情報が書き込まれているため再起動などが発生してもデータの消失なく復旧可能です。複数の Kestrel MQ をクラスタ構成にすることもできます。Kestrel では Memcache のクラスタ構成と同様にお互いのキューは独立しており互いに通信しないため、無限にスケールできます。一方で、各キュー単体では FIFO になっていますがクラスタ全体では FIFO になっているとは限りません。memcache プロトコルまたは RPC (remote procedure call) フレームワーク Apache Thrift で利用される thrift プロトコルが利用できます。
ダウンロード
こちらから最新のものをダウンロードします。
インストール
解凍してシンボリックリンクを作成します。
$ unzip kestrel-2.4.1.zip
$ sudo mkdir /usr/local/kestrel
$ sudo mv kestrel-2.4.1 /usr/local/kestrel/
$ sudo chown -R root: /usr/local/kestrel
$ sudo ln -s /usr/local/kestrel/kestrel-2.4.1 /usr/local/kestrel/current
動作させるためには Java 6 が必要です。
$ sudo yum install java-1.6.0-openjdk-devel
Kestrel で利用されている Scala のバージョンがやや古いため、起動時に Scala のコンフィグファイルを動的に Eval する際に例えば Java 8 では以下のようなエラーが発生します。
$ cat /var/log/kestrel/error
FATAL: Error in config file: %s
java.lang.UnsupportedOperationException: Position.line
...
JAVA_HOME
の設定を行います。
$ ls -l /usr/bin/javac
lrwxrwxrwx. 1 root root 22 Jun 6 15:53 /usr/bin/javac -> /etc/alternatives/javac
$ ls -l /etc/alternatives/javac
lrwxrwxrwx. 1 root root 73 Jun 6 15:53 /etc/alternatives/javac -> /usr/lib/jvm/java-1.6.0-openjdk.x86_64/bin/javac
$ sudo vi /etc/environment
$ export JAVA_HOME=/usr/lib/jvm/java-1.6.0-openjdk.x86_64
$ source /etc/environment
起動用のスクリプトへのリンクを作成します。
$ sudo ln -s /usr/local/kestrel/current/scripts/kestrel.sh /etc/init.d/kestrel
$ sudo chmod +x /etc/init.d/kestrel
chkconfig には登録できません。
$ sudo chkconfig --add kestrel
service kestrel does not support chkconfig
PID ファイルおよびログファイルの書き込み用ディレクトリを作成します。
$ sudo mkdir /var/run/kestrel
$ sudo mkdir /var/log/kestrel
起動します。
$ sudo /etc/init.d/kestrel start
メモリが不足している場合などは失敗します。以下のようなエラーが出力されています。
$ cat /var/log/kestrel/stdout
Error occurred during initialization of VM
Could not reserve enough space for object heap
例えばメモリ割り当て量を減らすことで対応できます。
$ sudo vi /etc/init.d/kestrel
#HEAP_OPTS="-Xmx4096m -Xms4096m -XX:NewSize=768m"
HEAP_OPTS="-Xmx1024m -Xms1024m -XX:NewSize=512m"
起動したことを確認します。
$ sudo jps -m
3656 Jps -m
3573 kestrel_2.9.2-2.4.1.jar
動作検証
memcache プロトコルで通信してみます。
$ telnet localhost 22133
...
stats ←統計情報
STAT uptime 213
STAT time 1433658666
STAT version 2.4.1
STAT curr_items 0 ←現在のキューの長さ
STAT total_items 0
STAT bytes 0
STAT reserved_memory_ratio 0.000
STAT curr_connections 1
STAT total_connections 2
STAT cmd_get 0
STAT cmd_set 0
STAT cmd_peek 0
STAT get_hits 0
STAT get_misses 0
STAT bytes_read 13
STAT bytes_written 14
STAT queue_creates 0
STAT queue_deletes 0
STAT queue_expires 0
set hello 0 0 3 ←値の格納
123
STORED
get hello ←値の取得 (MQ なので memcache と異なり一回取得されると消える)
VALUE hello 0 3
123
END
get hello ←値の取得 (空っぽ)
END
quit ←終了します
同封されているテストスクリプト を実行すれば性能を試験できます。
$ sudo chmod -R +x /usr/local/kestrel/current/scripts
$ /usr/local/kestrel/current/scripts/load/put-many -n 100000
$ /usr/local/kestrel/current/scripts/load/many-clients
$ /usr/local/kestrel/current/scripts/load/flood
$ /usr/local/kestrel/current/scripts/load/packing -c 10 -q small
$ /usr/local/kestrel/current/scripts/load/leaky-reader -n 100000 -t 10
補足
Finagle Kestrel クライアントについて
上述の通り Kestrel では memcache プロトコルまたは thrift プロトコルが利用できるため Scala に限らず様々な言語で実装したクライアントから扱えます。特に Scala で Kestrel クライアントを実装する場合には Finagle Kestrel クライアントの利用を検討するとよいかもしれません。Finagle は RPC を利用したシステムを作るためのフレームワークです。Scala で実装されています。memcache, http, kestrel(memcache) など様々なプロトコルをサポートしています。
〜間通信
- Scala アクター (スレッド間、同期・非同期)
- HTTP (アプリケーション間、プロセス間、同期、遅延が大きいとスプリットブレインの原因になる)
- その他 RPC (アプリケーション間、プロセス間、同期・非同期)
- Kestrel 等の MQ (アプリケーション間、プロセス間、非同期)
関連記事
- Spring Security フォームログインのサンプルコードSpring フレームワークによる Web アプリケーション開発で、ログイン処理を実装する際は Spring Security が便利です。ここでは特に Spring Boot で Web アプリケーションを開発する場合を対象とし、フォームによる ID/Password ログインを行うためのサンプルコードをまとめます。 公式ドキュメント [Spring Security チュートリアル](http...
- Java配列の宣言方法 (C/C++との違い)Javaの配列 Javaの配列宣言方法はC/C++と似ているようで若干異なる。 初期化しない場合 C/C++の int array[10]; はJavaでは int array[] = new int[10]; となる。同様にC/C++の int array[3][3]; はJavaでは int array[][] = new int[3][3]; となる。 初期化
- PlantUML による UML 図の描き方PlantUML はテキスト形式で表現されたシーケンス図やクラス図といった UML (Unified Modeling Language) 図の情報から画像を生成するためのツールです。簡単な使い方をまとめます。 インストール方法の選択 Atom や Eclipse のプラグインをインストールしてエディタから利用する方法、JAR をダウンロードして Java コマンドで実行する方法、Redmine ...
- Akka HTTP サンプルコード (Scala)Akka アクターを用いて実装された汎用 HTTP フレームワークです。Spray の後継です。コアモジュールである akka-http-core は 2016/2/17 に experimental が外れました。akka-http などのいくつかのサブモジュールは 2016/3/1 現在 experimental のままですが、基本的な
- Android Activity ライフサイクルの様子を把握するための簡易サンプルコードAndroid アプリケーションのコンポーネントの一つである Activity についてライフサイクルの様子を把握するための簡易サンプルコードです。 The Activity Lifecycle [ライフサイクルの状態遷移図](https://developer.android.com/guide/components/