# `DDD.Health`
[🔗](https://github.com/blackuprise/vicander/blob/v0.1.1/lib/ddd/operations/health.ex#L1)

A health check for the parts of the framework that can fall behind silently: the database,
the outbox and the projections.

    DDD.Health.check()
    # => %{
    #      status: :ok,
    #      checks: %{
    #        database: %{status: :ok},
    #        outbox: %{status: :ok, pending: 0, in_flight: 0, dead_letters: 0,
    #                  oldest_pending_age_ms: 0},
    #        projections: %{"MyApp.Projections.ListSummary" => %{status: :ok, pending: 0, ...}}
    #      }
    #    }

The overall `:status` is the worst of the checks:

  * `:unhealthy` - the database does not answer
  * `:degraded` - the outbox has unresolved dead letters, or its oldest pending event (or a
    projection's oldest unprocessed event) has waited longer than the threshold
  * `:ok`

The result is JSON-encodable, so serve it from a Plug route, a Phoenix controller, or the MCP
server (`DDD.Health.Query`). `mix vic.health` prints it and exits non-zero unless `:ok`.

## Options

Each falls back to `config :vicander, :health, ...`, then to the default:

  * `:repo` - default: the configured repo (`config :vicander, repo: MyApp.Repo`)
  * `:projections` - the projection modules to check (default `[]`)
  * `:max_outbox_age_ms` - default `60_000`
  * `:max_dead_letters` - default `0`
  * `:max_projection_lag_ms` - default `60_000`
  * `:emit` - also emit the `DDD.Telemetry` gauges (default `true`)

# `status`

```elixir
@type status() :: :ok | :degraded | :unhealthy
```

# `check`

```elixir
@spec check(keyword()) :: %{status: status(), checks: map()}
```

# `healthy?`

```elixir
@spec healthy?(keyword()) :: boolean()
```

True when `check/1` reports `:ok`.

---

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