Skip to content

[architect] refactor: extract explicit poller lifecycle from registerSaaSRoutes (hub testing.Testing() removal) - #5563

Merged
kubestellar-prow[bot] merged 1 commit into
v4from
arch/refactor-poller-lifecycle
Sep 1, 2026
Merged

[architect] refactor: extract explicit poller lifecycle from registerSaaSRoutes (hub testing.Testing() removal)#5563
kubestellar-prow[bot] merged 1 commit into
v4from
arch/refactor-poller-lifecycle

Conversation

@kubestellar-hive

Copy link
Copy Markdown
Contributor

Refactor

Cluster: pkg/hub poller lifecycle / test-mode coupling — src/pkg/hub/saas.go (registerSaaSRoutes), src/pkg/hub/advisory_diagnostics.go (StartAdvisoryDiagnostics), new src/pkg/hub/background_pollers.go, src/cmd/hive/main.go (runHub only), src/pkg/hub/reach_diag_wiring_test.go. Disjoint from PR #4032 (proxy auth injection: pkg/proxy, pkg/github token source, pkg/config/proxy_inject, func main hunk at main.go:2750).

Production code in pkg/hub imported testing and branched on testing.Testing():

  • registerSaaSRoutes spawned four long-lived pollers (startProvisionWatcher, StartLatestSHAPoller, StartAuthAudit, StartAdvisoryDiagnostics) behind if !testing.Testing(), hiding a lifecycle decision inside route registration and using four detached context.Background() calls that nothing could stop.
  • StartAdvisoryDiagnostics carried a second, redundant guard; TestStartAdvisoryDiagnosticsNoopInTests asserted the anti-pattern.

What changes structurally

  • New HubServer.StartBackgroundPollers(ctx) owns poller startup; all four pollers share one caller-owned context.
  • registerSaaSRoutes is now side-effect free; both testing imports are gone from production files.
  • The composition root (runHub in cmd/hive/main.go) calls StartBackgroundPollers once before serving — production behavior unchanged.
  • TestStartAdvisoryDiagnosticsStopsOnCancel replaces the noop-assert test, asserting the new contract (pollers stop on context cancellation).

Tests still get zero background goroutines — now by construction, not test-mode detection.

Validation

  • go vet ./pkg/hub ./cmd/hive clean
  • Full go test ./pkg/hub -count=1 green (141s)

Fixes #5562


Filed by architect agent (ACMM L5 — hold-gated mode). Hold-gated: human review required.

— hive: agent=architect backend=copilot model=claude-opus-4-6

…SaaSRoutes

Production code in pkg/hub branched on testing.Testing() in two places:
registerSaaSRoutes spawned four long-lived pollers behind !testing.Testing(),
and StartAdvisoryDiagnostics carried a second redundant guard. That coupled
the production binary to the testing package and hid a lifecycle decision
inside route registration.

- New HubServer.StartBackgroundPollers(ctx) (pkg/hub/background_pollers.go)
  owns poller startup; pollers now share a caller-owned context instead of
  four detached context.Background() calls.
- registerSaaSRoutes is now side-effect free; the testing import is gone
  from saas.go and advisory_diagnostics.go.
- cmd/hive runHub (the composition root) calls StartBackgroundPollers once
  before serving, so production behavior is unchanged.
- TestStartAdvisoryDiagnosticsNoopInTests (which asserted the anti-pattern)
  is replaced by TestStartAdvisoryDiagnosticsStopsOnCancel, asserting the
  new contract: pollers stop when the root context is cancelled.

No behavior change in production; tests get no background goroutines, as
before, but now by construction rather than by test-mode detection.

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Signed-off-by: architect <architect@hive>
@kubestellar-hive kubestellar-hive Bot added the hold label Sep 1, 2026
@kubestellar-prow kubestellar-prow Bot added dco-signoff: yes Indicates the PR's author has signed the DCO. size/M Denotes a PR that changes 30-99 lines, ignoring generated files. labels Sep 1, 2026
@github-actions

github-actions Bot commented Sep 1, 2026

Copy link
Copy Markdown
Contributor

Changelog: this PR changes code but does not touch CHANGELOG.md.

If it is user-visible — a feature, a fix an operator would notice, a
security change, a migration, a deprecation, or anything breaking —
please add a line under ## Unreleased. If it is a refactor, a
test-only change, or dependency churn, no entry is needed and you can
ignore this.

This is a reminder, not a gate; it never blocks a merge.

@clubanderson clubanderson added approved Indicates a PR has been approved by an approver from all required OWNERS files. lgtm Indicates that a PR is ready to be merged. labels Sep 1, 2026
@kubestellar-prow

Copy link
Copy Markdown
Contributor

[APPROVALNOTIFIER] This PR is APPROVED

Approval requirements bypassed by manually added approval.

This pull-request has been approved by:

The full list of commands accepted by this bot can be found here.

The pull request process is described here

Details Needs approval from an approver in each of these files:

Approvers can indicate their approval by writing /approve in a comment
Approvers can cancel approval by writing /approve cancel in a comment

@clubanderson clubanderson removed the hold label Sep 1, 2026
@kubestellar-prow
kubestellar-prow Bot merged commit c8a53ce into v4 Sep 1, 2026
54 checks passed
@kubestellar-prow
kubestellar-prow Bot deleted the arch/refactor-poller-lifecycle branch September 1, 2026 19:56
@github-actions

github-actions Bot commented Sep 1, 2026

Copy link
Copy Markdown
Contributor

Thank you for your contribution! Your PR has been merged.

Check out what's new:

Stay connected: Slack #kubestellar-dev | Multi-Cluster Survey

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

Labels

approved Indicates a PR has been approved by an approver from all required OWNERS files. copilot dco-signoff: yes Indicates the PR's author has signed the DCO. lgtm Indicates that a PR is ready to be merged. size/M Denotes a PR that changes 30-99 lines, ignoring generated files.

Projects

None yet

Development

Successfully merging this pull request may close these issues.

[architect] pkg/hub production code branches on testing.Testing() — poller lifecycle hidden inside route registration

1 participant