fix: improve kiro-cli state detection and add Refresh method
- IsBusy now checks /proc/PID/stat for process state (R/D = busy) when no child processes exist, fixing false idle detection - Add Refresh() to Session interface to re-detect state on demand
This commit is contained in:
parent
1656ff6a6b
commit
e28d39aab6
|
|
@ -31,6 +31,9 @@ type Session interface {
|
|||
// State returns current state ("starting", "idle", "running", "error: ...", "exited")
|
||||
State() string
|
||||
|
||||
// Refresh retries startup if in error state, or refreshes state detection
|
||||
Refresh(ctx context.Context) error
|
||||
|
||||
// Send sends a prompt and returns the response
|
||||
// Blocks until response is complete
|
||||
Send(ctx context.Context, prompt string) (string, error)
|
||||
|
|
|
|||
|
|
@ -475,3 +475,23 @@ func (s *Session) Close() error {
|
|||
s.state = "exited"
|
||||
return nil
|
||||
}
|
||||
|
||||
// Refresh re-detects state based on process activity
|
||||
func (s *Session) Refresh(ctx context.Context) error {
|
||||
s.mu.Lock()
|
||||
defer s.mu.Unlock()
|
||||
|
||||
if s.state == "exited" {
|
||||
return nil
|
||||
}
|
||||
|
||||
// Check if process is busy
|
||||
busy := s.stateInspector != nil && s.stateInspector.IsBusy(s.pid)
|
||||
if busy {
|
||||
s.state = "running"
|
||||
} else {
|
||||
s.state = "idle"
|
||||
}
|
||||
debug.Log("[session %s] refresh: state=%s", s.id, s.state)
|
||||
return nil
|
||||
}
|
||||
|
|
|
|||
|
|
@ -46,7 +46,27 @@ func (i *kiroStateInspector) IsBusy(panePID int) bool {
|
|||
}
|
||||
// Check if kiro-cli-chat has any children (tool executions)
|
||||
cmd := exec.Command("pgrep", "-P", fmt.Sprintf("%d", chatPID))
|
||||
return cmd.Run() == nil
|
||||
if cmd.Run() == nil {
|
||||
return true // has children = busy
|
||||
}
|
||||
// No children - check if process is actively running (not sleeping waiting for input)
|
||||
return isProcessActive(chatPID)
|
||||
}
|
||||
|
||||
// isProcessActive checks if a process is doing work (not blocked waiting for input)
|
||||
func isProcessActive(pid int) bool {
|
||||
data, err := os.ReadFile(fmt.Sprintf("/proc/%d/stat", pid))
|
||||
if err != nil {
|
||||
return false
|
||||
}
|
||||
fields := strings.Fields(string(data))
|
||||
if len(fields) < 3 {
|
||||
return false
|
||||
}
|
||||
state := fields[2]
|
||||
// R = running, D = disk sleep (I/O), both indicate active work
|
||||
// S = interruptible sleep (waiting for input) = idle
|
||||
return state == "R" || state == "D"
|
||||
}
|
||||
|
||||
// kiroCommands implements command handling for kiro-cli
|
||||
|
|
|
|||
Reference in New Issue