How can I create nodes in tests?

Hey, I’m working on next release candidate for my library ExApi.

My main module ExApi uses GenServer and have server api with calls to __MODULE__, so I do not need to pass pid. I have implemented and tested in two iex sessions sending events across nodes.

> iex --sname first -S mix
Erlang/OTP 20 [erts-9.0] [source] [64-bit] [smp:4:4] [ds:4:4:10] [async-threads:10] [hipe] [kernel-poll:false]

Interactive Elixir (1.5.1) - press Ctrl+C to exit (type h() ENTER for help)
iex(first@localhost)1>
# now second node:
> iex --sname second -S mix
Erlang/OTP 20 [erts-9.0] [source] [64-bit] [smp:4:4] [ds:4:4:10] [async-threads:10] [hipe] [kernel-poll:false]

Interactive Elixir (1.5.1) - press Ctrl+C to exit (type h() ENTER for help)
iex(second@localhost)1> Node.connect(:"first@localhost")
iex(second@localhost)2> import ExApi.Api
iex(second@localhost)3> def_api MyApi, do: nil
# back to first node:
iex(first@localhost)1> import ExApi.Api
iex(first@localhost)2> def_api MyApi, do: nil
iex(first@localhost)3> ExApi.register_api(MyApi)
# and again 2nd node:
iex(second@localhost)4> {:ok, api} = ExApi.get(MyApi)
{:ok,
 %ExApi.Api{default_implementation: {nil, nil}, doc: "", features: %{},
  implementations: %{}, line: 3, module: MyApi, pid: #PID<0.196.0>}}

I would like to write a tests for it. Can you help me with this?

1 Like

Have a look at how Phoenix PubSub does it https://github.com/phoenixframework/phoenix_pubsub/blob/master/test/support/cluster.ex

4 Likes

@chrismcg: Thanks, just tried it in iex and it works! I have only one question related to it.
Is it possible to change this:

:rpc.block_call(node, Code, :eval_string, ["""
  import ExApi.Api
  def_api MyApi, do: nil
"""])

to 2 calls of :rpc.block_call/4 function?
From what I can see module (2nd argument) is always required, but maybe there is something that I forgot about.
Update: It’s easy to not use any eval functions. I can use simply :erlang.apply(function, args) in block_call.

2 Likes