Skip to content

[RELEASE] Approvals empty states respect the runtime filter (no more OpenClaw copy under a Claude Code filter) - #5007

Merged
vivekchand merged 2 commits into
mainfrom
fix/approvals-empty-state-runtime-scoped
Aug 19, 2026
Merged

[RELEASE] Approvals empty states respect the runtime filter (no more OpenClaw copy under a Claude Code filter)#5007
vivekchand merged 2 commits into
mainfrom
fix/approvals-empty-state-runtime-scoped

Conversation

@vivekchand

Copy link
Copy Markdown
Owner

What the operator saw

Approvals tab filtered to Claude Code, yet the "No pending approvals" empty state was a ~90-word paragraph explaining every runtime's gating mechanics — and explicitly naming OpenClaw. The history empty state was equally generic. (Founder screenshot, 2026-08-19, v0.12.737.)

Fix

The pending + history lists already filter rows per-runtime; the empty-state copy now does too:

Filter Pending empty state
Claude Code No pending approvals for Claude Code. Turn on a protection rule on the right and risky Claude Code calls pause before they run (PreToolUse hook), then land here for a decision.
OpenClaw …pause before they run (exec-policy preset)…
Codex (etc.) …are caught as they happen…
all No pending approvals. Turn on a protection rule on the right and risky calls from your agents land here for a decision.

History: "No Claude Code decisions yet." (generic sentence retained for "all").

Verification

Booted the branch on a fake-HOME :8903 instance and rendered all four variants live (screenshot attached in session). Inline <script> passes node --check.

Notes

  • Drops 4 data-i18n keys (copy is now interpolated with the runtime label, which static keys can't express). test_i18n_no_raw_codes has 2 pre-existing failures on main (45 missing keys, none touched here).
  • The Protection Rules right-hand column is genuinely node-wide ("One rule, every runtime") and unchanged.

🤖 Generated with Claude Code

…f text

Under a Claude Code filter the pending empty state was a 90-word paragraph
explaining every runtime's gate — and named OpenClaw. Approvals are
per-runtime (both renders already filter on session-id prefix), so the copy
now is too:

- 'No pending approvals for Claude Code.' + one line naming only THAT
  runtime's gate (PreToolUse hook / exec-policy preset / reactive catch).
- History: 'No Claude Code decisions yet.'
- 'all' filter keeps a generic one-liner.

Verified live on a fake-HOME :8903 instance for claude_code / openclaw /
codex / all.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
@8090-software-factory

Copy link
Copy Markdown

⚠️ Drift Bot (ClawMetry): 1 potential drift finding(s)

1. Blueprint: Remote Alerts and Action Approvals

File: clawmetry/templates/tabs/approvals.html:588

The code calls _cmRuntimeLabel() to render runtime-specific empty state messages, but this function is not defined in the codebase. The function is only mocked in test files and the blueprint does not specify how runtime labels should be provided to the UI layer.

// default — rows carry the requesting session id, whose prefix names
// the runtime. BOTH renders (pending + history) filter identically.
var _rt = (typeof _cmRuntimeFilter === 'function') ? _cmRuntimeFilter() : 'all';
var _rtLbl = (_rt && _rt !== 'all' && typeof _cmRuntimeLabel === 'function') ? _cmRuntimeLabel(_rt) : '';

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Drift Bot (ClawMetry) — Blueprint: Remote Alerts and Action Approvals

The code calls _cmRuntimeLabel() to render runtime-specific empty state messages, but this function is not defined in the codebase. The function is only mocked in test files and the blueprint does not specify how runtime labels should be provided to the UI layer.

@github-actions

github-actions Bot commented Aug 19, 2026

Copy link
Copy Markdown
Contributor

Visual diff

Comparing 2ec290a2c1ae (head) against the PR base branch.

41 of 66 comparison(s) flagged (>1% pixel diff).

View Before After Diff
desktop overview ⚠️ before after diff · 100.00%
desktop flow ⚠️ before after diff · 8.77%
desktop brain ⚠️ before after diff · 6.85%
desktop usage before after diff · 0.98%
desktop crons ⚠️ before after diff · 2.96%
desktop memory ⚠️ before after diff · 3.22%
desktop security ⚠️ before after diff · 100.00%
desktop subagents ⚠️ before after diff · 2.11%
desktop transcripts before after diff · 0.07%
desktop logs ⚠️ before after diff · 5.33%
desktop skills ⚠️ before after diff · 2.88%
desktop models ⚠️ before after diff · 2.87%
desktop approvals before after diff · 0.23%
desktop alerts before after diff · 0.00%
desktop notifications before after diff · 0.02%
desktop limits ⚠️ before after diff · 1.54%
desktop clusters before after diff · 0.27%
desktop history ⚠️ before after diff · 2.04%
desktop channels before after diff · 0.01%
desktop dives before after diff · 0.00%
desktop harness ⚠️ before after diff · 3.35%
desktop inventory ⚠️ before after diff · 2.23%
desktop nemoclaw before after diff · 0.26%
desktop policy ⚠️ before after diff · 2.50%
desktop selfevolve before after diff · 0.26%
desktop swimlane ⚠️ before after diff · 2.24%
desktop tool-catalog before after diff · 0.28%
desktop tracing before after diff · 0.10%
desktop turn-anatomy before after diff · 0.26%
desktop version-impact before after diff · 0.00%
desktop context-economics before after diff · 0.01%
desktop agents ⚠️ before after diff · 1.50%
desktop evals ⚠️ before after diff · 23.68%
mobile overview ⚠️ before after diff · 100.00%
mobile flow before after diff · 0.33%
mobile brain ⚠️ before after diff · 6.82%
mobile usage ⚠️ before after diff · 100.00%
mobile crons ⚠️ before after diff · 5.81%
mobile memory ⚠️ before after diff · 100.00%
mobile security ⚠️ before after diff · 100.00%
mobile subagents ⚠️ before after diff · 3.42%
mobile transcripts before after diff · 0.01%
mobile logs ⚠️ before after diff · 1.95%
mobile skills ⚠️ before after diff · 100.00%
mobile models ⚠️ before after diff · 2.25%
mobile approvals ⚠️ before after diff · 100.00%
mobile alerts ⚠️ before after diff · 3.00%
mobile notifications before after diff · 0.01%
mobile limits before after diff · 0.07%
mobile clusters ⚠️ before after diff · 1.91%
mobile history ⚠️ before after diff · 100.00%
mobile channels ⚠️ before after diff · 100.00%
mobile dives ⚠️ before after diff · 100.00%
mobile harness before after diff · 0.01%
mobile inventory ⚠️ before after diff · 2.73%
mobile nemoclaw before after diff · 0.01%
mobile policy ⚠️ before after diff · 100.00%
mobile selfevolve before after diff · 0.01%
mobile swimlane ⚠️ before after diff · 1.68%
mobile tool-catalog before after diff · 0.07%
mobile tracing ⚠️ before after diff · 100.00%
mobile turn-anatomy ⚠️ before after diff · 100.00%
mobile version-impact ⚠️ before after diff · 100.00%
mobile context-economics before after diff · 0.02%
mobile agents ⚠️ before after diff · 100.00%
mobile evals before after diff · 0.00%

Folder: 2ec290a2c1ae. Full PNGs also attached as a workflow artefact.

Generated by visual-diff bot. Pixel diffs >1% flagged; eyeball the table before merging. This check is non-blocking — fail = bot bug, not a code problem.

@vivekchand

Copy link
Copy Markdown
Owner Author

Drift-bot triage (1 finding):

  • "_cmRuntimeLabel() is not defined in the codebase" — disproven; it is defined in clawmetry/static/js/app.js on both base and head:
    $ git show origin/main:clawmetry/static/js/app.js | grep -n "function _cmRuntimeLabel"
    11212:function _cmRuntimeLabel(rt) { return _CM_RT_LABEL[rt] || rt; }
    
    app.js loads on the same dashboard page before any tab template runs, and the call site guards with typeof _cmRuntimeLabel === 'function' (raw runtime id fallback).
  • "the blueprint does not specify how runtime labels should be provided to the UI layer" — real gap, now fixed: Remote Alerts and Action Approvals blueprint v8 adds "Runtime-scoped empty states on the Approvals tab (PR [RELEASE] Approvals empty states respect the runtime filter (no more OpenClaw copy under a Claude Code filter) #5007)" with the label-catalog contract and ADR-007.

@8090-software-factory

Copy link
Copy Markdown

⚠️ Drift Bot (ClawMetry): 1 potential drift finding(s)

1. Blueprint: Remote Alerts and Action Approvals

File: clawmetry/templates/tabs/approvals.html:588

The blueprint specifies runtime labels should come from "the dashboard's shared runtime label catalog — the same id-to-label mapping that every other tab uses," but the code introduces _cmRuntimeLabel() function that does not exist in the codebase and differs from the pattern used in alerts.js (_CM_RT_LABEL object). While the guard prevents runtime errors, it creates inconsistency with the documented shared catalog approach.

// default — rows carry the requesting session id, whose prefix names
// the runtime. BOTH renders (pending + history) filter identically.
var _rt = (typeof _cmRuntimeFilter === 'function') ? _cmRuntimeFilter() : 'all';
var _rtLbl = (_rt && _rt !== 'all' && typeof _cmRuntimeLabel === 'function') ? _cmRuntimeLabel(_rt) : '';

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Drift Bot (ClawMetry) — Blueprint: Remote Alerts and Action Approvals

The blueprint specifies runtime labels should come from "the dashboard's shared runtime label catalog — the same id-to-label mapping that every other tab uses," but the code introduces _cmRuntimeLabel() function that does not exist in the codebase and differs from the pattern used in alerts.js (_CM_RT_LABEL object). While the guard prevents runtime errors, it creates inconsistency with the documented shared catalog approach.

github-actions Bot pushed a commit that referenced this pull request Aug 19, 2026
@vivekchand

Copy link
Copy Markdown
Owner Author

Drift-bot round 2 triage: the remaining claim — "_cmRuntimeLabel() does not exist in the codebase / differs from the alerts.js pattern" — is the documented base-misread class. The function exists on main and head and IS the shared catalog accessor the blueprint (v8) describes:

$ git show origin/main:clawmetry/static/js/app.js | grep -n "_cmRuntimeLabel\|_CM_RT_LABEL = " | head -3
11128:var _CM_RT_LABEL = {
11212:function _cmRuntimeLabel(rt) { return _CM_RT_LABEL[rt] || rt; }

app.js loads globally before every tab template; alerts.js's local rtLabel wraps the same catalog. Blueprint gap from round 1 was fixed in v8 (ADR-007). Merging per the standing drift-bot policy: disprove with git show, don't rewrite a correct spec to match a misread.

@vivekchand
vivekchand merged commit da62489 into main Aug 19, 2026
23 of 24 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant