Move API artifacts out of docs/spec, define concrete execution and deletion refinements, and document TLA+ abstraction boundaries so architecture prose cannot become a competing protocol specification.
138 lines
5.3 KiB
JSON
138 lines
5.3 KiB
JSON
{
|
|
"$schema": "https://json-schema.org/draft/2020-12/schema",
|
|
"$id": "https://remora.invalid/api/events.schema.json",
|
|
"title": "Remora WebSocket frame",
|
|
"oneOf": [
|
|
{"$ref": "#/$defs/JobChanged"},
|
|
{"$ref": "#/$defs/DeletionChanged"},
|
|
{"$ref": "#/$defs/ResyncRequired"},
|
|
{"$ref": "#/$defs/Heartbeat"}
|
|
],
|
|
"$defs": {
|
|
"OpaqueId": {
|
|
"type": "string",
|
|
"pattern": "^[A-Za-z0-9][A-Za-z0-9_-]{7,127}$"
|
|
},
|
|
"Cursor": {
|
|
"type": "string",
|
|
"minLength": 16,
|
|
"maxLength": 2048
|
|
},
|
|
"Attempt": {
|
|
"type": "object",
|
|
"additionalProperties": false,
|
|
"required": ["attempt_id", "fence"],
|
|
"properties": {
|
|
"attempt_id": {"$ref": "#/$defs/OpaqueId"},
|
|
"fence": {"type": "integer", "minimum": 1}
|
|
}
|
|
},
|
|
"Progress": {
|
|
"type": "object",
|
|
"additionalProperties": false,
|
|
"required": ["attempt_id", "fence", "completed_bytes", "completed_members"],
|
|
"properties": {
|
|
"attempt_id": {"$ref": "#/$defs/OpaqueId"},
|
|
"fence": {"type": "integer", "minimum": 1},
|
|
"completed_bytes": {"type": "integer", "minimum": 0},
|
|
"total_bytes": {"type": ["integer", "null"], "minimum": 0},
|
|
"completed_members": {"type": "integer", "minimum": 0},
|
|
"total_members": {"type": ["integer", "null"], "minimum": 0}
|
|
}
|
|
},
|
|
"ServerBase": {
|
|
"type": "object",
|
|
"required": ["schema_version", "kind", "event_id", "sequence", "cursor", "occurred_at"],
|
|
"properties": {
|
|
"schema_version": {"const": 1},
|
|
"kind": {"type": "string"},
|
|
"event_id": {"$ref": "#/$defs/OpaqueId"},
|
|
"sequence": {"type": "integer", "minimum": 1},
|
|
"cursor": {"$ref": "#/$defs/Cursor"},
|
|
"occurred_at": {"type": "string", "format": "date-time"}
|
|
}
|
|
},
|
|
"JobChanged": {
|
|
"allOf": [
|
|
{"$ref": "#/$defs/ServerBase"},
|
|
{
|
|
"type": "object",
|
|
"additionalProperties": false,
|
|
"required": ["schema_version", "kind", "event_id", "sequence", "cursor", "occurred_at", "job_id", "job_revision", "phase", "lifecycle", "authoritative_attempt", "progress"],
|
|
"properties": {
|
|
"schema_version": {"const": 1},
|
|
"kind": {"const": "job_changed"},
|
|
"event_id": {"$ref": "#/$defs/OpaqueId"},
|
|
"sequence": {"type": "integer", "minimum": 1},
|
|
"cursor": {"$ref": "#/$defs/Cursor"},
|
|
"occurred_at": {"type": "string", "format": "date-time"},
|
|
"job_id": {"$ref": "#/$defs/OpaqueId"},
|
|
"job_revision": {"type": "integer", "minimum": 1},
|
|
"phase": {"enum": ["Queued", "Running", "RetryWait", "Cancelling", "Succeeded", "Failed", "Cancelled"]},
|
|
"lifecycle": {"enum": ["visible", "soft_deleted", "hard_deleting", "hard_deleted"]},
|
|
"authoritative_attempt": {"oneOf": [{"$ref": "#/$defs/Attempt"}, {"type": "null"}]},
|
|
"progress": {"oneOf": [{"$ref": "#/$defs/Progress"}, {"type": "null"}]}
|
|
}
|
|
}
|
|
]
|
|
},
|
|
"DeletionChanged": {
|
|
"allOf": [
|
|
{"$ref": "#/$defs/ServerBase"},
|
|
{
|
|
"type": "object",
|
|
"additionalProperties": false,
|
|
"required": ["schema_version", "kind", "event_id", "sequence", "cursor", "occurred_at", "job_id", "operation_id", "state"],
|
|
"properties": {
|
|
"schema_version": {"const": 1},
|
|
"kind": {"const": "deletion_changed"},
|
|
"event_id": {"$ref": "#/$defs/OpaqueId"},
|
|
"sequence": {"type": "integer", "minimum": 1},
|
|
"cursor": {"$ref": "#/$defs/Cursor"},
|
|
"occurred_at": {"type": "string", "format": "date-time"},
|
|
"job_id": {"$ref": "#/$defs/OpaqueId"},
|
|
"operation_id": {"$ref": "#/$defs/OpaqueId"},
|
|
"state": {"enum": ["queued", "running", "retry_wait", "blocked", "completed"]}
|
|
}
|
|
}
|
|
]
|
|
},
|
|
"ResyncRequired": {
|
|
"allOf": [
|
|
{"$ref": "#/$defs/ServerBase"},
|
|
{
|
|
"type": "object",
|
|
"additionalProperties": false,
|
|
"required": ["schema_version", "kind", "event_id", "sequence", "cursor", "occurred_at", "reason"],
|
|
"properties": {
|
|
"schema_version": {"const": 1},
|
|
"kind": {"const": "resync_required"},
|
|
"event_id": {"$ref": "#/$defs/OpaqueId"},
|
|
"sequence": {"type": "integer", "minimum": 1},
|
|
"cursor": {"$ref": "#/$defs/Cursor"},
|
|
"occurred_at": {"type": "string", "format": "date-time"},
|
|
"reason": {"enum": ["cursor_absent", "cursor_invalid", "cursor_expired", "authorization_changed", "history_unavailable"]}
|
|
}
|
|
}
|
|
]
|
|
},
|
|
"Heartbeat": {
|
|
"allOf": [
|
|
{"$ref": "#/$defs/ServerBase"},
|
|
{
|
|
"type": "object",
|
|
"additionalProperties": false,
|
|
"required": ["schema_version", "kind", "event_id", "sequence", "cursor", "occurred_at"],
|
|
"properties": {
|
|
"schema_version": {"const": 1},
|
|
"kind": {"const": "heartbeat"},
|
|
"event_id": {"$ref": "#/$defs/OpaqueId"},
|
|
"sequence": {"type": "integer", "minimum": 1},
|
|
"cursor": {"$ref": "#/$defs/Cursor"},
|
|
"occurred_at": {"type": "string", "format": "date-time"}
|
|
}
|
|
}
|
|
]
|
|
}
|
|
}
|
|
}
|