Edited at

ElixirのexrmライブラリのRPC機能

More than 3 years have passed since last update.

Elixirのexrmライブラリはプロジェクトのリリースを作成してくれるライブラリで、その中にRPCリモート呼び出し機能があります。この機能は動いているプログラム中の定義されている関数を呼び出すことができます。これはとても役に立つ機能で、例えば、一つのgen_fsmプロセスAがあって、このプロセスは三つの状態idle, calculating, pausedがあるとして, 普段プロセスAidleの状態で、イベントが送られてきたら、calculatingに変わって,何かを計算し始めわけです。ある時に、手動でコマンドラインからイベントを送りたいです. この場合はもう一個のBatchモジュールを定義して、このBatchモジュールの中にstart/1という関数を作成します. start/1関数にgen_fsm:sync_send_eventを呼びだしてAプロセスにメッセージを送ります.start/1関数にKeyword listを渡したい場合,例えば、

start([recalc: true, buckets: [{"key1", "value1"}, {"key2", "value2"}])

上の引数は一つのKeyword Listで,問題はOptionParser使わずに, どうやってコマンドラインでこの複雑のkeyword listを渡すのでしょう。結論からいうと、こんな感じです。

$ rel/my_app/bin/my_app rpc Elixir.MyApp.Batch start "[[{'recalc', 'true'}, {'buckets', [{<<\"key1\">>, <<\"value1\">>},{<<\"key2\">>, <<\"value2\">>}]}]]."

options is [recalc: true, buckets: [{"key1", "value1"}, {"key2", "value2"}]]

options is list true, length is 2

以下は自分の少しずつ試した結果で、説明はなかかな難しいです。Elixirのモジュールを呼び出すときにElixir.をつける必要があります。 参照できるリンクここにしかないようです。

$ rel/my_app/bin/my_app rpc Elixir.MyApp.Batch start "['1']."

options is :"1"
options is atom true

$ rel/my_app/bin/my_app rpc Elixir.MyApp.Batch start "[\"1\"]."
options is '1'
options is list true

$ rel/my_app/bin/my_app rpc Elixir.MyApp.Batch start "\"1\"."
options is 49
options is integer true

$ rel/my_app/bin/my_app rpc Elixir.MyApp.Batch start "[\"1, 2\"]."
options is '1, 2'
options is list true

$ rel/my_app/bin/my_app rpc Elixir.MyApp.Batch start "[\"{recalc: 2}\"]."
options is '{recalc: 2}'
options is list true

$ rel/my_app/bin/my_app rpc Elixir.MyApp.Batch start "[\"[recalc: 2, only_buckets: [{key1, value1}, {key1, value2}]}\"]."
options is '[recalc: 2, only_buckets: [{key1, value1}, {key1, value2}]}'
options is list true, length is 59 <----このは59文字だけ

$ rel/my_app/bin/my_app rpc Elixir.MyApp.Batch start "[{'aaa'}]."
options is {:aaa}
options is tuple true

$ rel/my_app/bin/my_app rpc Elixir.MyApp.Batch start "[[{'aaa', \"bbb\"}, {'ccc', \"ddd\"}]]."
options is [aaa: 'bbb', ccc: 'ddd']
options is list true

$ rel/riakcscalc/bin/riakcscalc rpc Elixir.MyApp.Batch start "[[{<<\"aaa\">>, \"bbb\"}, {'ccc', \"ddd\"}]]."
options is [{"aaa", 'bbb'}, {:ccc, 'ddd'}]
options is list true, length is 2 <-- 長さみて,ちゃんとリストとして渡している

$ rel/my_app/bin/my_app rpc Elixir.MyApp.Batch start "[[{<<\"aaa\">>, <<\"bbb\">>}, {<<\"ccc\">>, <<\"ddd\">>}]]."
options is [{"aaa", "bbb"}, {"ccc", "ddd"}]
options is list true, length is 2

$ rel/my_app/bin/my_app rpc Elixir.MyApp.Batch start "[[{'recalc', 'true'}, {'buckets', [{<<\"key1\">>, <<\"value1\">>},{<<\"key2\">>, <<\"value2\">>}]}]]."
options is [recalc: true, buckets: [{"key1", "value1"}, {"key2", "value2"}]]
options is list true, length is 2