Changelog automation¶
How Keprix maintains CHANGELOG.md, the marketing /changelog page, and GitHub Releases.
Source of truth¶
| Artifact | Path | Updated by |
|---|---|---|
| Canonical changelog | CHANGELOG.md (repo root) | release-please (on release PR merge) |
| Version | pyproject.toml | release-please |
| MkDocs copy | docs/reference/changelog.md | scripts/generate_doc_pages.py --only changelog |
| Marketing page | frontend/src/app/(marketing)/changelog/page.tsx | Reads CHANGELOG.md at render (ISR: 5 min) |
| GitHub Release | GitHub Releases UI | release-please (on release PR merge) |
| Docker images | Docker Hub | .github/workflows/release.yml on release: published |
Shipped workflow (Conventional Commits + release-please)¶
- Contributor opens a PR with Conventional Commit title and commits (commitlint in CI).
- Optional: review unreleased notes with
bash scripts/changelog-preview.sh(git-cliff). - PR merges to
main; no manualCHANGELOG.mdedit required. .github/workflows/release-please.ymlopens or updates a release PR with:- Finalized version section in
CHANGELOG.md - Fresh empty
## [Unreleased] pyproject.tomlversion bump- Maintainer reviews and merges the release PR.
- release-please creates tag
vX.Y.Zand GitHub Release. .github/workflows/release.ymlruns tests and publishes Docker images.frontendprebuildregeneratesdocs/reference/changelog.md; deploy updates/changelog.
How often the marketing page updates¶
| Environment | Behaviour |
|---|---|
Local pnpm dev | Refreshes on browser reload when CHANGELOG.md changes |
| Production | After commit + deploy; ISR revalidate = 300 re-reads file every 5 minutes |
The page does not poll GitHub. It only reads the CHANGELOG.md file on disk.
Helper commands¶
# Sync docs copy only (no API app import)
python3 scripts/generate_doc_pages.py --docs-dir docs --only changelog
# Verify root and docs copy match
bash scripts/check-changelog-sync.sh
# Preview unreleased entries from conventional commits (git-cliff; read-only)
bash scripts/changelog-preview.sh
# Full changelog from git history (stdout only; review before any manual replace)
bash scripts/changelog-generate-full.sh
Install git-cliff locally, or download the binary to .tools/git-cliff (see scripts/changelog-git-cliff.sh). CI installs git-cliff v2.7.0 in .github/workflows/changelog-generate.yml.
Configuration: cliff.toml at repo root. Commits matching docs, chore, ci, build, style, and test are skipped in generated output.
Tool roles¶
| Tool | Role |
|---|---|
| commitlint | Enforce Conventional Commits on PR commits and titles |
| git-cliff | Local preview and CI unreleased artifact (read-only) |
| release-please | Semver bumps, release PRs, CHANGELOG.md writer, tags, GitHub Releases |
Do not run git-cliff and release-please as writers on main. release-please owns versioned sections; git-cliff is for preview and drift checks only.
Conventional Commit to Keep a Changelog mapping¶
| Commit prefix | Changelog section |
|---|---|
feat | Added |
fix | Fixed |
perf | Changed |
refactor | Changed |
docs | Changed (or skip in user-facing changelog) |
chore, ci, build | Skip unless chore(deps) flagged |
BREAKING CHANGE footer or ! | Changed + breaking callout |
Scopes map to Keprix areas: mutation, billing, frontend, auth, research, etc.
Contributor and maintainer checklist¶
Contributors:
- Write Conventional Commit messages; do not hand-edit Unreleased for routine changes.
- Use
bash scripts/changelog-preview.shto preview unreleased notes locally.
Maintainers:
- Merge the release-please PR to cut a release (tag + GitHub Release).
- Edit release PR changelog text only for major announcements or corrections.
- Review the release-please PR changelog against
bash scripts/changelog-preview.shbefore merging.
First automated release (migration)¶
- Ensure
CHANGELOG.md[Unreleased]reflects commits since the last shipped version. - Confirm
.release-please-manifest.jsonmatches the latest## [x.y.z]inCHANGELOG.md. - Merge conventional commits to
main; wait for the release-please PR. - Review changelog text against
bash scripts/changelog-preview.sh. - Merge the release PR to publish the next semver tag.
Related files¶
release-please-config.json,.release-please-manifest.json.github/workflows/release-please.yml,.github/workflows/release.ymlfrontend/src/lib/changelog.tsparser (Keep a Changelog headings)scripts/generate_doc_pages.py(write_changelog)scripts/check-changelog-sync.sh.github/workflows/ci.yml(changelogjob).github/workflows/changelog-generate.yml(PR preview artifact).github/workflows/docs.yml(triggers onCHANGELOG.md)
Marketing note¶
The /changelog UI requires no changes; it already parses CHANGELOG.md. release-please output must keep Keep a Changelog headings:
## [Unreleased]
### Added
- ...
## [1.2.0] - 2026-07-06