aboutsummaryrefslogblamecommitdiff
path: root/lib/manager.ex
blob: ce11117b460a717c7cc63622d6240c04ffbd2f1b (plain) (tree)













































                                                                                       
defmodule Shard.Manager do
  use GenServer

  def start_link(_) do
    GenServer.start_link(__MODULE__, nil, name: __MODULE__)
  end

  def init(_) do
    state = %{
              shards: %{}
            }
    {:ok, state}
  end

  def handle_call({:find, shard_id}, _from, state) do
    {:reply, state.shards[shard_id], state}
  end

  def handle_call(:list, _from, state) do
    {:reply, Map.to_list(state.shards), state}
  end

  def handle_cast({:register, shard_id, pid}, state) do
    if Map.has_key?(state.shards, shard_id) do
      GenServer.cast(pid, {:redundant, shard_id})
      state
    else
      new_shards = Map.put(state.shards, shard_id, pid)
      {:noreply, %{ state | shards: new_shards }}
    end
  end

  def handle_cast({:interested, peer_id, peer_pid, shards}, state) do
    shards
    |> Enum.filter(&(Map.has_key?(state.shards, &1)))
    |> Enum.each(&(GenServer.cast(state.shards[&1], {:interested, peer_id, peer_pid})))
    {:noreply, state}
  end

  def handle_cast({:dispatch, peer_id, peer_pid, shard, msg}, state) do
    if Map.has_key?(state.shards, shard) do
      GenServer.cast(state.shards[shard], {:msg, peer_id, peer_pid, msg})
    end
    {:noreply, state}
  end
end