# V0 Agent Runtime API

## Purpose

The agent runtime API is the product-facing interface for data agents to discover, inspect, explain, query, and request actions against the lakehouse.

This document defines API shape, not implementation. The API may later be backed by one control plane or multiple services.

## Design Goals

The API should be:

- Product-first: agents discover data products before tables
- Contract-aware: served contract views are the core inspection object
- Governance-aware: responses include effective status and permission summaries
- Status-aware: agents can tell whether a product is healthy, degraded, blocked, deprecated, or retired
- Link-oriented: heavy details live behind specific endpoints
- Safe for action: mutating operations are requests, not direct production mutation

## Authentication and Authorization

V0 uses standard RBAC/ABAC-style permission resolution.

Authorization inputs may include:

- Principal
- Role
- Domain ownership
- Product governance policy
- Product health/status
- Requested action
- Action risk tier

The API should return effective decisions and denial reasons where safe.

## Core Resources

### Data Product

Primary discovery unit.

Identified by:

```text
product_id = <domain>.<product>
```

Examples:

```text
revenue.monthly_recurring_revenue
sales.pipeline_health
platform.query_audit_events
```

### Runtime Contract View

The denormalized JSON snapshot of a product's current contract and runtime state.

Schema:

```text
schemas/data-product-contract.runtime-view.v0.schema.json
```

### Action Request

A request for a controlled operation, such as rerun, backfill proposal, access request, ticket creation, or PR generation.

Actions are evaluated against risk tier, governance policy, product status, and caller authorization.

## Endpoint Summary

```text
GET  /api/v0/products
GET  /api/v0/products/{product_id}
GET  /api/v0/products/{product_id}/contract-view
GET  /api/v0/products/{product_id}/lineage
GET  /api/v0/products/{product_id}/runs
GET  /api/v0/products/{product_id}/tests
GET  /api/v0/products/{product_id}/docs
GET  /api/v0/products/{product_id}/policies
POST /api/v0/products/{product_id}/query
POST /api/v0/products/{product_id}/actions
GET  /api/v0/action-requests/{request_id}
```

## Discovery

### `GET /api/v0/products`

Returns a searchable, filterable list of data products.

Query parameters:

- `q`
- `domain`
- `layer`
- `classification`
- `status`
- `owner`
- `supports_action`
- `limit`
- `cursor`

Response shape:

```json
{
  "items": [
    {
      "id": "revenue.monthly_recurring_revenue",
      "name": "Monthly Recurring Revenue",
      "layer": "curated",
      "domain": "revenue",
      "owner": "revenue-analytics",
      "status": "healthy",
      "classifications": ["internal", "financial"],
      "summary": "Governed monthly recurring revenue measures.",
      "links": {
        "contract_view": "/api/v0/products/revenue.monthly_recurring_revenue/contract-view"
      }
    }
  ],
  "next_cursor": null
}
```

Discovery should be fast and denormalized. It should not require agents to crawl every contract view.

## Product Summary

### `GET /api/v0/products/{product_id}`

Returns a compact product summary.

Use this when the agent needs a quick answer about identity, status, layer, owner, and available links.

## Contract View

### `GET /api/v0/products/{product_id}/contract-view`

Returns the runtime-served contract view.

This is the primary inspection endpoint for agents.

The response must validate against:

```text
schemas/data-product-contract.runtime-view.v0.schema.json
```

Agents should read this before querying, explaining, or requesting actions.

## Lineage

### `GET /api/v0/products/{product_id}/lineage`

Returns lineage details for the product.

V0 does not decide the observed-lineage event model. This endpoint can expose a normalized lineage graph, link to a lineage backend, or return events from a later chosen model.

Query parameters:

- `direction`: upstream | downstream | both
- `depth`
- `include_columns`
- `include_runs`
- `cursor`

Response shape:

```json
{
  "product_id": "revenue.monthly_recurring_revenue",
  "direction": "upstream",
  "nodes": [],
  "edges": [],
  "links": {
    "contract_view": "/api/v0/products/revenue.monthly_recurring_revenue/contract-view"
  }
}
```

## Runs

### `GET /api/v0/products/{product_id}/runs`

Returns run history summaries for product assets.

Query parameters:

- `status`
- `from`
- `to`
- `limit`
- `cursor`

Response shape:

```json
{
  "product_id": "revenue.monthly_recurring_revenue",
  "items": [
    {
      "id": "run-123",
      "status": "succeeded",
      "started_at": "2026-05-25T03:40:00Z",
      "ended_at": "2026-05-25T03:45:00Z",
      "assets": ["mrr_by_account_month"]
    }
  ],
  "next_cursor": null
}
```

## Tests

### `GET /api/v0/products/{product_id}/tests`

Returns test definitions and current/history test results.

Query parameters:

- `severity`
- `status`
- `include_history`
- `limit`
- `cursor`

Response shape:

```json
{
  "product_id": "revenue.monthly_recurring_revenue",
  "summary": {
    "status": "passed",
    "blocking": { "passed": 1, "failed": 0 },
    "degrading": { "passed": 0, "failed": 0 },
    "informational": { "passed": 0, "failed": 0 },
    "experimental": { "passed": 0, "failed": 0 }
  },
  "items": [
    {
      "id": "mrr_non_negative",
      "severity": "blocking",
      "status": "passed",
      "last_run_at": "2026-05-25T03:45:00Z"
    }
  ]
}
```

## Docs

### `GET /api/v0/products/{product_id}/docs`

Returns generated documentation or a link to generated documentation.

Generated docs shape is deferred because it depends on the contract engine and rendering surface.

## Policies

### `GET /api/v0/products/{product_id}/policies`

Returns effective governance summaries and links to policy reasoning.

This endpoint should explain how classifications and explicit policy refinements resolved into effective access, masking, retention, audit, and agent-action constraints.

## Query

### `POST /api/v0/products/{product_id}/query`

Runs a governed query or query plan against a product.

V0 should treat this endpoint as a design placeholder. The exact query interface depends on TiDB Cloud Lake, workload isolation, SQL gateway design, and agent safety policy.

Request shape:

```json
{
  "mode": "dry_run",
  "statement": "select month, sum(mrr_usd) as mrr from analytics.revenue.mrr_by_account_month group by month",
  "purpose": "Explain MRR trend for finance analyst.",
  "max_rows": 1000
}
```

Response shape:

```json
{
  "status": "accepted",
  "query_id": "query-123",
  "decision": {
    "allowed": true,
    "reason": "Caller has query permission and product is healthy."
  }
}
```

V0 does not need to define result pagination in detail.

## Action Requests

### `POST /api/v0/products/{product_id}/actions`

Requests a controlled action.

Actions are requests, not direct mutation. The runtime evaluates permission, product status, risk tier, governance policy, and approval requirements.

The detailed approval workflow is deferred. V0 only requires action requests to represent approval-required states and expose enough status for agents and humans to continue safely.

Supported v0 action categories:

- `create_ticket`
- `open_pr`
- `request_access`
- `rerun`
- `propose_backfill`
- `propose_contract_change`
- `explain_status`

Request shape:

```json
{
  "action": "propose_backfill",
  "risk_tier": "controlled_operational",
  "reason": "Freshness missed after upstream invoice load failure.",
  "parameters": {
    "from": "2026-05-24T00:00:00Z",
    "to": "2026-05-25T00:00:00Z"
  }
}
```

Response shape:

```json
{
  "request_id": "actreq-123",
  "status": "pending_approval",
  "decision": {
    "allowed": true,
    "approval_required": true,
    "reason": "Backfill is controlled operational and requires owner approval for this product."
  },
  "links": {
    "self": "/api/v0/action-requests/actreq-123"
  }
}
```

### `GET /api/v0/action-requests/{request_id}`

Returns action request state.

Statuses:

- `accepted`
- `pending_approval`
- `running`
- `succeeded`
- `failed`
- `rejected`
- `canceled`

## Error Shape

Errors should be structured and agent-readable.

```json
{
  "error": {
    "code": "product_not_queryable",
    "message": "Product is degraded and cannot be used for authoritative reporting.",
    "details": {
      "product_id": "revenue.monthly_recurring_revenue",
      "status": "degraded"
    },
    "links": {
      "contract_view": "/api/v0/products/revenue.monthly_recurring_revenue/contract-view"
    }
  }
}
```

## Open Questions

1. Should the query endpoint return results directly in v0, or only create query jobs?
2. Should action requests be product-scoped only, or can they target domains and assets directly?
3. What approval system backs action request approvals?
4. What authentication mechanism should v0 assume?
5. How much policy reasoning can be safely returned to agents?
6. Should discovery include semantic/vector search in v0, or only structured filters?
