harden #5504 on rodboev's latest head: complete the tombstone wiring + CHANGELOG
@rodboev independently pushed fixes for messaging-tombstone (matches ours) and an
audit orphan-.bak skip — but the audit skip used _marks_deleted_webui_session
(index heuristic), which re-introduces the crash-suppression bug, and the other 4
resurrection/recovery paths were still open. Rebuilt the stage on rodboev's new
head (fc21c3f3, attribution preserved) and applied the complete superset:
- routes.py claim path: tombstone 404 gated on _state_db_session_source in
('','webui','fork') so foreign-source rows always materialize (finding B)
- models.py sidebar projection: skip tombstoned source='webui' rows w/ no live
sidecar so a deleted session can't resurface in /api/sessions (finding C)
- session_recovery.py orphan-.bak startup: skip restore when durable tombstone
present, durable-only (finding D)
- session_recovery.py audit orphan-.bak: durable-only classify as
deleted_session_skipped (corrects rodboev's index-heuristic version)
- session_recovery.py _read_state_db_missing_sidecar_rows: durable-tombstone-only
so a genuine crash (index intact, no durable tombstone) still repairs (finding F)
Regression tests (all verified fail-without-fix): sidebar-projection, orphan-.bak
startup skip, messaging-not-tombstoned, index-only-crash-repairable. Both advisors
(Codex SAFE TO SHIP + Opus ship-with-fixes) cleared the prior stage; this rebuild
carries the same fixes onto the contributor's latest work.
Co-authored-by: rodboev <rodboev@users.noreply.github.com>
This commit is contained in:
1 parent
06217c93b8
commit
63d0c00f8d
7 files changed
+193
-26
No files matched your search
@@ -5756,6 +5756,16 @@ def _load_cli_sessions_uncached(
|
||||
return None
|
||||
|
||||
profile_value = _cli_profile or 'default'
|
||||
# A deleted WebUI session is tombstoned (see _record_webui_deleted_session_tombstone)
|
||||
# so recovery/audit/claim treat it as gone. The sidebar's own state.db projection
|
||||
# must honor the same tombstone, or a deleted WebUI session reappears here as an
|
||||
# "Agent" ghost the moment non-WebUI sessions are shown (#5498, second path). Only
|
||||
# suppress genuine WebUI rows with no live sidecar — a re-created/re-imported sid
|
||||
# (live {sid}.json) always beats a stale tombstone.
|
||||
try:
|
||||
_deleted_webui_tombstone = _load_webui_deleted_session_tombstone()
|
||||
except Exception:
|
||||
_deleted_webui_tombstone = frozenset()
|
||||
for row in read_importable_agent_session_rows(
|
||||
db_path,
|
||||
limit=visible_session_limit if visible_session_limit is not None else (
|
||||
@@ -5774,6 +5784,14 @@ def _load_cli_sessions_uncached(
|
||||
profile = profile_value # CLI DB has no profile column; use active profile
|
||||
|
||||
_source = row['source'] or 'cli'
|
||||
# Honor the deleted-WebUI tombstone: a WebUI row the user deleted must
|
||||
# not resurface in this projection (the #5498 ghost). Live sidecar wins.
|
||||
if (
|
||||
_source == 'webui'
|
||||
and sid in _deleted_webui_tombstone
|
||||
and not (SESSION_DIR / f"{sid}.json").exists()
|
||||
):
|
||||
continue
|
||||
_source_meta = normalize_agent_session_source(_source)
|
||||
_title = row['title']
|
||||
if not _title and _source == 'cron':
|
||||
|
||||
Reference in new issue
Block a user