Date: July 2026 (2026-07-20)
Branch: master (commit fc69f6c85ee05636f782818b8a131be3716ee461)
Scope: hack/unwanted-dependencies.json — modules listed in spec.unwantedModules that are still present in vendor/
Prior report: June 2026 (same gist, now in gist revision history). All deltas below are measured against that report.
hack/unwanted-dependencies.json formalizes the list of Go modules the Kubernetes project wants to eliminate. It has three relevant sections:
spec.unwantedModules— the authoritative blocklist, each entry with a rationale. Now 89 entries (up from 88): the new entry isgithub.com/google/cadvisoritself — the fat cadvisor module is now blocklisted in favor of the new leangithub.com/google/cadvisor/libmodule that kubelet vendors instead.spec.pinnedModules— modules pinned below latest for a stated reason. Still two —github.com/google/cel-go→v0.27.0(#138334) andgithub.com/fsnotify/fsnotify→v1.9.0(#138812) — but the cel-go pin is on its way out: #138334 was closed 2026-05-05 (fixed upstream in cel-go v0.28.1 via cel-go#1303) and PR #140205 (pohly, open) deletes the pin and bumps to v0.29.x.status.unwantedReferences— the map of which vendored modules still pull in each unwanted module (the record of why each one cannot yet be removed).status.unwantedVendored— unwanted modules currently still invendor/.
Of the 89 unwanted modules, 80 are fully cleared. 9 remain — the same nine as May and June, but with the largest single-cycle movement yet underneath them.
Headline: The gogo/protobuf external track collapsed from 6 blockers to 2 in six weeks — a coordinated campaign (liggitt's checklist on k/k #96564, 2026-05-27) cleared ttrpc (v1.2.9 dropped gogo), typeurl and errdefs (left the vendor tree entirely), and cadvisor (replaced by the gogo-free
cadvisor/lib). What remains for gogo is one containerd/api tag plus Kubernetes' owngo-to-protobuf(KEP-5589 phase two). In the other direction, June's go-spew "✅ done upstream" framing is corrected to 🟡: an importer census shows testify was never the only gate —k8s.io/utils/dump(spew deliberately centralized there, baked into kubelet checkpoint checksums) and kustomize's kyaml stand behind it, and testify still has not released in 11 months. The SMDencoding/json/v2keystone had its dry-run import land in k/k (#140294) with Go 1.27 a month away.
| Module | Vendored version | Blocklist reason |
|---|---|---|
github.com/davecgh/go-spew |
v1.1.2-0.20180830191138-d8f796af33cc |
refer to #103942 (unmaintained) |
github.com/gogo/protobuf |
v1.3.2 |
unmaintained |
github.com/golang/protobuf |
v1.5.4 |
replace with google.golang.org/protobuf |
github.com/google/btree |
v1.1.3 |
unmaintained, archive mode |
github.com/json-iterator/go |
v1.1.12 |
refer to #105030 |
github.com/modern-go/concurrent |
v0.0.0-20180306012644-bacd9c7ef1dd |
problematic reliance on Go internals |
github.com/modern-go/reflect2 |
v1.0.3-0.20250322232337-35a7c28c31ee |
problematic reliance on Go internals |
golang.org/x/exp |
v0.0.0-20260410095643-746e56fc9e2f |
experimental/deprecated packages |
gopkg.in/yaml.v3 |
v3.0.1 |
prefer sigs.k8s.io/yaml/goyaml.v3 |
Coupling note: modern-go/concurrent and modern-go/reflect2 are pulled (almost) exclusively by github.com/json-iterator/go; they share its blockers and disappear when it does (analyzed together under json-iterator). The reflect2 pseudo-version oddity persists: k8s vendors v1.0.3-0.2025… although SMD and client_golang both declare v1.0.2.
Rationale: Unmaintained (last release v1.1.1, 2018). Tracked via #103942.
The correction: June concluded go-spew was "done upstream; gated only on a testify release." An importer census over vendor/ shows that was incomplete: the vendored source importers are testify (assert, mock), k8s.io/utils/dump, and sigs.k8s.io/kustomize/kyaml/yaml — and the same four existed in June (newly identified, not newly introduced). A testify release alone does not clear go-spew from the tree.
Upstream status:
- testify — still no release. Latest remains v1.11.1 (2025-08-27, 11 months ago);
masterstill has go-spew removed (June's internal-vendoring commit39877525holds; master's go.mod requires onlyobjx v0.5.3+yaml.v3 v3.0.1). No release-prep signal (last master merge 2026-06-10). k8s.io/utils/dump— spew is there on purpose. kubernetes/utils#343 (merged 2026-02-10) moveddumpfrom apimachinery to utils explicitly to centralize go-spew usage. ~50 k/k files import it, including production paths:pkg/util/hashDeepHashObject, kubelet cpu/memory-manager checkpoint checksums, kubeadm, client-go's retrywatcher. Because spew's output format is baked into persisted checksums, replacement is compatibility-sensitive. Zero removal issues/PRs exist in kubernetes/utils. The hash-safe option is testify-style internal vendoring of spew.- kustomize kyaml — fixed on master, unreleased. kustomize#6134 (merged 2026-05-01) removed the direct spew use in
fns.go; no tag contains it (newest kyaml tag v0.21.1, 2026-02-09 — exactly what k8s vendors). - Spot-checks: etcd v3.7.0 GA, kube-openapi
bc653b64f974, prometheus/common v0.67.5 all still pin testify v1.11.1 (spew + yaml.v3// indirect).
Prognosis: 🟡 Three sequential gates, none passed this cycle: (1) a testify release + tail bumps, (2) a kustomize/kyaml tag + k8s bump, (3) a k8s-owned decision on utils/dump — for which nothing is filed. The last gate is entirely in-project.
Rationale: Unmaintained fork of the Go protobuf API.
Blocker-list evolution since June (from the JSON at each k/k commit): 6 → 5 (#139594 typeurl v2.3.0 bump, liggitt, 2026-06-09) → 4 (#139870 kubelet→cadvisor/lib migration, dims, merged 2026-06-25 — also evicted typeurl and errdefs from the vendor tree entirely) → 3 (#140337 ttrpc v1.2.9, 2026-07-09) → 2 (#140385 cadvisor/lib v0.60.4, 2026-07-10). Remaining: github.com/containerd/containerd/api and k8s.io/code-generator.
Upstream status:
- ttrpc — RESOLVED at v1.2.9 (released 2026-07-08): v1.2.8 had gogo direct, v1.2.9 has none. Mechanism: runtime/wire usage was removed back in 2022 (PR #99); the remaining codegen path went via #226 (protobuild→buf, 2026-03-23) enabling ttrpc#239 ("Remove gogo vanity command and gogo dependency", liggitt, merged 2026-06-09). June-report correction: no "new major version" was needed — a patch release sufficed. Stale issue ttrpc#97 is still open and now obsolete; worth asking containerd to close it.
- typeurl — RESOLVED and gone. June-report correction: removal was not "structurally hard" — typeurl#51 (gogo removal) had been merged since 2024-11-05 and sat unreleased ~18 months until v2.3.0 was tagged (2026-05-27). k/k bumped (#139594), then #139870 removed typeurl (and errdefs) from the tree altogether.
- cadvisor — RESOLVED via the lib split. google/cadvisor#3895 (dims, merged 2026-06-20) introduced
github.com/google/cadvisor/lib, a lean kubelet-focused module whose go.mod carries zero gogo (the old v0.57.0 module had gogo indirect plus ttrpc v1.2.8/typeurl/errdefs). Follow-ups: #3902 (OOM watcher out of lib), #3914 (merged 2026-07-13 — release tags now auto-mirror tolib/tags, fixing the missing-lib-tag gap). k/k adopted through #139870 → #140026 → #140385 (lib v0.60.4). - containerd/api v1.11.1 — graph-only residue. gogo is
// indirectpurely via its ttrpc v1.2.5 and typeurl/v2 v2.1.1 requirements; its vendored generated code does not import gogo. containerd main's api go.mod is already gogo-free (#13490 merged 2026-05-28, #13740 merged 2026-07-12). Gate: no api tag after v1.11.1 yet — the next tag plus a routine k/k bump clears it with zero engineering. - k8s.io/code-generator — the last source importer. 4 files under
staging/src/k8s.io/code-generator/cmd/go-to-protobuf/still import gogo directly (the only staging go.mod with gogo). Vehicle: KEP-5589 (open, milestone v1.38) — phase one (runtime removal, v1.35) and the ProtoMessage removal (v1.36) are done (#134228, #134256, #137084); phase two (generation-time) is not — the fork POC #134530 closed unmerged 2026-04-18 and liggitt marked the approach "still TBD" (2026-05-21).
Net: a source grep of vendor/ confirms code-generator is now the only importer keeping gogo vendored; containerd/api keeps it in the require graph only.
Prognosis: 🟡 From "multi-year" to two well-defined items: wait for a containerd/api tag (mechanical), and do KEP-5589 phase two (the single piece of real engineering left, fully in-tree).
Rationale: Legacy v1 protobuf API; since v1.5.0 a shim over google.golang.org/protobuf.
Blockers: 8 (was 9) — konnectivity-client left the list.
Upstream status:
- konnectivity-client — CLEARED. v0.34.0 had the shim
// indirect; v0.36.0 has no entry. Mechanism: apiserver-network-proxy #824 (merged 2026-05-01) bumped client_golang v1.11.1→v1.22.0, dropping the shim edge; k/k consumed via #139636 (merged 2026-06-11, includes commitf9a4b842c42"Removing konnectivity-client from exception list"). - grpc-go — the immovable root. v1.82.1 (latest, 2026-07-15) and master both require the shim direct. Policy unchanged: #8940 closed 2026-03-06 ("as long as we are on grpc major version 1 … we cannot remove this dependency"); nothing newer found. (k/k #140740, bumping to v1.82.1 for its security content, is open — no shim impact.)
- etcd v3.7.0 GA — shim retained by design. Direct in api/client/server go.mods and on main; umbrella issue etcd#14533 ("cleanup both golang/protobuf and gogo/protobuf") closed COMPLETED 2026-05-29 with the shim kept; no successor issue. Four vendored etcd files import the shim.
- ttrpc — done on main, awaiting a tag. v1.2.9 kept the shim direct, but ttrpc#248 removed it on main — merged 2026-07-09, about five hours after v1.2.9 was published. The next ttrpc tag takes the list 8→7 (same tag-ask as the gogo item above).
- CSI spec — done on master, partially released. v1.9.0 (vendored) has it direct and its vendored
csi.pb.goimports the shim; v1.12.0 (latest) demotes it to// indirect; master removed it entirely (#602, 2026-04-29). A bump to v1.12.0 removes the vendored import but (by konnectivity/middleware precedent) an indirect entry still counts as a graph edge — full clearing needs an unreleased v1.13.0. - go-grpc-middleware/providers/prometheus — still v1.1.0/
// indirect, and main still carries it; a new release wouldn't clear it. - google.golang.org/protobuf pseudo-version — k/k still pins
v1.36.12-0.20260120151049-f2248ac996af(#137451: Go 1.26 broke dead-code elimination → binary-size explosion; the pinned commit has the fix). The needed v1.36.12 tag still does not exist (proxy @latest v1.36.11, 2025-12-12); the release request golang/protobuf#1711 (dims, 2026-04-21, re-pinged 06-12) has no maintainer reply. It stays listed because protobuf-go's own go.mod requires the shim (compat-test cycle); June's "target module, not a true blocker" framing holds.
Physical imports in vendor/: only gogo/protobuf's own code (11 files), etcd (4), and CSI v1.9.0 (1) import the shim; grpc and ttrpc are go.mod-edge-only.
Prognosis: 🔴 Blocked indefinitely by grpc-go's v1.x policy; realistic floor is 6 entries (grpc, etcd ×3, middleware, protobuf-go). Near-term achievable: 8→7 via a ttrpc tag, possibly →6 via CSI depending on how the verifier counts indirect edges.
Rationale: Unmaintained, archived. K8s already vendors the replacement (k8s.io/utils/third_party/forked/golang/btree — June's report said internal/btree; corrected).
Current state (all re-verified, all unchanged): sole vendored importer is still vendor/github.com/peterbourgon/diskv/index.go; client-go's discovery disk cache still constructs diskv.Options without an Index (staging/src/k8s.io/client-go/discovery/cached/disk/round_tripper.go:40-45), so the btree path remains dead weight; status.unwantedReferences still has no btree key at all (deleted by the etcd-bump JSON update 30794a7a71f on 2026-06-01; "diskv" appears nowhere in the JSON) — the stale-JSON problem June flagged is still unfixed.
Movement since June: only the close-out — etcd v3.7.0 GA vendored (#140333, merged 2026-07-08) and its GA server/go.mod verified btree-free. Nothing on the two June action items (fix the JSON; patch/replace diskv). All 2026-06+ k/k "btree" PRs (#139467, #139528, #139557, #139658) are apiserver watch-cache work on the utils btree — unrelated. diskv upstream remains dormant (last push 2021-11-10); btree remains archived. diskv /v3 still requires btree, so upgrading diskv does not help.
Prognosis: 🟡 Needs k8s-side action; none taken. Both fixes are fully in-project: record diskv as the go.mod-invisible referencer, and patch/fork diskv's index.go to the utils btree (or drop diskv from the discovery cache).
Rationale: Alternative JSON stack using unsafe reflection; #105030. The modern-go pair are pure satellites.
Blockers unchanged: prometheus/client_golang (v1.23.2 vendored) and sigs.k8s.io/structured-merge-diff/v6 (v6.4.2, was v6.4.0).
Upstream status:
- SMD — every June precondition executed except the merge itself. PR #292 ("Migrate to encoding/json/v2") is still open, needs-rebase (went lifecycle/rotten 2026-06-19; jpbetz de-rottened it the same day). Verified via the files API: it removes jsoniter and both modern-go modules from SMD's go.mod and rewrites exactly the three files k8s vendors. The v6.4.0→v6.4.2 delta (19 commits; prereqs #324/#328, converter #326, July nullable fixes) does not touch jsoniter or go.mod.
- The dry-run import happened: k/k #140294 (merged 2026-07-08; cherry-pick #140296 on 07-18) brought SMD HEAD → v6.4.2 into k/k — June's "liggitt proposed" item is done. Prereq test coverage completed early (jpbetz, 2026-05-27; June projected "~July").
- Go 1.27 timeline firmed up:
encoding/json/v2(golang/go#71497) is closed into the Go 1.27 milestone with release notes merged and aGOEXPERIMENT=nojsonv2opt-out. Go 1.27 ships ~Aug 2026 → plan of record remains #292 merge ~Aug → k8s 1.38. - client_golang — laggard with a new asterisk. v1.24.0 released today (2026-07-20); jsoniter still direct there and on main (
api/prometheus/v1/api.go). Zero removal activity — but new issue #1998 (bwplotka, May, active July) floats an OpenAPI-generated HTTP client possibly in a separate module (refs the #1649 module split); not a removal effort, but a split would evict jsoniter from the root module k8s requires. (k/k's v1.24.0 bump is imminent — after the rc dry-run #140680, closed today in favor of the final, dims gave the go-ahead to ship v1.24.0.) - Vendoring nuance (new this cycle): the only vendored source importers of jsoniter are three SMD files; client_golang's
api/tree is not vendored at all. So SMD is the sole source-level blocker; client_golang is go.mod residue. Once #292 lands and is vendored, jsoniter + modern-go source leavesvendor/entirely, with only require-graph entries left (the tooling PR to distinguish those two states, k/k #136748, was closed unmerged).
Prognosis: 🟡 Holding, with the keystone one rebase-and-merge away. Expect source-level clearance around k8s 1.38 if #292 lands on plan (slip past the Nov freeze → 1.39); full go.mod eradication still waits on Prometheus.
Rationale: Experimental/deprecated subrepo; only x/exp/slices is vendored (in stdlib since Go 1.21).
Blockers unchanged: antlr4-go/antlr/v4 v4.13.1 (direct root — one slices.EqualFunc call in lexer_action_executor.go, the sole vendored importer; no first-party k8s import), cel-go (indirect via antlr), go-grpc-middleware/v2 v2.3.3 (indirect).
Upstream status:
- antlr mirror — frozen; the May signal decayed. jimidle's 2026-05-19 "updates coming in the next two weekends" produced nothing in two months — no tag, commit, or go.mod change since v4.13.1 (2024-05-15). The repo is attended (PRs #16/#17 were closed unmerged, silently, on 2026-06-09), yet nothing ships. In the source repo, antlr/antlr4#4688 (the stdlib-slices swap) is still open (last activity: skitt's ping, 2026-04-23), #4294 likewise;
runtime/Gostill requires 2023-era x/exp. - cel-go v0.29.2 (2026-07-08; repo moved to the
cel-exprGitHub org, module path unchanged) — still requires antlr v4.13.1, so x/exp-neutral. - The k8s pin is being removed: #138334 closed 2026-05-05 (fixed in cel-go v0.28.1); PR #140205 (pohly, open) deletes the cel-go pin and bumps to v0.29.x (needs a retarget to v0.29.2 + rebase). Doesn't change x/exp either way.
- Vendored x/exp pseudo-version unchanged since June (
…20260410); upstream HEAD drift only.
Prognosis: 🟡 Unchanged, with the upstream signal now negative. Options remain: keep nudging #4688, fork/replace antlr's single slices.EqualFunc call (the replace-directive fork pattern is already demonstrated in #4688's thread), or accept the dep.
Rationale: go-yaml v3 archived 2025-04-01; prefer sigs.k8s.io/yaml/goyaml.v3.
Upstream status:
- Vendor-tree source importer census: exactly one file —
vendor/github.com/stretchr/testify/assert/yaml/yaml_default.go. testify is genuinely the only gate (unlike go-spew). - testify master AND v1.11.1 still require
yaml.v3 v3.0.1direct. PR #1772 (swap togo.yaml.in/yaml/v3) is still open: rebased 2026-05-06 at dolmen's request, then 2.5 months of maintainer silence despite community pings through July (including DataDog's dd-trace-go). Two gates — merge #1772, then cut a release — and neither moved this cycle. - The replacement is fully staged in-tree:
go.yaml.in/yamlv2.4.4 + v3.0.4 already vendored; kyaml and kube-openapi already use go.yaml.in directly.
Prognosis: 🟡 Steady-negative. When testify does merge + release, yaml.v3 clears for the whole ~35-module tail in the same release that drops go-spew from testify itself.
| Module | Key blocker(s) | Status | Prognosis | Δ since June |
|---|---|---|---|---|
github.com/davecgh/go-spew |
testify (release), kustomize/kyaml (tag), k8s.io/utils/dump (nothing filed) | 3 sequential gates; census corrected June's "testify-only" framing | 🟡 | ✅ → 🟡 correction |
github.com/gogo/protobuf |
containerd/api (awaiting tag), k8s code-generator (KEP-5589 ph. 2) |
4 of 6 blockers cleared in 6 weeks (ttrpc, typeurl, errdefs, cadvisor) | 🟡 | 🔴 → 🟡 major |
github.com/golang/protobuf |
grpc-go v1.x policy (+ etcd by design) | konnectivity cleared; ttrpc/CSI done-on-main unreleased | 🔴 floor 6 | edges 9→8, root unchanged |
github.com/google/btree |
peterbourgon/diskv (go.mod-invisible) |
JSON still stale; no k8s action on June items | 🟡 | none (etcd GA close-out only) |
github.com/json-iterator/go |
SMD #292 (sole source blocker), client_golang (go.mod-only) | dry-run import landed; json/v2 in Go 1.27 (~Aug) | 🟡 | keystone on final approach |
github.com/modern-go/concurrent |
(coupled to json-iterator) | resolves with SMD #292 | 🟡 | follows json-iterator |
github.com/modern-go/reflect2 |
(coupled to json-iterator) | resolves with SMD #292 | 🟡 | follows json-iterator |
golang.org/x/exp |
antlr4-go/antlr (frozen mirror) | maintainer promise expired; cel-go unpin in flight (#140205) | 🟡 | signal decayed |
gopkg.in/yaml.v3 |
testify #1772 + release | maintainer silent 2.5 months | 🟡 | steady-negative |
Scorecard: 0 ✅ / 8 🟡 / 1 🔴 (June: 1 ✅ / 6 🟡 / 2 🔴 — the ✅ loss is a correction, the 🔴 loss is a genuine upgrade).
- Fix the stale
unwanted-dependencies.jsonfor btree — carried over from June, still undone. Recordgithub.com/peterbourgon/diskvas the go.mod-invisible referencer; today the file implies btree is removable, which is wrong. - Ask containerd for two tags: a containerd/api tag past #13490/#13740 (clears gogo's last external blocker) and a ttrpc tag past #248 (clears golang/protobuf 8→7). Also ask them to close the obsolete ttrpc#97.
- Nudge dolmen on testify #1772 and a v1.12 release. One merge + one tag clears yaml.v3's only gate and ships testify's go-spew removal to the entire ~35-module tail. The PR has been rebase-ready since 2026-05-06.
- Ask kustomize to tag kyaml past #6134 (spew removal), then bump k/k's kustomize/kyaml.
- File the missing kubernetes/utils issue for
dump's spew dependency — the final go-spew gate is entirely k8s-owned and currently untracked. spew's output format is baked into kubelet checkpoint checksums andDeepHashObjecthashes, so the safe path is testify-style internal vendoring rather than a behavioral swap. - Drive SMD #292 to merge: it needs a rebase and a decision window before the k8s 1.38 freeze; everything else (prereqs, dry-run import, Go 1.27) is in place. This single merge removes the last source-level use of json-iterator + both modern-go modules.
- Land #140205 (cel-go unpin, retargeted to v0.29.2) to shrink
pinnedModulesback to one. - btree/diskv: patch or fork diskv's
index.goontok8s.io/utils/third_party/forked/golang/btree, or replace diskv in the discovery disk cache. - KEP-5589 phase two (go-to-protobuf without gogo) — the last real engineering item for gogo; approach still TBD per liggitt (2026-05-21).
- Ping golang/protobuf#1711 again for the v1.36.12 tag so k/k can drop its protobuf pseudo-version pin (#137451).
- grpc-go / golang/protobuf: carry indefinitely on grpc v1.x; the floor is 6 entries. Re-check only if a grpc v2 ever materializes.
- antlr x/exp: keep nudging antlr/antlr4#4688; if the mirror stays frozen through another cycle, evaluate the fork/replace-directive route for the single
slices.EqualFunccall. - prometheus/client_golang jsoniter: watch #1998/#1649 — a module split would clear the require-graph edge without upstream ever "removing" jsoniter.
- gogo/protobuf blockers 6 → 2 (🔴 → 🟡): ttrpc v1.2.9 dropped gogo (#239); typeurl v2.3.0 + errdefs left the vendor tree entirely; cadvisor replaced by the gogo-free
cadvisor/lib(#3895, dims). k/k chain: #139594 → #139870 → #140337 → #140385. Corrections to June: typeurl's fix had been merged upstream since 2024 (not "structurally hard"); ttrpc needed no major version. - go-spew ✅ → 🟡 (correction): importer census surfaced
k8s.io/utils/dump(spew centralized there deliberately in utils#343; checkpoint/hash-compat-sensitive; no removal issue exists) and kustomize kyaml (fixed on master via #6134, unreleased) alongside testify — which itself has now gone 11 months without a release. - golang/protobuf blockers 9 → 8: konnectivity-client v0.36.0 cleared it (ANP#824 → k/k #139636). ttrpc dropped the shim on main five hours after v1.2.9 tagged (#248); CSI master removed it in April (#602); etcd closed its cleanup umbrella (#14533) explicitly keeping the shim.
- SMD keystone advanced: dry-run import of SMD HEAD landed (k/k #140294, v6.4.2 vendored); prereq coverage done early;
encoding/json/v2closed into Go 1.27 (~Aug 2026) withGOEXPERIMENT=nojsonv2opt-out; #292 itself still open (needs-rebase, rescued from lifecycle/rotten on 2026-06-19). - client_golang v1.24.0 released 2026-07-20 — jsoniter unchanged; new module-split discussion (#1998) is the first, faint pathway. k/k bump imminent.
- antlr signal decayed: jimidle's May "two weekends" promise produced nothing in two months; mirror PRs closed silently in June; #4688 still open.
- cel-go: v0.29.2 out; repo moved to the
cel-exprorg; k/k pin issue #138334 closed (2026-05-05, pre-dated the June report but went unnoted there) and unpin PR #140205 is open. - etcd v3.7.0 GA vendored (#140333) — closes June's rc.0 caveats on both the btree and gogo/golang-protobuf entries.
- Blocklist 88 → 89:
github.com/google/cadvisoritself added (superseded bycadvisor/lib, whose release tags now auto-mirror tolib/tags via cadvisor#3914). - btree: June's two action items — fix the stale JSON, patch/replace diskv — saw zero movement; carried forward as Immediate #1.
- Version bumps in the blocker set: ttrpc v1.2.8→v1.2.9, containerd/api v1.11.0→v1.11.1, cadvisor v0.57.0→cadvisor/lib v0.60.4, etcd rc.0→v3.7.0, SMD v6.4.0→v6.4.2, kube-openapi 0519→0618 commit, konnectivity v0.34.0→v0.36.0; typeurl/errdefs/cadvisor(fat) left the tree. Path correction from June: the in-tree btree replacement is
k8s.io/utils/third_party/forked/golang/btree.
All data collected 2026-07-20 against master @ fc69f6c85ee (a detached worktree at upstream/master). go.mod claims verified by fetching the file at the exact tag/branch via raw.githubusercontent.com; releases/issues/PRs via gh; upstream research parallelized across six per-module groups, then cross-verified. Commands:
# Step 1 — unwanted modules still vendored (exact match)
python3 -c "
import json, re
data = json.load(open('hack/unwanted-dependencies.json'))
unwanted = set(data['spec']['unwantedModules'].keys())
vendored = {}
for line in open('vendor/modules.txt'):
m = re.match(r'^# (\S+) (\S+)', line)
if m: vendored[m.group(1)] = m.group(2)
for mod in sorted(set(unwanted) & set(vendored)):
print(mod, vendored[mod], '=>', data['spec']['unwantedModules'][mod])
"
# Step 2 — who pulls each one in (per the JSON)
python3 -c "
import json
data = json.load(open('hack/unwanted-dependencies.json'))
for mod, refs in data['status']['unwantedReferences'].items():
print(mod, len(refs)); [print(' ', r) for r in refs]
"
# Step 2b — TRUE source importers (catches go.mod-invisible blockers like diskv,
# and separates source-level from require-graph-only blockers like client_golang)
grep -rl '"<unwanted-module>' vendor/ --include='*.go' | grep -v 'vendor/<unwanted-module>/'
# Step 2c — diff the JSON + blocker versions against the previous report's commit
git show <prev-commit>:hack/unwanted-dependencies.json # compare spec/status in python
git show <prev-commit>:vendor/modules.txt | grep '^# <blocker> '
# Steps 3-6 — vendor versions; go.mod at vendored tag / main / latest release
grep '^# ' vendor/modules.txt | grep -E '<blockers>'
curl -s "https://raw.githubusercontent.com/<org>/<repo>/<tag-or-branch>/<path>/go.mod" | grep '<unwanted>'
gh api repos/<org>/<repo>/releases --jq '.[].tag_name,.published_at' | head
git ls-remote --tags https://github.com/<org>/<repo>
# Step 7 — issue/PR archaeology (fetch real state + dates; don't trust search snippets)
gh search prs --repo <org>/<repo> "<short-name>" --limit 8 --json number,title,state,url
gh search issues --repo <org>/<repo> "<short-name>" --limit 8 --json number,title,state,url
gh pr view <n> --repo <org>/<repo> --json title,state,updatedAt,mergedAt,comments
gh issue view <n> --repo <org>/<repo> --json title,state,closedAt,updatedAtEvery go.mod claim was verified at the exact tag/branch; every "no movement" claim is corroborated by both empty searches and unchanged go.mod/source state; blocker-list evolution was reconstructed from the JSON at each k/k merge commit. The compiled report was then independently re-verified end-to-end before publication: ~120 transcribed claims cross-checked against the group research logs, 44 live API spot-checks of the load-bearing facts, all 25 GitHub link targets resolved, and the importer censuses reproduced against the worktree.
The prompt that regenerates this analysis lives in the same gist as k8s-unwanted-deps-prompt.md:
https://gist.github.com/dims/c8dd44ba82ed51dfc242b065a6ff2284
Run it from the root of a current Kubernetes checkout. It produces ~/notes/k8s-unwanted-deps-<YYYY-MM>.md; the gist keeps only the latest report plus the prompt (older reports live in the gist's revision history).