API REST et protocole de l'agent
La référence contractuelle de chaque route, corps et code d'erreur est la section 7 (REST) et la section 8 (agent) de
navin-manager/CONTRACT.md. Le serveur en service publie aussi sa description OpenAPI sur
/api/v1/openapi.json.
Authentification
| Client | Méthode |
|---|---|
| Navigateur | POST /api/v1/auth/login pose le cookie nm_session et renvoie csrf_token. Envoyez-le dans l'en-tête X-CSRF-Token avec chaque POST, PUT, PATCH et DELETE. |
| Automatisation | Authorization: Bearer nmt_<id>_<secret> : un jeton d'API créé dans Profil, Jetons d'API (POST /api/v1/me/tokens). Pas d'en-tête CSRF. |
TOKEN=nmt_0123456789ab_...
curl -s -H "Authorization: Bearer $TOKEN" https://<manager-host>:8460/api/v1/clusters
La langue des messages suit le cookie nm_lang (en ou fr), puis l'en-tête Accept-Language.
Erreurs et listes
Chaque erreur a la même forme, avec le message dans les deux langues :
{"error": {"code": "cluster_not_empty", "message": "...", "message_i18n": {"en": "...", "fr": "..."},
"details": {}}}
| Statut | Codes typiques |
|---|---|
| 401 | unauthenticated, session_expired, token_invalid, invalid_credentials, agent_signature_invalid |
| 403 | permission_denied (les détails donnent la permission), csrf_invalid, account_disabled, password_expired |
| 404 | not_found, service_unknown, operation_not_found |
| 409 | cluster_not_empty, host_has_components, service_in_use, connection_in_use, artifact_missing, sandbox_only_service, last_admin |
| 422 | validation_error, config_invalid (les détails donnent les champs), password_policy |
| 423 | account_locked |
| 429 | too_many_attempts (en-tête Retry-After) |
Les listes acceptent ?limit= (50 par défaut, 500 au plus) et ?cursor= et renvoient
{"items": [...], "next_cursor": ...}. Un secret n'est jamais renvoyé : il s'affiche {"secret": true, "set": true} ;
renvoyer cette valeur conserve le secret stocké.
Routes principales
| Domaine | Routes |
|---|---|
| Session | /auth/providers, /auth/setup, /auth/login, /auth/mfa/*, /auth/password/change, /auth/session, /auth/logout, /auth/oidc/{id}/start et /callback, /me, /me/tokens |
| Administration | /users, /roles, /auth-config/ldap, /auth-config/oidc, /auth-config/policy, /audit, /audit/verify, /audit/export, /settings, /connections |
| Catalogue | /stack, /stack/services/{name}, /mirror, /mirror/reload |
| Clusters et hôtes | /clusters, /clusters/{id}/summary, /topology, /bootstrap-tokens, /hosts/ssh-bootstrap, /hosts, /hosts/{id}, /hosts/{id}/metrics, /preflight, /facts/refresh, /parameters, /decommission |
| Services | /clusters/{id}/services, /services/validate, /services/{name}, /actions, /commands/{command}, /components, /logs, /client-config |
| Configurations | /clusters/{id}/services/{name}/config, /config/versions, /config/diff, /config/versions/{v}/restore, /config/groups, /config/preview, /config/apply, /clusters/{id}/blueprint |
| Opérations | /clusters/{id}/operations, /operations/running, /operations/{id}, /operations/{id}/tasks/{task}, /logs, /abort, /retry |
| Alertes | /clusters/{id}/alerts, /alerts/{id}, /alerts/{id}/ack, /alert-definitions, /notification-targets |
| Supervision | /system/health, /clusters/{id}/sd/prometheus, /pki/ca, /clusters/{id}/certificates ; hors de /api/v1 : /healthz, /readyz, /metrics |
Toutes les routes ci-dessus se trouvent sous /api/v1.
Suivre une opération
Chaque action renvoie {"operation_id": "..."}. Interrogez GET /api/v1/operations/{id} pour les étapes, les tâches
et la progression, et GET /api/v1/operations/{id}/tasks/{task}/logs?after_seq=<n> pour les lignes de journal d'une
tâche (next_seq donne la valeur de l'appel suivant, done passe à vrai quand la tâche est terminée).
OP=$(curl -s -X POST -H "Authorization: Bearer $TOKEN" -H 'Content-Type: application/json' \
-d '{"action": "rolling_restart", "batch_size": 1}' \
https://<manager-host>:8460/api/v1/clusters/$CLUSTER/services/opa/actions | jq -r .operation_id)
curl -s -H "Authorization: Bearer $TOKEN" https://<manager-host>:8460/api/v1/operations/$OP | jq .status
Notifications webhook
Un destinataire webhook reçoit un POST JSON avec X-NM-Signature: t=<unix>,v1=<hex>. Vérifiez-la côté récepteur :
v1 doit valoir HMAC-SHA256(secret, "<t>.<corps brut>") et t doit dater de moins de 5 minutes.
Protocole de l'agent
L'agent appelle la console, jamais l'inverse :
POST /agent/v1/registersur le port 8460 avec le jeton d'amorçage, les faits et une demande de certificat ; la réponse contient l'identifiant de l'hôte, le secret de l'agent, le certificat et l'autorité de la console, dont l'agent compare l'empreinte sha256 avec--ca-sha256.- Sur le port 8461, avec le certificat client :
POST /agent/v1/heartbeattoutes les 15 secondes (métriques, état des composants, faits sur demande),GET /agent/v1/tasks?wait=25(attente longue),POST /agent/v1/tasks/{id}/logsetPOST /agent/v1/tasks/{id}/result,POST /agent/v1/renewavant l'expiration du certificat. - Chaque requête est signée :
Authorization: NM-HMAC <host_id>:<horodatage unix>:<hex>où le HMAC-SHA256 couvre la méthode, le chemin avec ses paramètres, l'horodatage et le sha256 du corps. Un horodatage éloigné de plus de 300 secondes est refusé.
Les types de tâches et leur contenu sont listés dans la section 9 du contrat.