Skip to content

Follow-up from PR #4386 R5 review: 3 polish items (warning width chrome, audit-log callId, ACP audit-log sibling) #4509

@LaZzyMan

Description

@LaZzyMan

Summary

Three small polishing items surfaced in the round-5 review of PR #4386. They're all observability / UI-polish suggestions — each is real but doesn't warrant landing in #4386 itself per the round-weighted-bar discipline (R5+: Suggestion / observability defaults to follow-up). Filing here so the findings aren't lost.

Items

1. safeWidth in ToolConfirmationMessage.tsx doesn't account for warning box chrome

packages/cli/src/ui/components/messages/ToolConfirmationMessage.tsx:267

safeWidth = Math.max(contentWidth, 1) is fed into the Math.ceil(textLen / safeWidth) wrap-row estimate, but the warning <Box> at line 309 renders with paddingX={1} marginLeft={1} — consuming 3 columns of available width. On contentWidth ≤ ~38 (very narrow terminals) the row estimate under-counts by 1, potentially pushing the options list off-screen by exactly that 1 row.

Fix is ~1 line:

const boxChrome = 3; // paddingX(1)*2 + marginLeft(1)
const safeWidth = Math.max(contentWidth - boxChrome, 1);

Round-5 review reference: #4386 (comment)

2. Substitution audit log lacks callId

packages/core/src/core/coreToolScheduler.ts:850

The current message is:

Auto-approving ${canonicalName} command with substitution (mode=${approvalMode}, bypass=${bypassReason}): ${cmd}

Other scheduler log entries (setToolCallOutcome, setStatusInternal, finalizeBlockedSpan) include callId as the primary correlation key. Adding callId=${callId} to this log line would let operators grep the surrounding permission decisions / span timing during incident response.

Fix is ~10 LOC: thread a callId: string parameter through maybeLogSubstitutionBypass and the 5 call sites that already have it in scope.

Round-5 review reference: #4386 (comment)

3. ACP Session.ts parallel bypass sites lack audit log

packages/cli/src/acp-integration/session/Session.ts ~ lines 1940 (PM allow-rule auto-approve), 1975 (AUTO mode), 2043 (hook allow), 2067 (sibling-tool auto-approval)

PR #4386 added maybeLogSubstitutionBypass to all 5 bypass paths in coreToolScheduler.ts, but Session.ts is a parallel implementation of the same flow for ACP clients (VS Code extension, daemon). Substitution-bearing commands auto-approved through ACP leave no forensic trace.

Fix is ~50 LOC: extract shouldAuditSubstitutionBypass (currently exported from coreToolScheduler.ts) plus the log helper to a shared module, then audit each of the 4 ACP bypass sites the same way.

Round-5 review reference: issue-comment 4354388397

Why not in #4386

PR #4386 is at round 5 of review on what started as a 1-line deny → ask permission-model fix. It's already 14× its original size and has shipped:

  • The original L4 substitution deny → ask change (R0)
  • Wrap-aware warning layout reservation (R1 + R3 self-review)
  • Monitor sibling alignment + ACP buildPermissionRequestContent exec branch + non-interactive controller (R2)
  • COMMAND_SUBSTITUTION_WARNING constant + buildShellExecWarnings helper extraction (R3)
  • Audit log on YOLO + auto-mode bypass paths (R3)
  • AST walker substitution-detection top-level guard for variable_assignment / redirected_statement blind spots (R4 — actual security fix)
  • Audit log extension to PM-allow + hook + sibling-auto-approve paths within coreToolScheduler.ts (R4)
  • Round-3 helper + audit-log dual-check / JSDoc / catch-block consistency (R4)

The R5 findings are all real but classify as polish under the round-weighted-bar discipline (Suggestion → follow-up at R5+). Keeping them in scope guarantees an R6/R7 finding the next observability sibling, then the next, indefinitely — the failure mode that took PR #4168 to 12 rounds and 6303 LOC.

Filing here so #4386 can land at its current scope and these get picked up cleanly when someone has bandwidth.

Metadata

Metadata

Assignees

No one assigned

    Labels

    Type

    No type
    No fields configured for issues without a type.

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions