From 9ec088ed7e61c545cde3a75f8c01025ad70c9f90 Mon Sep 17 00:00:00 2001 From: Brendan <2bndy5@gmail.com> Date: Mon, 29 Jul 2024 21:37:27 -0700 Subject: [PATCH] support for Sphinx v8.0 (#376) * support for Sphinx v8.0 * add sphinx v8 to CI reduce combinations of CI test matrix group nox sessions' output in CI logs skip uploading a non-existent coverage HTML report in CI job --- .github/workflows/build.yml | 19 ++++----------- noxfile.py | 44 ++++++++++++++++++++++++++-------- sphinx_immaterial/nav_adapt.py | 2 +- 3 files changed, 40 insertions(+), 25 deletions(-) diff --git a/.github/workflows/build.yml b/.github/workflows/build.yml index 0d434f5c..205fcbe3 100644 --- a/.github/workflows/build.yml +++ b/.github/workflows/build.yml @@ -122,7 +122,7 @@ jobs: - name: Build docs env: SPHINX_IMMATERIAL_EXTERNAL_RESOURCE_CACHE_DIR: ${{ github.workspace }}/theme_build_cache - run: nox -s docs + run: nox -s docs --forcecolor - name: Upload doc builds as artifacts uses: actions/upload-artifact@v4 with: @@ -149,11 +149,6 @@ jobs: - "3.10" - "3.11" - "3.12" - sphinx-version: - - "sphinx4" - - "sphinx5" - - "sphinx6" - - "sphinx7" node-version: - "16.x" runs-on: ${{ matrix.os }} @@ -185,13 +180,14 @@ jobs: - name: Run Python tests env: SPHINX_IMMATERIAL_EXTERNAL_RESOURCE_CACHE_DIR: ${{ github.workspace }}/theme_build_cache - COVERAGE_FILE: .coverage.${{ github.run_id }}.${{ github.run_attempt }}.${{ runner.os }}.${{ matrix.python-version }}.${{ matrix.sphinx-version }} + COVERAGE_FILE: .coverage.${{ github.run_id }}.${{ github.run_attempt }}.${{ runner.os }}.${{ matrix.python-version }} + PY_COLORS: 1 # `coverage run` cmd adds the working dir to python path, so no need to install pkg here - run: pipx run nox -s "tests-${{ matrix.python-version }}(${{ matrix.sphinx-version }})" + run: pipx run nox -s tests --forcecolor --python ${{ matrix.python-version }} - name: Upload coverage data uses: actions/upload-artifact@v4 with: - name: coverage-data-${{ runner.os }}-py${{ matrix.python-version }}-${{ matrix.sphinx-version }} + name: coverage-data-${{ runner.os }}-py${{ matrix.python-version }} path: .coverage* coverage-report: @@ -211,11 +207,6 @@ jobs: python-version: "3.x" - name: Create coverage report run: pipx run nox -s coverage - - name: Upload comprehensive coverage HTML report - uses: actions/upload-artifact@v4 - with: - name: coverage-report - path: htmlcov/ - name: Post coverage summary uses: codecov/codecov-action@v4 env: diff --git a/noxfile.py b/noxfile.py index ae41c3d1..54fb2501 100644 --- a/noxfile.py +++ b/noxfile.py @@ -1,9 +1,17 @@ import os +import logging import pathlib import re -from typing import Optional, List +import sys +from typing import Optional, List, cast import nox +ci_logger = logging.getLogger("CI logger") +ci_handler = logging.StreamHandler(stream=sys.stdout) +ci_handler.formatter = logging.Formatter("%(msg)s") +ci_logger.handlers.append(ci_handler) +ci_logger.propagate = False + nox.options.reuse_existing_virtualenvs = True nox.options.sessions = [ "ruff_format", @@ -161,7 +169,7 @@ def dist(session: nox.Session, cmd: str): session.run("pip", "install", "wheel", "setuptools_scm", "setuptools>=42") github_output = os.environ.get("GITHUB_OUTPUT", None) if cmd == "--version": - version: str = session.run("python", "setup.py", "--version", silent=True) + version = cast(str, session.run("python", "setup.py", "--version", silent=True)) version = version.splitlines()[-1].strip() if github_output is not None: with open(github_output, "a", encoding="utf-8") as output: @@ -185,6 +193,7 @@ def dist(session: nox.Session, cmd: str): ) def docs(session: nox.Session, builder: str): """Build docs.""" + ci_logger.info(f"::group::Using {builder} builder") session.run("pip", "install", "-r", "docs/requirements.txt") session.run( "sphinx-build", @@ -196,27 +205,40 @@ def docs(session: nox.Session, builder: str): "docs", f"docs/_build/{builder}", ) + ci_logger.info("::endgroup::") + + +SUPPORTED_SPHINX = [4, 5, 6, 7, 8] -@nox.session(python=SUPPORTED_PY_VER) +@nox.session @nox.parametrize( - "sphinx", - [">=4.5,<5", ">=5,<6", ">=6,<7", ">=7,<8"], - ids=["sphinx4", "sphinx5", "sphinx6", "sphinx7"], + "python,sphinx", + [ + (py, sphinx) + for py in SUPPORTED_PY_VER + for sphinx in SUPPORTED_SPHINX + if (sphinx, py) != (8, "3.9") # python v3.9 support dropped in sphinx v8 + ], ) -def tests(session: nox.Session, sphinx: str): +def tests(session: nox.Session, sphinx: int): """Run unit tests and collect code coverage analysis.""" + ci_logger.info(f"::group::Using sphinx v{sphinx} and python v{session.python}") if not pathlib.Path("node_modules").exists(): session.run("npm", "install", external=True) if not list(pathlib.Path().glob("sphinx_immaterial/*.html")): session.run("npm", "run", "build", external=True) - session.install(f"sphinx{sphinx}") - if sphinx.endswith("<5"): + sphinx_version = "sphinx>={},<{}".format( + str(sphinx) if sphinx > 4 else "4.5", sphinx + 1 + ) + session.install(sphinx_version) + if sphinx < 5: # sphinxcontrib deps that dropped support for sphinx v4.x session.install("-r", "tests/requirements-sphinx4.txt") session.install("-r", "tests/requirements.txt") session.run("coverage", "run", "-m", "pytest", "-vv", "-s", "--durations=5") # session.notify("docs") <- only calls docs(html), not dirhtml or latex builders + ci_logger.info("::endgroup::") @nox.session @@ -224,7 +246,9 @@ def coverage(session: nox.Session): """Create coverage report.""" session.install("coverage[toml]>=7.0") session.run("coverage", "combine") - total = int(session.run("coverage", "report", "--format=total", silent=True)) + total = int( + cast(str, session.run("coverage", "report", "--format=total", silent=True)) + ) md = session.run("coverage", "report", "--format=markdown", silent=True) pathlib.Path(".coverage_.md").write_text( f"
Coverage is {total}%\n\n{md}\n\n
", diff --git a/sphinx_immaterial/nav_adapt.py b/sphinx_immaterial/nav_adapt.py index ec6340f8..ced35337 100644 --- a/sphinx_immaterial/nav_adapt.py +++ b/sphinx_immaterial/nav_adapt.py @@ -850,7 +850,7 @@ def _html_page_context( [ repo_url.rstrip("/"), edit_uri.strip("/"), - env.doc2path(pagename, False), + str(env.doc2path(pagename, False)), ] ) context.update(