What's wrong
An agent can enter a bad state where the process heartbeat and inbound Telegram listener look alive, but the current LLM/tool turn is stuck and user Telegram messages are deferred. During recovery, lifecycle tools can disagree with observed liveness, and Telegram MCP can be partially initialized: inbound/listener works but outbound telegram.reply fails with Telegram manager not initialized.
This makes the agent appear online while it cannot actually serve the user, and normal CPR/interrupt/suspend signals do not reliably recover or classify the state.
Where
- Component: LingTai kernel runtime / lifecycle health / worker recovery / MCP readiness
- Likely areas:
system.cpr / system.interrupt / system.suspend liveness and recovery behavior
- LLM worker timeout/AED recovery path
- notification deferral while an agent is active
- Telegram MCP startup/readiness handling for outbound tools
- Repo:
Lingtai-AI/lingtai-kernel
Reproduction
This is from a real incident on 2026-07-15. Local paths, Telegram chat ids, and project-specific task content are omitted/redacted, but the exact runtime error strings are preserved.
Observed chain:
- The target agent received a user Telegram message and began responding.
- Runtime logs then repeatedly showed:
- After the watchdog/grace period, logs showed:
LLM worker thread still running after 300s + 5s grace — interface state may be inconsistent. Refusing AED retry.
-
From the user's perspective, the bot looked like it stopped replying. The agent could still appear alive at the process/heartbeat level, so this was not a simple process-dead condition.
-
system.cpr against the agent returned:
CPR launch did not produce a fresh heartbeat within 10s (...)
A follow-up host check shortly after showed the process was alive and heartbeat/status were fresh. The agent had woken on recovery/internal notifications rather than directly handling the user Telegram message.
- The fresh process then entered an internal tool call and did not complete it promptly:
While the agent was active in that tool call, Telegram handling remained deferred.
-
system.interrupt returned success (status: interrupted) but did not clear the active stuck state. A follow-up check still showed fresh heartbeat/status and active state with no tool completion.
-
system.suspend returned an opposite liveness classification:
Agent at <agent-dir> is not running — already suspended?
At that same time, a host check showed:
.agent.heartbeat fresh (<1s)
.status.json fresh and state=active
- the agent process still running
So the lifecycle tool's “not running” result contradicted process/heartbeat evidence.
- After a manual hard restart, inbound/listener and LLM work resumed, but the first outbound Telegram attempt failed. The agent attempted
telegram.reply; the tool returned:
Telegram manager not initialized — server boot failed. Check stderr for the underlying exception (most often missing LINGTAI_TELEGRAM_CONFIG or invalid bot token).
The startup log around that same restart had shown the Telegram listener initially running, followed by an eager-start failure:
[Errno 54] Connection reset by peer
So the agent could receive/process work, but outbound Telegram tool readiness was broken.
- A second clean restart finally restored all three layers:
- fresh heartbeat/status
- Telegram listener and
mcp_inbox poller running
MCP telegram ... loaded 1 tools
telegram.accounts succeeded
- later
telegram.reply returned status: sent
What you expected
- Heartbeat/liveness should not be treated as sufficient service readiness.
- A stuck LLM worker after the 300s + grace window should either be reliably terminated/recovered or put the agent into an explicit unhealthy/STUCK state that lifecycle tools can act on.
interrupt, suspend, and cpr should not report contradictory states for the same fresh process/heartbeat condition.
- Telegram MCP readiness should distinguish inbound listener startup from outbound tool availability; a partial startup failure should be surfaced and recoverable.
What actually happened
- The agent looked alive at heartbeat/listener level while the active turn was stuck and user Telegram was deferred.
interrupt reported success but did not restore responsiveness.
suspend reported “not running” while host evidence showed a live active process with fresh heartbeat.
- A restart could leave Telegram in a partial state: listener/inbound present, but outbound
telegram.reply failed because the Telegram manager was not initialized.
- Full recovery required manual PID-tree termination plus a second clean CPR/restart, followed by explicit verification that outbound Telegram tool calls succeeded.
Severity
major
This can make a user-facing bot stop responding while still appearing alive, and the workaround requires expert manual diagnosis/restart. It is not just a cosmetic status problem: it blocks the user-facing communication path and can mislead orchestration/lifecycle tools.
Suggested fix
Consider splitting agent health/readiness into separate dimensions and making lifecycle tools report/act on them explicitly:
- Process liveness: heartbeat / PID / process exists.
- Turn progress: no LLM worker stuck beyond watchdog/grace; active tool calls have bounded progress or explicit timeout state.
- Service readiness: notifications are not indefinitely deferred behind an abandoned active turn.
- MCP inbound readiness: listener/poller is running.
- MCP outbound readiness: tool manager initialized and
telegram.send/reply/accounts can be called.
Possible implementation directions:
- When
LLM worker thread still running after 300s + 5s grace occurs, mark the agent as a distinct unhealthy/STUCK/unsafe state rather than leaving it looking normally alive.
- Make
system.interrupt, system.suspend, and system.cpr consult more than the heartbeat predicate and return richer diagnostics when process liveness and service readiness disagree.
- Add a recovery path that can safely terminate/restart an abandoned worker/process group, or clearly instruct the operator that a hard restart is required.
- Add MCP readiness checks so startup failures like
[Errno 54] Connection reset by peer do not leave an agent able to receive/process but unable to send.
- Add regression tests for: fresh heartbeat + stuck active worker; interrupt success but no progress; suspend false “not running” while heartbeat fresh; Telegram listener started but outbound manager not initialized.
Related context: PR #940 addresses a narrower transient liveness false-bounce/message wording issue. This report is broader and should not be treated as fixed by that PR alone.
What's wrong
An agent can enter a bad state where the process heartbeat and inbound Telegram listener look alive, but the current LLM/tool turn is stuck and user Telegram messages are deferred. During recovery, lifecycle tools can disagree with observed liveness, and Telegram MCP can be partially initialized: inbound/listener works but outbound
telegram.replyfails withTelegram manager not initialized.This makes the agent appear online while it cannot actually serve the user, and normal CPR/interrupt/suspend signals do not reliably recover or classify the state.
Where
system.cpr/system.interrupt/system.suspendliveness and recovery behaviorLingtai-AI/lingtai-kernelReproduction
This is from a real incident on 2026-07-15. Local paths, Telegram chat ids, and project-specific task content are omitted/redacted, but the exact runtime error strings are preserved.
Observed chain:
From the user's perspective, the bot looked like it stopped replying. The agent could still appear alive at the process/heartbeat level, so this was not a simple process-dead condition.
system.cpragainst the agent returned:A follow-up host check shortly after showed the process was alive and heartbeat/status were fresh. The agent had woken on recovery/internal notifications rather than directly handling the user Telegram message.
While the agent was active in that tool call, Telegram handling remained deferred.
system.interruptreturned success (status: interrupted) but did not clear the active stuck state. A follow-up check still showed fresh heartbeat/status andactivestate with no tool completion.system.suspendreturned an opposite liveness classification:At that same time, a host check showed:
.agent.heartbeatfresh (<1s).status.jsonfresh andstate=activeSo the lifecycle tool's “not running” result contradicted process/heartbeat evidence.
telegram.reply; the tool returned:The startup log around that same restart had shown the Telegram listener initially running, followed by an eager-start failure:
So the agent could receive/process work, but outbound Telegram tool readiness was broken.
mcp_inboxpoller runningMCP telegram ... loaded 1 toolstelegram.accountssucceededtelegram.replyreturnedstatus: sentWhat you expected
interrupt,suspend, andcprshould not report contradictory states for the same fresh process/heartbeat condition.What actually happened
interruptreported success but did not restore responsiveness.suspendreported “not running” while host evidence showed a live active process with fresh heartbeat.telegram.replyfailed because the Telegram manager was not initialized.Severity
major
This can make a user-facing bot stop responding while still appearing alive, and the workaround requires expert manual diagnosis/restart. It is not just a cosmetic status problem: it blocks the user-facing communication path and can mislead orchestration/lifecycle tools.
Suggested fix
Consider splitting agent health/readiness into separate dimensions and making lifecycle tools report/act on them explicitly:
telegram.send/reply/accountscan be called.Possible implementation directions:
LLM worker thread still running after 300s + 5s graceoccurs, mark the agent as a distinct unhealthy/STUCK/unsafe state rather than leaving it looking normally alive.system.interrupt,system.suspend, andsystem.cprconsult more than the heartbeat predicate and return richer diagnostics when process liveness and service readiness disagree.[Errno 54] Connection reset by peerdo not leave an agent able to receive/process but unable to send.Related context: PR #940 addresses a narrower transient liveness false-bounce/message wording issue. This report is broader and should not be treated as fixed by that PR alone.