Skip to content

fix(kanban): preserve creation-time blocked provenance - #77049

Open
mattboostkit wants to merge 2 commits into
NousResearch:mainfrom
mattboostkit:fix/blocked-kanban-sticky-provenance-20260802
Open

fix(kanban): preserve creation-time blocked provenance#77049
mattboostkit wants to merge 2 commits into
NousResearch:mainfrom
mattboostkit:fix/blocked-kanban-sticky-provenance-20260802

Conversation

@mattboostkit

Copy link
Copy Markdown

Summary

  • treat initial_status="blocked" creation events as sticky human-ops provenance
  • clear that provenance only on explicit unblocked or promoted_manual events
  • fail closed on corrupt legacy creation payloads without crashing dispatch
  • cover recompute and full dispatch paths, typed human blocks, explicit clear semantics, circuit-breaker retry policy, and corrupt event shapes

Verification

  • scripts/run_tests.sh -j 4 tests/hermes_cli/test_kanban_blocked_sticky.py tests/hermes_cli/test_kanban_block_kinds.py tests/hermes_cli/test_kanban_cli.py tests/tools/test_kanban_tools.py tests/cli/test_cli_tools_command.py -q — 63 passed
  • uv run ruff check hermes_cli/kanban_db.py tests/hermes_cli/test_kanban_blocked_sticky.py — passed
  • uv run python -m compileall -q hermes_cli/kanban_db.py tests/hermes_cli/test_kanban_blocked_sticky.py — passed
  • git diff --check — passed

Broader baseline notes

  • tests/hermes_cli/test_kanban_db.py has 3 reproducible Windows/environment failures outside this diff: wait-status encoding, Git worktree slash normalization, and installed-shim fallback.
  • root npm run check exits non-zero in existing JS workspace checks; this change touches no JS files.

Review

Independent read-only review found three malformed-payload edge cases during iteration; all were fixed and regression-tested. Final re-review: no findings.

@mattboostkit

Copy link
Copy Markdown
Author

Independent verification: NO SHIP

High blocker — malformed creation provenance can still crash the dispatcher.

At exact head 6650855d0b162831dc74b3c3c3ae1ea1b4e9e925, _has_sticky_block() catches TypeError/ValueError from json.loads, but not RecursionError. A deeply nested corrupt created.payload makes recompute_ready() raise instead of preserving the blocked card, aborting the dispatch tick for the board.

Reproduced on Python 3.11 with an isolated HERMES_HOME/Path.home:

payload = "[" * 2000 + "]" * 2000
# write payload to the blocked task's created event
kb.recompute_ready(conn)
# RecursionError: maximum recursion depth exceeded while decoding a JSON array

Smallest remediation: fail closed before/around parsing (a sane payload-size cap plus catching RecursionError, or an equivalently bounded parser), and add recompute + dispatch regression coverage proving deep nesting neither raises nor claims/spawns the blocked card. Re-run the 63-test focused suite and quality gates on the new SHA.

Other reproduced evidence on this SHA: focused suite 63/63 passed; independent 19-case normal/malformed matrix passed; ruff, compileall, diff check passed; test_kanban_db.py remains 27 passed / 3 known Windows-environment failures. Exact tree 283875918851654431c96f3fa91dd72d377f70dd; diff hash 6a2d5dc1f9faff75ee75c9ada41b0c61b907f3244f905d7b9f9e751fe1c6719a. Repository remained clean.

@alt-glitch alt-glitch added type/bug Something isn't working P3 Low — cosmetic, nice to have comp/cron Cron scheduler and job management needs-decision Awaiting maintainer decision before any implementation labels Aug 2, 2026
@alt-glitch

Copy link
Copy Markdown
Collaborator

This was generated by AI during triage.

Related to #41497, #66993, #69531, and #70733: these patches share the creation-time sticky-block goal but make different provenance and explicit-clear choices. Please consolidate on one state-transition contract.

@mattboostkit

Copy link
Copy Markdown
Author

Recursive payload blocker remediated

Updated exact head: c42ae67db5969bbc5e608eb28b5b59c275b515d7
Tree: beebd8b450d5713b905bd920468c8dc370728e1c

Smallest fail-closed change:

  • _has_sticky_block() now treats RecursionError from deeply nested created-event JSON as corrupt provenance and preserves the blocked state.
  • Added isolated recompute and full dispatch regressions using 2,000-level nesting. The dispatch test forces profile_exists=True and proves zero promotion, claim, spawn, or fake-spawn calls.

Verification on this head:

  • RED before fix: 2 focused deep-payload tests failed with the reproduced RecursionError.
  • GREEN after fix: 2/2 deep-payload tests passed.
  • Canonical sticky/block-kind/CLI/tool-list suite: 65 passed, 0 failed.
  • Broader test_kanban_db.py: 27 passed, 3 unchanged Windows/environment baseline failures (rate-limit wait-status encoding, slash normalization, installed-shim fallback).
  • Ruff, compileall, and git diff --check: passed.

No merge, install, restart, live database, service, or config mutation was performed. Independent exact-SHA review is queued on Kanban card t_eba4f70e.

@teknium1 teknium1 added sweeper:risk-session-state Sweeper risk: may lose/corrupt/mis-associate session or context state sweeper:blast-moderate Sweeper blast radius: moderate — a subsystem or single platform labels Aug 2, 2026
@mattboostkit

Copy link
Copy Markdown
Author

Independent exact-SHA review: SHIP

I reviewed commit c42ae67db5969bbc5e608eb28b5b59c275b515d7 (tree beebd8b450d5713b905bd920468c8dc370728e1c) against parent 6650855d0b162831dc74b3c3c3ae1ea1b4e9e925 and the blocked-card provenance contract.

Evidence:

  • I reproduced the prior blocker against the parent with a 2,000-level JSON array. It raised RecursionError.
  • The exact candidate returned True for the same payload and preserved the blocked state.
  • Corrupt provenance did not promote, claim or spawn during dispatch tests.
  • Parentless and completed-parent initial blocks remained sticky.
  • needs_input and capability remained sticky.
  • Explicit unblocked and promoted_manual events cleared stickiness.
  • Later gave_up behavior retained the existing failure-limit policy.
  • Dependency blocks promoted only after the parent completed.

Verification:

  • Focused five-file contract suite: 65 passed, 0 failed.
  • Sticky-block suite: 27 passed.
  • Additional block-kind, retry-policy, promotion and unblock checks: 6 passed.
  • Ruff, AST parsing and git diff --check HEAD^ HEAD: passed.
  • Broader DB suite: 27 passed, 3 known Windows/environment baseline failures unrelated to the candidate line or tests.
  • Exact worktree was clean before and after review.

Residual risk is low. Corrupt provenance intentionally fails closed and may require explicit operator recovery. I did not run the entire repository suite.

This verdict applies only to exact commit c42ae67db5969bbc5e608eb28b5b59c275b515d7. It does not approve merging or installing the change into the running service.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

comp/cron Cron scheduler and job management needs-decision Awaiting maintainer decision before any implementation P3 Low — cosmetic, nice to have sweeper:blast-moderate Sweeper blast radius: moderate — a subsystem or single platform sweeper:risk-session-state Sweeper risk: may lose/corrupt/mis-associate session or context state type/bug Something isn't working

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants