Files
kandev/docs/plans/startup-observability-cleanup/task-03-instance-stop.md
T
2026-08-26 13:12:59 +00:00

95 lines
3.0 KiB
Markdown

---
id: "03-instance-stop"
title: "Idempotent agent instance stop"
status: done
wave: 3
depends_on:
- "02-agent-stderr-exit"
plan: "plan.md"
requirements:
- REQ-PLATFORM-AGENTCTL-INSTANCE-STOP-001
acceptance_criteria:
- AC-PLATFORM-AGENTCTL-INSTANCE-STOP-001.1
- AC-PLATFORM-AGENTCTL-INSTANCE-STOP-001.2
- AC-PLATFORM-AGENTCTL-INSTANCE-STOP-001.3
- AC-PLATFORM-AGENTCTL-INSTANCE-STOP-001.4
system_design:
- ../../specs/platform/system-design/agentctl-instance-stop.md
---
# Task 03: Idempotent agent instance stop
## Summary
Make an overlapping stop call succeed when the same instance has already been
fully removed by another stop operation. Keep unknown-instance responses and
real cleanup failures distinct.
## In scope
- Serialize and recheck the original instance pointer after `stopMu`.
- Treat removal of that same pointer as an already-satisfied stop.
- Release ports once and retain the current failure retry behavior.
- Add deterministic manager and control-boundary regression tests.
## Out of scope
- Changing the `ControlClient` lost-response retry contract.
- Changing process or HTTP-server grace periods.
- Changing instance persistence, IDs, or agent protocol behavior.
## Acceptance
- Overlapping stops for one instance do not produce a 500 solely because the
first stop removed the instance.
- Unknown IDs remain non-mutating 404 responses, and a different instance
reusing the ID is never mistaken for the original instance.
- Genuine cleanup failures remain HTTP 500/error-level and retain the instance
and port for retry; successful cleanup releases the port once.
## Verification
```bash
cd apps/backend && go test ./internal/agentctl/server/instance ./internal/agentctl/server/api -count=1
```
## Files likely touched
- `apps/backend/internal/agentctl/server/instance/manager.go`
- `apps/backend/internal/agentctl/server/instance/manager_shutdown_test.go`
- `apps/backend/internal/agentctl/server/api/control_server.go`
- `apps/backend/internal/agentctl/server/api/*_test.go`
## Dependencies
Task 02 is a prior plan wave. No data migration or external service is
required.
## Risks
- A missing map entry is only benign when it follows teardown of the exact
pointer captured before waiting; an ID reuse must remain an error.
## Parallelism
`sequential`
## Inputs
- `docs/specs/platform/requirements/agentctl-instance-stop.md`.
- `docs/specs/platform/system-design/agentctl-instance-stop.md`.
- Existing `Manager.StopInstance` failure-retention tests and
`ControlClient.DeleteInstance` 404 retry test.
## Results
Refactored stop handling so the initial instance pointer is passed through a
serialized stop operation. A pointer that was already removed by a successful
stop now returns success, while a replacement pointer still returns not found.
Added manager concurrency, port-reuse, replacement-safety, and unknown-control-
route coverage.
Verification:
- `go test ./internal/agentctl/server/instance ./internal/agentctl/server/api -count=1` passed with 463 tests.