Immortal.ETSTableManager
Creates and keeps an ETS table alive using the heir
feature. Normally, an ETS table will die as soon as its owner process dies. This means that if the owner and consumer of the table are the same process, you can lose your table to a crash.
However, if (prior to its death) your table sets a different process as its heir, the crash will not delete the table. Hence, Immortal.EtsTableManager
is designed to:
- Create an ETS table, setting itself as the heir.
- Give away ownership of the table to a named process of your choosing.
- If the other process crashes, receive ownership of the table back and wait until that process is rebooted by the supervisor.
- Give ownership back to the other process after it reboots.
Examples
Set up your supervisor children like this:
children = [
worker(YourApp.TableConsumer, []),
worker(Immortal.EtsTableManager, [YourApp.TableConsumer, [:public]])
]
Immortal.EtsTableManager
will wait until your YourApp.TableConsumer
process boots, and then hand over control of the table. The [:public]
argument is a configuration list that will be passed to :ets.new/2
when the ETS table is created.
The YourApp.TableConsumer
module should be a GenServer
, and implement the following callback in order to receive control of the table:
def handle_info({:"ETS-TRANSFER", table, _manager_pid, _data}, state) do
new_state = ... # add table to your state
{:noreply, new_state}
end
Summary↑
handle_call(msg, from, state) | Retrieve the ETS table |
handle_info(arg1, state) | Handle the ETS transfer if CallTracker crashes |
start_link(target_process_name, ets_options \\ []) | Start a new TableManager process |
table(manager) | Get the ID of the ETS table that a TableManager is currently managing |
Functions
Retrieve the ETS table
Handle the ETS transfer if CallTracker crashes
Specs:
- start_link(atom, list) :: {:ok, pid}
Start a new TableManager process.
target_process_name
: The name of the process that you want to give the table away to. The process must be named so that TableManager can find it again if it dies.ets_options
: Any options you want to pass to:ets.new/2
. If the:named_table
option is passed, the ETS table's name will be the same astarget_process_name
.
Example
iex> {:ok, pid} = Immortal.ETSTableManager.start_link(TableConsumer, [:public])
...> is_pid(pid)
true
Specs:
- table(pid) :: integer
Get the ID of the ETS table that a TableManager is currently managing.