diff --git a/.github/workflows/static.yaml b/.github/workflows/static.yaml index 66335344c..a367fb94e 100644 --- a/.github/workflows/static.yaml +++ b/.github/workflows/static.yaml @@ -44,3 +44,7 @@ jobs: - name: Run docs and check extensions run: | tox -e testdocs + + - name: Run sphinx extension tests + run: | + tox -e test-sphinx-ext diff --git a/.gitignore b/.gitignore index cfa1c1303..391b674af 100644 --- a/.gitignore +++ b/.gitignore @@ -10,3 +10,5 @@ _trial_temp/ apidocs/ *.egg-info .eggs +.hypothesis +__pycache__ \ No newline at end of file diff --git a/pydoctor/sphinx_ext/build_apidocs.py b/pydoctor/sphinx_ext/build_apidocs.py index 1247e0071..680dc7967 100644 --- a/pydoctor/sphinx_ext/build_apidocs.py +++ b/pydoctor/sphinx_ext/build_apidocs.py @@ -67,7 +67,12 @@ def on_build_finished(app: Sphinx, exception: Exception) -> None: temp_path = output_path.with_suffix('.pydoctor_temp') shutil.rmtree(sphinx_files, ignore_errors=True) - output_path.rename(sphinx_files) + try: + output_path.rename(sphinx_files) + except FileNotFoundError as e: + msg = str(e) + msg += '\nMake sur the pydoctor option --html-output is correctly configured.' + raise FileNotFoundError(msg) from e temp_path.rename(output_path) @@ -117,11 +122,11 @@ def on_builder_inited(app: Sphinx) -> None: # Build the API docs in temporary path. shutil.rmtree(temp_path, ignore_errors=True) - _run_pydoctor(key, arguments) + _run_pydoctor(key, arguments, app.warningiserror) output_path.rename(temp_path) -def _run_pydoctor(name: str, arguments: Sequence[str]) -> None: +def _run_pydoctor(name: str, arguments: Sequence[str], warningiserror:bool) -> None: """ Call pydoctor with arguments. @@ -135,8 +140,12 @@ def _run_pydoctor(name: str, arguments: Sequence[str]) -> None: with redirect_stdout(stream): main(args=arguments) + has_warnings = False for line in stream.getvalue().splitlines(): - logger.warning(line) + has_warnings = True + logger.info(line) + if has_warnings and warningiserror: + logger.warning('Pydocor build is not clean and sphinx option -W (turn warnings into errors) is enabled.') def _get_arguments(arguments: Sequence[str], placeholders: Mapping[str, str]) -> Sequence[str]: diff --git a/pydoctor/test/testpackages/epytext_syntax_error/__init__.py b/pydoctor/test/testpackages/epytext_syntax_error/__init__.py new file mode 100644 index 000000000..be15f9c7a --- /dev/null +++ b/pydoctor/test/testpackages/epytext_syntax_error/__init__.py @@ -0,0 +1,10 @@ + +""" + Title + ~~~~~ + + + Hello + ~~~~~ +""" +pass diff --git a/pydoctor/test/testsphinxextension/source/api/index.rst b/pydoctor/test/testsphinxextension/source/api/index.rst new file mode 100644 index 000000000..b62b2e25a --- /dev/null +++ b/pydoctor/test/testsphinxextension/source/api/index.rst @@ -0,0 +1,2 @@ +API ref +======= \ No newline at end of file diff --git a/pydoctor/test/testsphinxextension/source/conf.py b/pydoctor/test/testsphinxextension/source/conf.py new file mode 100644 index 000000000..b74bd09f3 --- /dev/null +++ b/pydoctor/test/testsphinxextension/source/conf.py @@ -0,0 +1,43 @@ +# Configuration file for the Sphinx documentation builder. +# +# For the full list of built-in configuration values, see the documentation: +# https://www.sphinx-doc.org/en/master/usage/configuration.html + +# -- Project information ----------------------------------------------------- +# https://www.sphinx-doc.org/en/master/usage/configuration.html#project-information + +project = 'test-sphinx-ext' +copyright = '2023, Contributors' +author = 'Contributors' +release = '0.0.1' + +# -- General configuration --------------------------------------------------- +# https://www.sphinx-doc.org/en/master/usage/configuration.html#general-configuration + +extensions = [] +templates_path = [] +exclude_patterns = [] + +# -- Options for HTML output ------------------------------------------------- +# https://www.sphinx-doc.org/en/master/usage/configuration.html#options-for-html-output + +html_theme = 'alabaster' +html_static_path = [] + +# ---------------------------------------------------------------------------- +# Test configuration for pydoctor.sphinx_ext.build_apidocs + +from pathlib import Path +extensions.append("pydoctor.sphinx_ext.build_apidocs") + +_testpackages = Path(__file__).parent.parent.parent.joinpath('testpackages') + +pydoctor_args = [ + '--project-name=test-sphinx-ext-api', + f'--project-version={release}', + '--docformat=epytext', + '--intersphinx=https://docs.python.org/3/objects.inv', + '--html-output={outdir}/api', + f'{_testpackages / "report_trigger"}', + f'{_testpackages / "epytext_syntax_error"}', + ] \ No newline at end of file diff --git a/pydoctor/test/testsphinxextension/source/index.rst b/pydoctor/test/testsphinxextension/source/index.rst new file mode 100644 index 000000000..d85e7a51f --- /dev/null +++ b/pydoctor/test/testsphinxextension/source/index.rst @@ -0,0 +1,21 @@ +.. test-sphinx-ext documentation master file, created by + sphinx-quickstart on Thu Oct 26 13:13:53 2023. + You can adapt this file completely to your liking, but it should at least + contain the root `toctree` directive. + +Welcome to test-sphinx-ext's documentation! +=========================================== + +.. toctree:: + :maxdepth: 2 + :caption: Contents: + + api/index + + +Indices and tables +================== + +* :ref:`genindex` +* :ref:`modindex` +* :ref:`search` diff --git a/pydoctor/test/testsphinxextension/tests/__init__.py b/pydoctor/test/testsphinxextension/tests/__init__.py new file mode 100644 index 000000000..e69de29bb diff --git a/pydoctor/test/testsphinxextension/tests/test_build_apidocs.py b/pydoctor/test/testsphinxextension/tests/test_build_apidocs.py new file mode 100644 index 000000000..02baf2b23 --- /dev/null +++ b/pydoctor/test/testsphinxextension/tests/test_build_apidocs.py @@ -0,0 +1,19 @@ +import os +import pathlib +from typing import List +import xml.etree.ElementTree as ET +import json + +from pydoctor import __version__ + +BASE_DIR = pathlib.Path(os.environ.get('TOX_INI_DIR', os.getcwd())) / 'build' / 'test-sphinx-ext' + +def test_rtd_pydoctor_call(): + """ + With the pydoctor Sphinx extension, the pydoctor API HTML files are + generated. + """ + # The pydoctor index is generated and overwrites the Sphinx files. + with open(BASE_DIR / 'api' / 'index.html', 'r') as stream: + page = stream.read() + assert 'moduleIndex.html' in page, page \ No newline at end of file diff --git a/tox.ini b/tox.ini index 706c60f15..c6e2b0f37 100644 --- a/tox.ini +++ b/tox.ini @@ -279,3 +279,17 @@ commands = echo "::endgroup::" pytest -vv docs/tests/test.py + +[testenv:test-sphinx-ext] +description = Run integration tests for the sphinx extension + +extras = docs +deps = pytest + +setenv = + TOX_INI_DIR = {toxinidir} + +commands = + + sphinx-build {posargs:} -aE -b html {toxinidir}/pydoctor/test/testsphinxextension/source {toxinidir}/build/test-sphinx-ext + pytest -vv {toxinidir}/pydoctor/test/testsphinxextension/tests/test_build_apidocs.py \ No newline at end of file