From 3455b27f6f809f414fb6ed936f70b3dcdc6a1774 Mon Sep 17 00:00:00 2001 From: arkon Date: Sun, 25 Jan 2026 08:01:57 +0100 Subject: [PATCH] fix: respawn disabled state not persisted across server restarts When /respawn/stop was called, the controller was stopped but remained in the respawnControllers map. This caused persistSessionState() to still read config.enabled=true and save respawnEnabled=true to state.json. On server restart, the respawn controller would be re-enabled because state.json had respawnEnabled=true. Fix: Remove controller from map and clear any timed respawn when /respawn/stop is called, so persistSessionState() correctly sets respawnEnabled=false. Co-Authored-By: Claude Opus 4.5 --- CLAUDE.md | 2 +- package.json | 2 +- src/web/server.ts | 10 ++++++++++ 3 files changed, 12 insertions(+), 2 deletions(-) diff --git a/CLAUDE.md b/CLAUDE.md index e80049aa..1bacfbdc 100644 --- a/CLAUDE.md +++ b/CLAUDE.md @@ -17,7 +17,7 @@ This file provides guidance to Claude Code (claude.ai/code) when working with co Claudeman is a Claude Code session manager with a web interface and autonomous Ralph Loop. It spawns Claude CLI processes via PTY, streams output in real-time via SSE, and supports scheduled/timed runs. -**Version**: 0.1347 +**Version**: 0.1348 **Tech Stack**: TypeScript (ES2022/NodeNext, strict mode), Node.js, Fastify, Server-Sent Events, node-pty diff --git a/package.json b/package.json index aa6da8c4..3780262c 100644 --- a/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "claudeman", - "version": "0.1347", + "version": "0.1348", "description": "The missing control plane for Claude Code - run 20 autonomous agents with real-time monitoring and session persistence", "type": "module", "main": "dist/index.js", diff --git a/src/web/server.ts b/src/web/server.ts index 4fa751d8..cfa5418b 100644 --- a/src/web/server.ts +++ b/src/web/server.ts @@ -790,6 +790,16 @@ export class WebServer extends EventEmitter { controller.stop(); + // Remove controller from map so persistSessionState doesn't save respawnEnabled: true + this.respawnControllers.delete(id); + + // Clear any timed respawn + const timerInfo = this.respawnTimers.get(id); + if (timerInfo) { + clearTimeout(timerInfo.timer); + this.respawnTimers.delete(id); + } + // Clear persisted respawn config this.screenManager.clearRespawnConfig(id);