chenhg5/cc-connect · error
session process is not running
Error message
session process is not running
What it means
Send checks the session's atomic alive flag before doing anything and refuses to talk to a dead Copilot process with 'session process is not running'. It exists so callers get an immediate, clear error instead of a write to a closed pipe or a silent hang.
Source
Thrown at agent/copilot/session.go:696
func summarizeToolInput(tool string, input map[string]any) string {
if input == nil {
return ""
}
b, err := json.Marshal(input)
if err != nil {
return ""
}
s := string(b)
if len(s) > 200 {
s = s[:200] + "..."
}
return s
}
// Send sends a user message to the running Copilot process.
func (cs *copilotSession) Send(prompt string, messageID string, images []core.ImageAttachment, files []core.FileAttachment) error {
if !cs.alive.Load() {
return fmt.Errorf("session process is not running")
}
// Handle images: save to temp dir and append file references
if len(images) > 0 {
imgPaths, err := saveImagesToTempDir(cs.workDir, images)
if err != nil {
slog.Warn("copilotSession: failed to save images", "error", err)
} else {
prompt = core.AppendFileRefs(prompt, imgPaths)
}
}
// Handle files
if len(files) > 0 {
filePaths := core.SaveFilesToDisk(cs.workDir, messageID, files)
prompt = core.AppendFileRefs(prompt, filePaths)
}
View on GitHub (pinned to 4000b2338a)
Solutions
- Start a new session (/new) or restart the agent so a fresh Copilot process is spawned, then resend the message.
- Check earlier logs for 'process exited' / 'copilotSession: process failed' with stderr to find why the CLI died, and fix that root cause.
- Re-authenticate the CLI if it exited due to auth expiry.
- If kills are environmental (OOM, supervisor), increase limits so the process survives.
- Add health checking/automatic restart for the agent process if this recurs.
Example fix
// before: sending into a dead session
session.Send("continue the task", msgID, nil, nil) // "session process is not running"
// after: recreate the session first
if !sessionAlive(session) {
session = agent.StartSession(ctx, opts) // fresh CLI process
}
session.Send("continue the task", msgID, nil, nil) Defensive patterns
Strategy: type-guard
Validate before calling
if !cs.alive.Load() {
return fmt.Errorf("cannot send: session process is not running")
} Type guard
func canSend(s *copilotSession) bool { return s.alive.Load() } Try / catch
if err := session.Send(prompt, msgID, nil, nil); err != nil {
if strings.Contains(err.Error(), "not running") {
session = agent.StartSession(ctx, opts)
err = session.Send(prompt, msgID, nil, nil)
}
} Prevention
- Check session liveness before sending instead of reusing cached session handles
- Restart the session after any 'process exited' event
- Monitor host memory so the CLI is not OOM-killed mid-conversation
- Recreate sessions after service restarts rather than reusing old handles
When it happens
Trigger: copilotSession.Send called when cs.alive.Load() is false — i.e. after readLoop's deferred cleanup ran because the CLI process exited (crash, kill, clean exit).
Common situations: User sends a chat message after the CLI crashed earlier in the conversation; long idle period during which the CLI was OOM-killed; engine retrying delivery to a session whose process already died; systemd restarting the service and stale session references being used.
Understand the failure class
Background: ECONNREFUSED and "connection refused" / "could not connect to server" errors: what they mean and how to fix them — this error's family across 44 libraries.
Related errors
AI-assisted analysis of chenhg5/cc-connect@4000b2338a (2026-09-06).
Data as JSON: /api/errors/49613523f2248018.
Report an issue: GitHub.