feat: implement server-wide management actions and enhance TUI dashboard

This commit is contained in:
2026-03-04 20:51:02 +00:00
parent 150f9d2990
commit ddec55871b
13 changed files with 621 additions and 52 deletions
+127 -7
View File
@@ -44,6 +44,18 @@ func (a *Adapter) RunIntent(intent puretui.Intent) tea.Cmd {
case puretui.IntentLoadLogs:
return a.loadLogs(intent.AgentID)
case puretui.IntentStartAll:
return a.startAll()
case puretui.IntentStopAll:
return a.stopAll()
case puretui.IntentRestartAll:
return a.restartAll()
case puretui.IntentKillAll:
return a.killAll()
case puretui.IntentTick:
return a.tick()
@@ -65,13 +77,14 @@ func (a *Adapter) loadAgents() tea.Cmd {
views := make([]puretui.AgentView, len(statuses))
for i, s := range statuses {
v := puretui.AgentView{
ID: s.ID,
Name: s.Name,
Version: s.Version,
Desc: s.Desc,
Enabled: s.Enabled,
Running: s.Running,
PID: s.PID,
ID: s.ID,
Name: s.Name,
Version: s.Version,
Desc: s.Desc,
Enabled: s.Enabled,
Running: s.Running,
PID: s.PID,
Instances: a.mgr.InstanceCount(s.ID),
}
if s.Running {
@@ -147,6 +160,113 @@ func (a *Adapter) restartAgent(id string) tea.Cmd {
}
}
func (a *Adapter) startAll() tea.Cmd {
return func() tea.Msg {
agents, err := a.mgr.Scan()
if err != nil {
return puretui.MsgServerActionDone{Action: "Start All", Errors: []string{err.Error()}, Failed: 1}
}
var total, failed int
var errs []string
for _, agent := range agents {
if !agent.Enabled {
continue
}
if a.mgr.IsRunning(agent.ID) {
continue
}
total++
if err := a.mgr.Start(agent); err != nil {
failed++
errs = append(errs, fmt.Sprintf("%s: %v", agent.ID, err))
}
}
if total > 0 {
time.Sleep(500 * time.Millisecond)
}
return puretui.MsgServerActionDone{Action: "Start All", Total: total, Failed: failed, Errors: errs}
}
}
func (a *Adapter) stopAll() tea.Cmd {
return func() tea.Msg {
statuses, err := a.mgr.StatusAll()
if err != nil {
return puretui.MsgServerActionDone{Action: "Stop All", Errors: []string{err.Error()}, Failed: 1}
}
var total, failed int
var errs []string
for _, s := range statuses {
if !s.Running {
continue
}
total++
if err := a.mgr.Stop(s.ID); err != nil {
failed++
errs = append(errs, fmt.Sprintf("%s: %v", s.ID, err))
}
}
return puretui.MsgServerActionDone{Action: "Stop All", Total: total, Failed: failed, Errors: errs}
}
}
func (a *Adapter) restartAll() tea.Cmd {
return func() tea.Msg {
agents, err := a.mgr.Scan()
if err != nil {
return puretui.MsgServerActionDone{Action: "Restart All", Errors: []string{err.Error()}, Failed: 1}
}
// Stop all running first
for _, agent := range agents {
if agent.Enabled && a.mgr.IsRunning(agent.ID) {
_ = a.mgr.Stop(agent.ID)
}
}
time.Sleep(300 * time.Millisecond)
// Start all enabled
var total, failed int
var errs []string
for _, agent := range agents {
if !agent.Enabled {
continue
}
total++
if err := a.mgr.Start(agent); err != nil {
failed++
errs = append(errs, fmt.Sprintf("%s: %v", agent.ID, err))
}
}
if total > 0 {
time.Sleep(500 * time.Millisecond)
}
return puretui.MsgServerActionDone{Action: "Restart All", Total: total, Failed: failed, Errors: errs}
}
}
func (a *Adapter) killAll() tea.Cmd {
return func() tea.Msg {
statuses, err := a.mgr.StatusAll()
if err != nil {
return puretui.MsgServerActionDone{Action: "Kill All", Errors: []string{err.Error()}, Failed: 1}
}
var total, failed int
var errs []string
for _, s := range statuses {
if !s.Running {
continue
}
total++
if err := a.mgr.Kill(s.ID); err != nil {
failed++
errs = append(errs, fmt.Sprintf("%s: %v", s.ID, err))
}
}
return puretui.MsgServerActionDone{Action: "Kill All", Total: total, Failed: failed, Errors: errs}
}
}
func (a *Adapter) loadLogs(id string) tea.Cmd {
return func() tea.Msg {
lines, err := a.mgr.LogTail(id, 100)