Skip to content

fix: preserve Kubernetes watch streaming in debug mode - #215

Merged
flemzord merged 1 commit into
mainfrom
feat/remove-kubernetes-debug-transport
Sep 7, 2026
Merged

flemzord merged 1 commit into
mainfrom
feat/remove-kubernetes-debug-transport

Conversation

@flemzord

@flemzord flemzord commented Sep 7, 2026

Copy link
Copy Markdown
Member

When debug logging was enabled, the Kubernetes HTTP debug transport buffered WATCH responses until the stream closed. This delayed stack, module, and version updates reaching Membership by several minutes. Remove that transport while retaining normal Agent debug logging.

Add a regression test using the command's Kubernetes configuration and a real client-go watch against a local server that keeps the response open. It covers debug on/off, regular watches, and initial WatchList events. Include command tests in the CI unit-test target.

Validation:

  • The regression failed for both debug-enabled cases before the fix and passes after removal.
  • go test -race ./cmd/... -count=1 -v
  • nix develop --impure --command just tests-unit (lint, generation, and unit tests)

@flemzord
flemzord requested a review from a team as a code owner September 7, 2026 07:47
@flemzord
flemzord merged commit 2c5732a into main Sep 7, 2026
7 checks passed
@flemzord
flemzord deleted the feat/remove-kubernetes-debug-transport branch September 7, 2026 08:55
@shipfox-ai

shipfox-ai Bot commented Sep 18, 2026

Copy link
Copy Markdown

This PR removes the debug HTTP transport wrapping of the Kubernetes REST config (which buffered streamed watch responses and blocked Kubernetes watches until EOF in debug mode) and adds a regression test that exercises a real client-go watch against a local httptest server that keeps the response open, spanning debug on/off × regular watches × initial WatchList events, plus CI wiring for ./cmd/... in the unit-test target. I independently verified every candidate finding from both prior reviews against the diff and the actual code: the transport block and its imports are fully removed with no re-wrapping anywhere, normal agent debug logging is retained (service.IsDebug(cmd) still reaches internal.NewModule), the test defer/goroutine lifecycle is sound (no deadlocks or leaked goroutines on failure paths), and the in-cluster CI guard (t.Setenv("KUBERNETES_SERVICE_HOST", "")) correctly forces the synthetic kubeconfig. No missing, partial, or incorrect implementations were found. Recommendation: approve.

Standards

No confirmed material findings. The two style-level observations from the prior reviews (the createK8SConfig helper in cmd/root.go reading a flag and delegating to internal.NewK8SConfig, and the branch structure of the 4-way test matrix in cmd/root_test.go) were verified against the code and rejected as non-material: the helper is the load-bearing test seam required by the spec's "using the command's Kubernetes configuration" clause, and the branching follows the repo's established table-test idiom. Neither carries correctness, security, compatibility, or risky-test impact.

Spec

No missing or partial requirements, no scope creep, and no incorrect implementations. All four spec requirements are verifiably implemented:

  • Transport removal with debug logging retained (cmd/root.go:127-131, 160-166): the restConfig.Wrap(...) debug HTTP-transport block and its imports (net/http, httpclient, k8s.io/client-go/transport) are fully removed; no NewDebugHTTPTransport/httpclient references remain in the repo. Debug logging is retained via service.IsDebug(cmd) passed to internal.NewModule (cmd/root.go:142) and the --debug flag registered by service.AddFlags.
  • Regression test against a real watch with the response held open (cmd/root_test.go): the config is built through the command's own createK8SConfig(cmd) helper, a real dynamic client watches, and the httptest handler flushes the ADDED (and, for WatchList, BOOKMARK) events and then blocks on <-streamClosed until the client has consumed them — asserting events are delivered while the body remains open, which is exactly the failure mode the debug transport caused.
  • Coverage matrix: the test spans debug ∈ {false,true} × initialEvents ∈ {false,true}, asserting the sendInitialEvents=true query parameter, the BOOKMARK event with the k8s.io/initial-events-end annotation, and correct option wiring (AllowWatchBookmarks, ResourceVersionMatch).
  • CI unit-test target (Justfile:33): tests-unit now runs go test ... ./cmd/... ./internal/....

One non-defect note for the record: createK8SConfig (cmd/root.go:163-167) never reads service.DebugFlag, so the debug=true/false subtests exercise the identical code path at the config level. That is the intended post-fix behavior — the debug dimension now serves as a regression guard (a reintroduced debug transport would hang the debug=true subtests into their timeouts) rather than branch coverage. This matches the spec's "remove that transport" intent and requires no change.

Reviewed independently by GLM (glm-5.3-flash) and DeepSeek (deepseek-v4-pro-0813) via Shipfox; verified and synthesized by GLM.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Development

Successfully merging this pull request may close these issues.

1 participant