-
Notifications
You must be signed in to change notification settings - Fork 0
136 lines (112 loc) · 5.23 KB
/
ci-python-mkdocs.yml
File metadata and controls
136 lines (112 loc) · 5.23 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
# ============================================================
# .github/workflows/ci-python-mkdocs.yml (Continuous Integration)
# ============================================================
# SOURCE: https://github.com/denisecase/templates
#
# WHY-FILE: Validate repository hygiene, python, and documentation builds.
# REQ: Any check that can be run locally MUST be available locally via pre-commit.
# REQ: CI MUST NOT introduce arbitrary rules that are not reproducible locally.
# OBS: CI validates only; it never edits files or deploys docs.
name: CI (Python + MkDocs)
# WHY: Validate code, docs, and repo metadata on PRs and pushes.
# OBS: This workflow validates only; it never deploys.
on:
push:
branches: [main] # WHY: Run when pushing to main branch.
pull_request:
branches: [main] # WHY: Run on pull requests targeting main branch.
workflow_dispatch: # WHY: Allow manual triggering from Actions tab.
permissions: # WHY: Use least privileges required.
contents: read
env:
PYTHONUNBUFFERED: "1" # WHY: Real-time logging.
PYTHONIOENCODING: "utf-8" # WHY: Ensure UTF-8 encoding for international characters.
jobs:
ci:
name: Repository / Python checks and MkDocs build
runs-on: ubuntu-latest # WHY: Linux environment matches most production deployments
timeout-minutes: 30 # WHY: Prevent hanging jobs. If over time, it is likely stuck.
steps:
# ============================================================
# ASSEMBLE: Get code and set up environment
# ============================================================
- name: A1) Checkout repository code
# WHY: Needed to access files for checks.
uses: actions/checkout@v6
- name: A2) Run pre-commit (all files)
# WHY: Single source of truth for locally runnable quality gates.
# OBS: Fails if hooks would modify files; does not commit changes.
id: precommit # WHY: Identify step for conditional follow-up.
uses: pre-commit/action@v3.0.1
with:
extra_args: --all-files
- name: A2f) If pre-commit failed, run it locally
if: failure()
run: |
echo "## Pre-commit failed" >> "$GITHUB_STEP_SUMMARY"
echo "Please run pre-commit locally and commit the resulting changes." >> "$GITHUB_STEP_SUMMARY"
- name: A3) Install uv (with caching)
uses: astral-sh/setup-uv@v7
with:
enable-cache: true # WHY: Speed up installs on subsequent runs
cache-dependency-glob: "uv.lock" # WHY: Only re-cache when dependencies change
- name: A4) Install Python 3.14
run: uv python install 3.14
- name: A5) Show tool versions
run: |
python --version
uv --version
- name: A6) Sync to install all dependencies
run: uv sync --extra dev --extra docs --upgrade
# ============================================================
# === BASELINE CHECKS ===
# ============================================================
- name: B1) validate-pyproject (must be in pyproject.toml deps)
run: uv run validate-pyproject pyproject.toml
- name: B2) Ruff format (check only; no fixes)
run: uv run ruff format --check --diff .
- name: B3) Ruff lint (no fixes)
run: uv run ruff check .
# ============================================================
# === COVERAGE AND TESTS: Verify functionality ===
# ============================================================
- name: C1) Run pytest with coverage
run: |
if [ -d "tests" ] && [ -n "$(find tests -name 'test_*.py' -o -name '*_test.py')" ]; then
uv run pytest --verbose --cov=src --cov-report=term-missing --cov-report=xml
else
echo "No tests found - creating empty coverage report"
echo "## No Tests Found" >> $GITHUB_STEP_SUMMARY
echo "Please add test files to the tests/ directory." >> $GITHUB_STEP_SUMMARY
# Create empty coverage file so artifact upload doesn't fail
echo '<?xml version="1.0" ?><coverage></coverage>' > coverage.xml
fi
- name: C2) Upload test coverage to GitHub Summary
if: always()
run: |
echo "## Test Coverage Report" >> $GITHUB_STEP_SUMMARY
if [ -f ".coverage" ]; then
echo '```' >> $GITHUB_STEP_SUMMARY
uv run coverage report >> $GITHUB_STEP_SUMMARY
echo '```' >> $GITHUB_STEP_SUMMARY
else
echo "No coverage data available." >> $GITHUB_STEP_SUMMARY
fi
- name: C3) Upload coverage artifact
if: always() && hashFiles('coverage.xml') != ''
uses: actions/upload-artifact@v6
with:
name: coverage-report
path: coverage.xml
retention-days: 30
# ============================================================
# === DEPLOY: Build only, don't deploy yet ===
# ============================================================
- name: D1) Build docs (mkdocs --strict)
id: build-docs
run: |
if [ -f "mkdocs.yml" ] || [ -f "mkdocs.yaml" ]; then
uv run mkdocs build --strict --verbose
else
echo "No mkdocs config found; skipping docs build."
fi