---
title: "Publish Postmortem"
description: "Publishes the postmortem of a resolved incident on its status pages, optionally with one notification to their subscribers."
---

`POST /api/incidents/:id/postmortem/publish`

Publishes the postmortem of an incident. It then appears under the incident on every status page the incident is shown on, in every layout, as an expandable section. This is what "Publish" in the postmortem card of the status pages module and the MCP tool `publish_postmortem` do.

- Only a **resolved** incident can get a published postmortem: resolved on the status pages (`publicStatus`, see [Get Incident Details](/api/monitoring/get-incident-details)). Otherwise the call answers `409 postmortemIncidentNotResolved`.
- With `body` the text is saved first, in the same call. Without it the text saved with [Save Postmortem](/api/monitoring/save-postmortem) is published; without a saved text the call answers `404 postmortemNotFound`.
- With `notifySubscribers: true` the subscribers of those pages get one notification `postmortem_published` (email, webhook, Slack, Teams), after the page's subscription delay. If the postmortem is unpublished before that, nothing is sent.
- **Repeats:** an already published postmortem stays published and answers `200 OK`. A `body` replaces its text; no second notification is sent.

## Authentication

Requires role `admin` or `editor` within the incident's customer scope. An incident without a customer needs an organization-wide role or token; for any other organization it answers `404 incidentNotFound`. `readonly` gets `403 forbidden`.

- Header: `Authorization: Bearer <token>`

## Path Parameters

- `id` (required): numeric id or `publicId` (UUID) of the incident.

## Request Body

Optional; an empty body publishes the saved text without notification.

| Field | Type | Required | Description |
|-------|------|----------|-------------|
| `body` | string | no | Markdown, 1 to 50,000 characters. Saved before publishing. |
| `notifySubscribers` | boolean | no | Default `false`. `true` notifies the subscribers of the pages once. |

Unknown fields are rejected with `400 invalidRequestBody`.

## Example (cURL)

```bash
curl -X POST "$BASE_URL/api/incidents/5121/postmortem/publish" \
  -H "Authorization: Bearer $TOKEN" \
  -H "Content-Type: application/json" \
  -d '{ "notifySubscribers": true }'
```

## Response

`200 OK`

```json
{
  "incidentId": 5121,
  "incidentPublicId": "8a3c1f6e-2b7d-4e59-9c1a-5d2e7f0b4c33",
  "body": "## Cause\nA database node ran out of disk space.",
  "publishedAt": "2026-10-28T14:05:40.000Z",
  "updatedAt": "2026-10-28T14:02:11.000Z"
}
```

On the public status page ([Get Public Status Page](/api/status-pages/get-public-status-page)) the incident then carries `postmortem: { body, publishedAt }`. To take it down again, use [Unpublish Postmortem](/api/monitoring/unpublish-postmortem).

## Common Errors

- `400 Bad Request` (`invalidRequestBody`) when `body` is empty or longer than 50,000 characters, a field has the wrong type, or an unknown field is sent
- `401 Unauthorized` when not authenticated
- `403 Forbidden` (`forbidden`) when your role or customer scope does not allow it
- `404 Not Found` (`incidentNotFound`) when the incident does not exist in your organization
- `404 Not Found` (`postmortemNotFound`) when no text was saved and no `body` was sent
- `409 Conflict` (`postmortemIncidentNotResolved`) when the incident is not resolved on the status pages
