Skip to content

AI response handler: the SHADOW_MODE compare still fails open #157

Open

Description

@NathanTarbert

Three pre-existing issues in packages/outpost/queue/src/handlers/ai-response.ts, all verified during the CR of #150 and all outside that PR's subject.

1. escalated: true is reported even when the escalation never enqueued

The escalation createJob is wrapped in a try/catch that logs and continues, but the handler's result still reports escalated: true. So a ticket whose escalation failed to enqueue looks escalated in the job record while no human was ever routed to it — the same "the record disagrees with what happened" class as #148.

2. A null description is stringified as the literal "null"

The classifier prompt interpolates ticket.description directly. Ticket.description is non-null in the schema today, but the AI pipeline path also handles tickets built from partial rows, and the guard costs nothing.

3. SHADOW_MODE === 'true' fails open

The strict comparison means SHADOW_MODE=TRUE, =1, or =yes all read as "not shadow mode" and post to real community surfaces. Shadow mode is a safety flag; it should fail closed on any truthy-looking value it does not recognize, and preferably log the value it rejected. This pattern is repo-wide, so fixing it centrally (a shared isShadowMode() helper) is probably better than patching one call site.

Found by: CR rounds 1-2 on #150 (slots 1-2, 2-1).

Activity

  1. added
    roadmapTracked on the Outpost roadmap
    roadmap: nowRoadmap horizon: V1 launch critical path / safety
    area: aiAI response pipeline, groundedness, confidence
    on Aug 17, 2026
  2. NathanTarbert commented on Sep 15, 2026

    @NathanTarbert
    CollaboratorAuthor

    Two of the three gaps here are fixed on main; retitling so the remaining scope matches what is left.

    Fixed by #191:

    • escalated is now derived from escalationEnqueued / escalationSkippedState rather than being reported unconditionally, so a throwing enqueue no longer reports a handoff that did not happen (packages/outpost/queue/src/handlers/ai-response.ts:1084-1085)
    • the classifier prompt joins only the parts that exist, so a null description no longer stringifies as the literal "null" (ai-response.ts:716-721)

    Still open — the one this issue now tracks: process.env.SHADOW_MODE === 'true' remains at ai-response.ts:829 and onboarding-digest.ts:119. The comparison accepts exactly one spelling, so TRUE, 1, yes and on all read as "not shadow mode" and post for real — a safety flag failing open on inputs an operator would reasonably expect to work.

    PR #233 replaces both call sites with a shared isShadowMode() that fails closed, and is open and green. This should close when that merges.

  3. changed the title [-]AI response handler: three small correctness gaps (escalation reporting, null description, SHADOW_MODE compare)[/-] [+]AI response handler: the SHADOW_MODE compare still fails open[/+] on Sep 15, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    area: aiAI response pipeline, groundedness, confidenceroadmapTracked on the Outpost roadmaproadmap: nowRoadmap horizon: V1 launch critical path / safety

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions