Skip to content

Add trace.py confirm: batch the dead-object judgment layer#59

Open
Richyread wants to merge 2 commits into
petrowsky:mainfrom
Richyread:feat/trace-confirm
Open

Add trace.py confirm: batch the dead-object judgment layer#59
Richyread wants to merge 2 commits into
petrowsky:mainfrom
Richyread:feat/trace-confirm

Conversation

@Richyread

Copy link
Copy Markdown
Contributor

Follow-on to #57. #57 made the engine see everything; this makes the agent able to afford to analyse it. Addresses #58.

dead emits candidates but does none of the judgment, so it's hand-cranked per candidate. confirm computes the deterministic half in one pass and suggests a conservative disposition that never auto-deletes.

Per candidate:

  • name-string hits (SELF vs EXTERNAL), labelled by HIT-KIND: benign (placeholder/label — cannot invoke) < calc (hideWhen/merge/calc — a live reference) < caller (Perform-by-name / Go-to-Layout-$var). Merge fields <<Table::Field>> are classified calc.
  • table-qualified field probes — the bare field name is matched only when unique across tables, so a same-named field on another table can't cross-rescue.
  • referrer-liveness (fields) — a calc/caller hit from a referrer that is itself live promotes the field to likely-live (keep at a glance); review is reserved for held/dead-referrer, entry-point, or dynamic cases.
  • dynamic-reachable flag, an on/off-canvas verdict from existing layout-summary bounds (informational by default; --canvas-strict to act on it), and an external-entry-point hint.

Compatibility: cmd_dead is refactored to share compute_dead_candidates(); dead output is byte-for-byte unchanged. New subparser flags: --json, --verbose, --canvas-strict.

Validation: measured on a real production audit — judgment-layer tool calls ~4.6x fewer, wall-clock ~6x faster, confirmed-dead set verified correct.

Stacked on #57 (reuses its module/trigger functions) — please merge after #57.

Deferred follow-ups (not this PR): capture merge-field refs in the xref build; reference-type-aware referrer-liveness for layouts/VLs/scripts; a focused confirm -n <name> for single-object queries.

🤖 Generated with Claude Code

@agentic-fm

Copy link
Copy Markdown
Collaborator

Thanks for this, @Richyread — and for stacking it cleanly on #57. Good news: #57 is now merged, so the dependency is satisfied.

Whenever you're ready, could you rebase this onto the latest main and mark it ready for review (it's currently a draft)? Once it's out of draft I'll give it a full end-to-end pass — reproducing the pre-confirm per-candidate hand-grep cost, and verifying that the dead output stays byte-for-byte identical and the new dispositions are as conservative as described. Really appreciate the measured design (never auto-deletes). 🙏

Richyread and others added 2 commits July 11, 2026 19:58
…layer

`trace.py dead` emits dead-object candidates but does none of the deterministic
judgment, so an operator hand-greps several lookups per candidate (name-string,
dynamic dispatch, on/off-canvas, entry-point) — on a large audit that is the
bulk of the cost. `confirm` runs that judgment in one pass and emits one
enriched table with a conservative suggested disposition (likely-dead / review /
likely-live) that never auto-deletes.

Per candidate it computes:
- name-string hits (SELF vs EXTERNAL), labelled by HIT-KIND: benign
  (placeholder/label/tooltip — cannot invoke) < calc (hideWhen/merge/calc — a
  live reference) < caller (Perform-by-name / Go-to-Layout-$var). Merge fields
  `<<Table::Field>>` are classified calc, not benign.
- field probes are table-qualified; the bare field name is matched only when it
  is unique across tables, so a same-named field on another table cannot
  cross-rescue.
- referrer-liveness (fields): a calc/caller hit from a referrer that is itself
  live promotes the field to likely-live (keep at a glance); review is reserved
  for held/dead-referrer, entry-point, or dynamic cases.
- a dynamic-reachable flag, an on/off-canvas verdict from the existing
  layout-summary bounds (informational by default; --canvas-strict to act on
  it), and an external-entry-point hint.

cmd_dead is refactored to share compute_dead_candidates(); `dead` output is
byte-for-byte unchanged. New confirm subparser: --json, --verbose,
--canvas-strict.

Validated end-to-end on a live audit of a real solution: judgment-layer tool
calls dropped ~4.6x and wall-clock ~6x versus the pre-confirm baseline, with the
confirmed-dead set verified correct (no live object flagged dead).

Co-Authored-By: Claude Opus 4.8 (1M context) <[email protected]>
Fields used only inside a layout-object formula were invisible to the
cross-reference index and could be false-flagged as dead — the dangerous
direction, since an operator could clear live schema on a "0 inbound" read.

The gap was two layers:

- layout_to_summary.py dropped the portal filter <Calculation>, kept only a
  count for conditional formatting (calc text discarded), and omitted the
  action-parameter calc on grouped/popover buttons.
- trace.py _walk_layout_json only inspected the "field"/"script" keys; it never
  tokenised the calc strings already present in the summary (hideWhen, tooltip).

Now the summariser keeps those calcs, and the layout walk mines portal filter,
hide condition, conditional formatting, tooltip and button-param calcs for
TO::Field reads, resolving each to its canonical base field via the existing
RE_TO_FIELD / resolve_to_field machinery. Each ref is labelled by origin
(portal filter, hide calc, conditional format calc, tooltip calc, button param
calc).

Validated on a live operator run: two calc-only search-index fields that
previously scanned as zero-inbound now resolve correctly (via their related TO)
and are no longer flagged dead.

Co-Authored-By: Claude Opus 4.8 (1M context) <[email protected]>
@Richyread
Richyread marked this pull request as ready for review July 11, 2026 19:04
@Richyread
Richyread force-pushed the feat/trace-confirm branch from fc10957 to 444eaf3 Compare July 11, 2026 19:04
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.

2 participants