diff options
-rw-r--r-- | CHANGES | 4 | ||||
-rw-r--r-- | doc/extdev/appapi.rst | 3 | ||||
-rw-r--r-- | sphinx/application.py | 10 | ||||
-rw-r--r-- | sphinx/builders/html/__init__.py | 8 | ||||
-rw-r--r-- | sphinx/domains/math.py | 7 | ||||
-rw-r--r-- | sphinx/ext/mathjax.py | 27 | ||||
-rw-r--r-- | tests/roots/test-ext-math/index.rst | 1 | ||||
-rw-r--r-- | tests/roots/test-ext-math/nomath.rst | 0 | ||||
-rw-r--r-- | tests/test_ext_math.py | 13 |
9 files changed, 55 insertions, 18 deletions
@@ -22,8 +22,12 @@ Features added * #8619: html: kbd role generates customizable HTML tags for compound keys * #8634: html: Allow to change the order of JS/CSS via ``priority`` parameter for :meth:`Sphinx.add_js_file()` and :meth:`Sphinx.add_css_file()` +* #6241: html: Allow to add JS/CSS files to the specific page when an extension + calls ``app.add_js_file()`` or ``app.add_css_file()`` on + :event:`html-page-context` event * #8649: imgconverter: Skip availability check if builder supports the image type +* #6241: mathjax: Include mathjax.js only on the document using equations * #8132: Add :confval:`project_copyright` as an alias of :confval:`copyright` Bugs fixed diff --git a/doc/extdev/appapi.rst b/doc/extdev/appapi.rst index 9f2c10676..a42e9184a 100644 --- a/doc/extdev/appapi.rst +++ b/doc/extdev/appapi.rst @@ -369,6 +369,9 @@ Here is a more detailed list of these events. You can return a string from the handler, it will then replace ``'page.html'`` as the HTML template for this page. + .. note:: You can install JS/CSS files for the specific page via + :meth:`Sphinx.add_js_file` and :meth:`Sphinx.add_css_file` since v3.5.0. + .. versionadded:: 0.4 .. versionchanged:: 1.3 diff --git a/sphinx/application.py b/sphinx/application.py index 2252705c0..54a2603aa 100644 --- a/sphinx/application.py +++ b/sphinx/application.py @@ -958,6 +958,9 @@ class Sphinx: * - 800 - default priority for :confval:`html_js_files` + A JavaScript file can be added to the specific HTML page when on extension + calls this method on :event:`html-page-context` event. + .. versionadded:: 0.5 .. versionchanged:: 1.8 @@ -965,7 +968,7 @@ class Sphinx: And it allows keyword arguments as attributes of script tag. .. versionchanged:: 3.5 - Take priority argument. + Take priority argument. Allow to add a JavaScript file to the specific page. """ self.registry.add_js_file(filename, priority=priority, **kwargs) if hasattr(self.builder, 'add_js_file'): @@ -1004,6 +1007,9 @@ class Sphinx: * - 800 - default priority for :confval:`html_css_files` + A CSS file can be added to the specific HTML page when on extension calls + this method on :event:`html-page-context` event. + .. versionadded:: 1.0 .. versionchanged:: 1.6 @@ -1018,7 +1024,7 @@ class Sphinx: And it allows keyword arguments as attributes of link tag. .. versionchanged:: 3.5 - Take priority argument. + Take priority argument. Allow to add a CSS file to the specific page. """ logger.debug('[app] adding stylesheet: %r', filename) self.registry.add_css_files(filename, priority=priority, **kwargs) diff --git a/sphinx/builders/html/__init__.py b/sphinx/builders/html/__init__.py index 84efa0cc0..4bb7ee510 100644 --- a/sphinx/builders/html/__init__.py +++ b/sphinx/builders/html/__init__.py @@ -466,6 +466,10 @@ class StandaloneHTMLBuilder(Builder): rellinks.append((indexname, indexcls.localname, '', indexcls.shortname)) + # back up script_files and css_files to allow adding JS/CSS files to a specific page. + self._script_files = list(self.script_files) + self._css_files = list(self.css_files) + if self.config.html_style is not None: stylename = self.config.html_style elif self.theme: @@ -1016,6 +1020,10 @@ class StandaloneHTMLBuilder(Builder): self.add_sidebars(pagename, ctx) ctx.update(addctx) + # revert script_files and css_files + self.script_files[:] = self._script_files + self.css_files[:] = self.css_files + self.update_page_context(pagename, templatename, ctx, event_arg) newtmpl = self.app.emit_firstresult('html-page-context', pagename, templatename, ctx, event_arg) diff --git a/sphinx/domains/math.py b/sphinx/domains/math.py index 6bd93e7b5..248a7a2a6 100644 --- a/sphinx/domains/math.py +++ b/sphinx/domains/math.py @@ -157,8 +157,11 @@ class MathDomain(Domain): targets = [eq for eq in self.equations.values() if eq[0] == docname] return len(targets) + 1 - def has_equations(self) -> bool: - return any(self.data['has_equations'].values()) + def has_equations(self, docname: str = None) -> bool: + if docname: + return self.data['has_equations'].get(docname, False) + else: + return any(self.data['has_equations'].values()) def setup(app: "Sphinx") -> Dict[str, Any]: diff --git a/sphinx/ext/mathjax.py b/sphinx/ext/mathjax.py index e4318f35d..ff8ef3718 100644 --- a/sphinx/ext/mathjax.py +++ b/sphinx/ext/mathjax.py @@ -17,14 +17,17 @@ from docutils import nodes import sphinx from sphinx.application import Sphinx -from sphinx.builders.html import StandaloneHTMLBuilder from sphinx.domains.math import MathDomain -from sphinx.environment import BuildEnvironment from sphinx.errors import ExtensionError from sphinx.locale import _ from sphinx.util.math import get_node_equation_number from sphinx.writers.html import HTMLTranslator +# more information for mathjax secure url is here: +# https://docs.mathjax.org/en/latest/start.html#secure-access-to-the-cdn +MATHJAX_URL = ('https://cdnjs.cloudflare.com/ajax/libs/mathjax/2.7.7/latest.js?' + 'config=TeX-AMS-MML_HTMLorMML') + def html_visit_math(self: HTMLTranslator, node: nodes.math) -> None: self.body.append(self.starttag(node, 'span', '', CLASS='math notranslate nohighlight')) @@ -66,25 +69,25 @@ def html_visit_displaymath(self: HTMLTranslator, node: nodes.math_block) -> None raise nodes.SkipNode -def install_mathjax(app: Sphinx, env: BuildEnvironment) -> None: +def install_mathjax(app: Sphinx, pagename: str, templatename: str, context: Dict, + event_arg: Any) -> None: if app.builder.format != 'html' or app.builder.math_renderer_name != 'mathjax': # type: ignore # NOQA return if not app.config.mathjax_path: raise ExtensionError('mathjax_path config value must be set for the ' 'mathjax extension to work') - builder = cast(StandaloneHTMLBuilder, app.builder) - domain = cast(MathDomain, env.get_domain('math')) - if domain.has_equations(): + domain = cast(MathDomain, app.env.get_domain('math')) + if domain.has_equations(pagename): # Enable mathjax only if equations exists options = {'async': 'async'} if app.config.mathjax_options: options.update(app.config.mathjax_options) - builder.add_js_file(app.config.mathjax_path, **options) + app.add_js_file(app.config.mathjax_path, **options) # type: ignore if app.config.mathjax_config: body = "MathJax.Hub.Config(%s)" % json.dumps(app.config.mathjax_config) - builder.add_js_file(None, type="text/x-mathjax-config", body=body) + app.add_js_file(None, type="text/x-mathjax-config", body=body) def setup(app: Sphinx) -> Dict[str, Any]: @@ -92,15 +95,11 @@ def setup(app: Sphinx) -> Dict[str, Any]: (html_visit_math, None), (html_visit_displaymath, None)) - # more information for mathjax secure url is here: - # https://docs.mathjax.org/en/latest/start.html#secure-access-to-the-cdn - app.add_config_value('mathjax_path', - 'https://cdnjs.cloudflare.com/ajax/libs/mathjax/2.7.7/latest.js?' - 'config=TeX-AMS-MML_HTMLorMML', 'html') + app.add_config_value('mathjax_path', MATHJAX_URL, 'html') app.add_config_value('mathjax_options', {}, 'html') app.add_config_value('mathjax_inline', [r'\(', r'\)'], 'html') app.add_config_value('mathjax_display', [r'\[', r'\]'], 'html') app.add_config_value('mathjax_config', None, 'html') - app.connect('env-updated', install_mathjax) + app.connect('html-page-context', install_mathjax) return {'version': sphinx.__display_version__, 'parallel_read_safe': True} diff --git a/tests/roots/test-ext-math/index.rst b/tests/roots/test-ext-math/index.rst index 4237b73ff..221284aeb 100644 --- a/tests/roots/test-ext-math/index.rst +++ b/tests/roots/test-ext-math/index.rst @@ -6,6 +6,7 @@ Test Math math page + nomath .. math:: a^2+b^2=c^2 diff --git a/tests/roots/test-ext-math/nomath.rst b/tests/roots/test-ext-math/nomath.rst new file mode 100644 index 000000000..e69de29bb --- /dev/null +++ b/tests/roots/test-ext-math/nomath.rst diff --git a/tests/test_ext_math.py b/tests/test_ext_math.py index 28c2c35a5..10c8c4866 100644 --- a/tests/test_ext_math.py +++ b/tests/test_ext_math.py @@ -15,6 +15,7 @@ import warnings import pytest from docutils import nodes +from sphinx.ext.mathjax import MATHJAX_URL from sphinx.testing.util import assert_node @@ -224,6 +225,18 @@ def test_mathjax_config(app, status, warning): '</script>' in content) +@pytest.mark.sphinx('html', testroot='ext-math', + confoverrides={'extensions': ['sphinx.ext.mathjax']}) +def test_mathjax_is_installed_only_if_document_having_math(app, status, warning): + app.builder.build_all() + + content = (app.outdir / 'index.html').read_text() + assert MATHJAX_URL in content + + content = (app.outdir / 'nomath.html').read_text() + assert MATHJAX_URL not in content + + @pytest.mark.sphinx('html', testroot='basic', confoverrides={'extensions': ['sphinx.ext.mathjax']}) def test_mathjax_is_not_installed_if_no_equations(app, status, warning): |