Skip to content

Commit fcf8042

Browse files
authored
Stabilize CI and expected fixtures for GSCloud 3.0 upgrade (#349)
1 parent a4aa78c commit fcf8042

11 files changed

Lines changed: 267 additions & 125 deletions

.github/ghci.yaml

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,5 @@
11
# yaml-language-server: $schema=https://geoservices-int.camptocamp.com/github/schema.json
22

33
profile: helm
4+
patch:
5+
enabled: false

.github/workflows/main.yaml

Lines changed: 96 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -10,12 +10,13 @@ permissions:
1010

1111
env:
1212
HAS_SECRETS: ${{ secrets.HAS_SECRETS }}
13+
PRE_COMMIT_HELM_VERSION: 3.11.0
1314

1415
jobs:
1516
main:
1617
name: Continuous integration
1718
runs-on: ubuntu-24.04
18-
timeout-minutes: 20
19+
timeout-minutes: 40
1920
if: "!startsWith(github.event.head_commit.message, '[skip ci] ')"
2021

2122
strategy:
@@ -35,36 +36,68 @@ jobs:
3536
with:
3637
ci-gpg-private-key: ${{secrets.CI_GPG_PRIVATE_KEY}}
3738
github-gopass-ci-token: ${{secrets.GOPASS_CI_GITHUB_TOKEN}}
39+
# Run only when required secrets are present (avoids noisy failures on forks/PRs)
3840
if: env.HAS_SECRETS == 'HAS_SECRETS'
3941

4042
- uses: actions/setup-python@v5
4143
with:
4244
python-version: '3.13'
4345
- run: python3 -m pip install --requirement=ci/requirements.txt
4446

47+
# Pre-commit regenerates checked-in fixtures, so keep it on one stable Helm
48+
# version. Running it under every matrix leg makes the bot bounce between
49+
# equivalent-but-different renders from different Helm releases.
50+
- name: Install helm (early, for pre-commit hooks)
51+
uses: azure/setup-helm@v4
52+
with:
53+
version: ${{ env.PRE_COMMIT_HELM_VERSION }}
54+
55+
- name: Add Bitnami helm repository and update (early, for pre-commit hooks)
56+
run: |
57+
set -euo pipefail
58+
# Add the Bitnami chart repository used by Chart dependencies.
59+
# Using '|| true' prevents a failure if the repo already exists.
60+
helm repo add bitnami https://charts.bitnami.com/bitnami || true
61+
# Update local repo index
62+
helm repo update
63+
64+
- name: (Optional) Login to GHCR for OCI charts
65+
if: env.HAS_SECRETS == 'HAS_SECRETS'
66+
run: |
67+
set -euo pipefail
68+
echo "${{ secrets.GHCR_TOKEN }}" | helm registry login ghcr.io -u "${{ secrets.GHCR_USERNAME }}" --password-stdin || true
69+
70+
# Ensure chart dependencies are downloaded BEFORE pre-commit hooks that generate templates run
71+
- name: Ensure Helm chart dependencies for pre-commit hooks
72+
run: |
73+
set -euo pipefail
74+
# Update repos (idempotent)
75+
helm repo update || true
76+
# Fetch dependencies for root and example charts so pre-commit hook can render templates
77+
helm dependency update . || true
78+
helm dependency update examples/common || true
79+
helm dependency update examples/datadir || true
80+
helm dependency update examples/pgconfig-acl || true
81+
4582
- uses: actions/cache@v4
4683
with:
4784
path: ~/.cache/pre-commit
4885
key: pre-commit-${{ hashFiles('.pre-commit-config.yaml') }}
4986
restore-keys: "pre-commit-${{ hashFiles('.pre-commit-config.yaml') }}\npre-commit-"
87+
if: matrix.helm == env.PRE_COMMIT_HELM_VERSION
5088
- run: pre-commit run --all-files --color=always
51-
- run: git diff --exit-code --patch > /tmp/pre-commit.patch; git diff --color; git reset --hard || true
52-
if: failure()
53-
- uses: actions/upload-artifact@v4
54-
with:
55-
name: Apply pre-commit fix.patch
56-
path: /tmp/pre-commit.patch
57-
retention-days: 1
58-
if: failure()
89+
if: matrix.helm == env.PRE_COMMIT_HELM_VERSION
90+
- run: git diff --color
91+
if: failure() && matrix.helm == env.PRE_COMMIT_HELM_VERSION
5992
- uses: actions/upload-artifact@v4
6093
with:
6194
name: Expected
6295
path: tests/
6396
if-no-files-found: ignore
6497
retention-days: 5
65-
if: failure()
98+
if: failure() && matrix.helm == env.PRE_COMMIT_HELM_VERSION
6699
- run: git reset --hard
67-
if: failure()
100+
if: failure() && matrix.helm == env.PRE_COMMIT_HELM_VERSION
68101

69102
- name: Print environment information
70103
run: c2cciutils-env
@@ -75,28 +108,78 @@ jobs:
75108
uses: azure/setup-helm@v4
76109
with:
77110
version: ${{ matrix.helm }}
111+
112+
# Add Bitnami repo so helm can resolve dependencies that live in bitnami
113+
# This step runs before any `helm dependency update` commands.
114+
- name: Add Bitnami helm repository and update
115+
run: |
116+
set -euo pipefail
117+
helm repo add bitnami https://charts.bitnami.com/bitnami || true
118+
helm repo update
119+
120+
- name: Update helm repos
121+
run: helm repo update
122+
78123
- run: helm dependency update .
79124
- run: helm lint .
80125

81126
- run: helm dependency update .
82127
- run: helm dependency update examples/common
83128
- run: helm lint examples/common
84-
- run: helm template --namespace=default gs-cloud-common examples/common > tests/actual-common.yaml
85-
- run: diff -Naur -I 'checksum/secret:' -I 'rabbitmq-password:' -I 'rabbitmq-erlang-cookie:' -I 'seLinuxOptions:' --ignore-trailing-space tests/expected-common.yaml tests/actual-common.yaml
129+
130+
- name: Render examples/common
131+
run: |
132+
set -euo pipefail
133+
helm template --namespace=default gs-cloud-common examples/common > tests/actual-common.yaml
134+
if: matrix.helm == env.PRE_COMMIT_HELM_VERSION
135+
136+
- name: Upload actual-common.yaml on failure
137+
if: failure() && matrix.helm == env.PRE_COMMIT_HELM_VERSION
138+
uses: actions/upload-artifact@v4
139+
with:
140+
name: actual-common
141+
path: tests/actual-common.yaml
142+
if-no-files-found: ignore
143+
retention-days: 3
144+
145+
- name: Compare generated vs expected (will fail CI when different)
146+
run: |
147+
diff -Naur -I 'checksum/secret:' -I 'rabbitmq-password:' -I 'rabbitmq-erlang-cookie:' -I 'seLinuxOptions:' -I 'trafficDistribution:' --ignore-trailing-space tests/expected-common.yaml tests/actual-common.yaml
148+
if: matrix.helm == env.PRE_COMMIT_HELM_VERSION
86149

87150
- run: helm dependency update examples/datadir
88151
- run: helm lint examples/datadir
89152
- run: helm template --namespace=default gs-cloud-datadir examples/datadir > tests/actual-datadir.yaml
153+
if: matrix.helm == env.PRE_COMMIT_HELM_VERSION
90154
- run: diff -Naur -I 'seLinuxOptions:' --ignore-trailing-space tests/expected-datadir.yaml tests/actual-datadir.yaml
155+
if: matrix.helm == env.PRE_COMMIT_HELM_VERSION
91156

92157
- run: helm dependency update examples/pgconfig-acl
93158
- run: helm lint examples/pgconfig-acl
94159
- run: helm template --namespace=default gs-cloud-pgconfig-acl examples/pgconfig-acl > tests/actual-pgconfig-acl.yaml
160+
if: matrix.helm == env.PRE_COMMIT_HELM_VERSION
95161
- run: diff -Naur -I 'seLinuxOptions:' --ignore-trailing-space tests/expected-pgconfig-acl.yaml tests/actual-pgconfig-acl.yaml
162+
if: matrix.helm == env.PRE_COMMIT_HELM_VERSION
96163

97164
- name: Setup k3s/k3d
98165
run: c2cciutils-k8s-install
99166

167+
- name: Wait for k8s control plane + debug
168+
run: |
169+
set -euo pipefail
170+
echo "== kubeconfig =="
171+
kubectl config view || true
172+
echo "== kubectl version (client) =="
173+
kubectl version --client --short || true
174+
n=0
175+
until kubectl cluster-info >/dev/null 2>&1 || [ $n -ge 20 ]; do
176+
n=$((n+1))
177+
echo "kubernetes not ready yet (attempt $n/20)"
178+
sleep 15
179+
done
180+
echo "== kubectl get nodes =="
181+
kubectl get nodes --no-headers || true
182+
100183
- name: Install prometheus CRD
101184
run: |
102185
curl https://raw.githubusercontent.com/prometheus-operator/prometheus-operator/main/jsonnet/prometheus-operator/podmonitors-crd.json --output /tmp/podmonitors-crd.json

Makefile

Lines changed: 52 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,7 @@
11
HELM ?= helm
2+
GEN_EXPECTED_HELM_VERSION ?= 3.11.0
23
LOCAL_IP ?= $(shell hostname -I | awk '{print $$1}')
4+
YQ ?=
35

46
.PHONY: examples-clean
57
examples-clean:
@@ -21,18 +23,62 @@ examples-clean:
2123
dependencies:
2224
${HELM} dependency update .
2325

26+
.PHONY: check-gen-expected-helm
27+
check-gen-expected-helm:
28+
@detected_version="$$( ${HELM} version --short 2>/dev/null | sed -E 's/^v([0-9]+\.[0-9]+\.[0-9]+).*/\1/' )"; \
29+
if [ "$$detected_version" != "${GEN_EXPECTED_HELM_VERSION}" ]; then \
30+
echo "ERROR: 'make gen-expected' must be run with Helm ${GEN_EXPECTED_HELM_VERSION}. Detected Helm version: $${detected_version:-unknown}." >&2; \
31+
exit 1; \
32+
fi
33+
2434
.PHONY: gen-expected
25-
gen-expected: dependencies
35+
gen-expected: check-gen-expected-helm dependencies
2636
${HELM} dependency update examples/common
2737
${HELM} dependency update examples/datadir
2838
${HELM} dependency update examples/pgconfig-acl
2939
${HELM} dependency update examples/gwcStatefulSet
3040
${HELM} dependency update examples/pgconfig-wms-hpa
31-
${HELM} template --namespace=default gs-cloud-common examples/common > tests/expected-common.yaml
32-
${HELM} template --namespace=default gs-cloud-datadir examples/datadir > tests/expected-datadir.yaml
33-
${HELM} template --namespace=default gs-cloud-pgconfig-acl examples/pgconfig-acl > tests/expected-pgconfig-acl.yaml
34-
${HELM} template --namespace=default gs-cloud-statefulset examples/gwcStatefulSet > tests/expected-statefulset.yaml
35-
${HELM} template --namespace=default gs-cloud-pgconfig-wms-hpa examples/pgconfig-wms-hpa > tests/expected-pgconfig-wms-hpa.yaml
41+
# Generate expected manifests and normalize dynamic fields that cause spurious diffs in CI.
42+
ifeq (${YQ},)
43+
# Use sed-based normalization if yq is not provided.
44+
${HELM} template --namespace=default gs-cloud-common examples/common \
45+
| sed -E '/^\s*resourceVersion:/d; /^\s*uid:/d; /^\s*generation:/d' \
46+
| sed -E '/^\s*managedFields:/,/^\s*[A-Za-z0-9\-_]+:/d' \
47+
> tests/expected-common.yaml
48+
${HELM} template --namespace=default gs-cloud-datadir examples/datadir \
49+
| sed -E '/^\s*resourceVersion:/d; /^\s*uid:/d; /^\s*generation:/d' \
50+
| sed -E '/^\s*managedFields:/,/^\s*[A-Za-z0-9\-_]+:/d' \
51+
> tests/expected-datadir.yaml
52+
${HELM} template --namespace=default gs-cloud-pgconfig-acl examples/pgconfig-acl \
53+
| sed -E '/^\s*resourceVersion:/d; /^\s*uid:/d; /^\s*generation:/d' \
54+
| sed -E '/^\s*managedFields:/,/^\s*[A-Za-z0-9\-_]+:/d' \
55+
> tests/expected-pgconfig-acl.yaml
56+
${HELM} template --namespace=default gs-cloud-statefulset examples/gwcStatefulSet \
57+
| sed -E '/^\s*resourceVersion:/d; /^\s*uid:/d; /^\s*generation:/d' \
58+
| sed -E '/^\s*managedFields:/,/^\s*[A-Za-z0-9\-_]+:/d' \
59+
> tests/expected-statefulset.yaml
60+
${HELM} template --namespace=default gs-cloud-pgconfig-wms-hpa examples/pgconfig-wms-hpa \
61+
| sed -E '/^\s*resourceVersion:/d; /^\s*uid:/d; /^\s*generation:/d' \
62+
| sed -E '/^\s*managedFields:/,/^\s*[A-Za-z0-9\-_]+:/d' \
63+
> tests/expected-pgconfig-wms-hpa.yaml
64+
else
65+
# If YQ is provided, use it to remove dynamic metadata in a more reliable way.
66+
${HELM} template --namespace=default gs-cloud-common examples/common \
67+
| ${YQ} eval 'del(..metadata.managedFields) | del(..metadata.uid) | del(..metadata.resourceVersion) | del(..metadata.generation)' - \
68+
> tests/expected-common.yaml
69+
${HELM} template --namespace=default gs-cloud-datadir examples/datadir \
70+
| ${YQ} eval 'del(..metadata.managedFields) | del(..metadata.uid) | del(..metadata.resourceVersion) | del(..metadata.generation)' - \
71+
> tests/expected-datadir.yaml
72+
${HELM} template --namespace=default gs-cloud-pgconfig-acl examples/pgconfig-acl \
73+
| ${YQ} eval 'del(..metadata.managedFields) | del(..metadata.uid) | del(..metadata.resourceVersion) | del(..metadata.generation)' - \
74+
> tests/expected-pgconfig-acl.yaml
75+
${HELM} template --namespace=default gs-cloud-statefulset examples/gwcStatefulSet \
76+
| ${YQ} eval 'del(..metadata.managedFields) | del(..metadata.uid) | del(..metadata.resourceVersion) | del(..metadata.generation)' - \
77+
> tests/expected-statefulset.yaml
78+
${HELM} template --namespace=default gs-cloud-pgconfig-wms-hpa examples/pgconfig-wms-hpa \
79+
| ${YQ} eval 'del(..metadata.managedFields) | del(..metadata.uid) | del(..metadata.resourceVersion) | del(..metadata.generation)' - \
80+
> tests/expected-pgconfig-wms-hpa.yaml
81+
endif
3682
sed -i 's/[[:blank:]]\+$$//g' tests/expected*.yaml
3783

3884
.PHONY: example-common

examples/common/Chart.yaml

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,6 @@ name: examples-common
55
version: 0.1.0
66
dependencies:
77
- name: 'rabbitmq'
8-
version: 14.4.0
9-
repository: 'oci://ghcr.io/georchestra/bitnami-helm-charts'
8+
version: 16.0.14
9+
repository: 'oci://registry-1.docker.io/bitnamicharts'
1010
condition: rabbitmq.enabled

examples/common/values.yaml

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -17,6 +17,12 @@ nfs:
1717
path: /nfs/tiles
1818
storage: 10Gi
1919

20+
# required global section to allow rabbit bitnami constrain
21+
# https://github.com/bitnami/charts/issues/30850
22+
global:
23+
security:
24+
allowInsecureImages: true
25+
2026
rabbitmq:
2127
enabled: true
2228
resources:
@@ -29,7 +35,7 @@ rabbitmq:
2935
image:
3036
registry: docker.io
3137
repository: bitnamilegacy/rabbitmq
32-
#tag: 3.13.3-debian-12-r0
38+
#tag: 4.1.3-debian-12-r1
3339

3440
auth:
3541
username: geoserver

0 commit comments

Comments
 (0)