helm-charts/.github/workflows/chart-release-steps.yaml
2025-03-04 18:27:39 +01:00

244 lines
8.3 KiB
YAML

---
name: "Release chart (Reusable)"
on:
workflow_call:
inputs:
chart:
description: >
Json encoded list of Helm charts to release.
Defaults to releasing everything.
required: true
type: string
createGithubRelease:
description: >
Should the chart be published as a GitHub release
default: false
required: false
type: boolean
publishToGhPages:
description: >
Should the charts be published to GitHub Pages.
default: false
required: false
type: boolean
deployGhPages:
description: >
Should the GitHub pages repo be deployed.
default: false
required: false
type: boolean
publishToOciRegistry:
description: >
Should the charts be published to an OCI registry.
default: false
required: false
type: boolean
helmVersion:
description: >
Helm version to use.
default: "3.11.2"
required: false
type: string
jobs:
release-chart:
name: Release chart
runs-on: ubuntu-22.04
permissions:
pages: write
id-token: write
contents: write
packages: write
steps:
# ----------------------------
# Setup
# ----------------------------
- name: Checkout source branch
uses: actions/checkout@v4
with:
path: src
- name: Install Helm
uses: azure/setup-helm@v4
with:
version: ${{ inputs.helmVersion }}
- name: Login to OCI Registry
if: ${{ inputs.publishToOciRegistry }}
uses: docker/login-action@v3
with:
registry: ghcr.io
username: ${{ github.actor }}
password: ${{ github.token }}
# ----------------------------
# Collect chart metadata
# ----------------------------
- name: Get chart details
id: chart-details
uses: bjw-s/helm-charts-actions/get-chart-details@main
with:
path: src/charts/${{ inputs.chart }}
validateChartYaml: true
requireChangelog: true
- name: Store chart folder
id: chart-folder
shell: bash
env:
CHART_DIR: "${{ inputs.chart }}"
run: |
TARGET_DIR=$(basename $(dirname ${CHART_DIR}))
echo "chart_folder=${TARGET_DIR}" >> "$GITHUB_OUTPUT"
- name: Format changelog
id: format-changelog
uses: actions/github-script@v7
with:
script: |
let input = '${{ steps.chart-details.outputs.changes }}';
let changelog = "## Changelog:";
let inputParsed = JSON.parse(input);
var changelogGrouped = inputParsed.reduce((result, currentValue) => {
(result[currentValue['kind']] = result[currentValue['kind']] || []).push(currentValue);
return result;
}, {});
for (const key in changelogGrouped) {
changelog = changelog + `\n### ${key[0].toUpperCase() + key.slice(1)}`;
let entries = changelogGrouped[key];
entries.forEach(function (entry) {
changelog = changelog + `\n- ${entry.description}`;
if ('links' in entry) {
entry.links.forEach(function (link) {
changelog = changelog + `\n - [${link.name}](${link.url})`;
});
}
});
changelog = changelog + `\n`;
}
core.setOutput('changelog', changelog);
# ----------------------------
# Package Helm chart
# ----------------------------
- name: Dereference JSON schema before packaging
uses: bjw-s/helm-charts-actions/dereference-json-schema@main
with:
schemaFile: "src/charts/${{ inputs.chart }}/values.schema.json"
outputFile: "src/charts/${{ inputs.chart }}/values.schema.json"
allowFileNotFound: true
- name: Package Helm Chart
id: package-chart
shell: bash
env:
CHART_DIR: "src/charts/${{ inputs.chart }}"
TARGET_DIR: "${{ runner.temp }}/charts_out"
run: |
mkdir -p "${TARGET_DIR}"
helm package "${CHART_DIR}" --dependency-update --destination "${TARGET_DIR}"
echo "result=$(ls ${TARGET_DIR}/*.tgz)" >> "$GITHUB_OUTPUT"
# ----------------------------
# Add chart to GitHub Pages
# ----------------------------
- name: Checkout gh-pages branch
uses: actions/checkout@v4
if: ${{ inputs.publishToGhPages }}
with:
path: gh-pages
ref: gh-pages
- name: Copy package to gh-pages structure
id: copy-package
if: ${{ inputs.publishToGhPages }}
shell: bash
env:
CHART_DIR: "${{ inputs.chart }}"
CHART_FOLDER: ${{ steps.chart-folder.outputs.chart_folder }}
PACKAGE_FILE: ${{ steps.package-chart.outputs.result }}
run: |
TARGET_DIR=$(dirname ${CHART_DIR})
cp "${PACKAGE_FILE}" "gh-pages/${CHART_FOLDER}/"
- name: Update repository
if: ${{ inputs.publishToGhPages }}
shell: bash
working-directory: gh-pages
run: |
git pull
- name: Update Helm chart index
if: ${{ inputs.publishToGhPages && inputs.deployGhPages }}
shell: bash
working-directory: gh-pages
run: |
helm repo index . --url https://bjw-s.github.io/helm-charts/
- name: Commit Changes
if: ${{ inputs.publishToGhPages }}
uses: stefanzweifel/git-auto-commit-action@v5
with:
commit_message: "feat: Add Chart package ${{ steps.chart-folder.outputs.chart_folder }}/${{ steps.chart-details.outputs.name }}-${{ steps.chart-details.outputs.version }}"
repository: gh-pages
branch: gh-pages
file_pattern: "index.yaml **/*.tgz"
commit_user_name: github-actions[bot]
commit_user_email: 41898282+github-actions[bot]@users.noreply.github.com
commit_author: github-actions[bot] <41898282+github-actions[bot]@users.noreply.github.com>
- name: Deploy changes to GitHub Pages
if: ${{ inputs.publishToGhPages && inputs.deployGhPages }}
uses: ./src/.github/actions/publish-folder-to-pages
with:
path: gh-pages/
deleteArtifactAfterPublish: true
# ----------------------------
# Create GitHub release
# ----------------------------
- name: Create tag
if: ${{ inputs.createGithubRelease }}
uses: EndBug/latest-tag@latest
with:
ref: ${{ steps.chart-details.outputs.name }}-${{ steps.chart-details.outputs.version }}
git-directory: src
- name: Create release for tag
uses: ncipollo/release-action@v1
if: ${{ inputs.createGithubRelease }}
with:
allowUpdates: true
tag: ${{ steps.chart-details.outputs.name }}-${{ steps.chart-details.outputs.version }}
body: ${{ steps.format-changelog.outputs.changelog }}
# ----------------------------
# Publish chart to bjw-s OCI registry
# ----------------------------
- name: Install Cosign
if: ${{ inputs.publishToOciRegistry }}
uses: sigstore/cosign-installer@v3.8.0
- name: Push Helm charts to OCI registry
if: ${{ inputs.publishToOciRegistry }}
shell: bash
env:
PACKAGE_FILE: ${{ steps.package-chart.outputs.result }}
CHART_NAME: ${{ steps.chart-details.outputs.name }}
CHART_VERSION: ${{ steps.chart-details.outputs.version }}
CHART_TAG_BASE: ghcr.io/bjw-s/helm
CHART_TAG: ${{ steps.chart-details.outputs.name }}:${{ inputs.steps.chart-details.outputs.version }}
run: |
helm push "${PACKAGE_FILE}" oci://${CHART_TAG_BASE} &> push-metadata.txt
cat push-metadata.txt
CHART_DIGEST=$(awk '/Digest: /{print $2}' push-metadata.txt)
cosign sign --yes "${CHART_TAG_BASE}/${CHART_TAG}@${CHART_DIGEST}"
cosign verify "${CHART_TAG_BASE}/${CHART_TAG}@${CHART_DIGEST}" \
--certificate-oidc-issuer "https://token.actions.githubusercontent.com" \
--certificate-identity "https://github.com/${{ github.repository }}/.github/workflows/chart-release-steps.yaml@${{ github.ref }}"