Sphinx 8.0.1__py3-none-any.whl → 8.1.0__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Potentially problematic release.
This version of Sphinx might be problematic. Click here for more details.
- sphinx/__init__.py +6 -3
- sphinx/_cli/__init__.py +40 -20
- sphinx/_cli/util/colour.py +5 -4
- sphinx/_cli/util/errors.py +28 -11
- sphinx/application.py +361 -38
- sphinx/builders/__init__.py +229 -83
- sphinx/builders/_epub_base.py +118 -71
- sphinx/builders/changes.py +39 -21
- sphinx/builders/dirhtml.py +4 -4
- sphinx/builders/dummy.py +2 -5
- sphinx/builders/epub3.py +43 -22
- sphinx/builders/gettext.py +43 -25
- sphinx/builders/html/__init__.py +284 -218
- sphinx/builders/html/_assets.py +62 -26
- sphinx/builders/html/_build_info.py +76 -0
- sphinx/builders/html/transforms.py +11 -9
- sphinx/builders/latex/__init__.py +139 -81
- sphinx/builders/latex/constants.py +7 -7
- sphinx/builders/latex/nodes.py +3 -2
- sphinx/builders/latex/theming.py +7 -5
- sphinx/builders/latex/transforms.py +27 -19
- sphinx/builders/linkcheck.py +146 -72
- sphinx/builders/manpage.py +30 -13
- sphinx/builders/singlehtml.py +22 -14
- sphinx/builders/texinfo.py +67 -37
- sphinx/builders/text.py +5 -5
- sphinx/builders/xml.py +6 -9
- sphinx/cmd/build.py +282 -103
- sphinx/cmd/make_mode.py +106 -63
- sphinx/cmd/quickstart.py +341 -145
- sphinx/config.py +45 -12
- sphinx/deprecation.py +8 -2
- sphinx/directives/__init__.py +28 -19
- sphinx/directives/code.py +86 -56
- sphinx/directives/other.py +50 -36
- sphinx/directives/patches.py +29 -19
- sphinx/domains/__init__.py +20 -120
- sphinx/domains/_domains_container.py +281 -0
- sphinx/domains/_index.py +110 -0
- sphinx/domains/c/__init__.py +3 -3
- sphinx/domains/c/_parser.py +10 -6
- sphinx/domains/changeset.py +5 -3
- sphinx/domains/citation.py +5 -3
- sphinx/domains/cpp/__init__.py +9 -11
- sphinx/domains/cpp/_parser.py +8 -7
- sphinx/domains/index.py +3 -3
- sphinx/domains/javascript.py +12 -7
- sphinx/domains/math.py +2 -2
- sphinx/domains/python/__init__.py +10 -5
- sphinx/domains/python/_object.py +1 -1
- sphinx/domains/rst.py +5 -5
- sphinx/domains/std/__init__.py +16 -11
- sphinx/environment/__init__.py +206 -146
- sphinx/environment/adapters/asset.py +3 -2
- sphinx/environment/adapters/indexentries.py +74 -33
- sphinx/environment/adapters/toctree.py +100 -43
- sphinx/environment/collectors/__init__.py +19 -8
- sphinx/environment/collectors/asset.py +47 -15
- sphinx/environment/collectors/dependencies.py +8 -4
- sphinx/environment/collectors/metadata.py +7 -2
- sphinx/environment/collectors/title.py +7 -2
- sphinx/environment/collectors/toctree.py +54 -22
- sphinx/errors.py +4 -1
- sphinx/events.py +314 -7
- sphinx/ext/apidoc.py +42 -18
- sphinx/ext/autodoc/__init__.py +52 -24
- sphinx/ext/autodoc/importer.py +6 -9
- sphinx/ext/autosectionlabel.py +1 -2
- sphinx/ext/autosummary/__init__.py +3 -1
- sphinx/ext/autosummary/generate.py +28 -14
- sphinx/ext/coverage.py +7 -7
- sphinx/ext/doctest.py +4 -8
- sphinx/ext/duration.py +6 -5
- sphinx/ext/inheritance_diagram.py +1 -1
- sphinx/ext/intersphinx/_cli.py +6 -4
- sphinx/ext/intersphinx/_load.py +77 -32
- sphinx/ext/intersphinx/_resolve.py +173 -79
- sphinx/ext/intersphinx/_shared.py +7 -5
- sphinx/ext/linkcode.py +7 -1
- sphinx/ext/mathjax.py +1 -2
- sphinx/ext/napoleon/__init__.py +37 -24
- sphinx/ext/napoleon/docstring.py +202 -134
- sphinx/ext/todo.py +5 -3
- sphinx/highlighting.py +10 -3
- sphinx/io.py +1 -1
- sphinx/jinja2glue.py +27 -6
- sphinx/locale/__init__.py +6 -2
- sphinx/locale/ar/LC_MESSAGES/sphinx.js +8 -1
- sphinx/locale/ar/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/ar/LC_MESSAGES/sphinx.po +2246 -2288
- sphinx/locale/bg/LC_MESSAGES/sphinx.js +4 -1
- sphinx/locale/bg/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/bg/LC_MESSAGES/sphinx.po +2113 -2159
- sphinx/locale/bn/LC_MESSAGES/sphinx.js +4 -1
- sphinx/locale/bn/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/bn/LC_MESSAGES/sphinx.po +2349 -2395
- sphinx/locale/ca/LC_MESSAGES/sphinx.js +4 -1
- sphinx/locale/ca/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/ca/LC_MESSAGES/sphinx.po +2846 -2892
- sphinx/locale/cak/LC_MESSAGES/sphinx.js +4 -1
- sphinx/locale/cak/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/cak/LC_MESSAGES/sphinx.po +2213 -2259
- sphinx/locale/cs/LC_MESSAGES/sphinx.js +6 -1
- sphinx/locale/cs/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/cs/LC_MESSAGES/sphinx.po +2225 -2269
- sphinx/locale/cy/LC_MESSAGES/sphinx.js +6 -1
- sphinx/locale/cy/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/cy/LC_MESSAGES/sphinx.po +2403 -2447
- sphinx/locale/da/LC_MESSAGES/sphinx.js +4 -1
- sphinx/locale/da/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/da/LC_MESSAGES/sphinx.po +2214 -2260
- sphinx/locale/de/LC_MESSAGES/sphinx.js +4 -1
- sphinx/locale/de/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/de/LC_MESSAGES/sphinx.po +2230 -2276
- sphinx/locale/de_DE/LC_MESSAGES/sphinx.js +4 -1
- sphinx/locale/de_DE/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/de_DE/LC_MESSAGES/sphinx.po +2113 -2159
- sphinx/locale/el/LC_MESSAGES/sphinx.js +4 -1
- sphinx/locale/el/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/el/LC_MESSAGES/sphinx.po +2619 -2665
- sphinx/locale/en_DE/LC_MESSAGES/sphinx.js +4 -1
- sphinx/locale/en_DE/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/en_DE/LC_MESSAGES/sphinx.po +2113 -2159
- sphinx/locale/en_FR/LC_MESSAGES/sphinx.js +4 -1
- sphinx/locale/en_FR/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/en_FR/LC_MESSAGES/sphinx.po +2113 -2159
- sphinx/locale/en_GB/LC_MESSAGES/sphinx.js +4 -1
- sphinx/locale/en_GB/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/en_GB/LC_MESSAGES/sphinx.po +2519 -2565
- sphinx/locale/en_HK/LC_MESSAGES/sphinx.js +4 -1
- sphinx/locale/en_HK/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/en_HK/LC_MESSAGES/sphinx.po +2113 -2159
- sphinx/locale/eo/LC_MESSAGES/sphinx.js +4 -1
- sphinx/locale/eo/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/eo/LC_MESSAGES/sphinx.po +2232 -2278
- sphinx/locale/es/LC_MESSAGES/sphinx.js +5 -1
- sphinx/locale/es/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/es/LC_MESSAGES/sphinx.po +2516 -2561
- sphinx/locale/es_CO/LC_MESSAGES/sphinx.js +5 -1
- sphinx/locale/es_CO/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/es_CO/LC_MESSAGES/sphinx.po +2114 -2159
- sphinx/locale/et/LC_MESSAGES/sphinx.js +4 -1
- sphinx/locale/et/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/et/LC_MESSAGES/sphinx.po +2317 -2363
- sphinx/locale/eu/LC_MESSAGES/sphinx.js +4 -1
- sphinx/locale/eu/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/eu/LC_MESSAGES/sphinx.po +2218 -2264
- sphinx/locale/fa/LC_MESSAGES/sphinx.js +4 -1
- sphinx/locale/fa/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/fa/LC_MESSAGES/sphinx.po +2505 -2551
- sphinx/locale/fi/LC_MESSAGES/sphinx.js +4 -1
- sphinx/locale/fi/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/fi/LC_MESSAGES/sphinx.po +2303 -2349
- sphinx/locale/fr/LC_MESSAGES/sphinx.js +6 -2
- sphinx/locale/fr/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/fr/LC_MESSAGES/sphinx.po +2863 -2908
- sphinx/locale/fr_FR/LC_MESSAGES/sphinx.js +5 -1
- sphinx/locale/fr_FR/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/fr_FR/LC_MESSAGES/sphinx.po +2114 -2159
- sphinx/locale/gl/LC_MESSAGES/sphinx.js +4 -1
- sphinx/locale/gl/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/gl/LC_MESSAGES/sphinx.po +2571 -2617
- sphinx/locale/he/LC_MESSAGES/sphinx.js +5 -1
- sphinx/locale/he/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/he/LC_MESSAGES/sphinx.po +2307 -2352
- sphinx/locale/hi/LC_MESSAGES/sphinx.js +4 -1
- sphinx/locale/hi/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/hi/LC_MESSAGES/sphinx.po +2580 -2626
- sphinx/locale/hi_IN/LC_MESSAGES/sphinx.js +4 -1
- sphinx/locale/hi_IN/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/hi_IN/LC_MESSAGES/sphinx.po +2113 -2159
- sphinx/locale/hr/LC_MESSAGES/sphinx.js +5 -1
- sphinx/locale/hr/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/hr/LC_MESSAGES/sphinx.po +2238 -2283
- sphinx/locale/hu/LC_MESSAGES/sphinx.js +4 -1
- sphinx/locale/hu/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/hu/LC_MESSAGES/sphinx.po +2228 -2274
- sphinx/locale/id/LC_MESSAGES/sphinx.js +3 -1
- sphinx/locale/id/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/id/LC_MESSAGES/sphinx.po +2787 -2834
- sphinx/locale/is/LC_MESSAGES/sphinx.js +4 -1
- sphinx/locale/is/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/is/LC_MESSAGES/sphinx.po +2224 -2270
- sphinx/locale/it/LC_MESSAGES/sphinx.js +5 -1
- sphinx/locale/it/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/it/LC_MESSAGES/sphinx.po +2231 -2276
- sphinx/locale/ja/LC_MESSAGES/sphinx.js +3 -1
- sphinx/locale/ja/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/ja/LC_MESSAGES/sphinx.po +2507 -2554
- sphinx/locale/ka/LC_MESSAGES/sphinx.js +4 -1
- sphinx/locale/ka/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/ka/LC_MESSAGES/sphinx.po +2428 -2474
- sphinx/locale/ko/LC_MESSAGES/sphinx.js +3 -1
- sphinx/locale/ko/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/ko/LC_MESSAGES/sphinx.po +2516 -2563
- sphinx/locale/lt/LC_MESSAGES/sphinx.js +6 -1
- sphinx/locale/lt/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/lt/LC_MESSAGES/sphinx.po +2425 -2469
- sphinx/locale/lv/LC_MESSAGES/sphinx.js +5 -1
- sphinx/locale/lv/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/lv/LC_MESSAGES/sphinx.po +2362 -2407
- sphinx/locale/mk/LC_MESSAGES/sphinx.js +4 -1
- sphinx/locale/mk/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/mk/LC_MESSAGES/sphinx.po +2121 -2167
- sphinx/locale/nb_NO/LC_MESSAGES/sphinx.js +4 -1
- sphinx/locale/nb_NO/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/nb_NO/LC_MESSAGES/sphinx.po +2220 -2266
- sphinx/locale/ne/LC_MESSAGES/sphinx.js +4 -1
- sphinx/locale/ne/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/ne/LC_MESSAGES/sphinx.po +2221 -2267
- sphinx/locale/nl/LC_MESSAGES/sphinx.js +4 -1
- sphinx/locale/nl/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/nl/LC_MESSAGES/sphinx.po +2240 -2286
- sphinx/locale/pl/LC_MESSAGES/sphinx.js +6 -1
- sphinx/locale/pl/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/pl/LC_MESSAGES/sphinx.po +2319 -2363
- sphinx/locale/pt/LC_MESSAGES/sphinx.js +5 -1
- sphinx/locale/pt/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/pt/LC_MESSAGES/sphinx.po +2114 -2159
- sphinx/locale/pt_BR/LC_MESSAGES/sphinx.js +5 -1
- sphinx/locale/pt_BR/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/pt_BR/LC_MESSAGES/sphinx.po +2854 -2899
- sphinx/locale/pt_PT/LC_MESSAGES/sphinx.js +5 -1
- sphinx/locale/pt_PT/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/pt_PT/LC_MESSAGES/sphinx.po +2224 -2269
- sphinx/locale/ro/LC_MESSAGES/sphinx.js +5 -1
- sphinx/locale/ro/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/ro/LC_MESSAGES/sphinx.po +2226 -2271
- sphinx/locale/ru/LC_MESSAGES/sphinx.js +8 -3
- sphinx/locale/ru/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/ru/LC_MESSAGES/sphinx.po +2841 -2885
- sphinx/locale/si/LC_MESSAGES/sphinx.js +4 -1
- sphinx/locale/si/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/si/LC_MESSAGES/sphinx.po +2294 -2340
- sphinx/locale/sk/LC_MESSAGES/sphinx.js +6 -1
- sphinx/locale/sk/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/sk/LC_MESSAGES/sphinx.po +2497 -2541
- sphinx/locale/sl/LC_MESSAGES/sphinx.js +6 -1
- sphinx/locale/sl/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/sl/LC_MESSAGES/sphinx.po +2331 -2375
- sphinx/locale/sphinx.pot +2121 -2167
- sphinx/locale/sq/LC_MESSAGES/sphinx.js +4 -1
- sphinx/locale/sq/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/sq/LC_MESSAGES/sphinx.po +2855 -2901
- sphinx/locale/sr/LC_MESSAGES/sphinx.js +5 -1
- sphinx/locale/sr/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/sr/LC_MESSAGES/sphinx.po +2203 -2248
- sphinx/locale/sr@latin/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/sr_RS/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/sv/LC_MESSAGES/sphinx.js +4 -1
- sphinx/locale/sv/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/sv/LC_MESSAGES/sphinx.po +2423 -2469
- sphinx/locale/te/LC_MESSAGES/sphinx.js +4 -1
- sphinx/locale/te/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/te/LC_MESSAGES/sphinx.po +2113 -2159
- sphinx/locale/tr/LC_MESSAGES/sphinx.js +4 -1
- sphinx/locale/tr/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/tr/LC_MESSAGES/sphinx.po +2443 -2489
- sphinx/locale/uk_UA/LC_MESSAGES/sphinx.js +6 -1
- sphinx/locale/uk_UA/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/uk_UA/LC_MESSAGES/sphinx.po +2329 -2373
- sphinx/locale/ur/LC_MESSAGES/sphinx.js +4 -1
- sphinx/locale/ur/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/ur/LC_MESSAGES/sphinx.po +2113 -2159
- sphinx/locale/vi/LC_MESSAGES/sphinx.js +3 -1
- sphinx/locale/vi/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/vi/LC_MESSAGES/sphinx.po +2199 -2246
- sphinx/locale/yue/LC_MESSAGES/sphinx.js +3 -1
- sphinx/locale/yue/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/yue/LC_MESSAGES/sphinx.po +2112 -2159
- sphinx/locale/zh_HK/LC_MESSAGES/sphinx.js +3 -1
- sphinx/locale/zh_HK/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/zh_HK/LC_MESSAGES/sphinx.po +2112 -2159
- sphinx/locale/zh_TW/LC_MESSAGES/sphinx.js +3 -1
- sphinx/locale/zh_TW/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/zh_TW/LC_MESSAGES/sphinx.po +2845 -2892
- sphinx/locale/zh_TW.Big5/LC_MESSAGES/sphinx.js +3 -1
- sphinx/locale/zh_TW.Big5/LC_MESSAGES/sphinx.mo +0 -0
- sphinx/locale/zh_TW.Big5/LC_MESSAGES/sphinx.po +2112 -2159
- sphinx/parsers.py +3 -1
- sphinx/project.py +6 -2
- sphinx/pycode/__init__.py +11 -4
- sphinx/pycode/ast.py +58 -58
- sphinx/pycode/parser.py +49 -28
- sphinx/pygments_styles.py +49 -49
- sphinx/registry.py +8 -3
- sphinx/roles.py +133 -13
- sphinx/search/__init__.py +146 -87
- sphinx/search/da.py +2 -4
- sphinx/search/de.py +2 -4
- sphinx/search/en.py +4 -4
- sphinx/search/es.py +2 -4
- sphinx/search/fi.py +2 -4
- sphinx/search/fr.py +2 -4
- sphinx/search/hu.py +2 -4
- sphinx/search/it.py +2 -4
- sphinx/search/ja.py +55 -32
- sphinx/search/nl.py +2 -4
- sphinx/search/no.py +2 -4
- sphinx/search/pt.py +2 -4
- sphinx/search/ro.py +0 -2
- sphinx/search/ru.py +2 -4
- sphinx/search/sv.py +2 -4
- sphinx/search/tr.py +0 -2
- sphinx/search/zh.py +18 -13
- sphinx/templates/graphviz/graphviz.css +0 -7
- sphinx/testing/fixtures.py +6 -5
- sphinx/testing/path.py +7 -5
- sphinx/testing/util.py +63 -29
- sphinx/texinputs/sphinx.sty +107 -39
- sphinx/texinputs/sphinxlatexadmonitions.sty +51 -35
- sphinx/texinputs/sphinxlatexcontainers.sty +1 -1
- sphinx/texinputs/sphinxlatexgraphics.sty +3 -2
- sphinx/texinputs/sphinxlatexindbibtoc.sty +1 -1
- sphinx/texinputs/sphinxlatexlists.sty +1 -1
- sphinx/texinputs/sphinxlatexliterals.sty +4 -1
- sphinx/texinputs/sphinxlatexnumfig.sty +22 -9
- sphinx/texinputs/sphinxlatexobjects.sty +1 -1
- sphinx/texinputs/sphinxlatexshadowbox.sty +72 -10
- sphinx/texinputs/sphinxlatexstyleheadings.sty +7 -2
- sphinx/texinputs/sphinxlatexstylepage.sty +2 -8
- sphinx/texinputs/sphinxlatexstyletext.sty +2 -4
- sphinx/texinputs/sphinxlatextables.sty +1 -1
- sphinx/texinputs/sphinxoptionsgeometry.sty +1 -1
- sphinx/texinputs/sphinxoptionshyperref.sty +1 -1
- sphinx/themes/agogo/layout.html +1 -10
- sphinx/themes/agogo/static/agogo.css.jinja +0 -7
- sphinx/themes/basic/defindex.html +1 -8
- sphinx/themes/basic/domainindex.html +1 -9
- sphinx/themes/basic/genindex-single.html +1 -9
- sphinx/themes/basic/genindex-split.html +1 -9
- sphinx/themes/basic/genindex.html +1 -9
- sphinx/themes/basic/globaltoc.html +1 -9
- sphinx/themes/basic/layout.html +1 -9
- sphinx/themes/basic/localtoc.html +1 -9
- sphinx/themes/basic/page.html +1 -9
- sphinx/themes/basic/relations.html +1 -9
- sphinx/themes/basic/search.html +1 -9
- sphinx/themes/basic/searchbox.html +1 -9
- sphinx/themes/basic/searchfield.html +4 -10
- sphinx/themes/basic/sourcelink.html +1 -9
- sphinx/themes/basic/static/basic.css.jinja +2 -13
- sphinx/themes/basic/static/doctools.js +0 -7
- sphinx/themes/basic/static/language_data.js.jinja +0 -7
- sphinx/themes/basic/static/searchtools.js +25 -13
- sphinx/themes/bizstyle/layout.html +1 -9
- sphinx/themes/bizstyle/static/bizstyle.css.jinja +0 -7
- sphinx/themes/bizstyle/static/bizstyle.js.jinja +5 -11
- sphinx/themes/classic/layout.html +1 -9
- sphinx/themes/classic/static/classic.css.jinja +0 -7
- sphinx/themes/classic/static/sidebar.js.jinja +0 -6
- sphinx/themes/epub/epub-cover.html +1 -9
- sphinx/themes/epub/layout.html +1 -9
- sphinx/themes/epub/static/epub.css.jinja +0 -7
- sphinx/themes/haiku/layout.html +1 -9
- sphinx/themes/haiku/static/haiku.css.jinja +0 -6
- sphinx/themes/nature/static/nature.css.jinja +0 -7
- sphinx/themes/nonav/layout.html +1 -9
- sphinx/themes/nonav/static/nonav.css.jinja +0 -7
- sphinx/themes/pyramid/static/epub.css.jinja +0 -7
- sphinx/themes/pyramid/static/pyramid.css.jinja +0 -7
- sphinx/themes/scrolls/layout.html +1 -10
- sphinx/themes/scrolls/static/scrolls.css.jinja +0 -7
- sphinx/themes/sphinxdoc/static/sphinxdoc.css.jinja +2 -7
- sphinx/themes/traditional/static/traditional.css.jinja +0 -7
- sphinx/theming.py +18 -6
- sphinx/transforms/__init__.py +56 -35
- sphinx/transforms/compact_bullet_list.py +3 -2
- sphinx/transforms/i18n.py +132 -50
- sphinx/transforms/post_transforms/__init__.py +94 -43
- sphinx/transforms/post_transforms/code.py +7 -6
- sphinx/transforms/post_transforms/images.py +71 -54
- sphinx/transforms/references.py +1 -2
- sphinx/util/__init__.py +23 -194
- sphinx/util/_files.py +80 -0
- sphinx/util/_importer.py +27 -0
- sphinx/util/_io.py +1 -2
- sphinx/util/_lines.py +26 -0
- sphinx/util/_pathlib.py +5 -2
- sphinx/util/_serialise.py +53 -0
- sphinx/util/_timestamps.py +2 -1
- sphinx/util/_uri.py +16 -0
- sphinx/util/cfamily.py +48 -25
- sphinx/util/console.py +1 -0
- sphinx/util/display.py +1 -1
- sphinx/util/docfields.py +125 -45
- sphinx/util/docstrings.py +1 -1
- sphinx/util/docutils.py +118 -44
- sphinx/util/exceptions.py +11 -5
- sphinx/util/fileutil.py +53 -32
- sphinx/util/http_date.py +9 -7
- sphinx/util/i18n.py +49 -16
- sphinx/util/images.py +7 -6
- sphinx/util/inspect.py +29 -12
- sphinx/util/inventory.py +47 -29
- sphinx/util/logging.py +58 -85
- sphinx/util/matching.py +3 -3
- sphinx/util/math.py +1 -1
- sphinx/util/nodes.py +176 -108
- sphinx/util/osutil.py +13 -10
- sphinx/util/parallel.py +5 -4
- sphinx/util/parsing.py +5 -3
- sphinx/util/png.py +3 -3
- sphinx/util/requests.py +8 -4
- sphinx/util/rst.py +5 -3
- sphinx/util/tags.py +5 -2
- sphinx/util/template.py +26 -11
- sphinx/util/texescape.py +2 -2
- sphinx/util/typing.py +89 -38
- sphinx/versioning.py +3 -1
- sphinx/writers/html.py +22 -7
- sphinx/writers/html5.py +113 -64
- sphinx/writers/latex.py +408 -221
- sphinx/writers/manpage.py +25 -15
- sphinx/writers/texinfo.py +94 -82
- sphinx/writers/text.py +87 -53
- sphinx/writers/xml.py +5 -4
- sphinx-8.1.0.dist-info/LICENSE.rst +31 -0
- {sphinx-8.0.1.dist-info → sphinx-8.1.0.dist-info}/METADATA +13 -11
- sphinx-8.1.0.dist-info/RECORD +598 -0
- sphinx-8.0.1.dist-info/LICENSE.rst +0 -67
- sphinx-8.0.1.dist-info/RECORD +0 -590
- {sphinx-8.0.1.dist-info → sphinx-8.1.0.dist-info}/WHEEL +0 -0
- {sphinx-8.0.1.dist-info → sphinx-8.1.0.dist-info}/entry_points.txt +0 -0
sphinx/environment/__init__.py
CHANGED
|
@@ -8,14 +8,22 @@ import pickle
|
|
|
8
8
|
from collections import defaultdict
|
|
9
9
|
from copy import copy
|
|
10
10
|
from os import path
|
|
11
|
-
from typing import TYPE_CHECKING
|
|
11
|
+
from typing import TYPE_CHECKING
|
|
12
12
|
|
|
13
13
|
from sphinx import addnodes
|
|
14
|
+
from sphinx.domains._domains_container import _DomainsContainer
|
|
14
15
|
from sphinx.environment.adapters import toctree as toctree_adapters
|
|
15
|
-
from sphinx.errors import
|
|
16
|
+
from sphinx.errors import (
|
|
17
|
+
BuildEnvironmentError,
|
|
18
|
+
DocumentError,
|
|
19
|
+
ExtensionError,
|
|
20
|
+
SphinxError,
|
|
21
|
+
)
|
|
16
22
|
from sphinx.locale import __
|
|
17
23
|
from sphinx.transforms import SphinxTransformer
|
|
18
|
-
from sphinx.util import
|
|
24
|
+
from sphinx.util import logging
|
|
25
|
+
from sphinx.util._files import DownloadFiles, FilenameUniqDict
|
|
26
|
+
from sphinx.util._serialise import stable_str
|
|
19
27
|
from sphinx.util._timestamps import _format_rfc3339_microseconds
|
|
20
28
|
from sphinx.util.docutils import LoggingReporter
|
|
21
29
|
from sphinx.util.i18n import CatalogRepository, docname_to_domain
|
|
@@ -23,8 +31,9 @@ from sphinx.util.nodes import is_translatable
|
|
|
23
31
|
from sphinx.util.osutil import _last_modified_time, canon_path, os_path
|
|
24
32
|
|
|
25
33
|
if TYPE_CHECKING:
|
|
26
|
-
from collections.abc import Callable, Iterator
|
|
34
|
+
from collections.abc import Callable, Iterable, Iterator
|
|
27
35
|
from pathlib import Path
|
|
36
|
+
from typing import Any, Literal
|
|
28
37
|
|
|
29
38
|
from docutils import nodes
|
|
30
39
|
from docutils.nodes import Node
|
|
@@ -45,6 +54,10 @@ default_settings: dict[str, Any] = {
|
|
|
45
54
|
'image_loading': 'link',
|
|
46
55
|
'embed_stylesheet': False,
|
|
47
56
|
'cloak_email_addresses': True,
|
|
57
|
+
'cve_base_url': 'https://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-',
|
|
58
|
+
'cve_references': None,
|
|
59
|
+
'cwe_base_url': 'https://cwe.mitre.org/data/definitions/',
|
|
60
|
+
'cwe_references': None,
|
|
48
61
|
'pep_base_url': 'https://peps.python.org/',
|
|
49
62
|
'pep_references': None,
|
|
50
63
|
'rfc_base_url': 'https://datatracker.ietf.org/doc/html/',
|
|
@@ -60,7 +73,7 @@ default_settings: dict[str, Any] = {
|
|
|
60
73
|
|
|
61
74
|
# This is increased every time an environment attribute is added
|
|
62
75
|
# or changed to properly invalidate pickle files.
|
|
63
|
-
ENV_VERSION =
|
|
76
|
+
ENV_VERSION = 64
|
|
64
77
|
|
|
65
78
|
# config status
|
|
66
79
|
CONFIG_UNSET = -1
|
|
@@ -81,61 +94,6 @@ versioning_conditions: dict[str, Literal[False] | Callable[[Node], bool]] = {
|
|
|
81
94
|
'text': is_translatable,
|
|
82
95
|
}
|
|
83
96
|
|
|
84
|
-
if TYPE_CHECKING:
|
|
85
|
-
from collections.abc import MutableMapping
|
|
86
|
-
from typing import Literal, overload
|
|
87
|
-
|
|
88
|
-
from sphinx.domains.c import CDomain
|
|
89
|
-
from sphinx.domains.changeset import ChangeSetDomain
|
|
90
|
-
from sphinx.domains.citation import CitationDomain
|
|
91
|
-
from sphinx.domains.cpp import CPPDomain
|
|
92
|
-
from sphinx.domains.index import IndexDomain
|
|
93
|
-
from sphinx.domains.javascript import JavaScriptDomain
|
|
94
|
-
from sphinx.domains.math import MathDomain
|
|
95
|
-
from sphinx.domains.python import PythonDomain
|
|
96
|
-
from sphinx.domains.rst import ReSTDomain
|
|
97
|
-
from sphinx.domains.std import StandardDomain
|
|
98
|
-
from sphinx.ext.duration import DurationDomain
|
|
99
|
-
from sphinx.ext.todo import TodoDomain
|
|
100
|
-
|
|
101
|
-
class _DomainsType(MutableMapping[str, Domain]):
|
|
102
|
-
@overload
|
|
103
|
-
def __getitem__(self, key: Literal["c"]) -> CDomain: ... # NoQA: E704
|
|
104
|
-
@overload
|
|
105
|
-
def __getitem__(self, key: Literal["cpp"]) -> CPPDomain: ... # NoQA: E704
|
|
106
|
-
@overload
|
|
107
|
-
def __getitem__(self, key: Literal["changeset"]) -> ChangeSetDomain: ... # NoQA: E704
|
|
108
|
-
@overload
|
|
109
|
-
def __getitem__(self, key: Literal["citation"]) -> CitationDomain: ... # NoQA: E704
|
|
110
|
-
@overload
|
|
111
|
-
def __getitem__(self, key: Literal["index"]) -> IndexDomain: ... # NoQA: E704
|
|
112
|
-
@overload
|
|
113
|
-
def __getitem__(self, key: Literal["js"]) -> JavaScriptDomain: ... # NoQA: E704
|
|
114
|
-
@overload
|
|
115
|
-
def __getitem__(self, key: Literal["math"]) -> MathDomain: ... # NoQA: E704
|
|
116
|
-
@overload
|
|
117
|
-
def __getitem__(self, key: Literal["py"]) -> PythonDomain: ... # NoQA: E704
|
|
118
|
-
@overload
|
|
119
|
-
def __getitem__(self, key: Literal["rst"]) -> ReSTDomain: ... # NoQA: E704
|
|
120
|
-
@overload
|
|
121
|
-
def __getitem__(self, key: Literal["std"]) -> StandardDomain: ... # NoQA: E704
|
|
122
|
-
@overload
|
|
123
|
-
def __getitem__(self, key: Literal["duration"]) -> DurationDomain: ... # NoQA: E704
|
|
124
|
-
@overload
|
|
125
|
-
def __getitem__(self, key: Literal["todo"]) -> TodoDomain: ... # NoQA: E704
|
|
126
|
-
@overload
|
|
127
|
-
def __getitem__(self, key: str) -> Domain: ... # NoQA: E704
|
|
128
|
-
def __getitem__(self, _key: str) -> Domain: raise NotImplementedError # NoQA: E704
|
|
129
|
-
def __setitem__( # NoQA: E301,E704
|
|
130
|
-
self, key: str, value: Domain,
|
|
131
|
-
) -> NoReturn: raise NotImplementedError
|
|
132
|
-
def __delitem__(self, key: str) -> NoReturn: raise NotImplementedError # NoQA: E704
|
|
133
|
-
def __iter__(self) -> NoReturn: raise NotImplementedError # NoQA: E704
|
|
134
|
-
def __len__(self) -> NoReturn: raise NotImplementedError # NoQA: E704
|
|
135
|
-
|
|
136
|
-
else:
|
|
137
|
-
_DomainsType = dict
|
|
138
|
-
|
|
139
97
|
|
|
140
98
|
class BuildEnvironment:
|
|
141
99
|
"""
|
|
@@ -144,8 +102,6 @@ class BuildEnvironment:
|
|
|
144
102
|
transformations to resolve links to them.
|
|
145
103
|
"""
|
|
146
104
|
|
|
147
|
-
domains: _DomainsType
|
|
148
|
-
|
|
149
105
|
# --------- ENVIRONMENT INITIALIZATION -------------------------------------
|
|
150
106
|
|
|
151
107
|
def __init__(self, app: Sphinx) -> None:
|
|
@@ -163,9 +119,6 @@ class BuildEnvironment:
|
|
|
163
119
|
self.versioning_condition: Literal[False] | Callable[[Node], bool] | None = None
|
|
164
120
|
self.versioning_compare: bool | None = None
|
|
165
121
|
|
|
166
|
-
# all the registered domains, set by the application
|
|
167
|
-
self.domains = _DomainsType()
|
|
168
|
-
|
|
169
122
|
# the docutils settings for building
|
|
170
123
|
self.settings: dict[str, Any] = default_settings.copy()
|
|
171
124
|
self.settings['env'] = self
|
|
@@ -242,7 +195,7 @@ class BuildEnvironment:
|
|
|
242
195
|
self.dlfiles: DownloadFiles = DownloadFiles()
|
|
243
196
|
|
|
244
197
|
# the original URI for images
|
|
245
|
-
self.original_image_uri: dict[
|
|
198
|
+
self.original_image_uri: dict[_StrPath, str] = {}
|
|
246
199
|
|
|
247
200
|
# temporary data storage while reading a document
|
|
248
201
|
self.temp_data: dict[str, Any] = {}
|
|
@@ -270,6 +223,9 @@ class BuildEnvironment:
|
|
|
270
223
|
# objtype index -> (domain, type, objname (localized))
|
|
271
224
|
self._search_index_objnames: dict[int, tuple[str, str, str]] = {}
|
|
272
225
|
|
|
226
|
+
# all the registered domains, set by the application
|
|
227
|
+
self.domains: _DomainsContainer = _DomainsContainer._from_environment(self)
|
|
228
|
+
|
|
273
229
|
# set up environment
|
|
274
230
|
self.setup(app)
|
|
275
231
|
|
|
@@ -277,7 +233,7 @@ class BuildEnvironment:
|
|
|
277
233
|
"""Obtains serializable data for pickling."""
|
|
278
234
|
__dict__ = self.__dict__.copy()
|
|
279
235
|
# clear unpickable attributes
|
|
280
|
-
__dict__.update(app=None, domains=
|
|
236
|
+
__dict__.update(app=None, domains=None, events=None)
|
|
281
237
|
# clear in-memory doctree caches, to reduce memory consumption and
|
|
282
238
|
# ensure that, upon restoring the state, the most recent pickled files
|
|
283
239
|
# on the disk are used instead of those from a possibly outdated state
|
|
@@ -304,51 +260,83 @@ class BuildEnvironment:
|
|
|
304
260
|
self.project = app.project
|
|
305
261
|
self.version = app.registry.get_envversion(app)
|
|
306
262
|
|
|
307
|
-
#
|
|
308
|
-
self.domains
|
|
309
|
-
|
|
310
|
-
self.domains
|
|
311
|
-
|
|
263
|
+
# initialise domains
|
|
264
|
+
if self.domains is None:
|
|
265
|
+
# if we are unpickling an environment, we need to recreate the domains
|
|
266
|
+
self.domains = _DomainsContainer._from_environment(self)
|
|
312
267
|
# setup domains (must do after all initialization)
|
|
313
|
-
|
|
314
|
-
domain.setup()
|
|
268
|
+
self.domains._setup()
|
|
315
269
|
|
|
316
|
-
#
|
|
317
|
-
self.
|
|
270
|
+
# Initialise config.
|
|
271
|
+
# The old config is self.config, restored from the pickled environment.
|
|
272
|
+
# The new config is app.config, always recreated from ``conf.py``
|
|
273
|
+
self.config_status, self.config_status_extra = self._config_status(
|
|
274
|
+
old_config=self.config, new_config=app.config, verbosity=app.verbosity
|
|
275
|
+
)
|
|
276
|
+
self.config = app.config
|
|
318
277
|
|
|
319
278
|
# initialize settings
|
|
320
279
|
self._update_settings(app.config)
|
|
321
280
|
|
|
322
|
-
|
|
323
|
-
|
|
324
|
-
|
|
325
|
-
|
|
326
|
-
|
|
327
|
-
|
|
328
|
-
|
|
329
|
-
|
|
330
|
-
|
|
331
|
-
|
|
281
|
+
@staticmethod
|
|
282
|
+
def _config_status(
|
|
283
|
+
*, old_config: Config | None, new_config: Config, verbosity: int
|
|
284
|
+
) -> tuple[int, str]:
|
|
285
|
+
"""Report the differences between two Config objects.
|
|
286
|
+
|
|
287
|
+
Returns a triple of:
|
|
288
|
+
|
|
289
|
+
1. The new configuration
|
|
290
|
+
2. A status code indicating how the configuration has changed.
|
|
291
|
+
3. A status message indicating what has changed.
|
|
292
|
+
"""
|
|
293
|
+
if old_config is None:
|
|
294
|
+
return CONFIG_NEW, ''
|
|
295
|
+
|
|
296
|
+
if old_config.extensions != new_config.extensions:
|
|
297
|
+
old_extensions = set(old_config.extensions)
|
|
298
|
+
new_extensions = set(new_config.extensions)
|
|
299
|
+
extensions = old_extensions ^ new_extensions
|
|
332
300
|
if len(extensions) == 1:
|
|
333
|
-
extension = extensions
|
|
301
|
+
extension = extensions.pop()
|
|
334
302
|
else:
|
|
335
|
-
extension = '
|
|
336
|
-
|
|
337
|
-
|
|
338
|
-
|
|
339
|
-
|
|
340
|
-
|
|
341
|
-
|
|
342
|
-
|
|
343
|
-
|
|
344
|
-
|
|
303
|
+
extension = f'{len(extensions)}'
|
|
304
|
+
return CONFIG_EXTENSIONS_CHANGED, f' ({extension!r})'
|
|
305
|
+
|
|
306
|
+
# Log any changes in configuration keys
|
|
307
|
+
if changed_keys := _differing_config_keys(old_config, new_config):
|
|
308
|
+
changed_num = len(changed_keys)
|
|
309
|
+
if changed_num == 1:
|
|
310
|
+
logger.info(
|
|
311
|
+
__('The configuration has changed (1 option: %r)'),
|
|
312
|
+
next(iter(changed_keys)),
|
|
313
|
+
)
|
|
314
|
+
elif changed_num <= 5 or verbosity >= 1:
|
|
315
|
+
logger.info(
|
|
316
|
+
__('The configuration has changed (%d options: %s)'),
|
|
317
|
+
changed_num,
|
|
318
|
+
', '.join(map(repr, sorted(changed_keys))),
|
|
319
|
+
)
|
|
320
|
+
else:
|
|
321
|
+
logger.info(
|
|
322
|
+
__('The configuration has changed (%d options: %s, ...)'),
|
|
323
|
+
changed_num,
|
|
324
|
+
', '.join(map(repr, sorted(changed_keys)[:5])),
|
|
325
|
+
)
|
|
326
|
+
|
|
327
|
+
# check if a config value was changed that affects how doctrees are read
|
|
328
|
+
for item in new_config.filter(frozenset({'env'})):
|
|
329
|
+
if old_config[item.name] != item.value:
|
|
330
|
+
return CONFIG_CHANGED, f' ({item.name!r})'
|
|
345
331
|
|
|
346
|
-
|
|
332
|
+
return CONFIG_OK, ''
|
|
347
333
|
|
|
348
334
|
def _update_settings(self, config: Config) -> None:
|
|
349
335
|
"""Update settings by new config."""
|
|
350
336
|
self.settings['input_encoding'] = config.source_encoding
|
|
351
|
-
self.settings['trim_footnote_reference_space'] =
|
|
337
|
+
self.settings['trim_footnote_reference_space'] = (
|
|
338
|
+
config.trim_footnote_reference_space
|
|
339
|
+
)
|
|
352
340
|
self.settings['language_code'] = config.language
|
|
353
341
|
|
|
354
342
|
# Allow to disable by 3rd party extension (workaround)
|
|
@@ -373,9 +361,12 @@ class BuildEnvironment:
|
|
|
373
361
|
condition = versioning_conditions[method]
|
|
374
362
|
|
|
375
363
|
if self.versioning_condition not in {None, condition}:
|
|
376
|
-
|
|
377
|
-
|
|
378
|
-
|
|
364
|
+
msg = __(
|
|
365
|
+
'This environment is incompatible with the '
|
|
366
|
+
'selected builder, please choose another '
|
|
367
|
+
'doctree directory.'
|
|
368
|
+
)
|
|
369
|
+
raise SphinxError(msg)
|
|
379
370
|
self.versioning_condition = condition
|
|
380
371
|
self.versioning_compare = compare
|
|
381
372
|
|
|
@@ -386,25 +377,24 @@ class BuildEnvironment:
|
|
|
386
377
|
self.included.pop(docname, None)
|
|
387
378
|
self.reread_always.discard(docname)
|
|
388
379
|
|
|
389
|
-
|
|
390
|
-
domain.clear_doc(docname)
|
|
380
|
+
self.domains._clear_doc(docname)
|
|
391
381
|
|
|
392
|
-
def merge_info_from(
|
|
393
|
-
|
|
382
|
+
def merge_info_from(
|
|
383
|
+
self, docnames: Iterable[str], other: BuildEnvironment, app: Sphinx
|
|
384
|
+
) -> None:
|
|
394
385
|
"""Merge global information gathered about *docnames* while reading them
|
|
395
386
|
from the *other* environment.
|
|
396
387
|
|
|
397
388
|
This possibly comes from a parallel build process.
|
|
398
389
|
"""
|
|
399
|
-
docnames =
|
|
390
|
+
docnames = frozenset(docnames)
|
|
400
391
|
for docname in docnames:
|
|
401
392
|
self.all_docs[docname] = other.all_docs[docname]
|
|
402
393
|
self.included[docname] = other.included[docname]
|
|
403
394
|
if docname in other.reread_always:
|
|
404
395
|
self.reread_always.add(docname)
|
|
405
396
|
|
|
406
|
-
|
|
407
|
-
domain.merge_domaindata(docnames, other.domaindata[domainname])
|
|
397
|
+
self.domains._merge_domain_data(docnames, other.domaindata)
|
|
408
398
|
self.events.emit('env-merge-info', self, docnames, other)
|
|
409
399
|
|
|
410
400
|
def path2doc(self, filename: str | os.PathLike[str]) -> str | None:
|
|
@@ -434,12 +424,13 @@ class BuildEnvironment:
|
|
|
434
424
|
if filename.startswith(('/', os.sep)):
|
|
435
425
|
rel_fn = filename[1:]
|
|
436
426
|
else:
|
|
437
|
-
docdir = path.dirname(self.doc2path(docname or self.docname,
|
|
438
|
-
base=False))
|
|
427
|
+
docdir = path.dirname(self.doc2path(docname or self.docname, base=False))
|
|
439
428
|
rel_fn = path.join(docdir, filename)
|
|
440
429
|
|
|
441
|
-
return (
|
|
442
|
-
|
|
430
|
+
return (
|
|
431
|
+
canon_path(path.normpath(rel_fn)),
|
|
432
|
+
path.normpath(path.join(self.srcdir, rel_fn)),
|
|
433
|
+
)
|
|
443
434
|
|
|
444
435
|
@property
|
|
445
436
|
def found_docs(self) -> set[str]:
|
|
@@ -451,9 +442,11 @@ class BuildEnvironment:
|
|
|
451
442
|
self.found_docs.
|
|
452
443
|
"""
|
|
453
444
|
try:
|
|
454
|
-
exclude_paths = (
|
|
455
|
-
|
|
456
|
-
|
|
445
|
+
exclude_paths = (
|
|
446
|
+
self.config.exclude_patterns
|
|
447
|
+
+ self.config.templates_path
|
|
448
|
+
+ builder.get_asset_paths()
|
|
449
|
+
)
|
|
457
450
|
self.project.discover(exclude_paths, self.config.include_patterns)
|
|
458
451
|
|
|
459
452
|
# Current implementation is applying translated messages in the reading
|
|
@@ -464,18 +457,25 @@ class BuildEnvironment:
|
|
|
464
457
|
# move i18n process into the writing phase, and remove these lines.
|
|
465
458
|
if builder.use_message_catalog:
|
|
466
459
|
# add catalog mo file dependency
|
|
467
|
-
repo = CatalogRepository(
|
|
468
|
-
|
|
460
|
+
repo = CatalogRepository(
|
|
461
|
+
self.srcdir,
|
|
462
|
+
self.config.locale_dirs,
|
|
463
|
+
self.config.language,
|
|
464
|
+
self.config.source_encoding,
|
|
465
|
+
)
|
|
469
466
|
mo_paths = {c.domain: c.mo_path for c in repo.catalogs}
|
|
470
467
|
for docname in self.found_docs:
|
|
471
468
|
domain = docname_to_domain(docname, self.config.gettext_compact)
|
|
472
469
|
if domain in mo_paths:
|
|
473
470
|
self.dependencies[docname].add(mo_paths[domain])
|
|
474
471
|
except OSError as exc:
|
|
475
|
-
raise DocumentError(
|
|
476
|
-
|
|
472
|
+
raise DocumentError(
|
|
473
|
+
__('Failed to scan documents in %s: %r') % (self.srcdir, exc)
|
|
474
|
+
) from exc
|
|
477
475
|
|
|
478
|
-
def get_outdated_files(
|
|
476
|
+
def get_outdated_files(
|
|
477
|
+
self, config_changed: bool
|
|
478
|
+
) -> tuple[set[str], set[str], set[str]]:
|
|
479
479
|
"""Return (added, changed, removed) sets."""
|
|
480
480
|
# clear all files no longer present
|
|
481
481
|
removed = set(self.all_docs) - self.found_docs
|
|
@@ -507,10 +507,12 @@ class BuildEnvironment:
|
|
|
507
507
|
mtime = self.all_docs[docname]
|
|
508
508
|
newmtime = _last_modified_time(self.doc2path(docname))
|
|
509
509
|
if newmtime > mtime:
|
|
510
|
-
logger.debug(
|
|
511
|
-
|
|
512
|
-
|
|
513
|
-
|
|
510
|
+
logger.debug(
|
|
511
|
+
'[build target] outdated %r: %s -> %s',
|
|
512
|
+
docname,
|
|
513
|
+
_format_rfc3339_microseconds(mtime),
|
|
514
|
+
_format_rfc3339_microseconds(newmtime),
|
|
515
|
+
)
|
|
514
516
|
changed.add(docname)
|
|
515
517
|
continue
|
|
516
518
|
# finally, check the mtime of dependencies
|
|
@@ -521,7 +523,8 @@ class BuildEnvironment:
|
|
|
521
523
|
if not path.isfile(deppath):
|
|
522
524
|
logger.debug(
|
|
523
525
|
'[build target] changed %r missing dependency %r',
|
|
524
|
-
docname,
|
|
526
|
+
docname,
|
|
527
|
+
deppath,
|
|
525
528
|
)
|
|
526
529
|
changed.add(docname)
|
|
527
530
|
break
|
|
@@ -529,7 +532,8 @@ class BuildEnvironment:
|
|
|
529
532
|
if depmtime > mtime:
|
|
530
533
|
logger.debug(
|
|
531
534
|
'[build target] outdated %r from dependency %r: %s -> %s',
|
|
532
|
-
docname,
|
|
535
|
+
docname,
|
|
536
|
+
deppath,
|
|
533
537
|
_format_rfc3339_microseconds(mtime),
|
|
534
538
|
_format_rfc3339_microseconds(depmtime),
|
|
535
539
|
)
|
|
@@ -557,8 +561,7 @@ class BuildEnvironment:
|
|
|
557
561
|
self.temp_data['docname'] = docname
|
|
558
562
|
# defaults to the global default, but can be re-set in a document
|
|
559
563
|
self.temp_data['default_role'] = self.config.default_role
|
|
560
|
-
self.temp_data['default_domain'] =
|
|
561
|
-
self.domains.get(self.config.primary_domain)
|
|
564
|
+
self.temp_data['default_domain'] = self.domains.get(self.config.primary_domain)
|
|
562
565
|
|
|
563
566
|
# utilities to use while reading a document
|
|
564
567
|
|
|
@@ -616,7 +619,8 @@ class BuildEnvironment:
|
|
|
616
619
|
try:
|
|
617
620
|
return self.domains[domainname]
|
|
618
621
|
except KeyError as exc:
|
|
619
|
-
|
|
622
|
+
msg = __('Domain %r is not registered') % domainname
|
|
623
|
+
raise ExtensionError(msg) from exc
|
|
620
624
|
|
|
621
625
|
# --------- RESOLVING REFERENCES AND TOCTREES ------------------------------
|
|
622
626
|
|
|
@@ -663,7 +667,10 @@ class BuildEnvironment:
|
|
|
663
667
|
# now, resolve all toctree nodes
|
|
664
668
|
for toctreenode in doctree.findall(addnodes.toctree):
|
|
665
669
|
result = toctree_adapters._resolve_toctree(
|
|
666
|
-
self,
|
|
670
|
+
self,
|
|
671
|
+
docname,
|
|
672
|
+
builder,
|
|
673
|
+
toctreenode,
|
|
667
674
|
prune=prune_toctrees,
|
|
668
675
|
includehidden=includehidden,
|
|
669
676
|
)
|
|
@@ -674,9 +681,17 @@ class BuildEnvironment:
|
|
|
674
681
|
|
|
675
682
|
return doctree
|
|
676
683
|
|
|
677
|
-
def resolve_toctree(
|
|
678
|
-
|
|
679
|
-
|
|
684
|
+
def resolve_toctree(
|
|
685
|
+
self,
|
|
686
|
+
docname: str,
|
|
687
|
+
builder: Builder,
|
|
688
|
+
toctree: addnodes.toctree,
|
|
689
|
+
prune: bool = True,
|
|
690
|
+
maxdepth: int = 0,
|
|
691
|
+
titles_only: bool = False,
|
|
692
|
+
collapse: bool = False,
|
|
693
|
+
includehidden: bool = False,
|
|
694
|
+
) -> Node | None:
|
|
680
695
|
"""Resolve a *toctree* node into individual bullet lists with titles
|
|
681
696
|
as items, returning None (if no containing titles are found) or
|
|
682
697
|
a new node.
|
|
@@ -689,7 +704,10 @@ class BuildEnvironment:
|
|
|
689
704
|
be collapsed.
|
|
690
705
|
"""
|
|
691
706
|
return toctree_adapters._resolve_toctree(
|
|
692
|
-
self,
|
|
707
|
+
self,
|
|
708
|
+
docname,
|
|
709
|
+
builder,
|
|
710
|
+
toctree,
|
|
693
711
|
prune=prune,
|
|
694
712
|
maxdepth=maxdepth,
|
|
695
713
|
titles_only=titles_only,
|
|
@@ -697,8 +715,9 @@ class BuildEnvironment:
|
|
|
697
715
|
includehidden=includehidden,
|
|
698
716
|
)
|
|
699
717
|
|
|
700
|
-
def resolve_references(
|
|
701
|
-
|
|
718
|
+
def resolve_references(
|
|
719
|
+
self, doctree: nodes.document, fromdocname: str, builder: Builder
|
|
720
|
+
) -> None:
|
|
702
721
|
self.apply_post_transforms(doctree, fromdocname)
|
|
703
722
|
|
|
704
723
|
def apply_post_transforms(self, doctree: nodes.document, docname: str) -> None:
|
|
@@ -723,7 +742,7 @@ class BuildEnvironment:
|
|
|
723
742
|
|
|
724
743
|
relations = {}
|
|
725
744
|
docnames = _traverse_toctree(
|
|
726
|
-
traversed, None, self.config.root_doc, self.toctree_includes
|
|
745
|
+
traversed, None, self.config.root_doc, self.toctree_includes
|
|
727
746
|
)
|
|
728
747
|
prev_doc = None
|
|
729
748
|
parent, docname = next(docnames)
|
|
@@ -750,15 +769,32 @@ class BuildEnvironment:
|
|
|
750
769
|
continue
|
|
751
770
|
if 'orphan' in self.metadata[docname]:
|
|
752
771
|
continue
|
|
753
|
-
logger.warning(
|
|
754
|
-
|
|
772
|
+
logger.warning(
|
|
773
|
+
__("document isn't included in any toctree"), location=docname
|
|
774
|
+
)
|
|
775
|
+
# Call _check_toc_parents here rather than in _get_toctree_ancestors()
|
|
776
|
+
# because that method is called multiple times per document and would
|
|
777
|
+
# lead to duplicate warnings.
|
|
778
|
+
_check_toc_parents(self.toctree_includes)
|
|
755
779
|
|
|
756
780
|
# call check-consistency for all extensions
|
|
757
|
-
|
|
758
|
-
domain.check_consistency()
|
|
781
|
+
self.domains._check_consistency()
|
|
759
782
|
self.events.emit('env-check-consistency', self)
|
|
760
783
|
|
|
761
784
|
|
|
785
|
+
def _differing_config_keys(old: Config, new: Config) -> frozenset[str]:
|
|
786
|
+
"""Return a set of keys that differ between two config objects."""
|
|
787
|
+
old_vals = {c.name: c.value for c in old}
|
|
788
|
+
new_vals = {c.name: c.value for c in new}
|
|
789
|
+
not_in_both = old_vals.keys() ^ new_vals.keys()
|
|
790
|
+
different_values = {
|
|
791
|
+
key
|
|
792
|
+
for key in old_vals.keys() & new_vals.keys()
|
|
793
|
+
if stable_str(old_vals[key]) != stable_str(new_vals[key])
|
|
794
|
+
}
|
|
795
|
+
return frozenset(not_in_both | different_values)
|
|
796
|
+
|
|
797
|
+
|
|
762
798
|
def _traverse_toctree(
|
|
763
799
|
traversed: set[str],
|
|
764
800
|
parent: str | None,
|
|
@@ -766,9 +802,12 @@ def _traverse_toctree(
|
|
|
766
802
|
toctree_includes: dict[str, list[str]],
|
|
767
803
|
) -> Iterator[tuple[str | None, str]]:
|
|
768
804
|
if parent == docname:
|
|
769
|
-
logger.warning(
|
|
770
|
-
|
|
771
|
-
|
|
805
|
+
logger.warning(
|
|
806
|
+
__('self referenced toctree found. Ignored.'),
|
|
807
|
+
location=docname,
|
|
808
|
+
type='toc',
|
|
809
|
+
subtype='circular',
|
|
810
|
+
)
|
|
772
811
|
return
|
|
773
812
|
|
|
774
813
|
# traverse toctree by pre-order
|
|
@@ -777,8 +816,29 @@ def _traverse_toctree(
|
|
|
777
816
|
|
|
778
817
|
for child in toctree_includes.get(docname, ()):
|
|
779
818
|
for sub_parent, sub_docname in _traverse_toctree(
|
|
780
|
-
traversed, docname, child, toctree_includes
|
|
819
|
+
traversed, docname, child, toctree_includes
|
|
781
820
|
):
|
|
782
821
|
if sub_docname not in traversed:
|
|
783
822
|
yield sub_parent, sub_docname
|
|
784
823
|
traversed.add(sub_docname)
|
|
824
|
+
|
|
825
|
+
|
|
826
|
+
def _check_toc_parents(toctree_includes: dict[str, list[str]]) -> None:
|
|
827
|
+
toc_parents: dict[str, list[str]] = {}
|
|
828
|
+
for parent, children in toctree_includes.items():
|
|
829
|
+
for child in children:
|
|
830
|
+
toc_parents.setdefault(child, []).append(parent)
|
|
831
|
+
|
|
832
|
+
for doc, parents in sorted(toc_parents.items()):
|
|
833
|
+
if len(parents) > 1:
|
|
834
|
+
logger.info(
|
|
835
|
+
__(
|
|
836
|
+
'document is referenced in multiple toctrees: %s, selecting: %s <- %s'
|
|
837
|
+
),
|
|
838
|
+
parents,
|
|
839
|
+
max(parents),
|
|
840
|
+
doc,
|
|
841
|
+
location=doc,
|
|
842
|
+
type='toc',
|
|
843
|
+
subtype='multiple_toc_parents',
|
|
844
|
+
)
|
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
"""Assets adapter for sphinx.environment."""
|
|
2
2
|
|
|
3
3
|
from sphinx.environment import BuildEnvironment
|
|
4
|
+
from sphinx.util._pathlib import _StrPath
|
|
4
5
|
|
|
5
6
|
|
|
6
7
|
class ImageAdapter:
|
|
@@ -9,7 +10,7 @@ class ImageAdapter:
|
|
|
9
10
|
|
|
10
11
|
def get_original_image_uri(self, name: str) -> str:
|
|
11
12
|
"""Get the original image URI."""
|
|
12
|
-
while name in self.env.original_image_uri:
|
|
13
|
-
name = self.env.original_image_uri[name]
|
|
13
|
+
while _StrPath(name) in self.env.original_image_uri:
|
|
14
|
+
name = self.env.original_image_uri[_StrPath(name)]
|
|
14
15
|
|
|
15
16
|
return name
|