Are "id" and "name" the same in Elixir Supervisor/Process?

Todoroki Source

I created a Supervisor named ElectionManager.Application and a worker.
Then I looked at the information of those processes:

iex(3)> proc = Process.whereis(ElectionManager.Application)
#PID<0.158.0>

iex(4)> Process.info proc
[registered_name: ElectionManager.Application,
 current_function: {:gen_server, :loop, 7},
 initial_call: {:proc_lib, :init_p, 5}, status: :waiting, message_queue_len: 0,
 messages: [], links: [#PID<0.156.0>, #PID<0.159.0>],
 dictionary: ["$initial_call": {:supervisor, Registry.Supervisor, 1},
  "$ancestors": [#PID<0.156.0>]], trap_exit: true,
 error_handler: :error_handler, priority: :normal, group_leader: #PID<0.155.0>,
 total_heap_size: 986, heap_size: 610, stack_size: 10, reductions: 339,
 garbage_collection: [max_heap_size: %{error_logger: true, kill: true, size: 0},
  min_bin_vheap_size: 46422, min_heap_size: 233, fullsweep_after: 65535,
  minor_gcs: 2], suspending: []]

iex(7)> {id, child, type, modules} = Supervisor.which_children(proc) |> List.first
{ElectionManager.Application.PIDPartition0, #PID<0.159.0>, :worker,
 [Registry.Partition]}

iex(8)> Process.info child
[registered_name: ElectionManager.Application.PIDPartition0,
 current_function: {:gen_server, :loop, 7},
 initial_call: {:proc_lib, :init_p, 5}, status: :waiting, message_queue_len: 0,
 messages: [], links: [#PID<0.158.0>, #PID<0.156.0>],
 dictionary: ["$initial_call": {Registry.Partition, :init, 1},
  "$ancestors": [ElectionManager.Application, #PID<0.156.0>]], trap_exit: true,
 error_handler: :error_handler, priority: :normal, group_leader: #PID<0.155.0>,
 total_heap_size: 233, heap_size: 233, stack_size: 10, reductions: 47,
 garbage_collection: [max_heap_size: %{error_logger: true, kill: true, size: 0},
  min_bin_vheap_size: 46422, min_heap_size: 233, fullsweep_after: 65535,
  minor_gcs: 0], suspending: []]

in the Elixir document, the differences between name and child_id wasn't clear, and there seems a id: something option for workers and name: something option for processes and Supervisors. I am confused.
From above, it seems that id and registered_name are the same.

I want to have my Supervisor to supervise multiple children, but I cannot do that by default (I get the :already_started error). Should I change both the name and the id, or only either?

elixirotp

Answers

answered 8 months ago narrowtux #1

The id is just an internal identifier used only by the supervisor of a worker. It has to be unique for all workers in the same supervisor.

The name is the value that you can address a process with, instead of using its PID.

The reason you're seeing the same values for the name and the id is that the supervisor uses the name of the process for the worker id by default.

answered 8 months ago vfsoraki #2

The name has nothing to do with supervisor. A process name is used to find the process when you want to refer to it, supervised or unsupervised.

The process id is an internal identifier BEAM uses for processes, just like your OS gives each process an id. Supervisor captures this id to be able to monitor and restart it later.

The child id you give to supervisor, is used to save children spec. If you don't provide it explicitly, it is the name of module that is used to start the child. It can be later used to retrieve the child spec.

If you want to start multiple children using the same module, you have to explicitly specify the child id, since two children can not have the same id (consider the children spec as a hash map of child_id => child_spec).

If you need to start multiple children using the same module, maybe you are looking for simple_one_to_one strategy of supervisor. Using this, you specify your spec once, and request the supervisor to start the children at run time (as apposed to others where the children are started on boot).

comments powered by Disqus