Documentation Workflow Guide¶
This guide explains how halfORM's documentation is managed with multi-version support and automated deployment.
Overview¶
halfORM uses a multi-version documentation system with automated deployment that mirrors the development workflow. Documentation is automatically built and deployed for different development stages.
Development Coordination
The same branch structure and versioning strategy applies to both code and documentation.
Branch Structure & Documentation Deployment¶
The documentation deployment follows the same branch structure as code development:
| Branch/Tag Pattern | Version Deployed | URL | Description |
|---|---|---|---|
main |
dev |
/dev/ |
Latest development documentation |
dev/X.Y.x |
X.Y.x-dev |
/X.Y.x-dev/ |
Patch development documentation |
release/X.Y.x |
X.Y.x-rc |
/X.Y.x-rc/ |
Release candidate documentation |
vX.Y.Z (tags) |
X.Y.Z |
/X.Y.Z/ + /latest/ |
Stable release (becomes default) |
URL Structure¶
https://half-orm.github.io/half-orm/
├── / # → Redirects to latest stable version
├── /latest/ # → Current stable version (alias)
├── /0.16.0/ # → Specific stable version
├── /0.16.x-rc/ # → Release candidate
├── /0.16.x-dev/ # → Development patches
└── /dev/ # → Main branch development
Automatic Deployment¶
GitHub Actions Integration¶
Documentation is automatically deployed via GitHub Actions when:
- Push to
main→ Deploysdevversion - Push to
dev/X.Y.x→ DeploysX.Y.x-devversion - Push to
release/X.Y.x→ DeploysX.Y.x-rcversion - Tag
vX.Y.Z→ DeploysX.Y.Zversion withlatestalias
Workflow Configuration¶
The documentation workflow is configured in .github/workflows/docs.yml:
name: Documentation
on:
push:
branches: [ main, 'release/*', 'dev/*' ]
tags: [ 'v*' ]
pull_request:
branches: [ main ]
Version Resolution¶
The workflow automatically determines the appropriate version and alias:
# Examples of automatic version resolution
dev/0.16.x → 0.16.x-dev
release/0.16.x → 0.16.x-rc
v1.1.0 → 1.1, titled "1.1.0"
main → dev
The latest alias goes to the highest released version, not to whichever tag
was pushed last: tagging a fix on a maintenance branch does not move it. The
title never says "(latest)" -- a title is fixed at deploy time while the alias
moves, so a title that claimed it would go on claiming it after the alias had
left.
Deprecating a version line¶
A branch declares itself end-of-life by carrying a .deprecated file at its
root. Its documentation is then titled 0.17.11 (deprecated) in the version
menu, and it can no longer take the latest alias.
Two things have to be on the branch, because GitHub runs the workflow file from the ref you dispatch against: the marker, and the workflow logic that reads it.
git switch 0.17
# if 0.17's docs.yml does not read .deprecated yet, bring it over first
echo "End of life since 2026-09. Upgrade to 1.1." > .deprecated
git commit -am "docs: mark 0.17 as deprecated"
git push
Then redeploy that line. Pushing to a maintenance branch triggers nothing --
only main, release/*, dev/*, doc and v* tags do -- so the rebuild is
a manual run:
- GitHub UI: Actions -> Documentation -> Run workflow, pick the branch
(
0.17) in Use workflow from, set version to0.17, leave alias empty, and run it. - REST API, with a token carrying the Actions: write permission:
curl -X POST -H "Authorization: Bearer $GITHUB_TOKEN" \
https://api.github.com/repos/half-orm/half-orm/actions/workflows/docs.yml/dispatches \
-d '{"ref":"0.17","inputs":{"version":"0.17"}}'
Do not dispatch from main with version=0.17: mike publishes whatever
is in the checkout, so that would file main's documentation under the 0.17
label.
The marker file's contents are optional -- an empty file is enough to mark the line -- and are echoed in the workflow log when present.
The statement lives on the branch rather than in a list inside the workflow,
because a list there goes stale: KEPT_VERSIONS still read 0.17 0.18 dev
after 1.0 and 1.1 had been released, and the cleanup step deletes whatever is
absent from it.
Deprecation is recorded in the title, unlike latest, because it only ever
moves one way. Redeploy the line when you deprecate it -- nothing rewrites
the titles of versions already published.
Local Development¶
Prerequisites¶
# Install dependencies
pip install mkdocs-material mkdocstrings-python mkdocs-git-revision-date-localized-plugin mike
Local Testing¶
# Serve current documentation (single version)
mkdocs serve
# Deploy version locally for testing
./scripts/deploy-docs.sh deploy dev
./scripts/deploy-docs.sh deploy 0.16.0-rc latest
# Serve multi-version documentation
./scripts/deploy-docs.sh serve
Local Version Management¶
# List deployed versions
./scripts/deploy-docs.sh list
# Deploy specific version
./scripts/deploy-docs.sh deploy 0.16.0 latest
# Set default version
./scripts/deploy-docs.sh set-default latest
# Delete version
./scripts/deploy-docs.sh delete 0.16.0-rc1
# Build documentation only
./scripts/deploy-docs.sh build
Content Management¶
Version-Specific Content¶
Use conditional blocks for version-specific content:
{% if version == "0.16.0" %}
This feature is new in version 0.16.0.
{% endif %}
{% if version != "dev" %}
This applies to stable versions only.
{% endif %}
Documentation Updates¶
When updating documentation:
- Update relevant sections for the changes
- Test locally with
mkdocs serve - Include version-specific notes if needed
- Update migration guides for breaking changes
- Verify all links work correctly
Cross-Version Compatibility¶
- Keep URLs stable across versions when possible
- Use relative links for internal references
- Document breaking changes prominently
- Provide clear migration paths
Version Management¶
Default Version¶
The default version is what users see when they visit the root URL (/). It's automatically set when:
- A tag with
latestalias is deployed - Manual override using
mike set-default
Version Lifecycle¶
# Development → Release Candidate → Stable
dev/0.16.x → release/0.16.x → v0.16.0
0.16.x-dev → 0.16.x-rc → 0.16.0 (latest)
Cleanup¶
# Remove old development versions
mike delete --push 0.15.x-dev 0.14.x-dev
# Remove old release candidates
mike delete --push 0.16.0-rc1 0.16.0-rc2
# Keep stable versions for reference
# 0.16.0, 0.15.0, etc. are kept for historical access
Troubleshooting¶
Common Issues¶
Documentation not updating: - Check GitHub Actions logs in the Actions tab - Verify push triggered the correct workflow - Ensure branch/tag naming follows conventions
Version conflicts:
# Reset local gh-pages branch
git fetch origin
git checkout gh-pages
git reset --hard origin/gh-pages
Site shows 404 or old version:
# Set default version explicitly
mike set-default --push latest
# Or check what versions are deployed
mike list
Local mike issues:
# Clean local mike state
rm -rf .git/refs/heads/gh-pages
git branch -D gh-pages
git fetch origin gh-pages:gh-pages
GitHub Pages Configuration¶
Ensure GitHub Pages is configured correctly:
- Go to Settings → Pages
- Set Source to "Deploy from a branch"
- Set Branch to
gh-pages - Set Folder to
/ (root)
Manual Deployment¶
If automatic deployment fails:
# Emergency manual deployment
mike deploy --push --update-aliases 0.16.0 latest
mike set-default --push latest
# Verify deployment
mike list
Best Practices¶
Content Guidelines¶
- Keep documentation synchronized with code changes
- Use consistent formatting across all versions
- Include version compatibility information
- Provide working examples for each version
- Test all links before publishing
Version Management¶
- Clean up old versions regularly
- Keep stable versions for historical reference
- Document version changes in release notes
- Test deployed versions after each release
Workflow Coordination¶
- Update documentation with code changes in the same branch
- Follow the same branch patterns as code development
- Coordinate releases between code and documentation
- Test locally before pushing to shared branches
Advanced Usage¶
Custom Version Deployment¶
# Deploy custom version for testing
mike deploy --push feature-test
mike set-default --push feature-test
# Deploy with custom alias
mike deploy --push --update-aliases 0.16.0 stable
Multiple Environment Support¶
# Deploy to staging (using different branch)
mike deploy --push --remote staging-origin staging
# Deploy to production (using main remote)
mike deploy --push --update-aliases 0.16.0 latest
Version Archival¶
# Archive old versions by moving to archive alias
mike deploy --push --update-aliases 0.14.0 archive-0.14.0
mike delete --push 0.14.0
Integration with Development Workflow¶
This documentation workflow follows the development process:
- Branch synchronization: Same branch names, same purposes
- Version coordination: Documentation versions match code versions
- Release coordination: Documentation and code released together
- Testing integration: Documentation tested with each code change
Scripts Reference¶
The scripts/deploy-docs.sh script provides convenient commands:
# Available commands
./scripts/deploy-docs.sh deploy VERSION [ALIAS]
./scripts/deploy-docs.sh list
./scripts/deploy-docs.sh serve
./scripts/deploy-docs.sh set-default VERSION
./scripts/deploy-docs.sh delete VERSION
./scripts/deploy-docs.sh build
./scripts/deploy-docs.sh help
See the script file for detailed usage and options.