Skip to content

Commit a90b1cb

Browse files
authored
fix: support staffbase-application Helm chart image field shape (#139)
* fix: auto-detect image field type to support staffbase-application chart The staffbase-application Helm chart splits the image into a mapping: image: repository: registry.staffbase.com/sb-images/app tag: dev-abc123 When gitops-github-action writes the full URI as a scalar to spec.values.workload.container.image, the kustomize patch replaces the mapping with a string. The chart then renders 'image: :' — both .image.repository and .image.tag resolve to empty. Fix: before writing, read the type of the target field using yq. - If the field is a mapping (!!map), write only INPUT_TAG to .field.tag - Otherwise, write the full image URI as before (Apperator pattern) Callers specifying spec.values.workload.container.image get the right behaviour automatically based on what is already in their overlay file. No changes to cicd.yml required. Backwards compatible: all existing Apperator-style callers have scalar image fields (!!str) and continue to receive the full URI unchanged. Assisted-by: pi:claude-sonnet-4-5 * refactor: handle all image field shapes via explicit and auto-detection Assisted-by: pi:claude-sonnet-4-5
1 parent da1135d commit a90b1cb

3 files changed

Lines changed: 56 additions & 1 deletion

File tree

scripts/lib/gitops-functions.sh

Lines changed: 11 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -36,7 +36,17 @@ update_file() {
3636
echo "Check if path ${file} ${field} exists and get old current version"
3737
yq -e ."${field}" "${file}"
3838
echo "Run update ${file} ${field} ${image}"
39-
yq -i ."${field}"=\""${image}"\" "${file}"
39+
if [[ "${field}" == *.tag ]]; then
40+
yq -i ".${field}=\"${INPUT_TAG}\"" "${file}"
41+
else
42+
local field_type
43+
field_type=$(yq "(.${field} | type)" "${file}" 2>/dev/null || echo "!!null")
44+
if [[ "${field_type}" == "!!map" ]] && yq -e ".${field}.tag" "${file}" > /dev/null 2>&1; then
45+
yq -i ".${field}.tag=\"${INPUT_TAG}\"" "${file}"
46+
else
47+
yq -i ."${field}"=\""${image}"\" "${file}"
48+
fi
49+
fi
4050

4151
echo "Writing deployment annotations to ${file}"
4252
yq -i '.metadata.annotations["deploy.staffbase.com/repositoryFullName"] = "'"${GITHUB_REPOSITORY}"'"' "${file}"

tests/fixtures/helmrelease.yaml

Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,13 @@
1+
apiVersion: helm.toolkit.fluxcd.io/v2
2+
kind: HelmRelease
3+
metadata:
4+
name: my-service
5+
namespace: my-service
6+
annotations: {}
7+
spec:
8+
values:
9+
workload:
10+
container:
11+
image:
12+
repository: registry.staffbase.com/sb-images/my-service
13+
tag: placeholder

tests/lib-gitops-functions.bats

Lines changed: 32 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -51,6 +51,38 @@ teardown() {
5151

5252
# --- update_file ---
5353

54+
@test "update_file writes full URI when field value is a scalar" {
55+
cat > "${TEST_TEMP_DIR}/mocks/yq" << 'YQ_MOCK'
56+
#!/usr/bin/env bash
57+
echo "yq $*" >> "${MOCK_CALLS_DIR}/yq_calls.log"
58+
if [[ "$*" == *"| type"* ]]; then echo "!!str"; fi
59+
exit 0
60+
YQ_MOCK
61+
chmod +x "${TEST_TEMP_DIR}/mocks/yq"
62+
update_file "deployment.yaml" "spec.template.spec.containers.app.image" "$IMAGE"
63+
grep -q "${IMAGE}" "${TEST_TEMP_DIR}/yq_calls.log"
64+
! grep -q ".tag=\"${INPUT_TAG}\"" "${TEST_TEMP_DIR}/yq_calls.log"
65+
}
66+
67+
@test "update_file writes tag to .tag subfield when field is a map with tag property" {
68+
cat > "${TEST_TEMP_DIR}/mocks/yq" << 'YQ_MOCK'
69+
#!/usr/bin/env bash
70+
echo "yq $*" >> "${MOCK_CALLS_DIR}/yq_calls.log"
71+
if [[ "$*" == *"| type"* ]]; then echo "!!map"; fi
72+
exit 0
73+
YQ_MOCK
74+
chmod +x "${TEST_TEMP_DIR}/mocks/yq"
75+
update_file "helmrelease.yaml" "spec.values.workload.container.image" "$IMAGE"
76+
grep -q ".spec.values.workload.container.image.tag=\"${INPUT_TAG}\"" "${TEST_TEMP_DIR}/yq_calls.log"
77+
! grep -q "${IMAGE}" "${TEST_TEMP_DIR}/yq_calls.log"
78+
}
79+
80+
@test "update_file writes tag only when field path ends with .tag" {
81+
update_file "helmrelease.yaml" "spec.values.workload.container.image.tag" "$IMAGE"
82+
grep -q ".spec.values.workload.container.image.tag=\"${INPUT_TAG}\"" "${TEST_TEMP_DIR}/yq_calls.log"
83+
! grep -q "${IMAGE}" "${TEST_TEMP_DIR}/yq_calls.log"
84+
}
85+
5486
@test "update_file calls yq to check and update field" {
5587
update_file "deployment.yaml" "spec.image" "$IMAGE"
5688
assert [ -f "${TEST_TEMP_DIR}/yq_calls.log" ]

0 commit comments

Comments
 (0)