swissd API (0.7.0)
Deploy and manage LLM inference releases from a model catalog.
swissd composes a model catalog entry with the cluster's site profile into a plan, dry-runs it against the live release, and installs it with helm or as an LLMService that llm-operator reconciles.
GET /api/catalog -> POST /api/plans -> POST /api/diff -> POST /api/install | /api/apply -> GET .../status
^ |
+------- re-diff <-------------------+ (409: live revision moved)
| Step | Endpoint | Writes |
|---|---|---|
| browse | GET /api/catalog, GET /api/catalog/{model} | nothing |
| compose | POST /api/plans | the plan, to swissd's database, keyed by hash |
| dry run | POST /api/diff | nothing; returns the live revision to assert |
| install | POST /api/install | the release (helm or LLMService) |
| upgrade | POST /api/apply with expectRevision | the release |
| roll back | POST /api/releases/{ns}/{release}/rollback | the release |
Every /api/ path except login, logout and session needs one of:
| Credential | How |
|---|---|
| session cookie | swiss_session, set by POST /api/login (HttpOnly, SameSite=Strict) |
| bearer token | Authorization: Bearer <token>, the token from POST /api/login |
| front-proxy key | Authorization: Bearer <proxyKey> plus X-Remote-User: <name> (the swiss chart's auth.proxyKey) |
Sessions slide: a request in the second half of a token's life gets a fresh cookie. Changing the password invalidates every outstanding token. With auth.disabled nothing is checked.
Every error is JSON {"error": "<message>"} with the status below.
| Status | Meaning |
|---|---|
| 400 | the request is wrong: bad JSON, unknown catalog, invalid field |
| 401 | not logged in |
| 403 | read-only swissd (server.allowDeploy off), or swissd cannot write |
| 404 | no such model, variant, plan, release or revision |
| 409 | the cluster moved or refuses: release exists / is missing / is pending, expectRevision stale, install method mismatch |
| 412 | the release has no reachable entrypoint (probe, chat) |
| 502 | a dependency failed: the Kubernetes API, the catalog, the chart registry, the SLO server |
| 503 | not available on this swissd: no database, SLO server not ready |
With server.allowDeploy off, POST /api/plans, /diff, /apply, /install, rollback, revision diff, uninstall, and PUT/DELETE on slo answer 403. Everything else works.
A release is stored one of two ways, chosen at install and never changed:
applyWith | Stored as | Applied by |
|---|---|---|
helm | the plan in ConfigMap swiss-plan-<release> beside the helm release | swissd running helmfile |
llmsvc | an LLMService (serving.modelsphere.dev) | llm-operator |
llmsvc needs the LLMService CRD and a plan composed from a schema v2 catalog. GET /api/cluster reports whether it is available.
Endpoints that read a catalog take ?catalog=<name>. Omitted, it is the only catalog, else the one the site profile marks default; with several and no default it is a 400. Catalog schema v1 is legacy and read-only; v2 pins each variant at its own version.
This document is checked against swissd's routes by internal/server/openapi_test.go.