openapi: 3.0.3
info:
title: Athena RS
version: 3.4.7
description: |
Athena gateway API and driver.
This specification covers the core gateway CRUD/query surface, management/admin provisioning and schema operations,
backup/storage utilities, pipeline orchestration, and registry/schema discovery routes.
Authentication and routing model:
- Most gateway routes resolve a target client from `X-Athena-Client`.
- Management routes require client-bound API keys with matching rights.
- Admin routes require the static admin key (`ATHENA_KEY_12`).
Response model:
- Most routes return a standard JSON envelope (`status`, `message`, `data`/`error`).
- RPC routes (`/gateway/rpc`, `/rpc/{function_name}`) return `{ "data": [...], "count": ... }` on success.
Every operation returns at least one 2xx (success) and one 5xx (server error) response; 3xx (redirect) is optional where applicable.
servers:
- url: https://mirror3.athena-db.com
tags:
- name: Health
description: Liveness, readiness, and cluster probe endpoints.
- name: Gateway
description: Core CRUD/query/RPC operations routed by `X-Athena-Client`.
- name: Pipelines
description: Config-driven source-transform-sink execution and simulation endpoints.
- name: Management
description: Client-bound schema and provisioning operations guarded by management rights.
- name: Admin
description: Static-admin-key control plane for API keys, client catalog, backups, and observability metadata.
- name: Schema
description: Table/column/migration discovery endpoints.
- name: Storage
description: S3-compatible object and bucket utility endpoints.
- name: Registry
description: Router and API registry discovery endpoints.
paths:
/:
get:
summary: API root and route listing
description: Returns health status and a list of all available routes with methods and summaries (PostgREST-style).
responses:
'200':
description: OK
content:
application/json:
schema:
type: object
properties:
message:
type: string
example: athena is online
version:
type: string
description: API version (cargo_toml_version)
athena_api:
type: string
example: online
athena_deadpool:
type: string
example: online
athena_scylladb:
type: string
enum:
- online
- offline
cargo_toml_version:
type: string
routes:
type: array
description: All available routes with path, methods, and summary
items:
type: object
properties:
path:
type: string
example: /gateway/data
methods:
type: array
items:
type: string
example:
- POST
summary:
type: string
'500':
$ref: '#/components/responses/DefaultServerError5xx'
/ping:
get:
summary: Health check
description: Returns `pong` so orchestrators and load balancers can verify the process is alive.
responses:
'200':
description: Pong response
content:
text/plain:
schema:
type: string
example: pong
'500':
$ref: '#/components/responses/DefaultServerError5xx'
/health/cluster:
get:
summary: Cluster mirror health and version checks
description: Checks Athena mirror domains, returns reachability, latency, throughput, and reported version metadata.
responses:
'200':
description: Cluster health details
content:
application/json:
schema:
$ref: '#/components/schemas/ClusterHealthResponse'
'500':
$ref: '#/components/responses/DefaultServerError5xx'
/management/capabilities:
get:
summary: List management API capabilities for a client
description: Requires `X-Athena-Client` and a client-bound API key with `management.read`.
parameters:
- in: header
name: X-Athena-Client
required: true
schema:
type: string
- in: header
name: apikey
required: true
schema:
type: string
- in: header
name: x-api-key
schema:
type: string
description: optional API key mirror of the `apikey` header
responses:
'200':
description: Management capability details
content:
application/json:
schema:
$ref: '#/components/schemas/ManagementCapabilitiesEnvelope'
'400':
description: Missing or unknown X-Athena-Client
'401':
description: Missing or invalid API key
'403':
description: API key is not client-bound or lacks management.read
'500':
$ref: '#/components/responses/DefaultServerError5xx'
/management/provision/providers/neon:
post:
summary: Provision/register a Neon Postgres database via management API
description: Requires `X-Athena-Client` and a client-bound API key with `management.provision.write`.
parameters:
- in: header
name: X-Athena-Client
required: true
schema:
type: string
- in: header
name: apikey
required: true
schema:
type: string
requestBody:
required: true
content:
application/json:
schema:
type: object
responses:
'200':
description: Neon database provisioned and optionally registered
'400':
description: Invalid provider payload
'401':
description: Missing or invalid API key
'403':
description: Missing management.provision.write or key is not client-bound
'500':
$ref: '#/components/responses/DefaultServerError5xx'
/management/provision/providers/railway:
post:
summary: Provision/register a Railway Postgres database via management API
description: Requires `X-Athena-Client` and a client-bound API key with `management.provision.write`.
parameters:
- in: header
name: X-Athena-Client
required: true
schema:
type: string
- in: header
name: apikey
required: true
schema:
type: string
requestBody:
required: true
content:
application/json:
schema:
type: object
responses:
'200':
description: Railway database provisioned and optionally registered
'400':
description: Invalid provider payload
'401':
description: Missing or invalid API key
'403':
description: Missing management.provision.write or key is not client-bound
'500':
$ref: '#/components/responses/DefaultServerError5xx'
/management/provision/providers/render:
post:
summary: Provision/register a Render Postgres database via management API
description: Requires `X-Athena-Client` and a client-bound API key with `management.provision.write`.
parameters:
- in: header
name: X-Athena-Client
required: true
schema:
type: string
- in: header
name: apikey
required: true
schema:
type: string
requestBody:
required: true
content:
application/json:
schema:
type: object
responses:
'200':
description: Render database provisioned and optionally registered
'400':
description: Invalid provider payload
'401':
description: Missing or invalid API key
'403':
description: Missing management.provision.write or key is not client-bound
'500':
$ref: '#/components/responses/DefaultServerError5xx'
/management/provision/local/databases:
get:
summary: List local cluster PostgreSQL databases for the caller client
description: Requires `X-Athena-Client` and a client-bound API key with `management.provision.write`.
parameters:
- in: header
name: X-Athena-Client
required: true
schema:
type: string
- in: header
name: apikey
required: true
schema:
type: string
responses:
'200':
description: Database inventory loaded
content:
application/json:
schema:
$ref: '#/components/schemas/LocalClusterDatabasesResponse'
'401':
description: Missing or invalid API key
'403':
description: Missing management.provision.write or key is not client-bound
'500':
$ref: '#/components/responses/DefaultServerError5xx'
post:
summary: Create a local cluster PostgreSQL database for the caller client
description: Requires `X-Athena-Client` and a client-bound API key with `management.provision.write`.
parameters:
- in: header
name: X-Athena-Client
required: true
schema:
type: string
- in: header
name: apikey
required: true
schema:
type: string
requestBody:
required: true
content:
application/json:
schema:
$ref: '#/components/schemas/LocalClusterCreateDatabaseRequest'
responses:
'201':
description: Local database created
'400':
description: Invalid payload
'401':
description: Missing or invalid API key
'403':
description: Missing management.provision.write or key is not client-bound
'409':
description: Database already exists
'500':
$ref: '#/components/responses/DefaultServerError5xx'
/management/tables:
post:
summary: Create a managed table
description: Requires `X-Athena-Client` and a client-bound API key with `management.tables.write`.
parameters:
- in: header
name: X-Athena-Client
required: true
schema:
type: string
- in: header
name: apikey
required: true
schema:
type: string
requestBody:
required: true
content:
application/json:
schema:
$ref: '#/components/schemas/CreateTableRequest'
responses:
'201':
description: Table created
content:
application/json:
schema:
type: object
'400':
description: Invalid payload
'401':
description: Missing or invalid API key
'403':
description: Missing management.tables.write or key is not client-bound
'409':
description: Table already exists
'503':
description: public.database_audit_log is missing on the gateway logging database, or the logging store is unavailable
/management/tables/{table_name}:
patch:
summary: Apply safe additive ALTER TABLE operations
description: Requires `X-Athena-Client` and a client-bound API key with `management.tables.write`.
parameters:
- in: path
name: table_name
required: true
schema:
type: string
- in: header
name: X-Athena-Client
required: true
schema:
type: string
- in: header
name: apikey
required: true
schema:
type: string
requestBody:
required: true
content:
application/json:
schema:
$ref: '#/components/schemas/EditTableRequest'
responses:
'200':
description: Table updated
'400':
description: Invalid payload or unsupported alteration
'401':
description: Missing or invalid API key
'403':
description: Missing management.tables.write or key is not client-bound
'404':
description: Table not found
'503':
description: public.database_audit_log is missing on the gateway logging database, or the logging store is unavailable
delete:
summary: Drop a managed table
description: Requires `X-Athena-Client` and a client-bound API key with `management.tables.drop`.
parameters:
- in: path
name: table_name
required: true
schema:
type: string
- in: header
name: X-Athena-Client
required: true
schema:
type: string
- in: header
name: apikey
required: true
schema:
type: string
requestBody:
required: true
content:
application/json:
schema:
$ref: '#/components/schemas/DropTableRequest'
responses:
'200':
description: Table dropped
'401':
description: Missing or invalid API key
'403':
description: Missing management.tables.drop or key is not client-bound
'404':
description: Table not found
'503':
description: public.database_audit_log is missing on the gateway logging database, or the logging store is unavailable
/management/tables/{table_name}/columns/{column_name}:
delete:
summary: Drop a managed table column
description: Requires `X-Athena-Client` and a client-bound API key with `management.columns.drop`.
parameters:
- in: path
name: table_name
required: true
schema:
type: string
- in: path
name: column_name
required: true
schema:
type: string
- in: header
name: X-Athena-Client
required: true
schema:
type: string
- in: header
name: apikey
required: true
schema:
type: string
requestBody:
required: true
content:
application/json:
schema:
$ref: '#/components/schemas/DropColumnRequest'
responses:
'200':
description: Column dropped
'400':
description: Invalid payload or reserved column
'401':
description: Missing or invalid API key
'403':
description: Missing management.columns.drop or key is not client-bound
'404':
description: Column not found
'503':
description: public.database_audit_log is missing on the gateway logging database, or the logging store is unavailable
/management/indexes:
post:
summary: Create an index
description: Requires `X-Athena-Client` and a client-bound API key with `management.indexes.write`.
parameters:
- in: header
name: X-Athena-Client
required: true
schema:
type: string
- in: header
name: apikey
required: true
schema:
type: string
requestBody:
required: true
content:
application/json:
schema:
$ref: '#/components/schemas/CreateIndexRequest'
responses:
'201':
description: Index created
'400':
description: Invalid payload
'401':
description: Missing or invalid API key
'403':
description: Missing management.indexes.write or key is not client-bound
'404':
description: Table not found
'409':
description: Index already exists
'503':
description: public.database_audit_log is missing on the gateway logging database, or the logging store is unavailable
/management/indexes/{index_name}:
delete:
summary: Drop an index
description: Requires `X-Athena-Client` and a client-bound API key with `management.indexes.drop`.
parameters:
- in: path
name: index_name
required: true
schema:
type: string
- in: header
name: X-Athena-Client
required: true
schema:
type: string
- in: header
name: apikey
required: true
schema:
type: string
requestBody:
required: true
content:
application/json:
schema:
$ref: '#/components/schemas/DropIndexRequest'
responses:
'200':
description: Index dropped
'401':
description: Missing or invalid API key
'403':
description: Missing management.indexes.drop or key is not client-bound
'404':
description: Index not found
'503':
description: public.database_audit_log is missing on the gateway logging database, or the logging store is unavailable
/management/extensions/install:
post:
summary: Install a Postgres extension
description: |
Installs an allowlisted Postgres extension on the selected `X-Athena-Client` database.
Requires a client-bound API key with `management.extensions.write`. Audit rows require `public.database_audit_log` on the gateway logging Postgres database.
parameters:
- in: header
name: X-Athena-Client
required: true
schema:
type: string
- in: header
name: apikey
required: true
schema:
type: string
requestBody:
required: true
content:
application/json:
schema:
type: object
required:
- extension_name
properties:
extension_name:
type: string
description: Extension to install (allowlisted).
example: pgcrypto
if_not_exists:
type: boolean
default: false
responses:
'200':
description: Extension installed
'400':
description: Invalid payload or extension is not allowlisted
'401':
description: Missing or invalid API key
'403':
description: Missing management.extensions.write or key is not client-bound
'503':
description: public.database_audit_log is missing on the gateway logging database, or the logging store is unavailable
/management/functions:
get:
summary: List Postgres functions for the target client
description: |
Queries `pg_proc` for ordinary functions (`prokind = 'f'`). Requires management client context and `management.functions.read`.
parameters:
- in: header
name: X-Athena-Client
required: true
schema:
type: string
- in: header
name: apikey
schema:
type: string
description: Management API key (also accepted via x-api-key, Authorization Bearer, etc.)
- in: query
name: schema
required: false
schema:
type: string
description: Filter by schema name
- in: query
name: name_like
required: false
schema:
type: string
description: ILIKE pattern for function name (server wraps with `%`)
- in: query
name: include_system
required: false
schema:
type: boolean
default: false
description: When false, excludes `pg_catalog` and `information_schema`
- in: query
name: include_definition
required: false
schema:
type: boolean
default: false
description: When true, includes `pg_get_functiondef` in the response
responses:
'200':
description: Functions listed (standard success envelope with `data.functions`)
'400':
description: Invalid query parameters
'401':
description: Unauthorized
'403':
description: Missing management.functions.read
'500':
description: Query failed
put:
summary: Create or replace a Postgres function from DDL
description: |
Runs validated `CREATE OR REPLACE FUNCTION` DDL inside a transaction with audit tables. Requires `management.functions.write`
Audit rows require `public.database_audit_log` and `public.function_ddl_audit_log` on the gateway logging Postgres database.
parameters:
- in: header
name: X-Athena-Client
required: true
schema:
type: string
- in: header
name: apikey
schema:
type: string
requestBody:
required: true
content:
application/json:
schema:
$ref: '#/components/schemas/UpsertFunctionRequest'
responses:
'200':
description: Function upserted
'400':
description: Invalid DDL
'401':
description: Unauthorized
'403':
description: Missing management.functions.write
'503':
description: Audit tables missing on gateway logging database or logging store unavailable
delete:
summary: Drop a Postgres function by signature
description: |
Issues `DROP FUNCTION schema.function(arg_types...) RESTRICT`. Requires `management.functions.drop` and the same audit tables as upsert.
parameters:
- in: header
name: X-Athena-Client
required: true
schema:
type: string
- in: header
name: apikey
schema:
type: string
requestBody:
required: true
content:
application/json:
schema:
$ref: '#/components/schemas/DropFunctionRequest'
responses:
'200':
description: Function dropped
'400':
description: Invalid request
'401':
description: Unauthorized
'403':
description: Missing management.functions.drop
'404':
description: Function not found
'503':
description: Audit tables missing on gateway logging database or logging store unavailable
/query/sql:
post:
summary: Execute SQL using selected driver
description: |
For `driver: postgresql`, connection resolution matches gateway handlers: send `X-Athena-Client` for a registered client pool, or `X-JDBC-URL` with a `jdbc:postgresql://...` URL for a direct connection (subject to gateway JDBC allowlists when configured).
requestBody:
required: true
content:
application/json:
schema:
$ref: '#/components/schemas/GatewaySqlExecutionRequest'
responses:
'200':
description: Query executed
content:
application/json:
schema:
type: object
'400':
description: Invalid driver
'500':
description: Driver execution failed
'503':
description: Athena/Scylla unavailable
/gateway/sql:
post:
summary: Execute SQL via driver (gateway alias)
description: |
Same request body and behavior as `POST /query/sql`. Provided for SDKs that target a `/gateway/*` prefix.
requestBody:
required: true
content:
application/json:
schema:
$ref: '#/components/schemas/GatewaySqlExecutionRequest'
responses:
'200':
description: Query executed
content:
application/json:
schema:
type: object
'400':
description: Invalid driver
'500':
description: Driver execution failed
'503':
description: Athena/Scylla unavailable
/query/count:
post:
summary: Cached row count (COUNT query or table reference)
description: |
Returns a single row count using the same cache layers as gateway fetch (in-process + Redis when configured).
Provide either validated `query` (single SELECT COUNT ... with no GROUP BY / UNION / comments) or `table_name` with optional `table_schema` (default `public`).
`Cache-Control: no-cache` bypasses the cache. Responses include `X-Athena-Cached`, `X-Athena-Cache-Outcome`, and `X-Athena-Cache-Source` when applicable.
parameters:
- in: header
name: X-Athena-Client
description: Required when driver is postgresql
schema:
type: string
- in: header
name: Cache-Control
description: Set to `no-cache` to bypass cached count
schema:
type: string
requestBody:
required: true
content:
application/json:
schema:
type: object
properties:
driver:
type: string
enum:
- athena
- postgresql
- supabase
db_name:
type: string
query:
type: string
description: Validated COUNT-only SQL (mutually exclusive with table_name)
table_name:
type: string
description: Table name when not using raw query (mutually exclusive with query)
table_schema:
type: string
description: Schema name; defaults to public when using table_name
required:
- driver
- db_name
example:
driver: postgresql
db_name: athena_logging
table_name: http_request_log
table_schema: public
responses:
'200':
description: Row count computed or served from cache
content:
application/json:
schema:
type: object
properties:
status:
type: string
example: success
message:
type: string
data:
type: object
properties:
count:
type: integer
format: int64
db_name:
type: string
duration_ms:
type: integer
format: int64
cache_key:
type: string
cache_lookup_outcome:
type: string
example:
status: success
message: Row count computed
data:
count: 2451
db_name: athena_logging
duration_ms: 12
cache_lookup_outcome: hit_local
'400':
description: Invalid driver, ambiguous body, or invalid count SQL
'500':
description: Driver execution failed
'503':
description: Athena/Scylla unavailable
/gateway/fetch:
post:
summary: Fetch data with conditions
description: |
Fetches rows from a table or view using structured conditions, optional pagination, sort instructions,
and optional post-processing (`group_by`, `time_granularity`, aggregation options).
Notes:
- Route selection is based on `X-Athena-Client` (or custom Supabase headers for `custom_supabase`).
- `X-Strip-Nulls` can be used to remove null-valued fields from response payloads.
- Cache behavior may include `X-Athena-Cached`, `X-Athena-Cache-Outcome`, and `X-Athena-Cache-Source` headers.
tags:
- Gateway
parameters:
- in: header
name: X-User-Id
schema:
type: string
- in: header
name: X-Athena-Client
schema:
type: string
- in: header
name: X-Strip-Nulls
schema:
type: string
- in: header
name: apikey
schema:
type: string
- in: header
name: x-api-key
description: optional API key mirror of the `apikey` header
schema:
type: string
- in: header
name: x-supabase-url
description: Required when X-Athena-Client is custom_supabase
schema:
type: string
format: uri
- in: header
name: x-supabase-key
description: Required when X-Athena-Client is custom_supabase
schema:
type: string
requestBody:
required: true
content:
application/json:
schema:
type: object
properties:
view_name:
type: string
table_name:
type: string
columns:
oneOf:
- type: array
items:
type: string
- type: string
conditions:
type: array
items:
type: object
properties:
eq_column:
type: string
eq_value:
type: string
limit:
type: integer
current_page:
type: integer
page_size:
type: integer
offset:
type: integer
total_pages:
type: integer
strip_nulls:
type: boolean
group_by:
type: string
description: Column name to group results by
time_granularity:
type: string
enum:
- day
- hour
- minute
description: Time granularity for grouping timestamp data
aggregation_column:
type: string
description: Column to aggregate (required when using aggregation_strategy)
aggregation_strategy:
type: string
enum:
- cumulative_sum
description: Aggregation strategy to apply (requires aggregation_column)
aggregation_dedup:
type: boolean
description: Whether to deduplicate during aggregation
sortBy:
type: object
description: Optional sort (camelCase). Use sort_by for snake_case.
properties:
field:
type: string
description: Column name to sort by
direction:
type: string
enum:
- asc
- desc
- ascending
- descending
default: asc
sort_by:
type: object
description: Optional sort (snake_case). Same shape as sortBy.
properties:
field:
type: string
direction:
type: string
enum:
- asc
- desc
- ascending
- descending
required:
- conditions
example:
table_name: http_request_log
columns:
- id
- path
- status_code
- created_at
conditions:
- eq_column: client_name
eq_value: athena_logging
limit: 25
current_page: 1
sortBy:
field: created_at
direction: desc
responses:
'200':
description: OK
content:
application/json:
schema:
type: object
example:
status: success
message: Fetched 25 rows
data:
rows:
- id: 5d845b27-8d06-40a0-9e76-08de9d9f3c1f
path: /gateway/fetch
status_code: 200
created_at: 2026-04-14T10:15:00Z
row_count: 25
'400':
description: Bad request
'500':
description: Internal error
/gateway/data:
post:
summary: Legacy alias for `/gateway/fetch`
description: Mirrors `/gateway/fetch` for clients still calling `/gateway/data` with the same payload/response envelope.
parameters:
- in: header
name: X-User-Id
schema:
type: string
- in: header
name: X-Athena-Client
schema:
type: string
- in: header
name: X-Strip-Nulls
schema:
type: string
- in: header
name: apikey
schema:
type: string
- in: header
name: x-api-key
description: optional API key mirror of the `apikey` header
schema:
type: string
- in: header
name: x-supabase-url
description: Required when X-Athena-Client is custom_supabase
schema:
type: string
format: uri
- in: header
name: x-supabase-key
description: Required when X-Athena-Client is custom_supabase
schema:
type: string
requestBody:
required: true
content:
application/json:
schema:
type: object
properties:
view_name:
type: string
table_name:
type: string
columns:
oneOf:
- type: array
items:
type: string
- type: string
conditions:
type: array
items:
type: object
properties:
eq_column:
type: string
eq_value:
type: string
limit:
type: integer
current_page:
type: integer
page_size:
type: integer
offset:
type: integer
total_pages:
type: integer
strip_nulls:
type: boolean
group_by:
type: string
description: Column name to group results by
time_granularity:
type: string
enum:
- day
- hour
- minute
description: Time granularity for grouping timestamp data
aggregation_column:
type: string
description: Column to aggregate (required when using aggregation_strategy)
aggregation_strategy:
type: string
enum:
- cumulative_sum
description: Aggregation strategy to apply (requires aggregation_column)
aggregation_dedup:
type: boolean
description: Whether to deduplicate during aggregation
sortBy:
type: object
description: Optional sort (camelCase). Use sort_by for snake_case.
properties:
field:
type: string
direction:
type: string
enum:
- asc
- desc
- ascending
- descending
sort_by:
type: object
description: Optional sort (snake_case). Same shape as sortBy.
properties:
field:
type: string
direction:
type: string
enum:
- asc
- desc
- ascending
- descending
required:
- conditions
responses:
'200':
description: OK
'400':
description: Bad request
'500':
description: Internal error
/data:
get:
summary: Fetch data via GET
description: |
Compatibility GET wrapper for fetch semantics. Converts query string filters and paging inputs into
an internal fetch-style request.
Use `sort_by`/`sort_direction` for simple ordering and the aggregation query parameters for grouped output.
tags:
- Gateway
parameters:
- in: query
name: view
required: true
schema:
type: string
- in: query
name: eq_column
required: true
schema:
type: string
- in: query
name: eq_value
required: true
schema:
type: string
- in: query
name: columns
schema:
type: string
- in: query
name: limit
schema:
type: integer
- in: query
name: current_page
schema:
type: integer
- in: query
name: page_size
schema:
type: integer
- in: query
name: offset
schema:
type: integer
- in: query
name: total_pages
schema:
type: integer
- in: query
name: strip_nulls
schema:
type: boolean
- in: query
name: sort_by
schema:
type: string
description: Column name to sort by (forwarded as sortBy.field in the internal POST)
- in: query
name: sort_direction
schema:
type: string
enum:
- asc
- desc
- ascending
- descending
description: Sort direction (default asc)
- in: query
name: group_by
schema:
type: string
description: Column name to group results by
- in: query
name: time_granularity
schema:
type: string
enum:
- day
- hour
- minute
description: Time granularity for grouping timestamp data
- in: query
name: aggregation_column
schema:
type: string
description: Column to aggregate (required when using aggregation_strategy)
- in: query
name: aggregation_strategy
schema:
type: string
enum:
- cumulative_sum
description: Aggregation strategy to apply (requires aggregation_column)
- in: query
name: aggregation_dedup
schema:
type: boolean
description: Whether to deduplicate during aggregation
- in: header
name: X-User-Id
schema:
type: string
- in: header
name: X-Athena-Client
schema:
type: string
- in: header
name: X-Strip-Nulls
schema:
type: string
- in: header
name: apikey
schema:
type: string
- in: header
name: x-api-key
description: optional API key mirror of the `apikey` header
schema:
type: string
- in: header
name: x-supabase-url
description: Optional custom Supabase URL when X-Athena-Client is custom_supabase
schema:
type: string
format: uri
- in: header
name: x-supabase-key
description: Optional custom Supabase key when X-Athena-Client is custom_supabase
schema:
type: string
responses:
'200':
description: OK
'400':
description: Bad request
'500':
description: Internal error
/gateway/insert:
put:
summary: Insert a row into a table
description: |
Inserts one row (or server-normalized payload) into the target table selected by `X-Athena-Client`.
The optional `X-Athena-Insert-Window` header can enable request-scoped batching for Postgres-backed inserts.
Conflict responses (409) are typically raised for unique/constraint violations.
tags:
- Gateway
parameters:
- in: header
name: X-User-Id
schema:
type: string
- in: header
name: X-Company-Id
required: true
schema:
type: string
- in: header
name: X-Organization-Id
required: true
schema:
type: string
- in: header
name: X-Publish-Event
schema:
type: string
- in: header
name: X-Athena-Insert-Window
description: |
Optional Postgres insert batching window in milliseconds (1–60000).
When non-zero, enables or overrides `gateway.insert_execution_window_ms` for this request.
The handler blocks until the window elapses and the row is flushed; under load, connection
hold time can increase by up to this value. Ignored when `X-Athena-Deadpool-Enable` requests
deadpool, when `update_body` is present, or for non-Postgres clients.
schema:
type: integer
minimum: 1
maximum: 60000
- in: header
name: X-Athena-Client
schema:
type: string
- in: header
name: apikey
schema:
type: string
requestBody:
required: true
content:
application/json:
schema:
type: object
properties:
table_name:
type: string
insert_body:
type: object
update_body:
type: object
required:
- table_name
- insert_body
example:
table_name: app_events
insert_body:
event_type: user_login
user_id: u_123
source: dashboard
responses:
'200':
description: Inserted
content:
application/json:
schema:
type: object
example:
status: success
message: Row inserted
data:
table_name: app_events
'400':
description: Bad request
'409':
description: Conflict
'500':
description: Internal error
/gateway/delete:
delete:
summary: Delete a row by id
description: |
Deletes rows from the target table, usually by primary/resource identifier fields in the request body.
Route authorization and client routing follow the same model as other gateway mutations.
tags:
- Gateway
parameters:
- in: header
name: X-User-Id
schema:
type: string
- in: header
name: X-Company-Id
required: true
schema:
type: string
- in: header
name: X-Organization-Id
required: true
schema:
type: string
- in: header
name: X-Athena-Client
schema:
type: string
- in: header
name: apikey
schema:
type: string
- in: header
name: x-supabase-url
description: Optional custom Supabase URL when X-Athena-Client is custom_supabase
schema:
type: string
format: uri
- in: header
name: x-supabase-key
description: Optional custom Supabase key when X-Athena-Client is custom_supabase
schema:
type: string
requestBody:
required: true
content:
application/json:
schema:
type: object
properties:
table_name:
type: string
resource_id:
type: string
required:
- table_name
- resource_id
example:
table_name: app_events
resource_id: 5d845b27-8d06-40a0-9e76-08de9d9f3c1f
responses:
'200':
description: Deleted
content:
application/json:
schema:
type: object
example:
status: success
message: Row deleted
data:
table_name: app_events
resource_id: 5d845b27-8d06-40a0-9e76-08de9d9f3c1f
'400':
description: Bad request
'500':
description: Internal error
/gateway/update:
post:
summary: Fetch or update data using a SQLx client (same payload as /gateway/fetch)
description: |
Applies updates to rows matching supplied conditions. Payload shape mirrors fetch-style condition blocks
so callers can reuse filtering logic between read and write flows.
Supports optional post-processing fields for response shaping where applicable.
tags:
- Gateway
parameters:
- in: header
name: X-User-Id
schema:
type: string
- in: header
name: X-Athena-Client
description: selects which PostgreSQL pool to use
schema:
type: string
- in: header
name: X-Strip-Nulls
schema:
type: string
- in: header
name: apikey
schema:
type: string
- in: header
name: x-api-key
description: optional API key mirror of the `apikey` header
schema:
type: string
- in: header
name: x-supabase-url
description: Required when X-Athena-Client is custom_supabase
schema:
type: string
format: uri
- in: header
name: x-supabase-key
description: Required when X-Athena-Client is custom_supabase
schema:
type: string
requestBody:
required: true
content:
application/json:
schema:
type: object
properties:
view_name:
type: string
table_name:
type: string
columns:
oneOf:
- type: array
items:
type: string
- type: string
conditions:
type: array
items:
type: object
properties:
eq_column:
type: string
eq_value:
type: string
limit:
type: integer
current_page:
type: integer
page_size:
type: integer
offset:
type: integer
total_pages:
type: integer
strip_nulls:
type: boolean
group_by:
type: string
description: Column name to group results by
time_granularity:
type: string
enum:
- day
- hour
- minute
description: Time granularity for grouping timestamp data
aggregation_column:
type: string
description: Column to aggregate (required when using aggregation_strategy)
aggregation_strategy:
type: string
enum:
- cumulative_sum
description: Aggregation strategy to apply (requires aggregation_column)
aggregation_dedup:
type: boolean
description: Whether to deduplicate during aggregation
required:
- conditions
example:
table_name: app_events
conditions:
- eq_column: id
eq_value: 5d845b27-8d06-40a0-9e76-08de9d9f3c1f
update_body:
source: api
responses:
'200':
description: OK
content:
application/json:
schema:
type: object
example:
status: success
message: Rows updated
data:
affected_rows: 1
'400':
description: Bad request
'500':
description: Internal error
/gateway/query:
post:
summary: Run a raw SQL query against the selected PostgreSQL pool
description: |
Executes raw SQL against the client selected by `X-Athena-Client`.
This route is intended for advanced workflows where structured gateway payloads are insufficient.
Use carefully with parameterized SQL on the caller side when constructing dynamic queries.
tags:
- Gateway
parameters:
- in: header
name: X-Athena-Client
description: selects which PostgreSQL pool the SQL executes against
required: true
schema:
type: string
- in: header
name: x-api-key
description: optional API key mirror of the `apikey` header in the body
schema:
type: string
requestBody:
required: true
content:
application/json:
schema:
type: object
properties:
query:
description: raw SQL to execute
type: string
required:
- query
example:
query: SELECT id, path, status_code FROM http_request_log ORDER BY created_at DESC LIMIT 10;
responses:
'200':
description: OK
content:
application/json:
schema:
type: object
example:
status: success
message: Query executed
data:
rows:
- id: 5d845b27-8d06-40a0-9e76-08de9d9f3c1f
path: /gateway/fetch
status_code: 200
'400':
description: Bad request
'500':
description: Internal error
/gateway/rpc:
post:
summary: Execute a Postgres function as RPC
description: |
Invokes `schema.function(arg => ...)` on the pool selected by `X-Athena-Client`. Requires API key with right `gateway.rpc.execute`.
Success responses return **`{"data": [...], "count": ...}`** (not the usual `status`/`message` envelope). Rows are JSON objects keyed by selected columns.
parameters:
- in: header
name: X-Athena-Client
required: true
schema:
type: string
- in: header
name: apikey
schema:
type: string
- in: header
name: x-api-key
schema:
type: string
- in: header
name: x-supabase-url
schema:
type: string
format: uri
- in: header
name: x-supabase-key
schema:
type: string
requestBody:
required: true
content:
application/json:
schema:
$ref: '#/components/schemas/GatewayRpcRequest'
example:
function: get_recent_events
schema: public
args:
p_limit: 10
select: id,event_type,created_at
order:
column: created_at
ascending: false
responses:
'200':
description: RPC result rows
content:
application/json:
schema:
type: object
required:
- data
properties:
data:
type: array
items:
type: object
additionalProperties: true
count:
type: integer
format: int64
description: Present when exact count was requested
example:
data:
- id: 5d845b27-8d06-40a0-9e76-08de9d9f3c1f
event_type: user_login
created_at: 2026-04-14T10:15:00Z
count: 1
'400':
description: Invalid RPC request or binding error
'401':
description: Unauthorized
'403':
description: Missing gateway.rpc.execute
'500':
description: Database or internal error
/rpc/{function_name}:
get:
summary: RPC compatibility (GET, query-string args)
description: |
Same execution as `POST /gateway/rpc` with `function` taken from the path. Query keys: `schema`, `select`, `count`, `limit`, `offset`, `order` (`column` or `column.desc`).
Other keys are either RPC arguments or filters written as `column=op.value` (e.g. `status=eq.active`). Arrays use `{a,b}` in the value portion.
parameters:
- name: function_name
in: path
required: true
schema:
type: string
- in: header
name: X-Athena-Client
required: true
schema:
type: string
- in: header
name: apikey
schema:
type: string
- in: header
name: x-api-key
schema:
type: string
responses:
'200':
description: RPC result rows (`data` + optional `count`)
content:
application/json:
schema:
type: object
required:
- data
properties:
data:
type: array
items:
type: object
additionalProperties: true
count:
type: integer
format: int64
'400':
description: Invalid query string
'401':
description: Unauthorized
'500':
description: Database or internal error
post:
summary: RPC compatibility (POST JSON body)
description: |
Body is either a plain JSON object of named arguments for `function_name`, or a full `GatewayRpcRequest`-shaped wrapper (`function`, `schema`, `args`, `filters`, etc.).
parameters:
- name: function_name
in: path
required: true
schema:
type: string
- in: header
name: X-Athena-Client
required: true
schema:
type: string
- in: header
name: apikey
schema:
type: string
- in: header
name: x-api-key
schema:
type: string
requestBody:
required: true
content:
application/json:
schema:
oneOf:
- $ref: '#/components/schemas/GatewayRpcRequest'
- type: object
additionalProperties: true
description: Bare argument object when not using wrapper fields
responses:
'200':
description: RPC result rows
content:
application/json:
schema:
type: object
required:
- data
properties:
data:
type: array
items:
type: object
additionalProperties: true
count:
type: integer
format: int64
'400':
description: Invalid body
'401':
description: Unauthorized
'500':
description: Database or internal error
/gateway/deferred/{request_id}:
get:
summary: Fetch deferred request status
description: |
Returns the current state of a deferred gateway request (`queued`, `running`, `completed`, `failed`, etc.)
together with available execution metadata.
tags:
- Gateway
parameters:
- in: path
name: request_id
required: true
schema:
type: string
responses:
'200':
description: Deferred request status loaded
content:
application/json:
schema:
type: object
'404':
description: Deferred request not found
'503':
description: Deferred queue/status storage unavailable
/gateway/deferred/{request_id}/requeue:
post:
summary: Requeue a deferred request
description: |
Re-enqueues an existing deferred request for execution. Useful for retries after transient failures
or for manually reprocessing a previously completed/failed deferred item.
tags:
- Gateway
parameters:
- in: path
name: request_id
required: true
schema:
type: string
responses:
'200':
description: Deferred request requeued
content:
application/json:
schema:
type: object
'404':
description: Deferred request not found
'503':
description: Deferred queue unavailable
/rest/v1/{table}:
get:
summary: Query a table using PostgREST-style filters
description: |
Mirrors the Supabase PostgREST query syntax. Supply filter expressions (`column.eq=value`, `column.lt=value`, `or=(cond1,cond2)`, etc.), `select`, `limit`, `offset`, `order`, and the optional `Range` header (`items=0-24`). The handler also honors `Prefer: return=minimal`.
parameters:
- in: path
name: table
required: true
schema:
type: string
description: Target table name (sanitized before execution).
- in: header
name: X-Athena-Client
required: true
schema:
type: string
description: Selects which Postgres pool executes the query.
- in: header
name: apikey
required: true
schema:
type: string
description: Gateway API key (can also be passed via Authorization or x-api-key).
- in: header
name: x-api-key
schema:
type: string
description: Mirror of `apikey` useful for proxies.
- in: query
name: select
schema:
type: string
description: PostgREST `select` clause (comma separated columns).
- in: query
name: limit
schema:
type: integer
description: Maximum number of rows to return (default 100).
- in: query
name: offset
schema:
type: integer
description: Row offset (default 0).
- in: query
name: order
schema:
type: string
description: Column ordering using `.asc`/`.desc` (e.g. `id.desc`).
- in: query
name: or
schema:
type: string
description: PostgREST `or` expression to build grouped filters (`(a.eq.1,b.eq.2)`).
- in: header
name: Range
schema:
type: string
description: Optional `items=start-end` range header that overrides offset/limit.
responses:
'200':
description: Rows fetched (Content-Range header reports `items start-end/total`).
headers:
Content-Range:
description: items start-end/*
schema:
type: string
content:
application/json:
schema:
type: object
properties:
data:
type: array
items:
type: object
'400':
description: Invalid filters or missing headers
'500':
description: Internal error
post:
summary: Insert or upsert rows via the REST gateway
description: |
Accepts a single object or array payload. Set `Prefer: return=minimal` for HTTP 204 responses and `Prefer: resolution=merge-duplicates` for upserts.
parameters:
- in: path
name: table
required: true
schema:
type: string
- in: header
name: X-Athena-Client
required: true
schema:
type: string
- in: header
name: apikey
required: true
schema:
type: string
- in: header
name: x-api-key
schema:
type: string
- in: header
name: Prefer
schema:
type: string
description: Use `return=minimal` for 204 or `resolution=merge-duplicates` for UPSERT.
requestBody:
required: true
content:
application/json:
schema:
oneOf:
- type: object
- type: array
items:
type: object
responses:
'200':
description: Rows inserted or upserted
content:
application/json:
schema:
type: object
properties:
data:
type: array
items:
type: object
'204':
description: 'Insert succeeded with Prefer: return=minimal'
'400':
description: Invalid payload or headers
'500':
description: Internal error
patch:
summary: Update rows filtered via PostgREST expressions
description: |
Filters are required (`column.eq=value`, `column.lte=value`, `or=(...)`). The request body must be an object describing the columns to patch. `Prefer: return=minimal` controls whether the response returns data.
parameters:
- in: path
name: table
required: true
schema:
type: string
- in: header
name: X-Athena-Client
required: true
schema:
type: string
- in: header
name: apikey
required: true
schema:
type: string
- in: header
name: x-api-key
schema:
type: string
- in: header
name: Prefer
schema:
type: string
description: Set `return=minimal` for HTTP 204.
requestBody:
required: true
content:
application/json:
schema:
type: object
responses:
'200':
description: Rows updated
content:
application/json:
schema:
type: object
properties:
data:
type: array
items:
type: object
'204':
description: 'Update succeeded with Prefer: return=minimal'
'400':
description: Missing filters or invalid payload
'500':
description: Internal error
delete:
summary: Delete rows using PostgREST-style filters
description: |
Filters are mandatory. Use the same query syntax as GET and include `Prefer: return=minimal` for HTTP 204 responses.
parameters:
- in: path
name: table
required: true
schema:
type: string
- in: header
name: X-Athena-Client
required: true
schema:
type: string
- in: header
name: apikey
required: true
schema:
type: string
- in: header
name: x-api-key
schema:
type: string
- in: header
name: Prefer
schema:
type: string
description: Set `return=minimal` for HTTP 204 responses.
responses:
'200':
description: Rows deleted
content:
application/json:
schema:
type: object
properties:
data:
type: array
items:
type: object
'204':
description: 'Delete succeeded with Prefer: return=minimal'
'400':
description: Missing filters
'500':
description: Internal error
/pipelines:
post:
summary: Run a config-driven pipeline (source → transform → sink)
description: |
Executes a pipeline with optional prebuilt reference and overrides. `source.client` and `sink.client` override the Postgres/Supabase pool per step; when omitted, `X-Athena-Client` is used. Optional column aliasing and `dry_run` are supported.
When gateway API keys are enforced, the key is validated against `X-Athena-Client`; step client overrides still route fetch/insert to other registered clients if specified.
Successful runs emit three rows to `pipeline_step_log` on the configured logging database (`gateway.logging_client`), correlatable via `pipeline_run_id` in the response.
parameters:
- in: header
name: X-Athena-Client
required: true
schema:
type: string
requestBody:
required: true
content:
application/json:
schema:
type: object
properties:
pipeline:
type: string
description: Prebuilt pipeline name from config/pipelines.yaml
source:
type: object
properties:
table_name:
type: string
view_name:
type: string
columns:
type: array
items:
type: string
conditions:
type: array
items:
type: object
properties:
eq_column:
type: string
eq_value:
type: string
limit:
type: integer
client:
type: string
description: Optional source step client override (falls back to X-Athena-Client).
transform:
type: object
properties:
group_by:
type: string
time_granularity:
type: string
enum:
- day
- hour
- minute
aggregation_column:
type: string
aggregation_strategy:
type: string
enum:
- cumulative_sum
aggregation_dedup:
type: boolean
column_aliases:
type: object
additionalProperties:
type: string
description: Optional map of source column names to sink aliases.
sink:
type: object
properties:
table_name:
type: string
client:
type: string
description: Optional sink step client override (falls back to X-Athena-Client).
dry_run:
type: boolean
description: When true, fetch+transform runs but sink inserts are skipped.
example:
source:
table_name: http_request_log
columns:
- client_name
- created_at
- status_code
limit: 100
transform:
group_by: client_name
aggregation_column: status_code
aggregation_strategy: cumulative_sum
sink:
table_name: gateway_rollups
dry_run: true
responses:
'200':
description: Pipeline run result
content:
application/json:
schema:
type: object
properties:
data:
type: array
description: Inserted rows (or preview rows for dry runs)
rows_fetched:
type: integer
rows_inserted:
type: integer
would_insert:
type: integer
nullable: true
dry_run:
type: boolean
source_client:
type: string
sink_client:
type: string
errors:
type: array
items:
type: object
properties:
index:
type: integer
error:
type: string
pipeline_run_id:
type: string
description: UUID correlating `pipeline_step_log` rows for this invocation.
example:
data: []
rows_fetched: 100
rows_inserted: 0
would_insert: 12
dry_run: true
source_client: athena_logging
sink_client: athena_logging
errors: []
pipeline_run_id: 0a9b5f6f-8a6c-4ba8-b41a-4a12ec2f5cb7
'400':
description: Bad request (e.g. missing X-Athena-Client or unknown pipeline)
'500':
description: Internal error
/pipelines/simulate:
post:
summary: Simulate a pipeline without writing
description: Executes fetch+transform only and returns a dry-run preview payload.
parameters:
- in: header
name: X-Athena-Client
required: true
schema:
type: string
requestBody:
required: true
content:
application/json:
schema:
type: object
description: Same schema as POST /pipelines.
responses:
'200':
description: Dry-run pipeline result
'400':
description: Bad request
'500':
description: Internal error
/pipelines/templates:
get:
summary: List available pipeline templates
description: Returns named pipeline templates loaded from config/pipelines.yaml.
parameters:
- in: header
name: X-Athena-Client
required: true
schema:
type: string
responses:
'200':
description: Template list
content:
application/json:
schema:
type: object
properties:
templates:
type: array
items:
type: object
properties:
name:
type: string
source_table:
type: string
sink_table:
type: string
has_transform:
type: boolean
source_client:
type: string
nullable: true
description: Optional `source.client` from YAML; omit uses request header client.
sink_client:
type: string
nullable: true
description: Optional `sink.client` from YAML; omit uses request header client.
'500':
description: Internal error
/admin/api-keys:
get:
summary: List all API keys
description: Requires the static admin key stored in `ATHENA_KEY_12`.
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
responses:
'200':
description: Paginated API key records
content:
application/json:
schema:
type: object
properties:
api_keys:
type: array
items:
$ref: '#/components/schemas/ApiKeyRecord'
'500':
$ref: '#/components/responses/DefaultServerError5xx'
post:
summary: Create a new API key
description: |
Creates a new API key record and returns a one-time plaintext credential (`ath_{public}.{secret}`).
Persist the returned secret securely; it is not retrievable later from the API.
tags:
- Admin
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
requestBody:
required: true
content:
application/json:
schema:
$ref: '#/components/schemas/CreateApiKeyRequest'
example:
name: gateway-readonly
description: Read-only key for dashboard fetch operations
client_name: athena_logging
rights:
- gateway.fetch.execute
- gateway.query.execute
responses:
'201':
description: API key created
content:
application/json:
schema:
$ref: '#/components/schemas/CreateApiKeyResponse'
example:
api_key: ath_abcd1234efgh5678.secretfragment
record:
id: f5c4dfb5-3318-4577-a0c3-ea03fc06f942
public_id: abcd1234efgh5678
name: gateway-readonly
description: Read-only key for dashboard fetch operations
client_name: athena_logging
is_active: true
rights:
- gateway.fetch.execute
- gateway.query.execute
'409':
description: Duplicate public_id
'500':
$ref: '#/components/responses/DefaultServerError5xx'
/admin/api-keys/{id}:
patch:
summary: Update an existing API key
description: Updates API key metadata, optional client binding, activation state, expiration, and grants.
tags:
- Admin
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
- $ref: '#/components/parameters/ApiKeyIdParam'
requestBody:
required: true
content:
application/json:
schema:
$ref: '#/components/schemas/UpdateApiKeyRequest'
responses:
'200':
description: API key updated
content:
application/json:
schema:
type: object
properties:
record:
$ref: '#/components/schemas/ApiKeyRecord'
'404':
description: API key not found
'500':
$ref: '#/components/responses/DefaultServerError5xx'
delete:
summary: Delete an API key
description: Removes (or archives) an API key so it can no longer authorize requests.
tags:
- Admin
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
- $ref: '#/components/parameters/ApiKeyIdParam'
responses:
'200':
description: API key removed
content:
application/json:
schema:
type: object
properties:
id:
type: string
format: uuid
'404':
description: API key not found
'500':
$ref: '#/components/responses/DefaultServerError5xx'
/admin/webhooks:
get:
summary: List gateway webhooks
description: Definitions for outbound HTTP hooks fired after successful gateway operations (requires static admin key).
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
- name: limit
in: query
schema:
type: integer
default: 50
- name: offset
in: query
schema:
type: integer
default: 0
- name: client_name
in: query
description: When set, only webhooks targeting this Athena client (`client_name` / `X-Athena-Client`) are returned.
schema:
type: string
responses:
'200':
description: Webhooks and total count
content:
application/json:
schema:
$ref: '#/components/schemas/ApiSuccessEnvelope'
'500':
$ref: '#/components/responses/DefaultServerError5xx'
post:
summary: Create or upsert a gateway webhook (idempotent natural key)
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
requestBody:
required: true
content:
application/json:
schema:
type: object
additionalProperties: true
responses:
'200':
description: Webhook saved
content:
application/json:
schema:
$ref: '#/components/schemas/ApiSuccessEnvelope'
'500':
$ref: '#/components/responses/DefaultServerError5xx'
/admin/webhooks/events:
get:
summary: List webhook event types
description: |
Returns every supported `route_key` for `gateway_webhook` definitions, with titles and descriptions
(gateway, PostgREST, and schema/management DDL triggers). Requires the static admin key.
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
responses:
'200':
description: Event catalog in `data.events`
content:
application/json:
schema:
$ref: '#/components/schemas/ApiSuccessEnvelope'
'500':
$ref: '#/components/responses/DefaultServerError5xx'
/admin/webhooks/{id}:
get:
summary: Get a gateway webhook by id
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
- $ref: '#/components/parameters/WebhookIdParam'
responses:
'200':
description: Webhook record
content:
application/json:
schema:
$ref: '#/components/schemas/ApiSuccessEnvelope'
'404':
description: Webhook not found
'500':
$ref: '#/components/responses/DefaultServerError5xx'
patch:
summary: Update a gateway webhook
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
- $ref: '#/components/parameters/WebhookIdParam'
requestBody:
required: true
content:
application/json:
schema:
type: object
additionalProperties: true
responses:
'200':
description: Updated webhook
content:
application/json:
schema:
$ref: '#/components/schemas/ApiSuccessEnvelope'
'404':
description: Webhook not found
'500':
$ref: '#/components/responses/DefaultServerError5xx'
delete:
summary: Delete a gateway webhook
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
- $ref: '#/components/parameters/WebhookIdParam'
responses:
'200':
description: Deleted
content:
application/json:
schema:
$ref: '#/components/schemas/ApiSuccessEnvelope'
'404':
description: Webhook not found
'500':
$ref: '#/components/responses/DefaultServerError5xx'
/admin/webhooks/{id}/deliveries:
get:
summary: List webhook delivery attempts
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
- $ref: '#/components/parameters/WebhookIdParam'
- name: limit
in: query
schema:
type: integer
- name: offset
in: query
schema:
type: integer
responses:
'200':
description: Delivery log rows
content:
application/json:
schema:
$ref: '#/components/schemas/ApiSuccessEnvelope'
'404':
description: Webhook not found
'500':
$ref: '#/components/responses/DefaultServerError5xx'
/admin/webhooks/{id}/test:
post:
summary: Execute a test webhook delivery
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
- $ref: '#/components/parameters/WebhookIdParam'
requestBody:
required: true
content:
application/json:
schema:
type: object
additionalProperties: true
responses:
'200':
description: Test completed
content:
application/json:
schema:
$ref: '#/components/schemas/ApiSuccessEnvelope'
'500':
$ref: '#/components/responses/DefaultServerError5xx'
/admin/api-key-rights:
get:
summary: List API key rights
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
responses:
'200':
description: Available rights
content:
application/json:
schema:
type: object
properties:
rights:
type: array
items:
$ref: '#/components/schemas/ApiKeyRightRecord'
'500':
$ref: '#/components/responses/DefaultServerError5xx'
post:
summary: Create a new API key right
description: Defines a reusable right/capability string that can be granted to one or more API keys.
tags:
- Admin
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
requestBody:
required: true
content:
application/json:
schema:
$ref: '#/components/schemas/ApiKeyRightRequest'
responses:
'201':
description: API key right created
content:
application/json:
schema:
type: object
properties:
right:
$ref: '#/components/schemas/ApiKeyRightRecord'
'500':
$ref: '#/components/responses/DefaultServerError5xx'
/admin/api-key-rights/{id}:
patch:
summary: Update an API key right
description: Renames or updates metadata for an existing API key right definition.
tags:
- Admin
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
- $ref: '#/components/parameters/ApiKeyIdParam'
requestBody:
required: true
content:
application/json:
schema:
$ref: '#/components/schemas/ApiKeyRightRequest'
responses:
'200':
description: API key right updated
content:
application/json:
schema:
type: object
properties:
right:
$ref: '#/components/schemas/ApiKeyRightRecord'
'404':
description: Right not found
'500':
$ref: '#/components/responses/DefaultServerError5xx'
delete:
summary: Delete an API key right
description: Deletes an API key right definition and removes associated grants.
tags:
- Admin
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
- $ref: '#/components/parameters/ApiKeyIdParam'
responses:
'200':
description: API key right removed
content:
application/json:
schema:
type: object
properties:
id:
type: string
format: uuid
'404':
description: Right not found
'500':
$ref: '#/components/responses/DefaultServerError5xx'
/admin/api-key-config:
get:
summary: Get global API key enforcement configuration
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
responses:
'200':
description: Global+per-client config
content:
application/json:
schema:
$ref: '#/components/schemas/ApiKeyConfigResponse'
'500':
$ref: '#/components/responses/DefaultServerError5xx'
put:
summary: Toggle global API key enforcement
description: Enables or disables global API key enforcement for routes that honor centralized key policy.
tags:
- Admin
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
requestBody:
required: true
content:
application/json:
schema:
$ref: '#/components/schemas/ApiKeyConfigRequest'
responses:
'200':
description: Updated global config
content:
application/json:
schema:
$ref: '#/components/schemas/ApiKeyConfigResponse'
'500':
$ref: '#/components/responses/DefaultServerError5xx'
/admin/api-key-clients:
get:
summary: List per-client API key enforcement overrides
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
responses:
'200':
description: Client configs
content:
application/json:
schema:
$ref: '#/components/schemas/ApiKeyClientListResponse'
'500':
$ref: '#/components/responses/DefaultServerError5xx'
/admin/api-key-clients/{client_name}:
put:
summary: Update or insert a client's enforcement override
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
- name: client_name
in: path
required: true
schema:
type: string
requestBody:
required: true
content:
application/json:
schema:
$ref: '#/components/schemas/ApiKeyClientConfigRequest'
responses:
'200':
description: Client config upserted
content:
application/json:
schema:
type: object
properties:
client:
$ref: '#/components/schemas/ApiKeyClientConfig'
'500':
$ref: '#/components/responses/DefaultServerError5xx'
delete:
summary: Remove a client's enforcement override
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
- name: client_name
in: path
required: true
schema:
type: string
responses:
'200':
description: Client override deleted
content:
application/json:
schema:
type: object
properties:
client_name:
type: string
'404':
description: Client config not found
'500':
$ref: '#/components/responses/DefaultServerError5xx'
/admin/clients:
get:
summary: List Athena clients from the database-backed catalog
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
responses:
'200':
description: Athena clients and their runtime state
content:
application/json:
schema:
$ref: '#/components/schemas/AdminClientsResponse'
'500':
$ref: '#/components/responses/DefaultServerError5xx'
post:
summary: Create a database-backed Athena client
description: Registers a new client in the catalog so it can be resolved by `X-Athena-Client` routing.
tags:
- Admin
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
requestBody:
required: true
content:
application/json:
schema:
$ref: '#/components/schemas/SaveAthenaClientRequest'
responses:
'201':
description: Athena client created
content:
application/json:
schema:
$ref: '#/components/schemas/AdminClientResponse'
'500':
$ref: '#/components/responses/DefaultServerError5xx'
/admin/clients/{client_name}:
patch:
summary: Update an Athena client
description: Updates client metadata and connection source fields for an existing catalog entry.
tags:
- Admin
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
- name: client_name
in: path
required: true
schema:
type: string
requestBody:
required: true
content:
application/json:
schema:
$ref: '#/components/schemas/SaveAthenaClientRequest'
responses:
'200':
description: Athena client updated
content:
application/json:
schema:
$ref: '#/components/schemas/AdminClientResponse'
'500':
$ref: '#/components/responses/DefaultServerError5xx'
delete:
summary: Soft-delete an Athena client
description: Soft-deletes the client in catalog storage and removes it from active runtime routing.
tags:
- Admin
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
- name: client_name
in: path
required: true
schema:
type: string
responses:
'200':
description: Athena client deleted
content:
application/json:
schema:
$ref: '#/components/schemas/AdminClientResponse'
'404':
description: Athena client not found
'500':
$ref: '#/components/responses/DefaultServerError5xx'
/admin/clients/{client_name}/freeze:
put:
summary: Freeze or unfreeze an Athena client
description: Toggles temporary routing disablement without deleting the underlying catalog entry.
tags:
- Admin
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
- name: client_name
in: path
required: true
schema:
type: string
requestBody:
required: true
content:
application/json:
schema:
$ref: '#/components/schemas/FreezeAthenaClientRequest'
responses:
'200':
description: Athena client freeze state updated
content:
application/json:
schema:
$ref: '#/components/schemas/AdminClientResponse'
'404':
description: Athena client not found
'500':
$ref: '#/components/responses/DefaultServerError5xx'
/admin/clients/statistics:
get:
summary: List Athena client statistics
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
responses:
'200':
description: Aggregated request and operation statistics
content:
application/json:
schema:
$ref: '#/components/schemas/ClientStatisticsListResponse'
'500':
$ref: '#/components/responses/DefaultServerError5xx'
/admin/clients/statistics/refresh:
post:
summary: Rebuild Athena client statistics from gateway logs
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
responses:
'200':
description: Statistics refreshed
content:
application/json:
schema:
$ref: '#/components/schemas/ClientStatisticsListResponse'
'500':
$ref: '#/components/responses/DefaultServerError5xx'
/admin/clients/{client_name}/statistics:
get:
summary: Inspect Athena client statistics and touched tables
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
- name: client_name
in: path
required: true
schema:
type: string
responses:
'200':
description: Per-client statistics
content:
application/json:
schema:
$ref: '#/components/schemas/ClientStatisticsDetailResponse'
'404':
description: Client statistics not found
'500':
$ref: '#/components/responses/DefaultServerError5xx'
/admin/clients/{client_name}/statistics/drilldown:
get:
summary: List gateway operation log rows for a client table operation
description: |
Returns rows from `gateway_operation_log` filtered by `client`, `table_name`, and `operation`, with optional
`status` (`all`, `errors`, or `normal`) and pagination. Requires the static admin key (`ATHENA_KEY_12`) and a
connected `athena_logging` pool.
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
- name: client_name
in: path
required: true
schema:
type: string
- name: table_name
in: query
required: true
schema:
type: string
description: Table name (matches `gateway_operation_log.table_name`).
- name: operation
in: query
required: true
schema:
type: string
description: Operation name (matches `gateway_operation_log.operation`).
- name: status
in: query
required: false
schema:
type: string
enum:
- all
- errors
- normal
default: all
description: |
`errors` includes rows where `error` is true or `status_code` is at least 400; `normal` excludes those.
- name: limit
in: query
required: false
schema:
type: integer
minimum: 1
maximum: 500
default: 100
- name: offset
in: query
required: false
schema:
type: integer
minimum: 0
default: 0
responses:
'200':
description: Drilldown rows and pagination echo
content:
application/json:
schema:
$ref: '#/components/schemas/ClientStatisticsDrilldownData'
'400':
description: Invalid query parameters
'500':
$ref: '#/components/responses/DefaultServerError5xx'
/admin/clients/{client_name}/query-optimizations:
get:
summary: List query optimization recommendations for a client
description: |
Returns stored recommendations from the logging database with optional status filter and pagination.
Requires the static admin key (`ATHENA_KEY_12`) and a connected `athena_logging` pool.
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
- name: client_name
in: path
required: true
schema:
type: string
- name: status
in: query
required: false
schema:
type: string
enum:
- all
- open
- applied
- dismissed
description: Filter by recommendation status; omit or `all` for every status.
- name: limit
in: query
required: false
schema:
type: integer
minimum: 1
maximum: 500
default: 100
- name: offset
in: query
required: false
schema:
type: integer
minimum: 0
default: 0
responses:
'200':
description: Recommendations and pagination echo
content:
application/json:
schema:
$ref: '#/components/schemas/QueryOptimizationRecommendationsListData'
'400':
description: Invalid status filter
'500':
$ref: '#/components/responses/DefaultServerError5xx'
/admin/clients/{client_name}/query-optimizations/refresh:
post:
summary: Refresh query optimization recommendations for a client
description: |
Recomputes recommendations for the client and returns the new run plus rows.
Requires the static admin key (`ATHENA_KEY_12`) and a connected `athena_logging` pool.
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
- name: client_name
in: path
required: true
schema:
type: string
responses:
'200':
description: Refresh run and recommendations
content:
application/json:
schema:
$ref: '#/components/schemas/QueryOptimizationRefreshData'
'500':
$ref: '#/components/responses/DefaultServerError5xx'
/admin/clients/{client_name}/query-optimizations/runs:
get:
summary: List query optimization runs for a client
description: |
Returns historical refresh runs with pagination.
Requires the static admin key (`ATHENA_KEY_12`) and a connected `athena_logging` pool.
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
- name: client_name
in: path
required: true
schema:
type: string
- name: limit
in: query
required: false
schema:
type: integer
minimum: 1
maximum: 500
default: 100
- name: offset
in: query
required: false
schema:
type: integer
minimum: 0
default: 0
responses:
'200':
description: Runs and pagination echo
content:
application/json:
schema:
$ref: '#/components/schemas/QueryOptimizationRunsListData'
'500':
$ref: '#/components/responses/DefaultServerError5xx'
/admin/clients/{client_name}/query-optimizations/{recommendation_id}/apply:
post:
summary: Apply a query optimization recommendation
description: |
Applies the recommendation identified by `recommendation_id` for `client_name`.
Optional JSON body may set `actor` for audit metadata.
Requires the static admin key (`ATHENA_KEY_12`) and a connected `athena_logging` pool.
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
- name: client_name
in: path
required: true
schema:
type: string
- name: recommendation_id
in: path
required: true
schema:
type: integer
format: int64
requestBody:
required: false
content:
application/json:
schema:
$ref: '#/components/schemas/ApplyQueryOptimizationRequest'
responses:
'200':
description: Apply result
content:
application/json:
schema:
$ref: '#/components/schemas/QueryOptimizationApplyData'
'404':
description: Recommendation not found for this client and id
'500':
$ref: '#/components/responses/DefaultServerError5xx'
/admin/vacuum-health:
get:
summary: List latest vacuum health snapshot per Postgres client
description: |
Returns the most recent `vacuum_health_snapshots` row per `client_name` stored in the logging database
(populated by the background vacuum health collector). Requires the static admin key (`ATHENA_KEY_12`).
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
responses:
'200':
description: Latest vacuum health summaries
content:
application/json:
schema:
$ref: '#/components/schemas/VacuumHealthListResponse'
'500':
$ref: '#/components/responses/DefaultServerError5xx'
/admin/vacuum-health/{client_name}:
get:
summary: Latest vacuum health snapshot and per-table stats for one client
description: |
Returns the latest snapshot for `client_name` plus all `vacuum_health_table_stats` rows for that snapshot.
Requires the static admin key (`ATHENA_KEY_12`).
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
- name: client_name
in: path
required: true
schema:
type: string
responses:
'200':
description: Snapshot and per-table statistics
content:
application/json:
schema:
$ref: '#/components/schemas/VacuumHealthDetailResponse'
'404':
description: No vacuum health snapshots for this client
'500':
$ref: '#/components/responses/DefaultServerError5xx'
/admin/admission-events:
get:
summary: List admission limiter events with optional decision and client filters
description: |
Returns rows from `gateway_admission_events` in descending `created_at` order.
Requires the static admin key (`ATHENA_KEY_12`) and a connected `athena_logging` pool.
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
- name: decision
in: query
required: false
schema:
type: string
description: Optional decision filter (for example `deferred` or `rejected`).
- name: client
in: query
required: false
schema:
type: string
description: Optional client name filter (matches `gateway_admission_events.client_name`).
- name: limit
in: query
required: false
schema:
type: integer
minimum: 1
maximum: 500
default: 100
- name: offset
in: query
required: false
schema:
type: integer
minimum: 0
default: 0
responses:
'200':
description: Admission event rows and applied filters
content:
application/json:
schema:
$ref: '#/components/schemas/AdmissionEventsListData'
'500':
$ref: '#/components/responses/DefaultServerError5xx'
/admin/backups:
post:
summary: Create a database backup and upload to S3
description: |
Uses `pg_dump` against the provided `client_name`, uploads the archive to the configured S3 bucket, and stores an optional `label` in the object metadata.
Requires the static admin key (`ATHENA_KEY_12`) and S3 configuration (`ATHENA_BACKUP_S3_BUCKET`, `ATHENA_BACKUP_S3_PREFIX`, and credentials).
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
requestBody:
required: true
content:
application/json:
schema:
$ref: '#/components/schemas/CreateBackupRequest'
responses:
'200':
description: Backup created and uploaded
content:
application/json:
schema:
type: object
properties:
key:
type: string
client_name:
type: string
label:
type: string
nullable: true
'400':
description: Missing or unknown client_name
'401':
description: Invalid admin API key
'503':
description: S3 not configured
get:
summary: List available backups in S3
description: Returns S3 backup objects filtered by optional `client_name` prefix, newest first.
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
- name: client_name
in: query
required: false
schema:
type: string
description: When set, only list backups for this client.
responses:
'200':
description: Backup listing
content:
application/json:
schema:
type: object
properties:
backups:
type: array
items:
$ref: '#/components/schemas/BackupObject'
'401':
description: Invalid admin API key
'503':
description: S3 not configured
/admin/backups/config:
get:
summary: Return backup storage configuration metadata
description: Returns non-secret S3 backup configuration (bucket, region, prefix, endpoint) for operators.
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
responses:
'200':
description: Backup storage configuration
content:
application/json:
schema:
type: object
'401':
description: Invalid admin API key
'503':
description: S3 not configured
/admin/backups/jobs:
get:
summary: List backup and restore jobs
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
- name: client_name
in: query
required: false
schema:
type: string
- name: status
in: query
required: false
schema:
type: string
- name: job_type
in: query
required: false
schema:
type: string
- name: limit
in: query
required: false
schema:
type: integer
minimum: 1
maximum: 500
default: 50
responses:
'200':
description: Backup job listing
content:
application/json:
schema:
type: object
'401':
description: Invalid admin API key
'500':
$ref: '#/components/responses/DefaultServerError5xx'
/admin/backups/jobs/{id}:
get:
summary: Get a backup or restore job with logs
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
- name: id
in: path
required: true
schema:
type: integer
format: int64
responses:
'200':
description: Backup job and recent logs
content:
application/json:
schema:
type: object
'401':
description: Invalid admin API key
'404':
description: Job not found
'500':
$ref: '#/components/responses/DefaultServerError5xx'
delete:
summary: Delete a completed, failed, or cancelled backup job
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
- name: id
in: path
required: true
schema:
type: integer
format: int64
responses:
'200':
description: Backup job deleted
content:
application/json:
schema:
type: object
'400':
description: Job is still running or pending
'401':
description: Invalid admin API key
'404':
description: Job not found
'500':
$ref: '#/components/responses/DefaultServerError5xx'
/admin/backups/jobs/{id}/cancel:
post:
summary: Cancel a running or pending backup or restore job
description: |
Marks the job as cancelled in `athena_logging` and signals the worker on this Athena process to stop `pg_dump` or `pg_restore` if still running.
Requires the static admin key (`ATHENA_KEY_12`).
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
- name: id
in: path
required: true
schema:
type: integer
format: int64
responses:
'200':
description: Job cancelled or cancellation recorded
'400':
description: Job is not running or pending
'401':
description: Invalid admin API key
'404':
description: Job not found
'500':
$ref: '#/components/responses/DefaultServerError5xx'
/admin/backups/schedules:
get:
summary: List backup schedules
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
responses:
'200':
description: Backup schedules listed
content:
application/json:
schema:
type: object
'401':
description: Invalid admin API key
'500':
$ref: '#/components/responses/DefaultServerError5xx'
post:
summary: Create a backup schedule
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
requestBody:
required: true
content:
application/json:
schema:
type: object
responses:
'200':
description: Backup schedule created
content:
application/json:
schema:
type: object
'400':
description: Invalid schedule payload
'401':
description: Invalid admin API key
'500':
$ref: '#/components/responses/DefaultServerError5xx'
/admin/backups/schedules/{id}:
patch:
summary: Update a backup schedule
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
- name: id
in: path
required: true
schema:
type: integer
format: int64
requestBody:
required: true
content:
application/json:
schema:
type: object
responses:
'200':
description: Backup schedule updated
content:
application/json:
schema:
type: object
'400':
description: Invalid schedule payload
'401':
description: Invalid admin API key
'404':
description: Schedule not found
'500':
$ref: '#/components/responses/DefaultServerError5xx'
delete:
summary: Delete a backup schedule
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
- name: id
in: path
required: true
schema:
type: integer
format: int64
responses:
'200':
description: Backup schedule deleted
content:
application/json:
schema:
type: object
'401':
description: Invalid admin API key
'404':
description: Schedule not found
'500':
$ref: '#/components/responses/DefaultServerError5xx'
/admin/backups/{key}/restore:
post:
summary: Restore a database backup from S3
description: |
Downloads the backup identified by the S3 object key, runs `pg_restore` into the target `client_name` Postgres pool, and returns the key plus client.
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
- name: key
in: path
required: true
schema:
type: string
description: S3 object key for the backup (URL-encoded, may contain slashes).
requestBody:
required: true
content:
application/json:
schema:
$ref: '#/components/schemas/RestoreBackupRequest'
responses:
'200':
description: Restore completed
content:
application/json:
schema:
type: object
properties:
key:
type: string
client_name:
type: string
'400':
description: Missing key or client_name
'401':
description: Invalid admin API key
'503':
description: S3 not configured
/admin/backups/{key}/download:
get:
summary: Download a backup archive from S3
description: |
Streams the raw `application/gzip` backup bytes with a `Content-Disposition: attachment` filename.
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
- name: key
in: path
required: true
description: S3 object key for the backup (URL-encoded, may contain slashes).
schema:
type: string
responses:
'200':
description: Backup archive
content:
application/gzip:
schema:
type: string
format: binary
'400':
description: Missing backup key
'401':
description: Invalid admin API key
'404':
description: Backup not found
'503':
description: S3 not configured
/admin/backups/{key}:
delete:
summary: Delete a backup from S3
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
- name: key
in: path
required: true
description: S3 object key for the backup (URL-encoded, may contain slashes).
schema:
type: string
responses:
'200':
description: Backup deleted
content:
application/json:
schema:
type: object
properties:
key:
type: string
'400':
description: Missing backup key
'401':
description: Invalid admin API key
'404':
description: Backup not found
'503':
description: S3 not configured
/admin/provision:
post:
summary: Provision a Postgres database with the Athena schema
description: |
Runs the bundled provisioning SQL against either a direct `uri` or a registered `client_name`.
When `register` is true and `uri` is provided, the client is added to the runtime catalog after provisioning.
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
requestBody:
required: true
content:
application/json:
schema:
$ref: '#/components/schemas/ProvisionRequest'
responses:
'200':
description: Provisioning completed
content:
application/json:
schema:
type: object
properties:
statements_executed:
type: integer
client:
type: string
registered:
type: string
nullable: true
tables:
type: array
items:
type: string
'400':
description: Ambiguous or missing target
'401':
description: Invalid admin API key
'503':
description: Target client unavailable
/admin/provision/status:
get:
summary: Check whether a client database is provisioned
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
- name: client_name
in: query
required: true
schema:
type: string
description: Registered client to check.
responses:
'200':
description: Provisioning status
content:
application/json:
schema:
$ref: '#/components/schemas/ProvisionStatusResponse'
'401':
description: Invalid admin API key
'503':
description: Client unavailable
/admin/provision/instances:
post:
summary: Spin up a local Docker-backed Postgres instance
description: |
Creates (or reuses) a managed local Postgres container, optionally provisions Athena schema,
and can register the resulting connection in runtime and/or catalog client registries.
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
requestBody:
required: true
content:
application/json:
schema:
$ref: '#/components/schemas/SpinUpInstanceRequest'
responses:
'200':
description: Postgres instance is ready
'400':
description: Invalid spin-up payload
'401':
description: Invalid admin API key
'409':
description: Container conflict (already exists and reuse disabled)
'503':
description: Docker unavailable
/admin/provision/instances/{container_name}:
get:
summary: Inspect a local managed Postgres instance
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
- name: container_name
in: path
required: true
schema:
type: string
- name: client_name
in: query
required: false
schema:
type: string
responses:
'200':
description: Instance status loaded
'401':
description: Invalid admin API key
'404':
description: Instance not found
'503':
description: Docker unavailable
delete:
summary: Delete a local managed Postgres instance
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
- name: container_name
in: path
required: true
schema:
type: string
requestBody:
required: false
content:
application/json:
schema:
$ref: '#/components/schemas/DeleteInstanceRequest'
responses:
'200':
description: Instance deleted
'401':
description: Invalid admin API key
'503':
description: Docker unavailable
/admin/provision/instances/{container_name}/start:
post:
summary: Start a managed Postgres instance
description: Optionally reconnects the runtime client when `sync_runtime` is true (default).
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
- name: container_name
in: path
required: true
schema:
type: string
requestBody:
required: false
content:
application/json:
schema:
$ref: '#/components/schemas/InstanceLifecycleRequest'
responses:
'200':
description: Instance started
'401':
description: Invalid admin API key
'404':
description: Instance not found
'503':
description: Docker unavailable
/admin/provision/instances/{container_name}/stop:
post:
summary: Stop a managed Postgres instance
description: When `sync_runtime` is true (default), marks the linked runtime client unavailable.
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
- name: container_name
in: path
required: true
schema:
type: string
requestBody:
required: false
content:
application/json:
schema:
$ref: '#/components/schemas/InstanceLifecycleRequest'
responses:
'200':
description: Instance stopped
'401':
description: Invalid admin API key
'404':
description: Instance not found
'503':
description: Docker unavailable
/admin/provision/instances/{container_name}/bindings:
post:
summary: Bind a managed instance host port to a public route mapping
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
- name: container_name
in: path
required: true
schema:
type: string
requestBody:
required: true
content:
application/json:
schema:
$ref: '#/components/schemas/BindInstancePortRouteRequest'
responses:
'200':
description: Binding saved
'400':
description: Invalid payload or missing client
'401':
description: Invalid admin API key
'404':
description: Instance not found
'503':
description: Docker unavailable or port not published
/admin/provision/providers/neon:
post:
summary: Provision/register a Neon Postgres database
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
requestBody:
required: true
content:
application/json:
schema:
$ref: '#/components/schemas/NeonProviderProvisionRequest'
responses:
'200':
description: Neon database provisioned
'400':
description: Invalid provider payload
'401':
description: Invalid admin API key
'503':
description: Provider unavailable
/admin/provision/providers/railway:
post:
summary: Provision/register a Railway Postgres database
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
requestBody:
required: true
content:
application/json:
schema:
$ref: '#/components/schemas/RailwayProviderProvisionRequest'
responses:
'200':
description: Railway database provisioned
'400':
description: Invalid provider payload
'401':
description: Invalid admin API key
'503':
description: Provider unavailable
/admin/provision/providers/render:
post:
summary: Provision/register a Render Postgres database
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
requestBody:
required: true
content:
application/json:
schema:
$ref: '#/components/schemas/RenderProviderProvisionRequest'
responses:
'200':
description: Render database provisioned
'400':
description: Invalid provider payload
'401':
description: Invalid admin API key
'503':
description: Provider unavailable
/admin/provision/local/databases:
get:
summary: List local cluster PostgreSQL databases for a registered server client
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
- name: client_name
in: query
required: true
schema:
type: string
description: Registered client connected to the target Postgres server.
responses:
'200':
description: Database inventory loaded
content:
application/json:
schema:
$ref: '#/components/schemas/LocalClusterDatabasesResponse'
'401':
description: Invalid admin API key
'503':
description: Client unavailable
post:
summary: Create a local cluster PostgreSQL database for a registered server client
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
requestBody:
required: true
content:
application/json:
schema:
allOf:
- $ref: '#/components/schemas/LocalClusterCreateDatabaseRequest'
- type: object
required:
- client_name
responses:
'201':
description: Local database created
'400':
description: Invalid payload
'401':
description: Invalid admin API key
'409':
description: Database already exists
'503':
description: Client unavailable
/api/v2/supabase/ssl_enforcement:
post:
summary: Toggle Supabase SSL enforcement for a project
requestBody:
required: true
content:
application/json:
schema:
type: object
properties:
enabled:
type: boolean
description: Set to true to enable SSL enforcement, false to disable
access_token:
type: string
description: Optional override for SUPABASE_ACCESS_TOKEN
project_ref:
type: string
description: Optional override for PROJECT_REF
required:
- enabled
responses:
'200':
description: SSL enforcement status returned
content:
application/json:
schema:
type: object
properties:
status:
type: string
example: success
message:
type: string
data:
type: object
properties:
currentConfig:
type: object
properties:
database:
type: boolean
appliedSuccessfully:
type: boolean
'400':
description: Missing credentials or bad payload
'500':
description: Supabase API error
/router/registry:
get:
summary: List Athena router registry entries
responses:
'200':
description: An array of router registry objects
content:
application/json:
schema:
type: array
items:
type: object
'500':
description: Failed to load router registry entries
/metrics:
get:
summary: Prometheus metrics endpoint
description: Exposes Prometheus text metrics including uptime, request counters, management mutation counters, cluster probe gauges, and 24-hour aggregates.
responses:
'200':
description: Metrics payload
content:
text/plain:
schema:
type: string
example: |
# TYPE athena_uptime_seconds gauge
athena_uptime_seconds 123.0
'500':
$ref: '#/components/responses/DefaultServerError5xx'
/registry:
get:
summary: List API registry entries
parameters:
- in: header
name: Cache-Control
schema:
type: string
description: Set to `no-cache` to skip the cached response.
responses:
'200':
description: API registry rows from Supabase
content:
application/json:
schema:
type: array
items:
type: object
'500':
description: Failed to list API registry entries
/registry/{api_registry_id}:
get:
summary: Lookup an API registry entry by ID
parameters:
- in: path
name: api_registry_id
required: true
schema:
type: string
description: Row identifier from the Supabase table
- in: header
name: Cache-Control
schema:
type: string
description: Set to `no-cache` to bypass the cached entry.
responses:
'200':
description: Matching registry entry (wrapped in an array)
content:
application/json:
schema:
type: array
items:
type: object
'500':
description: Failed to fetch the registry entry
/schema/clients:
get:
summary: List configured Postgres clients
description: Protected by the static admin key (`ATHENA_KEY_12`).
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
responses:
'200':
description: A JSON object containing a clients array
content:
application/json:
schema:
$ref: '#/components/schemas/ClientsResponse'
'500':
$ref: '#/components/responses/DefaultServerError5xx'
/clients:
get:
summary: List Athena/Postgres clients (admin)
description: Same response as `/schema/clients`, but exposed without the `schema` prefix.
parameters:
- $ref: '#/components/parameters/AdminApiKeyHeader'
responses:
'200':
description: Configured clients
content:
application/json:
schema:
$ref: '#/components/schemas/ClientsResponse'
'500':
$ref: '#/components/responses/DefaultServerError5xx'
/schema/tables:
get:
summary: List tables for the selected Postgres client
parameters:
- in: header
name: X-Athena-Client
required: true
schema:
type: string
description: Selects which Postgres pool provides the tables.
responses:
'200':
description: Table schema metadata
content:
application/json:
schema:
type: object
properties:
tables:
type: array
items:
type: object
properties:
table_schema:
type: string
table_name:
type: string
'400':
description: Missing or unknown X-Athena-Client
'500':
description: Failed to query information_schema.tables
/schema/columns:
get:
summary: Describe columns for a given table
parameters:
- in: header
name: X-Athena-Client
required: true
schema:
type: string
- in: header
name: X-API-Key
required: false
schema:
type: string
description: Optional API key (also apikey, X-Athena-Key, Authorization Bearer)
- in: query
name: table_name
required: true
schema:
type: string
description: Postgres table name to describe
- in: query
name: table_schema
required: false
schema:
type: string
description: Optional schema name; when provided, restricts columns to this schema
responses:
'200':
description: Column metadata
content:
application/json:
schema:
type: object
properties:
columns:
type: array
items:
type: object
properties:
column_name:
type: string
data_type:
type: string
nullable: true
column_default:
type: string
nullable: true
is_nullable:
type: string
nullable: true
'400':
description: Missing header or invalid table_name
'500':
description: Failed to fetch column metadata
/schema/migrations:
get:
summary: List schema migrations (Supabase-style)
description: Returns migration records from supabase_migrations.schema_migrations. If the table does not exist, returns an empty array with a message instead of an error.
parameters:
- in: header
name: X-Athena-Client
required: true
schema:
type: string
responses:
'200':
description: Migrations list or empty with message when table absent
content:
application/json:
schema:
type: object
properties:
migrations:
type: array
items:
type: object
properties:
version:
type: string
nullable: true
name:
type: string
nullable: true
message:
type: string
description: Present when migrations table does not exist
'400':
description: Missing X-Athena-Client
'500':
description: Other database error
/storage/objects:
post:
summary: List objects in an S3 bucket (ListObjectsV2)
requestBody:
required: true
content:
application/json:
schema:
$ref: '#/components/schemas/StorageListObjectsRequest'
responses:
'200':
description: Object listing
'400':
description: Invalid request
'500':
$ref: '#/components/responses/DefaultServerError5xx'
/storage/objects/url:
post:
summary: Generate a presigned GET URL for an object
requestBody:
required: true
content:
application/json:
schema:
$ref: '#/components/schemas/StorageGetObjectRequest'
responses:
'200':
description: Presigned download URL
'400':
description: Invalid request
'500':
$ref: '#/components/responses/DefaultServerError5xx'
/storage/objects/delete:
post:
summary: Delete an object
requestBody:
required: true
content:
application/json:
schema:
$ref: '#/components/schemas/StorageDeleteObjectRequest'
responses:
'200':
description: Object deleted
'400':
description: Invalid request
'500':
$ref: '#/components/responses/DefaultServerError5xx'
/storage/objects/folder:
post:
summary: Create a folder placeholder (prefix) in the bucket
requestBody:
required: true
content:
application/json:
schema:
$ref: '#/components/schemas/StorageCreateFolderRequest'
responses:
'200':
description: Folder created
'400':
description: Invalid request
'500':
$ref: '#/components/responses/DefaultServerError5xx'
/storage/objects/upload-url:
post:
summary: Generate a presigned PUT URL for upload
requestBody:
required: true
content:
application/json:
schema:
$ref: '#/components/schemas/StoragePresignUploadRequest'
responses:
'200':
description: Presigned upload URL
'400':
description: Invalid request
'500':
$ref: '#/components/responses/DefaultServerError5xx'
/storage/buckets/cors:
post:
summary: Read bucket CORS configuration (via s3cmd when available)
requestBody:
required: true
content:
application/json:
schema:
$ref: '#/components/schemas/StorageBucketCorsRequest'
responses:
'200':
description: CORS rules or message
'400':
description: Invalid request
'500':
$ref: '#/components/responses/DefaultServerError5xx'
/storage/buckets/cors/set:
post:
summary: Apply CORS rules to a bucket
requestBody:
required: true
content:
application/json:
schema:
$ref: '#/components/schemas/StorageSetBucketCorsRequest'
responses:
'200':
description: CORS updated
'400':
description: Invalid request
'500':
$ref: '#/components/responses/DefaultServerError5xx'
/storage/buckets/cors/delete:
post:
summary: Remove CORS configuration from a bucket
requestBody:
required: true
content:
application/json:
schema:
$ref: '#/components/schemas/StorageBucketCorsRequest'
responses:
'200':
description: CORS removed
'400':
description: Invalid request
'500':
$ref: '#/components/responses/DefaultServerError5xx'
/openapi.yaml:
get:
summary: Download the embedded OpenAPI YAML
responses:
'200':
description: OpenAPI spec fixture served by the API
content:
application/yaml:
schema:
type: string
'500':
description: Failed to read openapi.yaml
/openapi-wss.yaml:
get:
summary: Download the embedded WebSocket OpenAPI YAML
responses:
'200':
description: WebSocket OpenAPI spec fixture served by the API
content:
application/yaml:
schema:
type: string
'500':
description: Failed to read openapi-wss.yaml
/wss/info:
get:
summary: Read the WebSocket gateway contract
description: Returns rollout metadata and the current WebSocket gateway message contract.
responses:
'200':
description: WebSocket gateway contract metadata
content:
application/json:
schema:
type: object
properties:
status:
type: string
example: success
message:
type: string
example: Athena WebSocket gateway scaffold
data:
type: object
properties:
transport:
type: string
example: wss
path:
type: string
example: /wss/gateway
state:
type: string
example: scaffolded
notes:
type: array
items:
type: string
actions:
type: array
items:
type: string
example:
- gateway.fetch
- gateway.insert
- gateway.update
- gateway.delete
- gateway.query
'500':
$ref: '#/components/responses/DefaultServerError5xx'
/docs:
get:
summary: Redirect to the hosted Athena docs
responses:
'308':
description: Permanent redirect to https://xylex.group/docs/athena
headers:
Location:
schema:
type: string
format: uri
'500':
$ref: '#/components/responses/DefaultServerError5xx'
/public/{route_key}/{op}:
post:
summary: Dispatch a public route alias to gateway operations
description: Resolves a configured public route key to a provisioned Athena client and forwards to gateway query/fetch/insert/update/delete.
parameters:
- in: path
name: route_key
required: true
schema:
type: string
- in: path
name: op
required: true
schema:
type: string
enum:
- query
- fetch
- insert
- update
- delete
- in: header
name: X-Athena-Key
required: true
schema:
type: string
requestBody:
required: true
content:
application/json:
schema:
type: object
responses:
'200':
description: Forwarded successfully
'400':
description: Invalid operation or payload
'403':
description: Route inactive or operation not allowed
'404':
description: Unknown route key
'500':
$ref: '#/components/responses/DefaultServerError5xx'
/admin/public-routes:
get:
summary: List public route aliases
parameters:
- in: header
name: X-Athena-Key
required: true
schema:
type: string
responses:
'200':
description: Public routes list
'500':
$ref: '#/components/responses/DefaultServerError5xx'
post:
summary: Create a public route alias
parameters:
- in: header
name: X-Athena-Key
required: true
schema:
type: string
requestBody:
required: true
content:
application/json:
schema:
type: object
required:
- route_key
- client_name
- allowed_ops
properties:
route_key:
type: string
client_name:
type: string
allowed_ops:
type: array
items:
type: string
responses:
'201':
description: Created
'400':
description: Validation error
'409':
description: Duplicate route key
'500':
$ref: '#/components/responses/DefaultServerError5xx'
/admin/public-routes/{route_key}:
patch:
summary: Update a public route alias
parameters:
- in: path
name: route_key
required: true
schema:
type: string
- in: header
name: X-Athena-Key
required: true
schema:
type: string
requestBody:
required: true
content:
application/json:
schema:
type: object
responses:
'200':
description: Updated
'404':
description: Route not found
'500':
$ref: '#/components/responses/DefaultServerError5xx'
delete:
summary: Soft-delete a public route alias
parameters:
- in: path
name: route_key
required: true
schema:
type: string
- in: header
name: X-Athena-Key
required: true
schema:
type: string
responses:
'200':
description: Deleted
'404':
description: Route not found
'500':
$ref: '#/components/responses/DefaultServerError5xx'
components:
responses:
DefaultServerError5xx:
description: Internal server error (or other 5xx). Standard envelope with status, message, and error.
content:
application/json:
schema:
type: object
required:
- status
- message
- error
properties:
status:
type: string
example: error
message:
type: string
description: Human-readable summary
error:
type: string
description: Error detail
parameters:
AdminApiKeyHeader:
name: apikey
in: header
description: |
The static admin key configured as `ATHENA_KEY_12`. Authorization headers (`Bearer <key>`), `X-API-Key`, `X-Athena-Key`, or `?api_key=` are also accepted.
required: true
schema:
type: string
ApiKeyIdParam:
name: id
in: path
required: true
description: UUID that identifies an API key or API key right (`api_keys_id`, `api_key_rights_id`).
schema:
type: string
format: uuid
WebhookIdParam:
name: id
in: path
required: true
description: Numeric primary key of a `gateway_webhook` row.
schema:
type: integer
format: int64
schemas:
ApiSuccessEnvelope:
type: object
description: |
Standard JSON envelope for successful responses (`api_success` in `src/api/response.rs`).
required:
- status
- message
- data
properties:
status:
type: string
enum:
- success
message:
type: string
data:
type: object
additionalProperties: true
ApiKeyRecord:
type: object
description: Persisted API key metadata plus resolved rights for listing/detail responses.
properties:
id:
type: string
format: uuid
public_id:
type: string
name:
type: string
description:
type: string
nullable: true
client_name:
type: string
nullable: true
expires_at:
type: string
format: date-time
nullable: true
is_active:
type: boolean
last_used_at:
type: string
format: date-time
nullable: true
created_at:
type: string
format: date-time
updated_at:
type: string
format: date-time
rights:
type: array
items:
type: string
CreateApiKeyRequest:
type: object
description: Payload used to create a new API key and optional right grants.
properties:
name:
type: string
description:
type: string
nullable: true
client_name:
type: string
nullable: true
expires_at:
type: string
format: date-time
nullable: true
rights:
type: array
items:
type: string
required:
- name
UpdateApiKeyRequest:
type: object
description: Partial update payload for API key metadata, lifecycle state, and right grants.
properties:
name:
type: string
description:
type: string
nullable: true
client_name:
type: string
nullable: true
expires_at:
type: string
format: date-time
nullable: true
is_active:
type: boolean
rights:
type: array
items:
type: string
CreateApiKeyResponse:
type: object
description: One-time API key creation response that includes the plaintext key and stored record metadata.
properties:
api_key:
type: string
example: ath_abcdefghijklmnop.secret
record:
$ref: '#/components/schemas/ApiKeyRecord'
ApiKeyRightRequest:
type: object
properties:
name:
type: string
description:
type: string
nullable: true
required:
- name
ApiKeyRightRecord:
type: object
description: Canonical right definition assignable to API keys.
properties:
id:
type: string
format: uuid
name:
type: string
description:
type: string
nullable: true
created_at:
type: string
format: date-time
updated_at:
type: string
format: date-time
ApiKeyConfigRequest:
type: object
properties:
enforce_api_keys:
type: boolean
required:
- enforce_api_keys
ApiKeyGlobalConfig:
type: object
properties:
enforce_api_keys:
type: boolean
updated_at:
type: string
format: date-time
ApiKeyClientConfig:
type: object
properties:
client_name:
type: string
enforce_api_keys:
type: boolean
created_at:
type: string
format: date-time
updated_at:
type: string
format: date-time
ApiKeyConfigResponse:
type: object
properties:
global:
$ref: '#/components/schemas/ApiKeyGlobalConfig'
clients:
type: array
items:
$ref: '#/components/schemas/ApiKeyClientConfig'
ApiKeyClientConfigRequest:
type: object
properties:
enforce_api_keys:
type: boolean
required:
- enforce_api_keys
ApiKeyClientListResponse:
type: object
properties:
clients:
type: array
items:
$ref: '#/components/schemas/ApiKeyClientConfig'
ClientsResponse:
type: object
description: Simple admin client-name listing response.
properties:
clients:
type: array
items:
type: string
AthenaClientRecord:
type: object
description: Database-backed Athena client catalog row used for runtime routing and management.
properties:
id:
type: string
format: uuid
client_name:
type: string
description:
type: string
nullable: true
pg_uri:
type: string
nullable: true
pg_uri_env_var:
type: string
nullable: true
config_uri_template:
type: string
nullable: true
source:
type: string
is_active:
type: boolean
is_frozen:
type: boolean
last_synced_from_config_at:
type: string
format: date-time
nullable: true
last_seen_at:
type: string
format: date-time
nullable: true
metadata:
type: object
additionalProperties: true
created_at:
type: string
format: date-time
updated_at:
type: string
format: date-time
deleted_at:
type: string
format: date-time
nullable: true
RuntimeAthenaClient:
type: object
description: In-memory runtime view of a registered client and live pool connectivity state.
properties:
client_name:
type: string
source:
type: string
description:
type: string
nullable: true
pg_uri:
type: string
nullable: true
pg_uri_env_var:
type: string
nullable: true
config_uri_template:
type: string
nullable: true
is_active:
type: boolean
is_frozen:
type: boolean
pool_connected:
type: boolean
SaveAthenaClientRequest:
type: object
properties:
client_name:
type: string
description:
type: string
nullable: true
pg_uri:
type: string
nullable: true
pg_uri_env_var:
type: string
nullable: true
is_active:
type: boolean
FreezeAthenaClientRequest:
type: object
properties:
is_frozen:
type: boolean
required:
- is_frozen
AdminClientResponse:
type: object
properties:
client:
$ref: '#/components/schemas/AthenaClientRecord'
AdminClientsResponse:
type: object
properties:
clients:
type: array
items:
$ref: '#/components/schemas/AthenaClientRecord'
runtime:
type: array
items:
$ref: '#/components/schemas/RuntimeAthenaClient'
ClientStatisticsRecord:
type: object
description: Aggregated per-client request and operation counters derived from gateway log tables.
properties:
client_name:
type: string
total_requests:
type: integer
successful_requests:
type: integer
failed_requests:
type: integer
total_cached_requests:
type: integer
total_operations:
type: integer
last_request_at:
type: string
format: date-time
nullable: true
last_operation_at:
type: string
format: date-time
nullable: true
updated_at:
type: string
format: date-time
ClientTableStatisticsRecord:
type: object
description: Per-client, per-table, per-operation counters including error tallies.
properties:
client_name:
type: string
table_name:
type: string
operation:
type: string
total_operations:
type: integer
error_operations:
type: integer
last_operation_at:
type: string
format: date-time
nullable: true
updated_at:
type: string
format: date-time
ClientStatisticsListResponse:
type: object
properties:
statistics:
type: array
items:
$ref: '#/components/schemas/ClientStatisticsRecord'
ClientStatisticsDetailResponse:
type: object
properties:
statistics:
$ref: '#/components/schemas/ClientStatisticsRecord'
tables:
type: array
items:
$ref: '#/components/schemas/ClientTableStatisticsRecord'
ClientOperationDrilldownRecord:
type: object
properties:
created_at:
type: string
format: date-time
request_id:
type: string
operation:
type: string
nullable: true
table_name:
type: string
nullable: true
client_name:
type: string
nullable: true
method:
type: string
nullable: true
path:
type: string
nullable: true
status_code:
type: integer
nullable: true
duration_ms:
type: integer
format: int64
nullable: true
operation_time_ms:
type: number
nullable: true
details:
type: object
additionalProperties: true
nullable: true
error:
type: boolean
nullable: true
message:
type: string
nullable: true
cache_key:
type: string
nullable: true
ClientStatisticsDrilldownData:
type: object
description: Returned in the success envelope `data` field from GET /admin/clients/{client_name}/statistics/drilldown
properties:
client_name:
type: string
table_name:
type: string
operation:
type: string
status:
type: string
description: Echo of the applied filter (`all`, `errors`, or `normal`).
limit:
type: integer
offset:
type: integer
rows:
type: array
items:
$ref: '#/components/schemas/ClientOperationDrilldownRecord'
QueryOptimizationRecommendationsListData:
type: object
description: Returned in the success envelope `data` field from GET /admin/clients/{client_name}/query-optimizations
properties:
client_name:
type: string
status:
type: string
description: Echo of the applied filter (`all`, `open`, `applied`, or `dismissed`).
limit:
type: integer
offset:
type: integer
recommendations:
type: array
items:
type: object
additionalProperties: true
QueryOptimizationRefreshData:
type: object
description: Returned in the success envelope `data` field from POST /admin/clients/{client_name}/query-optimizations/refresh
properties:
client_name:
type: string
run:
type: object
additionalProperties: true
recommendations:
type: array
items:
type: object
additionalProperties: true
QueryOptimizationRunsListData:
type: object
description: Returned in the success envelope `data` field from GET /admin/clients/{client_name}/query-optimizations/runs
properties:
client_name:
type: string
limit:
type: integer
offset:
type: integer
runs:
type: array
items:
type: object
additionalProperties: true
ApplyQueryOptimizationRequest:
type: object
properties:
actor:
type: string
description: Optional actor label recorded with the apply action.
QueryOptimizationApplyData:
type: object
description: Returned in the success envelope `data` field from POST /admin/clients/{client_name}/query-optimizations/{recommendation_id}/apply
properties:
client_name:
type: string
result:
type: object
additionalProperties: true
AdmissionEventRecord:
type: object
properties:
id:
type: integer
format: int64
created_at:
type: string
format: date-time
event_id:
type: string
method:
type: string
route:
type: string
client_name:
type: string
nullable: true
request_bytes:
type: integer
format: int64
nullable: true
defer_requested:
type: boolean
is_query_route:
type: boolean
decision:
type: string
reason:
type: string
nullable: true
deferred_request_id:
type: string
nullable: true
retry_after_seconds:
type: integer
nullable: true
window_seconds:
type: integer
nullable: true
global_limit_per_window:
type: integer
format: int64
nullable: true
per_client_limit_per_window:
type: integer
format: int64
nullable: true
meta:
type: object
additionalProperties: true
AdmissionEventsListData:
type: object
description: Returned in the success envelope `data` field from GET /admin/admission-events
properties:
decision:
type: string
nullable: true
client:
type: string
nullable: true
limit:
type: integer
offset:
type: integer
events:
type: array
items:
$ref: '#/components/schemas/AdmissionEventRecord'
VacuumHealthSnapshotRecord:
type: object
properties:
id:
type: integer
format: int64
recorded_at:
type: string
format: date-time
client_name:
type: string
host:
type: string
nullable: true
instance_id:
type: string
format: uuid
nullable: true
total_dead_rows:
type: integer
format: int64
tables_with_bloat:
type: integer
xid_freeze_risk:
type: integer
tables_needing_vacuum:
type: integer
freeze_max_age:
type: integer
format: int64
nullable: true
collection_error:
type: string
nullable: true
VacuumHealthTableStatRecord:
type: object
properties:
id:
type: integer
format: int64
snapshot_id:
type: integer
format: int64
schemaname:
type: string
relname:
type: string
n_dead_tup:
type: integer
format: int64
n_live_tup:
type: integer
format: int64
dead_pct:
type: number
nullable: true
last_vacuum:
type: string
format: date-time
nullable: true
last_autovacuum:
type: string
format: date-time
nullable: true
xid_age:
type: integer
format: int64
nullable: true
xid_age_pct_of_freeze_max:
type: number
nullable: true
VacuumHealthListResponse:
type: object
description: Returned in the success envelope `data` field from GET /admin/vacuum-health
properties:
snapshots:
type: array
items:
$ref: '#/components/schemas/VacuumHealthSnapshotRecord'
VacuumHealthDetailResponse:
type: object
description: Returned in the success envelope `data` field from GET /admin/vacuum-health/{client_name}
properties:
snapshot:
$ref: '#/components/schemas/VacuumHealthSnapshotRecord'
tables:
type: array
items:
$ref: '#/components/schemas/VacuumHealthTableStatRecord'
ManagementColumnRequest:
type: object
properties:
name:
type: string
data_type:
type: string
nullable:
type: boolean
default: true
default_expression:
type: string
nullable: true
required:
- name
- data_type
CreateTableRequest:
type: object
properties:
schema_name:
type: string
default: public
table_name:
type: string
columns:
type: array
items:
$ref: '#/components/schemas/ManagementColumnRequest'
if_not_exists:
type: boolean
description: Accepted for compatibility but ignored; Athena still returns 409 when the table exists.
required:
- table_name
EditTableRequest:
type: object
properties:
schema_name:
type: string
default: public
operations:
type: array
items:
oneOf:
- type: object
properties:
type:
type: string
enum:
- add_column
column:
$ref: '#/components/schemas/ManagementColumnRequest'
required:
- type
- column
- type: object
properties:
type:
type: string
enum:
- rename_column
from:
type: string
to:
type: string
required:
- type
- from
- to
- type: object
properties:
type:
type: string
enum:
- set_default
column_name:
type: string
default_expression:
type: string
required:
- type
- column_name
- default_expression
- type: object
properties:
type:
type: string
enum:
- drop_default
column_name:
type: string
required:
- type
- column_name
- type: object
properties:
type:
type: string
enum:
- set_not_null
column_name:
type: string
required:
- type
- column_name
- type: object
properties:
type:
type: string
enum:
- drop_not_null
column_name:
type: string
required:
- type
- column_name
required:
- operations
DropTableRequest:
type: object
properties:
schema_name:
type: string
default: public
cascade:
type: boolean
default: false
DropColumnRequest:
type: object
properties:
schema_name:
type: string
default: public
cascade:
type: boolean
default: false
CreateIndexRequest:
type: object
properties:
schema_name:
type: string
default: public
table_name:
type: string
index_name:
type: string
nullable: true
columns:
type: array
items:
type: string
unique:
type: boolean
default: false
method:
type: string
default: btree
required:
- table_name
- columns
DropIndexRequest:
type: object
properties:
schema_name:
type: string
default: public
ManagementCapabilities:
type: object
properties:
backend:
type: string
retention_mutation_supported:
type: boolean
replication_mutation_supported:
type: boolean
supported_operations:
type: array
items:
type: string
required_rights:
type: array
items:
type: object
properties:
operation:
type: string
required_right:
type: string
allowed_index_methods:
type: array
items:
type: string
allowed_column_data_types:
type: array
items:
type: string
ManagementCapabilitiesEnvelope:
type: object
properties:
status:
type: string
message:
type: string
data:
$ref: '#/components/schemas/ManagementCapabilities'
ClusterMirrorHealth:
type: object
properties:
url:
type: string
format: uri
status:
type: string
enum:
- online
- offline
latency_ms:
type: number
nullable: true
download_bytes_per_sec:
type: number
nullable: true
cargo_toml_version:
type: string
nullable: true
message:
type: string
nullable: true
ClusterHealthResponse:
type: object
properties:
message:
type: string
version:
type: string
athena_api:
type: string
athena_deadpool:
type: string
athena_scylladb:
type: string
cargo_toml_version:
type: string
mirrors:
type: array
items:
$ref: '#/components/schemas/ClusterMirrorHealth'
CreateBackupRequest:
type: object
properties:
client_name:
type: string
description: Logical client whose Postgres URI will be dumped.
label:
type: string
nullable: true
description: Optional human-readable label stored in S3 object metadata.
required:
- client_name
RestoreBackupRequest:
type: object
properties:
client_name:
type: string
description: Logical client whose Postgres URI is the restore target.
required:
- client_name
BackupObject:
type: object
properties:
id:
type: string
description: Backup identifier derived from the S3 object key.
key:
type: string
description: Full S3 object key.
client_name:
type: string
label:
type: string
nullable: true
size_bytes:
type: integer
format: int64
created_at:
type: string
description: Timestamp string from S3 metadata.
ProvisionRequest:
type: object
properties:
uri:
type: string
format: uri
description: Direct Postgres URI to provision (mutually exclusive with client_name).
client_name:
type: string
description: Registered client whose URI will be used (mutually exclusive with uri).
register:
type: boolean
default: false
description: When true and uri is provided, register the client in the runtime catalog.
register_name:
type: string
nullable: true
description: Optional client name when registering (defaults to "provisioned").
ProvisionStatusResponse:
type: object
properties:
client_name:
type: string
provisioned:
type: boolean
present_tables:
type: array
items:
type: string
missing_tables:
type: array
items:
type: string
LocalClusterCreateDatabaseRequest:
type: object
properties:
client_name:
type: string
nullable: true
description: Required for admin API. Ignored in management API (caller `X-Athena-Client` is used).
database_name:
type: string
owner:
type: string
nullable: true
template:
type: string
nullable: true
encoding:
type: string
nullable: true
lc_collate:
type: string
nullable: true
lc_ctype:
type: string
nullable: true
tablespace:
type: string
nullable: true
register_name:
type: string
nullable: true
description: Optional Athena client name when registering. Defaults to database_name.
description:
type: string
nullable: true
provision_schema:
type: boolean
default: true
register_runtime:
type: boolean
default: true
register_catalog:
type: boolean
default: true
required:
- database_name
LocalClusterDatabasesResponse:
type: object
properties:
client_name:
type: string
all_databases:
type: array
items:
type: string
athena_managed_databases:
type: array
items:
type: object
properties:
client_name:
type: string
database_name:
type: string
source:
type: string
is_active:
type: boolean
is_frozen:
type: boolean
SpinUpInstanceRequest:
type: object
properties:
client_name:
type: string
container_name:
type: string
nullable: true
image:
type: string
nullable: true
host:
type: string
nullable: true
host_port:
type: integer
format: int32
nullable: true
db_name:
type: string
nullable: true
username:
type: string
nullable: true
password:
type: string
nullable: true
startup_timeout_secs:
type: integer
format: int64
nullable: true
reuse_existing:
type: boolean
default: false
provision_schema:
type: boolean
default: true
register_runtime:
type: boolean
default: true
register_catalog:
type: boolean
default: true
required:
- client_name
DeleteInstanceRequest:
type: object
properties:
client_name:
type: string
nullable: true
remove_runtime_client:
type: boolean
default: true
remove_catalog_client:
type: boolean
default: true
NeonProviderProvisionRequest:
type: object
properties:
client_name:
type: string
description:
type: string
nullable: true
connection_uri:
type: string
nullable: true
api_key:
type: string
nullable: true
project_id:
type: string
nullable: true
branch_id:
type: string
nullable: true
database_name:
type: string
nullable: true
role_name:
type: string
nullable: true
endpoint_id:
type: string
nullable: true
api_base_url:
type: string
nullable: true
create_project_if_missing:
type: boolean
default: false
project_name:
type: string
nullable: true
project_create_payload:
type: object
nullable: true
provision_schema:
type: boolean
default: true
register_runtime:
type: boolean
default: true
register_catalog:
type: boolean
default: true
required:
- client_name
RailwayProviderProvisionRequest:
type: object
properties:
client_name:
type: string
description:
type: string
nullable: true
connection_uri:
type: string
nullable: true
api_key:
type: string
nullable: true
project_id:
type: string
nullable: true
environment_id:
type: string
nullable: true
service_id:
type: string
nullable: true
plugin_id:
type: string
nullable: true
graphql_url:
type: string
nullable: true
create_project_if_missing:
type: boolean
default: false
project_name:
type: string
nullable: true
project_create_input:
type: object
nullable: true
create_service_if_missing:
type: boolean
default: false
service_name:
type: string
nullable: true
service_create_input:
type: object
nullable: true
create_plugin_if_missing:
type: boolean
default: false
plugin_name:
type: string
nullable: true
plugin_create_input:
type: object
nullable: true
provision_schema:
type: boolean
default: true
register_runtime:
type: boolean
default: true
register_catalog:
type: boolean
default: true
required:
- client_name
RenderProviderProvisionRequest:
type: object
properties:
client_name:
type: string
description:
type: string
nullable: true
connection_uri:
type: string
nullable: true
api_key:
type: string
nullable: true
service_id:
type: string
nullable: true
owner_id:
type: string
nullable: true
api_base_url:
type: string
nullable: true
create_service_if_missing:
type: boolean
default: false
service_name:
type: string
nullable: true
service_create_payload:
type: object
nullable: true
plan:
type: string
nullable: true
region:
type: string
nullable: true
postgres_version:
type: string
nullable: true
disk_size_gb:
type: integer
format: int32
nullable: true
provision_schema:
type: boolean
default: true
register_runtime:
type: boolean
default: true
register_catalog:
type: boolean
default: true
required:
- client_name
GatewaySqlExecutionRequest:
type: object
description: Driver-agnostic SQL execution payload used by `/query/sql` and `/gateway/sql`.
required:
- query
- driver
- db_name
properties:
query:
type: string
driver:
type: string
enum:
- athena
- postgresql
- supabase
db_name:
type: string
GatewayRpcFilterOperator:
type: string
enum:
- eq
- neq
- gt
- gte
- lt
- lte
- in
- like
- ilike
- is
description: Filter operator for RPC post-processing (JSON may use alias `i_like` for ilike)
GatewayRpcFilter:
type: object
required:
- column
- operator
properties:
column:
type: string
operator:
$ref: '#/components/schemas/GatewayRpcFilterOperator'
value:
description: JSON value compared against the column (default null)
nullable: true
GatewayRpcOrder:
type: object
required:
- column
properties:
column:
type: string
ascending:
type: boolean
default: true
GatewayRpcRequest:
type: object
description: Structured RPC invocation payload for Postgres function execution and optional row shaping.
required:
- function
properties:
function:
type: string
description: Function name (or `schema.function` when schema is `public`)
function_name:
type: string
description: Alias of `function` accepted in JSON
schema:
type: string
default: public
args:
type: object
additionalProperties: true
select:
type: string
description: Comma-separated columns for SELECT over RPC result
filters:
type: array
items:
$ref: '#/components/schemas/GatewayRpcFilter'
count:
type: string
description: Set to `exact` to include an exact row count
limit:
type: integer
format: int64
offset:
type: integer
format: int64
order:
$ref: '#/components/schemas/GatewayRpcOrder'
UpsertFunctionRequest:
type: object
required:
- ddl
properties:
ddl:
type: string
description: CREATE OR REPLACE FUNCTION ... DDL validated server-side
DropFunctionRequest:
type: object
required:
- function_name
- arg_types
properties:
schema_name:
type: string
default: public
function_name:
type: string
arg_types:
type: array
items:
type: string
description: Postgres type names for the function signature, e.g. `["text","integer"]`
InstanceLifecycleRequest:
type: object
properties:
client_name:
type: string
nullable: true
description: Optional client linked to the container for runtime sync
sync_runtime:
type: boolean
default: true
description: When true, reconnect or mark unavailable after start/stop
BindInstancePortRouteRequest:
type: object
required:
- route_key
properties:
route_key:
type: string
client_name:
type: string
nullable: true
public_host:
type: string
nullable: true
public_port:
type: integer
format: int32
nullable: true
persist_in_catalog:
type: boolean
default: true
StorageS3Credentials:
type: object
required:
- endpoint
- region
- bucket
- access_key_id
- secret_key
properties:
endpoint:
type: string
description: S3-compatible endpoint URL or host
region:
type: string
bucket:
type: string
access_key_id:
type: string
secret_key:
type: string
StorageListObjectsRequest:
allOf:
- $ref: '#/components/schemas/StorageS3Credentials'
- type: object
properties:
prefix:
type: string
nullable: true
delimiter:
type: string
nullable: true
continuation_token:
type: string
nullable: true
max_keys:
type: integer
format: int32
default: 200
StorageGetObjectRequest:
allOf:
- $ref: '#/components/schemas/StorageS3Credentials'
- type: object
required:
- key
properties:
key:
type: string
StorageDeleteObjectRequest:
allOf:
- $ref: '#/components/schemas/StorageS3Credentials'
- type: object
required:
- key
properties:
key:
type: string
StorageCreateFolderRequest:
allOf:
- $ref: '#/components/schemas/StorageS3Credentials'
- type: object
required:
- prefix
properties:
prefix:
type: string
StoragePresignUploadRequest:
allOf:
- $ref: '#/components/schemas/StorageS3Credentials'
- type: object
required:
- key
properties:
key:
type: string
content_type:
type: string
nullable: true
StorageBucketCorsRequest:
allOf:
- $ref: '#/components/schemas/StorageS3Credentials'
StorageSetBucketCorsRequest:
allOf:
- $ref: '#/components/schemas/StorageS3Credentials'
- type: object
required:
- rules
properties:
rules:
type: array
items:
type: object
required:
- allowed_origins
- allowed_methods
properties:
allowed_origins:
type: array
items:
type: string
allowed_methods:
type: array
items:
type: string
allowed_headers:
type: array
items:
type: string
expose_headers:
type: array
items:
type: string
max_age_seconds:
type: integer
format: int32
nullable: true