{
    "openapi": "3.1.0",
    "info": {
        "title": "FireStatus Management API",
        "version": "1.0.0",
        "description": "Reference for the FireStatus Management API v1 — the authenticated HTTP interface a tenant uses to run its status page: incidents, scheduled maintenances, components and component groups, announcements, subscribers and analytics.\n\nFireStatus is a multi-tenant status-page platform, and the management API has no central host: it answers only on a tenant's own status-page address — a verified custom domain, or the tenant's `{label}.firestatus.de` subdomain. Pick that host through the `status_page_host` server variable below; the API key must belong to the same tenant as the host.\n\nGenerated from the internal docs collection.",
        "contact": {
            "name": "FireStatus",
            "url": "https://firestatus.de"
        }
    },
    "servers": [
        {
            "url": "https://{status_page_host}/api/v1",
            "description": "A tenant's own status-page host — a verified custom domain, or {label}.firestatus.de. There is no central API host.",
            "variables": {
                "status_page_host": {
                    "default": "status.example.com",
                    "description": "The status-page hostname of the tenant you are calling, without scheme or path — e.g. `status.example.com` or `acme.firestatus.de`. The host is a tenant assignment in its own right: a key issued for another tenant is refused here with 403."
                }
            }
        }
    ],
    "security": [
        {
            "bearerAuth": []
        }
    ],
    "tags": [
        {
            "name": "Allgemein",
            "description": "Category Allgemein"
        },
        {
            "name": "Komponenten",
            "description": "Category Komponenten"
        },
        {
            "name": "Vorfälle",
            "description": "Category Vorfälle"
        },
        {
            "name": "Wartungen",
            "description": "Category Wartungen"
        },
        {
            "name": "Ankündigungen",
            "description": "Category Ankündigungen"
        },
        {
            "name": "Abonnenten",
            "description": "Category Abonnenten"
        },
        {
            "name": "Zugriffe",
            "description": "Category Zugriffe"
        }
    ],
    "paths": {
        "/me": {
            "get": {
                "tags": [
                    "Allgemein"
                ],
                "summary": "Schlüssel prüfen",
                "operationId": "getApiV1Me",
                "description": "Bestätigt in einem Aufruf, dass der Schlüssel gültig ist, auf die richtige Statusseite zeigt und wann er abläuft.",
                "responses": {
                    "200": {
                        "description": "Erfolg",
                        "content": {
                            "application/json": {
                                "example": {
                                    "data": {
                                        "tenant": {
                                            "id": "01kxrwdffkh0tpdf5dkdspy86w",
                                            "name": "Acme Hosting",
                                            "slug": "acme",
                                            "language_mode": "both",
                                            "locales": [
                                                "de",
                                                "en"
                                            ],
                                            "status_page_url": "https://status.example.com"
                                        },
                                        "api_key": {
                                            "id": 1,
                                            "name": "Grafana Monitoring",
                                            "abilities": [
                                                "incidents.manage",
                                                "announcements.manage",
                                                "components.manage",
                                                "components.view",
                                                "subscribers.manage",
                                                "analytics.view"
                                            ],
                                            "created_at": "2026-07-27T09:12:00Z",
                                            "last_used_at": "2026-07-27T14:00:00Z",
                                            "expires_at": null
                                        },
                                        "api_version": "v1"
                                    }
                                }
                            }
                        }
                    },
                    "401": {
                        "description": "Nicht authentifiziert",
                        "content": {
                            "application/json": {
                                "example": {
                                    "message": "Invalid API key."
                                }
                            }
                        }
                    },
                    "403": {
                        "description": "Fremder Schlüssel",
                        "content": {
                            "application/json": {
                                "example": {
                                    "message": "This API key does not belong to this status page. Call the API on your own status page domain."
                                }
                            }
                        }
                    },
                    "404": {
                        "description": "Nicht gefunden",
                        "content": {
                            "application/json": {
                                "example": {
                                    "message": "This endpoint exists, but not on this host. The FireStatus management API is served only on your own status page domain — for example https://status.example.com/api/v1/me or https://your-label.firestatus.de/api/v1/me. There is no central API endpoint on firestatus.de."
                                }
                            }
                        }
                    }
                }
            }
        },
        "/status": {
            "get": {
                "tags": [
                    "Allgemein"
                ],
                "summary": "Betriebsübersicht",
                "operationId": "getApiV1Status",
                "description": "Was Aufmerksamkeit braucht: unveröffentlichte Entwürfe, unbestätigte Vorfälle, anstehende Wartungen. Nicht die Besuchersicht — die liefert das unauthentifizierte /api/v2/status auf demselben Host.",
                "responses": {
                    "200": {
                        "description": "Erfolg",
                        "content": {
                            "application/json": {
                                "example": {
                                    "data": {
                                        "indicator": "degraded",
                                        "components": {
                                            "total": 11,
                                            "public": 9,
                                            "internal": 2,
                                            "by_status": {
                                                "operational": 10,
                                                "degraded": 1,
                                                "partial_outage": 0,
                                                "major_outage": 0,
                                                "under_maintenance": 0
                                            }
                                        },
                                        "incidents": {
                                            "active": 1,
                                            "unacknowledged": 1,
                                            "drafts": 2,
                                            "scheduled": 0
                                        },
                                        "maintenances": {
                                            "active": 0,
                                            "upcoming": 1,
                                            "drafts": 0
                                        },
                                        "announcements": {
                                            "active": 1,
                                            "total": 4
                                        },
                                        "subscribers": {
                                            "confirmed": 342,
                                            "pending": 3
                                        },
                                        "subscriptions_enabled": true,
                                        "generated_at": "2026-07-27T14:00:00Z"
                                    }
                                }
                            }
                        }
                    },
                    "401": {
                        "description": "Nicht authentifiziert",
                        "content": {
                            "application/json": {
                                "example": {
                                    "message": "Invalid API key."
                                }
                            }
                        }
                    }
                }
            }
        },
        "/components": {
            "get": {
                "tags": [
                    "Komponenten"
                ],
                "summary": "Komponenten auflisten",
                "operationId": "getApiV1Components",
                "description": "Enthält auch interne Komponenten, die auf den öffentlichen Flächen verborgen sind.",
                "x-required-permission": "components.view",
                "parameters": [
                    {
                        "name": "page",
                        "in": "query",
                        "required": false,
                        "schema": {
                            "type": "integer"
                        }
                    },
                    {
                        "name": "per_page",
                        "in": "query",
                        "required": false,
                        "description": "Wird auf die maximale Seitengröße begrenzt statt abgewiesen.",
                        "schema": {
                            "type": "integer"
                        }
                    },
                    {
                        "name": "group_id",
                        "in": "query",
                        "required": false,
                        "description": "Nach Gruppe filtern. Ein leerer Wert liefert Komponenten ohne Gruppe.",
                        "schema": {
                            "type": "integer"
                        }
                    },
                    {
                        "name": "is_public",
                        "in": "query",
                        "required": false,
                        "schema": {
                            "type": "boolean"
                        }
                    },
                    {
                        "name": "subscribable",
                        "in": "query",
                        "required": false,
                        "schema": {
                            "type": "boolean"
                        }
                    }
                ],
                "responses": {
                    "200": {
                        "description": "Erfolg",
                        "content": {
                            "application/json": {
                                "example": {
                                    "links": {
                                        "first": "https://status.example.com/api/v1/components?page=1",
                                        "last": "https://status.example.com/api/v1/components?page=1",
                                        "prev": null,
                                        "next": null
                                    },
                                    "meta": {
                                        "current_page": 1,
                                        "per_page": 25,
                                        "total": 1,
                                        "last_page": 1
                                    },
                                    "data": [
                                        {
                                            "id": 3,
                                            "name": {
                                                "de": "API-Gateway",
                                                "en": "API gateway"
                                            },
                                            "description": {
                                                "de": "Die öffentliche Schnittstelle",
                                                "en": null
                                            },
                                            "slug": "api-gateway",
                                            "group_id": 1,
                                            "position": 0,
                                            "is_public": true,
                                            "subscribable": true,
                                            "status": "degraded",
                                            "uptime_90d": 0.9982,
                                            "remote_trigger": {
                                                "webhook_enabled": true,
                                                "webhook_url": "https://status.example.com/remote/2f9c1d7ab3e54c08a1b6",
                                                "webhook_status": "degraded",
                                                "webhook_status_at": "2026-07-27T13:58:00Z",
                                                "host_system": null
                                            },
                                            "created_at": "2026-05-04T08:00:00Z",
                                            "updated_at": "2026-07-27T13:58:00Z"
                                        }
                                    ]
                                }
                            }
                        }
                    },
                    "401": {
                        "description": "Nicht authentifiziert",
                        "content": {
                            "application/json": {
                                "example": {
                                    "message": "Invalid API key."
                                }
                            }
                        }
                    }
                }
            },
            "post": {
                "tags": [
                    "Komponenten"
                ],
                "summary": "Komponente anlegen",
                "operationId": "postApiV1Components",
                "description": "Der Slug wird aus dem Namen abgeleitet und nicht vom Client entgegengenommen.",
                "x-required-permission": "components.manage",
                "requestBody": {
                    "required": true,
                    "content": {
                        "application/json": {
                            "schema": {
                                "type": "object",
                                "properties": {
                                    "name": {
                                        "type": "string",
                                        "description": "Locale-Objekt, z. B. {\"de\": \"API-Gateway\", \"en\": \"API gateway\"}."
                                    },
                                    "description": {
                                        "type": "string",
                                        "description": "Locale-Objekt wie bei name."
                                    },
                                    "group_id": {
                                        "type": "integer"
                                    },
                                    "is_public": {
                                        "type": "boolean"
                                    },
                                    "subscribable": {
                                        "type": "boolean"
                                    },
                                    "position": {
                                        "type": "integer"
                                    },
                                    "webhook_enabled": {
                                        "type": "boolean"
                                    },
                                    "host_system_id": {
                                        "type": "integer"
                                    }
                                },
                                "required": [
                                    "name"
                                ]
                            }
                        }
                    }
                },
                "responses": {
                    "201": {
                        "description": "Angelegt",
                        "content": {
                            "application/json": {
                                "example": {
                                    "data": {
                                        "id": 14,
                                        "name": {
                                            "de": "API-Gateway",
                                            "en": "API gateway"
                                        },
                                        "description": {
                                            "de": "Die öffentliche Schnittstelle",
                                            "en": null
                                        },
                                        "slug": "api-gateway",
                                        "group_id": 1,
                                        "position": 0,
                                        "is_public": true,
                                        "subscribable": true,
                                        "status": "operational",
                                        "uptime_90d": 1,
                                        "remote_trigger": {
                                            "webhook_enabled": false,
                                            "webhook_url": null,
                                            "webhook_status": null,
                                            "webhook_status_at": null,
                                            "host_system": null
                                        },
                                        "created_at": "2026-07-27T14:00:00Z",
                                        "updated_at": "2026-07-27T14:00:00Z"
                                    }
                                }
                            }
                        }
                    },
                    "422": {
                        "description": "Validierung fehlgeschlagen",
                        "content": {
                            "application/json": {
                                "example": {
                                    "message": "The name field must be filled in at least one language (de, en).",
                                    "errors": {
                                        "name": [
                                            "The name field must be filled in at least one language (de, en)."
                                        ]
                                    }
                                }
                            }
                        }
                    }
                }
            }
        },
        "/components/{component}": {
            "get": {
                "tags": [
                    "Komponenten"
                ],
                "summary": "Komponente abrufen",
                "operationId": "getApiV1ComponentsComponent",
                "description": "Enthält den arbitrierten Live-Status, die 90-Tage-Verfügbarkeit und die Remote-Trigger-Konfiguration.",
                "x-required-permission": "components.view",
                "parameters": [
                    {
                        "name": "component",
                        "in": "path",
                        "required": true,
                        "schema": {
                            "type": "integer"
                        }
                    }
                ],
                "responses": {
                    "200": {
                        "description": "Erfolg",
                        "content": {
                            "application/json": {
                                "example": {
                                    "data": {
                                        "id": 3,
                                        "name": {
                                            "de": "API-Gateway",
                                            "en": "API gateway"
                                        },
                                        "description": {
                                            "de": "Die öffentliche Schnittstelle",
                                            "en": null
                                        },
                                        "slug": "api-gateway",
                                        "group_id": 1,
                                        "position": 0,
                                        "is_public": true,
                                        "subscribable": true,
                                        "status": "degraded",
                                        "uptime_90d": 0.9982,
                                        "remote_trigger": {
                                            "webhook_enabled": true,
                                            "webhook_url": "https://status.example.com/remote/2f9c1d7ab3e54c08a1b6",
                                            "webhook_status": "degraded",
                                            "webhook_status_at": "2026-07-27T13:58:00Z",
                                            "host_system": null
                                        },
                                        "created_at": "2026-05-04T08:00:00Z",
                                        "updated_at": "2026-07-27T13:58:00Z"
                                    }
                                }
                            }
                        }
                    },
                    "404": {
                        "description": "Nicht gefunden",
                        "content": {
                            "application/json": {
                                "example": {
                                    "message": "Component not found."
                                }
                            }
                        }
                    }
                }
            },
            "patch": {
                "tags": [
                    "Komponenten"
                ],
                "summary": "Komponente aktualisieren",
                "operationId": "patchApiV1ComponentsComponent",
                "description": "Partiell: Weggelassene Felder behalten ihren Wert, eine weggelassene Sprache ihre Übersetzung.",
                "x-required-permission": "components.manage",
                "parameters": [
                    {
                        "name": "component",
                        "in": "path",
                        "required": true,
                        "schema": {
                            "type": "integer"
                        }
                    }
                ],
                "requestBody": {
                    "required": true,
                    "content": {
                        "application/json": {
                            "schema": {
                                "type": "object",
                                "properties": {
                                    "name": {
                                        "type": "string",
                                        "description": "Locale-Objekt, z. B. {\"de\": \"API-Gateway\", \"en\": \"API gateway\"}."
                                    },
                                    "description": {
                                        "type": "string",
                                        "description": "Locale-Objekt wie bei name."
                                    },
                                    "group_id": {
                                        "type": "integer"
                                    },
                                    "is_public": {
                                        "type": "boolean"
                                    },
                                    "subscribable": {
                                        "type": "boolean"
                                    },
                                    "position": {
                                        "type": "integer"
                                    },
                                    "webhook_enabled": {
                                        "type": "boolean"
                                    },
                                    "host_system_id": {
                                        "type": "integer"
                                    }
                                },
                                "required": [
                                    "name"
                                ]
                            }
                        }
                    }
                },
                "responses": {
                    "200": {
                        "description": "Erfolg",
                        "content": {
                            "application/json": {
                                "example": {
                                    "data": {
                                        "id": 3,
                                        "name": {
                                            "de": "API-Gateway",
                                            "en": "API gateway"
                                        },
                                        "description": {
                                            "de": "Die öffentliche Schnittstelle",
                                            "en": null
                                        },
                                        "slug": "api-gateway",
                                        "group_id": 1,
                                        "position": 0,
                                        "is_public": true,
                                        "subscribable": true,
                                        "status": "degraded",
                                        "uptime_90d": 0.9982,
                                        "remote_trigger": {
                                            "webhook_enabled": true,
                                            "webhook_url": "https://status.example.com/remote/2f9c1d7ab3e54c08a1b6",
                                            "webhook_status": "degraded",
                                            "webhook_status_at": "2026-07-27T13:58:00Z",
                                            "host_system": null
                                        },
                                        "created_at": "2026-05-04T08:00:00Z",
                                        "updated_at": "2026-07-27T13:58:00Z"
                                    }
                                }
                            }
                        }
                    },
                    "404": {
                        "description": "Nicht gefunden",
                        "content": {
                            "application/json": {
                                "example": {
                                    "message": "Component not found."
                                }
                            }
                        }
                    },
                    "422": {
                        "description": "Validierung fehlgeschlagen",
                        "content": {
                            "application/json": {
                                "example": {
                                    "message": "The name must remain filled in at least one language.",
                                    "errors": {
                                        "name": [
                                            "The name must remain filled in at least one language."
                                        ]
                                    }
                                }
                            }
                        }
                    }
                }
            },
            "put": {
                "tags": [
                    "Komponenten"
                ],
                "summary": "Komponente aktualisieren (Alias von PATCH)",
                "operationId": "putApiV1ComponentsComponent",
                "description": "Identisch zu PATCH, für Clients, die PUT bevorzugen.",
                "x-required-permission": "components.manage",
                "parameters": [
                    {
                        "name": "component",
                        "in": "path",
                        "required": true,
                        "schema": {
                            "type": "integer"
                        }
                    }
                ],
                "requestBody": {
                    "required": true,
                    "content": {
                        "application/json": {
                            "schema": {
                                "type": "object",
                                "properties": {
                                    "name": {
                                        "type": "string",
                                        "description": "Locale-Objekt, z. B. {\"de\": \"API-Gateway\", \"en\": \"API gateway\"}."
                                    },
                                    "description": {
                                        "type": "string",
                                        "description": "Locale-Objekt wie bei name."
                                    },
                                    "group_id": {
                                        "type": "integer"
                                    },
                                    "is_public": {
                                        "type": "boolean"
                                    },
                                    "subscribable": {
                                        "type": "boolean"
                                    },
                                    "position": {
                                        "type": "integer"
                                    },
                                    "webhook_enabled": {
                                        "type": "boolean"
                                    },
                                    "host_system_id": {
                                        "type": "integer"
                                    }
                                },
                                "required": [
                                    "name"
                                ]
                            }
                        }
                    }
                },
                "responses": {
                    "200": {
                        "description": "Erfolg",
                        "content": {
                            "application/json": {
                                "example": {
                                    "data": {
                                        "id": 3,
                                        "name": {
                                            "de": "API-Gateway",
                                            "en": "API gateway"
                                        },
                                        "description": {
                                            "de": "Die öffentliche Schnittstelle",
                                            "en": null
                                        },
                                        "slug": "api-gateway",
                                        "group_id": 1,
                                        "position": 0,
                                        "is_public": true,
                                        "subscribable": true,
                                        "status": "degraded",
                                        "uptime_90d": 0.9982,
                                        "remote_trigger": {
                                            "webhook_enabled": true,
                                            "webhook_url": "https://status.example.com/remote/2f9c1d7ab3e54c08a1b6",
                                            "webhook_status": "degraded",
                                            "webhook_status_at": "2026-07-27T13:58:00Z",
                                            "host_system": null
                                        },
                                        "created_at": "2026-05-04T08:00:00Z",
                                        "updated_at": "2026-07-27T13:58:00Z"
                                    }
                                }
                            }
                        }
                    },
                    "404": {
                        "description": "Nicht gefunden",
                        "content": {
                            "application/json": {
                                "example": {
                                    "message": "Component not found."
                                }
                            }
                        }
                    }
                }
            },
            "delete": {
                "tags": [
                    "Komponenten"
                ],
                "summary": "Komponente löschen",
                "operationId": "deleteApiV1ComponentsComponent",
                "description": "Endgültig — Komponenten haben keinen Papierkorb. Abonnements darauf und ihr Anteil an der Verfügbarkeitshistorie verschwinden mit.",
                "x-required-permission": "components.manage",
                "parameters": [
                    {
                        "name": "component",
                        "in": "path",
                        "required": true,
                        "schema": {
                            "type": "integer"
                        }
                    }
                ],
                "responses": {
                    "204": {
                        "description": "Gelöscht"
                    },
                    "404": {
                        "description": "Nicht gefunden",
                        "content": {
                            "application/json": {
                                "example": {
                                    "message": "Component not found."
                                }
                            }
                        }
                    }
                }
            }
        },
        "/component-groups": {
            "get": {
                "tags": [
                    "Komponenten"
                ],
                "summary": "Komponentengruppen auflisten",
                "operationId": "getApiV1ComponentGroups",
                "description": "Elternknoten zuerst sortiert, damit sich der Baum in einem Durchlauf aufbauen lässt.",
                "x-required-permission": "components.view",
                "parameters": [
                    {
                        "name": "page",
                        "in": "query",
                        "required": false,
                        "schema": {
                            "type": "integer"
                        }
                    },
                    {
                        "name": "per_page",
                        "in": "query",
                        "required": false,
                        "description": "Wird auf die maximale Seitengröße begrenzt statt abgewiesen.",
                        "schema": {
                            "type": "integer"
                        }
                    }
                ],
                "responses": {
                    "200": {
                        "description": "Erfolg",
                        "content": {
                            "application/json": {
                                "example": {
                                    "links": {
                                        "first": "https://status.example.com/api/v1/component-groups?page=1",
                                        "last": "https://status.example.com/api/v1/component-groups?page=1",
                                        "prev": null,
                                        "next": null
                                    },
                                    "meta": {
                                        "current_page": 1,
                                        "per_page": 25,
                                        "total": 1,
                                        "last_page": 1
                                    },
                                    "data": [
                                        {
                                            "id": 1,
                                            "name": {
                                                "de": "Rechenzentrum Frankfurt",
                                                "en": "Frankfurt data centre"
                                            },
                                            "slug": "rechenzentrum-frankfurt",
                                            "parent_id": null,
                                            "position": 0,
                                            "depth": 0,
                                            "created_at": "2026-05-04T08:00:00Z",
                                            "updated_at": "2026-05-04T08:00:00Z"
                                        }
                                    ]
                                }
                            }
                        }
                    }
                }
            },
            "post": {
                "tags": [
                    "Komponenten"
                ],
                "summary": "Gruppe anlegen",
                "operationId": "postApiV1ComponentGroups",
                "description": "Gruppen sind verschachtelbar — parent_id angeben, um eine Untergruppe anzulegen.",
                "x-required-permission": "components.manage",
                "requestBody": {
                    "required": true,
                    "content": {
                        "application/json": {
                            "schema": {
                                "type": "object",
                                "properties": {
                                    "name": {
                                        "type": "string",
                                        "description": "Locale-Objekt, z. B. {\"de\": \"API-Gateway\", \"en\": \"API gateway\"}."
                                    },
                                    "parent_id": {
                                        "type": "integer"
                                    },
                                    "position": {
                                        "type": "integer"
                                    }
                                },
                                "required": [
                                    "name"
                                ]
                            }
                        }
                    }
                },
                "responses": {
                    "201": {
                        "description": "Angelegt",
                        "content": {
                            "application/json": {
                                "example": {
                                    "data": {
                                        "id": 5,
                                        "name": {
                                            "de": "Rechenzentrum Frankfurt",
                                            "en": "Frankfurt data centre"
                                        },
                                        "slug": "rechenzentrum-frankfurt",
                                        "parent_id": null,
                                        "position": 0,
                                        "depth": 0,
                                        "created_at": "2026-07-27T14:00:00Z",
                                        "updated_at": "2026-07-27T14:00:00Z"
                                    }
                                }
                            }
                        }
                    },
                    "422": {
                        "description": "Validierung fehlgeschlagen",
                        "content": {
                            "application/json": {
                                "example": {
                                    "message": "The name field must be filled in at least one language (de, en).",
                                    "errors": {
                                        "name": [
                                            "The name field must be filled in at least one language (de, en)."
                                        ]
                                    }
                                }
                            }
                        }
                    }
                }
            }
        },
        "/component-groups/{group}": {
            "get": {
                "tags": [
                    "Komponenten"
                ],
                "summary": "Gruppe abrufen",
                "operationId": "getApiV1ComponentGroupsGroup",
                "description": "Enthält die Tiefe der Gruppe im Baum.",
                "x-required-permission": "components.view",
                "parameters": [
                    {
                        "name": "group",
                        "in": "path",
                        "required": true,
                        "schema": {
                            "type": "integer"
                        }
                    }
                ],
                "responses": {
                    "200": {
                        "description": "Erfolg",
                        "content": {
                            "application/json": {
                                "example": {
                                    "data": {
                                        "id": 1,
                                        "name": {
                                            "de": "Rechenzentrum Frankfurt",
                                            "en": "Frankfurt data centre"
                                        },
                                        "slug": "rechenzentrum-frankfurt",
                                        "parent_id": null,
                                        "position": 0,
                                        "depth": 0,
                                        "created_at": "2026-05-04T08:00:00Z",
                                        "updated_at": "2026-05-04T08:00:00Z"
                                    }
                                }
                            }
                        }
                    },
                    "404": {
                        "description": "Nicht gefunden",
                        "content": {
                            "application/json": {
                                "example": {
                                    "message": "Component group not found."
                                }
                            }
                        }
                    }
                }
            },
            "patch": {
                "tags": [
                    "Komponenten"
                ],
                "summary": "Gruppe umbenennen oder verschieben",
                "operationId": "patchApiV1ComponentGroupsGroup",
                "description": "Beim Verschieben werden die Baum-Invarianten erneut geprüft: nicht in den eigenen Teilbaum und innerhalb der maximalen Verschachtelungstiefe.",
                "x-required-permission": "components.manage",
                "parameters": [
                    {
                        "name": "group",
                        "in": "path",
                        "required": true,
                        "schema": {
                            "type": "integer"
                        }
                    }
                ],
                "requestBody": {
                    "required": true,
                    "content": {
                        "application/json": {
                            "schema": {
                                "type": "object",
                                "properties": {
                                    "name": {
                                        "type": "string",
                                        "description": "Locale-Objekt, z. B. {\"de\": \"API-Gateway\", \"en\": \"API gateway\"}."
                                    },
                                    "parent_id": {
                                        "type": "integer"
                                    },
                                    "position": {
                                        "type": "integer"
                                    }
                                },
                                "required": [
                                    "name"
                                ]
                            }
                        }
                    }
                },
                "responses": {
                    "200": {
                        "description": "Erfolg",
                        "content": {
                            "application/json": {
                                "example": {
                                    "data": {
                                        "id": 1,
                                        "name": {
                                            "de": "Rechenzentrum Frankfurt",
                                            "en": "Frankfurt data centre"
                                        },
                                        "slug": "rechenzentrum-frankfurt",
                                        "parent_id": null,
                                        "position": 0,
                                        "depth": 0,
                                        "created_at": "2026-05-04T08:00:00Z",
                                        "updated_at": "2026-05-04T08:00:00Z"
                                    }
                                }
                            }
                        }
                    },
                    "404": {
                        "description": "Nicht gefunden",
                        "content": {
                            "application/json": {
                                "example": {
                                    "message": "Component group not found."
                                }
                            }
                        }
                    },
                    "422": {
                        "description": "Validierung fehlgeschlagen",
                        "content": {
                            "application/json": {
                                "example": {
                                    "message": "A group cannot be moved into itself or one of its own sub-groups.",
                                    "errors": {
                                        "parent_id": [
                                            "A group cannot be moved into itself or one of its own sub-groups."
                                        ]
                                    }
                                }
                            }
                        }
                    }
                }
            },
            "put": {
                "tags": [
                    "Komponenten"
                ],
                "summary": "Gruppe aktualisieren (Alias von PATCH)",
                "operationId": "putApiV1ComponentGroupsGroup",
                "description": "Identisch zu PATCH, für Clients, die PUT bevorzugen.",
                "x-required-permission": "components.manage",
                "parameters": [
                    {
                        "name": "group",
                        "in": "path",
                        "required": true,
                        "schema": {
                            "type": "integer"
                        }
                    }
                ],
                "requestBody": {
                    "required": true,
                    "content": {
                        "application/json": {
                            "schema": {
                                "type": "object",
                                "properties": {
                                    "name": {
                                        "type": "string",
                                        "description": "Locale-Objekt, z. B. {\"de\": \"API-Gateway\", \"en\": \"API gateway\"}."
                                    },
                                    "parent_id": {
                                        "type": "integer"
                                    },
                                    "position": {
                                        "type": "integer"
                                    }
                                },
                                "required": [
                                    "name"
                                ]
                            }
                        }
                    }
                },
                "responses": {
                    "200": {
                        "description": "Erfolg",
                        "content": {
                            "application/json": {
                                "example": {
                                    "data": {
                                        "id": 1,
                                        "name": {
                                            "de": "Rechenzentrum Frankfurt",
                                            "en": "Frankfurt data centre"
                                        },
                                        "slug": "rechenzentrum-frankfurt",
                                        "parent_id": null,
                                        "position": 0,
                                        "depth": 0,
                                        "created_at": "2026-05-04T08:00:00Z",
                                        "updated_at": "2026-05-04T08:00:00Z"
                                    }
                                }
                            }
                        }
                    },
                    "404": {
                        "description": "Nicht gefunden",
                        "content": {
                            "application/json": {
                                "example": {
                                    "message": "Component group not found."
                                }
                            }
                        }
                    }
                }
            },
            "delete": {
                "tags": [
                    "Komponenten"
                ],
                "summary": "Gruppe löschen",
                "operationId": "deleteApiV1ComponentGroupsGroup",
                "description": "Wird abgelehnt, solange die Gruppe noch Komponenten oder Untergruppen enthält.",
                "x-required-permission": "components.manage",
                "parameters": [
                    {
                        "name": "group",
                        "in": "path",
                        "required": true,
                        "schema": {
                            "type": "integer"
                        }
                    }
                ],
                "responses": {
                    "204": {
                        "description": "Gelöscht"
                    },
                    "404": {
                        "description": "Nicht gefunden",
                        "content": {
                            "application/json": {
                                "example": {
                                    "message": "Component group not found."
                                }
                            }
                        }
                    },
                    "422": {
                        "description": "Validierung fehlgeschlagen",
                        "content": {
                            "application/json": {
                                "example": {
                                    "message": "This group still contains components or sub-groups. Move or delete them first.",
                                    "errors": {
                                        "group": [
                                            "This group still contains components or sub-groups. Move or delete them first."
                                        ]
                                    }
                                }
                            }
                        }
                    }
                }
            }
        },
        "/incidents": {
            "get": {
                "tags": [
                    "Vorfälle"
                ],
                "summary": "Vorfälle auflisten",
                "operationId": "getApiV1Incidents",
                "description": "Entwürfe, geplante und veröffentlichte Vorfälle gleichermaßen. Papierkorb-Einträge sind ausgenommen.",
                "x-required-permission": "incidents.manage",
                "parameters": [
                    {
                        "name": "page",
                        "in": "query",
                        "required": false,
                        "schema": {
                            "type": "integer"
                        }
                    },
                    {
                        "name": "per_page",
                        "in": "query",
                        "required": false,
                        "description": "Wird auf die maximale Seitengröße begrenzt statt abgewiesen.",
                        "schema": {
                            "type": "integer"
                        }
                    },
                    {
                        "name": "status",
                        "in": "query",
                        "required": false,
                        "schema": {
                            "$ref": "#/components/schemas/incidents_status"
                        }
                    },
                    {
                        "name": "state",
                        "in": "query",
                        "required": false,
                        "description": "Veröffentlichungs-Lebenszyklus, im Unterschied zum Arbeitsstatus.",
                        "schema": {
                            "$ref": "#/components/schemas/incidents_state"
                        }
                    },
                    {
                        "name": "active",
                        "in": "query",
                        "required": false,
                        "description": "Veröffentlicht und noch nicht abgeschlossen.",
                        "schema": {
                            "type": "boolean"
                        }
                    },
                    {
                        "name": "since",
                        "in": "query",
                        "required": false,
                        "description": "Untere Grenze für started_at.",
                        "schema": {
                            "type": "string"
                        }
                    },
                    {
                        "name": "until",
                        "in": "query",
                        "required": false,
                        "description": "Obere Grenze für started_at.",
                        "schema": {
                            "type": "string"
                        }
                    },
                    {
                        "name": "component_id",
                        "in": "query",
                        "required": false,
                        "schema": {
                            "type": "integer"
                        }
                    },
                    {
                        "name": "q",
                        "in": "query",
                        "required": false,
                        "description": "Groß-/Kleinschreibung-unabhängige Teilstring-Suche über Titel und Text in allen Sprachen.",
                        "schema": {
                            "type": "string"
                        }
                    }
                ],
                "responses": {
                    "200": {
                        "description": "Erfolg",
                        "content": {
                            "application/json": {
                                "example": {
                                    "links": {
                                        "first": "https://status.example.com/api/v1/incidents?page=1",
                                        "last": "https://status.example.com/api/v1/incidents?page=1",
                                        "prev": null,
                                        "next": null
                                    },
                                    "meta": {
                                        "current_page": 1,
                                        "per_page": 25,
                                        "total": 1,
                                        "last_page": 1
                                    },
                                    "data": [
                                        {
                                            "id": 12,
                                            "type": "incident",
                                            "status": "investigating",
                                            "title": {
                                                "de": "Störung im Netz",
                                                "en": "Network issue"
                                            },
                                            "body": {
                                                "de": "Wir untersuchen erhöhte Latenzen.",
                                                "en": null
                                            },
                                            "started_at": "2026-07-27T13:55:00Z",
                                            "scheduled_end_at": null,
                                            "published_at": "2026-07-27T14:00:00Z",
                                            "publish_at": "2026-07-27T14:00:00Z",
                                            "resolved_at": null,
                                            "acknowledged_at": null,
                                            "is_published": true,
                                            "is_scheduled": false,
                                            "is_resolved": false,
                                            "components": [
                                                {
                                                    "id": 3,
                                                    "impact": "degraded"
                                                }
                                            ],
                                            "public_url": "https://status.example.com/incidents/12",
                                            "updates": [],
                                            "created_at": "2026-07-27T14:00:00Z",
                                            "updated_at": "2026-07-27T14:00:00Z"
                                        }
                                    ]
                                }
                            }
                        }
                    }
                }
            },
            "post": {
                "tags": [
                    "Vorfälle"
                ],
                "summary": "Vorfall anlegen",
                "operationId": "postApiV1Incidents",
                "description": "Die Veröffentlichung ist eine ausdrückliche Entscheidung — sofort veröffentlichen, für später planen oder als Entwurf behalten. Sie wird nie daraus abgeleitet, welcher Zeitstempel gerade gesetzt ist.",
                "x-required-permission": "incidents.manage",
                "requestBody": {
                    "required": true,
                    "content": {
                        "application/json": {
                            "schema": {
                                "type": "object",
                                "properties": {
                                    "title": {
                                        "type": "string",
                                        "description": "Locale-Objekt, z. B. {\"de\": \"Störung\", \"en\": \"Outage\"}. Bei PATCH partiell; ein explizites null löscht die Übersetzung."
                                    },
                                    "body": {
                                        "type": "string",
                                        "description": "Locale-Objekt wie bei title. Markdown erlaubt."
                                    },
                                    "status": {
                                        "$ref": "#/components/schemas/incidents_status",
                                        "description": "Status, die ein VORFALL annehmen kann (IncidentStatus::forType)."
                                    },
                                    "components": {
                                        "type": "string",
                                        "description": "Liste betroffener Komponenten als JSON-Array, je Eintrag {\"id\": 3, \"impact\": \"degraded\"}. Erlaubte Auswirkungen: degraded, partial_outage, major_outage, under_maintenance."
                                    },
                                    "started_at": {
                                        "type": "string",
                                        "description": "Wann der Vorfall tatsächlich begann; darf vor dem Datensatz liegen."
                                    },
                                    "publish": {
                                        "$ref": "#/components/schemas/incidents_publish"
                                    },
                                    "publish_at": {
                                        "type": "string",
                                        "description": "Erforderlich bei publish=schedule; muss in der Zukunft liegen."
                                    },
                                    "notify": {
                                        "type": "boolean",
                                        "description": "Wird nur ausgewertet, wenn tatsächlich veröffentlicht wird."
                                    }
                                },
                                "required": [
                                    "title"
                                ]
                            }
                        }
                    }
                },
                "responses": {
                    "201": {
                        "description": "Angelegt",
                        "content": {
                            "application/json": {
                                "example": {
                                    "data": {
                                        "id": 12,
                                        "type": "incident",
                                        "status": "investigating",
                                        "title": {
                                            "de": "Störung im Netz",
                                            "en": "Network issue"
                                        },
                                        "body": {
                                            "de": "Wir untersuchen erhöhte Latenzen.",
                                            "en": null
                                        },
                                        "started_at": "2026-07-27T13:55:00Z",
                                        "scheduled_end_at": null,
                                        "published_at": "2026-07-27T14:00:00Z",
                                        "publish_at": "2026-07-27T14:00:00Z",
                                        "resolved_at": null,
                                        "acknowledged_at": null,
                                        "is_published": true,
                                        "is_scheduled": false,
                                        "is_resolved": false,
                                        "components": [
                                            {
                                                "id": 3,
                                                "impact": "degraded"
                                            }
                                        ],
                                        "public_url": "https://status.example.com/incidents/12",
                                        "updates": [],
                                        "created_at": "2026-07-27T14:00:00Z",
                                        "updated_at": "2026-07-27T14:00:00Z"
                                    }
                                }
                            }
                        }
                    },
                    "422": {
                        "description": "Validierung fehlgeschlagen",
                        "content": {
                            "application/json": {
                                "example": {
                                    "message": "The title field must be filled in at least one language (de, en).",
                                    "errors": {
                                        "title": [
                                            "The title field must be filled in at least one language (de, en)."
                                        ]
                                    }
                                }
                            }
                        }
                    }
                }
            }
        },
        "/incidents/{incident}": {
            "get": {
                "tags": [
                    "Vorfälle"
                ],
                "summary": "Vorfall mit Verlauf abrufen",
                "operationId": "getApiV1IncidentsIncident",
                "description": "Enthält den vollständigen Verlauf.",
                "x-required-permission": "incidents.manage",
                "parameters": [
                    {
                        "name": "incident",
                        "in": "path",
                        "required": true,
                        "description": "Numerische ID des Vorfalls bzw. Wartungsfensters. Beide Collections liegen auf einem Modell — deshalb heißt der Platzhalter auch auf den Wartungs-Routen {incident}.",
                        "schema": {
                            "type": "integer"
                        }
                    }
                ],
                "responses": {
                    "200": {
                        "description": "Erfolg",
                        "content": {
                            "application/json": {
                                "example": {
                                    "data": {
                                        "id": 12,
                                        "type": "incident",
                                        "status": "investigating",
                                        "title": {
                                            "de": "Störung im Netz",
                                            "en": "Network issue"
                                        },
                                        "body": {
                                            "de": "Wir untersuchen erhöhte Latenzen.",
                                            "en": null
                                        },
                                        "started_at": "2026-07-27T13:55:00Z",
                                        "scheduled_end_at": null,
                                        "published_at": "2026-07-27T14:00:00Z",
                                        "publish_at": "2026-07-27T14:00:00Z",
                                        "resolved_at": null,
                                        "acknowledged_at": null,
                                        "is_published": true,
                                        "is_scheduled": false,
                                        "is_resolved": false,
                                        "components": [
                                            {
                                                "id": 3,
                                                "impact": "degraded"
                                            }
                                        ],
                                        "public_url": "https://status.example.com/incidents/12",
                                        "updates": [],
                                        "created_at": "2026-07-27T14:00:00Z",
                                        "updated_at": "2026-07-27T14:00:00Z"
                                    }
                                }
                            }
                        }
                    },
                    "404": {
                        "description": "Nicht gefunden",
                        "content": {
                            "application/json": {
                                "example": {
                                    "message": "Incident not found."
                                }
                            }
                        }
                    }
                }
            },
            "patch": {
                "tags": [
                    "Vorfälle"
                ],
                "summary": "Vorfall aktualisieren",
                "operationId": "patchApiV1IncidentsIncident",
                "description": "Nur Stammdaten. published_at, publish_at und resolved_at sind hier NICHT schreibbar — dafür gibt es die Lebenszyklus-Endpunkte.",
                "x-required-permission": "incidents.manage",
                "parameters": [
                    {
                        "name": "incident",
                        "in": "path",
                        "required": true,
                        "description": "Numerische ID des Vorfalls bzw. Wartungsfensters. Beide Collections liegen auf einem Modell — deshalb heißt der Platzhalter auch auf den Wartungs-Routen {incident}.",
                        "schema": {
                            "type": "integer"
                        }
                    }
                ],
                "requestBody": {
                    "required": false,
                    "content": {
                        "application/json": {
                            "schema": {
                                "type": "object",
                                "properties": {
                                    "title": {
                                        "type": "string",
                                        "description": "Locale-Objekt, z. B. {\"de\": \"Störung\", \"en\": \"Outage\"}. Bei PATCH partiell; ein explizites null löscht die Übersetzung."
                                    },
                                    "body": {
                                        "type": "string",
                                        "description": "Locale-Objekt wie bei title. Markdown erlaubt."
                                    },
                                    "status": {
                                        "$ref": "#/components/schemas/incidents_status",
                                        "description": "Status, die ein VORFALL annehmen kann (IncidentStatus::forType)."
                                    },
                                    "started_at": {
                                        "type": "string"
                                    },
                                    "components": {
                                        "type": "string",
                                        "description": "Liste betroffener Komponenten als JSON-Array, je Eintrag {\"id\": 3, \"impact\": \"degraded\"}. Erlaubte Auswirkungen: degraded, partial_outage, major_outage, under_maintenance."
                                    }
                                }
                            }
                        }
                    }
                },
                "responses": {
                    "200": {
                        "description": "Erfolg",
                        "content": {
                            "application/json": {
                                "example": {
                                    "data": {
                                        "id": 12,
                                        "type": "incident",
                                        "status": "investigating",
                                        "title": {
                                            "de": "Störung im Netz",
                                            "en": "Network issue"
                                        },
                                        "body": {
                                            "de": "Wir untersuchen erhöhte Latenzen.",
                                            "en": null
                                        },
                                        "started_at": "2026-07-27T13:55:00Z",
                                        "scheduled_end_at": null,
                                        "published_at": "2026-07-27T14:00:00Z",
                                        "publish_at": "2026-07-27T14:00:00Z",
                                        "resolved_at": null,
                                        "acknowledged_at": null,
                                        "is_published": true,
                                        "is_scheduled": false,
                                        "is_resolved": false,
                                        "components": [
                                            {
                                                "id": 3,
                                                "impact": "degraded"
                                            }
                                        ],
                                        "public_url": "https://status.example.com/incidents/12",
                                        "updates": [],
                                        "created_at": "2026-07-27T14:00:00Z",
                                        "updated_at": "2026-07-27T14:00:00Z"
                                    }
                                }
                            }
                        }
                    },
                    "404": {
                        "description": "Nicht gefunden",
                        "content": {
                            "application/json": {
                                "example": {
                                    "message": "Incident not found."
                                }
                            }
                        }
                    },
                    "422": {
                        "description": "Validierung fehlgeschlagen",
                        "content": {
                            "application/json": {
                                "example": {
                                    "message": "The title must remain filled in at least one language.",
                                    "errors": {
                                        "title": [
                                            "The title must remain filled in at least one language."
                                        ]
                                    }
                                }
                            }
                        }
                    }
                }
            },
            "put": {
                "tags": [
                    "Vorfälle"
                ],
                "summary": "Vorfall aktualisieren (Alias von PATCH)",
                "operationId": "putApiV1IncidentsIncident",
                "description": "Identisch zu PATCH, für Clients, die PUT bevorzugen.",
                "x-required-permission": "incidents.manage",
                "parameters": [
                    {
                        "name": "incident",
                        "in": "path",
                        "required": true,
                        "description": "Numerische ID des Vorfalls bzw. Wartungsfensters. Beide Collections liegen auf einem Modell — deshalb heißt der Platzhalter auch auf den Wartungs-Routen {incident}.",
                        "schema": {
                            "type": "integer"
                        }
                    }
                ],
                "requestBody": {
                    "required": false,
                    "content": {
                        "application/json": {
                            "schema": {
                                "type": "object",
                                "properties": {
                                    "title": {
                                        "type": "string",
                                        "description": "Locale-Objekt, z. B. {\"de\": \"Störung\", \"en\": \"Outage\"}. Bei PATCH partiell; ein explizites null löscht die Übersetzung."
                                    },
                                    "body": {
                                        "type": "string",
                                        "description": "Locale-Objekt wie bei title. Markdown erlaubt."
                                    },
                                    "status": {
                                        "$ref": "#/components/schemas/incidents_status",
                                        "description": "Status, die ein VORFALL annehmen kann (IncidentStatus::forType)."
                                    },
                                    "started_at": {
                                        "type": "string"
                                    },
                                    "components": {
                                        "type": "string",
                                        "description": "Liste betroffener Komponenten als JSON-Array, je Eintrag {\"id\": 3, \"impact\": \"degraded\"}. Erlaubte Auswirkungen: degraded, partial_outage, major_outage, under_maintenance."
                                    }
                                }
                            }
                        }
                    }
                },
                "responses": {
                    "200": {
                        "description": "Erfolg",
                        "content": {
                            "application/json": {
                                "example": {
                                    "data": {
                                        "id": 12,
                                        "type": "incident",
                                        "status": "investigating",
                                        "title": {
                                            "de": "Störung im Netz",
                                            "en": "Network issue"
                                        },
                                        "body": {
                                            "de": "Wir untersuchen erhöhte Latenzen.",
                                            "en": null
                                        },
                                        "started_at": "2026-07-27T13:55:00Z",
                                        "scheduled_end_at": null,
                                        "published_at": "2026-07-27T14:00:00Z",
                                        "publish_at": "2026-07-27T14:00:00Z",
                                        "resolved_at": null,
                                        "acknowledged_at": null,
                                        "is_published": true,
                                        "is_scheduled": false,
                                        "is_resolved": false,
                                        "components": [
                                            {
                                                "id": 3,
                                                "impact": "degraded"
                                            }
                                        ],
                                        "public_url": "https://status.example.com/incidents/12",
                                        "updates": [],
                                        "created_at": "2026-07-27T14:00:00Z",
                                        "updated_at": "2026-07-27T14:00:00Z"
                                    }
                                }
                            }
                        }
                    },
                    "404": {
                        "description": "Nicht gefunden",
                        "content": {
                            "application/json": {
                                "example": {
                                    "message": "Incident not found."
                                }
                            }
                        }
                    }
                }
            },
            "delete": {
                "tags": [
                    "Vorfälle"
                ],
                "summary": "Vorfall in den Papierkorb verschieben",
                "operationId": "deleteApiV1IncidentsIncident",
                "description": "Papierkorb: verschwindet von der Statusseite und aus der Verfügbarkeitshistorie, 30 Tage lang wiederherstellbar.",
                "x-required-permission": "incidents.manage",
                "parameters": [
                    {
                        "name": "incident",
                        "in": "path",
                        "required": true,
                        "description": "Numerische ID des Vorfalls bzw. Wartungsfensters. Beide Collections liegen auf einem Modell — deshalb heißt der Platzhalter auch auf den Wartungs-Routen {incident}.",
                        "schema": {
                            "type": "integer"
                        }
                    }
                ],
                "responses": {
                    "204": {
                        "description": "Gelöscht"
                    },
                    "404": {
                        "description": "Nicht gefunden",
                        "content": {
                            "application/json": {
                                "example": {
                                    "message": "Incident not found."
                                }
                            }
                        }
                    }
                }
            }
        },
        "/incidents/{incident}/publish": {
            "post": {
                "tags": [
                    "Vorfälle"
                ],
                "summary": "Veröffentlichen",
                "operationId": "postApiV1IncidentsIncidentPublish",
                "description": "Macht den Vorfall öffentlich und benachrichtigt Abonnenten, sofern notify nicht false ist. Antwortet mit 409, wenn er bereits veröffentlicht ist.",
                "x-required-permission": "incidents.manage",
                "parameters": [
                    {
                        "name": "incident",
                        "in": "path",
                        "required": true,
                        "description": "Numerische ID des Vorfalls bzw. Wartungsfensters. Beide Collections liegen auf einem Modell — deshalb heißt der Platzhalter auch auf den Wartungs-Routen {incident}.",
                        "schema": {
                            "type": "integer"
                        }
                    }
                ],
                "requestBody": {
                    "required": false,
                    "content": {
                        "application/json": {
                            "schema": {
                                "type": "object",
                                "properties": {
                                    "at": {
                                        "type": "string",
                                        "description": "Datiert den öffentlichen Zeitstempel zurück."
                                    },
                                    "notify": {
                                        "type": "boolean"
                                    }
                                }
                            }
                        }
                    }
                },
                "responses": {
                    "200": {
                        "description": "Erfolg",
                        "content": {
                            "application/json": {
                                "example": {
                                    "data": {
                                        "id": 12,
                                        "type": "incident",
                                        "status": "investigating",
                                        "title": {
                                            "de": "Störung im Netz",
                                            "en": "Network issue"
                                        },
                                        "body": {
                                            "de": "Wir untersuchen erhöhte Latenzen.",
                                            "en": null
                                        },
                                        "started_at": "2026-07-27T13:55:00Z",
                                        "scheduled_end_at": null,
                                        "published_at": "2026-07-27T14:00:00Z",
                                        "publish_at": "2026-07-27T14:00:00Z",
                                        "resolved_at": null,
                                        "acknowledged_at": null,
                                        "is_published": true,
                                        "is_scheduled": false,
                                        "is_resolved": false,
                                        "components": [
                                            {
                                                "id": 3,
                                                "impact": "degraded"
                                            }
                                        ],
                                        "public_url": "https://status.example.com/incidents/12",
                                        "updates": [],
                                        "created_at": "2026-07-27T14:00:00Z",
                                        "updated_at": "2026-07-27T14:00:00Z"
                                    }
                                }
                            }
                        }
                    },
                    "404": {
                        "description": "Nicht gefunden",
                        "content": {
                            "application/json": {
                                "example": {
                                    "message": "Incident not found."
                                }
                            }
                        }
                    },
                    "409": {
                        "description": "Konflikt",
                        "content": {
                            "application/json": {
                                "example": {
                                    "message": "Incident is already published."
                                }
                            }
                        }
                    }
                }
            }
        },
        "/incidents/{incident}/resolve": {
            "post": {
                "tags": [
                    "Vorfälle"
                ],
                "summary": "Ohne Notiz beheben",
                "operationId": "postApiV1IncidentsIncidentResolve",
                "description": "Um MIT Abschlusstext zu schließen, stattdessen einen Verlaufseintrag mit terminalem Status veröffentlichen — ein Aufruf, eine Benachrichtigung.",
                "x-required-permission": "incidents.manage",
                "parameters": [
                    {
                        "name": "incident",
                        "in": "path",
                        "required": true,
                        "description": "Numerische ID des Vorfalls bzw. Wartungsfensters. Beide Collections liegen auf einem Modell — deshalb heißt der Platzhalter auch auf den Wartungs-Routen {incident}.",
                        "schema": {
                            "type": "integer"
                        }
                    }
                ],
                "requestBody": {
                    "required": false,
                    "content": {
                        "application/json": {
                            "schema": {
                                "type": "object",
                                "properties": {
                                    "at": {
                                        "type": "string"
                                    }
                                }
                            }
                        }
                    }
                },
                "responses": {
                    "200": {
                        "description": "Erfolg",
                        "content": {
                            "application/json": {
                                "example": {
                                    "data": {
                                        "id": 12,
                                        "type": "incident",
                                        "status": "investigating",
                                        "title": {
                                            "de": "Störung im Netz",
                                            "en": "Network issue"
                                        },
                                        "body": {
                                            "de": "Wir untersuchen erhöhte Latenzen.",
                                            "en": null
                                        },
                                        "started_at": "2026-07-27T13:55:00Z",
                                        "scheduled_end_at": null,
                                        "published_at": "2026-07-27T14:00:00Z",
                                        "publish_at": "2026-07-27T14:00:00Z",
                                        "resolved_at": null,
                                        "acknowledged_at": null,
                                        "is_published": true,
                                        "is_scheduled": false,
                                        "is_resolved": false,
                                        "components": [
                                            {
                                                "id": 3,
                                                "impact": "degraded"
                                            }
                                        ],
                                        "public_url": "https://status.example.com/incidents/12",
                                        "updates": [],
                                        "created_at": "2026-07-27T14:00:00Z",
                                        "updated_at": "2026-07-27T14:00:00Z"
                                    }
                                }
                            }
                        }
                    },
                    "404": {
                        "description": "Nicht gefunden",
                        "content": {
                            "application/json": {
                                "example": {
                                    "message": "Incident not found."
                                }
                            }
                        }
                    },
                    "409": {
                        "description": "Konflikt",
                        "content": {
                            "application/json": {
                                "example": {
                                    "message": "Incident is already resolved."
                                }
                            }
                        }
                    }
                }
            }
        },
        "/incidents/{incident}/updates": {
            "get": {
                "tags": [
                    "Vorfälle"
                ],
                "summary": "Verlaufseinträge auflisten",
                "operationId": "getApiV1IncidentsIncidentUpdates",
                "description": "Neueste zuerst.",
                "x-required-permission": "incidents.manage",
                "parameters": [
                    {
                        "name": "incident",
                        "in": "path",
                        "required": true,
                        "description": "Numerische ID des Vorfalls bzw. Wartungsfensters. Beide Collections liegen auf einem Modell — deshalb heißt der Platzhalter auch auf den Wartungs-Routen {incident}.",
                        "schema": {
                            "type": "integer"
                        }
                    },
                    {
                        "name": "page",
                        "in": "query",
                        "required": false,
                        "schema": {
                            "type": "integer"
                        }
                    },
                    {
                        "name": "per_page",
                        "in": "query",
                        "required": false,
                        "description": "Wird auf die maximale Seitengröße begrenzt statt abgewiesen.",
                        "schema": {
                            "type": "integer"
                        }
                    }
                ],
                "responses": {
                    "200": {
                        "description": "Erfolg",
                        "content": {
                            "application/json": {
                                "example": {
                                    "links": {
                                        "first": "https://status.example.com/api/v1/incidents/{incident}/updates?page=1",
                                        "last": "https://status.example.com/api/v1/incidents/{incident}/updates?page=1",
                                        "prev": null,
                                        "next": null
                                    },
                                    "meta": {
                                        "current_page": 1,
                                        "per_page": 25,
                                        "total": 1,
                                        "last_page": 1
                                    },
                                    "data": [
                                        {
                                            "id": 41,
                                            "incident_id": 12,
                                            "status": "monitoring",
                                            "body": {
                                                "de": "Ursache gefunden, wir beobachten.",
                                                "en": "Cause identified, monitoring."
                                            },
                                            "posted_at": "2026-07-27T14:20:00Z",
                                            "created_at": "2026-07-27T14:20:00Z"
                                        }
                                    ]
                                }
                            }
                        }
                    }
                }
            },
            "post": {
                "tags": [
                    "Vorfälle"
                ],
                "summary": "Verlaufseintrag veröffentlichen",
                "operationId": "postApiV1IncidentsIncidentUpdates",
                "description": "Enthält den neuen Status, den Text und optional geänderte Komponenten-Auswirkungen; benachrichtigt Abonnenten mit diesem Text. Ein terminaler Status schließt den Vorfall.",
                "x-required-permission": "incidents.manage",
                "parameters": [
                    {
                        "name": "incident",
                        "in": "path",
                        "required": true,
                        "description": "Numerische ID des Vorfalls bzw. Wartungsfensters. Beide Collections liegen auf einem Modell — deshalb heißt der Platzhalter auch auf den Wartungs-Routen {incident}.",
                        "schema": {
                            "type": "integer"
                        }
                    }
                ],
                "requestBody": {
                    "required": true,
                    "content": {
                        "application/json": {
                            "schema": {
                                "type": "object",
                                "properties": {
                                    "status": {
                                        "$ref": "#/components/schemas/incident_updates_status",
                                        "description": "Status, die ein VORFALL annehmen kann (IncidentStatus::forType)."
                                    },
                                    "body": {
                                        "type": "string",
                                        "description": "Locale-Objekt wie bei title. Markdown erlaubt."
                                    },
                                    "components": {
                                        "type": "string",
                                        "description": "Liste betroffener Komponenten als JSON-Array, je Eintrag {\"id\": 3, \"impact\": \"degraded\"}. Erlaubte Auswirkungen: degraded, partial_outage, major_outage, under_maintenance."
                                    },
                                    "posted_at": {
                                        "type": "string"
                                    },
                                    "notify": {
                                        "type": "boolean"
                                    }
                                },
                                "required": [
                                    "status",
                                    "body"
                                ]
                            }
                        }
                    }
                },
                "responses": {
                    "201": {
                        "description": "Angelegt",
                        "content": {
                            "application/json": {
                                "example": {
                                    "data": {
                                        "id": 41,
                                        "incident_id": 12,
                                        "status": "monitoring",
                                        "body": {
                                            "de": "Ursache gefunden, wir beobachten.",
                                            "en": "Cause identified, monitoring."
                                        },
                                        "posted_at": "2026-07-27T14:20:00Z",
                                        "created_at": "2026-07-27T14:20:00Z"
                                    }
                                }
                            }
                        }
                    },
                    "404": {
                        "description": "Nicht gefunden",
                        "content": {
                            "application/json": {
                                "example": {
                                    "message": "Incident not found."
                                }
                            }
                        }
                    },
                    "422": {
                        "description": "Validierung fehlgeschlagen",
                        "content": {
                            "application/json": {
                                "example": {
                                    "message": "The body field must be filled in at least one language (de, en).",
                                    "errors": {
                                        "body": [
                                            "The body field must be filled in at least one language (de, en)."
                                        ]
                                    }
                                }
                            }
                        }
                    }
                }
            }
        },
        "/maintenances": {
            "get": {
                "tags": [
                    "Wartungen"
                ],
                "summary": "Wartungsfenster auflisten",
                "operationId": "getApiV1Maintenances",
                "description": "Nur geplante Fenster; ungeplante Ereignisse liegen unter /incidents.",
                "x-required-permission": "incidents.manage",
                "parameters": [
                    {
                        "name": "page",
                        "in": "query",
                        "required": false,
                        "schema": {
                            "type": "integer"
                        }
                    },
                    {
                        "name": "per_page",
                        "in": "query",
                        "required": false,
                        "description": "Wird auf die maximale Seitengröße begrenzt statt abgewiesen.",
                        "schema": {
                            "type": "integer"
                        }
                    },
                    {
                        "name": "status",
                        "in": "query",
                        "required": false,
                        "schema": {
                            "$ref": "#/components/schemas/maintenances_status"
                        }
                    },
                    {
                        "name": "state",
                        "in": "query",
                        "required": false,
                        "description": "Veröffentlichungs-Lebenszyklus, im Unterschied zum Arbeitsstatus.",
                        "schema": {
                            "$ref": "#/components/schemas/maintenances_state"
                        }
                    },
                    {
                        "name": "active",
                        "in": "query",
                        "required": false,
                        "description": "Veröffentlicht und noch nicht abgeschlossen.",
                        "schema": {
                            "type": "boolean"
                        }
                    },
                    {
                        "name": "since",
                        "in": "query",
                        "required": false,
                        "description": "Untere Grenze für started_at.",
                        "schema": {
                            "type": "string"
                        }
                    },
                    {
                        "name": "until",
                        "in": "query",
                        "required": false,
                        "description": "Obere Grenze für started_at.",
                        "schema": {
                            "type": "string"
                        }
                    },
                    {
                        "name": "component_id",
                        "in": "query",
                        "required": false,
                        "schema": {
                            "type": "integer"
                        }
                    },
                    {
                        "name": "q",
                        "in": "query",
                        "required": false,
                        "description": "Groß-/Kleinschreibung-unabhängige Teilstring-Suche über Titel und Text in allen Sprachen.",
                        "schema": {
                            "type": "string"
                        }
                    }
                ],
                "responses": {
                    "200": {
                        "description": "Erfolg",
                        "content": {
                            "application/json": {
                                "example": {
                                    "links": {
                                        "first": "https://status.example.com/api/v1/maintenances?page=1",
                                        "last": "https://status.example.com/api/v1/maintenances?page=1",
                                        "prev": null,
                                        "next": null
                                    },
                                    "meta": {
                                        "current_page": 1,
                                        "per_page": 25,
                                        "total": 1,
                                        "last_page": 1
                                    },
                                    "data": [
                                        {
                                            "id": 12,
                                            "type": "incident",
                                            "status": "investigating",
                                            "title": {
                                                "de": "Störung im Netz",
                                                "en": "Network issue"
                                            },
                                            "body": {
                                                "de": "Wir untersuchen erhöhte Latenzen.",
                                                "en": null
                                            },
                                            "started_at": "2026-07-27T13:55:00Z",
                                            "scheduled_end_at": null,
                                            "published_at": "2026-07-27T14:00:00Z",
                                            "publish_at": "2026-07-27T14:00:00Z",
                                            "resolved_at": null,
                                            "acknowledged_at": null,
                                            "is_published": true,
                                            "is_scheduled": false,
                                            "is_resolved": false,
                                            "components": [
                                                {
                                                    "id": 3,
                                                    "impact": "degraded"
                                                }
                                            ],
                                            "public_url": "https://status.example.com/incidents/12",
                                            "updates": [],
                                            "created_at": "2026-07-27T14:00:00Z",
                                            "updated_at": "2026-07-27T14:00:00Z"
                                        }
                                    ]
                                }
                            }
                        }
                    }
                }
            },
            "post": {
                "tags": [
                    "Wartungen"
                ],
                "summary": "Wartungsfenster anlegen",
                "operationId": "postApiV1Maintenances",
                "description": "Beide Enden des Wartungsfensters sind erforderlich.",
                "x-required-permission": "incidents.manage",
                "requestBody": {
                    "required": true,
                    "content": {
                        "application/json": {
                            "schema": {
                                "type": "object",
                                "properties": {
                                    "title": {
                                        "type": "string",
                                        "description": "Locale-Objekt, z. B. {\"de\": \"Störung\", \"en\": \"Outage\"}. Bei PATCH partiell; ein explizites null löscht die Übersetzung."
                                    },
                                    "body": {
                                        "type": "string",
                                        "description": "Locale-Objekt wie bei title. Markdown erlaubt."
                                    },
                                    "status": {
                                        "$ref": "#/components/schemas/maintenances_status",
                                        "description": "Status, die ein WARTUNGSFENSTER annehmen kann (IncidentStatus::forType)."
                                    },
                                    "components": {
                                        "type": "string",
                                        "description": "Liste betroffener Komponenten als JSON-Array, je Eintrag {\"id\": 3, \"impact\": \"degraded\"}. Erlaubte Auswirkungen: degraded, partial_outage, major_outage, under_maintenance."
                                    },
                                    "started_at": {
                                        "type": "string",
                                        "description": "Wann der Vorfall tatsächlich begann; darf vor dem Datensatz liegen."
                                    },
                                    "publish": {
                                        "$ref": "#/components/schemas/maintenances_publish"
                                    },
                                    "publish_at": {
                                        "type": "string",
                                        "description": "Erforderlich bei publish=schedule; muss in der Zukunft liegen."
                                    },
                                    "notify": {
                                        "type": "boolean",
                                        "description": "Wird nur ausgewertet, wenn tatsächlich veröffentlicht wird."
                                    },
                                    "scheduled_end_at": {
                                        "type": "string"
                                    }
                                },
                                "required": [
                                    "title",
                                    "started_at",
                                    "scheduled_end_at"
                                ]
                            }
                        }
                    }
                },
                "responses": {
                    "201": {
                        "description": "Angelegt",
                        "content": {
                            "application/json": {
                                "example": {
                                    "data": {
                                        "id": 13,
                                        "type": "maintenance",
                                        "status": "scheduled",
                                        "title": {
                                            "de": "Datenbank-Wartung",
                                            "en": "Database maintenance"
                                        },
                                        "body": {
                                            "de": "Kurze Unterbrechungen möglich.",
                                            "en": null
                                        },
                                        "started_at": "2026-08-02T00:00:00Z",
                                        "scheduled_end_at": "2026-08-02T02:00:00Z",
                                        "published_at": null,
                                        "publish_at": null,
                                        "resolved_at": null,
                                        "acknowledged_at": null,
                                        "is_published": false,
                                        "is_scheduled": false,
                                        "is_resolved": false,
                                        "components": [
                                            {
                                                "id": 4,
                                                "impact": "under_maintenance"
                                            }
                                        ],
                                        "public_url": null,
                                        "updates": [],
                                        "created_at": "2026-07-27T14:00:00Z",
                                        "updated_at": "2026-07-27T14:00:00Z"
                                    }
                                }
                            }
                        }
                    },
                    "422": {
                        "description": "Validierung fehlgeschlagen",
                        "content": {
                            "application/json": {
                                "example": {
                                    "message": "The scheduled end at field must be a date after started at.",
                                    "errors": {
                                        "scheduled_end_at": [
                                            "The scheduled end at field must be a date after started at."
                                        ]
                                    }
                                }
                            }
                        }
                    }
                }
            }
        },
        "/maintenances/{incident}": {
            "get": {
                "tags": [
                    "Wartungen"
                ],
                "summary": "Wartungsfenster abrufen",
                "operationId": "getApiV1MaintenancesIncident",
                "description": "Enthält den vollständigen Verlauf.",
                "x-required-permission": "incidents.manage",
                "parameters": [
                    {
                        "name": "incident",
                        "in": "path",
                        "required": true,
                        "description": "Numerische ID des Vorfalls bzw. Wartungsfensters. Beide Collections liegen auf einem Modell — deshalb heißt der Platzhalter auch auf den Wartungs-Routen {incident}.",
                        "schema": {
                            "type": "integer"
                        }
                    }
                ],
                "responses": {
                    "200": {
                        "description": "Erfolg",
                        "content": {
                            "application/json": {
                                "example": {
                                    "data": {
                                        "id": 12,
                                        "type": "incident",
                                        "status": "investigating",
                                        "title": {
                                            "de": "Störung im Netz",
                                            "en": "Network issue"
                                        },
                                        "body": {
                                            "de": "Wir untersuchen erhöhte Latenzen.",
                                            "en": null
                                        },
                                        "started_at": "2026-07-27T13:55:00Z",
                                        "scheduled_end_at": null,
                                        "published_at": "2026-07-27T14:00:00Z",
                                        "publish_at": "2026-07-27T14:00:00Z",
                                        "resolved_at": null,
                                        "acknowledged_at": null,
                                        "is_published": true,
                                        "is_scheduled": false,
                                        "is_resolved": false,
                                        "components": [
                                            {
                                                "id": 3,
                                                "impact": "degraded"
                                            }
                                        ],
                                        "public_url": "https://status.example.com/incidents/12",
                                        "updates": [],
                                        "created_at": "2026-07-27T14:00:00Z",
                                        "updated_at": "2026-07-27T14:00:00Z"
                                    }
                                }
                            }
                        }
                    },
                    "404": {
                        "description": "Nicht gefunden",
                        "content": {
                            "application/json": {
                                "example": {
                                    "message": "Maintenance not found."
                                }
                            }
                        }
                    }
                }
            },
            "patch": {
                "tags": [
                    "Wartungen"
                ],
                "summary": "Wartungsfenster aktualisieren",
                "operationId": "patchApiV1MaintenancesIncident",
                "description": "Partiell wie bei Vorfällen. Ein verschobener Start aktiviert die „beginnt bald“-Erinnerung erneut.",
                "x-required-permission": "incidents.manage",
                "parameters": [
                    {
                        "name": "incident",
                        "in": "path",
                        "required": true,
                        "description": "Numerische ID des Vorfalls bzw. Wartungsfensters. Beide Collections liegen auf einem Modell — deshalb heißt der Platzhalter auch auf den Wartungs-Routen {incident}.",
                        "schema": {
                            "type": "integer"
                        }
                    }
                ],
                "requestBody": {
                    "required": false,
                    "content": {
                        "application/json": {
                            "schema": {
                                "type": "object",
                                "properties": {
                                    "title": {
                                        "type": "string",
                                        "description": "Locale-Objekt, z. B. {\"de\": \"Störung\", \"en\": \"Outage\"}. Bei PATCH partiell; ein explizites null löscht die Übersetzung."
                                    },
                                    "body": {
                                        "type": "string",
                                        "description": "Locale-Objekt wie bei title. Markdown erlaubt."
                                    },
                                    "status": {
                                        "$ref": "#/components/schemas/maintenances_status",
                                        "description": "Status, die ein WARTUNGSFENSTER annehmen kann (IncidentStatus::forType)."
                                    },
                                    "started_at": {
                                        "type": "string"
                                    },
                                    "components": {
                                        "type": "string",
                                        "description": "Liste betroffener Komponenten als JSON-Array, je Eintrag {\"id\": 3, \"impact\": \"degraded\"}. Erlaubte Auswirkungen: degraded, partial_outage, major_outage, under_maintenance."
                                    },
                                    "scheduled_end_at": {
                                        "type": "string"
                                    }
                                }
                            }
                        }
                    }
                },
                "responses": {
                    "200": {
                        "description": "Erfolg",
                        "content": {
                            "application/json": {
                                "example": {
                                    "data": {
                                        "id": 12,
                                        "type": "incident",
                                        "status": "investigating",
                                        "title": {
                                            "de": "Störung im Netz",
                                            "en": "Network issue"
                                        },
                                        "body": {
                                            "de": "Wir untersuchen erhöhte Latenzen.",
                                            "en": null
                                        },
                                        "started_at": "2026-07-27T13:55:00Z",
                                        "scheduled_end_at": null,
                                        "published_at": "2026-07-27T14:00:00Z",
                                        "publish_at": "2026-07-27T14:00:00Z",
                                        "resolved_at": null,
                                        "acknowledged_at": null,
                                        "is_published": true,
                                        "is_scheduled": false,
                                        "is_resolved": false,
                                        "components": [
                                            {
                                                "id": 3,
                                                "impact": "degraded"
                                            }
                                        ],
                                        "public_url": "https://status.example.com/incidents/12",
                                        "updates": [],
                                        "created_at": "2026-07-27T14:00:00Z",
                                        "updated_at": "2026-07-27T14:00:00Z"
                                    }
                                }
                            }
                        }
                    },
                    "404": {
                        "description": "Nicht gefunden",
                        "content": {
                            "application/json": {
                                "example": {
                                    "message": "Maintenance not found."
                                }
                            }
                        }
                    }
                }
            },
            "put": {
                "tags": [
                    "Wartungen"
                ],
                "summary": "Wartungsfenster aktualisieren (Alias von PATCH)",
                "operationId": "putApiV1MaintenancesIncident",
                "description": "Identisch zu PATCH, für Clients, die PUT bevorzugen.",
                "x-required-permission": "incidents.manage",
                "parameters": [
                    {
                        "name": "incident",
                        "in": "path",
                        "required": true,
                        "description": "Numerische ID des Vorfalls bzw. Wartungsfensters. Beide Collections liegen auf einem Modell — deshalb heißt der Platzhalter auch auf den Wartungs-Routen {incident}.",
                        "schema": {
                            "type": "integer"
                        }
                    }
                ],
                "requestBody": {
                    "required": false,
                    "content": {
                        "application/json": {
                            "schema": {
                                "type": "object",
                                "properties": {
                                    "title": {
                                        "type": "string",
                                        "description": "Locale-Objekt, z. B. {\"de\": \"Störung\", \"en\": \"Outage\"}. Bei PATCH partiell; ein explizites null löscht die Übersetzung."
                                    },
                                    "body": {
                                        "type": "string",
                                        "description": "Locale-Objekt wie bei title. Markdown erlaubt."
                                    },
                                    "status": {
                                        "$ref": "#/components/schemas/maintenances_status",
                                        "description": "Status, die ein WARTUNGSFENSTER annehmen kann (IncidentStatus::forType)."
                                    },
                                    "started_at": {
                                        "type": "string"
                                    },
                                    "components": {
                                        "type": "string",
                                        "description": "Liste betroffener Komponenten als JSON-Array, je Eintrag {\"id\": 3, \"impact\": \"degraded\"}. Erlaubte Auswirkungen: degraded, partial_outage, major_outage, under_maintenance."
                                    },
                                    "scheduled_end_at": {
                                        "type": "string"
                                    }
                                }
                            }
                        }
                    }
                },
                "responses": {
                    "200": {
                        "description": "Erfolg",
                        "content": {
                            "application/json": {
                                "example": {
                                    "data": {
                                        "id": 12,
                                        "type": "incident",
                                        "status": "investigating",
                                        "title": {
                                            "de": "Störung im Netz",
                                            "en": "Network issue"
                                        },
                                        "body": {
                                            "de": "Wir untersuchen erhöhte Latenzen.",
                                            "en": null
                                        },
                                        "started_at": "2026-07-27T13:55:00Z",
                                        "scheduled_end_at": null,
                                        "published_at": "2026-07-27T14:00:00Z",
                                        "publish_at": "2026-07-27T14:00:00Z",
                                        "resolved_at": null,
                                        "acknowledged_at": null,
                                        "is_published": true,
                                        "is_scheduled": false,
                                        "is_resolved": false,
                                        "components": [
                                            {
                                                "id": 3,
                                                "impact": "degraded"
                                            }
                                        ],
                                        "public_url": "https://status.example.com/incidents/12",
                                        "updates": [],
                                        "created_at": "2026-07-27T14:00:00Z",
                                        "updated_at": "2026-07-27T14:00:00Z"
                                    }
                                }
                            }
                        }
                    },
                    "404": {
                        "description": "Nicht gefunden",
                        "content": {
                            "application/json": {
                                "example": {
                                    "message": "Maintenance not found."
                                }
                            }
                        }
                    }
                }
            },
            "delete": {
                "tags": [
                    "Wartungen"
                ],
                "summary": "Wartungsfenster in den Papierkorb verschieben",
                "operationId": "deleteApiV1MaintenancesIncident",
                "description": "Papierkorb: verschwindet von der Statusseite, 30 Tage lang wiederherstellbar.",
                "x-required-permission": "incidents.manage",
                "parameters": [
                    {
                        "name": "incident",
                        "in": "path",
                        "required": true,
                        "description": "Numerische ID des Vorfalls bzw. Wartungsfensters. Beide Collections liegen auf einem Modell — deshalb heißt der Platzhalter auch auf den Wartungs-Routen {incident}.",
                        "schema": {
                            "type": "integer"
                        }
                    }
                ],
                "responses": {
                    "204": {
                        "description": "Gelöscht"
                    },
                    "404": {
                        "description": "Nicht gefunden",
                        "content": {
                            "application/json": {
                                "example": {
                                    "message": "Maintenance not found."
                                }
                            }
                        }
                    }
                }
            }
        },
        "/maintenances/{incident}/publish": {
            "post": {
                "tags": [
                    "Wartungen"
                ],
                "summary": "Veröffentlichen",
                "operationId": "postApiV1MaintenancesIncidentPublish",
                "description": "Kündigt das Fenster den Abonnenten an, sofern notify nicht false ist. Antwortet mit 409, wenn es bereits veröffentlicht ist.",
                "x-required-permission": "incidents.manage",
                "parameters": [
                    {
                        "name": "incident",
                        "in": "path",
                        "required": true,
                        "description": "Numerische ID des Vorfalls bzw. Wartungsfensters. Beide Collections liegen auf einem Modell — deshalb heißt der Platzhalter auch auf den Wartungs-Routen {incident}.",
                        "schema": {
                            "type": "integer"
                        }
                    }
                ],
                "requestBody": {
                    "required": false,
                    "content": {
                        "application/json": {
                            "schema": {
                                "type": "object",
                                "properties": {
                                    "at": {
                                        "type": "string",
                                        "description": "Datiert den öffentlichen Zeitstempel zurück."
                                    },
                                    "notify": {
                                        "type": "boolean"
                                    }
                                }
                            }
                        }
                    }
                },
                "responses": {
                    "200": {
                        "description": "Erfolg",
                        "content": {
                            "application/json": {
                                "example": {
                                    "data": {
                                        "id": 12,
                                        "type": "incident",
                                        "status": "investigating",
                                        "title": {
                                            "de": "Störung im Netz",
                                            "en": "Network issue"
                                        },
                                        "body": {
                                            "de": "Wir untersuchen erhöhte Latenzen.",
                                            "en": null
                                        },
                                        "started_at": "2026-07-27T13:55:00Z",
                                        "scheduled_end_at": null,
                                        "published_at": "2026-07-27T14:00:00Z",
                                        "publish_at": "2026-07-27T14:00:00Z",
                                        "resolved_at": null,
                                        "acknowledged_at": null,
                                        "is_published": true,
                                        "is_scheduled": false,
                                        "is_resolved": false,
                                        "components": [
                                            {
                                                "id": 3,
                                                "impact": "degraded"
                                            }
                                        ],
                                        "public_url": "https://status.example.com/incidents/12",
                                        "updates": [],
                                        "created_at": "2026-07-27T14:00:00Z",
                                        "updated_at": "2026-07-27T14:00:00Z"
                                    }
                                }
                            }
                        }
                    },
                    "409": {
                        "description": "Konflikt",
                        "content": {
                            "application/json": {
                                "example": {
                                    "message": "Maintenance is already published."
                                }
                            }
                        }
                    }
                }
            }
        },
        "/maintenances/{incident}/resolve": {
            "post": {
                "tags": [
                    "Wartungen"
                ],
                "summary": "Wartungsfenster abschließen",
                "operationId": "postApiV1MaintenancesIncidentResolve",
                "description": "Setzt den typrichtigen Endstatus: eine Wartung wird abgeschlossen, nicht behoben.",
                "x-required-permission": "incidents.manage",
                "parameters": [
                    {
                        "name": "incident",
                        "in": "path",
                        "required": true,
                        "description": "Numerische ID des Vorfalls bzw. Wartungsfensters. Beide Collections liegen auf einem Modell — deshalb heißt der Platzhalter auch auf den Wartungs-Routen {incident}.",
                        "schema": {
                            "type": "integer"
                        }
                    }
                ],
                "requestBody": {
                    "required": false,
                    "content": {
                        "application/json": {
                            "schema": {
                                "type": "object",
                                "properties": {
                                    "at": {
                                        "type": "string"
                                    }
                                }
                            }
                        }
                    }
                },
                "responses": {
                    "200": {
                        "description": "Erfolg",
                        "content": {
                            "application/json": {
                                "example": {
                                    "data": {
                                        "id": 12,
                                        "type": "incident",
                                        "status": "investigating",
                                        "title": {
                                            "de": "Störung im Netz",
                                            "en": "Network issue"
                                        },
                                        "body": {
                                            "de": "Wir untersuchen erhöhte Latenzen.",
                                            "en": null
                                        },
                                        "started_at": "2026-07-27T13:55:00Z",
                                        "scheduled_end_at": null,
                                        "published_at": "2026-07-27T14:00:00Z",
                                        "publish_at": "2026-07-27T14:00:00Z",
                                        "resolved_at": null,
                                        "acknowledged_at": null,
                                        "is_published": true,
                                        "is_scheduled": false,
                                        "is_resolved": false,
                                        "components": [
                                            {
                                                "id": 3,
                                                "impact": "degraded"
                                            }
                                        ],
                                        "public_url": "https://status.example.com/incidents/12",
                                        "updates": [],
                                        "created_at": "2026-07-27T14:00:00Z",
                                        "updated_at": "2026-07-27T14:00:00Z"
                                    }
                                }
                            }
                        }
                    },
                    "409": {
                        "description": "Konflikt",
                        "content": {
                            "application/json": {
                                "example": {
                                    "message": "Maintenance is already resolved."
                                }
                            }
                        }
                    }
                }
            }
        },
        "/maintenances/{incident}/updates": {
            "get": {
                "tags": [
                    "Wartungen"
                ],
                "summary": "Verlaufseinträge auflisten",
                "operationId": "getApiV1MaintenancesIncidentUpdates",
                "description": "Neueste zuerst.",
                "x-required-permission": "incidents.manage",
                "parameters": [
                    {
                        "name": "incident",
                        "in": "path",
                        "required": true,
                        "description": "Numerische ID des Vorfalls bzw. Wartungsfensters. Beide Collections liegen auf einem Modell — deshalb heißt der Platzhalter auch auf den Wartungs-Routen {incident}.",
                        "schema": {
                            "type": "integer"
                        }
                    },
                    {
                        "name": "page",
                        "in": "query",
                        "required": false,
                        "schema": {
                            "type": "integer"
                        }
                    },
                    {
                        "name": "per_page",
                        "in": "query",
                        "required": false,
                        "description": "Wird auf die maximale Seitengröße begrenzt statt abgewiesen.",
                        "schema": {
                            "type": "integer"
                        }
                    }
                ],
                "responses": {
                    "200": {
                        "description": "Erfolg",
                        "content": {
                            "application/json": {
                                "example": {
                                    "links": {
                                        "first": "https://status.example.com/api/v1/maintenances/{incident}/updates?page=1",
                                        "last": "https://status.example.com/api/v1/maintenances/{incident}/updates?page=1",
                                        "prev": null,
                                        "next": null
                                    },
                                    "meta": {
                                        "current_page": 1,
                                        "per_page": 25,
                                        "total": 1,
                                        "last_page": 1
                                    },
                                    "data": [
                                        {
                                            "id": 41,
                                            "incident_id": 12,
                                            "status": "monitoring",
                                            "body": {
                                                "de": "Ursache gefunden, wir beobachten.",
                                                "en": "Cause identified, monitoring."
                                            },
                                            "posted_at": "2026-07-27T14:20:00Z",
                                            "created_at": "2026-07-27T14:20:00Z"
                                        }
                                    ]
                                }
                            }
                        }
                    }
                }
            },
            "post": {
                "tags": [
                    "Wartungen"
                ],
                "summary": "Verlaufseintrag veröffentlichen",
                "operationId": "postApiV1MaintenancesIncidentUpdates",
                "description": "Wie bei einem Vorfall; ein terminaler Status schließt das Fenster ab.",
                "x-required-permission": "incidents.manage",
                "parameters": [
                    {
                        "name": "incident",
                        "in": "path",
                        "required": true,
                        "description": "Numerische ID des Vorfalls bzw. Wartungsfensters. Beide Collections liegen auf einem Modell — deshalb heißt der Platzhalter auch auf den Wartungs-Routen {incident}.",
                        "schema": {
                            "type": "integer"
                        }
                    }
                ],
                "requestBody": {
                    "required": true,
                    "content": {
                        "application/json": {
                            "schema": {
                                "type": "object",
                                "properties": {
                                    "status": {
                                        "$ref": "#/components/schemas/maintenance_updates_status",
                                        "description": "Status, die ein WARTUNGSFENSTER annehmen kann (IncidentStatus::forType)."
                                    },
                                    "body": {
                                        "type": "string",
                                        "description": "Locale-Objekt wie bei title. Markdown erlaubt."
                                    },
                                    "components": {
                                        "type": "string",
                                        "description": "Liste betroffener Komponenten als JSON-Array, je Eintrag {\"id\": 3, \"impact\": \"degraded\"}. Erlaubte Auswirkungen: degraded, partial_outage, major_outage, under_maintenance."
                                    },
                                    "posted_at": {
                                        "type": "string"
                                    },
                                    "notify": {
                                        "type": "boolean"
                                    }
                                },
                                "required": [
                                    "status",
                                    "body"
                                ]
                            }
                        }
                    }
                },
                "responses": {
                    "201": {
                        "description": "Angelegt",
                        "content": {
                            "application/json": {
                                "example": {
                                    "data": {
                                        "id": 42,
                                        "incident_id": 13,
                                        "status": "in_progress",
                                        "body": {
                                            "de": "Wartung hat begonnen.",
                                            "en": "Maintenance has started."
                                        },
                                        "posted_at": "2026-08-02T00:00:00Z",
                                        "created_at": "2026-08-02T00:00:00Z"
                                    }
                                }
                            }
                        }
                    },
                    "422": {
                        "description": "Validierung fehlgeschlagen",
                        "content": {
                            "application/json": {
                                "example": {
                                    "message": "The body field must be filled in at least one language (de, en).",
                                    "errors": {
                                        "body": [
                                            "The body field must be filled in at least one language (de, en)."
                                        ]
                                    }
                                }
                            }
                        }
                    }
                }
            }
        },
        "/announcements": {
            "get": {
                "tags": [
                    "Ankündigungen"
                ],
                "summary": "Ankündigungen auflisten",
                "operationId": "getApiV1Announcements",
                "description": "Vergangene, laufende und geplante Banner. Für die gerade sichtbaren den active-Filter nutzen.",
                "x-required-permission": "announcements.manage",
                "parameters": [
                    {
                        "name": "page",
                        "in": "query",
                        "required": false,
                        "schema": {
                            "type": "integer"
                        }
                    },
                    {
                        "name": "per_page",
                        "in": "query",
                        "required": false,
                        "description": "Wird auf die maximale Seitengröße begrenzt statt abgewiesen.",
                        "schema": {
                            "type": "integer"
                        }
                    },
                    {
                        "name": "active",
                        "in": "query",
                        "required": false,
                        "description": "Nur Banner, die gerade angezeigt werden.",
                        "schema": {
                            "type": "boolean"
                        }
                    },
                    {
                        "name": "level",
                        "in": "query",
                        "required": false,
                        "schema": {
                            "$ref": "#/components/schemas/announcements_level"
                        }
                    }
                ],
                "responses": {
                    "200": {
                        "description": "Erfolg",
                        "content": {
                            "application/json": {
                                "example": {
                                    "links": {
                                        "first": "https://status.example.com/api/v1/announcements?page=1",
                                        "last": "https://status.example.com/api/v1/announcements?page=1",
                                        "prev": null,
                                        "next": null
                                    },
                                    "meta": {
                                        "current_page": 1,
                                        "per_page": 25,
                                        "total": 1,
                                        "last_page": 1
                                    },
                                    "data": [
                                        {
                                            "id": "01kyhjx7hxggqfaekf2b5sy61x",
                                            "title": {
                                                "de": "Wartungsfenster am Sonntag",
                                                "en": "Maintenance window on Sunday"
                                            },
                                            "body": {
                                                "de": "Zwischen 02:00 und 04:00 Uhr kann es zu kurzen Unterbrechungen kommen.",
                                                "en": null
                                            },
                                            "level": "warning",
                                            "dismissible": true,
                                            "starts_at": "2026-07-24T00:00:00Z",
                                            "ends_at": "2026-07-28T00:00:00Z",
                                            "is_active": true,
                                            "created_at": "2026-07-23T10:00:00Z",
                                            "updated_at": "2026-07-23T10:00:00Z"
                                        }
                                    ]
                                }
                            }
                        }
                    }
                }
            },
            "post": {
                "tags": [
                    "Ankündigungen"
                ],
                "summary": "Ankündigung anlegen",
                "operationId": "postApiV1Announcements",
                "description": "Beide Grenzen sind optional: kein Start bedeutet „ab sofort“, kein Ende „bis zur Entfernung“.",
                "x-required-permission": "announcements.manage",
                "requestBody": {
                    "required": true,
                    "content": {
                        "application/json": {
                            "schema": {
                                "type": "object",
                                "properties": {
                                    "title": {
                                        "type": "string",
                                        "description": "Locale-Objekt, z. B. {\"de\": \"Störung\", \"en\": \"Outage\"}. Bei PATCH partiell; ein explizites null löscht die Übersetzung."
                                    },
                                    "body": {
                                        "type": "string",
                                        "description": "Locale-Objekt wie bei title. Markdown erlaubt."
                                    },
                                    "level": {
                                        "$ref": "#/components/schemas/announcements_level"
                                    },
                                    "dismissible": {
                                        "type": "boolean"
                                    },
                                    "starts_at": {
                                        "type": "string",
                                        "description": "Ohne Angabe unbegrenzt."
                                    },
                                    "ends_at": {
                                        "type": "string",
                                        "description": "Exklusiv. Ohne Angabe unbegrenzt."
                                    }
                                },
                                "required": [
                                    "title"
                                ]
                            }
                        }
                    }
                },
                "responses": {
                    "201": {
                        "description": "Angelegt",
                        "content": {
                            "application/json": {
                                "example": {
                                    "data": {
                                        "id": "01kyhjx7hxggqfaekf2b5sy61x",
                                        "title": {
                                            "de": "Wartungsfenster am Sonntag",
                                            "en": "Maintenance window on Sunday"
                                        },
                                        "body": {
                                            "de": "Zwischen 02:00 und 04:00 Uhr kann es zu kurzen Unterbrechungen kommen.",
                                            "en": null
                                        },
                                        "level": "warning",
                                        "dismissible": true,
                                        "starts_at": null,
                                        "ends_at": "2026-08-03T00:00:00Z",
                                        "is_active": true,
                                        "created_at": "2026-07-27T14:00:00Z",
                                        "updated_at": "2026-07-27T14:00:00Z"
                                    }
                                }
                            }
                        }
                    },
                    "422": {
                        "description": "Validierung fehlgeschlagen",
                        "content": {
                            "application/json": {
                                "example": {
                                    "message": "The title field must be filled in at least one language (de, en).",
                                    "errors": {
                                        "title": [
                                            "The title field must be filled in at least one language (de, en)."
                                        ]
                                    }
                                }
                            }
                        }
                    }
                }
            }
        },
        "/announcements/{announcement}": {
            "get": {
                "tags": [
                    "Ankündigungen"
                ],
                "summary": "Ankündigung abrufen",
                "operationId": "getApiV1AnnouncementsAnnouncement",
                "description": "is_active beantwortet, ob das Banner gerade angezeigt wird.",
                "x-required-permission": "announcements.manage",
                "parameters": [
                    {
                        "name": "announcement",
                        "in": "path",
                        "required": true,
                        "description": "ULID.",
                        "schema": {
                            "type": "string"
                        }
                    }
                ],
                "responses": {
                    "200": {
                        "description": "Erfolg",
                        "content": {
                            "application/json": {
                                "example": {
                                    "data": {
                                        "id": "01kyhjx7hxggqfaekf2b5sy61x",
                                        "title": {
                                            "de": "Wartungsfenster am Sonntag",
                                            "en": "Maintenance window on Sunday"
                                        },
                                        "body": {
                                            "de": "Zwischen 02:00 und 04:00 Uhr kann es zu kurzen Unterbrechungen kommen.",
                                            "en": null
                                        },
                                        "level": "warning",
                                        "dismissible": true,
                                        "starts_at": "2026-07-24T00:00:00Z",
                                        "ends_at": "2026-07-28T00:00:00Z",
                                        "is_active": true,
                                        "created_at": "2026-07-23T10:00:00Z",
                                        "updated_at": "2026-07-23T10:00:00Z"
                                    }
                                }
                            }
                        }
                    },
                    "404": {
                        "description": "Nicht gefunden",
                        "content": {
                            "application/json": {
                                "example": {
                                    "message": "Announcement not found."
                                }
                            }
                        }
                    }
                }
            },
            "patch": {
                "tags": [
                    "Ankündigungen"
                ],
                "summary": "Ankündigung aktualisieren",
                "operationId": "patchApiV1AnnouncementsAnnouncement",
                "description": "Partiell. Ein ends_at in der Vergangenheit beendet ein laufendes Banner sofort.",
                "x-required-permission": "announcements.manage",
                "parameters": [
                    {
                        "name": "announcement",
                        "in": "path",
                        "required": true,
                        "description": "ULID.",
                        "schema": {
                            "type": "string"
                        }
                    }
                ],
                "requestBody": {
                    "required": true,
                    "content": {
                        "application/json": {
                            "schema": {
                                "type": "object",
                                "properties": {
                                    "title": {
                                        "type": "string",
                                        "description": "Locale-Objekt, z. B. {\"de\": \"Störung\", \"en\": \"Outage\"}. Bei PATCH partiell; ein explizites null löscht die Übersetzung."
                                    },
                                    "body": {
                                        "type": "string",
                                        "description": "Locale-Objekt wie bei title. Markdown erlaubt."
                                    },
                                    "level": {
                                        "$ref": "#/components/schemas/announcements_level"
                                    },
                                    "dismissible": {
                                        "type": "boolean"
                                    },
                                    "starts_at": {
                                        "type": "string",
                                        "description": "Ohne Angabe unbegrenzt."
                                    },
                                    "ends_at": {
                                        "type": "string",
                                        "description": "Exklusiv. Ohne Angabe unbegrenzt."
                                    }
                                },
                                "required": [
                                    "title"
                                ]
                            }
                        }
                    }
                },
                "responses": {
                    "200": {
                        "description": "Erfolg",
                        "content": {
                            "application/json": {
                                "example": {
                                    "data": {
                                        "id": "01kyhjx7hxggqfaekf2b5sy61x",
                                        "title": {
                                            "de": "Wartungsfenster am Sonntag",
                                            "en": "Maintenance window on Sunday"
                                        },
                                        "body": {
                                            "de": "Zwischen 02:00 und 04:00 Uhr kann es zu kurzen Unterbrechungen kommen.",
                                            "en": null
                                        },
                                        "level": "warning",
                                        "dismissible": true,
                                        "starts_at": "2026-07-24T00:00:00Z",
                                        "ends_at": "2026-07-28T00:00:00Z",
                                        "is_active": true,
                                        "created_at": "2026-07-23T10:00:00Z",
                                        "updated_at": "2026-07-23T10:00:00Z"
                                    }
                                }
                            }
                        }
                    },
                    "404": {
                        "description": "Nicht gefunden",
                        "content": {
                            "application/json": {
                                "example": {
                                    "message": "Announcement not found."
                                }
                            }
                        }
                    }
                }
            },
            "put": {
                "tags": [
                    "Ankündigungen"
                ],
                "summary": "Ankündigung aktualisieren (Alias von PATCH)",
                "operationId": "putApiV1AnnouncementsAnnouncement",
                "description": "Identisch zu PATCH, für Clients, die PUT bevorzugen.",
                "x-required-permission": "announcements.manage",
                "parameters": [
                    {
                        "name": "announcement",
                        "in": "path",
                        "required": true,
                        "description": "ULID.",
                        "schema": {
                            "type": "string"
                        }
                    }
                ],
                "requestBody": {
                    "required": true,
                    "content": {
                        "application/json": {
                            "schema": {
                                "type": "object",
                                "properties": {
                                    "title": {
                                        "type": "string",
                                        "description": "Locale-Objekt, z. B. {\"de\": \"Störung\", \"en\": \"Outage\"}. Bei PATCH partiell; ein explizites null löscht die Übersetzung."
                                    },
                                    "body": {
                                        "type": "string",
                                        "description": "Locale-Objekt wie bei title. Markdown erlaubt."
                                    },
                                    "level": {
                                        "$ref": "#/components/schemas/announcements_level"
                                    },
                                    "dismissible": {
                                        "type": "boolean"
                                    },
                                    "starts_at": {
                                        "type": "string",
                                        "description": "Ohne Angabe unbegrenzt."
                                    },
                                    "ends_at": {
                                        "type": "string",
                                        "description": "Exklusiv. Ohne Angabe unbegrenzt."
                                    }
                                },
                                "required": [
                                    "title"
                                ]
                            }
                        }
                    }
                },
                "responses": {
                    "200": {
                        "description": "Erfolg",
                        "content": {
                            "application/json": {
                                "example": {
                                    "data": {
                                        "id": "01kyhjx7hxggqfaekf2b5sy61x",
                                        "title": {
                                            "de": "Wartungsfenster am Sonntag",
                                            "en": "Maintenance window on Sunday"
                                        },
                                        "body": {
                                            "de": "Zwischen 02:00 und 04:00 Uhr kann es zu kurzen Unterbrechungen kommen.",
                                            "en": null
                                        },
                                        "level": "warning",
                                        "dismissible": true,
                                        "starts_at": "2026-07-24T00:00:00Z",
                                        "ends_at": "2026-07-28T00:00:00Z",
                                        "is_active": true,
                                        "created_at": "2026-07-23T10:00:00Z",
                                        "updated_at": "2026-07-23T10:00:00Z"
                                    }
                                }
                            }
                        }
                    },
                    "404": {
                        "description": "Nicht gefunden",
                        "content": {
                            "application/json": {
                                "example": {
                                    "message": "Announcement not found."
                                }
                            }
                        }
                    }
                }
            },
            "delete": {
                "tags": [
                    "Ankündigungen"
                ],
                "summary": "Ankündigung löschen",
                "operationId": "deleteApiV1AnnouncementsAnnouncement",
                "description": "Endgültig — Ankündigungen haben keinen Papierkorb.",
                "x-required-permission": "announcements.manage",
                "parameters": [
                    {
                        "name": "announcement",
                        "in": "path",
                        "required": true,
                        "description": "ULID.",
                        "schema": {
                            "type": "string"
                        }
                    }
                ],
                "responses": {
                    "204": {
                        "description": "Gelöscht"
                    },
                    "404": {
                        "description": "Nicht gefunden",
                        "content": {
                            "application/json": {
                                "example": {
                                    "message": "Announcement not found."
                                }
                            }
                        }
                    }
                }
            }
        },
        "/subscribers": {
            "get": {
                "tags": [
                    "Abonnenten"
                ],
                "summary": "Abonnenten auflisten",
                "operationId": "getApiV1Subscribers",
                "description": "Adressen sind immer maskiert. Für die gezielte Suche den E-Mail-Filter nutzen: Er löst über den gespeicherten Hash auf und gibt nie eine Adresse zurück.",
                "x-required-permission": "subscribers.manage",
                "parameters": [
                    {
                        "name": "page",
                        "in": "query",
                        "required": false,
                        "schema": {
                            "type": "integer"
                        }
                    },
                    {
                        "name": "per_page",
                        "in": "query",
                        "required": false,
                        "description": "Wird auf die maximale Seitengröße begrenzt statt abgewiesen.",
                        "schema": {
                            "type": "integer"
                        }
                    },
                    {
                        "name": "email",
                        "in": "query",
                        "required": false,
                        "description": "Exakte Adresse, nach der gesucht wird.",
                        "schema": {
                            "type": "string"
                        }
                    },
                    {
                        "name": "confirmed",
                        "in": "query",
                        "required": false,
                        "schema": {
                            "type": "boolean"
                        }
                    }
                ],
                "responses": {
                    "200": {
                        "description": "Erfolg",
                        "content": {
                            "application/json": {
                                "example": {
                                    "links": {
                                        "first": "https://status.example.com/api/v1/subscribers?page=1",
                                        "last": "https://status.example.com/api/v1/subscribers?page=1",
                                        "prev": null,
                                        "next": null
                                    },
                                    "meta": {
                                        "current_page": 1,
                                        "per_page": 25,
                                        "total": 1,
                                        "last_page": 1
                                    },
                                    "data": [
                                        {
                                            "id": 87,
                                            "email_masked": "an***@example.com",
                                            "locale": "de",
                                            "channel": "email",
                                            "confirmed": true,
                                            "confirmed_at": "2026-06-02T09:31:00Z",
                                            "subscribe_all_components": false,
                                            "component_ids": [
                                                3,
                                                4
                                            ],
                                            "created_at": "2026-06-02T09:28:00Z"
                                        }
                                    ]
                                }
                            }
                        }
                    }
                }
            },
            "post": {
                "tags": [
                    "Abonnenten"
                ],
                "summary": "Abonnent hinzufügen",
                "operationId": "postApiV1Subscribers",
                "description": "Der Migrationsweg, um eine bestehende Liste nach FireStatus zu übernehmen. Legt einen BESTÄTIGTEN Eintrag ohne Double-Opt-in an und verlangt deshalb eine ausdrückliche Einwilligungs-Bestätigung. Für einen Eintrag MIT Double-Opt-in das öffentliche Abonnement-Formular nutzen.",
                "x-required-permission": "subscribers.manage",
                "requestBody": {
                    "required": true,
                    "content": {
                        "application/json": {
                            "schema": {
                                "type": "object",
                                "properties": {
                                    "email": {
                                        "type": "string"
                                    },
                                    "locale": {
                                        "type": "string"
                                    },
                                    "subscribe_all_components": {
                                        "type": "boolean"
                                    },
                                    "component_ids": {
                                        "type": "string",
                                        "description": "JSON-Array von Komponenten-IDs."
                                    },
                                    "acknowledge_consent": {
                                        "type": "boolean",
                                        "description": "Muss true sein. Bestätigt, dass die Einwilligung dieser Person vorliegt; der Eintrag wird ohne Double-Opt-in als bestätigt angelegt."
                                    }
                                },
                                "required": [
                                    "email",
                                    "acknowledge_consent"
                                ]
                            }
                        }
                    }
                },
                "responses": {
                    "201": {
                        "description": "Angelegt",
                        "content": {
                            "application/json": {
                                "example": {
                                    "data": {
                                        "id": 88,
                                        "email_masked": "an***@example.com",
                                        "locale": "de",
                                        "channel": "email",
                                        "confirmed": true,
                                        "confirmed_at": "2026-07-27T14:00:00Z",
                                        "subscribe_all_components": false,
                                        "component_ids": [
                                            3,
                                            4
                                        ],
                                        "created_at": "2026-07-27T14:00:00Z"
                                    }
                                }
                            }
                        }
                    },
                    "409": {
                        "description": "Konflikt",
                        "content": {
                            "application/json": {
                                "example": {
                                    "message": "This address is already subscribed."
                                }
                            }
                        }
                    },
                    "422": {
                        "description": "Validierung fehlgeschlagen",
                        "content": {
                            "application/json": {
                                "example": {
                                    "message": "Set acknowledge_consent to true to confirm you have this person's consent. This endpoint creates a confirmed subscriber without double opt-in.",
                                    "errors": {
                                        "acknowledge_consent": [
                                            "Set acknowledge_consent to true to confirm you have this person's consent. This endpoint creates a confirmed subscriber without double opt-in."
                                        ]
                                    }
                                }
                            }
                        }
                    }
                }
            }
        },
        "/subscribers/{subscriber}": {
            "delete": {
                "tags": [
                    "Abonnenten"
                ],
                "summary": "Abonnent entfernen",
                "operationId": "deleteApiV1SubscribersSubscriber",
                "description": "Der Löschweg nach Art. 17 DSGVO. Endgültig, und der Einwilligungsnachweis geht mit. Es gibt keinen Änderungs-Endpunkt: Ein Adresswechsel ist ein neues Abonnement, und Sprache sowie Umfang ändert die Person selbst über ihren Self-Service-Link.",
                "x-required-permission": "subscribers.manage",
                "parameters": [
                    {
                        "name": "subscriber",
                        "in": "path",
                        "required": true,
                        "schema": {
                            "type": "integer"
                        }
                    }
                ],
                "responses": {
                    "204": {
                        "description": "Gelöscht"
                    },
                    "404": {
                        "description": "Nicht gefunden",
                        "content": {
                            "application/json": {
                                "example": {
                                    "message": "Subscriber not found."
                                }
                            }
                        }
                    }
                }
            }
        },
        "/analytics/page-views": {
            "get": {
                "tags": [
                    "Zugriffe"
                ],
                "summary": "Seitenaufrufe",
                "operationId": "getApiV1AnalyticsPageViews",
                "description": "Vorab aggregierte Tageswerte der öffentlichen Flächen. Nichts davon identifiziert Besucher: Es werden weder IP noch User-Agent gespeichert, und der Eindeutigkeits-Fingerabdruck wird mit einem täglich rotierenden Schlüssel gesalzen.",
                "x-required-permission": "analytics.view",
                "parameters": [
                    {
                        "name": "days",
                        "in": "query",
                        "required": false,
                        "description": "Zeitfenster in Tagen, heute eingeschlossen.",
                        "schema": {
                            "type": "integer"
                        }
                    }
                ],
                "responses": {
                    "200": {
                        "description": "Erfolg",
                        "content": {
                            "application/json": {
                                "example": {
                                    "data": {
                                        "from": "2026-06-28",
                                        "to": "2026-07-27",
                                        "totals": {
                                            "views": 2068,
                                            "unique_visitors": 1204
                                        },
                                        "by_day": [
                                            {
                                                "date": "2026-07-26",
                                                "views": 61,
                                                "unique_visitors": 38
                                            },
                                            {
                                                "date": "2026-07-27",
                                                "views": 1840,
                                                "unique_visitors": 1102
                                            }
                                        ],
                                        "by_surface": {
                                            "public.status": 1840,
                                            "public.archive": 120,
                                            "public.component": 96,
                                            "public.postmortem": 12
                                        },
                                        "generated_at": "2026-07-27T14:00:00Z"
                                    }
                                }
                            }
                        }
                    },
                    "422": {
                        "description": "Validierung fehlgeschlagen",
                        "content": {
                            "application/json": {
                                "example": {
                                    "message": "The days field must not be greater than 90.",
                                    "errors": {
                                        "days": [
                                            "The days field must not be greater than 90."
                                        ]
                                    }
                                }
                            }
                        }
                    }
                }
            }
        }
    },
    "components": {
        "securitySchemes": {
            "bearerAuth": {
                "type": "http",
                "scheme": "bearer",
                "bearerFormat": "FireStatus API key (fs_…)",
                "description": "A FireStatus tenant API key (prefix `fs_`), sent as `Authorization: Bearer fs_…`.\n\nThe key is minted by a tenant admin on the Integrations page of that tenant's own status-page host (`https://{status_page_host}/admin/integrations`) and is shown once at creation.\n\nThe key belongs to the tenant, not to a person, and its abilities are hard-capped at the Manager role — incidents, announcements, components, subscribers and analytics. User management, tenant settings, branding and domains are structurally out of reach for a key; there is no per-key ability picker.\n\nThe key is also bound to its tenant: it is only accepted on that tenant's own status-page host. Replaying it against another status page is refused with 403."
            }
        },
        "schemas": {
            "announcements_level": {
                "type": "string",
                "enum": [
                    "info",
                    "warning",
                    "success"
                ]
            },
            "incident_updates_status": {
                "type": "string",
                "enum": [
                    "investigating",
                    "identified",
                    "monitoring",
                    "resolved"
                ]
            },
            "incidents_publish": {
                "type": "string",
                "enum": [
                    "now",
                    "schedule",
                    "draft"
                ]
            },
            "incidents_state": {
                "type": "string",
                "enum": [
                    "draft",
                    "scheduled",
                    "published"
                ]
            },
            "incidents_status": {
                "type": "string",
                "enum": [
                    "investigating",
                    "identified",
                    "monitoring",
                    "resolved"
                ]
            },
            "maintenance_updates_status": {
                "type": "string",
                "enum": [
                    "scheduled",
                    "in_progress",
                    "completed"
                ]
            },
            "maintenances_publish": {
                "type": "string",
                "enum": [
                    "now",
                    "schedule",
                    "draft"
                ]
            },
            "maintenances_state": {
                "type": "string",
                "enum": [
                    "draft",
                    "scheduled",
                    "published"
                ]
            },
            "maintenances_status": {
                "type": "string",
                "enum": [
                    "scheduled",
                    "in_progress",
                    "completed"
                ]
            },
            "updates_status": {
                "type": "string",
                "enum": [
                    "investigating",
                    "identified",
                    "monitoring",
                    "resolved",
                    "scheduled",
                    "in_progress",
                    "completed"
                ]
            }
        }
    }
}