I’m pretty sure the only requirement is that you be able to launch the child process with some MFA that returns one of {:ok, pid}, {:error, reason}, or :ignore, where pid is linked.
Tasks don’t emit messages, so that’s not a requirement. Nor do they accept messages, except for brutal_kill messages (that’s built into the VM, so no need to write any code for it). You can choose to handle a soft kill message, but that is optional, because a supervisor knows to brutal_kill after the grace period.
Elixir’s Task will take care of child_spec/1 and spawn_link. Often you want to implement orderly shutdown, like saving some states, I think you still need to do the following:
trap :EXIT in your process
handle :EXIT message to do your orderly shutdown
exit(:shutdown) to terminate the process and notify the supervisor you are done
The supervisor will send you a :EXIT message in shutdown, and wait up to 5 seconds (configurable). It expects you to shutdown yourself and notify the supervisor. If you do not trap, you will crash. If you trap, but do nothing, the supervisor will brutal_kill you after the timeout. If you shutdown but did not call exit(:shutdown) the supervisor will believe you crashed and print a warning.
Besides ˋTaskˋ another good example of processes using ˋ$callersˋ is the phoenix liveview test helpers. Everything runs in separate processes, but still uses e.g. a common ecto sandbox connection.
I am curious if there is any authorization library that uses the process dictionary and “$callers” to backtrack through to the process handling the web request or websocket connection, as a means to “paint” the scope of any given user’s auth, without having to pass authorization everywhere.
yeah this is a good point. Phoenix LiveViews are GenServers, so they don’t get “$callers” by default. It’s my opinion that GenServer should have some way to forward callers from its launching process, this would necessarily be a minor incompatibility with erlang, but then again the GenServer.start_link looks different from :gen_server.start_link anyways.
This would definitely feel too magical to me. Process dictionaries can have value for managing some of the runtime book keeping of process management but are in my opinion a terrible fit for your actual application data. Code that relies on it is harder to test, and may behave in unexpected ways if you call it from a process with an unexpected process dictionary value.
do keep in mind that the idea here is to use specifically the :"$callers" process dictionary value, and figure out auth scoping using Registry/ets table, and not a generic PD value, so it should have a “painted scope” that is well-defined by the standard library, and if you choose to alter how $callers works, that’s on you.
The thing that I would most worry about is if authz is revoked in persistent storage and not communicated to the ets Registry? “cache”, you could have an authz lifetime that mismatches the ground truth, and a long-lived process with inappropriate permissions.
Haha yes thank you. The talk was an attempt at redemption for not having finished the video series. I do want to get back into it eventually, but $dayjob got busy, then I changed jobs, etc…