How Chime knows the people of the app. The app writes one module, from the users it already has, and gives it to Chime's config:
defmodule MyApp.ChimeResolver do
@behaviour Chime.Resolver
import Ecto.Query
alias MyApp.{Repo, User}
@impl true
def recipient(%User{} = user) do
%Chime.Recipient{
id: "user:#{user.id}",
email: user.email,
name: user.name,
locale: user.locale,
time_zone: user.time_zone
}
end
@impl true
def recipients(ids) do
ids = for "user:" <> id <- ids, do: String.to_integer(id)
from(u in User, where: u.id in ^ids and is_nil(u.deleted_at))
|> Repo.all()
|> Enum.map(&recipient/1)
end
@impl true
def resolve_recipient(%Plug.Conn{assigns: %{current_user: %User{} = user}}),
do: recipient(user)
def resolve_recipient(%Phoenix.LiveView.Socket{assigns: %{current_user: %User{} = user}}),
do: recipient(user)
def resolve_recipient(_nobody), do: nil
endrecipient/1 turns what a notifier's recipients/1 gives (the app's
users) into a Chime.Recipient. recipients/1 finds the people by
their ids when a delivery goes, which may be later than the
notification (an email ten minutes after, a digest the next morning),
so that it writes to their address of then; a person it does not give
back gets nothing, and the log says why. resolve_recipient/1 says
who reads the feed: from a Plug.Conn (the JSON API, after the app's
own pipeline) or a LiveView socket (Chime.Live, after the app's own
on_mount hooks). Nil is nobody: the API answers 401, and the bell is
not shown.
Make the ids from the database, never from what a browser sends.
Summary
Callbacks
The recipient of something a notifier's recipients/1 gives.
The people of these ids that still are, in any order.
The person of a request or a LiveView, or nil.
The workspace of a request or a LiveView (a team, an organisation of
the app's), or nil for the whole feed. With it, the bell, the feed, its
counts and the preferences of Chime.Live and the JSON API are that
workspace's. Without this function, the whole feed.
Callbacks
@callback recipient(term()) :: Chime.Recipient.t()
The recipient of something a notifier's recipients/1 gives.
@callback recipients([String.t()]) :: [Chime.Recipient.t()]
The people of these ids that still are, in any order.
@callback resolve_recipient(Plug.Conn.t() | Phoenix.LiveView.Socket.t()) :: Chime.Recipient.t() | nil
The person of a request or a LiveView, or nil.
@callback resolve_workspace(Plug.Conn.t() | Phoenix.LiveView.Socket.t()) :: String.t() | nil
The workspace of a request or a LiveView (a team, an organisation of
the app's), or nil for the whole feed. With it, the bell, the feed, its
counts and the preferences of Chime.Live and the JSON API are that
workspace's. Without this function, the whole feed.