feat(P05): drain + daemon drain-and-stop (REQ-061) + job migrate (REQ-116)

orca node drain <host>: marks draining, stops allocs via SSH, marks
drained. orca daemon drain-and-stop: stops v0.8 daemons on peers.
orca job migrate <name> --to <node>: drain+reschedule composite
(C3=a, not live-migrate). Node states: draining, drained.

---ci---
project: orca
phase: 05
milestone: v0.11
status: execute
---/ci---
This commit is contained in:
Jon Chery
2026-08-07 05:17:01 +00:00
parent f61ef2aa9e
commit 41bcf0a6bf
7 changed files with 1269 additions and 3 deletions
+18
View File
@@ -154,6 +154,24 @@ func (r *NodeRepo) Delete(ctx context.Context, id string) error {
return nil
}
// SetNodeState updates a node's state to the given string value
// (REQ-061). Unlike UpdateState, which takes a model.NodeState, this
// accepts a raw string so callers can set arbitrary states (draining,
// drained) without coupling to every constant in the model package.
func (r *NodeRepo) SetNodeState(ctx context.Context, nodeID, state string) error {
res, err := r.db.ExecContext(ctx,
`UPDATE nodes SET state = ?, last_seen = ? WHERE id = ?`,
state, time.Now().UTC(), nodeID)
if err != nil {
return fmt.Errorf("update node state: %w", err)
}
rows, _ := res.RowsAffected()
if rows == 0 {
return ErrNotFound
}
return nil
}
type scanner interface {
Scan(dest ...any) error
}