Ingestion API Reference
The Ingestion Service accepts logs and metrics from external systems and pipelines. All endpoints return 202 Accepted on success.
Base URL: http://localhost:3001 (local) or your deployed ingestion endpoint.
Authentication & Multi-tenancy
All endpoints require an API key when OPERYN_API_KEY is configured on the server. You can find or rotate your Organization's API Key in the Dashboard (Settings → Organization).
In a multi-tenant environment, you must also provide your Organization ID to ensure data is routed to the correct account and service limits are enforced properly.
Pass the key in the x-api-key header, and your Organization ID in the x-organization-id header:
curl -X POST https://ingest.operyn.example.com/events/logs \
-H "Content-Type: application/json" \
-H "x-api-key: your-api-key-here" \
-H "x-organization-id: org_123456789" \
-d '{ ... }'
If x-organization-id is omitted, data is routed to the default organization, which is limited to 5 services.
If OPERYN_API_KEY is not set on the server, endpoints are open (suitable for local development).
POST /events/logs
Ingest a single log event.
Request Body
| Field | Type | Required | Description |
|---|---|---|---|
service | string | Yes | Name of the originating service (e.g. billing-service) |
level | string | Yes | Log level: debug, info, warn, error, or fatal |
message | string | Yes | The log message content |
timestamp | string | No | ISO 8601 timestamp. Defaults to server time if omitted |
traceId | string | No | Distributed trace ID for correlation |
spanId | string | No | Span ID within the trace |
metadata | object | No | Arbitrary key-value pairs (region, env, team, etc.) |
Example
curl -X POST http://localhost:3001/events/logs \
-H "Content-Type: application/json" \
-H "x-api-key: your-api-key" \
-H "x-organization-id: org_123456789" \
-d '{
"service": "api-gateway",
"level": "error",
"message": "Upstream timeout connecting to auth-service",
"traceId": "abc-123-def",
"metadata": {
"region": "us-east-1",
"env": "prod",
"team": "platform"
}
}'
Response — 202 Accepted
{
"id": "f47ac10b-58cc-4372-a567-0e02b2c3d479",
"queued": true
}
POST /events/logs/batch
Ingest multiple log events in a single request.
Request Body
An array of log event objects (same schema as POST /events/logs).
Example
curl -X POST http://localhost:3001/events/logs/batch \
-H "Content-Type: application/json" \
-H "x-api-key: your-api-key" \
-H "x-organization-id: org_123456789" \
-d '[
{
"service": "billing-service",
"level": "error",
"message": "Payment failed for customer 42"
},
{
"service": "billing-service",
"level": "warn",
"message": "Retry attempt 3 for payment gateway"
}
]'
Response — 202 Accepted
{
"accepted": 2
}
POST /events/metrics
Ingest a single metric data point.
Request Body
| Field | Type | Required | Description |
|---|---|---|---|
service | string | Yes | Name of the originating service |
name | string | Yes | Metric name (e.g. http_5xx_rate, cpu_utilization) |
value | number | Yes | Numeric value of the metric |
unit | string | Yes | Unit of measurement (e.g. percent, seconds, count) |
timestamp | string | No | ISO 8601 timestamp. Defaults to server time if omitted |
labels | object | No | String key-value pairs for dimensions (region, instance, etc.) |
Example
curl -X POST http://localhost:3001/events/metrics \
-H "Content-Type: application/json" \
-H "x-api-key: your-api-key" \
-H "x-organization-id: org_123456789" \
-d '{
"service": "api-gateway",
"name": "request_latency_p99",
"value": 2.34,
"unit": "seconds",
"labels": {
"region": "us-east-1",
"env": "prod",
"endpoint": "/api/v1/users"
}
}'
Response — 202 Accepted
{
"id": "e23f8a1c-9b4d-4e7f-8a2b-1c3d4e5f6a7b",
"queued": true
}
---
## POST /events/deployments
Record a deployment event to correlate with future incidents.
### Request Body
| Field | Type | Required | Description |
|---|---|---|---|
| `service` | `string` | Yes | Name of the service being deployed |
| `version` | `string` | Yes | Version or tag being deployed (e.g. `v1.2.3`) |
| `environment` | `string` | Yes | Environment (e.g. `production`, `staging`) |
| `gitHash` | `string` | No | Git commit hash |
| `timestamp` | `string` | No | ISO 8601 timestamp. Defaults to server time |
| `metadata` | `object` | No | Additional deployment context |
### Example
```bash
curl -X POST http://localhost:3001/events/deployments \
-H "Content-Type: application/json" \
-H "x-api-key: your-api-key" \
-H "x-organization-id: org_123456789" \
-d '{
"service": "payment-service",
"version": "v2.0.1",
"environment": "production",
"gitHash": "a1b2c3d4",
"metadata": {
"deployedBy": "jenkins",
"deployId": "job-123"
}
}'
Response — 202 Accepted
{
"id": "c1a2b3c4-d5e6-4f7g-8h9i-j0k1l2m3n4o5",
"queued": true
}
---
## Error Responses
### 401 Unauthorized
Returned when `x-api-key` is missing or invalid.
```json
{
"statusCode": 401,
"message": "Invalid or missing API key"
}
400 Bad Request
Returned when the request body fails Zod schema validation.
{
"statusCode": 400,
"message": "Invalid log event: ..."
}
Service Naming Conventions
Use consistent, lowercase, hyphenated names for the service field:
| Pattern | Example |
|---|---|
<service-name> | billing-service |
<team>-<service> | payments-billing-service |
Avoid spaces, underscores, or uppercase. The ingestion service trims whitespace but does not transform casing.
Recommended Metadata
Include these fields in metadata (logs) or labels (metrics) for best results:
| Key | Description | Example |
|---|---|---|
env | Deployment environment | prod, staging, dev |
region | Cloud region or data centre | us-east-1, eu-west-1 |
cluster | Kubernetes cluster name | prod-eks-1 |
team | Owning team | platform, payments |
source | Origin of the data | cloudwatch, gcp, fluent-bit, app |
Rate Limits
No rate limits are enforced by default. For production deployments, consider placing a load balancer or API gateway in front of the ingestion service with appropriate rate limiting.
Interactive API Docs
When running locally, visit:
- Swagger UI: http://localhost:3001/api
- Scalar Reference: http://localhost:3001/reference
- OpenAPI JSON: http://localhost:3001/openapi.json