Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
85 changes: 67 additions & 18 deletions .github/workflows/docs-gh-pages.yml
Original file line number Diff line number Diff line change
@@ -1,40 +1,89 @@
name: Build and Deploy Documentation
name: Docs — Build & Preview
permissions:
contents: read

on:
push:
branches:
- main
branches: [ main ] # regular prod deploy
paths:
- 'mkdocs.yml'
- 'docs/**'
pull_request: # preview only when docs are touched
branches: [ '**' ]
paths:
- 'mkdocs.yml'
- 'docs/**'

jobs:
build-and-deploy-docs:
build:
runs-on: ubuntu-latest
permissions:
contents: read
actions: write
steps:
- uses: actions/checkout@v4
with:
fetch-depth: 0 # Fetch all history for .git-restore-mtime to work correctly
with: { fetch-depth: 0 }

- name: Set up Python
uses: actions/setup-python@v5
- name: Set up Python 3.13
uses: actions/setup-python@v6
with:
python-version: '3.x'
python-version: "3.13"
allow-prereleases: true
cache: "pip"

- name: Install uv via GitHub Action
uses: astral-sh/setup-uv@v6
- uses: astral-sh/setup-uv@v7

- name: Install mesa-frames + docs dependencies
- name: Install mesa-frames + docs deps
run: |
uv pip install --system .
uv pip install --group docs --system

- name: Build MkDocs site (general documentation)
run: mkdocs build --config-file mkdocs.yml --site-dir ./site
- name: Convert jupytext .py notebooks to .ipynb
run: |
set -euxo pipefail
# Convert any jupytext .py files to .ipynb without executing them.
# Enable nullglob so the pattern expands to empty when there are no matches
# and globstar so we recurse into subdirectories (e.g., user-guide/).
shopt -s nullglob globstar || true
files=(docs/general/**/*.py)
if [ ${#files[@]} -eq 0 ]; then
echo "No jupytext .py files found under docs/general"
else
for src in "${files[@]}"; do
[ -e "$src" ] || continue
dest="${src%.py}.ipynb"
echo "Converting $src -> $dest"
# jupytext will write the .ipynb alongside the source file
uv run jupytext --to notebook "$src"
done
fi

- name: Build MkDocs site
run: uv run mkdocs build --config-file mkdocs.yml --site-dir ./site

- name: Build Sphinx docs (API documentation)
run: sphinx-build -b html docs/api site/api
- name: Build Sphinx docs (API)
run: uv run sphinx-build -b html docs/api site/api

- name: Deploy to GitHub Pages
- name: Upload site artifact
uses: actions/upload-artifact@v4
with:
name: site
path: site

deploy-main:
needs: build
if: github.event_name == 'push' && github.ref == 'refs/heads/main'
runs-on: ubuntu-latest
permissions:
contents: write
pages: write
steps:
- uses: actions/download-artifact@v4
with: { name: site, path: site }
- name: Deploy to GitHub Pages (main)
uses: peaceiris/actions-gh-pages@v4
with:
github_token: ${{ secrets.GITHUB_TOKEN }}
publish_branch: gh-pages
publish_dir: ./site
force_orphan: true
force_orphan: true
67 changes: 67 additions & 0 deletions .github/workflows/docs-preview-dispatch.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,67 @@
# Deploys preview artifacts produced by the Docs — Build & Preview workflow for PRs.
# The build workflow runs with read-only permissions on PRs (including forks) and
# uploads the built site as an artifact. This workflow runs in the base repo with
# the permissions needed to publish the preview to the gh-pages branch, but it
# never checks out or executes untrusted PR code.
name: Docs — Preview Deploy

on:
workflow_run:
workflows: ["Docs — Build & Preview"]
types: [completed]

permissions:
contents: write
actions: read
pages: write

jobs:
deploy-preview:
if: >
github.event.workflow_run.event == 'pull_request' &&
github.event.workflow_run.conclusion == 'success' &&
(github.event.workflow_run.pull_requests || null)
runs-on: ubuntu-latest
steps:
- name: Download built site artifact
uses: actions/download-artifact@v4
with:
name: site
path: site
run-id: ${{ github.event.workflow_run.id }}
github-token: ${{ secrets.GITHUB_TOKEN }}

- name: Derive preview metadata
id: meta
env:
HEAD_SHA: ${{ github.event.workflow_run.head_sha }}
HEAD_BRANCH: ${{ github.event.workflow_run.head_branch }}
PR_NUMBER: ${{ github.event.workflow_run.pull_requests[0].number }}
run: |
set -euo pipefail
short_sha="$(printf '%s' "$HEAD_SHA" | cut -c1-7)"
{
echo "short_sha=$short_sha"
echo "head_branch=$HEAD_BRANCH"
echo "pr_number=$PR_NUMBER"
} >> "$GITHUB_OUTPUT"

- name: Deploy preview under subfolder
uses: peaceiris/actions-gh-pages@v4
with:
github_token: ${{ secrets.GITHUB_TOKEN }}
publish_branch: gh-pages
publish_dir: ./site
destination_dir: preview/${{ steps.meta.outputs.head_branch }}/${{ steps.meta.outputs.short_sha }}
keep_files: true

- name: Print preview URL
env:
PREVIEW_OWNER: ${{ github.repository_owner }}
PREVIEW_REPO: ${{ github.repository }}
HEAD_BRANCH: ${{ steps.meta.outputs.head_branch }}
SHORT_SHA: ${{ steps.meta.outputs.short_sha }}
PR_NUMBER: ${{ steps.meta.outputs.pr_number }}
run: |
echo "Preview for PR #${PR_NUMBER}:"
echo "https://${PREVIEW_OWNER}.github.io/$(basename "$PREVIEW_REPO")/preview/${HEAD_BRANCH}/${SHORT_SHA}/"
75 changes: 56 additions & 19 deletions .github/workflows/publish.yml
Original file line number Diff line number Diff line change
Expand Up @@ -17,43 +17,80 @@ jobs:
with:
fetch-depth: 0
token: ${{ secrets.VERSION_PUSH_TOKEN }}
- name: Set up Python
uses: actions/setup-python@v5
with:
python-version: '3.x'
- name: Install dependencies
run: |
python -m pip install --upgrade pip
pip install hatch
- name: Setup uv
uses: astral-sh/setup-uv@v3
- name: Set release version
run: |
# Get the tag from the GitHub release
TAG=${GITHUB_REF#refs/tags/}
# Remove 'v' prefix if present
VERSION=${TAG#v}
hatch version $VERSION
uvx hatch version $VERSION
- name: Build package
run: hatch build
run: uvx hatch build
- name: Run tests
run: hatch run test:pytest
run: uvx hatch run test:pytest
- name: Publish package to PyPI
uses: pypa/gh-action-pypi-publish@release/v1
- name: Verify PyPI Release
run: |
# Verify PyPI release
PACKAGE_NAME="mesa_frames"
CURRENT_VERSION=$(hatch version)
pip install $PACKAGE_NAME==$CURRENT_VERSION
CURRENT_VERSION=$(uvx hatch version)
uv pip install --system $PACKAGE_NAME==$CURRENT_VERSION
python -c "import mesa_frames; print(mesa_frames.__version__)"
- name: Update GitHub Release
uses: softprops/action-gh-release@v1
if: startsWith(github.ref, 'refs/tags/')
with:
files: |
dist/*
- name: Generate changelog from release notes
id: notes
uses: actions/github-script@v7
with:
script: |
const fs = require('fs');
const tag = (context.payload.release && context.payload.release.tag_name)
? context.payload.release.tag_name
: (process.env.GITHUB_REF || '').replace('refs/tags/', '');

const body = (context.payload.release && context.payload.release.body) ? context.payload.release.body : '';
if (!body || body.trim().length === 0) {
core.setFailed('Release body is empty. Ensure the GitHub Release is created with auto-generated notes configured by .github/release.yml or supply a body.');
}

fs.writeFileSync('RELEASE_BODY.md', body, 'utf8');
core.setOutput('tag', tag);
- name: Prepend notes to CHANGELOG.md
env:
TAG: ${{ steps.notes.outputs.tag }}
run: |
VERSION_NO_V=${TAG#v}
DATE_UTC=$(date -u +%Y-%m-%d)
echo "## Version ${VERSION_NO_V} — ${DATE_UTC}" > RELEASE_HEADER.md
echo "" >> RELEASE_HEADER.md
if [ -f CHANGELOG.md ]; then
cat RELEASE_HEADER.md RELEASE_BODY.md CHANGELOG.md > CHANGELOG.new
else
cat RELEASE_HEADER.md RELEASE_BODY.md > CHANGELOG.new
fi
mv CHANGELOG.new CHANGELOG.md
- name: Commit and push CHANGELOG update
env:
TAG: ${{ steps.notes.outputs.tag }}
run: |
git config user.name github-actions
git config user.email [email protected]
# Ensure we are on the main branch before committing so the push lands on main.
git checkout main
git add CHANGELOG.md
# Avoid CI cycles
git commit -m "Changelog: add notes for ${TAG} [skip ci]" || echo "No changelog changes to commit"
git push origin main || true
- name: Create or recreate version branch
run: |
CURRENT_VERSION=$(hatch version)
CURRENT_VERSION=$(uvx hatch version)
BRANCH_NAME="v$CURRENT_VERSION"

git config user.name github-actions
Expand All @@ -72,15 +109,15 @@ jobs:
- name: Update to Next Version
run: |
# Bump to next development version
hatch version patch
hatch version dev
uvx hatch version patch
uvx hatch version dev

# Get the new version
NEW_VERSION=$(hatch version)
NEW_VERSION=$(uvx hatch version)

# Commit and push the version bump
git config user.name github-actions
git config user.email [email protected]
git add mesa_frames/__init__.py
git add mesa_frames/__init__.py CHANGELOG.md
git commit -m "Bump version to $NEW_VERSION [skip ci]"
git push origin main
git push origin main
Loading