From a3f1967bc82ca529bc5325e28c9645586d9024d2 Mon Sep 17 00:00:00 2001 From: Shivam Sharma <192242476+ShivamSharma43@users.noreply.github.com> Date: Wed, 11 Nov 2026 18:07:15 +0530 Subject: [PATCH] fix(incidentio): map the status categories the API returns mapStatusCategory matched triage, declared, active, paused, post-incident, closed and resolved. The incident.io API returns triage, declined, merged, canceled, live, learning, closed and paused; active and post-incident are only the app's names for live and learning. Declined, merged and canceled incidents fell through to IN_PROGRESS and stayed open, and live and learning logged an unknown category warning. Map triage, live, learning and paused to IN_PROGRESS and closed, declined, merged and canceled to DONE, and use live in the e2e raw fixture. Fixes #9374 Generated-by: Claude Code (Claude Opus 5.5) Co-Authored-By: Claude Opus 5.5 Signed-off-by: Shivam Sharma <192242476+ShivamSharma43@users.noreply.github.com> --- .../e2e/raw_tables/_raw_incidentio_incidents.csv | 2 +- .../plugins/incidentio/tasks/incidents_converter.go | 10 ++++++++-- .../incidentio/tasks/incidents_converter_test.go | 12 ++++++++---- 3 files changed, 17 insertions(+), 7 deletions(-) diff --git a/backend/plugins/incidentio/e2e/raw_tables/_raw_incidentio_incidents.csv b/backend/plugins/incidentio/e2e/raw_tables/_raw_incidentio_incidents.csv index 79882c03aa5..6143e924131 100644 --- a/backend/plugins/incidentio/e2e/raw_tables/_raw_incidentio_incidents.csv +++ b/backend/plugins/incidentio/e2e/raw_tables/_raw_incidentio_incidents.csv @@ -3,4 +3,4 @@ id,params,data,url,input,created_at 2,"{""ConnectionId"":1,""ScopeId"":""type_01""}","{""id"":""inc_02"",""reference"":""INC-102"",""name"":""Latency spike"",""summary"":""p99 latency above SLO"",""permalink"":""https://app.incident.io/example/incidents/102"",""mode"":""retrospective"",""created_at"":""2026-05-02T09:00:00Z"",""updated_at"":""2026-05-02T09:10:00Z"",""incident_status"":{""name"":""Closed"",""category"":""closed""},""severity"":{""id"":""sev_2"",""name"":""Major"",""rank"":2},""incident_type"":{""id"":""type_01"",""name"":""Default""},""creator"":{""user"":{""id"":""u2"",""name"":""Bob"",""email"":""bob@example.com""}},""incident_timestamp_values"":[{""incident_timestamp"":{""id"":""ts_2"",""name"":""Declared at""},""value"":{""value"":""2026-05-02T09:05:00Z""}},{""incident_timestamp"":{""id"":""ts_3"",""name"":""Resolved at""},""value"":{""value"":""2026-05-01T18:00:00Z""}},{""incident_timestamp"":{""id"":""ts_4"",""name"":""Closed at""},""value"":{""value"":""2026-05-02T09:10:00Z""}}]}",,null,2026-05-02T09:10:00.000+00:00 3,"{""ConnectionId"":1,""ScopeId"":""type_01""}","{""id"":""inc_03"",""reference"":""INC-103"",""name"":""Practice run"",""summary"":""Game day exercise"",""permalink"":""https://app.incident.io/example/incidents/103"",""mode"":""test"",""created_at"":""2026-05-03T12:00:00Z"",""updated_at"":""2026-05-03T12:30:00Z"",""incident_status"":{""name"":""Closed"",""category"":""closed""},""severity"":{""id"":""sev_1"",""name"":""Minor"",""rank"":1},""incident_type"":{""id"":""type_01"",""name"":""Default""},""incident_timestamp_values"":[{""incident_timestamp"":{""id"":""ts_2"",""name"":""Declared at""},""value"":{""value"":""2026-05-03T12:00:00Z""}}]}",,null,2026-05-03T12:30:00.000+00:00 4,"{""ConnectionId"":1,""ScopeId"":""type_01""}","{""id"":""inc_04"",""reference"":""INC-104"",""name"":""Queue backlog"",""summary"":""Worker queue backed up"",""permalink"":""https://app.incident.io/example/incidents/104"",""mode"":""standard"",""created_at"":""2026-05-04T08:00:00Z"",""updated_at"":""2026-05-04T08:31:00Z"",""incident_status"":{""name"":""Closed"",""category"":""closed""},""severity"":{""id"":""sev_1"",""name"":""Minor"",""rank"":1},""incident_type"":{""id"":""type_01"",""name"":""Default""},""creator"":{""user"":{""id"":""u1"",""name"":""Alice"",""email"":""alice@example.com""}},""incident_timestamp_values"":[{""incident_timestamp"":{""id"":""ts_2"",""name"":""Declared at""},""value"":{""value"":""2026-05-04T08:00:00Z""}},{""incident_timestamp"":{""id"":""ts_3"",""name"":""Resolved at""},""value"":null},{""incident_timestamp"":{""id"":""ts_4"",""name"":""Closed at""},""value"":{""value"":""2026-05-04T08:30:00Z""}}]}",,null,2026-05-04T08:31:00.000+00:00 -5,"{""ConnectionId"":1,""ScopeId"":""type_01""}","{""id"":""inc_05"",""reference"":""INC-105"",""name"":""Security review"",""summary"":""Belongs to the Security incident type"",""permalink"":""https://app.incident.io/example/incidents/105"",""mode"":""standard"",""created_at"":""2026-05-05T14:00:00Z"",""updated_at"":""2026-05-05T14:05:00Z"",""incident_status"":{""name"":""Investigating"",""category"":""active""},""severity"":{""id"":""sev_2"",""name"":""Major"",""rank"":2},""incident_type"":{""id"":""type_99"",""name"":""Security""},""incident_timestamp_values"":[{""incident_timestamp"":{""id"":""ts_2"",""name"":""Declared at""},""value"":{""value"":""2026-05-05T14:00:00Z""}}]}",,null,2026-05-05T14:05:00.000+00:00 +5,"{""ConnectionId"":1,""ScopeId"":""type_01""}","{""id"":""inc_05"",""reference"":""INC-105"",""name"":""Security review"",""summary"":""Belongs to the Security incident type"",""permalink"":""https://app.incident.io/example/incidents/105"",""mode"":""standard"",""created_at"":""2026-05-05T14:00:00Z"",""updated_at"":""2026-05-05T14:05:00Z"",""incident_status"":{""name"":""Investigating"",""category"":""live""},""severity"":{""id"":""sev_2"",""name"":""Major"",""rank"":2},""incident_type"":{""id"":""type_99"",""name"":""Security""},""incident_timestamp_values"":[{""incident_timestamp"":{""id"":""ts_2"",""name"":""Declared at""},""value"":{""value"":""2026-05-05T14:00:00Z""}}]}",,null,2026-05-05T14:05:00.000+00:00 diff --git a/backend/plugins/incidentio/tasks/incidents_converter.go b/backend/plugins/incidentio/tasks/incidents_converter.go index 9f3c9263a79..da1227d7dce 100644 --- a/backend/plugins/incidentio/tasks/incidents_converter.go +++ b/backend/plugins/incidentio/tasks/incidents_converter.go @@ -116,11 +116,17 @@ func ConvertIncidents(taskCtx plugin.SubTaskContext) errors.Error { // panicking; incident.io statuses are operator-defined, but their // categories form a small fixed enum, so anything new from upstream // shouldn't crash a production pipeline. +// +// The API values are triage, declined, merged, canceled, live, +// learning, closed and paused. The app shows live as "Active" and +// learning as "Post-incident". declined, merged and canceled are +// terminal: the incident was declined in triage, merged into another +// incident, or canceled. func mapStatusCategory(category string) (mapped string, known bool) { switch category { - case "triage", "declared", "active", "paused", "post-incident": + case "triage", "live", "learning", "paused": return ticket.IN_PROGRESS, true - case "closed", "resolved": + case "closed", "declined", "merged", "canceled": return ticket.DONE, true default: return ticket.IN_PROGRESS, false diff --git a/backend/plugins/incidentio/tasks/incidents_converter_test.go b/backend/plugins/incidentio/tasks/incidents_converter_test.go index 023e66543c8..82baef060d7 100644 --- a/backend/plugins/incidentio/tasks/incidents_converter_test.go +++ b/backend/plugins/incidentio/tasks/incidents_converter_test.go @@ -35,12 +35,16 @@ func TestMapStatusCategory(t *testing.T) { expectedKnown bool }{ {"triage", ticket.IN_PROGRESS, true}, - {"declared", ticket.IN_PROGRESS, true}, - {"active", ticket.IN_PROGRESS, true}, + {"live", ticket.IN_PROGRESS, true}, + {"learning", ticket.IN_PROGRESS, true}, {"paused", ticket.IN_PROGRESS, true}, - {"post-incident", ticket.IN_PROGRESS, true}, {"closed", ticket.DONE, true}, - {"resolved", ticket.DONE, true}, + {"declined", ticket.DONE, true}, + {"merged", ticket.DONE, true}, + {"canceled", ticket.DONE, true}, + // App display names, not API values. + {"active", ticket.IN_PROGRESS, false}, + {"post-incident", ticket.IN_PROGRESS, false}, {"wat", ticket.IN_PROGRESS, false}, {"", ticket.IN_PROGRESS, false}, }