> ## Documentation Index
> Fetch the complete documentation index at: https://docs.incident.io/llms.txt
> Use this file to discover all available pages before exploring further.

# Importing historical incidents

> Bring your incident history into incident.io using the API, so your reporting and insights cover more than just the incidents you declare from now on.

If you're moving to incident.io from another tool, you probably have a history of incidents you'd like to keep: for reporting, for insights, and so that the record of what happened lives in one place. This guide covers importing that history through the API.

If you're coming from Blameless, FireHydrant, or ServiceNow, we have importer tools that can do this for you. They aren't self-serve yet, so [contact support](mailto:support@incident.io) and we'll run the import with you.

This is about historical data only. If you're migrating your live setup (schedules, escalation policies, alert sources) see the guides for [PagerDuty](/getting-started/migrate-from-pagerduty) and [Opsgenie](/getting-started/migrate-from-opsgenie).

## Before you start

* **Decide what to bring over.** For each incident you'll want a name, a severity, and the timestamps that matter to your reporting (when it was reported, when it was resolved). Summaries and custom fields are worth mapping too. Skip anything that doesn't map cleanly. A sparse but accurate record beats a complete but messy one.
* **Cleaning up a bad import is tedious.** There's no delete via the API. If an import goes wrong, you can select the incidents in the dashboard and mark them as test incidents to get them out of your reporting, but for a large batch that's a chore you'd rather avoid. Import a small batch first, maybe five incidents, and check them in the dashboard before running the rest.
* **Check your channel creation settings.** Depending on your settings, each imported incident can create a Slack or Microsoft Teams channel. Five hundred imported incidents creating five hundred empty channels is not what anyone wants, and channel creation also determines which rate limit applies to you (see below). You can configure this per incident mode under channel creation settings in the dashboard.
* **Talk to us about rate limits.** Incident creation is deliberately rate limited to protect your account from runaway automations, which matters when you're intentionally creating thousands of records. [Contact support](mailto:support@incident.io) before a large import and we can temporarily raise the limits for your key.

## Create the incidents

Use the [create incident endpoint](/api-reference/incidents-v2/create) with `mode` set to `retrospective`:

```bash theme={null}
curl --request POST https://api.incident.io/v2/incidents \
  --header 'Authorization: Bearer <YOUR_API_KEY>' \
  --header 'Content-Type: application/json' \
  --data '{
    "idempotency_key": "import-jira-4521",
    "visibility": "public",
    "mode": "retrospective",
    "name": "Database connection pool exhausted",
    "summary": "Connection pool hit its limit during the evening peak.",
    "severity_id": "01FCNDV6P870EA6S7TK1DSYDG0",
    "incident_timestamp_values": [
      {
        "incident_timestamp_id": "01FCNDV6P870EA6S7TK1DSYDG0",
        "value": "2024-03-02T18:22:00Z"
      }
    ]
  }'
```

A few things to know about the payload:

* **`idempotency_key`** is required, and it's your friend during an import: retrying a failed request with the same key won't create a duplicate. Use something stable from your source system, like the original ticket reference.
* **`incident_timestamp_values`** is how you record when the incident actually happened. List your organization's timestamps with the [incident timestamps endpoint](/api-reference/incident-timestamps-v2/list) to find the IDs, then set the values that matter for your reporting. Without these, the incident is dated by when you imported it.
* **`custom_field_entries`** works the same as for any other incident, so you can carry over things like affected services or teams.

There are also a few options specific to retrospective incidents, set under `retrospective_incident_options`:

* **`slack_channel_id`** attaches an existing Slack channel to the incident instead of creating a new one. Useful if the original incident was run in Slack and the channel still exists.
* **`postmortem_document_url`** links an existing post-mortem document to the incident.
* **`external_id`** sets the incident number to match your previous system, so links and references keep making sense. This option needs enabling for your organization, so [contact support](mailto:support@incident.io) first if you'd like to use it.

### What retrospective mode does

Retrospective incidents are built for exactly this use case, and behave differently from incidents you declare live:

* They start in your closed status, rather than going through triage or active response.
* They skip the post-incident flow, so no post-incident tasks are created for them.
* Workflows don't run on them by default.

The result is an incident that exists in your history and your reporting without paging anyone or generating follow-up work.

## Pace the import

An API key can create 10 incidents per hour where a Slack or Microsoft Teams channel is created, and 300 per hour otherwise. Basically everyone hits this during an import, so it's worth understanding why the limits are shaped this way:

* Creating channels draws on Slack's own rate limits, which are aggressive. An import that creates hundreds of channels can exhaust that allowance and stop channels being created for *real* incidents happening at the same time, so incidents that create channels are limited hard.
* The broader creation limit protects your account from runaway automations. A misconfigured script creating incidents in a loop can do a lot of damage. A limit that a human import finds slow is one that stops a machine doing real harm.

This is why the channel creation settings above matter: an import that doesn't create channels runs at 300 per hour instead of 10. When you hit the limit, the API responds with `429 Too Many Requests`:

```json theme={null}
{
  "type": "rate_limit_reached",
  "status": 429,
  "errors": [
    {
      "code": "rate_limit_reached",
      "message": "You cannot create more than 10 incidents per hour. Please try again later."
    }
  ]
}
```

The limit counts incidents created over the last hour, so there's no fixed reset time: write your import script to run sequentially, and on a 429 wait a few minutes before retrying (your `idempotency_key` makes retries safe). You may also hit the general request limit, which returns `type: "too_many_requests"` with a `retry_after` timestamp you can wait on directly.

Do the arithmetic before you start: at the default limits, a thousand incidents is either a long afternoon or several days depending on your channel settings, which is why we recommend [contacting support](mailto:support@incident.io) for a temporary raise first.

## Check the result

List your imported incidents by filtering on mode:

```bash theme={null}
curl --request GET 'https://api.incident.io/v2/incidents?mode%5Bone_of%5D=retrospective&page_size=25' \
  --header 'Authorization: Bearer <YOUR_API_KEY>'
```

Spot-check a few in the dashboard: the timestamps should reflect when the incident happened, severities and custom fields should be populated, and they should appear in your [Insights](https://app.incident.io/~/insights) with their historical dates.

## Import the rest of your history

Incidents are usually the biggest piece, but not the only one:

* **Post-mortem documents**: import existing write-ups as post-mortems with the [import endpoint](/api-reference/incidents-v2/import-postmortem-document), which accepts markdown.
* **Status page history**: recreate your public status page timeline with [retrospective status page incidents](/api-reference/status-page-incidents-v2/create-retrospective).
* **Catalog**: for services, teams, and other catalog data, use the [catalog importer](/catalog/importing-data).
* **Alerts**: there's currently no way to import historical alerts.

If you get stuck or your import is unusually large, [get in touch](mailto:support@incident.io) and we'll help you plan it.
