Compare commits

...
Author SHA1 Message Date
Renovate Botanddanijel.simeunovic a273c279d4 chore(deps): update helm release opencost to v2
AI Code Review / ai-review (pull_request) Successful in 5s
scan.yaml / test (pull_request) Successful in 4s
2026-09-30 08:36:20 +00:00
danijel.simeunovic 407b06831f bump submodule
scan.yaml / test (push) Successful in 14s
2026-09-30 10:35:10 +02:00
danijel.simeunovic 3b8ec25c43 bump submodule
scan.yaml / test (push) Successful in 1m22s
2026-09-30 10:26:18 +02:00
danijel.simeunovic 3358950b34 format error
scan.yaml / test (push) Successful in 16s
2026-09-30 08:01:32 +00:00
danijel.simeunovic b2db9cd909 review with sonnet 5.5
scan.yaml / test (push) Successful in 18s
2026-09-30 08:00:59 +00:00
4d406c0223 chore(deps): update dependency kubernetes-helm to v4 (#48)
scan.yaml / test (push) Successful in 11s
This PR contains the following updates:

| Package | Update | Change |
|---|---|---|
| [kubernetes-helm](https://github.com/helm/helm) | major | `3.20.2` → `4.2.4` |

---

### Release Notes

<details>
<summary>helm/helm (kubernetes-helm)</summary>

### [`v4.2.4`](https://github.com/helm/helm/releases/tag/v4.2.4): Helm v4.2.4

Helm v4.2.4 is a patch release. Users are encouraged to upgrade for the best experience.

The community keeps growing, and we'd love to see you there!

- Join the discussion in [Kubernetes Slack](https://kubernetes.slack.com):
  - for questions and just to hang out
  - for discussing PRs, code, and bugs
- Hang out at the Public Developer Call: Thursday, 9:30 Pacific via [Zoom](https://zoom-lfx.platform.linuxfoundation.org/meeting/91295593969?password=17825db5-c698-44cc-9f00-ef1f61f5d3fb)
- Test, debug, and contribute charts: [ArtifactHub/packages](https://artifacthub.io/packages/search?kind=0)

#### Notable Changes

- fix: Improve error reporting for helm template --debug with --show-only- [#&#8203;31185](https://github.com/helm/helm/issues/31185) by [@&#8203;kyokuping](https://github.com/kyokuping)
- fix: fetch logs from all containers in test pods- [#&#8203;32099](https://github.com/helm/helm/issues/32099) by [@&#8203;SebTardif](https://github.com/SebTardif)
- fix(provenance): check error return in Digest and encodeRelease- [#&#8203;32136](https://github.com/helm/helm/issues/32136) by [@&#8203;SebTardif](https://github.com/SebTardif)
- fix panic on repeated IsReachable calls- [#&#8203;32184](https://github.com/helm/helm/issues/32184) by [@&#8203;atkrad](https://github.com/atkrad)
- fix: set \[pull,push] scope when helm push to a registry(use token auth) - v4- [#&#8203;31211](https://github.com/helm/helm/issues/31211) by [@&#8203;kimsungmin1](https://github.com/kimsungmin1)
- Fix missing conflict retry with server-side apply- [#&#8203;32088](https://github.com/helm/helm/issues/32088) by [@&#8203;Kajot-dev](https://github.com/Kajot-dev)
- Properly format the extra field in gzipped packages- [#&#8203;31884](https://github.com/helm/helm/issues/31884) by [@&#8203;ouillie](https://github.com/ouillie)
- Fix vanishing empty lines- [#&#8203;32327](https://github.com/helm/helm/issues/32327) by [@&#8203;matheuscscp](https://github.com/matheuscscp)
- fix: pass registry client to downloader.Manager in upgrade- [#&#8203;32400](https://github.com/helm/helm/issues/32400) by [@&#8203;SetagGnaw](https://github.com/SetagGnaw)
- chore(deps): bump google.golang.org/grpc from 1.80.0 to 1.82.1- for GO-2026-6061 [#&#8203;32450](https://github.com/helm/helm/issues/32450)
- fix: bump go.opentelemetry.io/otel to v1.44.0 for GO-2026-5158- [#&#8203;32521](https://github.com/helm/helm/issues/32521) by [@&#8203;TerryHowe](https://github.com/TerryHowe)

#### Installation and Upgrading

Download Helm v4.2.4. The common platform binaries are here:

- [MacOS amd64](https://get.helm.sh/helm-v4.2.4-darwin-amd64.tar.gz) ([checksum](https://get.helm.sh/helm-v4.2.4-darwin-amd64.tar.gz.sha256sum) / 6c163d687ca03c3b5c01928e53bbbcf9518278f47ce7a2f249a5a08e8bdaa2bc)
- [MacOS arm64](https://get.helm.sh/helm-v4.2.4-darwin-arm64.tar.gz) ([checksum](https://get.helm.sh/helm-v4.2.4-darwin-arm64.tar.gz.sha256sum) / d747eb4e28bd2727173d15b759fa0a17822291ec09db7ced3d55af290a3661a2)
- [Linux amd64](https://get.helm.sh/helm-v4.2.4-linux-amd64.tar.gz) ([checksum](https://get.helm.sh/helm-v4.2.4-linux-amd64.tar.gz.sha256sum) / c306b46f719b0a4da32d0f78ee21bf90ce8d602f15b22ab753f0674d1670a7f3)
- [Linux arm](https://get.helm.sh/helm-v4.2.4-linux-arm.tar.gz) ([checksum](https://get.helm.sh/helm-v4.2.4-linux-arm.tar.gz.sha256sum) / 894e901f7daaf9b458baad7b5c685bfeef49070d7d53f99687bd5846a6c13639)
- [Linux arm64](https://get.helm.sh/helm-v4.2.4-linux-arm64.tar.gz) ([checksum](https://get.helm.sh/helm-v4.2.4-linux-arm64.tar.gz.sha256sum) / 564de2191b881e9f71b5606b25345821ea1682f06ab90499d3ab22b530176da1)
- [Linux i386](https://get.helm.sh/helm-v4.2.4-linux-386.tar.gz) ([checksum](https://get.helm.sh/helm-v4.2.4-linux-386.tar.gz.sha256sum) / 45297aeac0c65173a89e8de832997f952ba5115c2db09b2e3f2c23a601e70583)
- [Linux loong64](https://get.helm.sh/helm-v4.2.4-linux-loong64.tar.gz) ([checksum](https://get.helm.sh/helm-v4.2.4-linux-loong64.tar.gz.sha256sum) / faafbfecc1a06196e650c3ce0c74d5ac32cb1c0c0a855fa76e59dd100cb8d4c4)
- [Linux ppc64le](https://get.helm.sh/helm-v4.2.4-linux-ppc64le.tar.gz) ([checksum](https://get.helm.sh/helm-v4.2.4-linux-ppc64le.tar.gz.sha256sum) / 5c00073e9d493de201384bb7eb19d60615bd7c39db52148473e8ce6da84bc70a)
- [Linux s390x](https://get.helm.sh/helm-v4.2.4-linux-s390x.tar.gz) ([checksum](https://get.helm.sh/helm-v4.2.4-linux-s390x.tar.gz.sha256sum) / 5396a35fca5fa46e5614140363f389ce66f96886c1b25f256d9e3028299422fa)
- [Linux riscv64](https://get.helm.sh/helm-v4.2.4-linux-riscv64.tar.gz) ([checksum](https://get.helm.sh/helm-v4.2.4-linux-riscv64.tar.gz.sha256sum) / d8532a3524ca842887b15ab794377dc9c8ced8f26264c84171b4b0aafff05411)
- [Windows amd64](https://get.helm.sh/helm-v4.2.4-windows-amd64.zip) ([checksum](https://get.helm.sh/helm-v4.2.4-windows-amd64.zip.sha256sum) / e94d83a4706fd82078c98dade2079fa9d9680c1c2bfb93bfc304ee6bc2412a32)
- [Windows arm64](https://get.helm.sh/helm-v4.2.4-windows-arm64.zip) ([checksum](https://get.helm.sh/helm-v4.2.4-windows-arm64.zip.sha256sum) / dbe8b49ea9877abe3d77354a792efb01920da9f65a492fcb8b4fce4e08bbae8f)

This release was signed with `208D D36E D5BB 3745 A167 43A4 C7C6 FBB5 B91C 1155` and can be found at [@&#8203;scottrigby](https://github.com/scottrigby) [keybase account](https://keybase.io/r6by). Please use the attached signatures for verifying this release using `gpg`.

The [Quickstart Guide](https://helm.sh/docs/intro/quickstart/) will get you going from there. For **upgrade instructions** or detailed installation notes, check the [install guide](https://helm.sh/docs/intro/install/). You can also use a [script to install](https://raw.githubusercontent.com/helm/helm/main/scripts/get-helm-4) on any system with `bash`.

#### What's Next

- 4.3.0 and 3.22.0 are the next minor releases scheduled for September 9, 2026

#### Changelog

- Minimal fix to build failure from [#&#8203;31211](https://github.com/helm/helm/issues/31211). [`3900f43`](https://github.com/helm/helm/commit/3900f434fd3ef2b84065dc04508df48f288dba00) (Scott Rigby)
- fix: bump go.opentelemetry.io/otel to v1.44.0 for GO-2026-5158 ([#&#8203;32521](https://github.com/helm/helm/issues/32521)) [`f7c6e8f`](https://github.com/helm/helm/commit/f7c6e8f0f1e0e649e8d03b1535db4f3b8d0c9af2) (Terry Howe)
- chore(deps): bump google.golang.org/grpc from 1.80.0 to 1.82.1 [`035a2c3`](https://github.com/helm/helm/commit/035a2c38e9a75ca0988c8449c0b7257f30d04064) (dependabot\[bot])
- fix: pass registry client to downloader.Manager in upgrade [`f76a5f4`](https://github.com/helm/helm/commit/f76a5f46a952f731cc1543f348121297c8b3f6cc) (Gates Wang)
- Apply suggestions [`5a7c6c7`](https://github.com/helm/helm/commit/5a7c6c7c732b04ad6517b452d538da9e18993d67) (Will Noble)
- Properly format the extra field in gzipped packages [`2281848`](https://github.com/helm/helm/commit/22818486ce0fc18d92e01ba39faf65f70ffa8865) (Will Noble)
- Fix missing conflict retry with server-side apply ([#&#8203;32088](https://github.com/helm/helm/issues/32088)) [`2c979a1`](https://github.com/helm/helm/commit/2c979a17ac6b6d7bfe2d6650b69fa9effe963d4d) (Jakub Jaruszewski)
- Potential fix for pull request finding [`2bd2c66`](https://github.com/helm/helm/commit/2bd2c66544634e419ede3cfa18952cce5a5acd08) (kimsungmin1)
- fix(registry): resolve golangci-lint issues in token-auth tests [`183a540`](https://github.com/helm/helm/commit/183a5402291c553898b9c404bc17c95c81ea1c6c) (kimsm28)
- chore: go mod tidy after rebase on main [`08d8da1`](https://github.com/helm/helm/commit/08d8da1aa9080772e57ab5bf5b00b3c13364af00) (kimsm28)
- fix(registry): use plain-http registry in token-auth scope test [`9655b5a`](https://github.com/helm/helm/commit/9655b5aecc0d36142d0620ff5ed762065a997739) (kimsm28)
- Update pkg/registry/client.go [`430dfac`](https://github.com/helm/helm/commit/430dfac3eeab03886f511761e3969f738f760364) (Terry Howe)
- test: improve client\_scope\_test.go to avoid data races and brittle assertions [`9569605`](https://github.com/helm/helm/commit/9569605eccf8318fe25bf78c46c4eb462ce8fc3f) (kimsm28)
- fix typos in withScopeHint function comment [`63f2b68`](https://github.com/helm/helm/commit/63f2b6809919e5e8e3e04f52064a536a14f1ff9b) (kimsm28)
- fix registry test failures by adjusting DockerRegistryHost and auth server listener management [`f7488c0`](https://github.com/helm/helm/commit/f7488c0be8c65dd16386c215cac4332900667278) (kimsm28)
- fix variable naming requestUrl -> requestURL [`8fe78fb`](https://github.com/helm/helm/commit/8fe78fbe46eb2db5c75ab1cc89699c750017dca6) (kimsm28)
- fix typo, remove unnecessary code, fix to avoid to use the assertion in http hanlder [`d0670d2`](https://github.com/helm/helm/commit/d0670d2fb2c3426cde4b41927b5e9b8b4370df93) (kimsm28)
- change suite.Nil, suite.NotNill to more proper function(suite.NoError, suite.Error) [`804256e`](https://github.com/helm/helm/commit/804256ef659226f26b2222ccb8f9cf18ef1b1946) (kimsungmin1)
- change client\_scope\_test.go to use httptest [`d79bceb`](https://github.com/helm/helm/commit/d79bceb807692512461d8007040c41bcd1547041) (kimsungmin1)
- fix typo [`d34fcd9`](https://github.com/helm/helm/commit/d34fcd9264225a1e6296c4b0ee124dc69f3b3ecc) (kimsungmin1)
- remove freeport dependency [`9fbd190`](https://github.com/helm/helm/commit/9fbd190c30addb4786e4fe930a0fe98bf354116a) (kimsungmin1)
- add newline in license header [`9275661`](https://github.com/helm/helm/commit/9275661357afdfe12b8ce561e8103673f16cca8d) (kimsungmin1)
- fix scope when helm push to a registry that use token auth [`fef91f3`](https://github.com/helm/helm/commit/fef91f3e6942a20148542461eaebfb24f2c09584) (kimsungmin1)
- fix panic on repeated IsReachable calls [`e89ce68`](https://github.com/helm/helm/commit/e89ce68bc5fec430bc1e2f0aef1aca6a2e71f795) (Mohammad Abdolirad)
- fix(provenance): check error return in Digest [`ff1ac83`](https://github.com/helm/helm/commit/ff1ac83bfb1246cdf1b57a4db0042085cc8b265d) (Sebastien Tardif)
- fix: address review feedback [`4b4dedb`](https://github.com/helm/helm/commit/4b4dedb2bdcfac886c124a361a5126e3c5e3c5df) (Sebastien Tardif)
- fix: fetch logs from all containers in test pods [`7c80103`](https://github.com/helm/helm/commit/7c8010322b8639cdf7844ac1ae5f8d444db43935) (Sebastien Tardif)
- chore: rename savedErr to clear its specific purpose [`ecc9cd2`](https://github.com/helm/helm/commit/ecc9cd2f1b5b53dadcd12395c032bc5b3ca02937) (Jeaeun Kim)
- chore: fix lint [`f6211ba`](https://github.com/helm/helm/commit/f6211ba49bfbf5768ea44be3a1402869a4709b37) (Jeaeun Kim)
- chore: store err separately for clarity [`3507ea5`](https://github.com/helm/helm/commit/3507ea5bfdbad921684ac131896b6968c76e9ca6) (Jeaeun Kim)
- chore: Improve error reporting for `helm template --debug` with `--show-only` [`211ffae`](https://github.com/helm/helm/commit/211ffae93d2d741a2dbcd74b4aa2a1bc2fc27d5f) (Jeaeun Kim)
- Address review comments [`51a9837`](https://github.com/helm/helm/commit/51a9837ba177812c381515886c4f0cd0b7a633e6) (Matheus Pimenta)
- Fix vanishing empty lines [`83a8b70`](https://github.com/helm/helm/commit/83a8b70ffc1bcf97bb293cf6b35bd3b5093e8c30) (Matheus Pimenta)

**Full Changelog**: <https://github.com/helm/helm/compare/v4.2.3...v4.2.4>

### [`v4.2.3`](https://github.com/helm/helm/releases/tag/v4.2.3): Helm v4.2.3

Helm v4.2.3 is a patch release. Users are encouraged to upgrade for the best experience.

The community keeps growing, and we'd love to see you there!

- Join the discussion in [Kubernetes Slack](https://kubernetes.slack.com):
  - for questions and just to hang out
  - for discussing PRs, code, and bugs
- Hang out at the Public Developer Call: Thursday, 9:30 Pacific via [Zoom](https://zoom.us/j/696660622)
- Test, debug, and contribute charts: [ArtifactHub/packages](https://artifacthub.io/packages/search?kind=0)

#### Installation and Upgrading

Download Helm v4.2.3. The common platform binaries are here:

- [MacOS amd64](https://get.helm.sh/helm-v4.2.3-darwin-amd64.tar.gz) ([checksum](https://get.helm.sh/helm-v4.2.3-darwin-amd64.tar.gz.sha256sum) / ff3ac86755a45f3422473bc1200776aac0fe04c5766abe6ca66699f7b564b23b)
- [MacOS arm64](https://get.helm.sh/helm-v4.2.3-darwin-arm64.tar.gz) ([checksum](https://get.helm.sh/helm-v4.2.3-darwin-arm64.tar.gz.sha256sum) / 048ecf5ad3160f83d918f9fe945238d2132b079640f7b106175331c25f242c64)
- [Linux amd64](https://get.helm.sh/helm-v4.2.3-linux-amd64.tar.gz) ([checksum](https://get.helm.sh/helm-v4.2.3-linux-amd64.tar.gz.sha256sum) / e9b88b4ee95b18c706839c28d3a0220e5bc470e9cd9262410c90793c45ff8b7c)
- [Linux arm](https://get.helm.sh/helm-v4.2.3-linux-arm.tar.gz) ([checksum](https://get.helm.sh/helm-v4.2.3-linux-arm.tar.gz.sha256sum) / ba00678361ca7a03ec42ca1ea459543e1d8eab2a7d5429a5eda71dc9741c8a9b)
- [Linux arm64](https://get.helm.sh/helm-v4.2.3-linux-arm64.tar.gz) ([checksum](https://get.helm.sh/helm-v4.2.3-linux-arm64.tar.gz.sha256sum) / 21abd9354d39b2cd79a8d76be6912cd137a983cbf997193503fb8a6a6e2f2785)
- [Linux i386](https://get.helm.sh/helm-v4.2.3-linux-386.tar.gz) ([checksum](https://get.helm.sh/helm-v4.2.3-linux-386.tar.gz.sha256sum) / 31d57972d36e60388e173327fffcf9d58f272349dfa9ed3e1914f3cd88fe7283)
- [Linux loong64](https://get.helm.sh/helm-v4.2.3-linux-loong64.tar.gz) ([checksum](https://get.helm.sh/helm-v4.2.3-linux-loong64.tar.gz.sha256sum) / 232f82d787d530a621b2006965ed2b99644b4391bbc6261e9787f95700fc44f7)
- [Linux ppc64le](https://get.helm.sh/helm-v4.2.3-linux-ppc64le.tar.gz) ([checksum](https://get.helm.sh/helm-v4.2.3-linux-ppc64le.tar.gz.sha256sum) / 43fc5a4b20839c3669a0748498bd2613b095e288425bf5678c6ba664eb4a0e70)
- [Linux s390x](https://get.helm.sh/helm-v4.2.3-linux-s390x.tar.gz) ([checksum](https://get.helm.sh/helm-v4.2.3-linux-s390x.tar.gz.sha256sum) / 17932091e19d352585b540a482fca9b953d32a8ad7afec72bf9cbbcd96b094cb)
- [Linux riscv64](https://get.helm.sh/helm-v4.2.3-linux-riscv64.tar.gz) ([checksum](https://get.helm.sh/helm-v4.2.3-linux-riscv64.tar.gz.sha256sum) / 09ff0772730678c652b9ac4a2b32cd20f4e62a2b040403bcacd4ad845d3d3e9c)
- [Windows amd64](https://get.helm.sh/helm-v4.2.3-windows-amd64.zip) ([checksum](https://get.helm.sh/helm-v4.2.3-windows-amd64.zip.sha256sum) / 5ca7de684c92d48b93d5c34a029fdda57b38e1eac04bc8541bdf1eb249388679)
- [Windows arm64](https://get.helm.sh/helm-v4.2.3-windows-arm64.zip) ([checksum](https://get.helm.sh/helm-v4.2.3-windows-arm64.zip.sha256sum) / 5f444ed097688ed3abaf1d8801e21110d9bddeb6ed13939afcac302888527ab5)

The [Quickstart Guide](https://helm.sh/docs/intro/quickstart/) will get you going from there. For **upgrade instructions** or detailed installation notes, check the [install guide](https://helm.sh/docs/intro/install/). You can also use a [script to install](https://raw.githubusercontent.com/helm/helm/main/scripts/get-helm-4) on any system with `bash`.

#### What's Next

- 4.2.4 and 3.21.4 are the next patch releases scheduled for August 12, 2026
- 4.3.0 and 3.22.0 are the next minor releases scheduled for September 9, 2026

#### Changelog

- chore(deps): bump golang.org/x/crypto from 0.53.0 to 0.54.0 [`43e8b7f`](https://github.com/helm/helm/commit/43e8b7feece8beb0fcba47059ec9b522fd929a64) (Terry Howe)

### [`v4.2.2`](https://github.com/helm/helm/releases/tag/v4.2.2): Helm v4.2.2

Helm v4.2.2 is a patch release. Users are encouraged to upgrade for the best experience.

The community keeps growing, and we'd love to see you there!

- Join the discussion in [Kubernetes Slack](https://kubernetes.slack.com):
  - for questions and just to hang out
  - for discussing PRs, code, and bugs
- Hang out at the Public Developer Call: Thursday, 9:30 Pacific via [Zoom](https://zoom.us/j/696660622)
- Test, debug, and contribute charts: [ArtifactHub/packages](https://artifacthub.io/packages/search?kind=0)

#### Notable Changes

- Revert: Fixed a race condition in WaitForDelete where the status observer canceled the watch too early, causing intermittent failures when running a full test suite [#&#8203;32214](https://github.com/helm/helm/issues/32214)

#### Installation and Upgrading

Download Helm v4.2.2. The common platform binaries are here:

- [MacOS amd64](https://get.helm.sh/helm-v4.2.2-darwin-amd64.tar.gz) ([checksum](https://get.helm.sh/helm-v4.2.2-darwin-amd64.tar.gz.sha256sum) / 10c1e36ee8c5f2e2ee25a16599cb03ab74c0953cd889cacb980a49ba4b6574ba)
- [MacOS arm64](https://get.helm.sh/helm-v4.2.2-darwin-arm64.tar.gz) ([checksum](https://get.helm.sh/helm-v4.2.2-darwin-arm64.tar.gz.sha256sum) / 5410a0dae3d5d91f45653b161260d9301aabc4ae80ae50a6605d66884b6df8ea)
- [Linux amd64](https://get.helm.sh/helm-v4.2.2-linux-amd64.tar.gz) ([checksum](https://get.helm.sh/helm-v4.2.2-linux-amd64.tar.gz.sha256sum) / 9adafecab4d406853bba163a70e9f104f47dbbf65ce24b7653bae7e36150bcb6)
- [Linux arm](https://get.helm.sh/helm-v4.2.2-linux-arm.tar.gz) ([checksum](https://get.helm.sh/helm-v4.2.2-linux-arm.tar.gz.sha256sum) / 7e9490169874695e04ab1af47c5620621fc13c84219a258fcc1afdcd40ca7438)
- [Linux arm64](https://get.helm.sh/helm-v4.2.2-linux-arm64.tar.gz) ([checksum](https://get.helm.sh/helm-v4.2.2-linux-arm64.tar.gz.sha256sum) / 78803142087a0069fa4b50d3f32a84d3ef25c14d1ee8a40fbccf86a6216d2f36)
- [Linux i386](https://get.helm.sh/helm-v4.2.2-linux-386.tar.gz) ([checksum](https://get.helm.sh/helm-v4.2.2-linux-386.tar.gz.sha256sum) / 8e1fdcda4a476ffc5d1179c7f16d33a3d54267efa08fd720f7678277d68bc2d5)
- [Linux loong64](https://get.helm.sh/helm-v4.2.2-linux-loong64.tar.gz) ([checksum](https://get.helm.sh/helm-v4.2.2-linux-loong64.tar.gz.sha256sum) / b8bfe96b8b0b0e2af51af4a00ef521cc5a7e03793aea3568cf8500a63ae05041)
- [Linux ppc64le](https://get.helm.sh/helm-v4.2.2-linux-ppc64le.tar.gz) ([checksum](https://get.helm.sh/helm-v4.2.2-linux-ppc64le.tar.gz.sha256sum) / 814a80fd98eb9e4c5a9d610f3b9c15ffe120c2f5e39df16a2f491723ebc90126)
- [Linux s390x](https://get.helm.sh/helm-v4.2.2-linux-s390x.tar.gz) ([checksum](https://get.helm.sh/helm-v4.2.2-linux-s390x.tar.gz.sha256sum) / d84cdf1123f20cfbef19a2af1cd6afe8b00626bd9846bccb9dae978c810c8274)
- [Linux riscv64](https://get.helm.sh/helm-v4.2.2-linux-riscv64.tar.gz) ([checksum](https://get.helm.sh/helm-v4.2.2-linux-riscv64.tar.gz.sha256sum) / f07c105180dff2619ab45134b9b47b7845387e8f3299e12ebe0efb87c7548717)
- [Windows amd64](https://get.helm.sh/helm-v4.2.2-windows-amd64.zip) ([checksum](https://get.helm.sh/helm-v4.2.2-windows-amd64.zip.sha256sum) / 5fad8562e98c34fa5af3ef904086a5874a6701050f9bf36e30238c975df94dcd)
- [Windows arm64](https://get.helm.sh/helm-v4.2.2-windows-arm64.zip) ([checksum](https://get.helm.sh/helm-v4.2.2-windows-arm64.zip.sha256sum) / 2e993d6a1dd8197a33e65d8e90b26df9d248ff3501701dea401856aa265a2dab)

This release was signed by [@&#8203;gjenkins8](https://github.com/gjenkins8) with key BF88 8333 D96A 1C18 E268 2AAE D79D 67C9 EC01 6739, which can be found at <https://keys.openpgp.org/vks/v1/by-fingerprint/BF888333D96A1C18E2682AAED79D67C9EC016739>. Please use the attached signatures for verifying this release using gpg.

The [Quickstart Guide](https://helm.sh/docs/intro/quickstart/) will get you going from there. For **upgrade instructions** or detailed installation notes, check the [install guide](https://helm.sh/docs/intro/install/). You can also use a [script to install](https://raw.githubusercontent.com/helm/helm/main/scripts/get-helm-4) on any system with `bash`.

#### What's Next

- 4.2.3 and 3.21.2 are the next patch releases scheduled for July 8, 2026
- 4.3.0 and 3.22.0 are the next minor releases scheduled for September 9, 2026

#### Changelog

- Revert "fix(kube): prevent spurious early exit in WaitForDelete during informer sync" [`b05881c`](https://github.com/helm/helm/commit/b05881cf967a5a09e19866799d0edfd40675803a) (George Jenkins)

**Full Changelog**: <https://github.com/helm/helm/compare/v4.2.1...v4.2.2>

### [`v4.2.1`](https://github.com/helm/helm/releases/tag/v4.2.1): Helm v4.2.1

Helm v4.2.1 is a patch release. Users are encouraged to upgrade for the best experience.

The community keeps growing, and we'd love to see you there!

- Join the discussion in [Kubernetes Slack](https://kubernetes.slack.com):
  - for questions and just to hang out
  - for discussing PRs, code, and bugs
- Hang out at the Public Developer Call: Thursday, 9:30 Pacific via [Zoom](https://zoom.us/j/696660622)
- Test, debug, and contribute charts: [ArtifactHub/packages](https://artifacthub.io/packages/search?kind=0)

#### Notable Changes

- Fixed data race detected by -race flag when concurrent goroutines (upgrade + rollback, install + uninstall) both call GetWaiterWithOptions on the same FailingKubeClient instance [#&#8203;31925](https://github.com/helm/helm/issues/31925)
- Fixed helm command success messages writing to stderr instead of stdout. Now correctly outputing to stdout [#&#8203;32056](https://github.com/helm/helm/issues/32056)
- Fixed Helm 4 emitting "unable to find exact version" when using version range constraints [#&#8203;31757](https://github.com/helm/helm/issues/31757)
- Fixed a race condition in WaitForDelete where the status observer canceled the watch too early, causing intermittent failures when running a full test suite [#&#8203;32081](https://github.com/helm/helm/issues/32081)
- Bumped golang.org/x/net to v0.55.0 to address GO-2026-5026 [#&#8203;32153](https://github.com/helm/helm/issues/32153)
- Fixed SDK errors by upgrading dependencies: cli-utils 1.2.1, controller-runtime 0.24.1 and k8s 1.36.1 [#&#8203;32128](https://github.com/helm/helm/issues/32128)
- Dependency updates

#### Installation and Upgrading

Download Helm v4.2.1. The common platform binaries are here:

- [MacOS amd64](https://get.helm.sh/helm-v4.2.1-darwin-amd64.tar.gz) ([checksum](https://get.helm.sh/helm-v4.2.1-darwin-amd64.tar.gz.sha256sum) / 2a21c9f368d608bcf6eb794ebc06514eb6b529a846b60fe4a43dea7bcce65228)
- [MacOS arm64](https://get.helm.sh/helm-v4.2.1-darwin-arm64.tar.gz) ([checksum](https://get.helm.sh/helm-v4.2.1-darwin-arm64.tar.gz.sha256sum) / 896472d2ec0740c60f64a9df0fc30d478beee38a1a2a6ed91aa6e6ee177c1575)
- [Linux amd64](https://get.helm.sh/helm-v4.2.1-linux-amd64.tar.gz) ([checksum](https://get.helm.sh/helm-v4.2.1-linux-amd64.tar.gz.sha256sum) / 479dca836e5b45e8bd222400c5591b0e3a647378f03ff96597180db97c17fdae)
- [Linux arm](https://get.helm.sh/helm-v4.2.1-linux-arm.tar.gz) ([checksum](https://get.helm.sh/helm-v4.2.1-linux-arm.tar.gz.sha256sum) / 49e8f7856de6eab170dc09671cfb0578cc455d820df5b0f54e6453058dc0e3f3)
- [Linux arm64](https://get.helm.sh/helm-v4.2.1-linux-arm64.tar.gz) ([checksum](https://get.helm.sh/helm-v4.2.1-linux-arm64.tar.gz.sha256sum) / 596b9a73d366c1e72ce67d595c22805480e30914593aafbc9f547694e72814db)
- [Linux i386](https://get.helm.sh/helm-v4.2.1-linux-386.tar.gz) ([checksum](https://get.helm.sh/helm-v4.2.1-linux-386.tar.gz.sha256sum) / e038eab680f22b1cebe68fd0536cf2397b0c10798dcb23c28e500e0804ec1a55)
- [Linux loong64](https://get.helm.sh/helm-v4.2.1-linux-loong64.tar.gz) ([checksum](https://get.helm.sh/helm-v4.2.1-linux-loong64.tar.gz.sha256sum) / 8ae26f15638d951c4ed21d0d3018b8800a137646e5e5151a3856cf324c2852ae)
- [Linux ppc64le](https://get.helm.sh/helm-v4.2.1-linux-ppc64le.tar.gz) ([checksum](https://get.helm.sh/helm-v4.2.1-linux-ppc64le.tar.gz.sha256sum) / 6f34eca5e314e941577a07be6c8b356f66b9cdefbed1175da1e7916368febcfc)
- [Linux s390x](https://get.helm.sh/helm-v4.2.1-linux-s390x.tar.gz) ([checksum](https://get.helm.sh/helm-v4.2.1-linux-s390x.tar.gz.sha256sum) / e6355691887d4185b7e077f058483c04f353229feb7d4a72edc3ebe0b8738a6a)
- [Linux riscv64](https://get.helm.sh/helm-v4.2.1-linux-riscv64.tar.gz) ([checksum](https://get.helm.sh/helm-v4.2.1-linux-riscv64.tar.gz.sha256sum) / 16a4299f14ff1ffa79bb22115051911c662fa2ecdd90e85b65d7d143e8de9d02)
- [Windows amd64](https://get.helm.sh/helm-v4.2.1-windows-amd64.zip) ([checksum](https://get.helm.sh/helm-v4.2.1-windows-amd64.zip.sha256sum) / 6e7fa7839444b8ddc407c5bcdb1edd1024f57d09c2db971dec511ee2f2616eb0)
- [Windows arm64](https://get.helm.sh/helm-v4.2.1-windows-arm64.zip) ([checksum](https://get.helm.sh/helm-v4.2.1-windows-arm64.zip.sha256sum) / ae4c9acd0d9acd1f9e9da2f60105f793f65fd49ab7c03c6c7d13804c3b885657)

This release was signed with `208D D36E D5BB 3745 A167 43A4 C7C6 FBB5 B91C 1155` and can be found at [@&#8203;scottrigby](https://github.com/scottrigby) [keybase account](https://keybase.io/r6by). Please use the attached signatures for verifying this release using `gpg`.

The [Quickstart Guide](https://helm.sh/docs/intro/quickstart/) will get you going from there. For **upgrade instructions** or detailed installation notes, check the [install guide](https://helm.sh/docs/intro/install/). You can also use a [script to install](https://raw.githubusercontent.com/helm/helm/main/scripts/get-helm-4) on any system with `bash`.

#### What's Next

- 4.2.2 and 3.21.2 are the next patch releases scheduled for July 8, 2026
- 4.3.0 and 3.22.0 are the next minor releases scheduled for September 9, 2026

#### Changelog

- fix: protect FailingKubeClient.RecordedWaitOptions from data race ([#&#8203;31925](https://github.com/helm/helm/issues/31925)) [`d591a19`](https://github.com/helm/helm/commit/d591a19b953bd9cfdf7d9ddd83c2f4ffdaeafb29) (Terry Howe)
- fix: route registry client output to stdout instead of stderr ([#&#8203;32056](https://github.com/helm/helm/issues/32056)) [`2a9fcae`](https://github.com/helm/helm/commit/2a9fcae29280472edec988c6bf0528e4ae79b33a) (Terry Howe)
- chore(deps): bump oras.land/oras-go/v2 from 2.6.0 to 2.6.1 [`ffa5bd6`](https://github.com/helm/helm/commit/ffa5bd693eee68ba9c1ba42d160c69114eda962c) (dependabot\[bot])
- chore(deps): bump golang.org/x/crypto from 0.52.0 to 0.53.0 [`9f9dbaf`](https://github.com/helm/helm/commit/9f9dbaf94008044a516cda4837565237306578a7) (dependabot\[bot])
- chore(deps): bump golang.org/x/term from 0.43.0 to 0.44.0 [`64a2891`](https://github.com/helm/helm/commit/64a2891699ae9c8f2d0e06d5db3dd117649886a2) (dependabot\[bot])
- chore(deps): bump golang.org/x/text from 0.37.0 to 0.38.0 [`e54a4a2`](https://github.com/helm/helm/commit/e54a4a2b7d4ed9ca3bb4be7562f76dd5f2fd8f71) (dependabot\[bot])
- chore(deps): bump github/codeql-action from 4.36.1 to 4.36.2 [`acb762b`](https://github.com/helm/helm/commit/acb762b0ef8882b062ba8f6b87261411309875b8) (dependabot\[bot])
- chore(deps): bump github/codeql-action from 4.36.0 to 4.36.1 [`768586d`](https://github.com/helm/helm/commit/768586df3f2a79fca5202b6713f8675bb097a904) (dependabot\[bot])
- fix(version): avoid false range detection on prerelease x/X [`eabfae5`](https://github.com/helm/helm/commit/eabfae560459d1ffe1f7a3268d5441238e9f84b2) (Benoit Tigeot)
- fix(version): version range || can has no space [`e3fd51f`](https://github.com/helm/helm/commit/e3fd51f331e14fb4056951540d2f2ffde81b405c) (Benoit Tigeot)
- feat: report in debug the version we select with version range arg [`1e47395`](https://github.com/helm/helm/commit/1e47395a9566bcaaaf7ed9e31a8367eb1f95e0a3) (Benoit Tigeot)
- fix: prevent warning when using version range constraints [`a33e239`](https://github.com/helm/helm/commit/a33e23939a85ac60eb9a6bee818f2c5459fda576) (Benoit Tigeot)
- fix(kube): always propagate context.Canceled in WaitForDelete [`fa06d44`](https://github.com/helm/helm/commit/fa06d4455724afe22bbe00af7925549a82d95e6c) (Terry Howe)
- fix(kube): prevent spurious early exit in WaitForDelete during informer sync [`360d483`](https://github.com/helm/helm/commit/360d4835df0fb8bd7cbde4cad0cbc79de01a6e93) (Terry Howe)
- chore(deps): bump github.com/tetratelabs/wazero from 1.11.0 to 1.12.0 [`7651edf`](https://github.com/helm/helm/commit/7651edf21e31b5c33df82e67f23855d1358d021d) (dependabot\[bot])
- chore(deps): bump golang.org/x/crypto from 0.51.0 to 0.52.0 [`b132e7e`](https://github.com/helm/helm/commit/b132e7e43f3620eb60ef3524527c1b2fceed90e9) (dependabot\[bot])
- fix(deps): bump golang.org/x/net to v0.55.0 to address GO-2026-5026 [`eee491a`](https://github.com/helm/helm/commit/eee491a7461a524b87e5bb73ea5a0c4f82c72469) (Terry Howe)
- chore(deps): bump golangci/golangci-lint-action from 9.2.0 to 9.2.1 [`3e3c575`](https://github.com/helm/helm/commit/3e3c5751b1723239cbce042533db0d84b65c6bc1) (dependabot\[bot])
- chore(deps): bump github/codeql-action from 4.35.5 to 4.36.0 [`c4ce2bb`](https://github.com/helm/helm/commit/c4ce2bb364dbfb781059e628572d7177ba191cc4) (dependabot\[bot])
- chore(deps): bump actions/stale from 10.2.0 to 10.3.0 [`3892dc2`](https://github.com/helm/helm/commit/3892dc2a11b2e111acddcbc55d5a4733ba461f20) (dependabot\[bot])
- chore(deps): bump github/codeql-action from 4.35.4 to 4.35.5 [`c4bbb62`](https://github.com/helm/helm/commit/c4bbb6263f59fe541acd75ce0b508034c65899e1) (dependabot\[bot])
- chore(deps): bump golang.org/x/crypto from 0.50.0 to 0.51.0 [`a0d7f16`](https://github.com/helm/helm/commit/a0d7f16b58aa4cb9dbaf8c37055faa28b1b350ae) (dependabot\[bot])
- chore(deps): bump github/codeql-action from 4.35.3 to 4.35.4 [`8a3de05`](https://github.com/helm/helm/commit/8a3de054b5ab1b59f60c790fad39861e294671f1) (dependabot\[bot])
- fix(upstream): upgrade to cli-utils 1.2.1, controller-runtime 0.24.1 and k8s 1.36.1 [`57a4803`](https://github.com/helm/helm/commit/57a4803bd4953d8ef9d51d927f492ecaaf5df9db) (Matheus Pimenta)
- chore(deps): bump github.com/fluxcd/cli-utils from 1.2.0 to 1.2.1 [`b33ae02`](https://github.com/helm/helm/commit/b33ae02b9cd7fcba804391ab3d364739cb2a8780) (dependabot\[bot])

**Full Changelog**: <https://github.com/helm/helm/compare/v4.2.0...v4.2.1>

### [`v4.2.0`](https://github.com/helm/helm/releases/tag/v4.2.0): Helm v4.2.0

Helm v4.2.0 is a feature release. Users are encouraged to upgrade for the best experience.

The community keeps growing, and we'd love to see you there!

- Join the discussion in [Kubernetes Slack](https://kubernetes.slack.com):
  - for questions and just to hang out
  - for discussing PRs, code, and bugs
- Hang out at the Public Developer Call: Thursday, 9:30 Pacific via [Zoom](https://zoom.us/j/696660622)
- Test, debug, and contribute charts: [ArtifactHub/packages](https://artifacthub.io/packages/search?kind=0)

#### Notable Changes

- Switch to `goreleaser` for release builds
- Kubernetes client libraries to v1.36
- Add `mustToToml` template function
- deprecate unused `--hide-notes` and `--render-subchart-notes` flags
- `--dry-run=server` now respects `generateName:`

#### Installation and Upgrading

Download Helm v4.2.0. The common platform binaries are here:

- [MacOS amd64](https://get.helm.sh/helm-v4.2.0-darwin-amd64.tar.gz) ([checksum](https://get.helm.sh/helm-v4.2.0-darwin-amd64.tar.gz.sha256sum) / 1376ea697140e4db316736e760d5a47d12afc1524dce704476ef06fd7fdeddc6)
- [MacOS arm64](https://get.helm.sh/helm-v4.2.0-darwin-arm64.tar.gz) ([checksum](https://get.helm.sh/helm-v4.2.0-darwin-arm64.tar.gz.sha256sum) / f13f959015447b6bc309f9fd506509926543988a39035c088b52522ec95e2acb)
- [Linux amd64](https://get.helm.sh/helm-v4.2.0-linux-amd64.tar.gz) ([checksum](https://get.helm.sh/helm-v4.2.0-linux-amd64.tar.gz.sha256sum) / 97dbeb971be4ac4b27e3839976d9564c0fb35c6f3b1da89dd1e292d236af4096)
- [Linux arm](https://get.helm.sh/helm-v4.2.0-linux-arm.tar.gz) ([checksum](https://get.helm.sh/helm-v4.2.0-linux-arm.tar.gz.sha256sum) / ae624870b2d50e655b6462daff117eb9d28c4bad45234ef24c1275113540fcb0)
- [Linux arm64](https://get.helm.sh/helm-v4.2.0-linux-arm64.tar.gz) ([checksum](https://get.helm.sh/helm-v4.2.0-linux-arm64.tar.gz.sha256sum) / 1f8de130dfbd04de64978e7b852a7a547be1404956a366608276d2520b678670)
- [Linux i386](https://get.helm.sh/helm-v4.2.0-linux-386.tar.gz) ([checksum](https://get.helm.sh/helm-v4.2.0-linux-386.tar.gz.sha256sum) / 9cf44acc59081aca98b4d9f09138348836b26761258e02ad2b99616f66eead5c)
- [Linux loong64](https://get.helm.sh/helm-v4.2.0-linux-loong64.tar.gz) ([checksum](https://get.helm.sh/helm-v4.2.0-linux-loong64.tar.gz.sha256sum) / 5b04f0167b8b415a057c1f4f809ede86d5ead840e0aa560db097da5be19f86d0)
- [Linux ppc64le](https://get.helm.sh/helm-v4.2.0-linux-ppc64le.tar.gz) ([checksum](https://get.helm.sh/helm-v4.2.0-linux-ppc64le.tar.gz.sha256sum) / 48f0637b93247717b725e8d4a8d2cf8df0e2fdea91bdd0e36e2426c2d5c76e4e)
- [Linux s390x](https://get.helm.sh/helm-v4.2.0-linux-s390x.tar.gz) ([checksum](https://get.helm.sh/helm-v4.2.0-linux-s390x.tar.gz.sha256sum) / 328e9ed27904f9910026240c4311bb1b0bf91c6fde1634f212097694507a702f)
- [Linux riscv64](https://get.helm.sh/helm-v4.2.0-linux-riscv64.tar.gz) ([checksum](https://get.helm.sh/helm-v4.2.0-linux-riscv64.tar.gz.sha256sum) / 5d292d57ab1f40e47e373a87187bafa66e8daac4ddc4a1333421c174e8184755)
- [Windows amd64](https://get.helm.sh/helm-v4.2.0-windows-amd64.zip) ([checksum](https://get.helm.sh/helm-v4.2.0-windows-amd64.zip.sha256sum) / 614f68ddc567ac9bfb0c205f869b1f83ba4e0a9aacd26cbae47743ae6082a579)
- [Windows arm64](https://get.helm.sh/helm-v4.2.0-windows-arm64.zip) ([checksum](https://get.helm.sh/helm-v4.2.0-windows-arm64.zip.sha256sum) / e740e4c19b6e2a0b428f7a52c38b7f0b092f0c43ac49870537d7e7fac9cedc07)

This release was signed by [@&#8203;gjenkins8](https://github.com/gjenkins8) with key BF88 8333 D96A 1C18 E268 2AAE D79D 67C9 EC01 6739, which can be found at <https://keys.openpgp.org/vks/v1/by-fingerprint/BF888333D96A1C18E2682AAED79D67C9EC016739>. Please use the attached signatures for verifying this release using gpg.

The [Quickstart Guide](https://helm.sh/docs/intro/quickstart/) will get you going from there. For **upgrade instructions** or detailed installation notes, check the [install guide](https://helm.sh/docs/intro/install/). You can also use a [script to install](https://raw.githubusercontent.com/helm/helm/main/scripts/get-helm-4) on any system with `bash`.

#### What's Next

- 4.2.1 will contain only bug fixes
- 4.3.0 is the next feature release

#### Changelog

- Bump to version v4.2 [`0646808`](https://github.com/helm/helm/commit/06468084e85c244c712834933d25ea232a4c2093) (George Jenkins)
- build: Clean up Goreleaser change ([#&#8203;32098](https://github.com/helm/helm/issues/32098)) [`e23bf3a`](https://github.com/helm/helm/commit/e23bf3af53c52185123278e83b7023c102707778) (Scott Rigby)
- fix: add -extldflags -static to dist target to match build-cross [`f60ab7c`](https://github.com/helm/helm/commit/f60ab7c31c81a73b8e0aade5aff41bfc01c08820) (Terry Howe)
- build: use goreleaser build with manual archive creation [`64aa46f`](https://github.com/helm/helm/commit/64aa46f2f1cf239cf6535c5e847e14dcb933a847) (Terry Howe)
- chore: remove build-cross dependency from test-acceptance [`d199a1a`](https://github.com/helm/helm/commit/d199a1a42c04bccb287f2c7d9c3f73b669412e5a) (Terry Howe)
- ci: add fetch-depth 0 to canary checkout for goreleaser [`8289940`](https://github.com/helm/helm/commit/82899404a68f3826389bb38cf67bf75085db6b2c) (Terry Howe)
- fix: address goreleaser build issues flagged in review [`c075022`](https://github.com/helm/helm/commit/c075022ce16489f5f7afd45a37b679cf58fa36ea) (Terry Howe)
- fix: pass VERSION as GORELEASER\_CURRENT\_TAG to preserve v-prefix in archive names [`04885dd`](https://github.com/helm/helm/commit/04885dd905b6f8a823733dbc9b9f5cb2843a975f) (Terry Howe)
- fix: disable goreleaser checksums.txt and restrict zip to windows only [`93103ce`](https://github.com/helm/helm/commit/93103ce66cb6374d9d7b552802f53b21ea2c2dd1) (Terry Howe)
- fix: use index for optional env var in version\_template [`e49a1dc`](https://github.com/helm/helm/commit/e49a1dc16eee526928d8928b8d96c01ee513ebd9) (Terry Howe)
- fix: canary build file names [`eaa0910`](https://github.com/helm/helm/commit/eaa09100b9b18175d878b1e114cbe9df2a3f70c2) (Terry Howe)
- Fix archive name [`5a75279`](https://github.com/helm/helm/commit/5a75279c1a017a60b97bd44986288af7399c6ff8) (Terry Howe)
- fix goreleaser archive [`37284a9`](https://github.com/helm/helm/commit/37284a9211972f7f41a2acc3c3313517596dd4b0) (Terry Howe)
- add support for loong64 [`45336cc`](https://github.com/helm/helm/commit/45336ccd5b2621357e3f785c1fe93627c5990a6e) (Terry Howe)
- fix artifact directory [`a9659b0`](https://github.com/helm/helm/commit/a9659b07e3eec20ab5b964fddae05f51f478f704) (Terry Howe)
- update configuration to v2 [`e368f17`](https://github.com/helm/helm/commit/e368f170af8a200e672adac5f765b8101db0c8fa) (Terry Howe)
- remove GOTOOLCHAIN [`e7bea85`](https://github.com/helm/helm/commit/e7bea8513c30475664919f031774e18fecdf1f66) (Terry Howe)
- chore: replace mitchellh/gox with goreleaser [`075c096`](https://github.com/helm/helm/commit/075c096afec70155bc43ac3587a119df1ae5fcc6) (Terry Howe)
- chore(deps): bump github.com/distribution/distribution/v3 [`12f2c41`](https://github.com/helm/helm/commit/12f2c41c0d7a74739c58a5995cbbb3125d9247e5) (dependabot\[bot])
- chore(deps): bump github/codeql-action from 4.35.2 to 4.35.3 [`58e8ffd`](https://github.com/helm/helm/commit/58e8ffdc3302260b1b55718c9b72c6f169a76ee0) (dependabot\[bot])
- chore(deps): bump github.com/Masterminds/semver/v3 from 3.4.0 to 3.5.0 [`e61bbfb`](https://github.com/helm/helm/commit/e61bbfbfff41958b0ba1984e4d6799fe131f325e) (dependabot\[bot])
- Upgrade kstatus to 1.2 and controller-runtime to 0.24 [`081c6df`](https://github.com/helm/helm/commit/081c6dff537087f52ec6e470d8986439e24e8e33) (Matheus Pimenta)
- fix: adds topLevel permissions to improve openSSF scores [`277d970`](https://github.com/helm/helm/commit/277d9702555532d13426119d31c70fffb389d589) (Gagan H R)
- Upgrade Go to 1.26, Kubernetes to 1.36, kstatus to 1.1 [`a4a9cc7`](https://github.com/helm/helm/commit/a4a9cc7a314d98456a2f23798a78e9ad05d96d0c) (Matheus Pimenta)
- fix(templating): hooks conflicting with templates in post-renderers ([#&#8203;32049](https://github.com/helm/helm/issues/32049)) [`8f56f24`](https://github.com/helm/helm/commit/8f56f24d638612a46f3e23265d06338c1f93bccb) (Matheus Pimenta)
- docs: fix grammar and spacing in CONTRIBUTING.md [`db40adb`](https://github.com/helm/helm/commit/db40adb1d13573280b65bc2002df7d75c009235a) (Mohit)
- chore(deps): bump the k8s-io group with 7 updates [`775e794`](https://github.com/helm/helm/commit/775e794319639f5c1e6b40448ce15ad3cc10d4e1) (dependabot\[bot])
- chore(deps): bump github/codeql-action from 4.35.1 to 4.35.2 [`934ace3`](https://github.com/helm/helm/commit/934ace35dfaef9eeb9997bf1ee385db0986daecc) (dependabot\[bot])
- fix(templating): SplitManifests must preserve line endings for downstream YAML parsers ([#&#8203;31952](https://github.com/helm/helm/issues/31952)) [`265c5eb`](https://github.com/helm/helm/commit/265c5eb530a36ec651e79ecf4d37ba2f098b7e59) (Matheus Pimenta)
- chore(deps): bump github.com/mattn/go-shellwords from 1.0.12 to 1.0.13 [`48e2b7d`](https://github.com/helm/helm/commit/48e2b7ddd4e960b768fe5daee34a33cb89852a6e) (dependabot\[bot])
- Update pkg/chart/common/util/coalesce.go [`a8e2497`](https://github.com/helm/helm/commit/a8e249714f5311b9aff44c4bd2bfc433ab1ab952) (Evans Mungai)
- test(values): Add test for nil cleanup in partially overridden subchart maps [`52fc971`](https://github.com/helm/helm/commit/52fc971da37cf34aa26e7d7c460f2430dfb01b26) (Johannes Lohmer)
- fix(values): do not copy chart-default nils into coalesced values [`0063877`](https://github.com/helm/helm/commit/00638773d1366dc962c785de3d297cf0279b9a0d) (Johannes Lohmer)
- test(values): add test for subchart nil producing %!s(<nil>) [`6eb4ebf`](https://github.com/helm/helm/commit/6eb4ebf0e1afb0c63d748bf116145a5b9e0842b7) (Johannes Lohmer)
- test(values): add tests for subchart nil value regressions [`5cb4e7d`](https://github.com/helm/helm/commit/5cb4e7d992d85d372f5d86c238330102d936bfe5) (Johannes Lohmer)
- chore(deps): bump actions/upload-artifact from 7.0.0 to 7.0.1 [`b5c7c80`](https://github.com/helm/helm/commit/b5c7c80de317643e383ca2926ebc0ad884021bba) (dependabot\[bot])
- fix(templating): fix wrong YAML separator parsing for post-renderers ([#&#8203;31941](https://github.com/helm/helm/issues/31941)) [`a27f1ad`](https://github.com/helm/helm/commit/a27f1add79c6c02459413dbb60f8438d8051cf06) (Matheus Pimenta)
- fix: add debug logging to HTTP getter for helm pull [`c26be60`](https://github.com/helm/helm/commit/c26be60d81e5cb6a147d6088477cf86fd5aaf1f0) (Cairon)
- chore(deps): bump golang.org/x/crypto from 0.49.0 to 0.50.0 [`953f5f0`](https://github.com/helm/helm/commit/953f5f031bb7fa8f3eccdea6520e09fd44fe3923) (dependabot\[bot])
- chore(deps): bump golang.org/x/term from 0.41.0 to 0.42.0 [`10fc5f3`](https://github.com/helm/helm/commit/10fc5f335b5fbb09f5d04cb0450839790ae15634) (dependabot\[bot])
- chore(deps): bump golang.org/x/text from 0.35.0 to 0.36.0 [`d89e7c6`](https://github.com/helm/helm/commit/d89e7c60762910204044c4215c7bb2f43ac3ef8f) (dependabot\[bot])
- chore: Update release notes script for Helm v4 [`8a95461`](https://github.com/helm/helm/commit/8a954619255a82890a08b7d1fa9e86a437c4cebb) (George Jenkins)
- refactor(cli): share RetryingRoundTripper via pkg/kubeenv [`213c869`](https://github.com/helm/helm/commit/213c869a988f2c7390c65673e3d677970d6220fd) (Sumit Solanki)
- chore(deps): bump github.com/lib/pq from 1.12.2 to 1.12.3 [`bd5027a`](https://github.com/helm/helm/commit/bd5027a9cf07993d7bfe4b60702b1a489fe8783e) (dependabot\[bot])
- fix: unnecessary-format lint issues from merge [`087736b`](https://github.com/helm/helm/commit/087736b66e97393ccaa0bdf1e5df13dcc9d88340) (George Jenkins)
- fix: Plugin missing provenance bypass [`586eb57`](https://github.com/helm/helm/commit/586eb57338d848e65686a3a9616e2776e87cfd1e) (George Jenkins)
- chore(deps): bump github.com/fluxcd/cli-utils [`c8c5dfa`](https://github.com/helm/helm/commit/c8c5dfad630cd7b238236c619c466488a547725c) (dependabot\[bot])
- chore(deps): bump go.opentelemetry.io/otel/exporters/otlp/otlpmetric/otlpmetrichttp [`998466c`](https://github.com/helm/helm/commit/998466cfcfee189ce7e3df5be8ffe79ed5f1f097) (dependabot\[bot])
- chore(deps): bump go.opentelemetry.io/otel/exporters/otlp/otlptrace/otlptracehttp [`b0cec58`](https://github.com/helm/helm/commit/b0cec589f50a7e16d942ad3385598a6dda2b0a20) (dependabot\[bot])
- chore(deps): bump go.opentelemetry.io/otel/exporters/otlp/otlplog/otlploghttp [`6ebfb29`](https://github.com/helm/helm/commit/6ebfb29dbf006ce78e9af8878008bda3578dcd3e) (dependabot\[bot])
- test(kube): fix flaky WaitForDelete test by avoiding informer sync race [`a7f8443`](https://github.com/helm/helm/commit/a7f84439aacd3864b40055b60a3c3e54292d1646) (Terry Howe)
- test(kube): fix flaky WaitForDelete timing in status wait tests [`4c0d21f`](https://github.com/helm/helm/commit/4c0d21f53f2ca78b525e31dbbf9cc9cfb818a2e3) (Terry Howe)
- chore(deps): bump github.com/distribution/distribution/v3 [`08dea9c`](https://github.com/helm/helm/commit/08dea9c140084b5d9fecb59a45a05f417415b591) (dependabot\[bot])
- Minor nit: fix import instructions to comply with canonical import paths [`de58531`](https://github.com/helm/helm/commit/de58531ca7ff557342acaa2c906082e58521ef47) (Anmol Virdi)
- chore(deps): bump github.com/distribution/distribution/v3 [`9b1ad4c`](https://github.com/helm/helm/commit/9b1ad4cf027452b828affb07318db2e931e734a5) (dependabot\[bot])
- fix(action): return correct error variable in prepareUpgrade [`8ef2d45`](https://github.com/helm/helm/commit/8ef2d45934ba1b9ca341818f1157112fcf7cdf1d) (Rhys McNeill)
- chore(deps): bump github.com/lib/pq from 1.12.1 to 1.12.2 [`cd7cf76`](https://github.com/helm/helm/commit/cd7cf76a174e856fd171b391995d9a65f97a79d3) (dependabot\[bot])
- chore(deps): bump github/codeql-action from 4.30.7 to 4.35.1 [`45ee55b`](https://github.com/helm/helm/commit/45ee55b83f8ad23798c84560ff65686e2ab298af) (dependabot\[bot])
- chore(deps): bump github.com/lib/pq from 1.12.0 to 1.12.1 [`9a06741`](https://github.com/helm/helm/commit/9a0674188412d1dcb2e7f018730aaa71781bd03b) (dependabot\[bot])
- chore(deps): bump actions/setup-go from 6.2.0 to 6.4.0 [`d1e31ca`](https://github.com/helm/helm/commit/d1e31ca507412d770a602e722060e6d7379f4f1a) (dependabot\[bot])
- fix(kube): clarify server-side apply patch errors [`f257c95`](https://github.com/helm/helm/commit/f257c95c783f5595e36cb5a7dcc862cc1f6266b5) (abhay1999)
- fix: pin codeql-action/upload-sarif to commit SHA in scorecards workflow [`7025480`](https://github.com/helm/helm/commit/7025480397d8b6b7fd8cdb5e083dc37b62dbd3d8) (Terry Howe)
- refactor(cli): decouple EnvSettings from pkg/kube [`64f1d0a`](https://github.com/helm/helm/commit/64f1d0af5b53f0a9292af2ba1efc42a46a57ed00) (Sumit Solanki)
- docs(registry): fix incorrect and improve clarity of comments in client.go [`85bf56e`](https://github.com/helm/helm/commit/85bf56ea82fd21452e53cae91b380b0afb3e8b83) (Debasish Mohanty)
- refactor(cli): decouple EnvSettings from pkg/kube to avoid import cycles [`1549937`](https://github.com/helm/helm/commit/154993723aadf45601d124c6750e8f4ae3b9f2fd) (Sumit Solanki)
- chore(deps): bump github.com/ProtonMail/go-crypto from 1.3.0 to 1.4.1 [`c7a75b1`](https://github.com/helm/helm/commit/c7a75b16cb8b0859bf32bf74ae98300e5b55361b) (dependabot\[bot])
- chore(deps): bump github.com/lib/pq from 1.11.2 to 1.12.0 [`3a7573a`](https://github.com/helm/helm/commit/3a7573a81ed5be2e00dfb74fa8d95c0cbe1c4f0d) (dependabot\[bot])
- chore(deps): bump github.com/fatih/color from 1.18.0 to 1.19.0 [`0229da1`](https://github.com/helm/helm/commit/0229da1803a29671b1becc4561c77f85db609aac) (dependabot\[bot])
- docs(engine): fix misleading toTOML doc comment [`c1a5a6e`](https://github.com/helm/helm/commit/c1a5a6e260bd070bce9a8299795400340e10c468) (Ilya Kiselev)
- feat(engine): add mustToToml template function [`b075f7a`](https://github.com/helm/helm/commit/b075f7a35d25ec0a4414b011142744f8f1821b47) (Ilya Kiselev)
- chore: fix unnecessary-format issues from revive [`7edfff3`](https://github.com/helm/helm/commit/7edfff33ebcb0f5d961afec34393c222de92de12) (Matthieu MOREL)
- chore(deps): bump google.golang.org/grpc from 1.78.0 to 1.79.3 [`37185d2`](https://github.com/helm/helm/commit/37185d2ea6a091b93d2e71cc55ab16b2c0f3f9e9) (dependabot\[bot])
- chore: fix bool-compare issues from testifylint [`071558d`](https://github.com/helm/helm/commit/071558d69ffbb408dcb56403d387a1aa90a7d3a8) (Matthieu MOREL)
- chore: enable perfsprint linter [`6249489`](https://github.com/helm/helm/commit/62494896e9a105b63df2c76c638c53304a37121e) (Matthieu MOREL)
- ignore error plugin loads (cli, getter) [`47a0840`](https://github.com/helm/helm/commit/47a084091eeb1c5de221e061866b319f5b5f99f5) (George Jenkins)
- chore(deps): bump golang.org/x/crypto from 0.48.0 to 0.49.0 [`3d06fd1`](https://github.com/helm/helm/commit/3d06fd1feb37f11d050e78f7c17df3c713fcd344) (dependabot\[bot])
- fix(kube): remove legacy import comments from test files [`e64d628`](https://github.com/helm/helm/commit/e64d628a139fab8c876a1d2f4c2928096b286bed) (Terry Howe)
- pkg/kube: remove legacy import comments [`d7cdc9e`](https://github.com/helm/helm/commit/d7cdc9e8fb20c42d19a2371f37ee719be6be6b94) (abhay1999)
- fix: Plugin version path traversal [`36dcc27`](https://github.com/helm/helm/commit/36dcc27ca3c0cd6d0d08713b03dca82f43d7c5f9) (George Jenkins)
- chore(deps): bump golang.org/x/term from 0.40.0 to 0.41.0 [`c4be7af`](https://github.com/helm/helm/commit/c4be7af2a14c1a01f21231ebb5dd41806fcb0797) (dependabot\[bot])
- chore: fix some minor issues in the comments [`259f181`](https://github.com/helm/helm/commit/259f181808f267493d56eccd7f6191f78225a6fa) (tsinglua)
- fix: Chart dot-name path bug [`6018499`](https://github.com/helm/helm/commit/60184996e5332d26e0b6390cefbf86776829dc46) (George Jenkins)
- chore(deps): bump sigs.k8s.io/controller-runtime from 0.23.1 to 0.23.3 [`74e7cf8`](https://github.com/helm/helm/commit/74e7cf877a4a674b65f7b7894d2dfde2832e39b1) (dependabot\[bot])
- fix: insert newline after doc separators glued to content by template trimming [`af94abf`](https://github.com/helm/helm/commit/af94abf976ce69dd635aaf086a0bb4b17bd95bc1) (Matheus Pimenta)
- chore(deps): bump github.com/cloudflare/circl from 1.6.1 to 1.6.3 [`16073b1`](https://github.com/helm/helm/commit/16073b1e3c7b90cda41ed70c8192eb6d16816723) (dependabot\[bot])
- chore: enable modernize linter ([#&#8203;31860](https://github.com/helm/helm/issues/31860)) [`e31a078`](https://github.com/helm/helm/commit/e31a078e6e0667dde72ff3bf4b5dfb625127076f) (Matthieu MOREL)
- Restored --atomic flag on install command [`16573f8`](https://github.com/helm/helm/commit/16573f87f5aebf8c2f9c40e67cc3cbe5eb93e733) (Travis Leeden)
- fix: bump go.opentelemetry.io/otel/sdk to v1.40.0 for GO-2026-4394 [`b550ce9`](https://github.com/helm/helm/commit/b550ce90946b3b47cecd290fc5d0eee637ddb531) (Terry Howe)
- fix: bump fluxcd/cli-utils to v0.37.2-flux.1 [`1dfa77e`](https://github.com/helm/helm/commit/1dfa77ed8ba6f9e26542064248bc9eab40c1a662) (Terry Howe)
- Update pkg/cmd/status.go [`5d40f17`](https://github.com/helm/helm/commit/5d40f17011a477620841edb740d381a012716ae8) (Matthieu MOREL)
- chore(internal): enable perfsprint linter ([#&#8203;31871](https://github.com/helm/helm/issues/31871)) [`d4f6193`](https://github.com/helm/helm/commit/d4f6193a7ec7ae9ea479da3372eeaf22b445ebcc) (Matthieu MOREL)
- chore(deps): bump actions/upload-artifact from 6.0.0 to 7.0.0 [`82d9bed`](https://github.com/helm/helm/commit/82d9bedea7d3e342011d82e2e11ff83b396dffbe) (dependabot\[bot])
- chore(pkg): fix perfsprint linter issues part 6 [`dc0e3f1`](https://github.com/helm/helm/commit/dc0e3f10c3ba8f25aa71c523d2e273690d338a17) (Matthieu MOREL)
- chore(pkg): enable perfsprint linter [`e3c74fd`](https://github.com/helm/helm/commit/e3c74fd9fae52c85899ee0ca9a0c1422d59e2bc2) (Matthieu MOREL)
- chore(pkg): enable perfsprint linter [`1d2d63c`](https://github.com/helm/helm/commit/1d2d63cc4330fcac786e70926f805b69c0b49ca2) (Matthieu MOREL)
- chore(pkg): enable perfsprint linter [`63f03c0`](https://github.com/helm/helm/commit/63f03c0f5c41b53de3d432b446da9430da99f5bd) (Matthieu MOREL)
- chore(pkg): enable perfsprint linter [`c25c988`](https://github.com/helm/helm/commit/c25c988cfb7bbe3b139dec39cad1db4be33b13c6) (Matthieu MOREL)
- chore(pkg): enable perfsprint linter [`0fecfd0`](https://github.com/helm/helm/commit/0fecfd04c2f9a748046a8421595f3b9da6c895c7) (Matthieu MOREL)
- chore(internal): enable perfsprint linter [`6524162`](https://github.com/helm/helm/commit/6524162a0e39bed187a16b692243703d78735471) (Matthieu MOREL)
- chore(pkg): enable perfsprint linter [`6c2cb2f`](https://github.com/helm/helm/commit/6c2cb2f54784b5ef6158dca0660f428a3baf75f5) (Matthieu MOREL)
- chore(internal): enable perfsprint linter [`9409226`](https://github.com/helm/helm/commit/9409226e15b26d05621f0b263f4ad6f597dfb7aa) (Matthieu MOREL)
- Replace unneeded use of t.Fatalf with t.Fatal [`36cb3a2`](https://github.com/helm/helm/commit/36cb3a2fe92a4564d2d7d79141f209af19b45d40) (Mads Jensen)
- fix: enable nolinlint linter [`5b6c6bb`](https://github.com/helm/helm/commit/5b6c6bbfc7ca9850c69d3823ca1e21b445e75c0d) (Matthieu MOREL)
- fixup `strings.Cut` variables [`b667317`](https://github.com/helm/helm/commit/b6673174220a2633fe97b5cd70a8386b79103464) (George Jenkins)
- chore: Improve `AGENTS.md` [`956c724`](https://github.com/helm/helm/commit/956c7245c346fc304c24ace930dada5f2c99f2b1) (George Jenkins)
- chore:  fixes [`92b64e8`](https://github.com/helm/helm/commit/92b64e87ad6245d64d5b49bbbbf8dead83faac22) (George Jenkins)
- fix: correct import comment in statuswait.go from v3 to v4 [`c59c140`](https://github.com/helm/helm/commit/c59c140ce07ce973f16fe50c0c5e991e1d6308a6) (rohansood10)
- fix: handle OCI digest algorithm prefix in chart downloader ([#&#8203;31601](https://github.com/helm/helm/issues/31601)) [`ee01860`](https://github.com/helm/helm/commit/ee018608f6fbf381fac1bae9759164a65c6a0b1f) (Evans Mungai)
- chore(deps): bump actions/stale from 10.1.1 to 10.2.0 [`304d25f`](https://github.com/helm/helm/commit/304d25ffd34fafccbcb81713cb3cfff1be595ae5) (dependabot\[bot])
- chore(deps): bump the k8s-io group with 7 updates [`0b13436`](https://github.com/helm/helm/commit/0b134362f442fec44ace35e9cfae6760a6b4e005) (dependabot\[bot])
- feat(release): add internal/release/v2 package for chart v3 support ([#&#8203;31709](https://github.com/helm/helm/issues/31709)) [`4a91f3a`](https://github.com/helm/helm/commit/4a91f3ad5cc0c1521f6d4dcb5681e2da4baaa157) (Evans Mungai)
- chore(deps): bump golang.org/x/crypto from 0.47.0 to 0.48.0 [`7823853`](https://github.com/helm/helm/commit/782385397ce1871f4c8a4d2e3c857937bd8988c9) (dependabot\[bot])
- chore(deps): bump golang.org/x/term from 0.39.0 to 0.40.0 [`aec7ace`](https://github.com/helm/helm/commit/aec7aced38d053a2df5d0973abdf21848778a722) (dependabot\[bot])
- chore(deps): bump github.com/lib/pq from 1.11.1 to 1.11.2 [`a23b638`](https://github.com/helm/helm/commit/a23b6388ac74984460fd4055de5120d2fc03d841) (dependabot\[bot])
- chore(deps): bump golang.org/x/text from 0.33.0 to 0.34.0 [`5cddc95`](https://github.com/helm/helm/commit/5cddc95bed0572b8d63a910843f0a70477a4ce33) (dependabot\[bot])
- chore(deps): bump sigs.k8s.io/kustomize/kyaml from 0.21.0 to 0.21.1 [`2e266c3`](https://github.com/helm/helm/commit/2e266c3ec9d70a6e656f8041bb31475e25e9eb22) (dependabot\[bot])
- fix(pkg): errorlint linter [`259f76a`](https://github.com/helm/helm/commit/259f76a849391e6ff60a9a2e95ce7310d958c602) (Matthieu MOREL)
- fix(internal): errorlint linter [`0254182`](https://github.com/helm/helm/commit/025418291a7911441e7962895ba4bc24b72b55b3) (Matthieu MOREL)
- fix(pkg): errorlint linter [`6d1490e`](https://github.com/helm/helm/commit/6d1490ed1ea5968235087658d03bb440e4014a36) (Matthieu MOREL)
- fix(pkg): errorlint linter [`4d0ae7f`](https://github.com/helm/helm/commit/4d0ae7f33a09093f8f52d02b952e3822c87b8c5f) (Matthieu MOREL)
- fix(internal): errorlint linter [`abecafa`](https://github.com/helm/helm/commit/abecafa0f507a69888877b9ddb714095714b64c8) (Matthieu MOREL)
- fix(pkg): errorlint linter [`4330bde`](https://github.com/helm/helm/commit/4330bdea0409f428e75145f15532bfa0e2bc945c) (Matthieu MOREL)
- fix(pkg): errorlint linter [`c8989d9`](https://github.com/helm/helm/commit/c8989d984ff69e8ad21b27d6ac6193dd3150b1a7) (Matthieu MOREL)
- fix(cmd): errorlint linter [`edbd705`](https://github.com/helm/helm/commit/edbd705bd034246700cc0998016caa303cff42dc) (Matthieu MOREL)
- chore: new KEYS entry for George Jenkins [`5638c35`](https://github.com/helm/helm/commit/5638c35399464b6432ba81b92a341218991efa5c) (George Jenkins)
- fix(downloader): safely handle concurrent file writes on Windows [`76eb37c`](https://github.com/helm/helm/commit/76eb37c01aaece271343039f44d7803017dd5c81) (Orgad Shaneh)
- fix(install): check nil for restClientGetter and fix tests [`9817a68`](https://github.com/helm/helm/commit/9817a68618245370e98e09d7f06c7cc1cefe8a62) (Manuel Alonso)
- feat(create): add --chart-api-version flag (when HELM\_EXPERIMENTAL\_CHART\_V3 env var is set) ([#&#8203;31592](https://github.com/helm/helm/issues/31592)) [`5aac320`](https://github.com/helm/helm/commit/5aac32077f87ed8cd80da1648abbd323320d4a0b) (Evans Mungai)
- chore(pkg): fix modernize linter [`0d75d86`](https://github.com/helm/helm/commit/0d75d8611d3daa6b820d94fc95347a069b062f72) (Matthieu MOREL)
- chore(internal): fix modernize linter [`859292e`](https://github.com/helm/helm/commit/859292e31bd4ceb170050eaa49e727bcd69572e2) (Matthieu MOREL)
- chore(pkg): fix modernize linter [`5cc2e55`](https://github.com/helm/helm/commit/5cc2e55714d20e6d1bd2663878a00571c084d6c2) (Matthieu MOREL)
- chore(pkg): fix modernize linter [`ba38159`](https://github.com/helm/helm/commit/ba38159313d4f09280591ba7f860ef0523716220) (Matthieu MOREL)
- chore(internal): fix modernize linter [`e2d184c`](https://github.com/helm/helm/commit/e2d184c79e9049c19bcc466bfe1289ccc6b73717) (Matthieu MOREL)
- chore(pkg): fix modernize linter [`111d4e6`](https://github.com/helm/helm/commit/111d4e6e0e86af6ba25a355be1a7599f5258ee58) (Matthieu MOREL)
- add image index test [`e8f386b`](https://github.com/helm/helm/commit/e8f386b5aac232c114a036598c2e3015fe296edc) (Pedro Tôrres)
- fix pulling charts from OCI indices [`d983696`](https://github.com/helm/helm/commit/d983696e354a9e0605cbb3034937dc84af42995c) (Pedro Tôrres)
- chore(deps): bump github.com/lib/pq from 1.10.9 to 1.11.1 [`9c9c3a6`](https://github.com/helm/helm/commit/9c9c3a6b5c0f1cd1e4c4e9f002aa411c58dd656a) (dependabot\[bot])
- Revert "Consider GroupVersionKind when matching resources" [`787b61c`](https://github.com/helm/helm/commit/787b61cedb933d22011e1da1368d0e615ea60ffe) (Matheus Pimenta)
- chore(deps): bump sigs.k8s.io/controller-runtime from 0.23.0 to 0.23.1 [`becf9bf`](https://github.com/helm/helm/commit/becf9bf7e33867a3f26affac34e9d51e277767bf) (dependabot\[bot])
- fix(template): deprecate unused --hide-notes and --render-subchart-notes flags [`6d5f56f`](https://github.com/helm/helm/commit/6d5f56fa6e7c8e4462d80895fcce87b926e4b8ce) (Scott Rigby)
- chore(deps): bump github.com/fluxcd/cli-utils [`b53198e`](https://github.com/helm/helm/commit/b53198e7eee04dab651c15cb7b3b6b77dd92553c) (dependabot\[bot])
- chore(deps): bump actions/checkout from 6.0.1 to 6.0.2 [`b59e533`](https://github.com/helm/helm/commit/b59e533b7675122631e0733adbfd6b35dd3515a6) (dependabot\[bot])
- whitespace [`ec07265`](https://github.com/helm/helm/commit/ec0726523e52448eb05c8b5b3faae969e3a79266) (Austin Abro)
- fix(copystructure): handle nil elements in slice copying [`e3829eb`](https://github.com/helm/helm/commit/e3829ebbbb833e159926c6193e474eb9d067ef75) (Philipp Born)
- use logger with waiter [`63b40a7`](https://github.com/helm/helm/commit/63b40a7a5e0d3f00ef2b4c1de9f50fb7d6df4ead) (Austin Abro)
- feat(kstatus): fine-grained context options for waiting [`b0b35f1`](https://github.com/helm/helm/commit/b0b35f1231b0b885b1624c5586938cfa69d30995) (Matheus Pimenta)
- Apply suggestions from code review [`26e28e8`](https://github.com/helm/helm/commit/26e28e846af1ceaf63e16c4f2e52bbfbab411ba1) (George Jenkins)
- Remove legacy sync-repo.sh script [`97fd007`](https://github.com/helm/helm/commit/97fd00786f16ebc3b68164bff7133592f19f70b6) (Jeevan Yewale)
- chore(deps): bump sigs.k8s.io/controller-runtime from 0.22.4 to 0.23.0 [`5262007`](https://github.com/helm/helm/commit/52620076e21ad6afd0f48df6772001b1466c966b) (dependabot\[bot])
- docs: document uninstall using cascade foreground flag [`e70d59d`](https://github.com/helm/helm/commit/e70d59de7cd7ea2a501d809b3245ebfa0412e0ec) (Evans Mungai)
- bugfix(kstatus): do not wait forever on failed resources [`bbec77c`](https://github.com/helm/helm/commit/bbec77c1f762c4d92678e7f455951757a2e036a3) (Matheus Pimenta)
- Modernize Helm v3 CONTRIBUTING.md [`443a2a6`](https://github.com/helm/helm/commit/443a2a6924fc384e87ff4251e5ac9c077d607f0f) (George Jenkins)
- chore(defaults): server-side apply SDK defaults should always match the CLI defaults [`c1cc625`](https://github.com/helm/helm/commit/c1cc6253232d697ad2ae29957cc49de223306b62) (Matheus Pimenta)
- chore: clarify --wait flag help text [`828038a`](https://github.com/helm/helm/commit/828038a8fe2142599ec557da2d12bb88b76fa0dd) (Evans Mungai)
- chore(deps): bump actions/setup-go from 6.1.0 to 6.2.0 [`e223771`](https://github.com/helm/helm/commit/e22377124dbca4b032c55f522358def0415a0e8a) (dependabot\[bot])
- chore(refactor): better testing and functionality for installing crd [`6501ef4`](https://github.com/helm/helm/commit/6501ef490a45e9b7edfed1432702532c5b11c6d2) (Manuel Alonso)
- bugfix(storage): fix storage not getting logger from driver [`a8eb527`](https://github.com/helm/helm/commit/a8eb5278478c940c615741312ca9f4fec0d84c1a) (Matheus Pimenta)
- chore(deps): bump golang.org/x/crypto from 0.46.0 to 0.47.0 [`da1d68a`](https://github.com/helm/helm/commit/da1d68adea91ab13b308c059c39381d48045a73a) (dependabot\[bot])
- fix(test): fix tests and check nil for restclient [`0f949a9`](https://github.com/helm/helm/commit/0f949a92c149cf11e5bb19caf4d19d05567be6eb) (Manuel Alonso)
- fix(test): merge fix correctly [`561410a`](https://github.com/helm/helm/commit/561410ae1d09c2aa289ff8d8cad5b7fa979cd135) (Manuel Alonso Gonzalez)
- Remove refactorring changes from coalesce\_test.go [`0298b2f`](https://github.com/helm/helm/commit/0298b2ffd0823eead74c75e1b890b0bf47d0db62) (Evans Mungai)
- Fix import [`b8937ad`](https://github.com/helm/helm/commit/b8937ad1922bca47be8bbf8e6274608ebc34a778) (Evans Mungai)
- Update pkg/chart/common/util/coalesce\_test.go [`a333bba`](https://github.com/helm/helm/commit/a333bbaf273645bf53fb873228040ca8edde849a) (Evans Mungai)
- Fix rollback for missing resources [`374aeb4`](https://github.com/helm/helm/commit/374aeb4b4e0463f72e3a0175138ed4bf7e87a156) (Feruzjon Muyassarov)
- fix(install): add more tests and check nil file data [`00f0a48`](https://github.com/helm/helm/commit/00f0a48a7dae379c2b6bd0dea43984d42b27a494) (Manuel Alonso)
- fix(test): no check empty resources [`0357e8d`](https://github.com/helm/helm/commit/0357e8d0f7eab074252ca49e1ca3aded834a001d) (Manuel Alonso)
- fix(install): check lenght and file nil, add tests [`52235cc`](https://github.com/helm/helm/commit/52235cc0bf7d0c8faf17c7dc8cddd77f93434aea) (Manuel Alonso)
- fix(action): crd resources can be empty [`268593b`](https://github.com/helm/helm/commit/268593bf2e9769ef4b75328b33dfb4195e6e9e5a) (Manuel Alonso)
- fix: casing issue fixed [`1709114`](https://github.com/helm/helm/commit/170911459bc4f2b5efea7e549e09bd45c7578cc4) (Mujib Ahasan)
- fix: error handled correctly [`9486062`](https://github.com/helm/helm/commit/94860626ce9c83a9227b5bce02a5c03a050816ac) (Mujib Ahasan)
- fix: doc string added [`12e8b71`](https://github.com/helm/helm/commit/12e8b715aa0732b613c3a9896fa6af29b3201536) (Mujib Ahasan)
- Fix lint warning [`3416dd5`](https://github.com/helm/helm/commit/3416dd5f215a6421a70c6ab22340a96312ce8c0b) (Evans Mungai)
- Preserve nil values in chart already [`679f051`](https://github.com/helm/helm/commit/679f0519804afeaa5ce8b930a30976ade2860fe0) (Evans Mungai)
- fix(values): preserve nil values when chart default is empty map [`292fe70`](https://github.com/helm/helm/commit/292fe702193e8ba9ce4c8ffffdd90cdfa761501c) (Evans Mungai)
- update: test coverage added for helper function validateNameAndGenerateName [`1154099`](https://github.com/helm/helm/commit/115409976b5c3fd94c893eabde114e655c01c573) (Mujib Ahasan)
- update: helper function added for the business logic [`522d2fe`](https://github.com/helm/helm/commit/522d2fe61508639cfe8f06a43235e7c3eaea3b9a) (Mujib Ahasan)
- generateName is also considered in logic [`6769fb6`](https://github.com/helm/helm/commit/6769fb6fb6704e29fe1215c802ecf0ea62b39715) (Mujib Ahasan)
- fxi: test concurrency download index [`64bae71`](https://github.com/helm/helm/commit/64bae717c58e80f05a60b84ddcd1f78387b4caee) (Terry Howe)
- update: business logic respected for skipping object missing name [`b357bca`](https://github.com/helm/helm/commit/b357bcae8640508f110b7e63a8dfacd865c27b6e) (Mujib Ahasan)
- fixed: --dry-run=server now respect generateName [`2820ebe`](https://github.com/helm/helm/commit/2820ebe8c97b7d7b8a447375b74c9cb3741a4ffa) (Mujib Ahasan)
- Make error message instructional for the case of lock file being out of date [`1836c59`](https://github.com/helm/helm/commit/1836c598f06377fd1571702fb2e0642f004cedef) (Andreas Sommer)

#### New Contributors

- [@&#8203;JeevanYewale](https://github.com/JeevanYewale) made their first contribution in [#&#8203;31742](https://github.com/helm/helm/pull/31742)
- [@&#8203;tamcore](https://github.com/tamcore) made their first contribution in [#&#8203;31751](https://github.com/helm/helm/pull/31751)
- [@&#8203;orgads](https://github.com/orgads) made their first contribution in [#&#8203;31128](https://github.com/helm/helm/pull/31128)
- [@&#8203;manute](https://github.com/manute) made their first contribution in [#&#8203;31578](https://github.com/helm/helm/pull/31578)
- [@&#8203;Mujib-Ahasan](https://github.com/Mujib-Ahasan) made their first contribution in [#&#8203;31563](https://github.com/helm/helm/pull/31563)
- [@&#8203;rohansood10](https://github.com/rohansood10) made their first contribution in [#&#8203;31852](https://github.com/helm/helm/pull/31852)
- [@&#8203;tleed5](https://github.com/tleed5) made their first contribution in [#&#8203;31901](https://github.com/helm/helm/pull/31901)
- [@&#8203;tsinglua](https://github.com/tsinglua) made their first contribution in [#&#8203;31921](https://github.com/helm/helm/pull/31921)
- [@&#8203;abhay1999](https://github.com/abhay1999) made their first contribution in [#&#8203;31931](https://github.com/helm/helm/pull/31931)
- [@&#8203;Mentigen](https://github.com/Mentigen) made their first contribution in [#&#8203;31957](https://github.com/helm/helm/pull/31957)
- [@&#8203;Debasish-87](https://github.com/Debasish-87) made their first contribution in [#&#8203;31973](https://github.com/helm/helm/pull/31973)
- [@&#8203;AnmolVirdi](https://github.com/AnmolVirdi) made their first contribution in [#&#8203;32014](https://github.com/helm/helm/pull/32014)
- [@&#8203;Y0-L0](https://github.com/Y0-L0) made their first contribution in [#&#8203;31979](https://github.com/helm/helm/pull/31979)
- [@&#8203;MohitSalvi16](https://github.com/MohitSalvi16) made their first contribution in [#&#8203;32057](https://github.com/helm/helm/pull/32057)
- [@&#8203;rhysmcneill](https://github.com/rhysmcneill) made their first contribution in [#&#8203;32008](https://github.com/helm/helm/pull/32008)
- [@&#8203;cairon-ab](https://github.com/cairon-ab) made their first contribution in [#&#8203;32034](https://github.com/helm/helm/pull/32034)
- [@&#8203;gaganhr94](https://github.com/gaganhr94) made their first contribution in [#&#8203;31923](https://github.com/helm/helm/pull/31923)
- [@&#8203;isumitsolanki](https://github.com/isumitsolanki) made their first contribution in [#&#8203;31970](https://github.com/helm/helm/pull/31970)

**Full Changelog**: <https://github.com/helm/helm/compare/v4.1.0...v4.2.0>

</details>

---

### Configuration

📅 **Schedule**: (in timezone Europe/Oslo)

- Branch creation
  - At any time (no schedule defined)
- Automerge
  - At any time (no schedule defined)

🚦 **Automerge**: Disabled by config. Please merge this manually once you are satisfied.

♻ **Rebasing**: Whenever PR becomes conflicted, or you tick the rebase/retry checkbox.

🔕 **Ignore**: Close this PR and you won't be reminded about this update again.

---

 - [ ] <!-- rebase-check -->If you want to rebase/retry this PR, check this box

---

This PR has been generated by [Mend Renovate CLI](https://github.com/renovatebot/renovate).
<!--renovate-debug:eyJjcmVhdGVkSW5WZXIiOiI0NC4xMTIuMyIsInVwZGF0ZWRJblZlciI6IjQ0LjExMi4zIiwidGFyZ2V0QnJhbmNoIjoibWFpbiIsImxhYmVscyI6WyJyZW5vdmF0ZSJdfQ==-->

---------

Co-authored-by: Renovate Bot <renovate@forteapps.net>
Reviewed-on: https://git.forteapps.net/Forte/launchpad/pulls/48
Reviewed-by: Danijel Simeunovic <danijel.simeunovic@fortedigital.com>
Co-authored-by: gitea_admin <admin@forteapps.net>
2026-09-29 07:06:48 +00:00
ff7e4b8894 chore(deps): update actions/checkout action to v7 (#41)
scan.yaml / test (push) Successful in 13s
This PR contains the following updates:

| Package | Type | Update | Change |
|---|---|---|---|
| [actions/checkout](https://github.com/actions/checkout) | action | major | `v4` → `v7` |

---

### Release Notes

<details>
<summary>actions/checkout (actions/checkout)</summary>

### [`v7.0.1`](https://github.com/actions/checkout/blob/HEAD/CHANGELOG.md#v701)

[Compare Source](https://github.com/actions/checkout/compare/v7.0.0...v7.0.1)

- Skip running unsafe pr check if input is default by [@&#8203;aiqiaoy](https://github.com/aiqiaoy) in [#&#8203;2518](https://github.com/actions/checkout/pull/2518)
- Trim only ascii whitespace for branch by [@&#8203;aiqiaoy](https://github.com/aiqiaoy) in [#&#8203;2521](https://github.com/actions/checkout/pull/2521)
- Escape values passed to --unset by [@&#8203;aiqiaoy](https://github.com/aiqiaoy) in [#&#8203;2530](https://github.com/actions/checkout/pull/2530)
- Various dependency updates

### [`v7.0.0`](https://github.com/actions/checkout/blob/HEAD/CHANGELOG.md#v700)

[Compare Source](https://github.com/actions/checkout/compare/v6.1.0...v7.0.0)

- Block checking out fork PR for pull\_request\_target and workflow\_run by [@&#8203;aiqiaoy](https://github.com/aiqiaoy) in [#&#8203;2454](https://github.com/actions/checkout/pull/2454)
- Various dependency updates

### [`v6.1.0`](https://github.com/actions/checkout/releases/tag/v6.1.0)

[Compare Source](https://github.com/actions/checkout/compare/v6.0.3...v6.1.0)

#### What's Changed

- **\[BREAKING]** backport `allow-unsafe-pr-checkout` to v6 by [@&#8203;aiqiaoy](https://github.com/aiqiaoy) in [#&#8203;2500](https://github.com/actions/checkout/pull/2500)
- backport fixes to releases-v6 by [@&#8203;aiqiaoy](https://github.com/aiqiaoy) in [#&#8203;2527](https://github.com/actions/checkout/pull/2527)

<https://github.blog/changelog/2026-06-18-safer-pull_request_target-defaults-for-github-actions-checkout/> for more details about this breaking change

**Full Changelog**: <https://github.com/actions/checkout/compare/v6.0.3...v6.1.0>

### [`v6.0.3`](https://github.com/actions/checkout/blob/HEAD/CHANGELOG.md#v603)

[Compare Source](https://github.com/actions/checkout/compare/v6.0.2...v6.0.3)

- Fix checkout init for SHA-256 repositories by [@&#8203;yaananth](https://github.com/yaananth) in [#&#8203;2439](https://github.com/actions/checkout/pull/2439)
- fix: expand merge commit SHA regex and add SHA-256 test cases by [@&#8203;yaananth](https://github.com/yaananth) in [#&#8203;2414](https://github.com/actions/checkout/pull/2414)

### [`v6.0.2`](https://github.com/actions/checkout/blob/HEAD/CHANGELOG.md#v602)

[Compare Source](https://github.com/actions/checkout/compare/v6.0.1...v6.0.2)

- Fix tag handling: preserve annotations and explicit fetch-tags by [@&#8203;ericsciple](https://github.com/ericsciple) in [#&#8203;2356](https://github.com/actions/checkout/pull/2356)

### [`v6.0.1`](https://github.com/actions/checkout/blob/HEAD/CHANGELOG.md#v601)

[Compare Source](https://github.com/actions/checkout/compare/v6.0.0...v6.0.1)

- Add worktree support for persist-credentials includeIf by [@&#8203;ericsciple](https://github.com/ericsciple) in [#&#8203;2327](https://github.com/actions/checkout/pull/2327)

### [`v6.0.0`](https://github.com/actions/checkout/blob/HEAD/CHANGELOG.md#v600)

[Compare Source](https://github.com/actions/checkout/compare/v5.1.0...v6.0.0)

- Persist creds to a separate file by [@&#8203;ericsciple](https://github.com/ericsciple) in [#&#8203;2286](https://github.com/actions/checkout/pull/2286)
- Update README to include Node.js 24 support details and requirements by [@&#8203;salmanmkc](https://github.com/salmanmkc) in [#&#8203;2248](https://github.com/actions/checkout/pull/2248)

### [`v5.1.0`](https://github.com/actions/checkout/releases/tag/v5.1.0)

[Compare Source](https://github.com/actions/checkout/compare/v5.0.1...v5.1.0)

#### What's Changed

- **\[BREAKING]** backport `allow-unsafe-pr-checkout` to v5 by [@&#8203;aiqiaoy](https://github.com/aiqiaoy) in [#&#8203;2501](https://github.com/actions/checkout/pull/2501)
- backport fixes to releases-v5 by [@&#8203;aiqiaoy](https://github.com/aiqiaoy) in [#&#8203;2523](https://github.com/actions/checkout/pull/2523)

<https://github.blog/changelog/2026-06-18-safer-pull_request_target-defaults-for-github-actions-checkout/> for more details about this breaking change

**Full Changelog**: <https://github.com/actions/checkout/compare/v5.0.1...v5.1.0>

### [`v5.0.1`](https://github.com/actions/checkout/blob/HEAD/CHANGELOG.md#v501)

[Compare Source](https://github.com/actions/checkout/compare/v5.0.0...v5.0.1)

- Port v6 cleanup to v5 by [@&#8203;ericsciple](https://github.com/ericsciple) in [#&#8203;2301](https://github.com/actions/checkout/pull/2301)

### [`v5.0.0`](https://github.com/actions/checkout/blob/HEAD/CHANGELOG.md#v500)

[Compare Source](https://github.com/actions/checkout/compare/v4.4.0...v5.0.0)

- Update actions checkout to use node 24 by [@&#8203;salmanmkc](https://github.com/salmanmkc) in [#&#8203;2226](https://github.com/actions/checkout/pull/2226)

</details>

---

### Configuration

📅 **Schedule**: (in timezone Europe/Oslo)

- Branch creation
  - At any time (no schedule defined)
- Automerge
  - At any time (no schedule defined)

🚦 **Automerge**: Disabled by config. Please merge this manually once you are satisfied.

♻ **Rebasing**: Whenever PR becomes conflicted, or you tick the rebase/retry checkbox.

🔕 **Ignore**: Close this PR and you won't be reminded about this update again.

---

 - [ ] <!-- rebase-check -->If you want to rebase/retry this PR, check this box

---

This PR has been generated by [Mend Renovate CLI](https://github.com/renovatebot/renovate).
<!--renovate-debug:eyJjcmVhdGVkSW5WZXIiOiI0NC4xMTIuMyIsInVwZGF0ZWRJblZlciI6IjQ0LjExMi4zIiwidGFyZ2V0QnJhbmNoIjoibWFpbiIsImxhYmVscyI6WyJyZW5vdmF0ZSJdfQ==-->

---------

Co-authored-by: Renovate Bot <renovate@forteapps.net>
Reviewed-on: #41
Reviewed-by: Danijel Simeunovic <danijel.simeunovic@fortedigital.com>
Co-authored-by: gitea_admin <admin@forteapps.net>
2026-09-29 07:05:19 +00:00
danijel.simeunovic 5bb21167fd chore(deps): update dependency claude-code to v2
scan.yaml / test (push) Successful in 17s
AI Code Review / ai-review (pull_request) Skipped
scan.yaml / test (pull_request) Successful in 15s
commit 00efdd8cd2
Author: gitea_admin <admin@forteapps.net>
Date:   Tue Sep 29 07:00:47 2026 +0000

    chore(deps): update dependency github-cli to v2 (#47)

    This PR contains the following updates:

    | Package | Update | Change |
    |---|---|---|
    | [github-cli](https://cli.github.com/) | major | `0.12.0` → `2.23.0` |

    ---

    ### Configuration

    📅 **Schedule**: (in timezone Europe/Oslo)

    - Branch creation
      - At any time (no schedule defined)
    - Automerge
      - At any time (no schedule defined)

    🚦 **Automerge**: Disabled by config. Please merge this manually once you are satisfied.

    ♻ **Rebasing**: Whenever PR becomes conflicted, or you tick the rebase/retry checkbox.

    🔕 **Ignore**: Close this PR and you won't be reminded about this update again.

    ---

     - [ ] <!-- rebase-check -->If you want to rebase/retry this PR, check this box

    ---

    This PR has been generated by [Mend Renovate CLI](https://github.com/renovatebot/renovate).
    <!--renovate-debug:eyJjcmVhdGVkSW5WZXIiOiI0NC4xMTIuMyIsInVwZGF0ZWRJblZlciI6IjQ0LjExMi4zIiwidGFyZ2V0QnJhbmNoIjoibWFpbiIsImxhYmVscyI6WyJyZW5vdmF0ZSJdfQ==-->

    ---------

    Co-authored-by: Renovate Bot <renovate@forteapps.net>
    Reviewed-on: #47
    Reviewed-by: Danijel Simeunovic <danijel.simeunovic@fortedigital.com>
    Co-authored-by: gitea_admin <admin@forteapps.net>

commit d480daccc8
Author: gitea_admin <admin@forteapps.net>
Date:   Tue Sep 29 07:00:03 2026 +0000

    chore(deps): update dependency argocd to v3 (#43)

    This PR contains the following updates:

    | Package | Update | Change |
    |---|---|---|
    | [argocd](https://argo-cd.readthedocs.io/en/stable/) | major | `2.14.11` → `3.4.6` |

    ---

    ### Configuration

    📅 **Schedule**: (in timezone Europe/Oslo)

    - Branch creation
      - At any time (no schedule defined)
    - Automerge
      - At any time (no schedule defined)

    🚦 **Automerge**: Disabled by config. Please merge this manually once you are satisfied.

    ♻ **Rebasing**: Whenever PR becomes conflicted, or you tick the rebase/retry checkbox.

    🔕 **Ignore**: Close this PR and you won't be reminded about this update again.

    ---

     - [ ] <!-- rebase-check -->If you want to rebase/retry this PR, check this box

    ---

    This PR has been generated by [Mend Renovate CLI](https://github.com/renovatebot/renovate).
    <!--renovate-debug:eyJjcmVhdGVkSW5WZXIiOiI0NC4xMTIuMyIsInVwZGF0ZWRJblZlciI6IjQ0LjExMi4zIiwidGFyZ2V0QnJhbmNoIjoibWFpbiIsImxhYmVscyI6WyJyZW5vdmF0ZSJdfQ==-->

    ---------

    Co-authored-by: Renovate Bot <renovate@forteapps.net>
    Reviewed-on: #43
    Reviewed-by: Danijel Simeunovic <danijel.simeunovic@fortedigital.com>
    Co-authored-by: gitea_admin <admin@forteapps.net>

commit 66f1dce46f
Author: gitea_admin <admin@forteapps.net>
Date:   Tue Sep 29 06:59:17 2026 +0000

    chore(deps): update dependency dotnet-sdk to v8 (#46)

    This PR contains the following updates:

    | Package | Update | Change |
    |---|---|---|
    | [dotnet-sdk](https://dotnet.github.io/) | major | `2.1.810` → `8.0.424` |

    ---

    ### Configuration

    📅 **Schedule**: (in timezone Europe/Oslo)

    - Branch creation
      - At any time (no schedule defined)
    - Automerge
      - At any time (no schedule defined)

    🚦 **Automerge**: Disabled by config. Please merge this manually once you are satisfied.

    ♻ **Rebasing**: Whenever PR becomes conflicted, or you tick the rebase/retry checkbox.

    🔕 **Ignore**: Close this PR and you won't be reminded about this update again.

    ---

     - [ ] <!-- rebase-check -->If you want to rebase/retry this PR, check this box

    ---

    This PR has been generated by [Mend Renovate CLI](https://github.com/renovatebot/renovate).
    <!--renovate-debug:eyJjcmVhdGVkSW5WZXIiOiI0NC4xMTIuMyIsInVwZGF0ZWRJblZlciI6IjQ0LjExMi4zIiwidGFyZ2V0QnJhbmNoIjoibWFpbiIsImxhYmVscyI6WyJyZW5vdmF0ZSJdfQ==-->

    ---------

    Co-authored-by: Renovate Bot <renovate@forteapps.net>
    Reviewed-on: #46
    Reviewed-by: Danijel Simeunovic <danijel.simeunovic@fortedigital.com>
    Co-authored-by: gitea_admin <admin@forteapps.net>
2026-09-29 09:03:34 +02:00
00efdd8cd2 chore(deps): update dependency github-cli to v2 (#47)
scan.yaml / test (push) Successful in 14s
This PR contains the following updates:

| Package | Update | Change |
|---|---|---|
| [github-cli](https://cli.github.com/) | major | `0.12.0` → `2.23.0` |

---

### Configuration

📅 **Schedule**: (in timezone Europe/Oslo)

- Branch creation
  - At any time (no schedule defined)
- Automerge
  - At any time (no schedule defined)

🚦 **Automerge**: Disabled by config. Please merge this manually once you are satisfied.

♻ **Rebasing**: Whenever PR becomes conflicted, or you tick the rebase/retry checkbox.

🔕 **Ignore**: Close this PR and you won't be reminded about this update again.

---

 - [ ] <!-- rebase-check -->If you want to rebase/retry this PR, check this box

---

This PR has been generated by [Mend Renovate CLI](https://github.com/renovatebot/renovate).
<!--renovate-debug:eyJjcmVhdGVkSW5WZXIiOiI0NC4xMTIuMyIsInVwZGF0ZWRJblZlciI6IjQ0LjExMi4zIiwidGFyZ2V0QnJhbmNoIjoibWFpbiIsImxhYmVscyI6WyJyZW5vdmF0ZSJdfQ==-->

---------

Co-authored-by: Renovate Bot <renovate@forteapps.net>
Reviewed-on: #47
Reviewed-by: Danijel Simeunovic <danijel.simeunovic@fortedigital.com>
Co-authored-by: gitea_admin <admin@forteapps.net>
2026-09-29 07:00:47 +00:00
d480daccc8 chore(deps): update dependency argocd to v3 (#43)
scan.yaml / test (push) Successful in 15s
This PR contains the following updates:

| Package | Update | Change |
|---|---|---|
| [argocd](https://argo-cd.readthedocs.io/en/stable/) | major | `2.14.11` → `3.4.6` |

---

### Configuration

📅 **Schedule**: (in timezone Europe/Oslo)

- Branch creation
  - At any time (no schedule defined)
- Automerge
  - At any time (no schedule defined)

🚦 **Automerge**: Disabled by config. Please merge this manually once you are satisfied.

♻ **Rebasing**: Whenever PR becomes conflicted, or you tick the rebase/retry checkbox.

🔕 **Ignore**: Close this PR and you won't be reminded about this update again.

---

 - [ ] <!-- rebase-check -->If you want to rebase/retry this PR, check this box

---

This PR has been generated by [Mend Renovate CLI](https://github.com/renovatebot/renovate).
<!--renovate-debug:eyJjcmVhdGVkSW5WZXIiOiI0NC4xMTIuMyIsInVwZGF0ZWRJblZlciI6IjQ0LjExMi4zIiwidGFyZ2V0QnJhbmNoIjoibWFpbiIsImxhYmVscyI6WyJyZW5vdmF0ZSJdfQ==-->

---------

Co-authored-by: Renovate Bot <renovate@forteapps.net>
Reviewed-on: #43
Reviewed-by: Danijel Simeunovic <danijel.simeunovic@fortedigital.com>
Co-authored-by: gitea_admin <admin@forteapps.net>
2026-09-29 07:00:03 +00:00
66f1dce46f chore(deps): update dependency dotnet-sdk to v8 (#46)
scan.yaml / test (push) Successful in 17s
This PR contains the following updates:

| Package | Update | Change |
|---|---|---|
| [dotnet-sdk](https://dotnet.github.io/) | major | `2.1.810` → `8.0.424` |

---

### Configuration

📅 **Schedule**: (in timezone Europe/Oslo)

- Branch creation
  - At any time (no schedule defined)
- Automerge
  - At any time (no schedule defined)

🚦 **Automerge**: Disabled by config. Please merge this manually once you are satisfied.

♻ **Rebasing**: Whenever PR becomes conflicted, or you tick the rebase/retry checkbox.

🔕 **Ignore**: Close this PR and you won't be reminded about this update again.

---

 - [ ] <!-- rebase-check -->If you want to rebase/retry this PR, check this box

---

This PR has been generated by [Mend Renovate CLI](https://github.com/renovatebot/renovate).
<!--renovate-debug:eyJjcmVhdGVkSW5WZXIiOiI0NC4xMTIuMyIsInVwZGF0ZWRJblZlciI6IjQ0LjExMi4zIiwidGFyZ2V0QnJhbmNoIjoibWFpbiIsImxhYmVscyI6WyJyZW5vdmF0ZSJdfQ==-->

---------

Co-authored-by: Renovate Bot <renovate@forteapps.net>
Reviewed-on: #46
Reviewed-by: Danijel Simeunovic <danijel.simeunovic@fortedigital.com>
Co-authored-by: gitea_admin <admin@forteapps.net>
2026-09-29 06:59:17 +00:00
danijel.simeunovic 5960da5522 chore(deps): update all non-major dependencies
/ test (push) Has started running
scan.yaml / test (push) Failing after 13m4s
2026-09-29 00:18:26 +02:00
ebbb06d7a2 chore(deps): update dependency _1password to v2 (#42)
/ test (push) Successful in 23s
This PR contains the following updates:

| Package | Update | Change |
|---|---|---|
| [_1password](https://developer.1password.com/docs/cli/) | major | `1.12.2` → `2.30.0` |

---

### Configuration

📅 **Schedule**: (in timezone Europe/Oslo)

- Branch creation
  - At any time (no schedule defined)
- Automerge
  - At any time (no schedule defined)

🚦 **Automerge**: Disabled by config. Please merge this manually once you are satisfied.

♻ **Rebasing**: Whenever PR becomes conflicted, or you tick the rebase/retry checkbox.

🔕 **Ignore**: Close this PR and you won't be reminded about this update again.

---

 - [ ] <!-- rebase-check -->If you want to rebase/retry this PR, check this box

---

This PR has been generated by [Mend Renovate CLI](https://github.com/renovatebot/renovate).
<!--renovate-debug:eyJjcmVhdGVkSW5WZXIiOiI0NC4xMTIuMyIsInVwZGF0ZWRJblZlciI6IjQ0LjExMi4zIiwidGFyZ2V0QnJhbmNoIjoibWFpbiIsImxhYmVscyI6WyJyZW5vdmF0ZSJdfQ==-->

---------

Co-authored-by: Renovate Bot <renovate@forteapps.net>
Reviewed-on: #42
Reviewed-by: Danijel Simeunovic <danijel.simeunovic@fortedigital.com>
Co-authored-by: gitea_admin <admin@forteapps.net>
Co-committed-by: gitea_admin <admin@forteapps.net>
2026-09-28 06:55:46 +00:00
52068dc533 chore(deps): update dependency grype to v0.118.0 (#34)
/ test (push) Failing after 14m26s
This PR contains the following updates:

| Package | Update | Change |
|---|---|---|
| [grype](https://github.com/anchore/grype) | minor | `0.92.2` → `0.118.0` |

---

### Release Notes

<details>
<summary>anchore/grype (grype)</summary>

### [`v0.118.0`](https://github.com/anchore/grype/releases/tag/v0.118.0)

##### Added Features

- apk matcher does alias aware aggregation \[PR [#&#8203;3634](https://github.com/anchore/grype/pull/3634) [@&#8203;crosleyzack](https://github.com/crosleyzack)]

##### Bug Fixes

- prevent panic on portage versions without digits \[PR [#&#8203;3655](https://github.com/anchore/grype/pull/3655) [@&#8203;ashvinctrl](https://github.com/ashvinctrl)]
- grype vex does not match oci purl with repository\_url \[Issue [#&#8203;3657](https://github.com/anchore/grype/issues/3657)] \[PR [#&#8203;3659](https://github.com/anchore/grype/pull/3659) [@&#8203;spiffcs](https://github.com/spiffcs)]
- Old JVM version comparisons sometimes incorrect \[Issue [#&#8203;2701](https://github.com/anchore/grype/issues/2701)] \[PR [#&#8203;3583](https://github.com/anchore/grype/pull/3583) [@&#8203;Eljees](https://github.com/Eljees)]
- CVSSv4 calculation can produce incorrect vulnerability severity \[Issue [#&#8203;3656](https://github.com/anchore/grype/issues/3656)]
- Grype 0.90.0 DB update failed \[Issue [#&#8203;3629](https://github.com/anchore/grype/issues/3629)]

##### Dependencies

72 dependency changes (70 updated, 1 added, 1 removed). 3 vulnerabilities remediated.

**🟢 Remediated (3)**

- [GO-2026-5158](https://github.com/open-telemetry/opentelemetry-go/security/advisories/GHSA-5wrp-cwcj-q835) (Medium) — go.opentelemetry.io/otel
- [GO-2026-6179](https://go.dev/issue/80744) (High) — golang.org/x/mod
- [GO-2026-6180](https://go.dev/issue/80745) (High) — golang.org/x/mod

<details>
<summary>Updated (70 packages)</summary>

- cel.dev/expr `v0.25.1` → `v0.25.2`
- cloud.google.com/go/auth `v0.18.2` → `v0.22.0`
- cloud.google.com/go/iam `v1.5.3` → `v1.11.0`
- cloud.google.com/go/logging `v1.13.1` → `v1.18.0`
- cloud.google.com/go/longrunning `v0.8.0` → `v1.2.0`
- cloud.google.com/go/monitoring `v1.24.3` → `v1.29.0`
- cloud.google.com/go/storage `v1.61.3` → `v1.64.0`
- cloud.google.com/go/trace `v1.11.7` → `v1.16.0`
- github.com/GoogleCloudPlatform/opentelemetry-operations-go/detectors/gcp `v1.32.0` → `v1.33.0`
- github.com/GoogleCloudPlatform/opentelemetry-operations-go/exporter/metric `v0.55.0` → `v0.57.0`
- github.com/GoogleCloudPlatform/opentelemetry-operations-go/internal/cloudmock `v0.55.0` → `v0.57.0`
- github.com/GoogleCloudPlatform/opentelemetry-operations-go/internal/resourcemapping `v0.55.0` → `v0.57.0`
- github.com/anchore/stereoscope `v0.3.0` → `v0.3.1`
- github.com/anchore/syft `v1.51.0` → `v1.51.1`
- github.com/aws/aws-sdk-go-v2 `v1.41.5` → `v1.43.4`
- github.com/aws/aws-sdk-go-v2/aws/protocol/eventstream `v1.7.8` → `v1.7.16`
- github.com/aws/aws-sdk-go-v2/config `v1.32.12` → `v1.32.35`
- github.com/aws/aws-sdk-go-v2/credentials `v1.19.12` → `v1.19.34`
- github.com/aws/aws-sdk-go-v2/feature/ec2/imds `v1.18.20` → `v1.18.35`
- github.com/aws/aws-sdk-go-v2/internal/configsources `v1.4.21` → `v1.4.35`
- github.com/aws/aws-sdk-go-v2/internal/endpoints/v2 `v2.7.21` → `v2.7.35`
- github.com/aws/aws-sdk-go-v2/internal/v4a `v1.4.22` → `v1.4.36`
- github.com/aws/aws-sdk-go-v2/service/internal/accept-encoding `v1.13.7` → `v1.13.15`
- github.com/aws/aws-sdk-go-v2/service/internal/checksum `v1.9.13` → `v1.9.28`
- github.com/aws/aws-sdk-go-v2/service/internal/presigned-url `v1.13.21` → `v1.13.35`
- github.com/aws/aws-sdk-go-v2/service/internal/s3shared `v1.19.21` → `v1.19.36`
- github.com/aws/aws-sdk-go-v2/service/s3 `v1.97.3` → `v1.106.5`
- github.com/aws/aws-sdk-go-v2/service/signin `v1.0.8` → `v1.5.4`
- github.com/aws/aws-sdk-go-v2/service/sso `v1.30.13` → `v1.33.4`
- github.com/aws/aws-sdk-go-v2/service/ssooidc `v1.35.17` → `v1.38.4`
- github.com/aws/aws-sdk-go-v2/service/sts `v1.41.9` → `v1.45.4`
- github.com/aws/smithy-go `v1.24.2` → `v1.27.6`
- github.com/containerd/containerd/v2 `v2.3.3` → `v2.3.4`
- github.com/containerd/platforms `v1.0.0-rc.4` → `v1.0.0-rc.5`
- github.com/docker/cli `v29.6.1+incompatible` → `v29.7.2+incompatible`
- github.com/docker/go-connections `v0.7.0` → `v0.8.1`
- github.com/fatih/color `v1.18.0` → `v1.19.0`
- github.com/google/go-containerregistry `v0.21.7` → `v0.21.9`
- github.com/google/pprof `v0.0.0-6e76a2b` → `v0.0.0-ef3492d`
- github.com/googleapis/enterprise-certificate-proxy `v0.3.14` → `v0.3.19`
- github.com/googleapis/gax-go/v2 `v2.17.0` → `v2.23.0`
- github.com/hashicorp/aws-sdk-go-base/v2 `v2.0.0-beta.72` → `v2.0.0-beta.74`
- github.com/hashicorp/go-getter `v1.8.6` → `v1.8.8`
- github.com/hashicorp/go-version `v1.8.0` → `v1.9.0`
- github.com/klauspost/compress `v1.19.1` → `v1.19.2`
- github.com/mattn/go-isatty `v0.0.20` → `v0.0.24`
- github.com/moby/moby/client `v0.5.0` → `v0.5.1`
- github.com/spiffe/go-spiffe/v2 `v2.6.0` → `v2.7.0`
- github.com/stretchr/objx `v0.5.2` → `v0.5.3`
- github.com/stretchr/testify `v1.11.1` → `v1.12.1`
- go.opentelemetry.io/contrib/detectors/gcp `v1.43.0` → `v1.44.0`
- go.opentelemetry.io/otel `v1.43.0` → `v1.44.0` **(🟢 remediated [GO-2026-5158](https://github.com/open-telemetry/opentelemetry-go/security/advisories/GHSA-5wrp-cwcj-q835))**
- go.opentelemetry.io/otel/exporters/stdout/stdoutmetric `v1.40.0` → `v1.44.0`
- go.opentelemetry.io/otel/metric `v1.43.0` → `v1.44.0`
- go.opentelemetry.io/otel/sdk `v1.43.0` → `v1.44.0`
- go.opentelemetry.io/otel/sdk/metric `v1.43.0` → `v1.44.0`
- go.opentelemetry.io/otel/trace `v1.43.0` → `v1.44.0`
- golang.org/x/crypto `v0.54.0` → `v0.55.0`
- golang.org/x/mod `v0.38.0` → `v0.40.0` **(🟢 remediated [GO-2026-6179](https://go.dev/issue/80744), [GO-2026-6180](https://go.dev/issue/80745))**
- golang.org/x/net `v0.57.0` → `v0.58.0`
- golang.org/x/text `v0.40.0` → `v0.41.0`
- golang.org/x/tools `v0.48.0` → `v0.49.0`
- google.golang.org/api `v0.271.0` → `v0.292.0`
- google.golang.org/genproto `v0.0.0-8636f87` → `v0.0.0-aa98bba`
- google.golang.org/genproto/googleapis/api `v0.0.0-afd174a` → `v0.0.0-925bb5d`
- google.golang.org/genproto/googleapis/rpc `v0.0.0-afd174a` → `v0.0.0-6ac0973`
- google.golang.org/grpc `v1.82.1` → `v1.83.0`
- modernc.org/cc/v4 `v4.29.0` → `v4.29.1`
- modernc.org/libc `v1.74.1` → `v1.74.4`
- modernc.org/sqlite `v1.55.0` → `v1.56.0`

</details>

<details>
<summary>Added (1 package)</summary>

- go.opentelemetry.io/otel/metric/x `v0.66.0`

</details>

<details>
<summary>Removed (1 package)</summary>

- github.com/aws/aws-sdk-go-v2/internal/ini `v1.8.6`

</details>

**[(Full Changelog)](https://github.com/anchore/grype/compare/v0.117.0...v0.118.0)**

### [`v0.117.0`](https://github.com/anchore/grype/releases/tag/v0.117.0)

##### Added Features

- Include vulnerable ranges in CycloneDX output format \[Issue [#&#8203;3512](https://github.com/anchore/grype/issues/3512)] \[PR [#&#8203;3519](https://github.com/anchore/grype/pull/3519) [@&#8203;somaz94](https://github.com/somaz94)]

##### Bug Fixes

- honor match.rust.using-cpes configuration \[PR [#&#8203;3611](https://github.com/anchore/grype/pull/3611) [@&#8203;Dashtid](https://github.com/Dashtid)]

##### Dependencies

11 dependency changes (11 updated). 2 vulnerabilities remediated.

**🟢 Remediated (2)**

- [GHSA-hc8v-wwc9-vgxm](https://github.com/advisories/GHSA-hc8v-wwc9-vgxm) (High) — github.com/go-git/go-git/v5
- [GHSA-qgq7-7hm3-q39j](https://github.com/advisories/GHSA-qgq7-7hm3-q39j) (Medium) — github.com/go-git/go-git/v5

<details>
<summary>Updated (11 packages)</summary>

- github.com/anchore/syft `v1.50.0` → `v1.51.0`
- github.com/diskfs/go-diskfs `v1.9.3` → `v1.9.4`
- github.com/gabriel-vasile/mimetype `v1.4.13` → `v1.4.15`
- github.com/go-git/go-billy/v5 `v5.9.0` → `v5.9.1`
- github.com/go-git/go-git/v5 `v5.19.1` → `v5.19.2` **(🟢 remediated [GHSA-hc8v-wwc9-vgxm](https://github.com/advisories/GHSA-hc8v-wwc9-vgxm), [GHSA-qgq7-7hm3-q39j](https://github.com/advisories/GHSA-qgq7-7hm3-q39j))**
- github.com/klauspost/compress `v1.19.0` → `v1.19.1`
- github.com/magiconair/properties `v1.8.10` → `v1.18.11`
- github.com/santhosh-tekuri/jsonschema/v6 `v6.0.2` → `v6.0.3`
- github.com/ulikunitz/xz `v0.5.15` → `v0.5.16`
- go.yaml.in/yaml/v3 `v3.0.4` → `v3.0.5`
- modernc.org/sqlite `v1.54.0` → `v1.55.0`

</details>

**[(Full Changelog)](https://github.com/anchore/grype/compare/v0.116.1...v0.117.0)**

### [`v0.116.1`](https://github.com/anchore/grype/releases/tag/v0.116.1)

##### Bug Fixes

- Ensure channel parsing is consistent \[PR [#&#8203;3603](https://github.com/anchore/grype/pull/3603) [@&#8203;wagoodman](https://github.com/wagoodman)]
- Scope Go GHSA twins by shared CVE \[PR [#&#8203;3592](https://github.com/anchore/grype/pull/3592) [@&#8203;wagoodman](https://github.com/wagoodman)]
- do not cache a comparator that failed to build \[PR [#&#8203;3567](https://github.com/anchore/grype/pull/3567) [@&#8203;arpitjain099](https://github.com/arpitjain099)]
- Add fix date to rhel minor records created from rhsa \[PR [#&#8203;3585](https://github.com/anchore/grype/pull/3585) [@&#8203;wagoodman](https://github.com/wagoodman)]
- grype reporting CVE-64091 as critical - redhat says it is not affected \[Issue [#&#8203;3591](https://github.com/anchore/grype/issues/3591)]
- panic: index out of range in distro.parseVersion for VERSION\_ID=v \[Issue [#&#8203;3588](https://github.com/anchore/grype/issues/3588)] \[PR [#&#8203;3589](https://github.com/anchore/grype/pull/3589) [@&#8203;matiasinsaurralde](https://github.com/matiasinsaurralde)]
- False Positive: GO-2026-5932 \[Issue [#&#8203;3573](https://github.com/anchore/grype/issues/3573)]

##### Dependencies

30 dependency changes (30 updated). 1 vulnerability remediated.

**🟢 Remediated (1)**

- [GHSA-hrxh-6v49-42gf](https://github.com/advisories/GHSA-hrxh-6v49-42gf) (High) — google.golang.org/grpc

<details>
<summary>Updated (30 packages)</summary>

- github.com/GoogleCloudPlatform/opentelemetry-operations-go/detectors/gcp `v1.31.0` → `v1.32.0`
- github.com/anchore/stereoscope `v0.2.2` → `v0.3.0`
- github.com/anchore/syft `v1.48.0` → `v1.50.0`
- github.com/cncf/xds/go `v0.0.0-ee656c7` → `v0.0.0-dba9d58`
- github.com/containerd/containerd/v2 `v2.3.2` → `v2.3.3`
- github.com/docker/cli `v29.5.3+incompatible` → `v29.6.1+incompatible`
- github.com/envoyproxy/go-control-plane/envoy `v1.36.0` → `v1.37.0`
- github.com/envoyproxy/protoc-gen-validate `v1.3.0` → `v1.3.3`
- github.com/gkampitakis/go-snaps `v0.5.22` → `v0.5.23`
- github.com/gpustack/gguf-parser-go `v0.24.1` → `v0.25.0`
- github.com/moby/moby/api `v1.54.2` → `v1.55.0`
- github.com/moby/moby/client `v0.4.1` → `v0.5.0`
- github.com/pelletier/go-toml/v2 `v2.3.1` → `v2.4.3`
- go.opentelemetry.io/contrib/detectors/gcp `v1.39.0` → `v1.43.0`
- golang.org/x/crypto `v0.53.0` → `v0.54.0`
- golang.org/x/mod `v0.37.0` → `v0.38.0`
- golang.org/x/net `v0.56.0` → `v0.57.0`
- golang.org/x/sync `v0.21.0` → `v0.22.0`
- golang.org/x/sys `v0.46.0` → `v0.47.0`
- golang.org/x/term `v0.44.0` → `v0.45.0`
- golang.org/x/text `v0.39.0` → `v0.40.0`
- golang.org/x/tools `v0.47.0` → `v0.48.0`
- google.golang.org/genproto/googleapis/api `v0.0.0-9d38bb4` → `v0.0.0-afd174a`
- google.golang.org/genproto/googleapis/rpc `v0.0.0-6f92a3b` → `v0.0.0-afd174a`
- google.golang.org/grpc `v1.80.0` → `v1.82.1` **(🟢 remediated [GHSA-hrxh-6v49-42gf](https://github.com/advisories/GHSA-hrxh-6v49-42gf))**
- modernc.org/cc/v4 `v4.28.4` → `v4.29.0`
- modernc.org/ccgo/v4 `v4.34.4` → `v4.34.6`
- modernc.org/gc/v3 `v3.1.3` → `v3.1.4`
- modernc.org/libc `v1.73.4` → `v1.74.1`
- modernc.org/sqlite `v1.53.0` → `v1.54.0`

</details>

**[(Full Changelog)](https://github.com/anchore/grype/compare/v0.116.0...v0.116.1)**

### [`v0.115.0`](https://github.com/anchore/grype/releases/tag/v0.115.0)

##### Added Features

- emit golang.org/x/net vulns from govlundb \[PR [#&#8203;3534](https://github.com/anchore/grype/pull/3534) [@&#8203;willmurphyscode](https://github.com/willmurphyscode)]
- Merge Go vuln matches with GHSA matches \[Issue [#&#8203;3515](https://github.com/anchore/grype/issues/3515)]

##### Bug Fixes

- only emit records for stdlib \[PR [#&#8203;3527](https://github.com/anchore/grype/pull/3527) [@&#8203;willmurphyscode](https://github.com/willmurphyscode)]
- mark hummingbird distro as rolling \[PR [#&#8203;3521](https://github.com/anchore/grype/pull/3521) [@&#8203;willmurphyscode](https://github.com/willmurphyscode)]
- disable go stdlib CPE matching by default \[PR [#&#8203;3517](https://github.com/anchore/grype/pull/3517) [@&#8203;willmurphyscode](https://github.com/willmurphyscode)]
- merge in custom ranges when applicable \[PR [#&#8203;3514](https://github.com/anchore/grype/pull/3514) [@&#8203;willmurphyscode](https://github.com/willmurphyscode)]
- exclude linux-kbuild deb indirect matches by default \[PR [#&#8203;3506](https://github.com/anchore/grype/pull/3506) [@&#8203;westonsteimel](https://github.com/westonsteimel)]
- avoid panic on invalid RHEL version IDs \[PR [#&#8203;3490](https://github.com/anchore/grype/pull/3490) [@&#8203;jspilman](https://github.com/jspilman)]
- Support reading CycloneDX 1.7 SBOMs \[Issue [#&#8203;3373](https://github.com/anchore/grype/issues/3373)]
- Grype cannot read mariadb version correctly \[Issue [#&#8203;3452](https://github.com/anchore/grype/issues/3452)]
- grype hangs when downloading certain images using registry client \[Issue [#&#8203;3492](https://github.com/anchore/grype/issues/3492)]
- Can we get a fix for these Critical findings reported for grype \[Issue [#&#8203;3484](https://github.com/anchore/grype/issues/3484)]

##### Additional Changes

- Security: bump golang.org/x/crypto to v0.52.0 to resolve multiple CVEs \[Issue [#&#8203;3493](https://github.com/anchore/grype/issues/3493)]
- Security: bump golang.org/x/net to v0.55.0 to resolve CVEs \[Issue [#&#8203;3494](https://github.com/anchore/grype/issues/3494)]

##### Dependencies

35 dependency changes (31 updated, 3 added, 1 removed). 5 vulnerabilities remediated.

**🟢 Remediated (5)**

- [GHSA-33vj-92qq-66hc](https://github.com/advisories/GHSA-33vj-92qq-66hc) (High) — github.com/containerd/containerd/v2
- [GHSA-cvxm-645q-p574](https://github.com/advisories/GHSA-cvxm-645q-p574) (Medium) — github.com/containerd/containerd/v2
- [GHSA-jpcc-p29g-p8mq](https://github.com/advisories/GHSA-jpcc-p29g-p8mq) (Medium) — github.com/containerd/containerd/v2
- [GHSA-rgh6-rfwx-v388](https://github.com/advisories/GHSA-rgh6-rfwx-v388) (High) — github.com/containerd/containerd/v2
- [GHSA-xhf5-7wjv-pqxp](https://github.com/advisories/GHSA-xhf5-7wjv-pqxp) (High) — github.com/containerd/containerd/v2

<details>
<summary>Updated (31 packages)</summary>

- github.com/ProtonMail/go-crypto `v1.4.0` → `v1.4.1`
- github.com/anchore/bubbly `v0.2.0` → `v0.2.1`
- github.com/anchore/clio `v0.1.0` → `v0.1.1`
- github.com/anchore/fangs `v0.1.0` → `v0.1.1`
- github.com/anchore/go-collections `v0.1.0` → `v0.1.1`
- github.com/anchore/go-homedir `v0.1.0` → `v0.1.1`
- github.com/anchore/go-logger `v0.1.0` → `v0.1.1`
- github.com/anchore/go-lzo `v0.1.0` → `v0.1.1`
- github.com/anchore/go-macholibre `v0.1.0` → `v0.1.1`
- github.com/anchore/go-make `v0.5.0` → `v0.8.0`
- github.com/anchore/go-struct-converter `v0.1.0` → `v0.2.0-rc2`
- github.com/anchore/go-sync `v0.1.0` → `v0.1.1`
- github.com/anchore/stereoscope `v0.2.1` → `v0.2.2`
- github.com/anchore/syft `v1.45.1` → `v1.46.0`
- github.com/charmbracelet/colorprofile `v0.4.1` → `v0.4.3`
- github.com/clipperhouse/displaywidth `v0.10.0` → `v0.11.0`
- github.com/clipperhouse/uax29/v2 `v2.6.0` → `v2.7.0`
- github.com/containerd/containerd/v2 `v2.3.1` → `v2.3.2` **(🟢 remediated [GHSA-33vj-92qq-66hc](https://github.com/advisories/GHSA-33vj-92qq-66hc), [GHSA-cvxm-645q-p574](https://github.com/advisories/GHSA-cvxm-645q-p574), [GHSA-jpcc-p29g-p8mq](https://github.com/advisories/GHSA-jpcc-p29g-p8mq), [GHSA-rgh6-rfwx-v388](https://github.com/advisories/GHSA-rgh6-rfwx-v388), [GHSA-xhf5-7wjv-pqxp](https://github.com/advisories/GHSA-xhf5-7wjv-pqxp))**
- github.com/docker/cli `v29.4.3+incompatible` → `v29.5.3+incompatible`
- github.com/google/go-containerregistry `v0.21.6` → `v0.21.7`
- github.com/mattn/go-runewidth `v0.0.19` → `v0.0.21`
- github.com/spdx/tools-golang `v0.5.7` → `v0.6.0-rc4`
- github.com/sylabs/sif/v2 `v2.24.0` → `v2.24.1`
- golang.org/x/crypto `v0.52.0` → `v0.53.0`
- golang.org/x/mod `v0.36.0` → `v0.37.0`
- golang.org/x/net `v0.55.0` → `v0.56.0`
- golang.org/x/sync `v0.20.0` → `v0.21.0`
- golang.org/x/sys `v0.45.0` → `v0.46.0`
- golang.org/x/term `v0.43.0` → `v0.44.0`
- golang.org/x/text `v0.37.0` → `v0.38.0`
- golang.org/x/tools `v0.45.0` → `v0.46.0`

</details>

<details>
<summary>Added (3 packages)</summary>

- github.com/piprate/json-gold `v0.7.0`
- github.com/pquerna/cachecontrol `v0.0.0-1555304`
- github.com/tailscale/hujson `v0.0.0-ecc657c`

</details>

<details>
<summary>Removed (1 package)</summary>

- github.com/google/osv-scanner `v1.9.2`

</details>

**[(Full Changelog)](https://github.com/anchore/grype/compare/v0.114.0...v0.115.0)**

### [`v0.114.0`](https://github.com/anchore/grype/releases/tag/v0.114.0)

##### Added Features

- Add ability to scan zarf packages \[[#&#8203;3329](https://github.com/anchore/grype/issues/3329) [#&#8203;3366](https://github.com/anchore/grype/pull/3366) [@&#8203;brandtkeller](https://github.com/brandtkeller)]

##### Additional Changes

- respect withdrawn status of Go Vuln DB OSV records \[[#&#8203;3495](https://github.com/anchore/grype/pull/3495) [@&#8203;willmurphyscode](https://github.com/willmurphyscode)]
- Govulndb OSV transformer \[[#&#8203;3485](https://github.com/anchore/grype/pull/3485) [@&#8203;willmurphyscode](https://github.com/willmurphyscode)]

**[(Full Changelog)](https://github.com/anchore/grype/compare/v0.113.0...v0.114.0)**

### [`v0.113.0`](https://github.com/anchore/grype/releases/tag/v0.113.0)

##### Added Features

- Include Ubuntu 26.04 "resolute" in distro codenames \[[#&#8203;3397](https://github.com/anchore/grype/pull/3397) [@&#8203;anchore-oss-update-bot](https://github.com/anchore-oss-update-bot)]
- source RPM filtering on Hummingbird \[[#&#8203;3410](https://github.com/anchore/grype/pull/3410) [@&#8203;willmurphyscode](https://github.com/willmurphyscode)]

##### Bug Fixes

- use relatedVulnerabilities description as fallback in SARIF output \[[#&#8203;3271](https://github.com/anchore/grype/pull/3271) [@&#8203;axidex](https://github.com/axidex)]
- improve platform CPE determination logic \[[#&#8203;3470](https://github.com/anchore/grype/pull/3470) [@&#8203;westonsteimel](https://github.com/westonsteimel)]
- normalize uppercase V in semantic version comparison \[[#&#8203;3461](https://github.com/anchore/grype/pull/3461) [@&#8203;immanuwell](https://github.com/immanuwell)]
- purl handling in cgr maven libs \[[#&#8203;3420](https://github.com/anchore/grype/pull/3420) [@&#8203;willmurphyscode](https://github.com/willmurphyscode)]
- Treat uppercase V prefixes the same as lowercase v prefixes in fuzzy version comparison \[[#&#8203;3037](https://github.com/anchore/grype/issues/3037) [#&#8203;3089](https://github.com/anchore/grype/pull/3089) [@&#8203;wasup-yash](https://github.com/wasup-yash)]
- Add Runtime Warnings When TLS Verification Is Disabled or HTTP Is Enabled \[[#&#8203;3101](https://github.com/anchore/grype/issues/3101) [#&#8203;3396](https://github.com/anchore/grype/pull/3396) [@&#8203;Dashtid](https://github.com/Dashtid)]
- Add support for the aarch64 architecture when parsing the version of Ruby gems in lockfiles \[[#&#8203;3442](https://github.com/anchore/grype/issues/3442) [#&#8203;3475](https://github.com/anchore/grype/pull/3475) [@&#8203;msnandhis](https://github.com/msnandhis)]
- zsh completion fails \[[#&#8203;2933](https://github.com/anchore/grype/issues/2933) [#&#8203;3433](https://github.com/anchore/grype/pull/3433) [@&#8203;brandtkeller](https://github.com/brandtkeller)]

**[(Full Changelog)](https://github.com/anchore/grype/compare/v0.112.0...v0.113.0)**

### [`v0.112.0`](https://github.com/anchore/grype/releases/tag/v0.112.0)

##### Added Features

- Expand ignore rules to owned sub packages of distro packages \[[#&#8203;3368](https://github.com/anchore/grype/issues/3368) [#&#8203;3326](https://github.com/anchore/grype/pull/3326) [@&#8203;kzantow](https://github.com/kzantow)]

##### Additional Changes

- update anchore dependencies \[[#&#8203;3391](https://github.com/anchore/grype/pull/3391) [@&#8203;anchore-oss-update-bot](https://github.com/anchore-oss-update-bot)]

**[(Full Changelog)](https://github.com/anchore/grype/compare/v0.111.1...v0.112.0)**

### [`v0.111.1`](https://github.com/anchore/grype/releases/tag/v0.111.1)

##### Bug Fixes

- apply overlap by ownership removal to dynamically created relationships \[[#&#8203;3363](https://github.com/anchore/grype/pull/3363) [@&#8203;kzantow](https://github.com/kzantow)]
- compare mismatched package / db versions \[[#&#8203;3372](https://github.com/anchore/grype/pull/3372) [@&#8203;kzantow](https://github.com/kzantow)]
- Grype doesn't recognize debian component when `"group" : "debian"` is specified \[[#&#8203;2967](https://github.com/anchore/grype/issues/2967)]
- HelpURI missing information in SARIF output \[[#&#8203;2874](https://github.com/anchore/grype/issues/2874) [#&#8203;3351](https://github.com/anchore/grype/pull/3351) [@&#8203;will-bates11](https://github.com/will-bates11)]

**[(Full Changelog)](https://github.com/anchore/grype/compare/v0.111.0...v0.111.1)**

### [`v0.108.0`](https://github.com/anchore/grype/releases/tag/v0.108.0)

##### Added Features

- enable disabling EOL warnings \[[#&#8203;3204](https://github.com/anchore/grype/pull/3204) [@&#8203;willmurphyscode](https://github.com/willmurphyscode)]

##### Bug Fixes

- fix fallback on major only distro \[[#&#8203;3213](https://github.com/anchore/grype/pull/3213) [@&#8203;willmurphyscode](https://github.com/willmurphyscode)]
- VEX Documents still not working with syft sbom \[[#&#8203;3167](https://github.com/anchore/grype/issues/3167)]
- VEX: minimal OpenVEX Example not working \[[#&#8203;3212](https://github.com/anchore/grype/issues/3212)]

##### Additional Changes

- support more accurate scanning for postmarketos \[[#&#8203;3182](https://github.com/anchore/grype/pull/3182) [@&#8203;westonsteimel](https://github.com/westonsteimel)]
- charmbracelet/bubbletea erases grype ui status line \[[#&#8203;3214](https://github.com/anchore/grype/pull/3214) [@&#8203;spiffcs](https://github.com/spiffcs)]
- bump labels and add several test images \[[#&#8203;3215](https://github.com/anchore/grype/pull/3215) [@&#8203;westonsteimel](https://github.com/westonsteimel)]
- improve VEX product and subcomponent matching \[[#&#8203;3168](https://github.com/anchore/grype/pull/3168) [@&#8203;dariozachow](https://github.com/dariozachow)]

**[(Full Changelog)](https://github.com/anchore/grype/compare/v0.107.1...v0.108.0)**

### [`v0.105.0`](https://github.com/anchore/grype/releases/tag/v0.105.0)

##### Added Features

- Add archlinux matcher to grype \[[#&#8203;3154](https://github.com/anchore/grype/pull/3154) [@&#8203;willmurphyscode](https://github.com/willmurphyscode)]

**[(Full Changelog)](https://github.com/anchore/grype/compare/v0.104.4...v0.105.0)**

### [`v0.104.4`](https://github.com/anchore/grype/releases/tag/v0.104.4)

##### Bug Fixes

- preserve local version segment in constraints for PEP 440 comparison \[[#&#8203;3146](https://github.com/anchore/grype/pull/3146) [@&#8203;willmurphyscode](https://github.com/willmurphyscode)]

##### Additional Changes

- correct help text for return code for fail-on severity option \[[#&#8203;3138](https://github.com/anchore/grype/pull/3138) [@&#8203;u-ways](https://github.com/u-ways)]

**[(Full Changelog)](https://github.com/anchore/grype/compare/v0.104.3...v0.104.4)**

### [`v0.104.3`](https://github.com/anchore/grype/releases/tag/v0.104.3)

##### Bug Fixes

- Use specifier matching rules when comparing python versions \[[#&#8203;3121](https://github.com/anchore/grype/pull/3121) [@&#8203;wagoodman](https://github.com/wagoodman)]

**[(Full Changelog)](https://github.com/anchore/grype/compare/v0.104.2...v0.104.3)**

### [`v0.104.2`](https://github.com/anchore/grype/releases/tag/v0.104.2)

##### Bug Fixes

- Since version 0.104.0 shaded jars are not reported \[[#&#8203;3098](https://github.com/anchore/grype/issues/3098)]
- db search fails with misleading message (out of memory) when no db is present \[[#&#8203;3049](https://github.com/anchore/grype/issues/3049) [#&#8203;3077](https://github.com/anchore/grype/pull/3077) [@&#8203;JvD-Ericsson](https://github.com/JvD-Ericsson)]

##### Additional Changes

- replace os.Chdir with t.Chdir in test code \[[#&#8203;3067](https://github.com/anchore/grype/pull/3067) [@&#8203;joonas](https://github.com/joonas)]

**[(Full Changelog)](https://github.com/anchore/grype/compare/v0.104.1...v0.104.2)**

### [`v0.104.1`](https://github.com/anchore/grype/releases/tag/v0.104.1)

##### Bug Fixes

- Redact during file output \[[#&#8203;3068](https://github.com/anchore/grype/pull/3068) [@&#8203;kzantow](https://github.com/kzantow)]
- Unaffected match table does not filter results if CPE matching is enabled \[[#&#8203;3056](https://github.com/anchore/grype/issues/3056) [#&#8203;3066](https://github.com/anchore/grype/pull/3066) [@&#8203;kzantow](https://github.com/kzantow)]

##### Additional Changes

- Migrate grype to use `mholt/archives` instead of anchore fork \[[#&#8203;3036](https://github.com/anchore/grype/pull/3036) [@&#8203;joonas](https://github.com/joonas)]

**[(Full Changelog)](https://github.com/anchore/grype/compare/v0.104.0...v0.104.1)**

### [`v0.104.0`](https://github.com/anchore/grype/releases/tag/v0.104.0)

##### Added Features

- Add `--from` flag \[[#&#8203;3035](https://github.com/anchore/grype/pull/3035) [@&#8203;wagoodman](https://github.com/wagoodman)]
- Let a suppression expire to prevent that one will forget to resolve a vulnerability \[[#&#8203;3031](https://github.com/anchore/grype/issues/3031)]

##### Bug Fixes

- Unnormalized fix version triggers false-positive in mssql-jdbc \[[#&#8203;3042](https://github.com/anchore/grype/issues/3042) [#&#8203;3034](https://github.com/anchore/grype/pull/3034) [@&#8203;jamestexas](https://github.com/jamestexas)]

##### Additional Changes

- junit template use CDATA block to prevent XML parse errors \[[#&#8203;3019](https://github.com/anchore/grype/pull/3019) [@&#8203;nvtkaszpir](https://github.com/nvtkaszpir)]
- Keep nested loggers labeled \[[#&#8203;3040](https://github.com/anchore/grype/pull/3040) [@&#8203;wagoodman](https://github.com/wagoodman)]

**[(Full Changelog)](https://github.com/anchore/grype/compare/v0.103.0...v0.104.0)**

### [`v0.103.0`](https://github.com/anchore/grype/releases/tag/v0.103.0)

##### Added Features

- Allow hyphen in version string \[[#&#8203;3021](https://github.com/anchore/grype/pull/3021) [@&#8203;willmurphyscode](https://github.com/willmurphyscode)]
- Respect rpmmod PURL qualifier \[[#&#8203;3020](https://github.com/anchore/grype/pull/3020) [@&#8203;willmurphyscode](https://github.com/willmurphyscode)]

**[(Full Changelog)](https://github.com/anchore/grype/compare/v0.102.0...v0.103.0)**

### [`v0.102.0`](https://github.com/anchore/grype/releases/tag/v0.102.0)

##### Added Features

- Use Alma Linux specific advisories for Alma Linux scans \[[#&#8203;2745](https://github.com/anchore/grype/issues/2745) [#&#8203;2939](https://github.com/anchore/grype/pull/2939) [@&#8203;willmurphyscode](https://github.com/willmurphyscode)]

##### Bug Fixes

- Bitnami packages with CPEs are not matched against CPE-based vulnerabilities \[[#&#8203;2997](https://github.com/anchore/grype/issues/2997)]

##### Additional Changes

- add markdown template \[[#&#8203;2987](https://github.com/anchore/grype/pull/2987) [@&#8203;sebdanielsson](https://github.com/sebdanielsson)]

**[(Full Changelog)](https://github.com/anchore/grype/compare/v0.101.1...v0.102.0)**

### [`v0.101.1`](https://github.com/anchore/grype/releases/tag/v0.101.1)

##### Bug Fixes

- Panic error scanning images with v0.101.0 on some java dependencies \[[#&#8203;3002](https://github.com/anchore/grype/issues/3002)]

**[(Full Changelog)](https://github.com/anchore/grype/compare/v0.101.0...v0.101.1)**

### [`v0.101.0`](https://github.com/anchore/grype/releases/tag/v0.101.0)

##### Added Features

- Add cyclonedx to RpmMetadata \[[#&#8203;2935](https://github.com/anchore/grype/pull/2935) [@&#8203;sfc-gh-rmaj](https://github.com/sfc-gh-rmaj)]
- `grype db search` can filter by fixed state \[[#&#8203;2968](https://github.com/anchore/grype/pull/2968) [@&#8203;willmurphyscode](https://github.com/willmurphyscode)]
- Support using VEX documents with directory scans and SBOMs \[[#&#8203;2471](https://github.com/anchore/grype/issues/2471) [#&#8203;2811](https://github.com/anchore/grype/pull/2811) [@&#8203;alegrey91](https://github.com/alegrey91)]

##### Bug Fixes

- Issue installing Grype using documented curl command \[[#&#8203;2985](https://github.com/anchore/grype/issues/2985)]
- Advisory ID blank in JSON output \[[#&#8203;2965](https://github.com/anchore/grype/issues/2965)]

##### Additional Changes

- update flags with v3 to not use default config \[[#&#8203;3000](https://github.com/anchore/grype/pull/3000) [@&#8203;spiffcs](https://github.com/spiffcs)]
- fix Cosign documentation URL in installer \[[#&#8203;2995](https://github.com/anchore/grype/pull/2995) [@&#8203;lime](https://github.com/lime)]
- set advisory id again \[[#&#8203;2979](https://github.com/anchore/grype/pull/2979) [@&#8203;willmurphyscode](https://github.com/willmurphyscode)]
- add db schema validation \[[#&#8203;2962](https://github.com/anchore/grype/pull/2962) [@&#8203;willmurphyscode](https://github.com/willmurphyscode)]

**[(Full Changelog)](https://github.com/anchore/grype/compare/v0.100.0...v0.101.0)**

### [`v0.100.0`](https://github.com/anchore/grype/releases/tag/v0.100.0)

##### Added Features

- Add unaffected package and CPE stores \[[#&#8203;2888](https://github.com/anchore/grype/pull/2888) [@&#8203;wagoodman](https://github.com/wagoodman)]
- use unaffected match table to remove appropriate vulns \[[#&#8203;2886](https://github.com/anchore/grype/pull/2886) [@&#8203;CrosleyZack](https://github.com/CrosleyZack)]

**[(Full Changelog)](https://github.com/anchore/grype/compare/v0.99.1...v0.100.0)**

</details>

---

### Configuration

📅 **Schedule**: (in timezone Europe/Oslo)

- Branch creation
  - At any time (no schedule defined)
- Automerge
  - At any time (no schedule defined)

🚦 **Automerge**: Disabled by config. Please merge this manually once you are satisfied.

♻ **Rebasing**: Whenever PR becomes conflicted, or you tick the rebase/retry checkbox.

🔕 **Ignore**: Close this PR and you won't be reminded about this update again.

---

 - [ ] <!-- rebase-check -->If you want to rebase/retry this PR, check this box

---

This PR has been generated by [Mend Renovate CLI](https://github.com/renovatebot/renovate).
<!--renovate-debug:eyJjcmVhdGVkSW5WZXIiOiI0NC4xMTIuMyIsInVwZGF0ZWRJblZlciI6IjQ0LjExMi4zIiwidGFyZ2V0QnJhbmNoIjoibWFpbiIsImxhYmVscyI6WyJyZW5vdmF0ZSJdfQ==-->

---------

Co-authored-by: Danijel Simeunovic <danijel.simeunovic@fortedigital.com>
Co-authored-by: Renovate Bot <renovate@forteapps.net>
Reviewed-on: https://git.forteapps.net/Forte/launchpad/pulls/34
Reviewed-by: Danijel Simeunovic <danijel.simeunovic@fortedigital.com>
Co-authored-by: gitea_admin <admin@forteapps.net>
Co-committed-by: gitea_admin <admin@forteapps.net>
2026-09-27 22:15:50 +00:00
365661853a chore(deps): update dependency k9s to v0.51.0 (#35)
/ test (push) Failing after 10m18s
This PR contains the following updates:

| Package | Update | Change |
|---|---|---|
| [k9s](https://github.com/derailed/k9s) | minor | `0.50.7` → `0.51.0` |

---

### Release Notes

<details>
<summary>derailed/k9s (k9s)</summary>

### [`v0.51.0`](https://github.com/derailed/k9s/releases/tag/v0.51.0)

<img src="https://raw.githubusercontent.com/derailed/k9s/master/assets/k9s.png" align="center" width="800" height="auto"/>

### Release v0.51.0
#### Notes

Thank you to all that contributed with flushing out issues and enhancements for K9s!
I'll try to mark some of these issues as fixed. But if you don't mind grab the latest rev
and see if we're happier with some of the fixes!
If you've filed an issue please help me verify and close.

Your support, kindness and awesome suggestions to make K9s better are, as ever, very much noted and appreciated!
Also big thanks to all that have allocated their own time to help others on both slack and on this repo!!

As you may know, K9s is not pimped out by big corporations with deep pockets, thus if you feel K9s is helping in your Kubernetes journey, please consider joining our [sponsorship program](https://github.com/sponsors/derailed) and/or make some noise on social! [@&#8203;kitesurfer](https://twitter.com/kitesurfer)

On Slack? Please join us [K9slackers](https://join.slack.com/t/k9sers/shared_invite/zt-3360a389v-ElLHrb0Dp1kAXqYUItSAFA)

***

#### ♫ Sounds Behind The Release ♭

- [Aprieta - Vincen Garcia](https://www.youtube.com/watch?v=ldQ6hpg9BD0\&list=RDldQ6hpg9BD0\&start_radio=1)
- [Graham Chapman - John Cleese](https://www.youtube.com/watch?v=Bm2XPkqENaw)
- [Kill the pain - SYZGYX](https://www.youtube.com/watch?v=5XuvMhHZorw\&list=RD5XuvMhHZorw\&start_radio=1)

***

#### Maintenance Release!

Please help me welcome [Ümüt Özalp](https://github.com/uozalp) as a core contributor to K9s!
Ümüt has been instrumental in helping this project grow.
I trust you will help Ümüt triage issues and prs reviews and show him
the kindness and patience all k9sers are famous for!

Sponsorships are dropping at an alarming rate which puts this project in the red.
This is becoming a concern and sad not to mention unsustainable ;(
If you dig `k9s` and want to help the project, please consider `paying it forward!` and
don't become just another `satisfied, non paying customer!`.
K9s does take a lot of my `free` time to maintain, enhance and keep the light on.
Many cool ideas are making it straight to the `freezer` as I just can't budget them in.
I know many of you work for big corporations, so please put in the word/work and have
them help us out via sponsorships or other means.

Thank you!

***

#### Contributed PRs

Please be sure to give `Big Thanks!` and `ATTA Girls/Boys!` to all the fine contributors for making K9s better for all of us!!

- [#&#8203;4026](https://github.com/derailed/k9s/pull/4026) fix(xray): disable edit/delete actions in XRay view when readonly mode is enabled
- [#&#8203;4024](https://github.com/derailed/k9s/pull/4024) Fix 'J'umping to owner of cluster scoped resources
- [#&#8203;4005](https://github.com/derailed/k9s/pull/4005) Fix pod status for sidecar init containers
- [#&#8203;4001](https://github.com/derailed/k9s/pull/4001) Adjust namespace handling for RBAC checks in CanForResource and CanForInstance
- [#&#8203;3997](https://github.com/derailed/k9s/pull/3997) chore: fix wrong function name in comment
- [#&#8203;3993](https://github.com/derailed/k9s/pull/3993) fix(browser): show syncing status instead of spurious no-resources warning
- [#&#8203;3989](https://github.com/derailed/k9s/pull/3989) perf: skip reconcile cycle when informer data is unchanged
- [#&#8203;3988](https://github.com/derailed/k9s/pull/3988) perf: raise default client QPS from 5 to 50
- [#&#8203;3987](https://github.com/derailed/k9s/pull/3987) fix: paginate metrics API calls to prevent timeout on large clusters
- [#&#8203;3986](https://github.com/derailed/k9s/pull/3986) perf: batch Hydrate workers to eliminate per-item goroutine overhead
- [#&#8203;3917](https://github.com/derailed/k9s/pull/3917) Respect wide columns in default view
- [#&#8203;3911](https://github.com/derailed/k9s/pull/3911) fix: reset styles before loading skin on context switch
- [#&#8203;3908](https://github.com/derailed/k9s/pull/3908) fix: populate pod count in Node.Get() for single-node view
- [#&#8203;3902](https://github.com/derailed/k9s/pull/3902) Add OSC52 clipboard backend with native fallback
- [#&#8203;3888](https://github.com/derailed/k9s/pull/3888) feat: add One Light skin
- [#&#8203;3879](https://github.com/derailed/k9s/pull/3879) feat: allow users to cycle pulse grid selection forwards and backwards
- [#&#8203;3873](https://github.com/derailed/k9s/pull/3873) feat: enhance pvc-shell configuration with dynamic inputs and RWO support
- [#&#8203;3872](https://github.com/derailed/k9s/pull/3872) Add default confirm:true for plugins with inputs
- [#&#8203;3871](https://github.com/derailed/k9s/pull/3871) internal/render: prevent index out of range panic in initContainerStats
- [#&#8203;3865](https://github.com/derailed/k9s/pull/3865) Handle blank PVC capacities for the purpose of sorting
- [#&#8203;3854](https://github.com/derailed/k9s/pull/3854) feat: enhance debug container configuration with input fields
- [#&#8203;3851](https://github.com/derailed/k9s/pull/3851) Use \*grey instead of grey in black-and-wtf.yaml
- [#&#8203;3839](https://github.com/derailed/k9s/pull/3839) fix: optimize context switching to reduce redundant API calls
- [#&#8203;3823](https://github.com/derailed/k9s/pull/3823) feat: add resize PVC plugin for dynamic storage resizing
- [#&#8203;3821](https://github.com/derailed/k9s/pull/3821) feat: add support for plugin input fields
- [#&#8203;3817](https://github.com/derailed/k9s/pull/3817) Fix Readme: Ubuntu installation command not working
- [#&#8203;3798](https://github.com/derailed/k9s/pull/3798) Fix boom on Jumping Owner in rare cases
- [#&#8203;3797](https://github.com/derailed/k9s/pull/3797) feat: add extra hints for column navigation in table view
- [#&#8203;3792](https://github.com/derailed/k9s/pull/3792) fix: adjust resource access checks for namespace resources
- [#&#8203;3783](https://github.com/derailed/k9s/pull/3783) fix: avoid logging errors when no context is configured
- [#&#8203;3780](https://github.com/derailed/k9s/pull/3780) feat: add selected color to table header
- [#&#8203;3736](https://github.com/derailed/k9s/pull/3736) feat: add custom resource jump support
- [#&#8203;3634](https://github.com/derailed/k9s/pull/3634) Add shell detection for Windows NanoServer containers

***

<img src="https://raw.githubusercontent.com/derailed/k9s/master/assets/imhotep_logo.png" width="32" height="auto"/> © 2026 Imhotep Software LLC. All materials licensed under [Apache v2.0](http://www.apache.org/licenses/LICENSE-2.0)#

### [`v0.50.18`](https://github.com/derailed/k9s/releases/tag/v0.50.18)

<img src="https://raw.githubusercontent.com/derailed/k9s/master/assets/k9s.png" align="center" width="800" height="auto"/>

### Release v0.50.18
#### Notes

🥳🎉 Happy new year fellow k9ers!🎊🍾 Hoping 2026 will bring good health and great success to you and yours...

Thank you to all that contributed with flushing out issues and enhancements for K9s!
I'll try to mark some of these issues as fixed. But if you don't mind grab the latest rev
and see if we're happier with some of the fixes!
If you've filed an issue please help me verify and close.

Your support, kindness and awesome suggestions to make K9s better are, as ever, very much noted and appreciated!
Also big thanks to all that have allocated their own time to help others on both slack and on this repo!!

As you may know, K9s is not pimped out by big corporations with deep pockets, thus if you feel K9s is helping in your Kubernetes journey, please consider joining our [sponsorship program](https://github.com/sponsors/derailed) and/or make some noise on social! [@&#8203;kitesurfer](https://twitter.com/kitesurfer)

On Slack? Please join us [K9slackers](https://join.slack.com/t/k9sers/shared_invite/zt-3360a389v-ElLHrb0Dp1kAXqYUItSAFA)

***

#### ♫ Sounds Behind The Release ♭

- [A cool new way - Joe Satriani](https://www.youtube.com/watch?v=4apA948yOF0)
- [Song for you - Ray Charles](https://www.youtube.com/watch?v=CzAkTrDiXxg)
- [Kill the pain - SYZGYX](https://www.youtube.com/watch?v=5XuvMhHZorw\&list=RD5XuvMhHZorw\&start_radio=1)

***

#### Maintenance Release!

Oops! I've missed a PR in the v0.50.17 excitement ;( Dropping v0.50.18 with feelings...

Sponsorships are dropping at an alarming rate which puts this project in the red. This is becoming a concern and sad not to mention unsustainable ;( If you dig `k9s` and want to help the project, please consider `paying it forward!` and don't become just another `satisfied, non paying customer!`. K9s does take a lot of my `free` time to maintain, enhance and keep the light on. Many cool ideas are making it straight to the `freezer` as I just can't budget them in.
I know many of you work for big corporations, so please put in the word/work and have them help us out via sponsorships or other means.

Thank you!

***

#### A Word From Our Sponsors...

To all the good folks and orgs below that opted to `pay it forward` and join our sponsorship program, I salute you!!

- [Philomena Yeboah](https://github.com/PhilomenaYeboah1989)
- [Kilian](https://github.com/kaerbr)
- [TVRiddle](https://github.com/TVRiddle)
- [Tom Morelly](https://github.com/FalcoSuessgott)
- [Nikhil Narayen](https://github.com/nnarayen)
- [Andrew Aadland](https://github.com/DaemonDude23)
- [Radek](https://github.com/radvym)
- [Timothée Gerber](https://github.com/TimotheeGerber)
- [Matthias](https://github.com/maetthu)
- [DKB](https://github.com/dkb-bank) ❤️
- [Kraken Tech](https://github.com/kraken-tech)
- [Daniel](https://github.com/sherlock7402)
- [Fred Loucks](https://github.com/fullmetal-fred)
- [Patricia Mascaros](https://github.com/ccong2586)
- [Qube Research & Technologies](https://github.com/qube-rt)
- [Michel Jung](https://github.com/micheljung)
- [Ümüt Özalp](https://github.com/uozalp)
- [Nathan Papapietro](https://github.com/npapapietro)
- [Oleksandr Podze](https://github.com/dasdy)
- [Lee Jones](https://github.com/leejones)
- [tsahlif](https://github.com/tshalif)
- [Jean-Christophe Amiel](https://github.com/jcamiel)
- [Lightspark](https://github.com/lightsparkdev)
- [egs-hub](https://github.com/egs-hub) ❤️
- [Sergey](https://github.com/malsatin)
- [Wynter Inc](https://github.com/copytesting)
- [Jen Norris](https://github.com/tnorris)
- [Joakim-Byg](https://github.com/Joakim-Byg)
- [Oleksandr Podze](https://github.com/dasdy)
- [Lee Jones](https://github.com/leejones)

> Sponsorship cancellations since the last release: **17!** 🥹

#### Resolved Issues

- [#&#8203;3765](https://github.com/derailed/k9s/issues/3765) quay.io docker images not up to date but referenced in README.md
- [#&#8203;3762](https://github.com/derailed/k9s/issues/3762) Copy multiple selected items
- [#&#8203;3751](https://github.com/derailed/k9s/issues/3751) Improve visual distinction for cordoned nodes in Node view
- [#&#8203;3735](https://github.com/derailed/k9s/issues/3735) Cannot decode secret if there is no get permissions for all secrets
- [#&#8203;3708](https://github.com/derailed/k9s/issues/3708) Editing a single Namespace opens the editor with a list of all Namespaces
- [#&#8203;3731](https://github.com/derailed/k9s/issues/3731) feat: add neat plugin
- [#&#8203;3735](https://github.com/derailed/k9s/issues/3735) Cannot decode secret if there is no get permissions for all secrets
- [#&#8203;3708](https://github.com/derailed/k9s/issues/3708) Editing a single Namespace opens the editor with a list of all Namespaces
- [#&#8203;3649](https://github.com/derailed/k9s/issues/3649) Improved Column Sorting

***

#### Contributed PRs

Please be sure to give `Big Thanks!` and `ATTA Girls/Boys!` to all the fine contributors for making K9s better for all of us!!

- [#&#8203;3763](https://github.com/derailed/k9s/pull/3763) feat: enable copying multiple resource, namespace names to clipboard
- [#&#8203;3760](https://github.com/derailed/k9s/pull/3760) fix: Editing a single Namespace opens the editor with a list of all Namespaces
- [#&#8203;3756](https://github.com/derailed/k9s/pull/3756) feat: Add reconcile plugin for Flux instances
- [#&#8203;3755](https://github.com/derailed/k9s/pull/3755) fix: panic on 'jump to owner' of reflect.Value.Elem on zero Value
- [#&#8203;3753](https://github.com/derailed/k9s/pull/3553) feat: add plugins for argo workflows
- [#&#8203;3750](https://github.com/derailed/k9s/pull/3750) fix: Flux trace plugin shortcut conflict by changing to Shift-Q
- [#&#8203;3749](https://github.com/derailed/k9s/pull/3749) feat: add dark/light theme inversion using Oklch
- [#&#8203;3739](https://github.com/derailed/k9s/pull/3739) chore: refine LabelsSelector comment to match function behavior
- [#&#8203;3738](https://github.com/derailed/k9s/pull/3738) feat: add symlink handle for plugin directory
- [#&#8203;3720](https://github.com/derailed/k9s/pull/3720) fix(internal/render): ensure object is deep copied before realization in Render method
- [#&#8203;3704](https://github.com/derailed/k9s/pull/3704) Allow k9s to start without a valid Kubernetes context
- [#&#8203;3699](https://github.com/derailed/k9s/pull/3699) feat(pulse): map hjkl to navigate as help shows
- [#&#8203;3697](https://github.com/derailed/k9s/pull/3697) Issue 3667 Fix
- [#&#8203;3696](https://github.com/derailed/k9s/pull/3696) fix for scale option appearing on non-scalable resources
- [#&#8203;3690](https://github.com/derailed/k9s/pull/3690) feat: add support for scaling HPA targets
- [#&#8203;3671](https://github.com/derailed/k9s/pull/3671) fix fails to modify or delete namespaces using RBAC
- [#&#8203;3669](https://github.com/derailed/k9s/pull/3669) feat: logs column lock
- [#&#8203;3663](https://github.com/derailed/k9s/pull/3663) Map Q to "Back"
- [#&#8203;3661](https://github.com/derailed/k9s/pull/3661) refactor: remove unused sorting key bindings from various views
- [#&#8203;3859](https://github.com/derailed/k9s/pull/3859) fix: update busybox image version to 1.37.0 in configuration files
- [#&#8203;3650](https://github.com/derailed/k9s/pull/3650) Sort all columns
- [#&#8203;3458](https://github.com/derailed/k9s/pull/3458) Document how to install on Fedora

***

<img src="https://raw.githubusercontent.com/derailed/k9s/master/assets/imhotep_logo.png" width="32" height="auto"/> © 2026 Imhotep Software LLC. All materials licensed under [Apache v2.0](http://www.apache.org/licenses/LICENSE-2.0)#

### [`v0.50.16`](https://github.com/derailed/k9s/releases/tag/v0.50.16)

<img src="https://raw.githubusercontent.com/derailed/k9s/master/assets/k9s.png" align="center" width="800" height="auto"/>

### Release v0.50.16
#### Notes

Thank you to all that contributed with flushing out issues and enhancements for K9s!
I'll try to mark some of these issues as fixed. But if you don't mind grab the latest rev
and see if we're happier with some of the fixes!
If you've filed an issue please help me verify and close.

Your support, kindness and awesome suggestions to make K9s better are, as ever, very much noted and appreciated!
Also big thanks to all that have allocated their own time to help others on both slack and on this repo!!

As you may know, K9s is not pimped out by big corporations with deep pockets, thus if you feel K9s is helping in your Kubernetes journey, please consider joining our [sponsorship program](https://github.com/sponsors/derailed) and/or make some noise on social! [@&#8203;kitesurfer](https://twitter.com/kitesurfer)

On Slack? Please join us [K9slackers](https://join.slack.com/t/k9sers/shared_invite/zt-3360a389v-ElLHrb0Dp1kAXqYUItSAFA)

#### Maintenance Release!

Sponsorships are dropping at an alarming rate which puts this project in the red. This is becoming a concern and sad not to mention unsustainable ;( If you dig `k9s` and want to help the project, please consider `paying it forward!` and don't become just another `satisfied, non paying customer!`. K9s does take a lot of my `free` time to maintain, enhance and keep the light on. Many cool ideas are making it straight to the `freezer` as I just can't budget them in.
I know many of you work for big corporations, so please put in the word/work and have them help us out via sponsorships or other means.

Thank you!

##### Warp Speed Scotty!

As of this drop, we are introducing `namespace warp` via shortcut `w`.
This affords to view all resources of that type based on the currently selected resource namespace.
This command is only available on namespaced resources.
For example, if you are in pod view and select pod-xxx in namespace `bozo`, hitting `w` will `warp`
you to view all pods in namespace `bozo`.

#### Resolved Issues

- [#&#8203;3629](https://github.com/derailed/k9s/issues/3629) vulnerability in k9s project
- [#&#8203;3621](https://github.com/derailed/k9s/issues/3621) Switching to ":Deploy" sends you to deployments from namespace "deploy"
- [#&#8203;3620](https://github.com/derailed/k9s/issues/3620) Trying to show pod yaml using custom views.yaml crashes k9s
- [#&#8203;3608](https://github.com/derailed/k9s/issues/3608) k9s crashes when :namespaces used
- [#&#8203;3601](https://github.com/derailed/k9s/issues/3601) Can't delete namespace
- [#&#8203;3595](https://github.com/derailed/k9s/issues/3595) Toggle Namespace Filter in Pods View with 'n' Key
- [#&#8203;3576](https://github.com/derailed/k9s/issues/3576) Custom alias/view not working anymore since v0.50.10

***

#### Contributed PRs

Please be sure to give `Big Thanks!` and `ATTA Girls/Boys!` to all the fine contributors for making K9s better for all of us!!

- [#&#8203;3625](https://github.com/derailed/k9s/pull/3625) fix: debug-container plugin when KUBECONFIG has multiple files
- [#&#8203;3623](https://github.com/derailed/k9s/pull/3623) bugfix: fix panic in BenchmarkPodRender by using NewPod() constructor
- [#&#8203;3619](https://github.com/derailed/k9s/pull/3619) feat: plugin to list all resources by namespace
- [#&#8203;3605](https://github.com/derailed/k9s/pull/3605) browser: do not prevent redraw when connection unavailable
- [#&#8203;3600](https://github.com/derailed/k9s/pull/3600) fix(shell): set linux when OS detection fails
- [#&#8203;3588](https://github.com/derailed/k9s/pull/3588) fix: do not error out of shellIn if OS detection fails

***

<img src="https://raw.githubusercontent.com/derailed/k9s/master/assets/imhotep_logo.png" width="32" height="auto"/> © 2025 Imhotep Software LLC. All materials licensed under [Apache v2.0](http://www.apache.org/licenses/LICENSE-2.0)#

### [`v0.50.15`](https://github.com/derailed/k9s/releases/tag/v0.50.15)

<img src="https://raw.githubusercontent.com/derailed/k9s/master/assets/k9s.png" align="center" width="800" height="auto"/>

### Release v0.50.15
#### Notes

Thank you to all that contributed with flushing out issues and enhancements for K9s!
I'll try to mark some of these issues as fixed. But if you don't mind grab the latest rev
and see if we're happier with some of the fixes!
If you've filed an issue please help me verify and close.

Your support, kindness and awesome suggestions to make K9s better are, as ever, very much noted and appreciated!
Also big thanks to all that have allocated their own time to help others on both slack and on this repo!!

As you may know, K9s is not pimped out by big corporations with deep pockets, thus if you feel K9s is helping in your Kubernetes journey, please consider joining our [sponsorship program](https://github.com/sponsors/derailed) and/or make some noise on social! [@&#8203;kitesurfer](https://twitter.com/kitesurfer)

On Slack? Please join us [K9slackers](https://join.slack.com/t/k9sers/shared_invite/zt-3360a389v-ElLHrb0Dp1kAXqYUItSAFA)

#### Maintenance Release!

Sponsorships are dropping at an alarming rate which puts this project in the red. This is becoming a concern and sad not to mention unsustainable ;( If you dig `k9s` and want to help the project, please consider `paying it forward!` and don't become just another `satisfied, non paying customer!`. K9s does take a lot of my `free` time to maintain, enhance and keep the light on. Many cool ideas are making it straight to the `freezer` as I just can't budget them in.
I know many of you work for big corporations, so please put in the word/work and have them help us out via sponsorships or other means.

Thank you!

#### Resolved Issues

- [#&#8203;3591](https://github.com/derailed/k9s/issues/3591) REVERTED! Accept suggestion with enter (without having to "tab")

***

<img src="https://raw.githubusercontent.com/derailed/k9s/master/assets/imhotep_logo.png" width="32" height="auto"/> © 2025 Imhotep Software LLC. All materials licensed under [Apache v2.0](http://www.apache.org/licenses/LICENSE-2.0)#

### [`v0.50.13`](https://github.com/derailed/k9s/releases/tag/v0.50.13)

<img src="https://raw.githubusercontent.com/derailed/k9s/master/assets/k9s.png" align="center" width="800" height="auto"/>

### Release v0.50.13
#### Notes

Thank you to all that contributed with flushing out issues and enhancements for K9s!
I'll try to mark some of these issues as fixed. But if you don't mind grab the latest rev
and see if we're happier with some of the fixes!
If you've filed an issue please help me verify and close.

Your support, kindness and awesome suggestions to make K9s better are, as ever, very much noted and appreciated!
Also big thanks to all that have allocated their own time to help others on both slack and on this repo!!

As you may know, K9s is not pimped out by corps with deep pockets, thus if you feel K9s is helping your Kubernetes journey,
please consider joining our [sponsorship program](https://github.com/sponsors/derailed) and/or make some noise on social! [@&#8203;kitesurfer](https://twitter.com/kitesurfer)

On Slack? Please join us [K9slackers](https://join.slack.com/t/k9sers/shared_invite/zt-3360a389v-ElLHrb0Dp1kAXqYUItSAFA)

#### Maintenance Release!

#### Resolved Issues

- [#&#8203;3587](https://github.com/derailed/k9s/issues/3587) UI doesn't show any updates when restarting a Deployment
- [#&#8203;3585](https://github.com/derailed/k9s/issues/3585) abbreviation sec for secret not working
- [#&#8203;3584](https://github.com/derailed/k9s/issues/3584) Show managed fields doesn't show them
- [#&#8203;3583](https://github.com/derailed/k9s/issues/3583) Cannot open shell to pods without node read access as of 0.50.12
- [#&#8203;3577](https://github.com/derailed/k9s/issues/3577) Log view is broken as of v0.50.10
- [#&#8203;3574](https://github.com/derailed/k9s/issues/3574) Aliases for pods with label filters not working

***

<img src="https://raw.githubusercontent.com/derailed/k9s/master/assets/imhotep_logo.png" width="32" height="auto"/> © 2025 Imhotep Software LLC. All materials licensed under [Apache v2.0](http://www.apache.org/licenses/LICENSE-2.0)#

### [`v0.50.12`](https://github.com/derailed/k9s/releases/tag/v0.50.12)

<img src="https://raw.githubusercontent.com/derailed/k9s/master/assets/k9s.png" align="center" width="800" height="auto"/>

### Release v0.50.12
#### Notes

Thank you to all that contributed with flushing out issues and enhancements for K9s!
I'll try to mark some of these issues as fixed. But if you don't mind grab the latest rev
and see if we're happier with some of the fixes!
If you've filed an issue please help me verify and close.

Your support, kindness and awesome suggestions to make K9s better are, as ever, very much noted and appreciated!
Also big thanks to all that have allocated their own time to help others on both slack and on this repo!!

As you may know, K9s is not pimped out by corps with deep pockets, thus if you feel K9s is helping your Kubernetes journey,
please consider joining our [sponsorship program](https://github.com/sponsors/derailed) and/or make some noise on social! [@&#8203;kitesurfer](https://twitter.com/kitesurfer)

On Slack? Please join us [K9slackers](https://join.slack.com/t/k9sers/shared_invite/zt-3360a389v-ElLHrb0Dp1kAXqYUItSAFA)

#### Maintenance Release!

#### Resolved Issues

- [#&#8203;3570](https://github.com/derailed/k9s/issues/3570) 0.50.11 could not display any resources
- [#&#8203;3562](https://github.com/derailed/k9s/issues/3562) Can't delete namespace
- [#&#8203;3547](https://github.com/derailed/k9s/issues/3547) Error message from admission controller

***

<img src="https://raw.githubusercontent.com/derailed/k9s/master/assets/imhotep_logo.png" width="32" height="auto"/> © 2025 Imhotep Software LLC. All materials licensed under [Apache v2.0](http://www.apache.org/licenses/LICENSE-2.0)#

### [`v0.50.9`](https://github.com/derailed/k9s/releases/tag/v0.50.9)

<img src="https://raw.githubusercontent.com/derailed/k9s/master/assets/k9s.png" align="center" width="800" height="auto"/>

### Release v0.50.9
#### Notes

Thank you to all that contributed with flushing out issues and enhancements for K9s!
I'll try to mark some of these issues as fixed. But if you don't mind grab the latest rev
and see if we're happier with some of the fixes!
If you've filed an issue please help me verify and close.

Your support, kindness and awesome suggestions to make K9s better are, as ever, very much noted and appreciated!
Also big thanks to all that have allocated their own time to help others on both slack and on this repo!!

As you may know, K9s is not pimped out by corps with deep pockets, thus if you feel K9s is helping your Kubernetes journey,
please consider joining our [sponsorship program](https://github.com/sponsors/derailed) and/or make some noise on social! [@&#8203;kitesurfer](https://twitter.com/kitesurfer)

On Slack? Please join us [K9slackers](https://join.slack.com/t/k9sers/shared_invite/zt-3360a389v-ElLHrb0Dp1kAXqYUItSAFA)

#### Maintenance Release!

***

#### Resolved Issues

- [#&#8203;3459](https://github.com/derailed/k9s/issues/3459) Update the tablewriter dependency + implementation
- [#&#8203;3458](https://github.com/derailed/k9s/issues/3458) Unable to switch namespaces with 0.50.8

***

#### Contributed PRs

Please be sure to give `Big Thanks!` and `ATTA Girls/Boys!` to all the fine contributors for making K9s better for all of us!!

- [#&#8203;3460](https://github.com/derailed/k9s/pull/3460) update to tablewriter v1 apis

***

<img src="https://raw.githubusercontent.com/derailed/k9s/master/assets/imhotep_logo.png" width="32" height="auto"/> © 2025 Imhotep Software LLC. All materials licensed under [Apache v2.0](http://www.apache.org/licenses/LICENSE-2.0)#

</details>

---

### Configuration

📅 **Schedule**: (in timezone Europe/Oslo)

- Branch creation
  - At any time (no schedule defined)
- Automerge
  - At any time (no schedule defined)

🚦 **Automerge**: Disabled by config. Please merge this manually once you are satisfied.

♻ **Rebasing**: Whenever PR becomes conflicted, or you tick the rebase/retry checkbox.

🔕 **Ignore**: Close this PR and you won't be reminded about this update again.

---

 - [ ] <!-- rebase-check -->If you want to rebase/retry this PR, check this box

---

This PR has been generated by [Mend Renovate CLI](https://github.com/renovatebot/renovate).
<!--renovate-debug:eyJjcmVhdGVkSW5WZXIiOiI0NC4xMTIuMyIsInVwZGF0ZWRJblZlciI6IjQ0LjExMi4zIiwidGFyZ2V0QnJhbmNoIjoibWFpbiIsImxhYmVscyI6WyJyZW5vdmF0ZSJdfQ==-->

---------

Co-authored-by: Danijel Simeunovic <danijel.simeunovic@fortedigital.com>
Co-authored-by: Renovate Bot <renovate@forteapps.net>
Reviewed-on: https://git.forteapps.net/Forte/launchpad/pulls/35
Reviewed-by: Danijel Simeunovic <danijel.simeunovic@fortedigital.com>
Co-authored-by: gitea_admin <admin@forteapps.net>
Co-committed-by: gitea_admin <admin@forteapps.net>
2026-09-27 22:14:56 +00:00
2e54387eed chore(deps): update dependency kubectl-tree to v0.6.0 (#39)
/ test (push) Failing after 12m43s
This PR contains the following updates:

| Package | Update | Change |
|---|---|---|
| [kubectl-tree](https://github.com/ahmetb/kubectl-tree) | minor | `0.4.3` → `0.6.0` |

---

### Release Notes

<details>
<summary>ahmetb/kubectl-tree (kubectl-tree)</summary>

### [`v0.6.0`](https://github.com/ahmetb/kubectl-tree/releases/tag/v0.6.0)

#### Changelog

- [`07c5f12`](https://github.com/ahmetb/kubectl-tree/commit/07c5f1241c0af99171cd3d3ff5ec0f109f37058f) Release v0.6.0
- [`52dda04`](https://github.com/ahmetb/kubectl-tree/commit/52dda045e341f7b24e4258c0286c3fec10410ed2) feat: filter resources ([#&#8203;115](https://github.com/ahmetb/kubectl-tree/issues/115))
- [`55f6b48`](https://github.com/ahmetb/kubectl-tree/commit/55f6b482b7a828554850d30a603fc7bfcd05ba43) Merge pull request [#&#8203;117](https://github.com/ahmetb/kubectl-tree/issues/117) from ahmetb/dependabot/go\_modules/github.com/fatih/color-1.19.0
- [`f8a3daf`](https://github.com/ahmetb/kubectl-tree/commit/f8a3daf738056f538876d39047c24c7859650884) Merge pull request [#&#8203;116](https://github.com/ahmetb/kubectl-tree/issues/116) from ahmetb/dependabot/go\_modules/kubernetes-cc55a87f86
- [`f524512`](https://github.com/ahmetb/kubectl-tree/commit/f5245124c6dd6885075bc80d1a88a46e515c87ca) chore(deps): bump github.com/fatih/color from 1.15.0 to 1.19.0
- [`9d3c3c9`](https://github.com/ahmetb/kubectl-tree/commit/9d3c3c9aaa641f2c2a2a5a55077acd5d9477144b) chore(deps): bump the kubernetes group with 3 updates

### [`v0.5.0`](https://github.com/ahmetb/kubectl-tree/releases/tag/v0.5.0)

#### Changelog

- [`44b7841`](https://github.com/ahmetb/kubectl-tree/commit/44b784104c46a1ebd3c9a2f990106c2790de7708) chore(deps): bump goreleaser/goreleaser-action from 6 to 7 ([#&#8203;110](https://github.com/ahmetb/kubectl-tree/issues/110))

### [`v0.4.6`](https://github.com/ahmetb/kubectl-tree/releases/tag/v0.4.6)

#### Changelog

- [`ee7f2ca`](https://github.com/ahmetb/kubectl-tree/commit/ee7f2ca11e271c8ece1a8426bce4119d1ff38bac) Fix namespace and CRD handling logic (vibe slop)

</details>

---

### Configuration

📅 **Schedule**: (in timezone Europe/Oslo)

- Branch creation
  - At any time (no schedule defined)
- Automerge
  - At any time (no schedule defined)

🚦 **Automerge**: Disabled by config. Please merge this manually once you are satisfied.

♻ **Rebasing**: Whenever PR becomes conflicted, or you tick the rebase/retry checkbox.

🔕 **Ignore**: Close this PR and you won't be reminded about this update again.

---

 - [ ] <!-- rebase-check -->If you want to rebase/retry this PR, check this box

---

This PR has been generated by [Mend Renovate CLI](https://github.com/renovatebot/renovate).
<!--renovate-debug:eyJjcmVhdGVkSW5WZXIiOiI0NC4xMTIuMyIsInVwZGF0ZWRJblZlciI6IjQ0LjExMi4zIiwidGFyZ2V0QnJhbmNoIjoibWFpbiIsImxhYmVscyI6WyJyZW5vdmF0ZSJdfQ==-->

---------

Co-authored-by: Danijel Simeunovic <danijel.simeunovic@fortedigital.com>
Co-authored-by: Renovate Bot <renovate@forteapps.net>
Reviewed-on: https://git.forteapps.net/Forte/launchpad/pulls/39
Reviewed-by: Danijel Simeunovic <danijel.simeunovic@fortedigital.com>
Co-authored-by: gitea_admin <admin@forteapps.net>
Co-committed-by: gitea_admin <admin@forteapps.net>
2026-09-27 22:12:29 +00:00
danijel.simeunovic f35af13ef3 group:allNonMajor
/ test (push) Failing after 13m29s
2026-09-27 22:11:47 +00:00
7abee90f4e chore(deps): update dependency claude-code to v0.2.122 (#27)
/ test (push) Successful in 29s
This PR contains the following updates:

| Package | Update | Change |
|---|---|---|
| [claude-code](https://github.com/anthropics/claude-code) | patch | `latest` → `0.2.122` |

---

### Release Notes

<details>
<summary>anthropics/claude-code (claude-code)</summary>

### [`v0.2.107`](https://github.com/anthropics/claude-code/blob/HEAD/CHANGELOG.md#02107)

- CLAUDE.md files can now import other files. Add @&#8203;path/to/file.md to ./CLAUDE.md to load additional files on launch

### [`v0.2.74`](https://github.com/anthropics/claude-code/blob/HEAD/CHANGELOG.md#0274)

- Added support for refreshing dynamically generated API keys (via apiKeyHelper), with a 5 minute TTL
- Task tool can now perform writes and run bash commands

### [`v0.2.69`](https://github.com/anthropics/claude-code/blob/HEAD/CHANGELOG.md#0269)

- Fixed UI glitches with improved Select component behavior
- Enhanced terminal output display with better text truncation logic

### [`v0.2.67`](https://github.com/anthropics/claude-code/blob/HEAD/CHANGELOG.md#0267)

- Shared project permission rules can be saved in .claude/settings.json

### [`v0.2.59`](https://github.com/anthropics/claude-code/blob/HEAD/CHANGELOG.md#0259)

- Copy+paste images directly into your prompt
- Improved progress indicators for bash and fetch tools
- Bugfixes for non-interactive mode (-p)

### [`v0.2.54`](https://github.com/anthropics/claude-code/blob/HEAD/CHANGELOG.md#0254)

- Quickly add to Memory by starting your message with '#'
- Press ctrl+r to see full output for long tool results
- Added support for MCP SSE transport

### [`v0.2.53`](https://github.com/anthropics/claude-code/blob/HEAD/CHANGELOG.md#0253)

- New web fetch tool lets Claude view URLs that you paste in
- Fixed a bug with JPEG detection

### [`v0.2.41`](https://github.com/anthropics/claude-code/blob/HEAD/CHANGELOG.md#0241)

- MCP server startup timeout can now be configured via MCP\_TIMEOUT environment variable
- MCP server startup no longer blocks the app from starting up

### [`v0.2.32`](https://github.com/anthropics/claude-code/blob/HEAD/CHANGELOG.md#0232)

- Interactive MCP setup wizard: Run "claude mcp add" to add MCP servers with a step-by-step interface
- Fix for some PersistentShell issues

### [`v0.2.30`](https://github.com/anthropics/claude-code/blob/HEAD/CHANGELOG.md#0230)

- Added ANSI color theme for better terminal compatibility
- Fixed issue where slash command arguments weren't being sent properly
- (Mac-only) API keys are now stored in macOS Keychain

</details>

---

### Configuration

📅 **Schedule**: (in timezone Europe/Oslo)

- Branch creation
  - At any time (no schedule defined)
- Automerge
  - At any time (no schedule defined)

🚦 **Automerge**: Disabled by config. Please merge this manually once you are satisfied.

♻ **Rebasing**: Whenever PR becomes conflicted, or you tick the rebase/retry checkbox.

🔕 **Ignore**: Close this PR and you won't be reminded about this update again.

---

 - [ ] <!-- rebase-check -->If you want to rebase/retry this PR, check this box

---

This PR has been generated by [Mend Renovate CLI](https://github.com/renovatebot/renovate).
<!--renovate-debug:eyJjcmVhdGVkSW5WZXIiOiI0NC4xMTIuMyIsInVwZGF0ZWRJblZlciI6IjQ0LjExMi4zIiwidGFyZ2V0QnJhbmNoIjoibWFpbiIsImxhYmVscyI6WyJyZW5vdmF0ZSJdfQ==-->

---------

Co-authored-by: Danijel Simeunovic <danijel.simeunovic@fortedigital.com>
Co-authored-by: Renovate Bot <renovate@forteapps.net>
Reviewed-on: #27
Reviewed-by: Danijel Simeunovic <danijel.simeunovic@fortedigital.com>
Co-authored-by: gitea_admin <admin@forteapps.net>
Co-committed-by: gitea_admin <admin@forteapps.net>
2026-09-25 05:47:12 +00:00
bb37c6051f chore(deps): update dependency _1password to v1.12.2 (#30)
/ test (push) Failing after 14m48s
This PR contains the following updates:

| Package | Update | Change |
|---|---|---|
| [_1password](https://developer.1password.com/docs/cli/) | minor | `latest` → `1.12.2` |

---

### Configuration

📅 **Schedule**: (in timezone Europe/Oslo)

- Branch creation
  - At any time (no schedule defined)
- Automerge
  - At any time (no schedule defined)

🚦 **Automerge**: Disabled by config. Please merge this manually once you are satisfied.

♻ **Rebasing**: Whenever PR becomes conflicted, or you tick the rebase/retry checkbox.

🔕 **Ignore**: Close this PR and you won't be reminded about this update again.

---

 - [ ] <!-- rebase-check -->If you want to rebase/retry this PR, check this box

---

This PR has been generated by [Mend Renovate CLI](https://github.com/renovatebot/renovate).
<!--renovate-debug:eyJjcmVhdGVkSW5WZXIiOiI0NC4xMTIuMyIsInVwZGF0ZWRJblZlciI6IjQ0LjExMi4zIiwidGFyZ2V0QnJhbmNoIjoibWFpbiIsImxhYmVscyI6WyJyZW5vdmF0ZSJdfQ==-->

---------

Co-authored-by: Danijel Simeunovic <danijel.simeunovic@fortedigital.com>
Co-authored-by: Renovate Bot <renovate@forteapps.net>
Reviewed-on: #30
Reviewed-by: Danijel Simeunovic <danijel.simeunovic@fortedigital.com>
Co-authored-by: gitea_admin <admin@forteapps.net>
Co-committed-by: gitea_admin <admin@forteapps.net>
2026-09-25 05:46:32 +00:00
91c7a90d1b chore(deps): update alpine docker tag to v3.24 (#29)
/ test (push) Failing after 10m45s
This PR contains the following updates:

| Package | Update | Change |
|---|---|---|
| [alpine](https://hub.docker.com/_/alpine) ([source](https://github.com/alpinelinux/docker-alpine)) | minor | `3.20` → `3.24` |

---

### Configuration

📅 **Schedule**: (in timezone Europe/Oslo)

- Branch creation
  - At any time (no schedule defined)
- Automerge
  - At any time (no schedule defined)

🚦 **Automerge**: Disabled by config. Please merge this manually once you are satisfied.

♻ **Rebasing**: Whenever PR becomes conflicted, or you tick the rebase/retry checkbox.

🔕 **Ignore**: Close this PR and you won't be reminded about this update again.

---

 - [ ] <!-- rebase-check -->If you want to rebase/retry this PR, check this box

---

This PR has been generated by [Mend Renovate CLI](https://github.com/renovatebot/renovate).
<!--renovate-debug:eyJjcmVhdGVkSW5WZXIiOiI0NC4xMTIuMyIsInVwZGF0ZWRJblZlciI6IjQ0LjExMi4zIiwidGFyZ2V0QnJhbmNoIjoibWFpbiIsImxhYmVscyI6WyJyZW5vdmF0ZSJdfQ==-->

---------

Co-authored-by: Renovate Bot <renovate@forteapps.net>
Reviewed-on: #29
Reviewed-by: Danijel Simeunovic <danijel.simeunovic@fortedigital.com>
Co-authored-by: gitea_admin <admin@forteapps.net>
Co-committed-by: gitea_admin <admin@forteapps.net>
2026-09-25 05:40:40 +00:00
d42b5a89f3 chore(deps): update dependency dotnet-sdk to v2.1.810 (#28)
/ test (push) Failing after 11m30s
This PR contains the following updates:

| Package | Update | Change |
|---|---|---|
| [dotnet-sdk](https://dotnet.github.io/) | patch | `latest` → `2.1.810` |

---

### Configuration

📅 **Schedule**: (in timezone Europe/Oslo)

- Branch creation
  - At any time (no schedule defined)
- Automerge
  - At any time (no schedule defined)

🚦 **Automerge**: Disabled by config. Please merge this manually once you are satisfied.

♻ **Rebasing**: Whenever PR becomes conflicted, or you tick the rebase/retry checkbox.

🔕 **Ignore**: Close this PR and you won't be reminded about this update again.

---

 - [ ] <!-- rebase-check -->If you want to rebase/retry this PR, check this box

---

This PR has been generated by [Mend Renovate CLI](https://github.com/renovatebot/renovate).
<!--renovate-debug:eyJjcmVhdGVkSW5WZXIiOiI0NC4xMTIuMyIsInVwZGF0ZWRJblZlciI6IjQ0LjExMi4zIiwidGFyZ2V0QnJhbmNoIjoibWFpbiIsImxhYmVscyI6WyJyZW5vdmF0ZSJdfQ==-->

---------

Co-authored-by: Renovate Bot <renovate@forteapps.net>
Reviewed-on: #28
Reviewed-by: Danijel Simeunovic <danijel.simeunovic@fortedigital.com>
Co-authored-by: gitea_admin <admin@forteapps.net>
Co-committed-by: gitea_admin <admin@forteapps.net>
2026-09-25 05:39:52 +00:00
danijel.simeunovic c1f4298bfe renovate
/ test (push) Successful in 23s
2026-09-25 00:02:00 +02:00
danijel.simeunovic 14cabaf3f5 version bumps
/ test (push) Successful in 36s
2026-09-24 23:56:20 +02:00
danijel.simeunovic 809e90d12d upgrade loki
/ test (push) Successful in 31s
2026-09-23 20:46:25 +00:00
danijel.simeunovic eeb7321819 loki values
/ test (push) Failing after 11m2s
2026-09-23 20:20:19 +00:00
danijel.simeunovic 133bdb8715 benken secret
/ test (push) Successful in 46s
2026-09-23 20:30:09 +02:00
danijel.simeunovic c47e89e02a Update infra/values/base/loki-values.yaml
/ test (push) Successful in 11s
2026-09-16 17:17:12 +00:00
danijel.simeunovic 3bf6f22a4a keycloak client cleanup: harden candidate selection
/ test (push) Successful in 8s
2026-09-04 12:05:23 +00:00
danijel.simeunovic 10f27fa3c4 harden client cleanup scheduling
/ test (push) Successful in 13s
timeZone: "Europe/Oslo"
    startingDeadlineSeconds: 3600
2026-09-04 11:38:33 +00:00
gitea_admin 90ba7ac905 Keycloak: Run client cleanup once a month
/ test (push) Successful in 13s
2026-09-03 09:52:49 +00:00
gitea_admin b616e59231 Increase min age for keycloak client cleanup
/ test (push) Successful in 13s
increase to 15 days min age
2026-09-03 07:26:30 +00:00
danijel.simeunovic 705c010806 Mute deployment notifications
/ test (push) Successful in 9s
2026-08-25 12:34:33 +00:00
29624e845d fix(forte-drop-pg-backup): set MC_CONFIG_DIR so backups can upload (#23)
/ test (push) Successful in 10s
The nightly Postgres backup CronJob has been **failing every run** — no backups exist in `s3://drops/_pgbackups/`.

**Cause:** the upload container runs as uid 65532 (`runAsNonRoot`). `mc` defaults its config to `$HOME/.mc` = `/.mc` and dies with `mkdir /.mc: permission denied` on the non-writable root fs — before any upload.

**Fix:** set `MC_CONFIG_DIR=/work/.mc` (the shared emptyDir, writable via `fsGroup: 65532`). The `pg_dump` initContainer already succeeds; this lets the upload step actually run.

Validated: `kubectl kustomize` renders clean; env present on the upload container.

🤖 Generated with [Claude Code](https://claude.com/claude-code)

---------

Co-authored-by: Danijel Simeunovic <danijel.simeunovic@fortedigital.com>
Co-authored-by: Sten <sten@Sten-sin-MacBook-Pro.local>
Reviewed-on: #23
Reviewed-by: Danijel Simeunovic <danijel.simeunovic@fortedigital.com>
Co-authored-by: Jørgen Stensrud <jorgen.stensrud@fortedigital.com>
Co-committed-by: Jørgen Stensrud <jorgen.stensrud@fortedigital.com>
2026-08-25 09:44:02 +00:00
danijel.simeunovic 4712eb4804 wayfinder instructions
/ test (push) Successful in 8s
2026-08-01 12:10:50 +02:00
danijel.simeunovic 2696044a02 docs
/ test (push) Successful in 8s
2026-08-01 12:07:26 +02:00
danijel.simeunovic b0c0074f7f Merge branch 'main' of https://git.forteapps.net/Forte/launchpad
/ test (push) Successful in 8s
2026-07-02 15:27:25 +02:00
danijel.simeunovic 7f4a0bccf1 notify mail 2026-07-02 15:27:16 +02:00
jorgen.stensrud 52c752caba feat(auth-sidecar): inject AUTH_OIDC_ALLOWED_RETURN_HOSTS (#25)
/ test (push) Successful in 9s
2026-07-02 13:17:57 +00:00
danijel.simeunovic af1e94d85d review
/ test (push) Successful in 9s
2026-07-02 12:25:11 +02:00
jorgen.stensrudanddanijel.simeunovic df35cd0630 feat(auth-sidecar): inject AUTH_OIDC_COOKIE_DOMAIN (#24)
/ test (push) Successful in 10s
Adds AUTH_OIDC_COOKIE_DOMAIN to the injected OIDC sidecar, from the `policies.forteapps.io/auth-oidc-cookie-domain` annotation. Empty when unset = host-only = unchanged for every app. Pairs with forte-helm + auth-sidecar#23. Safe to merge anytime (opt-in).

---------

Co-authored-by: Danijel Simeunovic <danijel.simeunovic@fortedigital.com>
Reviewed-on: #24
Reviewed-by: Danijel Simeunovic <danijel.simeunovic@fortedigital.com>
2026-06-30 06:59:37 +00:00
danijel.simeunovic 04b3a210fe shared-prompts
/ test (push) Successful in 8s
2026-06-29 17:02:50 +02:00
danijel.simeunovic 330c25f241 model
/ test (push) Successful in 8s
2026-06-29 16:47:51 +02:00
jorgen.stensrud 3a23451802 feat(forte-drop): issuer dnsZones for *.drop.forteapps.net (subdomain-per-drop) (#22)
/ test (push) Successful in 12s
2026-06-26 11:38:30 +00:00
danijel.simeunovic 9297398d56 gitea update
/ test (push) Successful in 8s
2026-06-11 13:03:59 +02:00
danijel.simeunovic b0804e1e6a scan
/ test (push) Successful in 11s
2026-06-11 10:34:11 +02:00
danijel.simeunovic 8216399155 trufflehog
/ test (push) Failing after 33s
2026-06-11 10:14:25 +02:00
danijel.simeunovic a70f078bbb drop drop 2026-06-05 19:38:30 +02:00
danijel.simeunovic a24e61d538 disable slack notifications for forte-drop
Signed-off-by: Danijel Simeunovic <danijel.simeunovic@fortedigital.com>
2026-06-05 13:41:42 +00:00
jorgen.stensrudandSten 275ec675da fix(apps): drop dangling namespace.yaml ref (enterprise-apps ComparisonError) (#19)
0a98674 deleted `namespace.yaml` but `apps/overlays/upc-dev/forte-drop/kustomization.yaml` still lists it → `kustomize build` fails → the **enterprise-apps** app-of-apps has a ComparisonError and the whole overlay stopped syncing. Visible symptom: `secret "forte-drop-secrets" not found` on all forte-drop pods (the SealedSecret no longer applies).

One-line fix: remove the dangling resource entry. The namespace itself is fine — the forte-drop Application has `CreateNamespace=true`.

@danijel.simeunovic — pairs with your cleanup; after this merges the secret re-applies and the pods only need the right image tag (helm-prod-values PR #4: `buildcache` → `v20260604-200105-1316f7a`, buildcache is the buildx cache manifest, not a runnable image).

Co-authored-by: Sten <sten@Sten-sin-MacBook-Pro.local>
Reviewed-on: #19
Reviewed-by: Danijel Simeunovic <danijel.simeunovic@fortedigital.com>
2026-06-05 08:44:56 +00:00
danijel.simeunovic 0a98674a27 not needed 2026-06-05 00:05:56 +02:00
b713ec853c feat(apps): forte-drop web + mcp argocd apps (prod) (#18)
## Summary

ArgoCD Applications + Keycloak clients + sealed secret for forte-drop **web + mcp** (PROD).

## What changed

- **forte-drop** + **forte-drop-mcp** ArgoCD Applications (two-source: forte-helm chart + helm-prod-values).
- **namespace.yaml** — explicit `forte-drop` Namespace at sync-wave -1, `Prune=false` (avoids first-sync race for namespaced resources; doesn't cascade-delete on base removal).
- **keycloak-client-forte-drop** + **keycloak-client-forte-drop-mcp** — labeled config Secrets; the registrar creates the OIDC clients in the `forte` realm within ~2 min.
- **forte-drop-secrets** SealedSecret — UpCloud S3 creds (existing drops bucket) + PG creds + PASSWORD_GATE_SECRET. Consumed by both deployments + the pg-backup CronJob.
- **forte-drop-web PDB** — minAvailable 1 (selector verified against the live forteapp chart's pod labels).
- Wired into `apps/overlays/upc-dev` (NOT base → stays out of upc-prod).

## Post-merge manual step (one-time)

`auth-oidc` SealedSecret for the web sidecar is still commented out — it needs the `client-secret` the Keycloak registrar writes to `forte-drop-oidc-credentials` after first sync:

```bash
CLIENT_SECRET=$(kubectl -n forte-drop get secret forte-drop-oidc-credentials -o jsonpath='{.data.client-secret}' | base64 -d)
kubectl create secret generic auth-oidc -n forte-drop \
  --from-literal=client-secret="$CLIENT_SECRET" \
  --from-literal=cookie-secret="$(openssl rand -hex 32)" \
  --dry-run=client -o yaml > private/auth-oidc.yaml
kubeseal --format=yaml --controller-name=sealed-secrets-controller --controller-namespace=kube-system \
  < private/auth-oidc.yaml > apps/base/forte-drop/auth-oidc-sealed.yaml
# uncomment in kustomization, commit, push
```

## Depends on

- launchpad PR #17 (postgres + namespace via CreateNamespace).
- helm-prod-values forte-drop PR (values).

## Review

- [x] codex: namespace first-sync race → fixed (explicit namespace, sync-wave -1).
- [x] Keycloak registrar unblocked (stale chibisafe/minio config secrets removed; registrar green).

🤖 Generated with Claude Code

Co-authored-by: Sten <sten@Sten-sin-MacBook-Pro.local>
Co-authored-by: Sten <sten@Mac.domain_not_set.invalid>
Co-authored-by: Danijel Simeunovic <danijel.simeunovic@fortedigital.com>
Reviewed-on: #18
Reviewed-by: Danijel Simeunovic <danijel.simeunovic@fortedigital.com>
2026-06-04 18:47:08 +00:00
danijel.simeunovic dffb9c43f0 dbunk delete 2026-06-03 20:16:37 +02:00
danijel.simeunovic 33f0463c1f upc dev spec 2026-06-03 20:14:21 +02:00
danijel.simeunovic a997a6b81e kc cleanup 2026-06-03 17:41:10 +02:00
danijel.simeunovic 071f57f1d3 kc cleanup 2026-06-03 17:39:02 +02:00
danijel.simeunovic ecf871f0e4 kc fix 2026-06-03 17:36:29 +02:00
danijel.simeunovic 376d81a5ac keycloak client cleanup 2026-06-03 17:28:08 +02:00
danijel.simeunovic 428de7af78 tofu config and docs 2026-05-31 20:48:25 +02:00
danijel.simeunovic 24c59256c9 tofu+tools 2026-05-31 19:53:26 +02:00
danijel.simeunovic e319295f62 bunker host 2026-05-29 22:06:08 +02:00
danijel.simeunovic a7106bc8f4 new tls wildcard 2026-05-29 21:58:34 +02:00
danijel.simeunovic 6d874111da tenantID 2026-05-29 21:51:27 +02:00
danijel.simeunovic a8cc103e4c dns01 2026-05-29 21:48:32 +02:00
Ghostdanijel.simeunovicGhost <>
a9dbaf5354 feature/tofu (#15)
@thomas.solbjor her er "import" av tofu fra ditt repo med justeringer for å tilpasse patterns her. Også minimalisert til å kun opprette cluster, ingen managed services som postgres etc. Ta en titt.

Co-authored-by: Danijel Simeunovic <danijel.simeunovic@fortedigital.com>
Reviewed-on: #15
Reviewed-by: Danijel Simeunovic <danijel.simeunovic@fortedigital.com>
Co-authored-by: Ghost <>
Co-committed-by: Ghost <>
2026-05-29 15:48:28 +00:00
danijel.simeunovic 6e175e9e8c docs 2026-05-29 15:20:51 +02:00
jorgen.stensrudandSten 396c771f59 feat(homepage): list forte_drop in Apps (#16)
Adds forte_drop as an external service entry in the upc-dev Homepage portal.

- Target host: https://drop.hackathon.forteapps.net (current Coolify deploy).
- One-line addition under `services > Apps` in `infra/values/upc-dev/homepage-values.yaml`.
- Will be retargeted to https://drop.forteapps.net once the K8s migration ships (spec in forte_drop repo: docs/superpowers/specs/2026-05-28-k8s-migration-design.md).

Zero risk — pure metadata, no cluster mutation beyond Homepage refresh.

Co-authored-by: Sten <sten@Mac.domain_not_set.invalid>
Reviewed-on: #16
Reviewed-by: Danijel Simeunovic <danijel.simeunovic@fortedigital.com>
2026-05-28 14:04:05 +00:00
danijel.simeunovic 0582cd9917 policy 2026-05-27 23:23:21 +02:00
danijel.simeunovic c49d03d7f7 onlySSO 2026-05-16 23:04:11 +02:00
danijel.simeunovic d47dba2ae5 signups 2026-05-16 22:12:04 +02:00
danijel.simeunovic cf9eb47ecf script fix 2026-05-16 22:08:56 +02:00
danijel.simeunovic 3eca723f05 diffs 2026-05-16 22:05:02 +02:00
danijel.simeunovic f36996da11 script fix 2026-05-16 21:57:44 +02:00
danijel.simeunovic 6bf7db21d0 registrar error 2026-05-16 21:55:44 +02:00
danijel.simeunovic 2641d55784 scopes 2026-05-16 21:53:36 +02:00
danijel.simeunovic 117297effc sso vw 2026-05-16 21:47:59 +02:00
danijel.simeunovic fda90f9e01 adminToken enc 2026-05-16 21:34:34 +02:00
danijel.simeunovic 1124377d97 adminToken 2026-05-16 21:29:14 +02:00
danijel.simeunovic c0710b89bb no signup 2026-05-16 21:15:38 +02:00
danijel.simeunovic d7bda18aea domain 2026-05-16 21:11:17 +02:00
danijel.simeunovic 2796e1b9d3 name 2026-05-16 21:09:04 +02:00
danijel.simeunovic d7a0c26117 icon 2026-05-16 21:08:36 +02:00
danijel.simeunovic 693f2f9168 homepage 2026-05-16 21:07:29 +02:00
danijel.simeunovic 2509ef062c domain restriction 2026-05-16 20:58:00 +02:00
danijel.simeunovic 957757e557 host 2026-05-16 20:51:44 +02:00
danijel.simeunovic 070799da05 bitw 2026-05-16 20:49:25 +02:00
danijel.simeunovic 1a2817e537 domain fix 2026-05-16 20:42:17 +02:00
danijel.simeunovic b47b0035f5 smtp auth 2026-05-16 20:38:21 +02:00
danijel.simeunovic d3fac4d43e smtp port 2026-05-16 20:34:22 +02:00
danijel.simeunovic c37bd3ef04 from 2026-05-16 20:30:32 +02:00
danijel.simeunovic ad661ba3dd allow signup 2026-05-16 20:27:36 +02:00
danijel.simeunovic a9625f96e6 db secrets 2026-05-16 20:23:58 +02:00
danijel.simeunovic cb64edc927 cleanup 2026-05-16 20:18:48 +02:00
danijel.simeunovic ac1c242fb9 kust 2026-05-16 20:17:14 +02:00
danijel.simeunovic 4b29c07fd6 secret 2026-05-16 20:15:37 +02:00
danijel.simeunovic 52732626e5 ignorediffs 2026-05-16 20:10:19 +02:00
danijel.simeunovic 8634436dd4 StatefulSet 2026-05-16 20:07:17 +02:00
danijel.simeunovic a8baa169e9 secrets vw 2026-05-16 20:00:22 +02:00
danijel.simeunovic 73ef3a6e12 pg fix 2026-05-16 19:49:38 +02:00
danijel.simeunovic 302705d374 icon 2026-05-16 19:45:19 +02:00
danijel.simeunovic f3286ef77e homepage vw 2026-05-16 19:44:17 +02:00
danijel.simeunovic 74f4f86770 vw apps 2026-05-16 19:34:42 +02:00
danijel.simeunovic f2c56156bf vw postgres 2026-05-16 18:10:14 +02:00
danijel.simeunovic 21fb50ba00 vw fixes 2026-05-16 15:55:18 +02:00
danijel.simeunovic b90b630b06 comment 2026-05-16 15:52:10 +02:00
danijel.simeunovic 66de9b8a0a replicas 2026-05-16 15:48:13 +02:00
danijel.simeunovic 716c552be9 ns 2026-05-16 15:44:04 +02:00
danijel.simeunovic f048b47a0f vaultwarden 2026-05-16 15:39:55 +02:00
danijel.simeunovic 66f40427ee mappings 2026-05-15 15:47:25 +02:00
danijel.simeunovic 332881cbd0 fix 2026-05-14 23:47:14 +02:00
danijel.simeunovic f363afa087 browser flow override 2026-05-14 23:43:40 +02:00
danijel.simeunovic bc42347cb6 gitea+ACCOUNT_LINKING 2026-05-14 21:30:53 +02:00
danijel.simeunovic 80d7bff4bc groups 2026-05-14 21:18:17 +02:00
danijel.simeunovic 3644a3ec87 mappers 2026-05-14 21:14:57 +02:00
danijel.simeunovic bd478478f1 fix attemt 2026-05-14 20:40:44 +02:00
danijel.simeunovic 67b1d95509 account linking 2026-05-14 19:39:38 +02:00
danijel.simeunovic fff95d98a5 remove protocol mappers 2026-05-13 23:15:28 +02:00
danijel.simeunovic 8b743efa43 KC fix 2026-05-13 23:13:09 +02:00
danijel.simeunovic 4ca9039686 kpolicy 2026-04-29 12:54:07 +02:00
danijel.simeunovic 6a9eadbde8 vault ignore diffs 2026-04-29 12:50:10 +02:00
danijel.simeunovic f19f7c9237 icon 2026-04-29 12:07:04 +02:00
danijel.simeunovic 5a459d486e dbunk-demo 2026-04-29 10:53:35 +02:00
danijel.simeunovic 31fb476a78 row 2026-04-29 10:06:02 +02:00
danijel.simeunovic a088425b70 homepage config 2026-04-29 10:04:20 +02:00
danijel.simeunovic b3b3edf82c no header 2026-04-28 23:03:15 +02:00
danijel.simeunovic 308755a4b3 layout 2026-04-28 23:02:13 +02:00
danijel.simeunovicandCopilot db6afaf180 vault
Co-authored-by: Copilot <copilot@github.com>
2026-04-28 22:44:57 +02:00
danijel.simeunovic 5a2f9a1b88 Update infra/values/base/keycloak-values.yaml
Signed-off-by: Danijel Simeunovic <danijel.simeunovic@fortedigital.com>
2026-04-28 19:27:38 +00:00
danijel.simeunovic 1c6f18b67c homepage 2026-04-28 20:38:59 +02:00
danijel.simeunovic 7132f5000e docs 2026-04-27 20:35:27 +02:00
danijel.simeunovic b4100bd456 mm ns 2026-04-27 20:16:06 +02:00
danijel.simeunovic fff117a500 ns 2026-04-27 17:40:46 +02:00
danijel.simeunovic 03c75fc4cd mm ns 2026-04-27 17:40:05 +02:00
danijel.simeunovic df73c4bdc0 mm sync pol 2026-04-27 17:37:54 +02:00
danijel.simeunovic 6a7de704f2 enterprise-apps 2026-04-27 17:34:43 +02:00
danijel.simeunovic be8bbd2c12 aksapps 2026-04-27 17:33:47 +02:00
danijel.simeunovic c469ab44b0 ent apps 2026-04-27 17:28:48 +02:00
danijel.simeunovic 290c8b91f8 db pass 2026-04-27 14:05:38 +02:00
danijel.simeunovic a776bae4bd image tag 2026-04-27 13:00:37 +02:00
danijel.simeunovic 7405ce27dd chart name 2026-04-27 12:55:20 +02:00
danijel.simeunovic 1281e8ef37 databunker 2026-04-27 12:54:18 +02:00
danijel.simeunovic c497c54e8e fix 2026-04-27 12:28:47 +02:00
danijel.simeunovic b57459cf85 rm secrets2 2026-04-27 12:25:25 +02:00
danijel.simeunovic e8dd213685 rm secrets 2026-04-27 12:24:14 +02:00
danijel.simeunovic 1d879c82f9 secrets shuffle 2026-04-27 12:21:50 +02:00
danijel.simeunovic 94c8265475 overlays2 2026-04-27 12:01:59 +02:00
danijel.simeunovic 17d7c4a655 overlays 2026-04-27 11:49:10 +02:00
danijel.simeunovic f3dba72c5d aks-dev 2026-04-27 11:33:24 +02:00
danijel.simeunovic cc9c9049eb ignore diff 2026-04-26 23:55:55 +02:00
danijel.simeunovic 9f6c5105af netpol all remove 2026-04-25 16:04:13 +02:00
danijel.simeunovic 45e502d74d argocd tls 2026-04-25 11:49:17 +02:00
214 changed files with 5943 additions and 601 deletions
+2
View File
@@ -0,0 +1,2 @@
# Force LF line endings for shell scripts
*.sh text eol=lf
+8 -4
View File
@@ -23,25 +23,29 @@ jobs:
REVIEW__INLINE_COMMENT_FALLBACK: "false" REVIEW__INLINE_COMMENT_FALLBACK: "false"
# LLM configuration # LLM configuration
LLM__PROVIDER: CLAUDE LLM__PROVIDER: CLAUDE
LLM__META__MODEL: claude-sonnet-4-20250514 LLM__META__MODEL: claude-sonnet-5-5
LLM__META__REASONING__EFFORT: high
LLM__META__MAX_TOKENS: "4096" LLM__META__MAX_TOKENS: "4096"
LLM__HTTP_CLIENT__API_URL: https://api.anthropic.com LLM__HTTP_CLIENT__API_URL: https://api.anthropic.com
LLM__HTTP_CLIENT__API_TOKEN: ${{ secrets.ANTHROPIC_API_KEY }} LLM__HTTP_CLIENT__API_TOKEN: ${{ secrets.ANTHROPIC_API_KEY }}
steps: steps:
- name: Checkout repository - name: Checkout repository
uses: actions/checkout@v4 uses: actions/checkout@v7
with: with:
submodules: true submodules: true
fetch-depth: 0 fetch-depth: 0
token: ${{ secrets.AI_REVIEW_TOKEN }} token: ${{ secrets.AI_REVIEW_TOKEN }}
- name: Update submodules to remote
run: git submodule update --remote --merge
- name: Run inline review - name: Run inline review
uses: docker://nikitafilonov/ai-review:v0.64.0 uses: docker://nikitafilonov/ai-review:v0.77.0
with: with:
args: ai-review run-inline args: ai-review run-inline
- name: Run summary review - name: Run summary review
uses: docker://nikitafilonov/ai-review:v0.64.0 uses: docker://nikitafilonov/ai-review:v0.77.0
with: with:
args: ai-review run-summary args: ai-review run-summary
+20
View File
@@ -0,0 +1,20 @@
on:
push:
branches:
- main
pull_request:
jobs:
test:
runs-on: ubuntu-latest
steps:
- name: Checkout code
uses: actions/checkout@v7
with:
fetch-depth: 0
- name: Install TruffleHog
run: |
curl -sSfL https://raw.githubusercontent.com/trufflesecurity/trufflehog/main/scripts/install.sh \
| sh -s -- -b /usr/local/bin
- name: Secret Scanning
run: trufflehog git file://. --fail --no-update --results=verified,unknown
+9 -1
View File
@@ -15,4 +15,12 @@ CLAUDE.md
devbox.d/ devbox.d/
devbox.lock devbox.lock
.devbox/ .devbox/
bash.exe.stackdump bash.exe.stackdump
# OpenTofu
.tofu/configs/*.env
.tofu/scripts/*.config
.tofu/platforms/**/.terraform/
.tofu/platforms/**/terraform.tfstate*
.tofu/platforms/**/tfplan
.tofu/platforms/**/.terraform.lock.hcl
+2
View File
@@ -1,3 +1,5 @@
[submodule "shared-prompts"] [submodule "shared-prompts"]
path = shared-prompts path = shared-prompts
url = https://git.forteapps.net/Forte/ai-review-prompts.git url = https://git.forteapps.net/Forte/ai-review-prompts.git
branch = main
+9
View File
@@ -0,0 +1,9 @@
# Azure AKS credentials — copy to aks.env and fill in values
# NEVER commit aks.env to git!
# Required
AZURE_TENANT_ID=your-azure-tenant-id
AZURE_SUBSCRIPTION_ID=your-azure-subscription-id
# Optional — defaults to cluster name if not set
ARM_RESOURCE_GROUP=
+10
View File
@@ -0,0 +1,10 @@
# AWS EKS credentials — copy to eks.env and fill in values
# NEVER commit eks.env to git!
# Required — AWS CLI profile or access key
AWS_PROFILE=default
AWS_REGION=eu-west-1
# Optional — override with explicit keys instead of profile
# AWS_ACCESS_KEY_ID=
# AWS_SECRET_ACCESS_KEY=
+9
View File
@@ -0,0 +1,9 @@
# GCP GKE credentials — copy to gke.env and fill in values
# NEVER commit gke.env to git!
# Required
GCP_PROJECT_ID=your-gcp-project-id
GCP_REGION=europe-west4
# Optional — path to service account JSON key (if not using gcloud auth)
# GOOGLE_APPLICATION_CREDENTIALS=/path/to/sa-key.json
+8
View File
@@ -0,0 +1,8 @@
# UpCloud credentials — copy to upc.env and fill in values
# NEVER commit upc.env to git!
# Required
UPCLOUD_TOKEN=your-upcloud-api-token
# Optional — set after cluster creation for kubeconfig retrieval
UPCLOUD_CLUSTER_ID=
+18
View File
@@ -0,0 +1,18 @@
module "cluster" {
source = "../modules/cluster"
prefix = "clst-dev"
location = "norwayeast"
resource_group_name = "clst-dev-rg"
# AKS — small dev nodes
aks_node_vm_size = "Standard_B2s"
aks_node_count = 2
enable_delete_lock = false
tags = {
Environment = "dev"
ManagedBy = "tofu"
}
}
+26
View File
@@ -0,0 +1,26 @@
# ─── Cluster ─────────────────────────────────────────────────────────
output "cluster_name" {
value = module.cluster.cluster_name
}
output "resource_group_name" {
value = module.cluster.resource_group_name
}
output "kubernetes_version" {
value = module.cluster.kubernetes_version
}
output "location" {
value = module.cluster.location
}
output "oidc_issuer_url" {
value = module.cluster.oidc_issuer_url
}
output "kubeconfig" {
value = module.cluster.kubeconfig
sensitive = true
}
+17
View File
@@ -0,0 +1,17 @@
terraform {
required_version = ">= 1.0"
required_providers {
azurerm = {
source = "hashicorp/azurerm"
version = "~> 4.0"
}
}
}
provider "azurerm" {
features {}
# Credentials via environment variables:
# ARM_SUBSCRIPTION_ID, ARM_TENANT_ID, ARM_CLIENT_ID, ARM_CLIENT_SECRET
# Or: az login (uses your Azure CLI session)
}
@@ -0,0 +1,72 @@
# Current Azure/Entra ID context — provides tenant_id used in outputs
data "azurerm_client_config" "current" {}
# ─── Resource Group ───────────────────────────────────────────────────
resource "azurerm_resource_group" "main" {
name = var.resource_group_name
location = var.location
tags = var.tags
}
resource "azurerm_management_lock" "main" {
count = var.enable_delete_lock ? 1 : 0
name = "${var.prefix}-delete-lock"
scope = azurerm_resource_group.main.id
lock_level = "CanNotDelete"
notes = "Prevents accidental deletion of production resources"
}
# ─── Networking ───────────────────────────────────────────────────────
resource "azurerm_virtual_network" "main" {
name = "${var.prefix}-vnet"
resource_group_name = azurerm_resource_group.main.name
location = azurerm_resource_group.main.location
address_space = [var.vnet_address_space]
tags = var.tags
}
# AKS nodes subnet
resource "azurerm_subnet" "aks" {
name = "${var.prefix}-aks-subnet"
resource_group_name = azurerm_resource_group.main.name
virtual_network_name = azurerm_virtual_network.main.name
address_prefixes = [var.aks_subnet_cidr]
}
# ─── AKS Cluster ──────────────────────────────────────────────────────
resource "azurerm_kubernetes_cluster" "main" {
name = "${var.prefix}-aks"
resource_group_name = azurerm_resource_group.main.name
location = azurerm_resource_group.main.location
dns_prefix = replace(var.prefix, "-", "")
kubernetes_version = var.aks_kubernetes_version
tags = var.tags
default_node_pool {
name = "system"
node_count = var.aks_node_count
vm_size = var.aks_node_vm_size
vnet_subnet_id = azurerm_subnet.aks.id
node_labels = {
prefix = var.prefix
role = "worker"
env = lookup(var.tags, "Environment", "dev")
}
}
identity {
type = "SystemAssigned"
}
network_profile {
network_plugin = "azure"
network_policy = "azure"
}
# Enable Workload Identity for keyless Azure service access (MSI)
oidc_issuer_enabled = true
workload_identity_enabled = true
}
@@ -0,0 +1,32 @@
# ─── Cluster ─────────────────────────────────────────────────────────
output "cluster_name" {
description = "AKS cluster name"
value = azurerm_kubernetes_cluster.main.name
}
output "resource_group_name" {
description = "Resource group name"
value = azurerm_resource_group.main.name
}
output "kubernetes_version" {
description = "Kubernetes version"
value = azurerm_kubernetes_cluster.main.kubernetes_version
}
output "location" {
description = "Azure region"
value = azurerm_resource_group.main.location
}
output "oidc_issuer_url" {
description = "AKS OIDC issuer URL (for workload identity federation)"
value = azurerm_kubernetes_cluster.main.oidc_issuer_url
}
output "kubeconfig" {
description = "Kubeconfig for the AKS cluster"
value = azurerm_kubernetes_cluster.main.kube_config_raw
sensitive = true
}
@@ -0,0 +1,18 @@
terraform {
required_version = ">= 1.0"
required_providers {
azurerm = {
source = "hashicorp/azurerm"
version = "~> 4.0"
}
azuread = {
source = "hashicorp/azuread"
version = "~> 3.0"
}
random = {
source = "hashicorp/random"
version = "~> 3.0"
}
}
}
@@ -0,0 +1,56 @@
# ─── Cluster ─────────────────────────────────────────────────────────
variable "prefix" {
description = "Prefix for resource names"
type = string
}
variable "location" {
description = "Azure region (e.g., norwayeast, westeurope, northeurope)"
type = string
}
variable "resource_group_name" {
description = "Name of the Azure Resource Group to create"
type = string
}
variable "vnet_address_space" {
description = "Address space for the virtual network"
type = string
default = "10.100.0.0/16"
}
variable "aks_subnet_cidr" {
description = "CIDR block for the AKS node subnet"
type = string
default = "10.100.0.0/22"
}
variable "aks_node_vm_size" {
description = "VM size for AKS worker nodes (e.g., Standard_B2s, Standard_D4s_v3)"
type = string
}
variable "aks_node_count" {
description = "Number of AKS worker nodes"
type = number
}
variable "aks_kubernetes_version" {
description = "Kubernetes version for AKS (null = latest stable)"
type = string
default = null
}
variable "enable_delete_lock" {
description = "Protect the resource group from accidental deletion"
type = bool
default = false
}
variable "tags" {
description = "Tags applied to all resources"
type = map(string)
default = {}
}
+18
View File
@@ -0,0 +1,18 @@
module "cluster" {
source = "../modules/cluster"
prefix = "clst"
location = "westeurope"
resource_group_name = "clst-prod-rg"
# AKS — general-purpose nodes for production
aks_node_vm_size = "Standard_D4s_v3"
aks_node_count = 3
enable_delete_lock = true
tags = {
Environment = "prod"
ManagedBy = "tofu"
}
}
+26
View File
@@ -0,0 +1,26 @@
# ─── Cluster ─────────────────────────────────────────────────────────
output "cluster_name" {
value = module.cluster.cluster_name
}
output "resource_group_name" {
value = module.cluster.resource_group_name
}
output "kubernetes_version" {
value = module.cluster.kubernetes_version
}
output "location" {
value = module.cluster.location
}
output "oidc_issuer_url" {
value = module.cluster.oidc_issuer_url
}
output "kubeconfig" {
value = module.cluster.kubeconfig
sensitive = true
}
+17
View File
@@ -0,0 +1,17 @@
terraform {
required_version = ">= 1.0"
required_providers {
azurerm = {
source = "hashicorp/azurerm"
version = "~> 4.0"
}
}
}
provider "azurerm" {
features {}
# Credentials via environment variables:
# ARM_SUBSCRIPTION_ID, ARM_TENANT_ID, ARM_CLIENT_ID, ARM_CLIENT_SECRET
# Or: az login (uses your Azure CLI session)
}
+173
View File
@@ -0,0 +1,173 @@
# =============================================================================
# Azure Workload Cluster
# =============================================================================
# A lean AKS cluster for running application workloads. No managed data
# services — those live on the platform cluster. ArgoCD (on the platform
# cluster) deploys apps to this cluster via the app-of-apps pattern.
#
# Platform components deployed by deploy-workload.sh:
# nginx-ingress, cert-manager, external-dns, external-secrets, alloy
#
# Usage:
# tofu init && tofu plan && tofu apply
# ./sync-tofu-outputs.sh --env azure-workload
# ./deploy-workload.sh --env azure-workload
# =============================================================================
variable "prefix" {
description = "Prefix for resource names (e.g., clst-workload)"
type = string
default = "clst-workload"
}
variable "location" {
description = "Azure region"
type = string
default = "norwayeast"
}
variable "resource_group_name" {
description = "Name of the Azure Resource Group to create"
type = string
default = "clst-workload-rg"
}
variable "vnet_address_space" {
description = "Address space for the virtual network"
type = string
default = "10.110.0.0/16"
}
variable "aks_subnet_cidr" {
description = "CIDR block for the AKS node subnet"
type = string
default = "10.110.0.0/22"
}
variable "aks_node_vm_size" {
description = "VM size for AKS worker nodes"
type = string
default = "Standard_B2s"
}
variable "aks_node_count" {
description = "Number of AKS worker nodes"
type = number
default = 2
}
variable "aks_kubernetes_version" {
description = "Kubernetes version for AKS (null = latest stable)"
type = string
default = null
}
variable "domain" {
description = "Public domain name — must have an existing Azure DNS zone"
type = string
}
variable "dns_zone_resource_group" {
description = "Resource group containing the Azure DNS zone (defaults to cluster RG)"
type = string
default = ""
}
variable "tags" {
description = "Tags applied to all resources"
type = map(string)
default = {
Environment = "workload"
ManagedBy = "tofu"
}
}
# ─── Resource Group ───────────────────────────────────────────────────
resource "azurerm_resource_group" "main" {
name = var.resource_group_name
location = var.location
tags = var.tags
}
# ─── Networking ───────────────────────────────────────────────────────
resource "azurerm_virtual_network" "main" {
name = "${var.prefix}-vnet"
resource_group_name = azurerm_resource_group.main.name
location = azurerm_resource_group.main.location
address_space = [var.vnet_address_space]
tags = var.tags
}
resource "azurerm_subnet" "aks" {
name = "${var.prefix}-aks-subnet"
resource_group_name = azurerm_resource_group.main.name
virtual_network_name = azurerm_virtual_network.main.name
address_prefixes = [var.aks_subnet_cidr]
}
# ─── AKS Cluster ──────────────────────────────────────────────────────
resource "azurerm_kubernetes_cluster" "main" {
name = "${var.prefix}-aks"
resource_group_name = azurerm_resource_group.main.name
location = azurerm_resource_group.main.location
dns_prefix = replace(var.prefix, "-", "")
kubernetes_version = var.aks_kubernetes_version
tags = var.tags
default_node_pool {
name = "system"
node_count = var.aks_node_count
vm_size = var.aks_node_vm_size
vnet_subnet_id = azurerm_subnet.aks.id
node_labels = {
prefix = var.prefix
role = "worker"
env = lookup(var.tags, "Environment", "workload")
}
}
identity {
type = "SystemAssigned"
}
network_profile {
network_plugin = "azure"
network_policy = "azure"
}
oidc_issuer_enabled = true
workload_identity_enabled = true
}
# ─── External-DNS Workload Identity ──────────────────────────────────
# Allows external-dns to manage Azure DNS records for app ingresses.
data "azurerm_dns_zone" "main" {
name = var.domain
resource_group_name = var.dns_zone_resource_group != "" ? var.dns_zone_resource_group : azurerm_resource_group.main.name
}
resource "azurerm_user_assigned_identity" "external_dns" {
name = "${var.prefix}-external-dns-identity"
resource_group_name = azurerm_resource_group.main.name
location = azurerm_resource_group.main.location
tags = var.tags
}
resource "azurerm_role_assignment" "external_dns_dns_contributor" {
scope = data.azurerm_dns_zone.main.id
role_definition_name = "DNS Zone Contributor"
principal_id = azurerm_user_assigned_identity.external_dns.principal_id
}
resource "azurerm_federated_identity_credential" "external_dns" {
name = "${var.prefix}-external-dns-fedcred"
resource_group_name = azurerm_resource_group.main.name
parent_id = azurerm_user_assigned_identity.external_dns.id
audience = ["api://AzureADTokenExchange"]
issuer = azurerm_kubernetes_cluster.main.oidc_issuer_url
subject = "system:serviceaccount:external-dns:external-dns"
}
+4
View File
@@ -0,0 +1,4 @@
output "cluster_name" { value = azurerm_kubernetes_cluster.main.name }
output "resource_group_name" { value = azurerm_resource_group.main.name }
output "location" { value = azurerm_resource_group.main.location }
output "external_dns_identity_client_id" { value = azurerm_user_assigned_identity.external_dns.client_id }
+21
View File
@@ -0,0 +1,21 @@
terraform {
required_version = ">= 1.0"
required_providers {
azurerm = {
source = "hashicorp/azurerm"
version = "~> 4.0"
}
random = {
source = "hashicorp/random"
version = "~> 3.0"
}
}
}
provider "azurerm" {
features {}
# Credentials via environment variables:
# ARM_SUBSCRIPTION_ID, ARM_TENANT_ID, ARM_CLIENT_ID, ARM_CLIENT_SECRET
# Or: az login (uses your Azure CLI session)
}
+21
View File
@@ -0,0 +1,21 @@
module "cluster" {
source = "../modules/cluster"
region = var.region
prefix = "clst-dev"
# VPC
availability_zones = ["${var.region}a", "${var.region}b"]
# EKS — small dev nodes
node_instance_type = "t3.medium"
node_count = 2
node_min_count = 1
node_max_count = 4
kubernetes_version = "1.30"
tags = {
Environment = "dev"
ManagedBy = "tofu"
}
}
+5
View File
@@ -0,0 +1,5 @@
output "cluster_name" { value = module.cluster.cluster_name }
output "aws_region" { value = module.cluster.aws_region }
output "oidc_issuer_url" { value = module.cluster.oidc_issuer_url }
output "oidc_provider_arn" { value = module.cluster.oidc_provider_arn }
output "vpc_id" { value = module.cluster.vpc_id }
+24
View File
@@ -0,0 +1,24 @@
terraform {
required_providers {
aws = {
source = "hashicorp/aws"
version = "~> 5.0"
}
tls = {
source = "hashicorp/tls"
version = "~> 4.0"
}
}
}
# Authentication: set AWS_ACCESS_KEY_ID, AWS_SECRET_ACCESS_KEY, AWS_SESSION_TOKEN
# or configure an AWS profile: export AWS_PROFILE=clst
provider "aws" {
region = var.region
}
variable "region" {
description = "AWS region for dev environment"
type = string
default = "eu-west-1"
}
+207
View File
@@ -0,0 +1,207 @@
# ─── VPC ──────────────────────────────────────────────────────────────
resource "aws_vpc" "main" {
cidr_block = var.vpc_cidr
enable_dns_hostnames = true
enable_dns_support = true
tags = merge(var.tags, { Name = "${var.prefix}-vpc" })
}
resource "aws_internet_gateway" "main" {
vpc_id = aws_vpc.main.id
tags = merge(var.tags, { Name = "${var.prefix}-igw" })
}
# Public subnets (one per AZ) — for NAT gateways and load balancers
resource "aws_subnet" "public" {
count = length(var.availability_zones)
vpc_id = aws_vpc.main.id
cidr_block = cidrsubnet(var.vpc_cidr, 4, count.index)
availability_zone = var.availability_zones[count.index]
map_public_ip_on_launch = true
tags = merge(var.tags, {
Name = "${var.prefix}-public-${count.index + 1}"
"kubernetes.io/cluster/${var.prefix}-eks" = "shared"
"kubernetes.io/role/elb" = "1"
})
}
# Private subnets (one per AZ) — for EKS nodes
resource "aws_subnet" "private" {
count = length(var.availability_zones)
vpc_id = aws_vpc.main.id
cidr_block = cidrsubnet(var.vpc_cidr, 4, count.index + length(var.availability_zones))
availability_zone = var.availability_zones[count.index]
tags = merge(var.tags, {
Name = "${var.prefix}-private-${count.index + 1}"
"kubernetes.io/cluster/${var.prefix}-eks" = "shared"
"kubernetes.io/role/internal-elb" = "1"
})
}
# NAT Gateway (single, in first public subnet — use one per AZ for prod HA)
resource "aws_eip" "nat" {
domain = "vpc"
tags = merge(var.tags, { Name = "${var.prefix}-nat-eip" })
}
resource "aws_nat_gateway" "main" {
allocation_id = aws_eip.nat.id
subnet_id = aws_subnet.public[0].id
tags = merge(var.tags, { Name = "${var.prefix}-nat" })
depends_on = [aws_internet_gateway.main]
}
resource "aws_route_table" "public" {
vpc_id = aws_vpc.main.id
route {
cidr_block = "0.0.0.0/0"
gateway_id = aws_internet_gateway.main.id
}
tags = merge(var.tags, { Name = "${var.prefix}-public-rt" })
}
resource "aws_route_table_association" "public" {
count = length(var.availability_zones)
subnet_id = aws_subnet.public[count.index].id
route_table_id = aws_route_table.public.id
}
resource "aws_route_table" "private" {
vpc_id = aws_vpc.main.id
route {
cidr_block = "0.0.0.0/0"
nat_gateway_id = aws_nat_gateway.main.id
}
tags = merge(var.tags, { Name = "${var.prefix}-private-rt" })
}
resource "aws_route_table_association" "private" {
count = length(var.availability_zones)
subnet_id = aws_subnet.private[count.index].id
route_table_id = aws_route_table.private.id
}
# ─── EKS Cluster ──────────────────────────────────────────────────────
resource "aws_iam_role" "eks_cluster" {
name_prefix = "${var.prefix}-eks-cluster-"
assume_role_policy = jsonencode({
Version = "2012-10-17"
Statement = [{
Action = "sts:AssumeRole"
Effect = "Allow"
Principal = { Service = "eks.amazonaws.com" }
}]
})
tags = var.tags
}
resource "aws_iam_role_policy_attachment" "eks_cluster_policy" {
policy_arn = "arn:aws:iam::aws:policy/AmazonEKSClusterPolicy"
role = aws_iam_role.eks_cluster.name
}
resource "aws_eks_cluster" "main" {
name = "${var.prefix}-eks"
role_arn = aws_iam_role.eks_cluster.arn
version = var.kubernetes_version
vpc_config {
subnet_ids = concat(aws_subnet.private[*].id, aws_subnet.public[*].id)
endpoint_private_access = true
endpoint_public_access = true
}
# Enable OIDC issuer for IRSA (IAM Roles for Service Accounts)
access_config {
authentication_mode = "API_AND_CONFIG_MAP"
}
tags = var.tags
depends_on = [aws_iam_role_policy_attachment.eks_cluster_policy]
}
# OIDC provider — required for IRSA (IAM Roles for Service Accounts)
data "tls_certificate" "eks" {
url = aws_eks_cluster.main.identity[0].oidc[0].issuer
}
resource "aws_iam_openid_connect_provider" "eks" {
client_id_list = ["sts.amazonaws.com"]
thumbprint_list = [data.tls_certificate.eks.certificates[0].sha1_fingerprint]
url = aws_eks_cluster.main.identity[0].oidc[0].issuer
tags = var.tags
}
# EKS Node Group
resource "aws_iam_role" "eks_nodes" {
name_prefix = "${var.prefix}-eks-nodes-"
assume_role_policy = jsonencode({
Version = "2012-10-17"
Statement = [{
Action = "sts:AssumeRole"
Effect = "Allow"
Principal = { Service = "ec2.amazonaws.com" }
}]
})
tags = var.tags
}
resource "aws_iam_role_policy_attachment" "eks_worker_node_policy" {
policy_arn = "arn:aws:iam::aws:policy/AmazonEKSWorkerNodePolicy"
role = aws_iam_role.eks_nodes.name
}
resource "aws_iam_role_policy_attachment" "eks_cni_policy" {
policy_arn = "arn:aws:iam::aws:policy/AmazonEKS_CNI_Policy"
role = aws_iam_role.eks_nodes.name
}
resource "aws_iam_role_policy_attachment" "eks_ecr_readonly" {
policy_arn = "arn:aws:iam::aws:policy/AmazonEC2ContainerRegistryReadOnly"
role = aws_iam_role.eks_nodes.name
}
resource "aws_eks_node_group" "main" {
cluster_name = aws_eks_cluster.main.name
node_group_name = "${var.prefix}-nodes"
node_role_arn = aws_iam_role.eks_nodes.arn
subnet_ids = aws_subnet.private[*].id
instance_types = [var.node_instance_type]
scaling_config {
desired_size = var.node_count
max_size = var.node_max_count
min_size = var.node_min_count
}
update_config {
max_unavailable = 1
}
tags = var.tags
depends_on = [
aws_iam_role_policy_attachment.eks_worker_node_policy,
aws_iam_role_policy_attachment.eks_cni_policy,
aws_iam_role_policy_attachment.eks_ecr_readonly,
]
}
@@ -0,0 +1,26 @@
# ─── Cluster ─────────────────────────────────────────────────────────
output "cluster_name" {
description = "EKS cluster name"
value = aws_eks_cluster.main.name
}
output "aws_region" {
description = "AWS region"
value = var.region
}
output "oidc_issuer_url" {
description = "EKS OIDC issuer URL (for IRSA)"
value = aws_eks_cluster.main.identity[0].oidc[0].issuer
}
output "oidc_provider_arn" {
description = "IAM OIDC provider ARN (for IRSA trust policies)"
value = aws_iam_openid_connect_provider.eks.arn
}
output "vpc_id" {
description = "VPC ID"
value = aws_vpc.main.id
}
@@ -0,0 +1,12 @@
terraform {
required_providers {
aws = {
source = "hashicorp/aws"
version = "~> 5.0"
}
tls = {
source = "hashicorp/tls"
version = "~> 4.0"
}
}
}
@@ -0,0 +1,61 @@
# ─── Region ──────────────────────────────────────────────────────────
variable "region" {
description = "AWS region (e.g., eu-west-1, us-east-1)"
type = string
}
variable "prefix" {
description = "Prefix for resource names (e.g., clst-dev)"
type = string
}
# ─── Networking ───────────────────────────────────────────────────────
variable "vpc_cidr" {
description = "VPC CIDR block"
type = string
default = "10.100.0.0/16"
}
variable "availability_zones" {
description = "List of AZs for subnets (2–3 recommended)"
type = list(string)
}
# ─── EKS Cluster ─────────────────────────────────────────────────────
variable "node_instance_type" {
description = "EKS node instance type (e.g., t3.medium, m5.xlarge)"
type = string
}
variable "node_count" {
description = "Desired number of EKS worker nodes"
type = number
}
variable "node_min_count" {
description = "Minimum number of EKS worker nodes"
type = number
default = 1
}
variable "node_max_count" {
description = "Maximum number of EKS worker nodes"
type = number
}
variable "kubernetes_version" {
description = "Kubernetes version for EKS (e.g., \"1.30\")"
type = string
default = "1.30"
}
# ─── Tags ─────────────────────────────────────────────────────────────
variable "tags" {
description = "Tags applied to all resources"
type = map(string)
default = {}
}
+21
View File
@@ -0,0 +1,21 @@
module "cluster" {
source = "../modules/cluster"
region = var.region
prefix = "clst"
# VPC
availability_zones = ["${var.region}a", "${var.region}b", "${var.region}c"]
# EKS — general-purpose nodes for production
node_instance_type = "m5.xlarge"
node_count = 3
node_min_count = 3
node_max_count = 6
kubernetes_version = "1.30"
tags = {
Environment = "prod"
ManagedBy = "tofu"
}
}
+5
View File
@@ -0,0 +1,5 @@
output "cluster_name" { value = module.cluster.cluster_name }
output "aws_region" { value = module.cluster.aws_region }
output "oidc_issuer_url" { value = module.cluster.oidc_issuer_url }
output "oidc_provider_arn" { value = module.cluster.oidc_provider_arn }
output "vpc_id" { value = module.cluster.vpc_id }
+22
View File
@@ -0,0 +1,22 @@
terraform {
required_providers {
aws = {
source = "hashicorp/aws"
version = "~> 5.0"
}
tls = {
source = "hashicorp/tls"
version = "~> 4.0"
}
}
}
provider "aws" {
region = var.region
}
variable "region" {
description = "AWS region for prod environment"
type = string
default = "eu-west-1"
}
+339
View File
@@ -0,0 +1,339 @@
# =============================================================================
# AWS Workload Cluster
# =============================================================================
# A lean EKS cluster for running application workloads. No managed data
# services — those live on the platform cluster. ArgoCD (on the platform
# cluster) deploys apps to this cluster via the app-of-apps pattern.
#
# Platform components deployed by deploy-workload.sh:
# nginx-ingress, cert-manager, external-dns, external-secrets, alloy
#
# Usage:
# tofu init && tofu plan && tofu apply
# ./sync-tofu-outputs.sh --env aws-workload
# ./deploy-workload.sh --env aws-workload
# =============================================================================
variable "prefix" {
description = "Prefix for resource names (e.g., clst-workload)"
type = string
default = "clst-workload"
}
variable "availability_zones" {
description = "List of AZs for subnets"
type = list(string)
default = ["eu-west-1a", "eu-west-1b"]
}
variable "vpc_cidr" {
description = "VPC CIDR block"
type = string
default = "10.110.0.0/16"
}
variable "node_instance_type" {
description = "EKS node instance type"
type = string
default = "t3.medium"
}
variable "node_count" {
description = "Desired number of EKS worker nodes"
type = number
default = 2
}
variable "node_min_count" {
description = "Minimum number of EKS worker nodes"
type = number
default = 1
}
variable "node_max_count" {
description = "Maximum number of EKS worker nodes"
type = number
default = 4
}
variable "kubernetes_version" {
description = "Kubernetes version for EKS"
type = string
default = "1.30"
}
variable "domain" {
description = "Public domain name — must have an existing Route53 hosted zone"
type = string
}
variable "tags" {
description = "Tags applied to all resources"
type = map(string)
default = {
Environment = "workload"
ManagedBy = "tofu"
}
}
# ─── VPC ──────────────────────────────────────────────────────────────
resource "aws_vpc" "main" {
cidr_block = var.vpc_cidr
enable_dns_hostnames = true
enable_dns_support = true
tags = merge(var.tags, { Name = "${var.prefix}-vpc" })
}
resource "aws_internet_gateway" "main" {
vpc_id = aws_vpc.main.id
tags = merge(var.tags, { Name = "${var.prefix}-igw" })
}
resource "aws_subnet" "public" {
count = length(var.availability_zones)
vpc_id = aws_vpc.main.id
cidr_block = cidrsubnet(var.vpc_cidr, 4, count.index)
availability_zone = var.availability_zones[count.index]
map_public_ip_on_launch = true
tags = merge(var.tags, {
Name = "${var.prefix}-public-${count.index + 1}"
"kubernetes.io/cluster/${var.prefix}-eks" = "shared"
"kubernetes.io/role/elb" = "1"
})
}
resource "aws_subnet" "private" {
count = length(var.availability_zones)
vpc_id = aws_vpc.main.id
cidr_block = cidrsubnet(var.vpc_cidr, 4, count.index + length(var.availability_zones))
availability_zone = var.availability_zones[count.index]
tags = merge(var.tags, {
Name = "${var.prefix}-private-${count.index + 1}"
"kubernetes.io/cluster/${var.prefix}-eks" = "shared"
"kubernetes.io/role/internal-elb" = "1"
})
}
resource "aws_eip" "nat" {
domain = "vpc"
tags = merge(var.tags, { Name = "${var.prefix}-nat-eip" })
}
resource "aws_nat_gateway" "main" {
allocation_id = aws_eip.nat.id
subnet_id = aws_subnet.public[0].id
tags = merge(var.tags, { Name = "${var.prefix}-nat" })
depends_on = [aws_internet_gateway.main]
}
resource "aws_route_table" "public" {
vpc_id = aws_vpc.main.id
route {
cidr_block = "0.0.0.0/0"
gateway_id = aws_internet_gateway.main.id
}
tags = merge(var.tags, { Name = "${var.prefix}-public-rt" })
}
resource "aws_route_table_association" "public" {
count = length(var.availability_zones)
subnet_id = aws_subnet.public[count.index].id
route_table_id = aws_route_table.public.id
}
resource "aws_route_table" "private" {
vpc_id = aws_vpc.main.id
route {
cidr_block = "0.0.0.0/0"
nat_gateway_id = aws_nat_gateway.main.id
}
tags = merge(var.tags, { Name = "${var.prefix}-private-rt" })
}
resource "aws_route_table_association" "private" {
count = length(var.availability_zones)
subnet_id = aws_subnet.private[count.index].id
route_table_id = aws_route_table.private.id
}
# ─── EKS Cluster ──────────────────────────────────────────────────────
resource "aws_iam_role" "eks_cluster" {
name_prefix = "${var.prefix}-eks-cluster-"
assume_role_policy = jsonencode({
Version = "2012-10-17"
Statement = [{
Action = "sts:AssumeRole"
Effect = "Allow"
Principal = { Service = "eks.amazonaws.com" }
}]
})
tags = var.tags
}
resource "aws_iam_role_policy_attachment" "eks_cluster_policy" {
policy_arn = "arn:aws:iam::aws:policy/AmazonEKSClusterPolicy"
role = aws_iam_role.eks_cluster.name
}
resource "aws_eks_cluster" "main" {
name = "${var.prefix}-eks"
role_arn = aws_iam_role.eks_cluster.arn
version = var.kubernetes_version
vpc_config {
subnet_ids = concat(aws_subnet.private[*].id, aws_subnet.public[*].id)
endpoint_private_access = true
endpoint_public_access = true
}
access_config {
authentication_mode = "API_AND_CONFIG_MAP"
}
tags = var.tags
depends_on = [aws_iam_role_policy_attachment.eks_cluster_policy]
}
# OIDC provider — required for IRSA
data "tls_certificate" "eks" {
url = aws_eks_cluster.main.identity[0].oidc[0].issuer
}
resource "aws_iam_openid_connect_provider" "eks" {
client_id_list = ["sts.amazonaws.com"]
thumbprint_list = [data.tls_certificate.eks.certificates[0].sha1_fingerprint]
url = aws_eks_cluster.main.identity[0].oidc[0].issuer
tags = var.tags
}
resource "aws_iam_role" "eks_nodes" {
name_prefix = "${var.prefix}-eks-nodes-"
assume_role_policy = jsonencode({
Version = "2012-10-17"
Statement = [{
Action = "sts:AssumeRole"
Effect = "Allow"
Principal = { Service = "ec2.amazonaws.com" }
}]
})
tags = var.tags
}
resource "aws_iam_role_policy_attachment" "eks_worker_node_policy" {
policy_arn = "arn:aws:iam::aws:policy/AmazonEKSWorkerNodePolicy"
role = aws_iam_role.eks_nodes.name
}
resource "aws_iam_role_policy_attachment" "eks_cni_policy" {
policy_arn = "arn:aws:iam::aws:policy/AmazonEKS_CNI_Policy"
role = aws_iam_role.eks_nodes.name
}
resource "aws_iam_role_policy_attachment" "eks_ecr_readonly" {
policy_arn = "arn:aws:iam::aws:policy/AmazonEC2ContainerRegistryReadOnly"
role = aws_iam_role.eks_nodes.name
}
resource "aws_eks_node_group" "main" {
cluster_name = aws_eks_cluster.main.name
node_group_name = "${var.prefix}-nodes"
node_role_arn = aws_iam_role.eks_nodes.arn
subnet_ids = aws_subnet.private[*].id
instance_types = [var.node_instance_type]
scaling_config {
desired_size = var.node_count
max_size = var.node_max_count
min_size = var.node_min_count
}
update_config {
max_unavailable = 1
}
tags = var.tags
depends_on = [
aws_iam_role_policy_attachment.eks_worker_node_policy,
aws_iam_role_policy_attachment.eks_cni_policy,
aws_iam_role_policy_attachment.eks_ecr_readonly,
]
}
# ─── External-DNS IRSA ───────────────────────────────────────────────
# Allows external-dns to manage Route53 records for app ingresses.
data "aws_route53_zone" "main" {
name = var.domain
private_zone = false
}
data "aws_iam_policy_document" "external_dns_assume_role" {
statement {
effect = "Allow"
principals {
type = "Federated"
identifiers = [aws_iam_openid_connect_provider.eks.arn]
}
actions = ["sts:AssumeRoleWithWebIdentity"]
condition {
test = "StringEquals"
variable = "${replace(aws_iam_openid_connect_provider.eks.url, "https://", "")}:sub"
values = ["system:serviceaccount:external-dns:external-dns"]
}
condition {
test = "StringEquals"
variable = "${replace(aws_iam_openid_connect_provider.eks.url, "https://", "")}:aud"
values = ["sts.amazonaws.com"]
}
}
}
resource "aws_iam_role" "external_dns_irsa" {
name_prefix = "${var.prefix}-external-dns-irsa-"
assume_role_policy = data.aws_iam_policy_document.external_dns_assume_role.json
tags = var.tags
}
data "aws_iam_policy_document" "external_dns_route53" {
statement {
effect = "Allow"
actions = ["route53:ChangeResourceRecordSets"]
resources = ["arn:aws:route53:::hostedzone/${data.aws_route53_zone.main.zone_id}"]
}
statement {
effect = "Allow"
actions = ["route53:ListHostedZones", "route53:ListResourceRecordSets", "route53:ListTagsForResource"]
resources = ["*"]
}
}
resource "aws_iam_role_policy" "external_dns_route53" {
name_prefix = "${var.prefix}-external-dns-route53-"
role = aws_iam_role.external_dns_irsa.id
policy = data.aws_iam_policy_document.external_dns_route53.json
}
+3
View File
@@ -0,0 +1,3 @@
output "cluster_name" { value = aws_eks_cluster.main.name }
output "aws_region" { value = var.region }
output "external_dns_irsa_role_arn" { value = aws_iam_role.external_dns_irsa.arn }
+24
View File
@@ -0,0 +1,24 @@
terraform {
required_providers {
aws = {
source = "hashicorp/aws"
version = "~> 5.0"
}
tls = {
source = "hashicorp/tls"
version = "~> 4.0"
}
}
}
# Authentication: set AWS_ACCESS_KEY_ID, AWS_SECRET_ACCESS_KEY, AWS_SESSION_TOKEN
# or configure an AWS profile: export AWS_PROFILE=clst
provider "aws" {
region = var.region
}
variable "region" {
description = "AWS region for the workload environment"
type = string
default = "eu-west-1"
}
+17
View File
@@ -0,0 +1,17 @@
module "cluster" {
source = "../modules/cluster"
project_id = var.project_id
region = var.region
prefix = "clst-dev"
# GKE — small dev nodes
node_machine_type = "e2-standard-2"
node_count = 2
deletion_protection = false
labels = {
environment = "dev"
managed-by = "tofu"
}
}
+3
View File
@@ -0,0 +1,3 @@
output "cluster_name" { value = module.cluster.cluster_name }
output "project_id" { value = module.cluster.project_id }
output "region" { value = module.cluster.region }
+26
View File
@@ -0,0 +1,26 @@
terraform {
required_providers {
google = {
source = "hashicorp/google"
version = "~> 6.0"
}
}
}
# Authentication: use Application Default Credentials (gcloud auth application-default login)
# or set GOOGLE_APPLICATION_CREDENTIALS to a service account key file.
provider "google" {
project = var.project_id
region = var.region
}
variable "project_id" {
description = "GCP project ID for the dev environment"
type = string
}
variable "region" {
description = "GCP region"
type = string
default = "europe-west4"
}
+115
View File
@@ -0,0 +1,115 @@
# ─── Required APIs ────────────────────────────────────────────────────
resource "google_project_service" "compute" {
project = var.project_id
service = "compute.googleapis.com"
disable_on_destroy = false
}
resource "google_project_service" "container" {
project = var.project_id
service = "container.googleapis.com"
disable_on_destroy = false
}
# ─── Networking ───────────────────────────────────────────────────────
resource "google_compute_network" "main" {
project = var.project_id
name = "${var.prefix}-vpc"
auto_create_subnetworks = false
depends_on = [google_project_service.compute]
}
resource "google_compute_subnetwork" "main" {
project = var.project_id
name = "${var.prefix}-subnet"
ip_cidr_range = "10.100.0.0/22"
region = var.region
network = google_compute_network.main.id
# Secondary ranges required for GKE VPC-native cluster
secondary_ip_range {
range_name = "pods"
ip_cidr_range = "10.200.0.0/14" # /14 = ~262k pod IPs
}
secondary_ip_range {
range_name = "services"
ip_cidr_range = "10.204.0.0/20" # /20 = ~4k service IPs
}
}
# ─── GKE Cluster ──────────────────────────────────────────────────────
#
# Regional cluster (3 control-plane replicas) for HA.
# Workload Identity enabled — allows K8s service accounts to impersonate
# Google Service Accounts for keyless access to GCP services.
resource "google_container_cluster" "main" {
project = var.project_id
name = "${var.prefix}-gke"
location = var.region # regional cluster
network = google_compute_network.main.id
subnetwork = google_compute_subnetwork.main.id
# VPC-native cluster with alias IP ranges
ip_allocation_policy {
cluster_secondary_range_name = "pods"
services_secondary_range_name = "services"
}
# Workload Identity pool — enables OIDC token projection for pods
workload_identity_config {
workload_pool = "${var.project_id}.svc.id.goog"
}
# Remove default node pool — we manage our own below
remove_default_node_pool = true
initial_node_count = 1
deletion_protection = var.deletion_protection
dynamic "release_channel" {
for_each = var.kubernetes_version == null ? [1] : []
content {
channel = "STABLE"
}
}
resource_labels = var.labels
depends_on = [google_project_service.container]
}
resource "google_container_node_pool" "main" {
project = var.project_id
name = "${var.prefix}-nodes"
location = var.region
cluster = google_container_cluster.main.name
node_count = var.node_count
node_config {
machine_type = var.node_machine_type
# GKE_METADATA mode is required for Workload Identity
workload_metadata_config {
mode = "GKE_METADATA"
}
oauth_scopes = [
"https://www.googleapis.com/auth/cloud-platform",
]
labels = merge(var.labels, {
role = "worker"
})
}
management {
auto_repair = true
auto_upgrade = true
}
}
@@ -0,0 +1,16 @@
# ─── Cluster ─────────────────────────────────────────────────────────
output "cluster_name" {
description = "GKE cluster name"
value = google_container_cluster.main.name
}
output "project_id" {
description = "GCP project ID"
value = var.project_id
}
output "region" {
description = "GCP region"
value = var.region
}
@@ -0,0 +1,8 @@
terraform {
required_providers {
google = {
source = "hashicorp/google"
version = "~> 6.0"
}
}
}
@@ -0,0 +1,48 @@
# ─── Project / Region ────────────────────────────────────────────────
variable "project_id" {
description = "GCP project ID"
type = string
}
variable "region" {
description = "GCP region (e.g., europe-west4, europe-west1)"
type = string
}
variable "prefix" {
description = "Prefix for resource names (e.g., clst-dev)"
type = string
}
# ─── GKE Cluster ─────────────────────────────────────────────────────
variable "node_machine_type" {
description = "GKE node machine type (e.g., e2-standard-2, e2-standard-4)"
type = string
}
variable "node_count" {
description = "Number of nodes per zone (regional cluster spawns nodes in each zone)"
type = number
}
variable "kubernetes_version" {
description = "GKE Kubernetes version channel (null = STABLE release channel)"
type = string
default = null
}
variable "deletion_protection" {
description = "Prevent cluster deletion (set true for production)"
type = bool
default = false
}
# ─── Labels ──────────────────────────────────────────────────────────
variable "labels" {
description = "Labels applied to all resources"
type = map(string)
default = {}
}
+17
View File
@@ -0,0 +1,17 @@
module "cluster" {
source = "../modules/cluster"
project_id = var.project_id
region = var.region
prefix = "clst"
# GKE — general-purpose nodes for production
node_machine_type = "e2-standard-4"
node_count = 3
deletion_protection = true
labels = {
environment = "prod"
managed-by = "tofu"
}
}
+3
View File
@@ -0,0 +1,3 @@
output "cluster_name" { value = module.cluster.cluster_name }
output "project_id" { value = module.cluster.project_id }
output "region" { value = module.cluster.region }
+24
View File
@@ -0,0 +1,24 @@
terraform {
required_providers {
google = {
source = "hashicorp/google"
version = "~> 6.0"
}
}
}
provider "google" {
project = var.project_id
region = var.region
}
variable "project_id" {
description = "GCP project ID for the prod environment"
type = string
}
variable "region" {
description = "GCP region"
type = string
default = "europe-west1"
}
+194
View File
@@ -0,0 +1,194 @@
# =============================================================================
# GCP Workload Cluster
# =============================================================================
# A lean GKE cluster for running application workloads. No managed data
# services — those live on the platform cluster. ArgoCD (on the platform
# cluster) deploys apps to this cluster via the app-of-apps pattern.
#
# Platform components deployed by deploy-workload.sh:
# nginx-ingress, cert-manager, external-dns, external-secrets, alloy
#
# Usage:
# tofu init && tofu plan && tofu apply
# ./sync-tofu-outputs.sh --env gcp-workload
# ./deploy-workload.sh --env gcp-workload
# =============================================================================
variable "prefix" {
description = "Prefix for resource names (e.g., clst-workload)"
type = string
default = "clst-workload"
}
variable "node_machine_type" {
description = "GKE node machine type"
type = string
default = "e2-standard-2"
}
variable "node_count" {
description = "Number of nodes per zone"
type = number
default = 1
}
variable "kubernetes_version" {
description = "GKE Kubernetes version (null = STABLE release channel)"
type = string
default = null
}
variable "deletion_protection" {
description = "Prevent cluster deletion"
type = bool
default = false
}
variable "labels" {
description = "Labels applied to all resources"
type = map(string)
default = {
environment = "workload"
managed-by = "tofu"
}
}
# ─── Required APIs ────────────────────────────────────────────────────
resource "google_project_service" "compute" {
project = var.project_id
service = "compute.googleapis.com"
disable_on_destroy = false
}
resource "google_project_service" "container" {
project = var.project_id
service = "container.googleapis.com"
disable_on_destroy = false
}
resource "google_project_service" "iam" {
project = var.project_id
service = "iam.googleapis.com"
disable_on_destroy = false
}
resource "google_project_service" "dns" {
project = var.project_id
service = "dns.googleapis.com"
disable_on_destroy = false
}
# ─── Networking ───────────────────────────────────────────────────────
resource "google_compute_network" "main" {
project = var.project_id
name = "${var.prefix}-vpc"
auto_create_subnetworks = false
depends_on = [google_project_service.compute]
}
resource "google_compute_subnetwork" "main" {
project = var.project_id
name = "${var.prefix}-subnet"
ip_cidr_range = "10.110.0.0/22"
region = var.region
network = google_compute_network.main.id
secondary_ip_range {
range_name = "pods"
ip_cidr_range = "10.210.0.0/14"
}
secondary_ip_range {
range_name = "services"
ip_cidr_range = "10.214.0.0/20"
}
}
# ─── GKE Cluster ──────────────────────────────────────────────────────
resource "google_container_cluster" "main" {
project = var.project_id
name = "${var.prefix}-gke"
location = var.region
network = google_compute_network.main.id
subnetwork = google_compute_subnetwork.main.id
ip_allocation_policy {
cluster_secondary_range_name = "pods"
services_secondary_range_name = "services"
}
workload_identity_config {
workload_pool = "${var.project_id}.svc.id.goog"
}
remove_default_node_pool = true
initial_node_count = 1
deletion_protection = var.deletion_protection
dynamic "release_channel" {
for_each = var.kubernetes_version == null ? [1] : []
content {
channel = "STABLE"
}
}
resource_labels = var.labels
depends_on = [google_project_service.container]
}
resource "google_container_node_pool" "main" {
project = var.project_id
name = "${var.prefix}-nodes"
location = var.region
cluster = google_container_cluster.main.name
node_count = var.node_count
node_config {
machine_type = var.node_machine_type
workload_metadata_config {
mode = "GKE_METADATA"
}
oauth_scopes = [
"https://www.googleapis.com/auth/cloud-platform",
]
labels = merge(var.labels, { role = "worker" })
}
management {
auto_repair = true
auto_upgrade = true
}
}
# ─── External-DNS Workload Identity ──────────────────────────────────
# Allows external-dns to manage Cloud DNS records for app ingresses.
resource "google_service_account" "external_dns" {
project = var.project_id
account_id = "${var.prefix}-external-dns"
display_name = "External-DNS Service Account (Workload Identity)"
depends_on = [google_project_service.iam]
}
resource "google_project_iam_member" "external_dns_dns_admin" {
project = var.project_id
role = "roles/dns.admin"
member = "serviceAccount:${google_service_account.external_dns.email}"
}
resource "google_service_account_iam_member" "external_dns_workload_identity" {
service_account_id = google_service_account.external_dns.name
role = "roles/iam.workloadIdentityUser"
member = "serviceAccount:${var.project_id}.svc.id.goog[external-dns/external-dns]"
}
+4
View File
@@ -0,0 +1,4 @@
output "cluster_name" { value = google_container_cluster.main.name }
output "project_id" { value = var.project_id }
output "region" { value = var.region }
output "external_dns_gsa_email" { value = google_service_account.external_dns.email }
+26
View File
@@ -0,0 +1,26 @@
terraform {
required_providers {
google = {
source = "hashicorp/google"
version = "~> 6.0"
}
}
}
# Authentication: use Application Default Credentials (gcloud auth application-default login)
# or set GOOGLE_APPLICATION_CREDENTIALS to a service account key file.
provider "google" {
project = var.project_id
region = var.region
}
variable "project_id" {
description = "GCP project ID for the workload environment"
type = string
}
variable "region" {
description = "GCP region"
type = string
default = "europe-west4"
}
+14
View File
@@ -0,0 +1,14 @@
module "cluster" {
source = "../modules/cluster"
prefix = "clst-dev"
zone = "no-svg1"
node_plan = "DEV-1xCPU-2GB"
node_count = 2
network_cidr = "10.100.0.0/24"
tags = {
Environment = "dev"
ManagedBy = "tofu"
}
}
+13
View File
@@ -0,0 +1,13 @@
# ─── Cluster ─────────────────────────────────────────────────────────
output "cluster_id" {
value = module.cluster.cluster_id
}
output "cluster_name" {
value = module.cluster.cluster_name
}
output "zone" {
value = module.cluster.zone
}
+14
View File
@@ -0,0 +1,14 @@
terraform {
required_version = ">= 1.0"
required_providers {
upcloud = {
source = "UpCloudLtd/upcloud"
version = "~> 5.0"
}
}
}
provider "upcloud" {
# Set via environment variables: UPCLOUD_USERNAME, UPCLOUD_PASSWORD
}
@@ -0,0 +1,64 @@
# Router for the private network
resource "upcloud_router" "kubernetes" {
name = "${var.prefix}-${var.cluster_name}-router"
}
# Gateway for internet connectivity
resource "upcloud_gateway" "kubernetes" {
name = "${var.prefix}-${var.cluster_name}-gateway"
zone = var.zone
features = ["nat"]
router {
id = upcloud_router.kubernetes.id
}
}
# Private network for the Kubernetes cluster
resource "upcloud_network" "kubernetes" {
name = "${var.prefix}-${var.cluster_name}-network"
zone = var.zone
router = upcloud_router.kubernetes.id
ip_network {
address = var.network_cidr
dhcp = true
dhcp_default_route = true
family = "IPv4"
gateway = cidrhost(var.network_cidr, 1)
}
depends_on = [upcloud_gateway.kubernetes]
}
# Kubernetes cluster
resource "upcloud_kubernetes_cluster" "main" {
name = "${var.prefix}-${var.cluster_name}"
zone = var.zone
network = upcloud_network.kubernetes.id
control_plane_ip_filter = var.control_plane_ip_filter
private_node_groups = true
}
# Node group for worker nodes
resource "upcloud_kubernetes_node_group" "workers" {
cluster = upcloud_kubernetes_cluster.main.id
name = "${var.prefix}-${var.cluster_name}-workers"
node_count = var.node_count
plan = var.node_plan
anti_affinity = var.node_count > 1
dynamic "cloud_native_plan" {
for_each = var.storage_size != null ? [1] : []
content {
storage_size = var.storage_size
}
}
labels = {
prefix = var.prefix
cluster = var.cluster_name
role = "worker"
env = lookup(var.tags, "Environment", "dev")
}
}
@@ -0,0 +1,31 @@
# ─── Cluster ─────────────────────────────────────────────────────────
output "cluster_id" {
description = "The ID of the Kubernetes cluster"
value = upcloud_kubernetes_cluster.main.id
}
output "cluster_name" {
description = "The name of the Kubernetes cluster"
value = upcloud_kubernetes_cluster.main.name
}
output "network_id" {
description = "The ID of the private network"
value = upcloud_network.kubernetes.id
}
output "network_cidr" {
description = "The CIDR block of the private network"
value = var.network_cidr
}
output "kubernetes_version" {
description = "The Kubernetes version of the cluster"
value = upcloud_kubernetes_cluster.main.version
}
output "zone" {
description = "The zone where the cluster is deployed"
value = var.zone
}
@@ -0,0 +1,8 @@
terraform {
required_providers {
upcloud = {
source = "UpCloudLtd/upcloud"
version = "~> 5.0"
}
}
}
@@ -0,0 +1,50 @@
# ─── Cluster ─────────────────────────────────────────────────────────
variable "prefix" {
description = "Prefix for resource names"
type = string
}
variable "cluster_name" {
description = "Name of the Kubernetes cluster"
type = string
default = "main"
}
variable "zone" {
description = "UpCloud zone"
type = string
}
variable "node_plan" {
description = "UpCloud server plan for worker nodes"
type = string
}
variable "node_count" {
description = "Number of worker nodes"
type = number
}
variable "network_cidr" {
description = "CIDR block for the private network"
type = string
default = "10.100.0.0/24"
}
variable "control_plane_ip_filter" {
description = "CIDRs allowed to access the K8s API"
type = list(string)
default = ["0.0.0.0/0"]
}
variable "storage_size" {
description = "Storage size in GB for worker nodes (overrides plan default via cloud_native_plan block)"
type = number
default = null
}
variable "tags" {
description = "Labels to apply to resources"
type = map(string)
}
+120
View File
@@ -0,0 +1,120 @@
# =============================================================================
# UpCloud Workload Cluster
# =============================================================================
# A lean UCS cluster for running application workloads. No managed data
# services — those live on the platform cluster. ArgoCD (on the platform
# cluster) deploys apps to this cluster via the app-of-apps pattern.
#
# Platform components deployed by deploy-workload.sh:
# nginx-ingress, cert-manager, external-dns, external-secrets, alloy
#
# Usage:
# tofu init && tofu plan && tofu apply
# ./sync-tofu-outputs.sh --env upcloud-workload
# ./deploy-workload.sh --env upcloud-workload
# =============================================================================
variable "prefix" {
description = "Prefix for resource names"
type = string
default = "clst-workload"
}
variable "zone" {
description = "UpCloud zone"
type = string
default = "no-svg1"
}
variable "node_plan" {
description = "UpCloud server plan for worker nodes"
type = string
default = "2xCPU-4GB"
}
variable "node_count" {
description = "Number of worker nodes"
type = number
default = 2
}
variable "network_cidr" {
description = "CIDR block for the private network"
type = string
default = "10.110.0.0/24"
}
variable "control_plane_ip_filter" {
description = "CIDRs allowed to access the K8s API"
type = list(string)
default = ["0.0.0.0/0"]
}
variable "tags" {
description = "Labels to apply to resources"
type = map(string)
default = {
Environment = "workload"
ManagedBy = "tofu"
}
}
module "cluster" {
source = "../modules/cluster"
prefix = "clst-prod"
zone = "no-svg1"
node_plan = "CLOUDNATIVE-4xCPU-8GB"
node_count = 4
storage_size = 30
network_cidr = "10.100.0.0/24"
control_plane_ip_filter = ["0.0.0.0/0"] # TODO: restrict to known CIDRs
tags = {
Environment = "prod"
ManagedBy = "tofu"
}
}
# ─── Networking ───────────────────────────────────────────────────────
resource "upcloud_router" "kubernetes" {
name = "${var.prefix}-workload-router"
}
resource "upcloud_gateway" "kubernetes" {
name = "${var.prefix}-workload-gateway"
zone = var.zone
features = ["nat"]
router {
id = upcloud_router.kubernetes.id
}
}
resource "upcloud_network" "kubernetes" {
name = "${var.prefix}-workload-network"
zone = var.zone
router = upcloud_router.kubernetes.id
ip_network {
address = var.network_cidr
dhcp = true
dhcp_default_route = true
family = "IPv4"
gateway = cidrhost(var.network_cidr, 1)
}
depends_on = [upcloud_gateway.kubernetes]
}
# ─── Kubernetes Cluster ───────────────────────────────────────────────
resource "upcloud_kubernetes_cluster" "main-prod" {
name = "${var.prefix}-workload"
zone = var.zone
network = upcloud_network.kubernetes.id
control_plane_ip_filter = var.control_plane_ip_filter
private_node_groups = true
}
+13
View File
@@ -0,0 +1,13 @@
# ─── Cluster ─────────────────────────────────────────────────────────
output "cluster_id" {
value = module.cluster.cluster_id
}
output "cluster_name" {
value = module.cluster.cluster_name
}
output "zone" {
value = module.cluster.zone
}
+14
View File
@@ -0,0 +1,14 @@
terraform {
required_version = ">= 1.0"
required_providers {
upcloud = {
source = "UpCloudLtd/upcloud"
version = "~> 5.0"
}
}
}
provider "upcloud" {
# Set via environment variables: UPCLOUD_USERNAME, UPCLOUD_PASSWORD
}
+116
View File
@@ -0,0 +1,116 @@
# =============================================================================
# UpCloud Workload Cluster
# =============================================================================
# A lean UCS cluster for running application workloads. No managed data
# services — those live on the platform cluster. ArgoCD (on the platform
# cluster) deploys apps to this cluster via the app-of-apps pattern.
#
# Platform components deployed by deploy-workload.sh:
# nginx-ingress, cert-manager, external-dns, external-secrets, alloy
#
# Usage:
# tofu init && tofu plan && tofu apply
# ./sync-tofu-outputs.sh --env upcloud-workload
# ./deploy-workload.sh --env upcloud-workload
# =============================================================================
variable "prefix" {
description = "Prefix for resource names"
type = string
default = "clst-workload"
}
variable "zone" {
description = "UpCloud zone"
type = string
default = "no-svg1"
}
variable "node_plan" {
description = "UpCloud server plan for worker nodes"
type = string
default = "2xCPU-4GB"
}
variable "node_count" {
description = "Number of worker nodes"
type = number
default = 2
}
variable "network_cidr" {
description = "CIDR block for the private network"
type = string
default = "10.110.0.0/24"
}
variable "control_plane_ip_filter" {
description = "CIDRs allowed to access the K8s API"
type = list(string)
default = ["0.0.0.0/0"]
}
variable "tags" {
description = "Labels to apply to resources"
type = map(string)
default = {
Environment = "workload"
ManagedBy = "tofu"
}
}
# ─── Networking ───────────────────────────────────────────────────────
resource "upcloud_router" "kubernetes" {
name = "${var.prefix}-workload-router"
}
resource "upcloud_gateway" "kubernetes" {
name = "${var.prefix}-workload-gateway"
zone = var.zone
features = ["nat"]
router {
id = upcloud_router.kubernetes.id
}
}
resource "upcloud_network" "kubernetes" {
name = "${var.prefix}-workload-network"
zone = var.zone
router = upcloud_router.kubernetes.id
ip_network {
address = var.network_cidr
dhcp = true
dhcp_default_route = true
family = "IPv4"
gateway = cidrhost(var.network_cidr, 1)
}
depends_on = [upcloud_gateway.kubernetes]
}
# ─── Kubernetes Cluster ───────────────────────────────────────────────
resource "upcloud_kubernetes_cluster" "main" {
name = "${var.prefix}-workload"
zone = var.zone
network = upcloud_network.kubernetes.id
control_plane_ip_filter = var.control_plane_ip_filter
private_node_groups = true
}
resource "upcloud_kubernetes_node_group" "workers" {
cluster = upcloud_kubernetes_cluster.main.id
name = "${var.prefix}-workload-workers"
node_count = var.node_count
plan = var.node_plan
anti_affinity = var.node_count > 1
labels = {
prefix = var.prefix
cluster = "workload"
role = "worker"
env = lookup(var.tags, "Environment", "workload")
}
}
+3
View File
@@ -0,0 +1,3 @@
output "cluster_name" { value = upcloud_kubernetes_cluster.main.name }
output "cluster_id" { value = upcloud_kubernetes_cluster.main.id }
output "zone" { value = var.zone }
+14
View File
@@ -0,0 +1,14 @@
terraform {
required_version = ">= 1.0"
required_providers {
upcloud = {
source = "UpCloudLtd/upcloud"
version = "~> 5.0"
}
}
}
provider "upcloud" {
# Set via environment variables: UPCLOUD_USERNAME, UPCLOUD_PASSWORD
}
+66
View File
@@ -0,0 +1,66 @@
#!/bin/bash
set -euo pipefail
SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
TOFU_ROOT="$(dirname "$SCRIPT_DIR")"
PROJECT_ROOT="$(dirname "$TOFU_ROOT")"
CLUSTER="${1:?Usage: $0 <cluster> (e.g., aks-dev, eks-prod)}"
PLATFORM="${CLUSTER%%-*}"
ENV="${CLUSTER#*-}"
KUBECONFIG_FILE="$PROJECT_ROOT/private/$CLUSTER/kubeconfig"
if [[ -f "$KUBECONFIG_FILE" ]]; then
echo "Kubeconfig already exists: $KUBECONFIG_FILE"
echo ""
echo " export KUBECONFIG=$KUBECONFIG_FILE"
else
echo "No cached kubeconfig. Fetching from platform..."
# Load platform credentials
ENV_FILE="$TOFU_ROOT/configs/$PLATFORM.env"
if [[ -f "$ENV_FILE" ]]; then
set -a; source "$ENV_FILE"; set +a
fi
TOFU_DIR="$TOFU_ROOT/platforms/$PLATFORM/$ENV"
mkdir -p "$(dirname "$KUBECONFIG_FILE")"
case "$PLATFORM" in
aks)
cd "$TOFU_DIR"
RG=$(tofu output -raw resource_group_name 2>/dev/null || echo "$CLUSTER-rg")
NAME=$(tofu output -raw cluster_name 2>/dev/null || echo "$CLUSTER")
az aks get-credentials --resource-group "$RG" --name "$NAME" --file "$KUBECONFIG_FILE" --overwrite-existing
;;
eks)
cd "$TOFU_DIR"
NAME=$(tofu output -raw cluster_name 2>/dev/null || echo "$CLUSTER")
REGION=$(tofu output -raw aws_region 2>/dev/null || echo "${AWS_REGION:-eu-west-1}")
aws eks update-kubeconfig --name "$NAME" --region "$REGION" --kubeconfig "$KUBECONFIG_FILE"
;;
gke)
cd "$TOFU_DIR"
NAME=$(tofu output -raw cluster_name 2>/dev/null || echo "$CLUSTER")
REGION=$(tofu output -raw region 2>/dev/null || echo "${GCP_REGION:-europe-west4}")
PROJECT=$(tofu output -raw project_id 2>/dev/null || echo "${GCP_PROJECT_ID:-}")
gcloud container clusters get-credentials "$NAME" --region "$REGION" --project "$PROJECT"
cp ~/.kube/config "$KUBECONFIG_FILE"
;;
upc)
cd "$TOFU_DIR"
CLUSTER_ID=$(tofu output -raw cluster_id 2>/dev/null || echo "${UPCLOUD_CLUSTER_ID:-}")
upctl kubernetes config "$CLUSTER_ID" > "$KUBECONFIG_FILE"
;;
*)
echo "Error: unknown platform '$PLATFORM'"
exit 1
;;
esac
chmod 600 "$KUBECONFIG_FILE"
echo "Kubeconfig saved: $KUBECONFIG_FILE"
echo ""
echo " export KUBECONFIG=$KUBECONFIG_FILE"
fi
+246
View File
@@ -0,0 +1,246 @@
#!/bin/bash
set -euo pipefail
SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
TOFU_ROOT="$(dirname "$SCRIPT_DIR")"
PROJECT_ROOT="$(dirname "$TOFU_ROOT")"
# ─── Usage ────────────────────────────────────────────────────────────
usage() {
cat <<EOF
Usage: $0 <cluster> [options]
Provision a Kubernetes cluster using OpenTofu.
Mirrors bootstrap.sh convention: cluster = <platform>-<env>
Clusters: aks-dev | aks-prod | eks-dev | eks-prod
gke-dev | gke-prod | upc-dev | upc-prod
<platform>-workload (for workload clusters)
Options:
--plan Plan only, don't apply
--destroy Destroy the cluster (use teardown-cluster.sh instead)
--auto Skip confirmation prompts
-h, --help Show this help
Examples:
$0 aks-dev
$0 eks-prod --plan
$0 upc-dev --auto
Prerequisites:
- tofu, kubectl, helm installed
- Platform credentials in .tofu/configs/<platform>.env
- Cluster config in clusters/<cluster>.yaml
After provisioning, run:
./bootstrap.sh <cluster>
EOF
exit "${1:-0}"
}
# ─── Parse arguments ──────────────────────────────────────────────────
CLUSTER=""
PLAN_ONLY=false
DESTROY=false
AUTO_APPROVE=false
while [[ $# -gt 0 ]]; do
case "$1" in
--plan) PLAN_ONLY=true; shift ;;
--destroy) DESTROY=true; shift ;;
--auto) AUTO_APPROVE=true; shift ;;
-h|--help) usage 0 ;;
-*) echo "Unknown option: $1"; usage 1 ;;
*)
if [[ -z "$CLUSTER" ]]; then
CLUSTER="$1"
else
echo "Error: unexpected argument '$1'"
usage 1
fi
shift
;;
esac
done
[[ -z "$CLUSTER" ]] && { echo "Error: <cluster> argument required"; usage 1; }
# ─── Map cluster → platform + env ────────────────────────────────────
PLATFORM="${CLUSTER%%-*}" # aks-dev → aks
ENV="${CLUSTER#*-}" # aks-dev → dev
case "$PLATFORM" in
aks|eks|gke|upc) ;;
*) echo "Error: unknown platform '$PLATFORM'. Expected: aks, eks, gke, upc"; exit 1 ;;
esac
TOFU_DIR="$TOFU_ROOT/platforms/$PLATFORM/$ENV"
if [[ ! -d "$TOFU_DIR" ]]; then
echo "Error: tofu directory not found: $TOFU_DIR"
echo "Available environments for $PLATFORM:"
ls -1 "$TOFU_ROOT/platforms/$PLATFORM/" 2>/dev/null | grep -v modules || echo " (none)"
exit 1
fi
echo "========================================="
echo " Kubernetes Cluster Setup"
echo "========================================="
echo ""
echo " Cluster: $CLUSTER"
echo " Platform: $PLATFORM"
echo " Env: $ENV"
echo " Tofu dir: $TOFU_DIR"
echo ""
# ─── Prerequisites ────────────────────────────────────────────────────
echo "=== Checking Prerequisites ==="
command -v tofu >/dev/null 2>&1 || { echo "Error: tofu is not installed."; exit 1; }
command -v kubectl >/dev/null 2>&1 || { echo "Error: kubectl is not installed."; exit 1; }
command -v helm >/dev/null 2>&1 || { echo "Error: helm is not installed."; exit 1; }
echo " tofu, kubectl, helm: OK"
# ─── Load platform credentials ────────────────────────────────────────
ENV_FILE="$TOFU_ROOT/configs/$PLATFORM.env"
if [[ -f "$ENV_FILE" ]]; then
echo " Loading credentials from configs/$PLATFORM.env"
set -a
# shellcheck disable=SC1090
source "$ENV_FILE"
set +a
else
echo " Warning: $ENV_FILE not found — using existing environment/CLI auth"
echo " Copy configs/$PLATFORM.env.example → configs/$PLATFORM.env to configure"
fi
# ─── Load cluster config (if exists) ──────────────────────────────────
CLUSTER_CONFIG="$PROJECT_ROOT/clusters/$CLUSTER.yaml"
if [[ -f "$CLUSTER_CONFIG" ]]; then
echo " Loading cluster config from clusters/$CLUSTER.yaml"
if command -v yq >/dev/null 2>&1; then
eval "$(yq -r 'to_entries[] | "export CLUSTER_\(.key)=\"\(.value)\""' "$CLUSTER_CONFIG")"
echo " Cluster name: ${CLUSTER_clusterName:-$CLUSTER}"
else
echo " Warning: yq not installed — cluster config not loaded"
fi
else
echo " Warning: $CLUSTER_CONFIG not found — using defaults"
fi
echo ""
# ─── Run OpenTofu ─────────────────────────────────────────────────────
cd "$TOFU_DIR"
echo "=== Initializing OpenTofu ==="
tofu init
echo ""
if $DESTROY; then
echo "=== Planning Destruction ==="
tofu plan -destroy -out=tfplan
if ! $AUTO_APPROVE; then
echo ""
read -rp "DESTROY cluster $CLUSTER? This is irreversible. (yes/no) " REPLY
[[ "$REPLY" == "yes" ]] || { echo "Cancelled."; exit 1; }
fi
echo "Destroying infrastructure..."
tofu apply tfplan
echo ""
echo "=== Cluster $CLUSTER Destroyed ==="
elif $PLAN_ONLY; then
echo "=== Planning Infrastructure ==="
tofu plan
echo ""
echo "=== Plan complete (--plan mode, no changes applied) ==="
else
echo "=== Planning Infrastructure ==="
tofu plan -out=tfplan
if ! $AUTO_APPROVE; then
echo ""
read -rp "Apply this plan for $CLUSTER? (y/n) " -n 1 REPLY
echo
[[ "$REPLY" =~ ^[Yy]$ ]] || { echo "Cancelled."; exit 1; }
fi
echo "Applying infrastructure..."
tofu apply tfplan
# ─── Save kubeconfig ──────────────────────────────────────────────
KUBECONFIG_DIR="$PROJECT_ROOT/private/$CLUSTER"
mkdir -p "$KUBECONFIG_DIR"
KUBECONFIG_FILE="$KUBECONFIG_DIR/kubeconfig"
echo ""
echo "=== Saving Kubeconfig ==="
case "$PLATFORM" in
aks)
if tofu output -raw kubeconfig > "$KUBECONFIG_FILE" 2>/dev/null; then
echo " Saved from tofu output"
else
echo " Fetching from Azure CLI..."
RG=$(tofu output -raw resource_group_name 2>/dev/null || echo "${CLUSTER_clusterName:-$CLUSTER}-rg")
NAME=$(tofu output -raw cluster_name 2>/dev/null || echo "${CLUSTER_clusterName:-$CLUSTER}")
az aks get-credentials --resource-group "$RG" --name "$NAME" --file "$KUBECONFIG_FILE" --overwrite-existing
fi
;;
eks)
NAME=$(tofu output -raw cluster_name 2>/dev/null || echo "${CLUSTER_clusterName:-$CLUSTER}")
REGION=$(tofu output -raw aws_region 2>/dev/null || echo "${AWS_REGION:-eu-west-1}")
aws eks update-kubeconfig --name "$NAME" --region "$REGION" --kubeconfig "$KUBECONFIG_FILE"
;;
gke)
NAME=$(tofu output -raw cluster_name 2>/dev/null || echo "${CLUSTER_clusterName:-$CLUSTER}")
REGION=$(tofu output -raw region 2>/dev/null || echo "${GCP_REGION:-europe-west4}")
PROJECT=$(tofu output -raw project_id 2>/dev/null || echo "${GCP_PROJECT_ID:-}")
gcloud container clusters get-credentials "$NAME" --region "$REGION" --project "$PROJECT" 2>/dev/null \
&& cp ~/.kube/config "$KUBECONFIG_FILE" \
|| echo " Warning: could not fetch kubeconfig via gcloud"
;;
upc)
if tofu output -raw kubeconfig > "$KUBECONFIG_FILE" 2>/dev/null; then
echo " Saved from tofu output"
else
CLUSTER_ID=$(tofu output -raw cluster_id 2>/dev/null || echo "${UPCLOUD_CLUSTER_ID:-}")
if [[ -n "$CLUSTER_ID" ]]; then
upctl kubernetes config "$CLUSTER_ID" > "$KUBECONFIG_FILE"
else
echo " Warning: could not determine cluster ID for kubeconfig"
fi
fi
;;
esac
if [[ -f "$KUBECONFIG_FILE" ]]; then
chmod 600 "$KUBECONFIG_FILE"
echo " Kubeconfig: $KUBECONFIG_FILE"
fi
# ─── Wait for nodes ──────────────────────────────────────────────
echo ""
echo "=== Waiting for Cluster Nodes ==="
export KUBECONFIG="$KUBECONFIG_FILE"
if kubectl wait --for=condition=Ready nodes --all --timeout=300s 2>/dev/null; then
echo " All nodes ready"
else
echo " Warning: nodes not ready within timeout — check cluster status"
fi
# ─── Summary ─────────────────────────────────────────────────────
echo ""
echo "========================================="
echo " Cluster $CLUSTER Provisioned"
echo "========================================="
echo ""
echo " Kubeconfig: $KUBECONFIG_FILE"
echo ""
echo " Next steps:"
echo " export KUBECONFIG=$KUBECONFIG_FILE"
echo " ./bootstrap.sh $CLUSTER"
echo ""
fi
+7
View File
@@ -0,0 +1,7 @@
#!/bin/bash
set -euo pipefail
SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
# Delegate to setup-cluster.sh with --destroy flag
exec "$SCRIPT_DIR/setup-cluster.sh" "$@" --destroy
+47 -24
View File
@@ -57,7 +57,7 @@ This repository contains the complete GitOps configuration for our Kubernetes cl
### What's Inside ### What's Inside
- **Infrastructure Applications**: Traefik, Cert-Manager, Kyverno, Prometheus, Grafana, Loki, Tempo, Sealed Secrets - **Infrastructure Applications**: Traefik, Cert-Manager, Kyverno, Prometheus, Grafana, Loki, Tempo, Sealed Secrets, Homepage (platform dashboard)
- **Business Applications**: MCP10X, MusicMan, Dot-AI Stack, ArgoCD MCP - **Business Applications**: MCP10X, MusicMan, Dot-AI Stack, ArgoCD MCP
- **Policies**: Kyverno security policies for secret management, namespace controls, pod verification - **Policies**: Kyverno security policies for secret management, namespace controls, pod verification
- **Monitoring**: Full observability stack with metrics, logs, traces, and alerting - **Monitoring**: Full observability stack with metrics, logs, traces, and alerting
@@ -80,28 +80,44 @@ This repository contains the complete GitOps configuration for our Kubernetes cl
``` ```
. .
├── bootstrap.sh # Cluster initialization script ├── bootstrap.sh # Cluster initialization (ArgoCD + GitOps)
├── _app-of-apps.yaml # Root ArgoCD Application (App-of-Apps pattern) ├── _app-of-apps-{cluster}.yaml # Root ArgoCD Application (per cluster)
│
├── .tofu/ # Infrastructure provisioning (OpenTofu)
│ ├── platforms/ # Per-platform IaC (one dir per cloud)
│ │ ├── aks/ # Azure AKS (modules/ + dev/ + prod/ + workload/)
│ │ ├── eks/ # AWS EKS
│ │ ├── gke/ # GCP GKE
│ │ └── upc/ # UpCloud
│ ├── configs/ # Platform credentials (git-ignored)
│ │ └── *.env.example # Template for each platform
│ └── scripts/ # Cluster lifecycle scripts
│ ├── setup-cluster.sh # Create cluster: ./setup-cluster.sh aks-dev
│ ├── teardown-cluster.sh
│ └── get-kubeconfig.sh
│
├── clusters/ # Cluster metadata (domain, trustedIPs, etc.)
│ │
├── infra/ # Infrastructure ArgoCD Applications (Kustomize multi-cluster) ├── infra/ # Infrastructure ArgoCD Applications (Kustomize multi-cluster)
│ ├── base/ # Base ArgoCD Application manifests (EU defaults) │ ├── base/ # Base ArgoCD Application manifests (one dir per component)
│ │ ├── kustomization.yaml │ │ ├── kustomization.yaml # Aggregates all component subdirectories
│ │ ├── traefik-application.yaml │ │ ├── traefik-application/
│ │ ├── keycloak.yaml │ │ │ ├── kustomization.yaml
│ │ ├── grafana.yaml │ │ │ └── traefik-application.yaml
│ │ ├── gitea.yaml │ │ ├── keycloak/
│ │ ├── gitea-actions.yaml │ │ │ ├── kustomization.yaml
│ │ ├── tempo.yaml │ │ │ └── keycloak.yaml
│ │ ├── renovate.yaml │ │ ├── grafana/
│ │ ├── ... # All other Application manifests │ │ ├── prometheus/
│ │ └── secrets.yaml │ │ ├── ... # Each component in its own subdirectory
│ │ └── secrets/
│ ├── overlays/ # Per-cluster overrides (Kustomize) │ ├── overlays/ # Per-cluster overrides (Kustomize)
│ │ ├── upc-dev/ # UpCloud Dev (uses base as-is) │ │ ├── upc-dev/ # UpCloud Dev — includes all base components
│ │ ├── upc-prod/ # UpCloud Prod (patches value paths) │ │ ├── upc-prod/ # UpCloud Prod — all components + patches
│ │ ├── aks-dev/ # Azure AKS Dev — selective components only
│ │ ├── aks-prod/ # Azure AKS Prod
│ │ ├── eks-dev/ # AWS EKS Dev │ │ ├── eks-dev/ # AWS EKS Dev
│ │ ├── eks-prod/ # AWS EKS Prod │ │ ├── eks-prod/ # AWS EKS Prod
│ │ ├── aks-dev/ # Azure AKS Dev
│ │ ├── aks-prod/ # Azure AKS Prod
│ │ ├── gke-dev/ # GCP GKE Dev │ │ ├── gke-dev/ # GCP GKE Dev
│ │ └── gke-prod/ # GCP GKE Prod │ │ └── gke-prod/ # GCP GKE Prod
│ ├── dashboards/ # Grafana dashboard ConfigMaps │ ├── dashboards/ # Grafana dashboard ConfigMaps
@@ -116,11 +132,18 @@ This repository contains the complete GitOps configuration for our Kubernetes cl
│ ├── gke-dev/ # GCP GKE Dev │ ├── gke-dev/ # GCP GKE Dev
│ └── gke-prod/ # GCP GKE Prod │ └── gke-prod/ # GCP GKE Prod
│ │
├── apps/ # Business Applications ├── apps/ # Business Applications (Kustomize, same pattern as infra)
│ ├── mcp10x.yaml │ ├── base/ # One subdirectory per app
│ ├── musicman.yaml │ │ ├── kustomization.yaml
│ ├── dot-ai-stack.yaml │ │ ├── musicman/
│ └── argo-mcp.yaml │ │ ├── mcp10x/
│ │ ├── dot-ai-stack/
│ │ ├── ts-mcp/
│ │ └── argo-mcp/
│ └── overlays/ # Per-cluster: cherry-pick or include all
│ ├── upc-dev/ # All apps
│ ├── upc-prod/ # All apps + patches
│ └── aks-dev/ # Selective apps only
│ │
├── cluster-resources/ # Cluster-wide Kubernetes resources ├── cluster-resources/ # Cluster-wide Kubernetes resources
│ ├── letsencrypt-issuer.yaml │ ├── letsencrypt-issuer.yaml
@@ -372,7 +395,7 @@ kubectl patch application myapp -n argocd \
## 📖 Key Concepts ## 📖 Key Concepts
### App-of-Apps Pattern ### App-of-Apps Pattern
`_app-of-apps-{cluster}.yaml` is the root Application that manages all other Applications in `infra/`. Kustomize overlays in `infra/overlays/{cluster}/` render the base Applications with per-cluster patches (e.g., swapping value file paths). Supported clusters: `upc-dev`, `upc-prod`, `eks-dev`, `eks-prod`, `aks-dev`, `aks-prod`, `gke-dev`, `gke-prod`. `_app-of-apps-{cluster}.yaml` is the root Application that manages all other Applications in `infra/`. Each component in `infra/base/` lives in its own subdirectory (e.g., `infra/base/grafana/`). Overlays can either include **all** components (via `../../base`) or **cherry-pick** specific ones (via `../../base/grafana`, `../../base/prometheus`, etc.). Per-cluster patches swap Helm value file paths. Supported clusters: `upc-dev`, `upc-prod`, `eks-dev`, `eks-prod`, `aks-dev`, `aks-prod`, `gke-dev`, `gke-prod`.
### Multi-Source Pattern ### Multi-Source Pattern
Applications reference both: Applications reference both:
+6
View File
@@ -0,0 +1,6 @@
apiVersion: kustomize.config.k8s.io/v1beta1
kind: Kustomization
resources:
- argo-mcp.yaml
- argocdmcp-auth-oidc-sealed.yaml
- argocd-mcp-credentials.yaml
@@ -15,9 +15,6 @@ metadata:
namespace: argocd namespace: argocd
annotations: annotations:
argocd.argoproj.io/sync-wave: "1" argocd.argoproj.io/sync-wave: "1"
notifications.argoproj.io/subscribe.on-sync-succeeded.slack: ""
notifications.argoproj.io/subscribe.on-sync-failed.slack: ""
notifications.argoproj.io/subscribe.on-degraded.slack: ""
labels: labels:
app.kubernetes.io/name: dot-ai-stack app.kubernetes.io/name: dot-ai-stack
app.kubernetes.io/part-of: apps app.kubernetes.io/part-of: apps
@@ -0,0 +1,5 @@
apiVersion: kustomize.config.k8s.io/v1beta1
kind: Kustomization
resources:
- dot-ai-stack.yaml
- dot-ai-secrets.yaml
+5 -5
View File
@@ -1,8 +1,8 @@
apiVersion: kustomize.config.k8s.io/v1beta1 apiVersion: kustomize.config.k8s.io/v1beta1
kind: Kustomization kind: Kustomization
resources: resources:
- dot-ai-stack.yaml - dot-ai-stack
- mcp10x.yaml - mcp10x
- musicman.yaml - musicman
- ts-mcp.yaml - ts-mcp
- argo-mcp.yaml - argo-mcp
@@ -0,0 +1,17 @@
---
apiVersion: bitnami.com/v1alpha1
kind: SealedSecret
metadata:
creationTimestamp: null
name: app-credentials
namespace: mcp10x
spec:
encryptedData:
BENKEN_CLIENT_SECRET: AgBjps8BCn20C8upAaAdb1fG4Qh3eKBbTeFuuWhQb8WoIvHmk+v03mw8i39evkQwlUWvLBWV1mtGiKwpCNhmAAdicRFG6u0m30+21K6ZtYqtKEniPKo/kjPd9nDbtxvIwiaqKs+kvFpqbxKaeqF5THYNxHZBg8gGeSbAkSx+BNIY2iLm8NRBzgC5FME5jbX8pet+DN7tbmsQTtG5f1q+h24aKXjvN5SigPft1BetfleHGlus0hFXpJ7zS4rV7rpSKSiLVV/KtS5YqEDj9uunZKyGT8j93z5xQbj0bCPVF3TU5+RCL6eE/GSgJxM4ePZ2gWZRG4eHDlGK2qE+JaNIng8wWycqLVrbs1kWoP2cdRGq6b8GHwoplAM4h4ud2fac6+5V4alhy8uhRTAX7dUG3UkwOQV/hTRb97pctPwQfltkBpDBhhW3Lfy9whSdqBuD9OqhegTqxCuWXr/P4KVOORUr0V0Iex45oLMqivI3FB2rTq9Lkwpf5YKE14d7RbKWF1G28FCNAcV8vnOIslkztLuu3GgQbVIoIiZGnnYEPofjUxbDZ/Sd1LrGeHEPR+/JJnNhNxv2297UuIIEC8kfiKuwjtLOMVQg51UbESx/+d1XmgLPqkz+jAqEPxvu8u5wO0Dov6vliTbtewJf8+fet3xnFNvyuY5ymmiTla6Gm9XPJscLj5iCzT3VhA/QuhhWXinmE/UnpYP0U4YPl5B/dUA9qT95BA6GBpDXPrDJRWNfpAH1wfG70lEBuBQXgdixYlwvx2JO6OI5+ztBKO0qFkgK
FLOWCASE_TOKEN: AgBLN1BWnFs3R2K+Wvb37ABucQWvx8mVVDEhZiIOYYLE8SDdbshxluP4J4IISmHwLX7Q0gYWeypfTCfvMa9c5b9AEjTcpodv4CMhjp5Mq7zUCtTI6pH6QZgLhjGheKCY+RciIK1DBsNk7CZa9MuVUdd1w0/m2C7fwikPPvNDHcNLR7zBBPWVlprgRyMrsdykcm7cmWcyqTwa/55DVPPJsG9x1K2YnjzgWHlX7BoLB/Nx7qX4XVadKEXnV0jVO5isalARxvke32pwebaiFSg8EZMhe4lntOqMSP26y/9RbveeEZS8qxzoR2OmsVrHUpMeppzpVkvQ9sKi2B4Vx8XoiRY6hZR+TmZKTvFa6JKx9gwAOVs53LEUaF7+uOQOrIcFyOXm7Ibj/azf7opqfvGajygRzSUaffTIixj+M5eJnm/iua/BWarW2w4c+ZIKvQ9DhcYpnF9Gj0U7+EWfNZyzlMoLRHsOIyKNUhOeEaSLoVQGyqRY72ZGqs83EPfQYlEu74PGyXPjd11KMhAayluGLadeAH2QDyigpf7REdXAGULNDhkJrqeYMmmGCZCyrvNOoXjYC4jQQEYA4Sd4QJA05q/EW8aFE/++nY8RqhbHqDz6wshAW/WFsTsR4JC6fc5qR+YVSmjKOa7lnk7I9vD7uPEZzCc6ImvA/NxTCfDKCREvLA5G0lYsmiTuxYmBesUgCSVVMxflEl1GXvGpFniZKPyvxIdna9j7XEQjUZsGTiyN1w==
template:
metadata:
creationTimestamp: null
name: app-credentials
namespace: mcp10x
type: Opaque
+5
View File
@@ -0,0 +1,5 @@
apiVersion: kustomize.config.k8s.io/v1beta1
kind: Kustomization
resources:
- mcp10x.yaml
- forte10x-app-credentials-sealed.yaml
+5
View File
@@ -0,0 +1,5 @@
apiVersion: kustomize.config.k8s.io/v1beta1
kind: Kustomization
resources:
- musicman.yaml
- musicman-credentials.yaml
@@ -4,6 +4,8 @@ metadata:
creationTimestamp: null creationTimestamp: null
name: musicman-credentials name: musicman-credentials
namespace: music-man namespace: music-man
annotations:
argocd.argoproj.io/sync-wave: "12"
spec: spec:
encryptedData: encryptedData:
DATABASE_URL: AgBGLu8Rw9z9WMo3uX7fezN7tOVlEsmWtikFlyBxuSuQ1dCv6KTCePkwxJx4LuKvaHXlwdWl5yP8wQxMJP0BNJ1wewFb9zeUkP1YuCz4MrfuXq1zrecIr86R5hNbPiOb66e/4oOTCY/z3QREX9WjZdLJV/PCyBz8MP0D51pgWXpM6CBdhwpFbHSALyJk89+q44c9KkRxAUG2OLnesMeRe9nXJt5ariUCl9Qd2POIjx2hSNII1l0KbTcjI9hCf91DYM6poqKYYQUpnrjKv3LJwWS79I2b56+iTtroH3usIRgaiwgtFt2INm+8gwLBmC4xxKJ5VAjjYB/3dcN9XeboXvj0NB05P9jS3e77imUFANIB9coeaNlcvRWxwGCewYMp8+7RT7jPVA41/+aT/zT74tq9WhkKvgrr1It9/5fRnXtFEkhZg5bBcYCChzooarHkiwKlA3Wo0CrFsDPqy89oZrnwMRnVqKWBf79koZV4l7uCA0do9ojf55lTy8mt3mKQkwfqK9UdzZNbYzH0/Fk6gxlSxANOOqe7kt6VPywYUBnh6JS5U+kdTgNeSrFy/xqLFz28fXuikSJvLEouSFu66MeT+6uvYEmdfdLeh7quW/n+p7QTok3v3kRYJ/1Dl8ZtgvM7e8F/J5bLcacj394AJ/bBt+RIDa+XBjNNPrWKcWt/mkudZ25F/84G+hNxYQv7PIbhYfA1JTuHmQSoF+xah5QhKpyNpI3+knJmJj/4MhPKLnTuebg0xfbPevm2CU9fSa4sPIqmSvSGtqlXODvCfDSFEYzWfyfXV5Tys1NGAt04V8fl9A9UxULUm510NCeD0jzFeeYm3ZJiyavA5xF6hXCHoqLE DATABASE_URL: AgBGLu8Rw9z9WMo3uX7fezN7tOVlEsmWtikFlyBxuSuQ1dCv6KTCePkwxJx4LuKvaHXlwdWl5yP8wQxMJP0BNJ1wewFb9zeUkP1YuCz4MrfuXq1zrecIr86R5hNbPiOb66e/4oOTCY/z3QREX9WjZdLJV/PCyBz8MP0D51pgWXpM6CBdhwpFbHSALyJk89+q44c9KkRxAUG2OLnesMeRe9nXJt5ariUCl9Qd2POIjx2hSNII1l0KbTcjI9hCf91DYM6poqKYYQUpnrjKv3LJwWS79I2b56+iTtroH3usIRgaiwgtFt2INm+8gwLBmC4xxKJ5VAjjYB/3dcN9XeboXvj0NB05P9jS3e77imUFANIB9coeaNlcvRWxwGCewYMp8+7RT7jPVA41/+aT/zT74tq9WhkKvgrr1It9/5fRnXtFEkhZg5bBcYCChzooarHkiwKlA3Wo0CrFsDPqy89oZrnwMRnVqKWBf79koZV4l7uCA0do9ojf55lTy8mt3mKQkwfqK9UdzZNbYzH0/Fk6gxlSxANOOqe7kt6VPywYUBnh6JS5U+kdTgNeSrFy/xqLFz28fXuikSJvLEouSFu66MeT+6uvYEmdfdLeh7quW/n+p7QTok3v3kRYJ/1Dl8ZtgvM7e8F/J5bLcacj394AJ/bBt+RIDa+XBjNNPrWKcWt/mkudZ25F/84G+hNxYQv7PIbhYfA1JTuHmQSoF+xah5QhKpyNpI3+knJmJj/4MhPKLnTuebg0xfbPevm2CU9fSa4sPIqmSvSGtqlXODvCfDSFEYzWfyfXV5Tys1NGAt04V8fl9A9UxULUm510NCeD0jzFeeYm3ZJiyavA5xF6hXCHoqLE
@@ -36,13 +36,8 @@ spec:
automated: automated:
prune: true prune: true
selfHeal: true selfHeal: true
allowEmpty: false
syncOptions: syncOptions:
- CreateNamespace=true - CreateNamespace=true
- Validate=true
- ServerSideApply=false
- Replace=false
retry: retry:
limit: 5 limit: 5
backoff: backoff:
+5
View File
@@ -0,0 +1,5 @@
apiVersion: kustomize.config.k8s.io/v1beta1
kind: Kustomization
resources:
- ts-mcp.yaml
- ts-mcp-secrets-sealed.yaml
+4
View File
@@ -0,0 +1,4 @@
apiVersion: kustomize.config.k8s.io/v1beta1
kind: Kustomization
resources:
- ../../base/musicman
@@ -0,0 +1,47 @@
apiVersion: argoproj.io/v1alpha1
kind: Application
metadata:
name: dbunk-demo
namespace: argocd
annotations:
argocd.argoproj.io/sync-wave: "12"
labels:
app.kubernetes.io/name: dbunk-demo
app.kubernetes.io/part-of: apps
app.kubernetes.io/managed-by: argocd
finalizers:
- resources-finalizer.argocd.argoproj.io
spec:
project: default
sources:
- repoURL: ssh://git@git.forteapps.net:2222/Forte/forte-helm.git
path: forteapp
targetRevision: HEAD
helm:
valueFiles:
- $values/dbunk-demo/values.yaml
- repoURL: ssh://git@git.forteapps.net:2222/Forte/helm-prod-values.git
targetRevision: HEAD
ref: values
destination:
server: https://kubernetes.default.svc
namespace: dbunk-demo
syncPolicy:
automated:
prune: true
selfHeal: true
allowEmpty: false
syncOptions:
- CreateNamespace=true
- Validate=true
- ServerSideApply=true
retry:
limit: 5
backoff:
duration: 5s
factor: 2
maxDuration: 3m
@@ -0,0 +1,4 @@
apiVersion: kustomize.config.k8s.io/v1beta1
kind: Kustomization
resources:
- dbunk-demo.yaml
@@ -1,27 +1,34 @@
apiVersion: argoproj.io/v1alpha1 apiVersion: argoproj.io/v1alpha1
kind: Application kind: Application
metadata: metadata:
name: secrets name: forte-drop-mcp
namespace: argocd namespace: argocd
annotations: annotations:
argocd.argoproj.io/sync-wave: "2" argocd.argoproj.io/sync-wave: "1"
notifications.argoproj.io/subscribe.on-sync-succeeded.slack: "" notifications.argoproj.io/subscribe.on-sync-succeeded.slack: ""
notifications.argoproj.io/subscribe.on-sync-failed.slack: "" notifications.argoproj.io/subscribe.on-sync-failed.slack: ""
notifications.argoproj.io/subscribe.on-degraded.slack: "" notifications.argoproj.io/subscribe.on-degraded.slack: ""
labels: labels:
app.kubernetes.io/name: secrets app.kubernetes.io/name: forte-drop-mcp
app.kubernetes.io/part-of: platform app.kubernetes.io/part-of: apps
app.kubernetes.io/managed-by: argocd app.kubernetes.io/managed-by: argocd
finalizers: finalizers:
- resources-finalizer.argocd.argoproj.io - resources-finalizer.argocd.argoproj.io
spec: spec:
project: default project: default
source: sources:
repoURL: ssh://git@git.forteapps.net:2222/Forte/launchpad.git - repoURL: ssh://git@git.forteapps.net:2222/Forte/forte-helm.git
path: secrets/overlays/upc-dev path: forteapp
targetRevision: HEAD
helm:
valueFiles:
- $values/forte-drop-mcp/values.yaml
- repoURL: ssh://git@git.forteapps.net:2222/Forte/helm-prod-values.git
targetRevision: HEAD
ref: values
destination: destination:
server: https://kubernetes.default.svc server: https://kubernetes.default.svc
namespace: secrets namespace: forte-drop
syncPolicy: syncPolicy:
automated: automated:
prune: true prune: true
@@ -0,0 +1,8 @@
apiVersion: kustomize.config.k8s.io/v1beta1
kind: Kustomization
resources:
- forte-drop-mcp.yaml
# No keycloak-client config + no auth-oidc Secret for mcp mode. The chart's
# auth.type: mcp auto-registers the MCP client; the sidecar is an RFC 9728
# resource server that validates tokens (no client-secret of its own).
# forte-drop-secrets (shared with web) covers PG + S3 creds.
@@ -0,0 +1,143 @@
# forte-drop Postgres — backup & restore runbook
## What gets backed up
A CronJob (`forte-drop-pg-backup`, namespace `forte-drop`) runs nightly at **02:00 UTC**:
1. `pg_dump` of the `drops` database → gzip.
2. Upload to **UpCloud Managed Object Storage**: `s3://drops/_pgbackups/forte-drop-<TS>.sql.gz`
(the `_pgbackups/` prefix is collision-proof: app slugs match `/^[a-z0-9][a-z0-9-]{0,62}$/`
and can never start with `_`).
3. Retention: dumps older than **30 days** are pruned.
S3 creds come from the `forte-drop-secrets` Secret (`S3_ENDPOINT` / `S3_KEY` / `S3_SECRET`).
Postgres creds from `forte-drop-pg-creds` (`pgusername` / `pgpassword`).
> **Object storage is the durable tier.** App data + DB backups both live in UpCloud
> Managed Object Storage (replicated by UpCloud). The in-cluster Postgres PVC is the
> live working copy; the nightly dump is the recovery point. The PVC carries
> `Prune=false,Delete=false` so ArgoCD never deletes it.
## Prerequisites
```bash
export KUBECONFIG=~/Downloads/dev-fd-no-svg1_kubeconfig.yaml
# Confirm the namespace + DB pod are up:
kubectl -n forte-drop get pods -l app.kubernetes.io/name=postgresql
```
## List available backups
```bash
# Run an ephemeral mc pod with the app's S3 creds:
kubectl -n forte-drop run mc-list --rm -it --restart=Never \
--image=quay.io/minio/mc:RELEASE.2024-11-21T17-21-54Z \
--overrides='{"spec":{"containers":[{"name":"mc","image":"quay.io/minio/mc:RELEASE.2024-11-21T17-21-54Z","command":["sh","-c","mc alias set obj \"$S3_ENDPOINT\" \"$S3_KEY\" \"$S3_SECRET\" >/dev/null && mc ls obj/drops/_pgbackups/"],"envFrom":[{"secretRef":{"name":"forte-drop-secrets"}}]}]}}'
```
## Manually trigger a backup (before risky changes)
```bash
kubectl -n forte-drop create job --from=cronjob/forte-drop-pg-backup pg-backup-manual-$(date +%s)
# Watch:
kubectl -n forte-drop get jobs -l app.kubernetes.io/component=backup
kubectl -n forte-drop logs -l app.kubernetes.io/component=backup --tail=40
```
## Restore a dump
> **Destructive.** This overwrites the live `drops` database. Take a fresh manual
> backup first (above) and confirm with whoever owns the data before proceeding.
### 1. Pick the dump to restore
List backups (above), choose `forte-drop-<TS>.sql.gz`.
### 2. Run a restore pod that pulls the dump and pipes it into Postgres
```bash
DUMP="forte-drop-20260530T020000Z.sql.gz" # <-- set to the chosen file
kubectl -n forte-drop run pg-restore --rm -it --restart=Never \
--image=postgres:16-alpine \
--overrides='{
"spec": {
"containers": [{
"name": "restore",
"image": "postgres:16-alpine",
"command": ["sh","-c","set -euo pipefail; \
apk add --no-cache curl >/dev/null; \
# download via mc is simpler — use a 2-step instead (see note). \
echo placeholder"],
"envFrom": [
{"secretRef":{"name":"forte-drop-pg-creds"}},
{"secretRef":{"name":"forte-drop-secrets"}}
]
}]
}
}'
```
**Simpler 2-pod approach (recommended — avoids cramming mc + psql in one image):**
```bash
DUMP="forte-drop-20260530T020000Z.sql.gz"
# (a) Download the dump from object storage to a local file:
kubectl -n forte-drop run mc-get --rm -it --restart=Never \
--image=quay.io/minio/mc:RELEASE.2024-11-21T17-21-54Z \
--overrides='{"spec":{"containers":[{"name":"mc","image":"quay.io/minio/mc:RELEASE.2024-11-21T17-21-54Z","command":["sh","-c","mc alias set obj \"$S3_ENDPOINT\" \"$S3_KEY\" \"$S3_SECRET\" >/dev/null && mc cat obj/drops/_pgbackups/'"$DUMP"'"],"envFrom":[{"secretRef":{"name":"forte-drop-secrets"}}]}]}}' \
> /tmp/$DUMP
# (b) Pipe it into the live Postgres via the service:
gunzip -c /tmp/$DUMP | kubectl -n forte-drop run pg-restore --rm -i --restart=Never \
--image=postgres:16-alpine \
--overrides='{"spec":{"containers":[{"name":"psql","image":"postgres:16-alpine","stdin":true,"command":["sh","-c","PGPASSWORD=\"$pgpassword\" psql -h forte-drop-postgresql.forte-drop.svc -U \"$pgusername\" -d drops"],"env":[{"name":"pgusername","valueFrom":{"secretKeyRef":{"name":"forte-drop-pg-creds","key":"pgusername"}}},{"name":"pgpassword","valueFrom":{"secretKeyRef":{"name":"forte-drop-pg-creds","key":"pgpassword"}}}]}]}}'
```
> The app's schema is created idempotently on boot (`CREATE TABLE IF NOT EXISTS` +
> `ALTER TABLE ... ADD COLUMN IF NOT EXISTS` in `src/repo/pg.ts`), and `pg_dump`
> output includes the data. For a clean restore into a fresh DB this just works.
> To restore over an existing DB with conflicting rows, drop/recreate the `drops`
> database first (coordinate downtime — scale the web Deployment to 0 during the
> restore so the app isn't writing).
### 3. Verify
```bash
kubectl -n forte-drop run pg-check --rm -it --restart=Never \
--image=postgres:16-alpine \
--env="PGPASSWORD=$(kubectl -n forte-drop get secret forte-drop-pg-creds -o jsonpath='{.data.pgpassword}' | base64 -d)" \
--command -- psql -h forte-drop-postgresql.forte-drop.svc -U drops -d drops \
-c "SELECT count(*) AS drops FROM drops;" -c "SELECT count(*) AS view_hits FROM view_hits;"
```
### 4. Bring the app back
```bash
# If you scaled web to 0 for the restore:
kubectl -n forte-drop scale deploy/forte-drop --replicas=2
```
## Object data (uploaded drop files)
Drop files live in `s3://drops/<slug>/...` in the same managed bucket. They are
**not** part of the pg backup (the dump only holds metadata). Object storage is
UpCloud-managed/replicated, so no separate file backup is configured. If a
file-level backup is later required, mirror the bucket to a second bucket/region:
```bash
mc mirror --overwrite obj/drops/ backup-target/drops-mirror/
```
(Exclude `_pgbackups/` from the app-data mirror if you split them.)
## Disaster scenarios
| Scenario | Recovery |
|---|---|
| Postgres pod crash / reschedule | StatefulSet reattaches the PVC; ~1–2 min downtime; no data loss. |
| PVC lost / corrupted | Recreate StatefulSet, restore latest nightly dump (above). Data since last dump is lost. |
| Accidental `drops` table data loss | Restore latest dump; or `pg_restore` a single table from a dump. |
| Namespace deleted | PVC has `Prune=false,Delete=false`; recreate Applications, PVC re-binds, app recovers. Backups in object storage are independent. |
| Object storage bucket lost | UpCloud-managed (replicated). If the IAM key is rotated, update `forte-drop-secrets` (re-seal). |
@@ -1,14 +1,14 @@
apiVersion: argoproj.io/v1alpha1 apiVersion: argoproj.io/v1alpha1
kind: Application kind: Application
metadata: metadata:
name: network-policies name: forte-drop-postgresql
namespace: argocd namespace: argocd
labels:
app.kubernetes.io/name: network-policies
app.kubernetes.io/part-of: platform
app.kubernetes.io/managed-by: argocd
annotations: annotations:
argocd.argoproj.io/sync-wave: "1" argocd.argoproj.io/sync-wave: "0"
labels:
app.kubernetes.io/name: forte-drop-postgresql
app.kubernetes.io/part-of: apps
app.kubernetes.io/managed-by: argocd
finalizers: finalizers:
- resources-finalizer.argocd.argoproj.io - resources-finalizer.argocd.argoproj.io
spec: spec:
@@ -17,17 +17,24 @@ spec:
source: source:
repoURL: ssh://git@git.forteapps.net:2222/Forte/launchpad.git repoURL: ssh://git@git.forteapps.net:2222/Forte/launchpad.git
targetRevision: HEAD targetRevision: HEAD
path: cluster-resources/network path: apps/overlays/upc-dev/forte-drop-postgresql/resources
destination: destination:
server: https://kubernetes.default.svc server: https://kubernetes.default.svc
namespace: forte-drop
syncPolicy: syncPolicy:
automated: automated:
prune: true prune: true
selfHeal: true selfHeal: true
allowEmpty: false allowEmpty: false
syncOptions: syncOptions:
- CreateNamespace=true
- Validate=true - Validate=true
- ServerSideApply=true - ServerSideApply=true
ignoreDifferences:
- group: apps
kind: StatefulSet
jsonPointers:
- /spec/volumeClaimTemplates
@@ -0,0 +1,4 @@
apiVersion: kustomize.config.k8s.io/v1beta1
kind: Kustomization
resources:
- forte-drop-postgresql.yaml
@@ -0,0 +1,14 @@
---
apiVersion: bitnami.com/v1alpha1
kind: SealedSecret
metadata:
name: forte-drop-pg-creds
namespace: forte-drop
spec:
encryptedData:
pgpassword: AgBYokuQRCTmPGC8soB7n8W39nmSAZDTV97i77NmdMh5ndaZNtCtXxhMcpM2z8kaGv2tCWIh47dr38a5tGPZ0TsmeEQOF9Rbbtq1fyR7pJwT8S+N2Z2zu354wNWQlltEAVvTvthe2wTer/BpyRofeSZprxihmfNpuHUP8rLsnIXln5tOWDzJ8hnRWoYZFITaihC2qrJj/kFE0Rfdcmzt1tSq3jCB/rWijVaJF9XSh4rzQoqZDiUNjDPUjyERILw59JWU4zf9OKcqNHDnmpXBR4LSjLhd9waN6ElEzO4gGcVaHISKrTwewX1ONwPHDnw6lqkQObyBPx8aUsGzxLkUhNDtvIYDkB4BKWP5Qu4bNcSztIbrxi6l7Lr/DWC9qTbKm1/p83rc6r8VqRMURUyQg8/vBlCHOIUbZ8DM1OfNlMd8gvcSkaxEVIdCDUjguCvE3cGyG4cqv2unllZQ+9417WwLNJecT6x1EL3nQyAlK5c9vUIbcVyaFlbSUcGB7xmPgZrZ6/3RDyOH6Tmew1ssV9gLvdaehscUE0fjnnFnJpczkwdyxIOSNLIkjlWetCKEbhowJbzk05h3M2p6XQQOuNTnsYjAADMGD72GUgAQlY8KXmDELtv09KELcXbeYS4gABPpMrVmvZymq8lqQ13Py8o+cIqbrU5V86WxASTfQ5gMo/ymYabuhTBIapcnaKR1dFCCfu8deh5f2HJ6/1NjdWR+XvEshg+EF5OkTUInukX4vA==
pgusername: AgCs6vyQ8CIv5OneP/jMltIPGdZQbpq/BFmQM1mkBD61Ve+anzve5K0Gkg+zsNfbZf0pOPAXtu4C4aL1Lwv7gqpoe4Hp/UEb/X9uLfJ1b8ZitmM1XsPmmSiCskHjrc2BLkAvfrVIXkHc3LOY2uZ/E5stc6Ss2WFE8/uzzVXW0B8fdEK0criludQ8iwR1gypulEcDNomXgkK/1gmmCWosUcVv4jDMDhqBD+b9WYnBB6J73gUclWVMvYDFdNas2PuoRzu5Twc9TAZrTxN5lvLOXAonOo0YiUbUhEC83sfMWYDT5/9OxqcJhAxtgFe9j83MpCwLSwfeLZm7UsUapWDb60MxPJLGvoGD/ZOhkeYt/YCZYROa57TMslVIL5YU1KCiNWvtRjIqnvdiBxI7MRvPUfAoawS4ktT5PDhTTfrixFbaF95jul2kKBXV+OYB1UNsFhcCgZx9rzYRt4lNmBv4m4HeXIp3EYY8VlGLQ45BVVqjJ4QkISvb7ifQWH1aPMQllj+J3GwW0KJN0dEgsh1LT+C7W5I5mq461NOTF1eih/XRBeuPoLlgApxiGXvFCTx8lji2/JIdOaqcg29hdabSprxa0YMStChi2pbtHhRzAuFCp8mInGt8Q406vu67Y4/51yuwI40YeDVu0lf010TB+/v2Zy3OrNyjlqrD5JNynsLuRl3UhuAKC14Xhg/MiDLvTzfsYE8aog==
template:
metadata:
name: forte-drop-pg-creds
namespace: forte-drop
@@ -0,0 +1,6 @@
apiVersion: kustomize.config.k8s.io/v1beta1
kind: Kustomization
resources:
- postgresql.yaml
- forte-drop-pg-creds-sealed.yaml
- pg-backup-cronjob.yaml
@@ -0,0 +1,99 @@
# Nightly logical backup of the forte-drop Postgres → UpCloud Managed Object Storage.
# Dumps to s3://drops/_pgbackups/ (the `_` prefix is collision-proof: app slugs match
# /^[a-z0-9][a-z0-9-]{0,62}$/ and can never start with `_`). Retains 30 days.
#
# Pod shape: initContainer pg_dump → shared emptyDir → mc upload + retention prune.
# Both images pinned. S3 creds reuse forte-drop-secrets (the app's UpCloud user has
# s3:* on the drops bucket). PG creds from forte-drop-pg-creds.
apiVersion: batch/v1
kind: CronJob
metadata:
name: forte-drop-pg-backup
namespace: forte-drop
labels:
app.kubernetes.io/name: postgresql
app.kubernetes.io/instance: forte-drop
app.kubernetes.io/component: backup
spec:
schedule: "0 2 * * *" # 02:00 UTC daily
concurrencyPolicy: Forbid
successfulJobsHistoryLimit: 3
failedJobsHistoryLimit: 3
jobTemplate:
spec:
backoffLimit: 2
template:
metadata:
labels:
app.kubernetes.io/name: postgresql
app.kubernetes.io/instance: forte-drop
app.kubernetes.io/component: backup
spec:
restartPolicy: Never
securityContext:
runAsNonRoot: true
runAsUser: 65532
fsGroup: 65532
volumes:
- name: work
emptyDir: {}
initContainers:
- name: dump
image: postgres:16-alpine
command:
- sh
- -c
- |
set -euo pipefail
TS=$(date -u +%Y%m%dT%H%M%SZ)
echo "dumping to /work/forte-drop-${TS}.sql.gz"
PGPASSWORD="$PGPASSWORD" pg_dump \
-h forte-drop-postgresql.forte-drop.svc \
-p 5432 -U "$PGUSER" -d drops \
--no-owner --no-privileges \
| gzip -9 > "/work/forte-drop-${TS}.sql.gz"
echo "dump complete: $(ls -lh /work/)"
env:
- name: PGUSER
valueFrom:
secretKeyRef: { name: forte-drop-pg-creds, key: pgusername }
- name: PGPASSWORD
valueFrom:
secretKeyRef: { name: forte-drop-pg-creds, key: pgpassword }
volumeMounts:
- name: work
mountPath: /work
containers:
- name: upload
image: quay.io/minio/mc:RELEASE.2024-11-21T17-21-54Z
command:
- sh
- -c
- |
set -euo pipefail
mc alias set obj "$S3_ENDPOINT" "$S3_KEY" "$S3_SECRET"
mc cp /work/*.sql.gz "obj/${S3_BUCKET}/_pgbackups/"
echo "uploaded. pruning backups older than 30d:"
mc rm --recursive --force --older-than 30d "obj/${S3_BUCKET}/_pgbackups/" || true
echo "backup retention pass complete"
env:
# mc writes its config under $MC_CONFIG_DIR; point it at the shared
# emptyDir (writable by uid 65532 via fsGroup). Without this it tries
# to mkdir /.mc on the read-only-to-nonroot root fs -> "mkdir /.mc:
# permission denied" and every run fails before uploading.
- name: MC_CONFIG_DIR
value: "/work/.mc"
- name: S3_ENDPOINT
valueFrom:
secretKeyRef: { name: forte-drop-secrets, key: S3_ENDPOINT }
- name: S3_BUCKET
value: "drops"
- name: S3_KEY
valueFrom:
secretKeyRef: { name: forte-drop-secrets, key: S3_KEY }
- name: S3_SECRET
valueFrom:
secretKeyRef: { name: forte-drop-secrets, key: S3_SECRET }
volumeMounts:
- name: work
mountPath: /work
@@ -0,0 +1,105 @@
apiVersion: v1
kind: Service
metadata:
name: forte-drop-postgresql
namespace: forte-drop
labels:
app.kubernetes.io/name: postgresql
app.kubernetes.io/instance: forte-drop
app.kubernetes.io/component: database
spec:
type: ClusterIP
ports:
- name: tcp-postgresql
port: 5432
targetPort: tcp-postgresql
selector:
app.kubernetes.io/name: postgresql
app.kubernetes.io/instance: forte-drop
---
apiVersion: apps/v1
kind: StatefulSet
metadata:
name: forte-drop-postgresql
namespace: forte-drop
labels:
app.kubernetes.io/name: postgresql
app.kubernetes.io/instance: forte-drop
app.kubernetes.io/component: database
spec:
serviceName: forte-drop-postgresql
replicas: 1
selector:
matchLabels:
app.kubernetes.io/name: postgresql
app.kubernetes.io/instance: forte-drop
template:
metadata:
labels:
app.kubernetes.io/name: postgresql
app.kubernetes.io/instance: forte-drop
app.kubernetes.io/component: database
spec:
containers:
- name: postgresql
image: postgres:16-alpine
# NOTE: no securityContext. The official postgres image's entrypoint must
# start as root to chown a fresh /var/lib/postgresql/data, then drops to
# the postgres user (uid 70 in alpine) via gosu. Forcing runAsNonRoot here
# breaks initdb on a fresh PVC. Matches the vaultwarden-postgresql pattern.
ports:
- name: tcp-postgresql
containerPort: 5432
env:
- name: POSTGRES_USER
valueFrom:
secretKeyRef:
name: forte-drop-pg-creds
key: pgusername
- name: POSTGRES_PASSWORD
valueFrom:
secretKeyRef:
name: forte-drop-pg-creds
key: pgpassword
- name: POSTGRES_DB
value: drops
- name: PGDATA
value: /var/lib/postgresql/data/pgdata
volumeMounts:
- name: data
mountPath: /var/lib/postgresql/data
livenessProbe:
exec:
command:
- sh
- -c
- pg_isready -U "$POSTGRES_USER" -d drops
initialDelaySeconds: 30
periodSeconds: 10
readinessProbe:
exec:
command:
- sh
- -c
- pg_isready -U "$POSTGRES_USER" -d drops
initialDelaySeconds: 5
periodSeconds: 5
resources:
requests:
cpu: 100m
memory: 256Mi
limits:
cpu: 500m
memory: 512Mi
volumeClaimTemplates:
- metadata:
name: data
annotations:
argocd.argoproj.io/sync-options: Prune=false,Delete=false
spec:
accessModes:
- ReadWriteOnce
storageClassName: upcloud-block-storage-maxiops
resources:
requests:
storage: 5Gi
@@ -0,0 +1,24 @@
# Keep at least 1 web pod up during voluntary disruptions (node drain, upgrade).
# Pairs with replicaCount: 2 so a drain can evict one pod while the other serves.
#
# Selector verified against live forteapp-chart deployments (mcp10x, argocd-mcp):
# the chart's pod selector is {app.kubernetes.io/instance, app.kubernetes.io/name,
# component: app} where instance/name == the ArgoCD Application (Helm release) name.
# Using all three labels also disambiguates the web pods from the forte-drop-mcp
# deployment that shares the forte-drop namespace (its instance/name == forte-drop-mcp).
apiVersion: policy/v1
kind: PodDisruptionBudget
metadata:
name: forte-drop-web
namespace: forte-drop
labels:
app.kubernetes.io/name: forte-drop
app.kubernetes.io/part-of: apps
app.kubernetes.io/managed-by: argocd
spec:
minAvailable: 1
selector:
matchLabels:
app.kubernetes.io/instance: forte-drop
app.kubernetes.io/name: forte-drop
component: app
@@ -0,0 +1,24 @@
---
apiVersion: bitnami.com/v1alpha1
kind: SealedSecret
metadata:
name: forte-drop-secrets
namespace: forte-drop
spec:
encryptedData:
BASE_DOMAIN: AgAFybdBryVb2AQuGQC8REXzW0YZlyycJp/KeXnROkW71UjDe4qMAWkWszrJWxZMvAPO/tXmibp7jEol6aB5GKG0k3tswWoprTFXLd9CMR2U9SWR3ZCol4npPXo7uOxhBcNSVt+cDXyejSiFTi6goY2oOtbKAJSF9Nv7Z5ePaqhhFni3ntcmM0S1Ad1l3QR7VvyazHFBXfO0b8Z9NgYsUNbGrXWDwoSAZIv3ly3wx90AXn+dXX5FNPtl9CtyAVhHsl3liwQdhEwS2krZZjj7NiQTCfNXp7BSB9ZETpo9KkoV4AZNy1zupd3HpeXHsyhHjq/JqXIAF3iFU0tZTWjhcwnehYdEU5oduwfLCWym5PYgpiQAGiazpkm1Ss3/PYpZYnR2nWv60b1Pa5i79ZiPNi4GL67AiWoJDw6QxV0Kbzi0AvUkZI1E2PeIJvv1w9NKdMRo49xK8LUx2qSTpWeqRP+1kzklHqclTuNVxiWtR2wUgdoLzvU7p5ETu7kPEmaoE8rYw4dKgQvHlMok2Ky2JsELGBkCiYjUN75T+yNlGs5dzbiwtWOja/r0dJ3ZGBQjcK4/BbTLiMYsrxmJTPPF/2zhCOlFY6cfcRMmc7Mwr68mK9m2rTOJQNjBMDoASiqVMmeSqfRSln7JNb1pAeq4xcz9YJMBJhPy2XNiBvRJK3pGIjVcNST0jSpic1X01NJTy7aFbcniZzYnsKJV61AQb+daGEsB1Ib3GnJ+Rv8+9NfvWg==
PASSWORD_GATE_SECRET: AgDIiAPb7bCpTeORoZXIn7Is/yKT7Qm+qSexgmXuXpe+WaLCJDWM5uOlvxp5tbtK2KD3SNtUDrOJQYfWYBOAPrBMBnSpDr8Ie7/wlJBxXCfROk1TldOU3s5O+5OnFfTDS9rAdcWdZdJ+Bt0aktnpuHJpjdurFca5o8ne5SRwYtGk6mNinCYRcnwMApZ9Y7IxvC9xzOi1QIhoOepMrotRkVJtbrXiclN5cI+P/nU8LaGwM4AEJtO3L8zY5QK30SZ/Tsz20Qo8HHGdIBLhHbhTALrFe8+n+Egda66Vr1DkKgDERW59PeWBd6xHCRGNuAk2ZzUmuiN5DJmWgacAGy9QblMMjhOIGKgiqsd4jx/8wC8FoyxBSstGFajahL2C6oFzCpbp5NiS185znN0ohJXqQzkp5RbcBliSYUZgHC8D1jDGxzcTksD2Hgh2NIAlJOStsfB3fUb6hWIFzxim0lyP9kFM5y92Sf5B1/h6PeHKOi1CMC5RFAEKhoyM4W1W+NxASJeT/NptTehcrjBPxLVKBPh/qgMcuNYNk34EB0asELalYBJ5cxzt31LLiLE/uDxCydXiSk7ACho7LxNffcUUakEwwsJDmjFiCscu83TfZq2vw5/2bgOzUng4XGDBgYwwr/KEHueGX4Keg255R3KqxyiMSKDi4CUEtYShjSsSYwU62rdogOQu20N3HGVn+/CksqKky7GoD958d4PwT5MGJwQhp8EjemBomDxTKNsO+C4moMNZpAEBtPlP65Lc1cfcaLlaFrwP4VtYHLXXBIvMzCC+
PGDATABASE: AgCCkY7AUaoy2V+fRXrEeLODlHOTXWXmWCW6MBWEY1J32QrN0bWUmwDdTxv5KHchbhH8lra9bABNOGfRcz59GIg8fH3fwTWOE8luh9cD50QkphjZPe9eGXc6YzheG0CG5hDnUoiJjnP9/l5cZc6sRxAo7for/bbLa0zja3VMzI+NMhVVRZT01G5R/Aoyf+B/TGm4mYbMyWAIgEEfjl50yIkc4WscfQrRkbxAtBF2qFuS3OL95TYSRULBAt0f3Z2WpCdS2b/pUyHJuuoi8aTo1a9QLFMrUdxVi6ydIKaMcx8xR8DlXQLOOdtIQu4TrgzGX2MgHwrbWuf/SFO5IWB/6/JI3yubo+i88M9LwPKsGeslcquoBG3Ibqlnmw8pcPrXUwBq2BowjAqpGsxdiR5XIi2j8QnpA8dTmFARX9CWKHoXFH5+uxx7SSTPG+izlGtVspsu5xx3F8MZ6eStInCyBimTVrn74+IvMPEBrj7wThO6Bl9EA3POkTRf6AmjuPItTgZK8lfXY/t0qDN5zApeB051+jSGZ0/o4PaY414vCm/+OteuCAI4ooCpDOwG3QD52VtpmoAvGjtuWExrvCHMW+hTIxsNbYJ+2SE1oQy8n8J5kKK+AU/SnYf/VEpbawHrpU48g6sDUHQzzPhoLN41j67qopmfRZAo1r5Tb4n7MnEOF3Yi7aT3lE6JvB3gZUSRqnDYSWObTg==
PGHOST: AgCWDPCQ4P+vPKQXmzNspODUJYVidwQDzFRxY8JDj5JYW1u+2xK8LqE2uWWYCW3YjF+H6yJoH6gu35KqOtjm0E23zMlknwZwkK+L93J/nrnNZHCznoub9jEzaAsTRhytvuIUBPQnFulP/t9Q04RjmR9c14puS7VS/tM57/cLq5zq/BiSYL3Wx2lblE7Xn6k44+8robPP3YkmlOuqziM1li/qevB/jxRV9YFjIpCz6D7WG6Kkx9CA6fzgalMJ5ErUVTJOuLDDty3qKd+9mg4WCLahjyzhPq/rIPUFE77EBDCulnnlMyvOSPSP7pMzkaNR1Ce3cOxOYAZ5mO2u5Y5pXt34V8iPe87N85KHQNZTu1Mu5ELMLdhEYOlO5ZX2x/RsdEuriWz1NW8MC57pEUGE/XrFhDe6x80eHi++qDRat2d04rTBOtlceZMmPVxs8tTa3VaD4PepekSogddLVooscLL7lYIpyR0Q6qOA1NdF2uOpx7hf6QLY1HeD4V8RSVVxV9uK5lUTrnBjtU/aUwnGs0xKxVNdBEKwG5Kh7qdsgyBiEa9V4Y2ElteGHave4J7xzimdASrbgMnlgIfcMuo94eX/0M0BAmpD4bEByMCWbcFgAfNnIOpXLZvoEfZ3DxVysmCzD+0nq+CEatdOjKp11EKbtf3H4PgnKqWDe2p8FNPXhev60CMhFvXS/QYg9fe2YJt/wqcN5MstCej4IuiOJkuFJ0UhZ/F5760xhuPYCUWP1suIVZM=
PGPASSWORD: AgBH32G+EUtc3jzGCA9bf27TCbzgK9xz+r4dqd0QQJL9xHbqgOARGVVaQ88AOkWV5VgYjqc/GFp51jLzVOHxgLdkqO/oCBuX9ajQEoGfq24AxFnaB7fh+Vlc3/N9yhT8lWoxHmHjyMVeX75g/9KvhNaRKBgiWQNHlt1C2FNh1h3U/aMfWVJIENmKKH2A5sxWe5haB7nynZc9r1QXBQKa7XVpuxAFXDHz3j3cFyR5Qflp+ac2APEM1/xbiaZDgkBtBd6dsDoCP56Dr1m91kaRGgbeX6WmRJ/Y89WAp4yt3QVfa8uGL1+DrBBMcfB1nAQKA45eZjPE6zTOEHxgTETCcmXJQiOzttDmBHRkIClOLLipgGDJwMqtgQoEMoJKjXMC0rsRy0NVRmibZa310R3PQjuHrQXxRD9ZAXkYg3opwLKeKi07b/7mvLHr7hU81fkBGnqNm/6heOSAqDZfRdregbBbcI/go72aypn2vQ5R+ozCdfwcp1tGla8FGpkI+zAdBKihp5Yo21VZ83FlIMq2JHF2+tv58C+LFeyqL1nr6BUmGKUQ+lEOnRzGYo1sbO5wBChc6yP3ZbzZYfxfvXAdfDY7vZUsareOC4uyR1wDnIiJgQ4kqmAKf7HulJJatKNgsvbmukj7c6lHLsfFRg5pwLO6iese9TZgtima2wkdcRpHSdt4ycnyHbwrEZ4kepfFlN1pGUl573/3l2cOdzO+WLCqV96P5myL6OOmCTxOaLdSyA==
PGPORT: AgCXyGjhlTcq3ffD+ZZZxe5gvqRLQl2MYGl7SfJDjw4LMdr3iojAeQNdYZIeZN4Bec9thhz1DI/Bc5Iiw5TiB3MAAvl/XtQM/T23JrSlUsfqECuHKQGw5kkgeVCds4j4d/IHFt9yBv4W4+ogcL5TZIGGgMiKa/99T77xgE4OqjeqqC+bpFuLObiKt5sYcqcHl2DDshTy4xeukfdA2yI3N9Tq7zfbLpZUKHWWe1gE+FbA0s+QA1ZCYv9uEtu/E5BWOYxE0u4GKhMDfMpguks0CNnIoRpovY3vmOxzFtqa7RpPoQrQtEN2Xtizu/G8K8p+mZLQ0cf3KX0rwp8tAsVKWrp8FYOy6+2OLYlhmDl1hK+M15czaL60DVBqiRIlQFdj9K+s5KQ0qfsG9m4v2WPSeCLEKwcsyLyq9vzXbDKwcMN2DOMOan8VDo04UZzkfdZa3lztfw7MWIdpvB0+cpgK3mdbbPCqSIQ8UTjeSVBgEz4EPUds81W8gqAgmeVKpUQplgFuLNwCTnCkuMSNiA93D3dgGccXzXiDrIBIcLzxHAWr0XEjISyD/pmNEowbDvXB5yRlNi1ZB5AHsRPurUYs4XtZN5ar+sxyex78tG18OkcBbABatBp3ol28Rs1LEN+HJupzNl4XDUx35/j3t/FPcw9PkcF+hzaQL7aWj4EDEWfjlzz5FEBlU5N6sd078tB79TpasuIk
PGUSER: AgDH9oSzu61NVOUlK7Evr278VuOx7ZxZgdsk+kdJmwpBGX7r5gmPrdomh/mqLYTuLokkanFiTfchRWHc76FvjbA/KxqwCq1qsZbW+dXrRtx/z1wQApKxNUJ7JolwMwP7tHE6QlGzO2mWj6RUROnhKpNybJXVvC3E5sSyz2QWC9hjamQP997RGA9yiiT/OShC7I6drFYR5cRDtpjW7Sy46qhMwlCRppiKh3wOV7qIAa0aPQE3Rfcg2WpK2ugRL1N+SiVnM+wPQwYVLiDaVF40vP40Kari99hIgmhcbjPeGG3kGX5VLww9KGm7iryrW3Yx45L/CCh1arUUpjkK2FGLVKtb3+YmDadnOA/I8Rr5kebhoMc93E3U3+mDfQA3cO/23xgpOJEGRCQwBlN9mazqkdq4zQkb4+nuxsdyQcxYtncgxhfCcZ0mXnbX2aW2kYcxKqa/jNjBcEpGMvos7dq6QzNq2nHrITo15S74M0292CAje2NFvKURA/KZnT26dDw3e5xa74E1nI/tBJEHWrUwRXpPu7naCZ2sZMxQV6ixQMuDakx3YamXZmMwgFO2FZ6ZL9BDDsbV4+JAsNwEaHGIIaTbE28R/xPIcUqcxrQV4ZWmHnJXFGyJ0XXxJ57GGjs7QwvvzAm+9WGYtlSC6H/8rX8uZIQLr3llVbJMuLpIv45i3p0Nkx8jyxGSG3rNQ4l3K0rjly2qZg==
S3_BUCKET: AgBcx2UvWafkVQ4fc+Xuc+gCLm5O5DceYSYBslL1bd8p4hKI/2hJF9z9UoLyAedyyrx8pHizcugkcIccrV1iyfQod2lDrivVJCy3qHz0mrQ6ZCOAk9ApNJTYUn+x/AYZL9EKVj/vfEzSwOTqlri6H53aUrZr8lv01TqLcrZDeG+jv64psydYKmSESkPl0iQ9DOx2sGkowNYbiTjux+ED9yXDMDdzojhMepbuUHhjNr7V7Z2NpX8+pNVz2o8o/oIA0zAJs3+C02018N3cyJ9P9BP2/qR6N31aykyI4P6GU5WlL0CDGKaheYy9ukM5x8SoU87yZBHLUxN0MhrMVKoFswU6CwTG/A8Gjkp84ce2cvlnuXP6JEMlqgSb+O+SeCH8+kwL9A87xmb42OOXSGokS188/2/13b6S733WL81B0RX1X1pOfWybpJzDhgiOC3Pjn18ItVHjKw3FlY6kwk1+P1vbZoRl343avRdyQyJam28A9UvZeTG+ac7drRTDndKYKGP8IWg/A32MEFSiKHsvnRQoYE7KORyzJxp610L1+w46KOUF5VF2afch02Jt4uLcmCOyUb6LdcWln3Jiz+wydJI1HK1RPio5oUT5d5se3K3DCa+GffbPMorHe/SdzqaBH2+uBcQn+wZO7JC1ei7hz4U1xdV41gkG1uq7Xz49ymW6P7G6qUr65MtvD73iMRlnJt/mdkw5UQ==
S3_ENDPOINT: AgDA5n96LeW1spJfmm7f9lcus5Ndv/91HAlhOfv0YwP+9R8rQhKF1sEL9Oi7Fpd4VJCQi9vDbeWYjGOMtsMqsLJivcZK6367rdSqL/YpKax9SkDgU+UG5Bpr5SDv4p5C3/J4+GPkZV+BduJQlNVPycTrdM80VBK8aALCNs7gGxy68v6mMgI90MpTp84ZeWgtJ7ZpTySivpwgycwcezldJTYDDjOvVfbK79trsRzDtjbAZzbDn0M8At4LYAfY7JTqcdCRHSGnzyg+81CX2jjyMOH0K55SsIqPEBdXqvh+VmC+jPyFMzfAN5hA8+otWTXfI7VucxAMZtRUiLU3I4/kIO60OkVjEf/SWrJv3nKb85aVfvRZ9k/A7kJ/ysKTXz2/iSAHU1DHTJlMW7SfhXciotx1p3BWOREF0QAQvrNCURFP+eZogBCIuiP38fD0gHkhG2BZkAY/OVZTr17a3F02kwemAuJ85hgUf0iwFV+/LD6X2OiqM85lnac/3B5Qp7UQf+Enn5RTqd90Pk/7QtAf/zTDmfxiWTkwpKXeQ62xcnHL9dQnUmDDs16eJZd04AJGgT8yrC//2lVOht7u6KuyG/+JXRxLBXAkGkr68lHBBuGmeVZ/t7ChL2Asyfu/uUTl9E1BOUfNvZXxwyLgqueL0Uw/MGLgswBsP6pYNGraMF+K5v7dse8cUxpyqk3s1C1zqoAhkehsCBtTjI+hF90G9Nh6mVSocoH12znt7fgUnwNbpg==
S3_KEY: AgAiciTM2ZNVlU1M1CNNXLkhCEYYbO7q5+Mp/DoC4OHBgIDKVfHurH39Dniuwxe6DcvE3vG2glRyTxQEg/ASLcwa7HBwBAwXe3wl1tRGM5Bp40/Vq935BXpkhcdp2fSoup8lPEbKS8q+L5LOqUlx7jmnkHXbI1tasz63KE8O9RUFDdQ8Gxy3nn/u4xkvibYxwmo60ApLKYgOu/ODPEETrWBcITHAVFUxbA8Kr9X9mPm3VpfrnFcUlxsCFr/zZwE/Y01eWdi8GGafb+apDPKMd7mAsLHFcPIQlpkHVT1M21qwwntZg9yV0RBACNu5BVPUgbmtUOQeWYMXn3FE+NJ7ajfdKAUCcEUV/f4s00b0S7jJTJwOUixDquMKSfu00AwDRCs8UcouikZe110uWnfEF3tVE0xQGF/3ItLni9VugBz7wQv7ACvmwnHmX5ZcjE0hxYcIS7ABWgHOZxgWoRWPao8eNAATipafcVIG1szl5ZMNTmAqHFyp2dlNU3zaiW6fz4q4CU7SrlhsrtqYM788qHvpJvDpFdF/i6oitH9CgpwmdCpH6YbBXxatnkWq9bqjEFcSZGDfDyT+iZaoPwhiOfaEoCyKlZ9RLLaK3E8zFcCDRXHnvnkqPtP/+VG30xz9pIat2EVB1N4b/kVIrr+fIM28mwk0vkC/tU8T55GF5BZr7VaYedHM9DVcQ4OJl7Ctrc9Ki8PXrne8gywyomA0F+YY9lxdDw==
S3_REGION: AgAAHTbNQ3gGnvg67ck2N5zSKKhMwR1j6pi/tZzYMEPK8jSnDTBkLYAt6ZVRtdsO+dG9kjnMsc/xTUMxJspbvQkgLSd9mG5FzJ37rBn+azCCSTDYBKq2ddGK1Yf/9w7MxOgN8aCyD4QCFOzR0EI49GbVYQynxDD5BwYuf7y4t2xCYt5wRGsjyNAmH3202Z90XKUkts8Na1hyD+xrrtrAtNfugyZqKo2WUSsHu82TD+cu5xZI51oQ9w9Mh9LaH3nfn/X5S+t17TjYvI7/c6hOwCVv10OdoaZa+SzqOvy7XxnqAShAYkPqJKfWhjecE1b9c/Cun32X4MRI0GBWyA02z4nR+WBbaVmasicx6hchVn8/wZeKMIl68F5LE7184MKKPNNwqsYslwFhuWq8dEw3TaVvnWgx3+cSMiX15SBwcLtE2UzJp+jjN/dpQ2MM0+6uV1GK4mNso5JAwGpUUUi2i+V1Ng7uXipI+5J9w6K0IMg1puGqFyahby42saSuH6vuPnjSx+2dXQTlgbl2SvCBoCgyOOJs4q5IafEvupAmRCNzx2HHv8/z6CFbSQZITQ3plmyNGLFXjynVw/6Q1PD4z3Pows4uVcYOEPbC0UoaXVgwgdBWa2N44BUhpdbqJUCyKuapLigpjKujG43jmdLzuk6gaPeH7SJTZKr624vs9hrGhzQYKdl6FZOQhmCFRDKXVCUiH2Z2pfwd3oo=
S3_SECRET: AgCcVQ7YtBAGpKBm+rE/hQBHrFlX5O0JO94xkZeoAppA9Tf8YR/PguZRGBWgLdNEJRI8C08lRRCUX3PY68jTySyjamb32iQkslOXGjAfnULeNGoGg05nLY2ZDYCEom6ieL8cc2xfbrV3yHoPQ7yVz9vcLjh1vATxyfdkqMapl8FpvQf0k0Zecmw3rLWE9y6vAn6Gb+/CWTnuhcW/8uDykmjIBTDQQddWshaZi+HosHyDbNxlnGj4U8mie68wytpS+Unp1gIWWE0hvelqO/3OUEEBB1OYMLV2DW8v86HXAE1Ix9jiCpSbyB+UzjOlrE/p4fJpeG4FtUC+/5ibRSxxgQRQYklKFJmdRDYWUnOngjgcT/Ewe41mTrpCUvb+jtir68pYLmVrLoha7S60w1YQHNkDAN2GftOyBjkkt6MtUDNzvNkfnKqKGUWyDSC27yfJdE/9k/4lDxQs0Sp20kIuz66/culBpg/s/oPSNs4SolCqG3GVLlKL775uqwLLuDN3txlPLb+Ex5vZAUapke+rn2zXzJVc1qlPfI/96vSEy6cx58LXdBadmBXn6c4Uy2MDa66EwsxOMXxzGLTd7AGkd5oeQVYfVPdTfGV5zx1AdzQhP3u/DD5FhKeWGDOr21iYB2jNm/P/hw0nFP2pf83W4/jLzPvuth1LF/WLF8cjclnGbcep2Kxrh/Xq0LmufofuVJyEI9/fl6onl5KIa6ZnVBJ8TsQesXJtNEKt9cPHiCvBKfLj5C+a4FlY
template:
metadata:
name: forte-drop-secrets
namespace: forte-drop
@@ -0,0 +1,37 @@
apiVersion: argoproj.io/v1alpha1
kind: Application
metadata:
name: forte-drop
namespace: argocd
annotations:
argocd.argoproj.io/sync-wave: "1"
# notifications.argoproj.io/subscribe.on-sync-succeeded.slack: ""
# notifications.argoproj.io/subscribe.on-sync-failed.slack: ""
# notifications.argoproj.io/subscribe.on-degraded.slack: ""
labels:
app.kubernetes.io/name: forte-drop
app.kubernetes.io/part-of: apps
app.kubernetes.io/managed-by: argocd
finalizers:
- resources-finalizer.argocd.argoproj.io
spec:
project: default
sources:
- repoURL: ssh://git@git.forteapps.net:2222/Forte/forte-helm.git
path: forteapp
targetRevision: HEAD
helm:
valueFiles:
- $values/forte-drop/values.yaml
- repoURL: ssh://git@git.forteapps.net:2222/Forte/helm-prod-values.git
targetRevision: HEAD
ref: values
destination:
server: https://kubernetes.default.svc
namespace: forte-drop
syncPolicy:
automated:
prune: true
selfHeal: true
syncOptions:
- CreateNamespace=true
@@ -0,0 +1,33 @@
apiVersion: v1
kind: Secret
metadata:
name: keycloak-client-forte-drop
namespace: forte-drop
labels:
keycloak.forteapps.net/client-config: "true"
annotations:
keycloak.forteapps.net/source-namespace: "forte-drop"
stringData:
client.json: |
{
"clientId": "forte-drop",
"name": "Forte Drop (web)",
"enabled": true,
"protocol": "openid-connect",
"clientAuthenticatorType": "client-secret",
"standardFlowEnabled": true,
"directAccessGrantsEnabled": false,
"serviceAccountsEnabled": false,
"publicClient": false,
"redirectUris": ["https://drop.forteapps.net/auth/callback"],
"webOrigins": ["https://drop.forteapps.net"],
"defaultClientScopes": ["openid","email","profile"],
"secret": {
"namespace": "forte-drop",
"name": "forte-drop-oidc-credentials",
"keys": {
"clientId": "client-id",
"clientSecret": "client-secret"
}
}
}
@@ -0,0 +1,7 @@
apiVersion: kustomize.config.k8s.io/v1beta1
kind: Kustomization
resources:
- forte-drop.yaml
- keycloak-client-forte-drop.yaml
- forte-drop-pdb.yaml
- forte-drop-secrets-sealed.yaml
+8 -2
View File
@@ -2,6 +2,12 @@ apiVersion: kustomize.config.k8s.io/v1beta1
kind: Kustomization kind: Kustomization
resources: resources:
- ../../base - ../../base
- forte-drop-postgresql
- forte-drop
- forte-drop-mcp
# No patches needed — base already has "upc-dev" paths # No patches needed — base apps already default to "upc-dev" value paths
# upc-dev is the default/base cluster # (upc-dev is the default/base cluster).
# forte-drop (postgres + web + mcp) and dbunk-demo are upc-dev-only apps — their
# values hardcode upc-dev hosts (drop.forteapps.net etc.) and must not sync to
# upc-prod, so they live here in the overlay rather than in apps/base/.

Some files were not shown because too many files have changed in this diff Show More