diff --git a/doc/languages-frameworks/python.section.md b/doc/languages-frameworks/python.section.md index 8de523e89df..bde4183a65b 100644 --- a/doc/languages-frameworks/python.section.md +++ b/doc/languages-frameworks/python.section.md @@ -744,6 +744,53 @@ with the exception of `other` (see `format` in unittestFlags = [ "-s" "tests" "-v" ]; ``` +##### Using sphinxHook {#using-sphinxhook} + +The `sphinxHook` is a helpful tool to build documentation and manpages +using the popular Sphinx documentation generator. +It is setup to automatically find common documentation source paths and +render them using the default `html` style. + +``` + outputs = [ + "out" + "doc" + ]; + + nativeBuildInputs = [ + sphinxHook + ]; +``` + +The hook will automatically build and install the artifact into the +`doc` output, if it exists. It also provides an automatic diversion +for the artifacts of the `man` builder into the `man` target. + +``` + outputs = [ + "out" + "doc" + "man" + ]; + + # Use multiple builders + sphinxBuilders = [ + "singlehtml" + "man" + ]; +``` + +Overwrite `sphinxRoot` when the hook is unable to find your +documentation source root. + +``` + # Configure sphinxRoot for uncommon paths + sphinxRoot = "weird/docs/path"; +``` + +The hook is also available to packages outside the python ecosystem by +referencing it using `python3.pkgs.sphinxHook`. + ### Develop local package {#develop-local-package} As a Python developer you're likely aware of [development mode](http://setuptools.readthedocs.io/en/latest/setuptools.html#development-mode) @@ -1270,16 +1317,17 @@ are used in `buildPythonPackage`. - `pytestCheckHook` to run tests with `pytest`. See [example usage](#using-pytestcheckhook). - `pythonCatchConflictsHook` to check whether a Python package is not already existing. - `pythonImportsCheckHook` to check whether importing the listed modules works. +- `pythonRelaxDepsHook` will relax Python dependencies restrictions for the package. + See [example usage](#using-pythonrelaxdepshook). - `pythonRemoveBinBytecode` to remove bytecode from the `/bin` folder. - `setuptoolsBuildHook` to build a wheel using `setuptools`. - `setuptoolsCheckHook` to run tests with `python setup.py test`. +- `sphinxHook` to build documentation and manpages using Sphinx. - `venvShellHook` to source a Python 3 `venv` at the `venvDir` location. A `venv` is created if it does not yet exist. `postVenvCreation` can be used to to run commands only after venv is first created. - `wheelUnpackHook` to move a wheel to the correct folder so it can be installed with the `pipInstallHook`. -- `pythonRelaxDepsHook` will relax Python dependencies restrictions for the package. - See [example usage](#using-pythonrelaxdepshook). - `unittestCheckHook` will run tests with `python -m unittest discover`. See [example usage](#using-unittestcheckhook). ### Development mode {#development-mode} diff --git a/pkgs/development/interpreters/python/hooks/default.nix b/pkgs/development/interpreters/python/hooks/default.nix index 0f175c90920..5d605b240ad 100644 --- a/pkgs/development/interpreters/python/hooks/default.nix +++ b/pkgs/development/interpreters/python/hooks/default.nix @@ -6,6 +6,7 @@ , isPy3k , ensureNewerSourcesForZipFilesHook , findutils +, installShellFiles }: let @@ -190,6 +191,6 @@ in rec { sphinxHook = callPackage ({ sphinx }: makeSetupHook { name = "python${python.pythonVersion}-sphinx-hook"; - deps = [ sphinx ]; + deps = [ sphinx installShellFiles ]; } ./sphinx-hook.sh) {}; } diff --git a/pkgs/development/interpreters/python/hooks/sphinx-hook.sh b/pkgs/development/interpreters/python/hooks/sphinx-hook.sh index 92cc9e52ed2..ae386ca859f 100644 --- a/pkgs/development/interpreters/python/hooks/sphinx-hook.sh +++ b/pkgs/development/interpreters/python/hooks/sphinx-hook.sh @@ -1,20 +1,14 @@ -# This hook automatically finds Sphinx documentation, builds it in html format -# and installs it. -# -# This hook knows about several popular locations in which subdirectory -# documentation may be, but in very unusual cases $sphinxRoot directory can be -# set explicitly. -# -# Name of the directory relative to ${doc:-$out}/share/doc is normally also -# deduced automatically, but can be overridden with $sphinxOutdir variable. -# -# Sphinx build system can depend on arbitrary amount of python modules, client -# code is responsible for ensuring that all dependencies are present. +# shellcheck shell=bash +echo "Sourcing sphinx-hook" + +declare -a __sphinxBuilders buildSphinxPhase() { - local __sphinxRoot="" o + echo "Executing buildSphinxPhase" + local __sphinxRoot="" runHook preBuildSphinx + if [[ -n "${sphinxRoot:-}" ]] ; then # explicit root if ! [[ -f "${sphinxRoot}/conf.py" ]] ; then echo 2>&1 "$sphinxRoot/conf.py: no such file" @@ -22,10 +16,10 @@ buildSphinxPhase() { fi __sphinxRoot=$sphinxRoot else - for o in doc docs doc/source docs/source ; do - if [[ -f "$o/conf.py" ]] ; then - echo "Sphinx documentation found in $o" - __sphinxRoot=$o + for candidate in doc docs doc/source docs/source ; do + if [[ -f "$candidate/conf.py" ]] ; then + echo "Sphinx documentation found in $candidate" + __sphinxRoot=$candidate break fi done @@ -35,23 +29,44 @@ buildSphinxPhase() { echo 2>&1 "Sphinx documentation not found, use 'sphinxRoot' variable" exit 1 fi - sphinx-build -M html "${__sphinxRoot}" ".sphinx/html" -v + + if [ -n "${sphinxBuilders-}" ]; then + eval "__sphinxBuilders=($sphinxBuilders)" + else + __sphinxBuilders=(html) + fi + + for __builder in "${__sphinxBuilders[@]}"; do + echo "Executing sphinx-build with ${__builder} builder" + sphinx-build -M "${__builder}" "${__sphinxRoot}" ".sphinx/${__builder}" -v + done runHook postBuildSphinx } installSphinxPhase() { + echo "Executing installSphinxPhase" + local docdir="" runHook preInstallSphinx - docdir="${doc:-$out}/share/doc/${sphinxOutdir:-$name}" - mkdir -p "$docdir" + for __builder in "${__sphinxBuilders[@]}"; do + # divert output for man builder + if [ "$__builder" == "man" ]; then + installManPage .sphinx/man/man/* - cp -r .sphinx/html/html "$docdir/" - rm -fr "${docdir}/html/_sources" "${docdir}/html/.buildinfo" + else + # shellcheck disable=2154 + docdir="${doc:-$out}/share/doc/${pname}" + + mkdir -p "$docdir" + + cp -r ".sphinx/${__builder}/${__builder}" "$docdir/" + rm -fr "${docdir}/${__builder}/_sources" "${docdir}/${__builder}/.buildinfo" + fi + done runHook postInstallSphinx } -preDistPhases+=" buildSphinxPhase" -postPhases+=" installSphinxPhase" +preDistPhases+=" buildSphinxPhase installSphinxPhase" diff --git a/pkgs/tools/backup/borgbackup/default.nix b/pkgs/tools/backup/borgbackup/default.nix index 7ffca4203bb..adfd0b42e39 100644 --- a/pkgs/tools/backup/borgbackup/default.nix +++ b/pkgs/tools/backup/borgbackup/default.nix @@ -33,13 +33,15 @@ python3.pkgs.buildPythonApplication rec { setuptools-scm # docs - sphinx + sphinxHook guzzle_sphinx_theme # shell completions installShellFiles ]; + sphinxBuilders = [ "singlehtml" "man" ]; + buildInputs = [ libb2 lz4 @@ -67,14 +69,6 @@ python3.pkgs.buildPythonApplication rec { ]; postInstall = '' - make -C docs singlehtml - mkdir -p $out/share/doc/borg - cp -R docs/_build/singlehtml $out/share/doc/borg/html - - make -C docs man - mkdir -p $out/share/man - cp -R docs/_build/man $out/share/man/man1 - installShellCompletion --cmd borg \ --bash scripts/shell_completions/bash/borg \ --fish scripts/shell_completions/fish/borg.fish \