Elixir GenServer.start_link выдает исключение вместо возврата кортежа
Я немного играю с GenServer
и у меня есть проблемы с реализацией пользовательских init
Перезвоните.
Пожалуйста, рассмотрите следующий код:
defmodule GenS do
use GenServer
def start_link(initial \\ 0) do
GenServer.start_link(__MODULE__, initial)
end
def init(initial) do
case initial do
3 -> {:stop, "Can't initialise with 3"}
_ -> {:ok, initial}
end
end
end
case GenS.start_link(3) do
{:error, reason} -> IO.puts "Failed with #{reason}"
{:ok, _} -> IO.puts "This has worked!"
end
IO.puts "I'm still alive!"
При выполнении этого кода я вижу вывод:
▶ elixir gens.ex
** (EXIT from #PID<0.46.0>) "Can't initialise with 3"
В то время как я ожидал аналогичный вывод для успешной ветви (когда значение отличается от 3
в качестве аргумента)
▶ elixir gens.ex
This has worked!
I'm still alive!
Согласно документации GenServer.start_link/3
:
Если
init/1
обратный вызов завершается неудачно с причиной, эта функция возвращает{:error, reason}
, В противном случае, если он вернется{:stop, reason}
или же:ignore
, процесс завершается и эта функция возвращает{:error, reason}
или же:ignore
соответственно.
Я ожидаю, что кортеж будет возвращен, что я мог бы скорректировать, но, похоже, это не так. Есть ли у вас какие-либо рекомендации?
1 ответ
Я ожидаю, что кортеж будет возвращен, что я мог бы скорректировать, но, похоже, это не так. Есть ли у вас какие-либо рекомендации?
Проблема здесь в том, что вы связываете с порожденным процессом и возвращаете {:stop, ...}
от init
отправляет сигнал на выход вызывающему процессу, который по умолчанию убивает вызывающий процесс.
Вы можете либо перейти на использование GenServer.start
(и вручную связать процессы позже, если хотите), или перехватить сигналы выхода, выполнив следующее перед запуском GenS
:
Process.flag(:trap_exit, true)
(Обратите внимание, что это отправит сообщение вызывающему процессу, когда GenS
умирает, от которого вы можете отказаться, чтобы предотвратить потерю памяти.)
В обоих случаях я получаю следующий вывод:
Failed with Can't initialise with 3
I'm still alive!