Files
helmfile/pkg/app/testdata/testapply/smoke/log
T
yxxheroandRoman Mykhailiuk 9d3a9ad6c7 feat: parallel kubedog tracking with progress printer and safety valves (#2654)
* feat: parallel kubedog tracking with progress printer and safety valves

Rework kubedog integration so resource tracking runs in parallel with
helm upgrade/install, giving live progress output and recovering from
known helm/kubedog wedge conditions.

Core:
- kubedogTrackingHandle runs tracking in a background goroutine alongside
  the helm subprocess (startBackgroundKubedogTracking); helm output is
  buffered and replayed as a single block so it no longer interleaves
  with progress ticks.
- Capture UID+generation baselines before handing off to helm so each
  tracker waits until the resource actually changes (freshness gate).

Progress printer (pkg/kubedog/printer.go):
- Styled, auto-sized progress table with a heartbeat flusher, child (pod)
  status roll-up, pre-ready pod-phase handling, multi-namespace support,
  and optional color. PreviewBreakdown summarizes kept/filtered resources.

Safety valves (verify cluster state via the live API):
- Tracker-race valve (always on): when helm succeeds but a dyntracker
  goroutine is wedged, poll the API and cancel the tracker so wait()
  returns success instead of blocking until --track-timeout.
- Helm-stuck killer (opt-in via helmStuckGrace): if the cluster stays
  converged while helm v4's hook waiter is wedged, SIGINT the helm
  subprocess to recover.
- Failure watchdog (pkg/kubedog/watchdog.go): surface failing pods that
  never made it into dyntracker's resource graph.

Options: trackFailedLogs, helmStuckGrace, trackTimeout, color
(Color/NoColor), and resource filtering (trackKinds/skipKinds/
trackResources). PersistentVolumeClaim support in resource classification.

Signed-off-by: Roman Mykhailiuk <romanm@cybellum.com>

* test: add unit tests for kubedog tracking

Cover the progress printer, resource classification, the failure
watchdog, helm-output trimming/dedup, the release hard-timeout helper,
and the color/track option plumbing.

Signed-off-by: Roman Mykhailiuk <romanm@cybellum.com>

* test: update golden logs, e2e snapshots, and values-id fixtures

Refresh pkg/app testapply/testdestroy golden logs, e2e template
snapshots, and the TestGenerateID values-id golden hashes for the new
kubedog progress output and the merged release struct layout.

Signed-off-by: Roman Mykhailiuk <romanm@cybellum.com>

* refactor: remove dead kubedog display code and dedupe tracker setup

Deep-review pass on the parallel kubedog tracking changes:

- Remove pkg/kubedog/display.go (308 lines) and display_test.go (453 lines).
  These rendered progress for the legacy per-kind trackers that this PR
  replaces; in the merged tree every function is unreferenced outside its
  own tests. The new progressPrinter (printer.go) supersedes them.
  TestMain (color.ForceColor for deterministic ANSI in tests) is preserved
  in a new main_test.go.
- Dedupe trackWithKubedog: the post-helm fallback rebuilt the exact same
  tracker options as buildReleaseTracker. Reuse buildReleaseTracker instead,
  dropping ~40 lines of duplicated timeout/log/filter/tracker construction.

No behavior change; build, go vet, golangci-lint, and the kubedog/state
unit tests all pass.

Signed-off-by: yxxhero <aiopsclub@163.com>

* fix: stop waitForFreshness busy-looping the API after helm finishes

Once upstreamDoneCh closes it is always ready, so the select in
waitForFreshness stopped blocking on the ticker and re-ran probe() (a
live GET) as fast as the round-trip allowed for the whole 3s grace
window — hammering the API server once per tracked resource.

Track a local view of the channel and nil it out on first delivery so
the first hit records the timestamp (one fast retry, as intended) and
all subsequent polls are ticker-throttled. Functional behavior is
unchanged: return nil when fresh, errUpstreamDoneNoChange after grace.

Signed-off-by: yxxhero <aiopsclub@163.com>

* test: drop trailing blank line from helm4 OCI pull snapshots

The trailing-newline trim in helmexec.info() removes the blank line helm
prints after the OCI chart "Digest:" line. The helm3 (output.yaml)
snapshots never captured that line, but the helm4 (output-helm4.yaml)
snapshots for oci_chart_pull{,_direct,_once,_once2} and
issue_473_oci_chart_url_fetch still expected it, so they failed under
helm 4. Remove the blank line so the snapshots match the trimmed output.

Signed-off-by: yxxhero <aiopsclub@163.com>

* test: refresh diff-args integration goldens for styled release headers

DisplayAffectedReleases now emits a styled "========== Updated Releases
==========" header (matching the app/e2e goldens already updated by this
PR) and helmexec.info() trims the trailing blank after helm's install
status. Update the diff-args apply-stderr{,-helm4} and apply-live-
stderr{,-helm4} goldens accordingly so they match the actual stderr.

Signed-off-by: yxxhero <aiopsclub@163.com>

* test: drop trimmed blank line from v1-subhelmfile template golden

The trailing-newline trim in helmexec.info() removes the blank line helm
prints after '"incubator" has been added to your repositories'. Update
the v1-subhelmfile-multi-bases-with-array-values result and result-live
goldens so the template stdout comparison matches.

Signed-off-by: yxxhero <aiopsclub@163.com>

---------

Signed-off-by: Roman Mykhailiuk <romanm@cybellum.com>
Signed-off-by: yxxhero <aiopsclub@163.com>
Co-authored-by: Roman Mykhailiuk <romanm@cybellum.com>
2026-06-21 13:43:17 +08:00

65 lines
2.7 KiB
Plaintext

merged environment: &{default map[] map[] map[]}
10 release(s) found in helmfile.yaml
Affected releases are:
anotherbackend (charts/anotherbackend) UPDATED
backend-v1 (charts/backend) DELETED
backend-v2 (charts/backend) UPDATED
database (charts/mysql) UPDATED
front-proxy (stable/envoy) UPDATED
frontend-v1 (charts/frontend) DELETED
frontend-v3 (charts/frontend) UPDATED
logging (charts/fluent-bit) UPDATED
servicemesh (charts/istio) UPDATED
invoking preapply hooks for 5 groups of releases in this order:
GROUP RELEASES
1 default//frontend-v1, default//frontend-v2, default//frontend-v3
2 default//backend-v1, default//backend-v2
3 default//anotherbackend
4 default//database, default//servicemesh
5 default//logging, default//front-proxy
invoking preapply hooks for releases in group 1/5: default//frontend-v1, default//frontend-v2, default//frontend-v3
invoking preapply hooks for releases in group 2/5: default//backend-v1, default//backend-v2
invoking preapply hooks for releases in group 3/5: default//anotherbackend
invoking preapply hooks for releases in group 4/5: default//database, default//servicemesh
invoking preapply hooks for releases in group 5/5: default//logging, default//front-proxy
processing 2 groups of releases in this order:
GROUP RELEASES
1 default//frontend-v1
2 default//backend-v1
processing releases in group 1/2: default//frontend-v1
processing releases in group 2/2: default//backend-v1
processing 5 groups of releases in this order:
GROUP RELEASES
1 default//logging, default//front-proxy
2 default//database, default//servicemesh
3 default//anotherbackend
4 default//backend-v2
5 default//frontend-v3
processing releases in group 1/5: default//logging, default//front-proxy
processing releases in group 2/5: default//database, default//servicemesh
processing releases in group 3/5: default//anotherbackend
processing releases in group 4/5: default//backend-v2
processing releases in group 5/5: default//frontend-v3
========== Updated Releases ==========
NAME NAMESPACE CHART VERSION DURATION
logging charts/fluent-bit 3.1.0 0s
front-proxy stable/envoy 3.1.0 0s
database charts/mysql 3.1.0 0s
servicemesh charts/istio 3.1.0 0s
anotherbackend charts/anotherbackend 3.1.0 0s
backend-v2 charts/backend 3.1.0 0s
frontend-v3 charts/frontend 3.1.0 0s
========== Deleted Releases ==========
NAME NAMESPACE DURATION
frontend-v1 0s
backend-v1 0s