agentsclimarketplace

Incident response

Skill medy-gribkov/arcana/skills/incident-response

Engineering incident response covering on-call runbooks, blameless postmortems, status pages, rollback procedures, communication protocols, severity levels, and SLO breach handling.From its SKILL.md

Install
npx -y skills add medy-gribkov/arcana --skill incident-response

Assembled from the repository path, not quoted from the project. Check it against their README if it does not work.

One thing to look at

  • 1 stars1 stars. Stars are a popularity signal and not a quality one, but at this level it is likely that nobody has read this closely except its author, and you would be relying on your own review.

SKILL.md

10.2 KB, ~2.4k tokens by cl100k_base, as published. Nobody here has run it

Purpose

Handle production incidents with speed, clarity, and accountability. This skill provides frameworks for on-call response, structured communication, rollback execution, and learning from failures.

Severity Classification

  • SEV-1 (Critical): Complete service outage, data loss, or security breach. All hands on deck. Resolve in minutes.
  • SEV-2 (Major): Significant degradation affecting most users. Dedicated incident commander. Target resolution under 1 hour.
  • SEV-3 (Minor): Partial degradation, workaround available. On-call engineer handles. Target resolution under 4 hours.
  • SEV-4 (Low): Cosmetic issues, minor bugs, non-user-facing failures. Handle during business hours.
  • Classify based on user impact, not technical complexity. A simple bug affecting all users is higher severity than a complex bug affecting one.
  • Escalate severity upward when impact grows. Never downgrade severity during an active incident.

On-Call Runbooks

BAD - Vague runbook:

## Database Issues
If the database is slow, check the connections and maybe restart it.
Contact the DBA if it doesn't work.

GOOD - Actionable runbook with copy-paste commands:

## Runbook: Database Connection Pool Exhausted

### Symptoms
- API returns 503 errors
- Grafana alert: `db_active_connections > 95% of pool_size`
- Logs: "connection pool exhausted, 0 idle connections"

### Diagnose (< 1 minute)
    kubectl exec -it deploy/api -- curl localhost:8080/debug/db
    # Shows: active=100, idle=0, max=100, waiting=47

    psql -h $DB_HOST -c "SELECT count(*) FROM pg_stat_activity WHERE state='active';"

### Fix (choose one)
1. **Kill idle transactions** (safest):
       psql -h $DB_HOST -c "SELECT pg_terminate_backend(pid) FROM pg_stat_activity WHERE state='idle in transaction' AND query_start < now() - interval '5 min';"

2. **Increase pool size** (temporary):
       kubectl set env deploy/api DB_POOL_SIZE=200
       kubectl rollout restart deploy/api

3. **Rollback last deploy** (if caused by new code):
       kubectl rollout undo deploy/api

### Do NOT
- Do NOT restart the database. Active transactions will be lost.
- Do NOT increase pool size above 200 without DBA approval.

### Escalation
- Slack: #team-platform | PagerDuty: Platform On-Call

Write runbooks for every known failure mode. Structure: symptom, diagnostic commands, fix steps, escalation contacts. Store where on-call engineers find them in 30 seconds. Link directly from monitoring alerts. Review quarterly.

Incident Command Structure

  • Assign an Incident Commander (IC) immediately. The IC coordinates, does not debug.
  • The IC's responsibilities: delegate tasks, track progress, communicate externally, decide on escalation.
  • Assign a Communications Lead for SEV-1 and SEV-2 incidents. They update the status page and notify stakeholders.
  • Engineers working the incident report findings to the IC, not to each other. Single channel of communication.
  • Use a dedicated incident channel (Slack, Teams). Name it #inc-YYYY-MM-DD-description.
  • The IC calls the all-clear. No one else declares the incident resolved.

Communication Protocols

  • First update within 5 minutes of detection for SEV-1, 15 minutes for SEV-2.
  • Update every 30 minutes during an active incident, even if there is no progress. Silence causes panic.
  • Use structured updates: current status, what we know, what we are doing, next update time.
  • Internal updates go to the engineering team and leadership. External updates go to the status page.
  • Avoid blame language during the incident. Focus on symptoms and actions.
  • After resolution, send a final summary: root cause, fix applied, user impact duration, follow-up actions.

Status Page Management

  • Maintain a public status page for external services. Update it before customers ask.
  • Use clear, non-technical language: "Some users may experience slow page loads" over "Database replica lag exceeding threshold."
  • Define status levels: Operational, Degraded Performance, Partial Outage, Major Outage.
  • Pre-write templates for common scenarios. Fill in specifics during the incident.
  • Include estimated resolution time when possible. Update it as the estimate changes.
  • Post a follow-up after resolution confirming the issue is fully resolved.

Rollback Procedures

  • Every deployment must have a documented rollback path before it ships.
  • For application deployments: revert to the previous container image or artifact version.
  • For database migrations: write and test the down migration before applying the up migration.
  • For feature flags: disable the flag. This is the fastest rollback available.
  • For infrastructure changes: use version-controlled IaC. Revert the commit and apply.
  • Practice rollbacks in staging. A rollback you have never tested is a guess, not a plan.
  • Set a time limit for debugging before rolling back. For SEV-1, roll back first, debug later.
  • Preserve logs, metrics, and state before rolling back. You need evidence for the postmortem.

Blameless Postmortems

BAD - Blame-focused postmortem:

Root Cause: John deployed broken code on Friday at 5pm without testing.
Action Items: John needs to be more careful.

GOOD - Systems-focused postmortem:

## Postmortem: API Outage 2025-03-15

### Timeline (UTC)
- 16:42 - Deploy v2.3.1 to production (automated via merge to main)
- 16:44 - Error rate spikes from 0.1% to 34%
- 16:47 - PagerDuty alert fires, on-call acknowledges
- 16:52 - IC declared, #inc-2025-03-15-api-errors created
- 16:58 - Root cause identified: missing DB migration
- 17:01 - Rollback initiated (kubectl rollout undo)
- 17:03 - Error rate returns to 0.1%, all-clear declared

### Impact
- Duration: 21 minutes
- Users affected: ~12,000 (API returned 500 on /orders endpoint)
- Revenue impact: ~$3,200 in failed checkouts

### Root Cause
Deploy v2.3.1 added a query on `orders.status_v2` column. The migration
to add this column was not included in the deploy pipeline.

### Contributing Factors
- CI pipeline does not run pending migrations before integration tests
- No pre-deploy check that verifies schema compatibility
- Deploy happened automatically on merge, no manual gate

### Action Items
| Action | Owner | Due |
|--------|-------|-----|
| Add migration check to CI pipeline | @platform | 2025-03-22 |
| Add schema compatibility pre-deploy hook | @platform | 2025-03-29 |
| Document migration-first deploy process | @docs | 2025-03-22 |

Conduct postmortems for every SEV-1 and SEV-2 within 48 hours. Focus on system failures, not human errors. Ask "why did the system allow this?" Track action item completion. Review quarterly for recurring themes.

SLO Breach Handling

  • Define SLOs (Service Level Objectives) for latency, availability, and error rate before incidents happen.
  • Calculate error budgets: if SLO is 99.9% uptime, the error budget is 43.2 minutes per month.
  • When the error budget is exhausted, freeze feature releases and focus on reliability work.
  • Alert at 50% and 80% error budget consumption. Do not wait until the budget is gone.
  • Tie SLO breaches to business impact. Leadership cares about customer trust, not percentiles.
  • Review SLOs quarterly. Adjust targets based on customer expectations and operational capacity.
  • Use SLO data to justify reliability investments. "We burned 90% of error budget last month" is a concrete argument.

Post-Incident Improvement

  • Convert every postmortem action item into a tracked issue with a deadline and an owner.
  • Prioritize automation that prevents recurrence over documentation that describes it.
  • Add monitoring for the specific failure mode that caused the incident.
  • Update runbooks with lessons learned from the incident.
  • Share incident learnings in team retrospectives and engineering all-hands.
  • Measure MTTR (Mean Time to Resolution) and MTTD (Mean Time to Detection) over time. Both should trend downward.

PagerDuty/OpsGenie Webhook Integration

// ✅ Production-Ready: PagerDuty Events API v2
import axios from "axios";

interface PagerDutyEvent {
  routing_key: string;
  event_action: "trigger" | "acknowledge" | "resolve";
  dedup_key?: string;
  payload: {
    summary: string;
    severity: "critical" | "error" | "warning" | "info";
    source: string;
    timestamp?: string;
    custom_details?: Record<string, unknown>;
  };
}

async function triggerPagerDutyAlert(
  routingKey: string,
  summary: string,
  severity: "critical" | "error" | "warning" | "info",
  details?: Record<string, unknown>
) {
  const event: PagerDutyEvent = {
    routing_key: routingKey,
    event_action: "trigger",
    payload: {
      summary,
      severity,
      source: "monitoring-system",
      timestamp: new Date().toISOString(),
      custom_details: details,
    },
  };

  const response = await axios.post(
    "https://events.pagerduty.com/v2/enqueue",
    event,
    { headers: { "Content-Type": "application/json" } }
  );

  return response.data.dedup_key; // Use this to acknowledge/resolve later
}

// Usage: trigger SEV-1 alert
const dedupKey = await triggerPagerDutyAlert(
  process.env.PAGERDUTY_ROUTING_KEY!,
  "Database connection pool exhausted",
  "critical",
  { activeConnections: 100, maxConnections: 100, queuedRequests: 250 }
);
# OpsGenie Alert API
import requests
import os

def create_opsgenie_alert(message: str, priority: str, details: dict):
    """Create OpsGenie alert via REST API."""
    url = "https://api.opsgenie.com/v2/alerts"
    headers = {
        "Authorization": f"GenieKey {os.getenv('OPSGENIE_API_KEY')}",
        "Content-Type": "application/json"
    }

    payload = {
        "message": message,
        "priority": priority,  # P1-P5
        "details": details,
        "tags": ["production", "automated"],
        "source": "monitoring"
    }

    response = requests.post(url, json=payload, headers=headers)
    response.raise_for_status()
    return response.json()["requestId"]

# Usage
create_opsgenie_alert(
    message="API latency p99 > 2s for 5 minutes",
    priority="P1",
    details={"p99_latency": "2.3s", "endpoint": "/api/orders", "region": "us-east-1"}
)

What ships with it: 1 file

3.9 KB alongside SKILL.md

references/

Keep looking

Skills are one crate of 325,949. Ordering is by how many stacks a row turns up in, so the top of any crate is what has actually been picked rather than what has the most stars.