The runtime exposes an internal HTTP API reachable only on the private Docker network — never from the public internet. It is the sole writer of both theDocumentation Index
Fetch the complete documentation index at: https://mintlify.com/joseluis-dev/harness-ai/llms.txt
Use this file to discover all available pages before exploring further.
executions table and the audit_events table; no other service opens a direct Postgres connection. The BFF forwards all create and read requests here via fetch() over the Docker-internal hostname runtime-python:8000. Swagger UI and ReDoc are intentionally disabled on this service.
Pydantic Schemas
The runtime’s request and response shapes are defined as Pydantic v2 models withextra="forbid" — unknown fields are rejected at the boundary.
GET /healthz
Liveness probe used by the Docker healthcheck directive and by the BFF’s aggregate health endpoint.
Response — 200 OK
Always
"ok" when the process is alive and accepting connections.Always
"runtime-python".Service version string.
POST /internal/executions
Creates an execution row in Postgres and enqueues an RQ job for the worker. This is the sole writer of the executions table.
Request Body
The kind of caller driving the execution. 1–128 characters. Corresponds to
source.type in the Execution Event Contract.Semantic description of the desired action. 1–128 characters.
Free-form JSONB body for the execution. Stored in the
executions.payload column. Defaults to an empty object when omitted.Optional constraints envelope. When provided, merged into
payload under the "constraints" key before the row is committed.Response — 201 Created
The new execution’s UUID. The BFF proxies this value to the caller verbatim.
Always
"queued" immediately after creation.Error Responses
The runtime commits the Postgres row first, then enqueues the RQ job. This ordering means the execution row always exists even during a broker outage. The worker is idempotent, so a duplicate enqueue after a retry is safe. A
503 from this endpoint means the row was written — the BFF should retry the enqueue rather than creating a duplicate row.GET /internal/executions
Lists executions ordered by created_at descending. Supports pagination.
Query Parameters
Number of results to return. Minimum
1, maximum 200.Number of results to skip. Minimum
0. Use with limit to paginate.Response — 200 OK
Array of ExecutionResponse objects.
GET /internal/executions/{execution_id}
Fetches a single execution row by its UUID.
Path Parameters
The execution’s UUID.
Response — 200 OK
Full ExecutionResponse object.
UUID of the execution.
Current status:
queued | running | completed | failed.The originating source type.
The semantic intent string.
The stored JSONB payload including any merged constraints.
Row creation timestamp.
Last modification timestamp.
Completion timestamp, or
null if not yet complete.Error Response — 404 Not Found
GET /internal/executions/{execution_id}/events
Fetches the audit_events rows for a single execution, ordered by created_at ascending (oldest first).
Path Parameters
The execution’s UUID.
Response — 200 OK
Array of AuditEventResponse objects.
Unique ID of the audit event row.
The associated execution UUID.
null for cross-service events forwarded via /internal/audit/ingest.The audit event name, e.g.
execution.queued, execution.completed, model.call.The execution status before this transition.
null for the first event or for non-lifecycle events.The execution status after this transition.
Type of principal that triggered the event:
user | service | system.Identifier of the actor, if available.
JSONB payload for the event — contents vary by
event_type.Timestamp of the audit event.
This endpoint returns
200 [] for unknown execution IDs — it does not return 404. This is intentional: the BFF can forward the response without branching on whether the execution exists yet, and the UI can render “no events yet” as a normal empty state.POST /internal/audit/ingest
Accepts forwarded audit events from sidecars and other internal services (currently: model-gateway). Writes one audit_events row per event with execution_id=NULL.
Request Body
List of audit event objects to persist. Minimum
1 item, maximum 1024 items per request. Each element is a free-form object whose fields are stored verbatim in the JSONB payload column.model-gateway emitter always includes these additional fields in each event object, all of which are stored in the JSONB payload column:
| Field | Description |
|---|---|
provider | The provider name that served the call. |
model | The model name used. |
provider_kind | "local" | "self" | "cloud" | "mock". |
tokens_in | Input token count. |
tokens_out | Output token count. |
latency_ms | Wall-clock latency of the provider call. |
correlation_id | Request-scoped correlation UUID. |
Response — 200 OK
Number of events successfully written to
audit_events.Error Response — 422 Unprocessable Entity
Returned when the events array is empty (Pydantic v2 min_length=1 validation).
The runtime is the sole writer of
audit_events. The BFF must not open a direct Postgres connection to write audit rows — all audit writes flow through either the execution lifecycle (state transition writer) or this ingest endpoint. This invariant is enforced by the architecture and validated on every PR gate.Cross-service events written via this endpoint carry
execution_id=NULL. They are not lifecycle transitions (so from_status and to_status are also NULL), but they are fully queryable by event_type, actor_id, or the fields in the JSONB payload column.