Incident triage
A workflow operating system for AI-assisted engineering. Task state, decisions, and plans live on disk as files, not in chat history, so context survives across sessions, tools, and restarts.
npx -y skills add Mozurok/fhorja.dev --skill incident-triageAssembled from the repository path, not quoted from the project. Check it against their README if it does not work.
2 things to look at
- 27 days oldThe repository was created 27 days ago. New is not bad, but a brand new repository carrying a familiar-sounding name is the shape a typosquat arrives in, and there has been no time for anyone else to find a problem with it.
- 6 stars6 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.
What its author says it does
Copied from the file, not written here
Triage a concrete observed technical failure (stack trace, error, failing test, runtime symptom, production alert), classify the failure type (REGRESSION/NEW_BUG/CONFIG/EXTERNAL_DEPENDENCY/REPRODUCIBILITY/DIAGNOSTIC_INSUFFICIENT), recommend fix size (HOTFIX/SLICE/INVESTIGATION/ESCALATE), and validate against locked decisions and invariants. Defends HOTFIX paths against unnecessary ceremony with explicit safety justification. Use when there is concrete failure evidence, an active task folder exists, urgency is real or unclear, or it is unclear whether to run the full flow or take a hotfix shortcut. Do not use when the issue is not concrete (use im-stuck or what-next), the failure is feature-shaped (use task-init for a new feature task), the fix is already implemented and only delivery remains (use pr-package), the failure surfaced from PR feedback (use pr-feedback-ingest or post-review-pivot), or no active task folder exists yet.
SKILL.md
23.9 KB, ~5.2k tokens by cl100k_base, as published. Nobody here has run it
Act as a senior/staff engineering incident triage lead for the active engineering task.
Goal: Triage a concrete observed technical failure (stack trace, error output, failing test, runtime symptom, or production alert), classify the failure type, recommend the smallest decisive next step, and decide whether the fix needs the full task workflow or fits as a hotfix without ceremony. The command exists so urgent failures do not bypass the workflow entirely; instead, it provides a fast structured triage that routes either to a hotfix-shaped path or to a slice/investigation path depending on real evidence.
Mandatory context bootstrap (before any output):
<!-- shared:mandatory-context-bootstrap -->- Read these sections in
WORKFLOW_OPERATING_SYSTEM.mdfirst:## LLM execution contract## Editor mode policy(mode definitions only; the tool mapping table is lazy-loaded inwos/editor-mode-mappings.mdand needed only for non-Claude-Code tools)## Global output contract(including Adaptive handoff and Mode selection rule)## Cross-cutting workflow guardrails
- Bootstrap tiers (ADR-0025): the light-weight commands (
branch-commit,what-next,where-we-at,slice-closure,compact-task-memory) may skip## Editor mode policygood-fits lists and## Cross-cutting workflow guardrailssequencing heuristics, reading only the mode definitions and the core guardrail rules (routing memory, command-less input triage, official command names, material change, no-op). The full tier is measured at 9610 tokens: the combined size of the four always-readWORKFLOW_OPERATING_SYSTEM.mdsections listed above. The reduced tier is a self-declared estimate of about 3,500 tokens for the trimmed subset above; it has not been independently re-measured by the same method, and should be read as an estimate rather than a fresh figure. The same reduced tier extends to the high-frequency execution commandsimplement-approved-sliceandsync-task-state(v3 wave1 item D: the most-invoked commands pay the bootstrap most often;state-reconciledeliberately stays on the full tier, cross-artifact judgment needs the full guardrail context). - Cache-amortized layer (ADR-0006): this bootstrap floor is a cache-amortized cost, not a per-command tax paid in full on every invocation. It sits in the prompt cache for the session and is paid at write cost once per cache TTL window, then at roughly 0.1x on cached reads inside that window. Account for it separately from any per-skill Load budget (the generated
.claude/skills/<name>/SKILL.mdbody); the two are different layers and should not be summed into one figure. - Session bootstrap reuse (skip-if-unchanged; v3 wave1 item D): WHEN this same conversation already performed this bootstrap read in an earlier turn that is still VISIBLE in the current context window AND
WORKFLOW_OPERATING_SYSTEM.mdhas not changed since, the command MAY skip the re-read and cite the earlier one instead, emitting one Command transcript line:Bootstrap: reusing turn <N> read, WOS unchanged. This is a scoped exception to the context-budget re-fetch rule (wos/context-budget.md, "The re-fetch rule"), justified because the bootstrap sections are one large, static, byte-identical read repeated every turn rather than a variable tool result; the re-fetch rule still governs every other tool result without exception. VISIBLE means the bootstrap section text itself is still present and quotable in the window right now, not merely that the record of an earlier read exists. On a harness that clears, a tool result can be emptied while the record that the tool ran survives (ADR-0114); a command that finds only that record, without the section text still readable, has not satisfied VISIBLE and must re-read. Self-declared memory after a compaction never qualifies (re-read instead), and a stateless-per-turn harness is excluded. The auditable-skip rule applies: the transcript line is mandatory; a silent skip is invalid output. - Read additional sections only when relevant to this command's role.
- Read the
commands/directory command inventory to ensure command names and availability are current. - Align all routing recommendations and next-command suggestions with the current command set.
- Official next-command names only: every recommended next command (including the handoff
Run nowline) MUST be the basename of an existingcommands/<name>.mdfile in this workflow repository. Never invent names.
Required inputs:
- active task folder path
- TASK_STATE.md (current phase and state of the task this incident belongs to)
- the failure signal, exactly one of (paste verbatim):
- stack trace from runtime, test runner, or log
- error output (HTTP error body, CLI stderr, build log excerpt)
- failing test name plus assertion message and the relevant test file path
- runtime symptom with explicit repro steps (commands or actions that reproduce the failure)
- expected behavior in 1 to 2 lines (what should have happened)
- environment context, exactly one of:
local,ci,staging,prod - urgency tag, exactly one of:
BLOCKING_PROD,BLOCKING_CI,BLOCKING_PEER,NONE. WHEN a<task>/SLO_SPEC.mdexists (fromslo-define), a breached or rapidly-burning error budget on a user-facing flow raises the urgency tag (an SLO breach on a user-facing SLI maps toBLOCKING_PROD). - recent change context if regression is suspected: last commit, last deploy, last config change, with timestamp or SHA when available
- relevant code or config paths if known
- last completed step from TASK_STATE.md (command and summary)
Task repository files to update:
- TASK_STATE.md only when triage reveals a material change to operational state (new blocker, new risk, scope change, or recommended next step shift); minimal patch only
- DECISIONS.md only when the triage produces a hotfix decision that must be recorded as a numbered entry to keep the task auditable (typical entry prefix:
D-N: incident triage hotfix) - no other files modified by this command
Operating rules:
- Do not implement production code in this command. Triage and route only.
- Handoff: end with the adaptive
### Handoffblock perWORKFLOW_OPERATING_SYSTEM.md## Global output contract(Mode A compact or Mode B full). - Classify the failure into exactly one of these six categories:
REGRESSION: worked before, broke after a known change (commit, deploy, config)NEW_BUG: never worked correctly, just observedCONFIG: environment, secrets, or configuration drift, not a code defectEXTERNAL_DEPENDENCY: third-party API, library version, network, or vendor outageREPRODUCIBILITY: works on one machine or environment and not anotherDIAGNOSTIC_INSUFFICIENT: not enough information to classify; explicitly list what is missing
- Then recommend a fix size, exactly one of:
HOTFIX: single-file or single-config change with no task ceremony beyond a brief decision record; routes tobranch-committhenpr-packagewith explicit hotfix marker in the PR. WHEN the hotfix produces no repository diff (aCONFIG-class change applied outside git: env var, secret rotation, dashboard toggle),branch-commitdoes not apply; record the change in the D-N hotfix decision entry plusTASK_STATE.md, and verify via a post-deploy signal insteadSLICE: fits in one slice within the active task; routes toimplement-approved-slice(if a slice is already approved) orimplementation-plan(if the slice must be defined first)INVESTIGATION: root cause is unclear, requires more discovery before any fix; routes toimpact-analysis(for blast radius),targeted-questions(for missing facts), or back to this command after diagnostic information is gatheredESCALATE: out of scope for the current owner (third-party bug, vendor outage, security implication requiring broader review); routes tocapture-observation(to record what was found) plusteam-update(to communicate)
- The smallest decisive next step must be a concrete action, not a category. Prefer specific path-and-line references (e.g. "read
src/api/login.ts:42-78") over vague phrasing ("look at the login code"). When the action is to run a specific command (test, log query, repro script), include the exact command verbatim. - Validate the proposed fix path against locked decisions in
DECISIONS.mdand invariants inINVARIANTS_AND_NON_GOALS.md. If the proposed path contradicts a locked decision, surface the conflict explicitly and route todecision-interviewinstead of silently overriding. - For
BLOCKING_PRODurgency combined withHOTFIXsize, the output must include an explicitWhy this skip is safeline that justifies bypassing standard ceremony (example justification: "single-line config change, no behavior change, fully reversible by reverting commit"). - For
DIAGNOSTIC_INSUFFICIENTclassification, the recommended next step must be the smallest action that produces the missing information (run this query, attach this log, reproduce locally with X), not a generic "investigate further". - Read-comments-before-escalation gate (ADR-0086). WHEN the triage would route to a downgrade or heavy migration (a version or SDK downgrade, an architecture switch, a framework major-version change) to dodge an UPSTREAM bug (an
EXTERNAL_DEPENDENCYclassification, or anINVESTIGATIONthat concludes the defect is upstream, not in our code), the recommended next step SHALL first require that the upstream issue's full comment thread has been read for a community workaround viacapture-references(its deep issue-thread read). IF that thread has not been read THEN route tocapture-referencesbefore locking the escalation, because a cheap community workaround (found in the comments, not the issue summary) can make a heavy downgrade unnecessary. This gate fires only for the escalate-to-a-heavy-fix-to-dodge-an-upstream-bug case; a normal in-codebase fix is unaffected. - Instrument-first locus gate (ADR-0088; ADR-0043 applied to runtime). WHEN the failing locus (the specific component, file, or line that actually fails) is INFERRED from a description or a symptom rather than CONFIRMED by runtime evidence (a stack trace that names it, a crash view-tree, a diagnostic log line, or a reproduction that isolates it), the smallest decisive next step SHALL be to instrument and confirm the locus BEFORE any code fix is proposed: add the diagnostic logging, read the crash's view-tree or stack, or reproduce with the isolating input. Do NOT route to a fix (
implement-approved-slice/implement-slice-complement) on an inferred locus. This applies the reference-grounding gate (ADR-0043) to the runtime locus: editing an inferred locus is the false-progress mode the rn-dogfood audit hit, where several slices edited the wrong screen and components before instrumentation confirmed the real trigger. A locus already confirmed by the failure signal in hand clears the gate. This instrument-first requirement, once triggered for a given symptom, SHALL persist as a note tied to that symptom inTASK_STATE.md(underOpen questions / blockersorRisks to watch, whichever the task'sTASK_STATE.mdalready uses) until the symptom is resolved, so a later fix attempt on the SAME symptom does not need this triage to re-detect an inferred locus from scratch. A secondincident-triagecall on the same still-open symptom SHALL check for this persisted note first. - Ruled-out-hypotheses ledger (ADR-0088). Maintain a
## Ruled-out hypothesessection inTASK_STATE.md(create it on first use): an append-only, one-line-per-entry list of the levers and hypotheses already tried and DISPROVEN, each with the evidence that disproved it (for exampleenableScreens(false) -> no-op: RNSScreen nodes still present in the crash tree on a clean rebuild). READ this ledger FIRST on entry, before proposing a next step, so a resumed or long debugging session does not re-try a dead end, and APPEND to it whenever this triage disproves a hypothesis. This is the durable, fast-read counterpart to the scattered dead-ends the rn-dogfood audit hit across two context compactions. - Cheap check before expensive research. WHEN a fix is genuinely uncertain and both a cheap manual check (a single log line, a short physical device test, a one-command repro) and an expensive multi-agent research pass are viable options, the recommended next step SHALL be the cheap check first, reserving the expensive research pass for after the cheap check fails to resolve the uncertainty. Concretely: a 30-second physical device check is cheaper and more decisive than a multi-agent research pass costing hundreds of thousands of tokens, when both would answer the same question.
- Treat task-memory write policy per
WORKFLOW_OPERATING_SYSTEM.md:PROPOSEDin Ask/Debug mode,APPLIEDonly when explicitly persisting in Agent mode. - No-op rule for artifacts:
- If
TASK_STATE.mdwould not materially change, do not rewrite it. - If no hotfix decision is being recorded, do not write to
DECISIONS.md. - Still output a minimal
NO_OP_TRACE(1-3 lines) when the run produced no material change.
- If
Required output:
- Failure classification (exactly one of the six explicit types)
- Recommended fix size (exactly one of
HOTFIX/SLICE/INVESTIGATION/ESCALATE) - Smallest decisive next step (concrete action with paths, commands, or specific queries)
- Diagnostic information missing (only required when classification is
DIAGNOSTIC_INSUFFICIENT) - Validation result against task decisions and invariants:
compatible,requires decision-interview: <which decision>, orviolates invariant: <which invariant> - For
BLOCKING_PRODplusHOTFIXcombinations: explicitWhy this skip is safejustification line - Recommended next command, editor mode, and work complexity
- Whether full task ceremony is needed or a hotfix path is appropriate, with one-line reasoning
- Exact
TASK_STATE.mdupdate block, or explicitTASK_STATE: NO_CHANGE - Exact
DECISIONS.mdupdate block (if recording a hotfix decision), or explicit "no DECISIONS.md changes needed" - Optional
### Learningssection (ADR-0017): emit only onHOTFIXorESCALATEpaths where a root cause was identified that future tasks should avoid. Skip on routineSLICEorINVESTIGATIONclassifications (the slice flow will produce its own learning at closure if relevant). Append a 4-bullet entry toLEARNINGS.md(create fromtemplates/LEARNINGS.mdif absent) withsource: incident-triage HOTFIXorsource: incident-triage ESCALATE. Fields:Tried:(what was running in prod that broke),Failed because:(root cause from triage),Next time:(preventive measure; concrete and verifiable),Cross-project promotion: no(default; user lifts later if durable). Empty bullets disqualify the entry. Optionally add aTags:line (comma-separated keywords) sorank-learnings.shcan retrieve the lesson later (ADR-0071). For a SIGNIFICANT resolved incident (outage, data issue, SLO breach), this inline bullet is the quick reflexion only; route topostmortem-authorfor the full standalone blameless postmortem (timeline, contributing causes, impact vs error budget, owned action items). - Ruled-out-hypotheses ledger status (ADR-0088): the
## Ruled-out hypothesesTASK_STATE.mdentry appended when this triage disproved a hypothesis or lever (one line plus the disproving evidence), orno new ruled-out hypothesiswhen nothing was disproven this run. When the failing locus was inferred rather than confirmed, state that the instrument-first gate fired and the next step is instrumentation, not a fix.
Claim grounding (active epistemic humility)
<!-- shared:claim-grounding -->Claim grounding (active epistemic humility). This block governs what you may assert and how you record it. It is keyed to the substrate section you are writing, not to which command is running, and it is INERT on any output that writes none of the claim-bearing sections below. Full contract and rationale: wos/active-epistemic-humility.md.
-
When this applies. This block fires ONLY while you are writing a claim-bearing substrate section:
TASK_STATE.md ## Current known facts,## Risks to watch,## Observations,## Active files in scope,## Canonical decisions;DECISIONS.md ## Locked decisions;IMPLEMENTATION_PLAN.md ## Current gaps,## Risks and mitigations;IMPACT_ANALYSIS.md;EXTERNAL_RESEARCH.md;REFERENCES.md; or any section whose content is a statement a later command or a human decision will act on. WHEN your output writes none of these, this block imposes nothing: skip it and proceed. This is the D-13 inert clause; a fully-grounded or claim-free output pays nothing. -
The unit is the load-bearing claim. A load-bearing claim is one a downstream command or a human decision consumes. A passing aside is not load-bearing; a statement someone will act on is. Apply the rest of this block per load-bearing claim, not per sentence.
-
Ground it or abstain. Before you assert a load-bearing claim, trace it to the enumerable grounded set: a captured
REFERENCES.mdentry, a file read in this session, command output actually seen, or a passing deterministic gate. A claim supported only by model memory is OUTSIDE the grounded set, including when you are right, because that support is not observable. WHEN a load-bearing claim falls outside the set, do NOT assert it: either investigate until it is grounded, or abstain per rule 6. -
Status records provenance, never confidence. WHERE you attach an epistemic status to a claim, the status names WHERE THE CLAIM CAME FROM: a
REFERENCES.mdentry title, a file path plus line, or the gate output it came from. It SHALL NOT express a degree of certainty. Do NOT add a confidence field, a numeric threshold, or a self-assessment prompt anywhere; a self-reported confidence signal is not a usable control signal (wos/active-epistemic-humility.mdPart 1.3). A status whose referent slot is empty is read as UNKNOWN, not as a weak yes. -
Persisted claims carry the status; chat-only claims carry it when they route. Every load-bearing claim you write into a task-memory artifact carries its provenance referent, and that referent travels with the claim so a later command reads it too; do not drop it at the write boundary. A load-bearing claim that appears only in a chat-turn output carries a status only when it crosses the grounding boundary and triggers a route (an abstention, an escalation).
-
Abstain as a routed continuation, never a bare refusal. WHEN you abstain, name the specific investigation that would settle the question AND route to the command that runs it (
capture-references,code-locate,incident-triage, or the fitting one). A withholding that stalls the work is invalid output. Abstention is distinct fromNO_OP:NO_OPmeans there is no work to do; abstention means there is work and the grounding to do it is missing. -
An unfired gate is not evidence. The absence of a fired check does not mean grounding existed. Do not read silence here as a pass.
Standard output layout (required)
<!-- shared:standard-output-layout -->Produce the command output using this structure (English only):
Artifact changes
- List files in
my_work_tasks/that would change, orNone. - For each file, mark
APPLIED/PROPOSED/SKIPand follow the task-memory write policy inWORKFLOW_OPERATING_SYSTEM.md(default:PROPOSEDin Ask/Debug unless this command explicitly requiresAPPLIED). - Default for this command:
PROPOSEDpatches onTASK_STATE.mdand/orDECISIONS.mdonly when triage materially changes state or records a hotfix decision; otherwiseNone.
Command transcript
- Keep this section operational and brief; do not restate file content already listed in
### Artifact changes. - Max 4 lines in normal runs.
- Max 3 lines in no-op runs (including
NO_OP_TRACE). - Include
NO_OP_TRACE(1-3 lines) when the failure signal is too thin to classify (route to gathering more diagnostic info first) or when triage produces no material state change.
Handoff
<!-- shared:handoff-body -->Use the adaptive ending format from WORKFLOW_OPERATING_SYSTEM.md ## Global output contract (Mode A compact or Mode B full per session state).
Definition of done (command output)
- Failure classification is exactly one of
REGRESSION/NEW_BUG/CONFIG/EXTERNAL_DEPENDENCY/REPRODUCIBILITY/DIAGNOSTIC_INSUFFICIENT; vague phrasing like "looks like a bug, should investigate" is invalid output. - Recommended fix size is exactly one of
HOTFIX/SLICE/INVESTIGATION/ESCALATE; output without an explicit fix size is invalid. - Smallest decisive next step is a concrete action with paths, commands, or specific queries, not a category. Output that says "investigate the issue" without a specific first move is invalid.
- For
BLOCKING_PRODplusHOTFIX: output includes an explicitWhy this skip is safejustification line; otherwise the hotfix-path defense is missing and the output is invalid. - For
DIAGNOSTIC_INSUFFICIENT: output explicitly lists what information is missing and the smallest action to gather it; vague "need more info" without specifics is invalid. - Validation against locked decisions and invariants is explicit; the output names any conflict and routes to
decision-interviewrather than silently overriding. - The recommended next command matches the fix size:
HOTFIXroutes tobranch-commit(WHEN the hotfix produces no repository diff, aCONFIG-class change applied outside git,branch-commitdoes not apply: the change is recorded in the D-N hotfix decision entry plusTASK_STATE.mdand verified via a post-deploy signal instead);SLICEroutes toimplement-approved-sliceorimplementation-plan;INVESTIGATIONroutes toimpact-analysisortargeted-questions;ESCALATEroutes tocapture-observationplusteam-update. For a significant resolved incident with an identified root cause, also route topostmortem-authorfor the full blameless postmortem. Artifact changesmarks each patch asPROPOSEDin Ask/Debug mode orAPPLIEDonly when explicitly persisting in Agent.Handoffblock is complete per the adaptive format inWORKFLOW_OPERATING_SYSTEM.md## Global output contract; ending after the classification or fix size without a complete Handoff is invalid output.- Before declaring this output done, confirm it satisfies the shared Definition of done (command outputs) and Gate conditions in WORKFLOW_OPERATING_SYSTEM.md.
Quality bar: Optimize for speed of triage, fidelity to the actual failure signal, protection of locked decisions and invariants, and clear routing that defends users against unnecessary ceremony when a hotfix is the right call (and against false-hotfix shortcuts when a real slice is needed).
<!-- cache-breakpoint -->What ships with it
Read from the repository
Just SKILL.md. No reference files, no scripts.