# `Chime.Explain`
[🔗](https://github.com/hattoriai/chime/blob/v0.1.0-dev/lib/chime/explain.ex#L1)

Why a person got a notification, or did not: the log of what Chime
decided, with the reason of each decision.

Chime chooses not to send many things, on purpose: the person turned
the channel off, read the notification in the feed before its email's
time, has no address, or the notifier's condition said no. From the
outside it looks the same as a failure ("I never got the email"). The
log tells them apart:

    Chime.explain(notification_id) |> Chime.Explain.format() |> IO.puts()

    2026-10-25 14:02:11Z  new_comment  to user:42  (comments)
    2026-10-25 14:02:11Z  feed      shown
    2026-10-25 14:02:11Z  telegram  skipped    the person has no Telegram chat
    2026-10-25 14:05:40Z  feed      read
    2026-10-25 14:12:11Z  email     skipped    read in the feed at 2026-10-25 14:05:40Z

The steps are the notification's (it came, an event of its group joined
it, it was seen, read, archived) and each delivery's, as
`Chime.Delivery` keeps them. They are kept as long as the notification
(`:keep_days` of `Chime.Config`).

# `step`

```elixir
@type step() :: %{
  at: DateTime.t(),
  channel: String.t(),
  status: String.t(),
  reason: String.t() | nil
}
```

A step of the log.

# `t`

```elixir
@type t() :: %{notification: Chime.Notification.t(), steps: [step()]}
```

The log of a notification.

# `format`

```elixir
@spec format(t() | nil) :: String.t()
```

The log as lines of text, one for each step.

---

*Consult [api-reference.md](api-reference.md) for complete listing*
