Assert Linked Process Raised Error
Linked processes bubble up errors, but not in a way that you can catch with rescue
:
test "catch child process error?" do
spawn_link(fn ->
raise "3RA1N1AC"
end)
rescue
e in RuntimeError ->
IO.puts e
end
This test fails because the error wasn't caught. The error bubbles up outside of normal execution so you can't rely on procedural methods of catching the error.
But, because the error causes on exit on the parent process (the test process)
you can trap the exit with Process.flag(:trap_exit, true)
. This flag changes exit behavior. Instead of exiting, the parent process will now receive an :EXIT
message.
test "catch child process error?" do
Process.flag(:trap_exit, true)
child_pid = spawn_link(fn ->
raise "3RA1N1AC"
end)
assert_receive {
:EXIT,
^child_pid,
{%RuntimeError{message: "3RA1N1AC"}, _stack}
}
end
The error struct is returned in the message tuple so you can pattern match on it and assert about.
This method is still subject to race conditions. The child process must throw the error before the assert_receive
times out.
There is a different example in the Elixir docs for catch_exit.
Tweet