Homework — Chart Packaging & Registries
Apply what you learned about packaging, repositories, OCI registries, and CI/CD pipelines.
Task 1 — GitHub Pages Chart Repository
Set up a chart repository hosted on GitHub Pages. This simulates a real open-source chart distribution workflow.
- Create a new GitHub repository (or use an existing one) and enable GitHub Pages on the
docs/folder of themainbranch. - Create a Helm chart called
myservicewithversion: 1.0.0andappVersion: "2.0.0". - Write a
.helmignorethat excludes.git,*.md,tests/,ci/,.env, and editor swap files. - Package the chart into the
docs/directory. - Generate
index.yamlwith your GitHub Pages URL as the base URL. - Commit, push, and verify the repo works:
helm repo add mypages https://<username>.github.io/<repo> helm repo update helm search repo mypages/myservice - Bump the chart to
version: 1.1.0, re-package, regenerate the index (use--mergeto preserve existing entries), commit, and push. - Verify both versions are discoverable with
helm search repo mypages/myservice --versions.
Self-Check
helm repo addsucceeds without errors.helm search repo --versionsshows both1.0.0and1.1.0.- The
index.yamlhas correcturlspointing to the GitHub Pages domain. - The
.helmignorekeeps the archive lean (no.md, notests/).
Task 2 — OCI Multi-Version Release Pipeline
Build a shell script that automates the full lint-package-push pipeline for an OCI registry.
- Start a local OCI registry:
docker run -d -p 5000:5000 --name hw-registry registry:2 - Create a shell script called
release.shthat accepts a chart directory and a version as arguments and performs:#!/usr/bin/env bash set -euo pipefail CHART_DIR="$1" VERSION="$2" REGISTRY="oci://localhost:5000/charts" # Step 1: Lint helm lint "$CHART_DIR" --strict # Step 2: Package with version override helm package "$CHART_DIR" --version "$VERSION" -d ./build/ # Step 3: Push to OCI registry ARCHIVE="./build/$(basename "$CHART_DIR")-${VERSION}.tgz" helm push "$ARCHIVE" "$REGISTRY" echo "Released $(basename "$CHART_DIR") v${VERSION}" - Run the script three times to release versions
1.0.0,1.1.0, and2.0.0-rc1of your chart. - Verify all three tags exist in the registry:
curl -s http://localhost:5000/v2/charts/<name>/tags/list - Pull each version and confirm the
Chart.yamlinside has the correct version.
Self-Check
release.shexits on any lint or push failure (set -euo pipefail).- The registry API returns all three tags:
1.0.0,1.1.0,2.0.0-rc1. helm show chart oci://localhost:5000/charts/<name> --version 2.0.0-rc1shows the correct metadata.- The pre-release version (
2.0.0-rc1) is a valid SemVer string.
Task 3 — GitHub Actions CI/CD Workflow (Stretch)
Write a GitHub Actions workflow that automates chart releases on tag pushes.
- Create
.github/workflows/helm-release.yamlin a GitHub repository. - Trigger on pushes of tags matching
v*(e.g.,v1.2.0). - The workflow should:
- Check out the repository.
- Install Helm using
azure/setup-helm@v4. - Run
helm lint --strict. - Run
helm templateto validate rendered output. - Package the chart with the version derived from the tag (
${GITHUB_REF_NAME#v}). - Authenticate to GitHub Container Registry using
GITHUB_TOKEN. - Push to
oci://ghcr.io/${{ github.repository_owner }}/charts.
- Test by creating and pushing a tag:
git tag v1.0.0 && git push origin v1.0.0. - Verify the chart appears in your GitHub Packages page.
Self-Check
- The workflow runs without errors on tag push.
- The lint step would catch a broken chart (test by intentionally breaking a template).
- The chart is visible at
ghcr.io/<owner>/charts/<name>. helm pull oci://ghcr.io/<owner>/charts/<name> --version 1.0.0works from a different machine (if the package is public).
Grading Rubric
| Criterion | Points | Description |
|---|---|---|
| Task 1 — GitHub Pages repo works | 35 | Both chart versions are discoverable via helm search repo; index.yaml is correct; .helmignore is present and effective. |
| Task 2 — OCI pipeline script | 40 | Script lints, packages, and pushes; all three versions appear in registry; set -euo pipefail ensures failure stops the pipeline; pulled charts have correct metadata. |
| Task 3 — GitHub Actions workflow | 25 | Workflow file is syntactically valid; includes lint, template, package, and push stages; uses tag-derived versioning; authenticates correctly to GHCR. |
| Total | 100 |
Note: Task 3 is a stretch goal. If you do not have a GitHub account or prefer not to push to a public registry, you can write the workflow file locally and validate it with
actionlint or the online checker without actually running it.