Hi all
How can I detect if a module is implement GenServer callbacks?
Thanks
Hi all
How can I detect if a module is implement GenServer callbacks?
Thanks
You can use module_name.module_info[:attributes][:behaviour]
for this.
I want to write a supervisor that will on the start_link function expect as the argument a module and number of workers. Consider following supervisor:
defmodule ProcessDiscovery.WorkerSuperVisor do
use Supervisor
def start_link(module, numbers) do
Supervisor.start_link(__MODULE__, {module, numbers})
end
def init({module, numbers}) do
workers = for w <- 1..numbers do
worker(module, [], id: {:worker, w})
end
# supervise/2 is imported from Supervisor.Spec
supervise(workers, strategy: :one_for_one)
end
end
As you can see, I will create workers depends on number that the user will pass. What I want to do is, to ensure that the user pass a module with implemented genserver. Otherwise it should throw error.
How can I validate a parameter, that should be a module? It is a good idea to use @spec in this scenario?
Thanks
As @Nobbz said, you can use module.module_info[:attributes][:behaviour]
to see what behaviours the module implements.
You could then write your check as:
unless Enum.member?(module.module_info[:attributes][:behaviour], GenServer) do
raise "Module #{inspect(module)} must implement GenServer to be used as a worker"
end
Just some thoughts. You’re requiring that the worker use the GenServer
behaviour but that would exclude any workers written in erlang or workers that implement the interface fully and don’t implement the behaviour. Are you sure you need a hard check here? Might it not be better just to document your expectations?
I’ve never think about it. That a good argumentation I would let it like you sad.
Thanks