Skip to content

Release

Release #82

Workflow file for this run

name: Release
# Two-phase release flow:
# 1. Pushing a tag (yyyy.week.day) runs `build` — validates the release
# cut compiles, tests pass, and the wheel is reproducible. No publish.
# 2. Publishing to PyPI is a separate manual step via workflow_dispatch
# with `publish: true`. This lets us tag freely without every tag
# becoming a public release.
on:
push:
tags:
- '20[0-9][0-9].[0-9]*.[0-9]' # yyyy.week.day — e.g. 2026.17.3
workflow_dispatch:
inputs:
publish:
description: "Publish the built wheel to PyPI"
required: true
type: boolean
default: false
permissions:
contents: read
jobs:
# ──────────────────────────────────────────────────────────────
# Build + test — runs on every tag push and every dispatch.
# Always produces a `bindu-dist` artifact; never publishes.
# ──────────────────────────────────────────────────────────────
build:
name: Build and test
runs-on: ubuntu-latest
steps:
- name: Checkout code
uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4.2.2
with:
fetch-depth: 0 # Fetch all history and tags for version detection
- name: Install uv
uses: astral-sh/setup-uv@eac588ad8def6316056a12d4907a9d4d84ff7a3b # v7.3.0
- name: "Set up Python"
uses: actions/setup-python@a309ff8b426b58ec0e2a45f0f869d46889d02405 # v6.2.0
with:
python-version: "3.13"
- name: Install the project
run: uv sync --locked --all-extras --dev
- name: Run pre-commit checks
run: uv run pre-commit run --all-files
- name: Run tests with coverage
run: uv run pytest --cov=bindu --cov-report=term-missing --cov-report=xml:coverage.xml --cov-fail-under=60
- name: Upload coverage to Coveralls
uses: coverallsapp/github-action@648a8eb78e6d50909eff900e4ec85cab4524a45b # v2.3.6
continue-on-error: true # Don't block release if Coveralls is down
with:
file: coverage.xml
format: cobertura
- name: Build package
run: uv build
- name: Upload package artifact
uses: actions/upload-artifact@ea165f8d65b6e75b540449e92b4886f43607fa02 # v4.6.2
with:
name: bindu-dist
path: dist/
retention-days: 90
# ──────────────────────────────────────────────────────────────
# Publish to PyPI — only runs when someone triggers
# workflow_dispatch with publish=true. Gated by the `release`
# environment so a reviewer must approve before secrets unlock.
# ──────────────────────────────────────────────────────────────
publish:
name: Publish to PyPI
needs: build
if: github.event_name == 'workflow_dispatch' && inputs.publish
runs-on: ubuntu-latest
environment:
name: release
url: https://pypi.org/project/bindu/
permissions:
id-token: write
contents: read
steps:
- name: Download package artifact
uses: actions/download-artifact@cc203385981b70ca67e1cc392babf9cc229d5806 # v4.1.9
with:
name: bindu-dist
path: dist/
- name: Install uv
uses: astral-sh/setup-uv@eac588ad8def6316056a12d4907a9d4d84ff7a3b # v7.3.0
- name: Publish package to PyPI
run: uv publish --token ${{ secrets.PYPI_API_TOKEN }} dist/*