The HTTP API
chaosd exposes an HTTP/JSON API served by the chaos-api crate. It is the contract every control surface builds against; the CLI consumes only this API. An OpenAPI 3 document is generated from the route annotations, committed, drift-tested in CI, and served at /swagger-ui.
Transport
In this release the API is served over a Unix domain socket, not a TCP port. There is no TLS and no authentication on this surface yet; those are planned for a later phase. The socket path defaults to /run/chaosd/chaosd.sock and is set in chaosd configuration. The daemon removes any stale socket on start and unlinks it on clean shutdown.
The API speaks ordinary HTTP/1.1 over the socket. The CLI ships a minimal Unix-socket client; any HTTP client that can connect to a Unix socket works the same way.
Endpoints
| Method | Path | Purpose |
|---|---|---|
GET | /v1/system | Version, port bindings, backend capabilities |
GET | /v1/impairments/{direction} | Current applied state for a direction |
PUT | /v1/impairments/{direction} | Apply an impairment to a direction |
DELETE | /v1/impairments/{direction} | Clear all impairments on a direction |
GET | /v1/impairments/{direction}/stats | Live qdisc statistics for a direction |
GET | /v1/calibration/baseline | The stored calibration baseline |
{direction} is port1 or port2. An unknown direction segment is a 400.
System
GET /v1/system reports the daemon version, the resolved per-direction bindings, and the backend capabilities:
{
"version": "0.1.0",
"ports": [
{ "direction": "port1", "interface": "enp4s0", "bdf": "0000:04:00.0" },
{ "direction": "port2", "interface": "enp5s0", "bdf": "0000:05:00.0" }
],
"capabilities": {
"supports_latency": true,
"supports_loss_bernoulli": true,
"supports_loss_gilbert_elliott": false,
"supports_rate": true,
"supports_distributions": [ { "kind": "uniform" }, { "kind": "normal" }, { "kind": "pareto" } ],
"backend_name": "…",
"backend_version": "…"
}
}
Read, apply, clear
GET /v1/impairments/{direction} returns the current AppliedState — the kernel read-back.
PUT /v1/impairments/{direction} takes an Impairment body, programs it, and returns the post-apply AppliedState with any divergence:
curl --unix-socket /run/chaosd/chaosd.sock \
-X PUT http://localhost/v1/impairments/port1 \
-H 'content-type: application/json' \
-d '{"latency":{"kind":"constant","duration":40000000}}'
{
"direction": "port1",
"impairment": { "latency": { "kind": "constant", "duration": 40000000 } },
"captured_at": 123456789,
"captured_at_wall": 1700000000000000000
}
The divergence array is omitted when empty. DELETE /v1/impairments/{direction} clears the direction and returns the cleared state; a foreign root qdisc is left in place and surfaced as a divergence.
Statistics
GET /v1/impairments/{direction}/stats returns a LinkStats sample — cumulative counters plus monotonic and wall-clock sample timestamps. Poll it and compute rates from deltas between samples; the wire shape never carries rates.
Calibration baseline
GET /v1/calibration/baseline returns the stored baseline as opaque JSON, read from the configured baseline_path. When no baseline is stored, it returns 404.
Errors
Errors are returned as application/problem+json (RFC 7807) with type, title, status, and detail:
| Status | Condition |
|---|---|
400 | Unknown direction or malformed body |
403 | Permission denied — the daemon lacks CAP_NET_ADMIN |
404 | No calibration baseline stored |
422 | Unsupported configuration or kernel rejection |
500 | Backend or I/O error |
A 422 is the response to an impairment the backend cannot apply — for example Gilbert-Elliott loss or the paretonormal distribution in this release.
OpenAPI
The generated OpenAPI document is the source of truth for the surface and is served at /api-docs/openapi.json, with the Swagger UI mounted at /swagger-ui. A CI test fails if the committed spec drifts from the annotations, so the spec and the handlers stay in lockstep. Any change to this surface is a gated change kept synchronized with the spec.
Next steps
- The CLI — the operator client for these endpoints.
- The impairment surface — the body shapes the API accepts.
