Close the harness command client before Windows removes its state dir (#2558)

Since #2550 merged, `main`'s Windows x64 job fails three
`internal/hostagent` tests, and so does every PR whose diff triggers
that job. The check isn't required, so #2550 and later PRs merged while
it was red:

```
--- FAIL: TestObserverAckNeverReleasesOrNamesTheCommandChannel
    testing.go:1464: TempDir RemoveAll cleanup: unlinkat ...\operation-receipts.db: The process cannot access the file because it is being used by another process.
--- FAIL: TestSupersededCommandClientCannotOccupyTheRunSlot   (same)
--- FAIL: TestReplayedReportAckNeverNegotiatesTheCurrentChannel   (same)
```

**Cause:** these three tests build the command identity harness but
never call `run`. Nothing closes the command client that `New` created,
so its receipts database stays open, and Windows refuses to delete an
open file. Other platforms delete it anyway, which is why only Windows
fails.

**Change:** the harness now stops and closes the command client in a
`t.Cleanup`. That cleanup is registered after the state `TempDir`, so it
runs first. `CommandClient.Close` is idempotent, so the tests that do
`run` the agent are unaffected.

This is a test-only change. Production already closes the client when
`Run` exits or a new identity supersedes it.

**Verification:** I can't run Windows locally. On macOS, a throwaway
check (not committed) confirmed that without this change the harness's
client is still open after all the test's cleanups, and with it the
client is closed. `go test ./internal/hostagent -count=3` passes. This
PR's own Windows x64 job is the real proof.
This commit is contained in:
rcourtman
2026-10-06 10:42:03 +01:00
committed by GitHub
@@ -601,6 +601,10 @@ func newCommandIdentityHarness(t *testing.T, presentedID string, interval time.D
agent.httpClient = h.server.Client()
agent.trimmedPulseURL = h.server.URL
h.agent = agent
// Run closes the command client on exit, but several tests never call
// run. Close it here, before the state TempDir is removed: Windows cannot
// delete the open operation-receipts.db.
t.Cleanup(func() { agent.stopCommandClient(true) })
return h
}