claude-code - 💡(How to fix) Fix [BUG] Background-fleet "deleteJob" silently unlinks main session JSONL despite cleanupPeriodDays: 36500

Official PRs (…)
ON THIS PAGE

Recommended Tools

×6

Utilities matched from this issue’s tags and category — try them while you read without losing context.

GitHub issue graph ai analysis

Paste a GitHub issue URL. We fetch that issue, discover linked issues from bodies/comments/timeline, collect linked pull requests, and produce a structured English report.

The report is written in English Markdown for sharing and archival.

Helpful · Quick feedback

Loading…

Code Example

// ~/.claude/settings.json
{
  "cleanupPeriodDays": 36500,
  "env": { "DISABLE_AUTO_COMPACT": "1" }
}

---

2026-05-16 20:45    852 KB  conversacion.jsonl
2026-05-17 16:34   1.7 MB  conversacion.jsonl
2026-05-18 09:29   1.9 MB  conversacion.jsonl   ← last snapshot

---

~/.claude/daemon.log
[2026-05-18T14:20:43.986Z] [bg] bg claimed-spare 1789cd89 (fleet)
[2026-05-18T14:29:50.619Z] [bg] bg settled 1789cd89 (killed)

---

[PERF:bg-spare-start]
[PERF:bg-spare-spawned]
[PERF:bg-claim-start]
[bg-spare] claim miss (
tengu_bg_spare_claim_fail
job_claim_spare_delete_failed
[bg-spare] deleteJob unconfirmed (
 dir preserved
job_respawn_kill_unconfirmed
.jsonl

---

Skipping retention cleanup: userSettings source is disabled (--setting-sources) and no enabled source provides cleanupPeriodDays.
Skipping cleanup: settings have validation errors but cleanupPeriodDays was explicitly set. Fix settings errors to enable cleanup.
cleanupPeriodDays must be at least 1. To keep transcripts for a long time, set a large number (e.g. 3650 for ~10 years).
RAW_BUFFERClick to expand / collapse

Preflight Checklist

  • I have searched existing issues and this hasn't been reported yet (related but distinct: #41458, #59248, #59848)
  • This is a single bug report
  • I am using the latest version of Claude Code (2.1.143, 2.1.144 just downloaded)

What's Wrong?

The background-fleet ("bg-spare") session lifecycle introduced in Claude Code 2.1.x silently deletes the main session JSONL from ~/.claude/projects/<encoded-cwd>/<UUID>.jsonl when a job is claimed/settled, even though cleanupPeriodDays: 36500 is set. The companion directory ~/.claude/projects/<encoded-cwd>/<UUID>/ (containing subagents/, tool-results/, etc.) is intentionally preserved — leaving an orphaned directory with no main transcript.

This is not the same as the TTL-based retention path covered in #41458 / #59248. The retention cleanup respects cleanupPeriodDays; this lifecycle path does not.

Observed scope: 374 out of 1462 sessions (≈25%) are now orphaned across all projects on my machine.

Evidence

1. Setting is correctly applied:

// ~/.claude/settings.json
{
  "cleanupPeriodDays": 36500,
  "env": { "DISABLE_AUTO_COMPACT": "1" }
}

2. Inventory across ~/.claude/projects/:

MetricCount
Total session dirs <UUID>/1016
Total main JSONLs <UUID>.jsonl1462
Orphans (dir exists, sibling .jsonl missing)374

3. Reproducible case — session 1789cd89-4253-40f8-a063-ea3fc8f35778:

~/.claude/projects/-Users-davidgonzalez-Workspace-repos-Certainty/:

  • 1789cd89-4253-40f8-a063-ea3fc8f35778/subagents/... exists (dir mtime 2026-05-16)
  • 1789cd89-4253-40f8-a063-ea3fc8f35778.jsonl missing

Out-of-band S3 backup (taken by my own /guardar-historial-equipo hook before kill) confirms the JSONL existed and was actively growing across three days:

2026-05-16 20:45    852 KB  conversacion.jsonl
2026-05-17 16:34   1.7 MB  conversacion.jsonl
2026-05-18 09:29   1.9 MB  conversacion.jsonl   ← last snapshot

4. Daemon log shows the kill that immediately preceded the local deletion:

~/.claude/daemon.log
[2026-05-18T14:20:43.986Z] [bg] bg claimed-spare 1789cd89 (fleet)
[2026-05-18T14:29:50.619Z] [bg] bg settled 1789cd89 (killed)

That settled killed (14:29:50Z = 09:29:50 local) matches the timestamp of the final S3 snapshot (09:29:32 local) within ~20 s. After this moment, the local .jsonl is gone but the dir with subagents/ remains.

5. Strings in the binary ~/.local/share/claude/versions/2.1.143 (Mach-O arm64, sha hidden, 197 MB) confirm the mechanism is deliberate:

[PERF:bg-spare-start]
[PERF:bg-spare-spawned]
[PERF:bg-claim-start]
[bg-spare] claim miss (
tengu_bg_spare_claim_fail
job_claim_spare_delete_failed
[bg-spare] deleteJob unconfirmed (
 dir preserved
job_respawn_kill_unconfirmed
.jsonl

The literal dir preserved warning, alongside deleteJob, shows the fleet code path explicitly tries to delete .jsonl and explicitly keeps the sibling directory.

6. The retention-cleanup code path is a different one that does respect cleanupPeriodDays. Around offset 211987 in the strings dump:

Skipping retention cleanup: userSettings source is disabled (--setting-sources) and no enabled source provides cleanupPeriodDays.
Skipping cleanup: settings have validation errors but cleanupPeriodDays was explicitly set. Fix settings errors to enable cleanup.
cleanupPeriodDays must be at least 1. To keep transcripts for a long time, set a large number (e.g. 3650 for ~10 years).

That retention path iterates over baseLogs, mcp-logs-, cc-transcript-*.txt, shell-snapshots, feedback-bundles, cc-transcript-*.txt, dump-prompts-*.jsonl, etc. — but the main session JSONLs are also deleted via the unrelated fleet deleteJob path, which neither logs to daemon.log with a recognizable cleanup tag nor honors the user's retention setting.

Steps to Reproduce

  1. Set "cleanupPeriodDays": 36500 in ~/.claude/settings.json.
  2. Use Claude Code 2.1.x with background-fleet enabled (default since 2.1.142). Open and resume the same session across multiple days via --resume <UUID> or the Agents view. Make sure subagents are spawned so the <UUID>/subagents/ dir is populated.
  3. End or close the session.
  4. Inspect ~/.claude/projects/<encoded-cwd>/:
    • <UUID>/subagents/... — present
    • <UUID>.jsonldeleted

Expected Behavior

cleanupPeriodDays: 36500 should keep main session JSONLs on disk regardless of which lifecycle path closes the session. The fleet deleteJob should not unlink the persistent transcript that the user expects to keep for cleanupPeriodDays days.

Actual Behavior

Fleet deleteJob silently unlinks <UUID>.jsonl regardless of cleanupPeriodDays. No log line is emitted to daemon.log explaining the deletion; the only nearby line is bg settled <UUID> (killed). The sibling directory is preserved (intentionally per binary string dir preserved), which makes the deletion look more like data corruption than a retention sweep.

Impact

  • 25% of historical sessions on my machine are now orphaned locally.
  • For users without an out-of-band backup (in my case /guardar-historial-equipo mirrors to S3 before each kill), the conversations would be permanently lost.
  • --resume <UUID> against an affected session fails with no transcript.

Environment

  • macOS Darwin 25.3.0 (arm64)
  • Claude Code 2.1.143 (active), 2.1.144 (downloaded)
  • Plan: paid; daemon mode enabled; using Agents view + multi-pane workflows extensively
  • No iCloud sync on ~/.claude/
  • No user hooks touch ~/.claude/projects/

Suggested Fix

In the fleet lifecycle (job_claim_spare, bg settled killed), do not unlink the main session JSONL. Either:

  1. Leave the JSONL on disk and let the retention sweep (hi3() / cleanupPeriodDays) decide when to delete it, or
  2. Move the JSONL to an "archived" location instead of deleting, or
  3. Honor cleanupPeriodDays inside deleteJob.

Related

  • #41458 — cleanupPeriodDays: 99999 ignored (TTL path; this issue is the fleet path)
  • #59248 — Silent retention cleanup (no warning/opt-in)
  • #48334 — Desktop app deletes session history
  • #59848 — Interactive sessions classified as background jobs post-2.1.139 (likely upstream cause: foreground sessions now travel the fleet path)

CC: not applicable — repro is on my account but the mechanism is generic.

Vote matrix · Quick signals

Works
Did the solution work? Tap to confirm.
Easy Fix
Was it a quick fix?
Time Saver
Did it save you time?
Blocking
Was it severely blocking?
Common Issue
Are others likely hitting this too?
Flaky / Intermittent
Is it intermittent?
Verified / Reproducible
Can you reproduce it reliably?
Loading…

Still need to ship something?

×6

Another batch ranked right after the header list — different links, same matching logic.

Back to top recommendations

TRENDING

claude-code - 💡(How to fix) Fix [BUG] Background-fleet "deleteJob" silently unlinks main session JSONL despite cleanupPeriodDays: 36500