Resume sessions whose background subagents a restart killed
This commit is contained in:
@@ -35,6 +35,8 @@ const agentActor = "agent"
|
|||||||
|
|
||||||
const restartNotice = "byre restarted while you were mid-turn, so your last turn was cut off. Re-check the working tree (git status and the files you were editing) before continuing where you left off."
|
const restartNotice = "byre restarted while you were mid-turn, so your last turn was cut off. Re-check the working tree (git status and the files you were editing) before continuing where you left off."
|
||||||
|
|
||||||
|
const subagentsLostNotice = "Your agent process ended while background subagents you started were still running, so they were stopped and will never report back. Anything they found is lost; redo that work (run them again or do it yourself) and carry on where you left off."
|
||||||
|
|
||||||
var progressSubtypes = map[string]bool{"status": true, "thinking_tokens": true}
|
var progressSubtypes = map[string]bool{"status": true, "thinking_tokens": true}
|
||||||
|
|
||||||
type Manager struct {
|
type Manager struct {
|
||||||
@@ -456,11 +458,15 @@ func (m *Manager) Recover(ctx context.Context) error {
|
|||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
orphaned := []string{}
|
||||||
for _, sess := range stale {
|
for _, sess := range stale {
|
||||||
err = m.store.SetSubagents(ctx, sess.Id, 0, "byre")
|
err = m.store.SetSubagents(ctx, sess.Id, 0, "byre")
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
if sess.State == api.AgentSessionStateIdle {
|
||||||
|
orphaned = append(orphaned, sess.Id)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
sessions, err := m.store.SessionsInState(ctx, api.AgentSessionStateRunning)
|
sessions, err := m.store.SessionsInState(ctx, api.AgentSessionStateRunning)
|
||||||
@@ -488,6 +494,10 @@ func (m *Manager) Recover(ctx context.Context) error {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
for _, id := range orphaned {
|
||||||
|
m.wakeOrphaned(ctx, id)
|
||||||
|
}
|
||||||
|
|
||||||
idle, err := m.store.SessionsInState(ctx, api.AgentSessionStateIdle)
|
idle, err := m.store.SessionsInState(ctx, api.AgentSessionStateIdle)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
@@ -508,6 +518,15 @@ func (m *Manager) Recover(ctx context.Context) error {
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (m *Manager) wakeOrphaned(ctx context.Context, sessionID string) {
|
||||||
|
_, _, err := m.Message(ctx, sessionID, "byre", Prompt{Text: subagentsLostNotice})
|
||||||
|
if err != nil {
|
||||||
|
slog.Error("wake session whose subagents were stopped", "session", sessionID, "err", err)
|
||||||
|
return
|
||||||
|
}
|
||||||
|
slog.Info("woke session whose subagents were stopped", "session", sessionID)
|
||||||
|
}
|
||||||
|
|
||||||
func (m *Manager) failResume(ctx context.Context, sess api.AgentSession, err error) error {
|
func (m *Manager) failResume(ctx context.Context, sess api.AgentSession, err error) error {
|
||||||
slog.Error("resume session", "session", sess.Id, "err", err)
|
slog.Error("resume session", "session", sess.Id, "err", err)
|
||||||
if sess.Role == api.Reviewer {
|
if sess.Role == api.Reviewer {
|
||||||
@@ -982,7 +1001,8 @@ func (m *Manager) pump(l *live) {
|
|||||||
quiet := closing || l.stopping
|
quiet := closing || l.stopping
|
||||||
m.mu.Unlock()
|
m.mu.Unlock()
|
||||||
|
|
||||||
if len(l.subagents) > 0 && !closing {
|
orphaned := len(l.subagents) > 0 && !closing
|
||||||
|
if orphaned {
|
||||||
err := m.store.SetSubagents(ctx, l.id, 0, "byre")
|
err := m.store.SetSubagents(ctx, l.id, 0, "byre")
|
||||||
if err != nil {
|
if err != nil {
|
||||||
slog.Error("clear exited session's subagents", "session", l.id, "err", err)
|
slog.Error("clear exited session's subagents", "session", l.id, "err", err)
|
||||||
@@ -1000,6 +1020,10 @@ func (m *Manager) pump(l *live) {
|
|||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if sess.State == api.AgentSessionStateIdle && orphaned {
|
||||||
|
m.wakeOrphaned(ctx, l.id)
|
||||||
|
return
|
||||||
|
}
|
||||||
if sess.State != api.AgentSessionStateRunning {
|
if sess.State != api.AgentSessionStateRunning {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user