Files
git.stella-ops.org/docs/api/signals/reachability-contract.md
StellaOps Bot 999e26a48e up
2025-12-13 02:22:15 +02:00

3.3 KiB

Signals API (Reachability)

Status: Working contract (aligns with src/Signals/StellaOps.Signals/Program.cs).

Auth, scopes, sealed mode

  • Scopes: signals:read, signals:write, signals:admin (endpoint-specific; see below).
  • Dev fallback: when Authority auth is disabled, requests must include X-Scopes: <space-separated scopes> (example: X-Scopes: signals:write).
  • Sealed mode: when enabled, Signals may return 503 with { "error": "sealed-mode evidence invalid", ... }.

Endpoints

Health & status

  • GET /healthz (anonymous)
  • GET /readyz (anonymous; 503 when not ready or sealed-mode blocked)
  • GET /signals/ping (scope: signals:read, response: 204)
  • GET /signals/status (scope: signals:read)

Callgraph ingestion & retrieval

  • POST /signals/callgraphs (scope: signals:write)
    • Body: CallgraphIngestRequest (language, component, version, artifactContentBase64, …).
    • Response: 202 Accepted with CallgraphIngestResponse and Location: /signals/callgraphs/{callgraphId}.
    • Graph hash is computed deterministically from normalized nodes/edges/roots; see graphHash in the response.
  • GET /signals/callgraphs/{callgraphId} (scope: signals:read)
  • GET /signals/callgraphs/{callgraphId}/manifest (scope: signals:read)

Sample request: docs/api/signals/samples/callgraph-sample.json

Runtime facts ingestion

  • POST /signals/runtime-facts (scope: signals:write)
    • Body: RuntimeFactsIngestRequest with subject, callgraphId, and events[].
  • POST /signals/runtime-facts/ndjson?callgraphId=...&scanId=... (scope: signals:write)
    • Body: NDJSON of RuntimeFactEvent objects; Content-Encoding: gzip supported.
  • POST /signals/runtime-facts/synthetic (scope: signals:write)
    • Generates a small deterministic sample set of runtime events for a callgraph to unblock testing.

Unknowns ingestion & retrieval

  • POST /signals/unknowns (scope: signals:write)
    • Body: UnknownsIngestRequest (subject, callgraphId, unknowns[]).
  • GET /signals/unknowns/{subjectKey} (scope: signals:read)

Reachability scoring & facts

  • POST /signals/reachability/recompute (scope: signals:admin)
    • Body: ReachabilityRecomputeRequest (callgraphId, subject, entryPoints[], targets[], optional runtimeHits[], optional blockedEdges[]).
    • Response: 200 OK with { id, callgraphId, subject, entryPoints, states, computedAt }.
  • GET /signals/facts/{subjectKey} (scope: signals:read)
    • Response: ReachabilityFactDocument (per-target states, score, riskScore, unknowns pressure, optional uncertainty states, runtime facts snapshot).

Sample fact: docs/api/signals/samples/facts-sample.json

Reachability union bundle ingestion (CAS layout)

  • POST /signals/reachability/union (scope: signals:write)
    • Body: application/zip bundle containing nodes.ndjson, edges.ndjson, meta.json.
    • Optional header: X-Analysis-Id (defaults to a new GUID if omitted).
    • Response: 202 Accepted with ReachabilityUnionIngestResponse and Location: /signals/reachability/union/{analysisId}/meta.
  • GET /signals/reachability/union/{analysisId}/meta (scope: signals:read)
  • GET /signals/reachability/union/{analysisId}/files/{fileName} (scope: signals:read)