Merge branch '6.1.x'

# Conflicts:
#	CHANGES
#	sphinx/__init__.py
This commit is contained in:
Adam Turner 2023-01-07 17:51:48 +00:00
commit 8384aa51a7
10 changed files with 136 additions and 17 deletions

24
CHANGES
View File

@ -29,9 +29,30 @@ Bugs fixed
Testing Testing
-------- --------
Release 6.1.2 (in development) Release 6.1.3 (in development)
============================== ==============================
Dependencies
------------
Incompatible changes
--------------------
Deprecated
----------
Features added
--------------
Bugs fixed
----------
Testing
--------
Release 6.1.2 (released Jan 07, 2023)
=====================================
Bugs fixed Bugs fixed
---------- ----------
@ -45,6 +66,7 @@ Bugs fixed
margin since Sphinx 5.1.0 margin since Sphinx 5.1.0
.. _contents: https://docutils.sourceforge.io/docs/ref/rst/directives.html#table-of-contents .. _contents: https://docutils.sourceforge.io/docs/ref/rst/directives.html#table-of-contents
* #11100: Fix copying images when running under parallel mode.
Release 6.1.1 (released Jan 05, 2023) Release 6.1.1 (released Jan 05, 2023)
===================================== =====================================

View File

@ -162,9 +162,12 @@ ignore = [
# flake8-bandit # flake8-bandit
"S101", # assert used "S101", # assert used
"S105", # possible hardcoded password "S105", # possible hardcoded password
"S113", # probable use of requests call without timeout
"S324", # probable use of insecure hash functions
# flake8-simplify # flake8-simplify
"SIM102", # nested 'if' statements "SIM102", # nested 'if' statements
"SIM105", # use contextlib.suppress "SIM105", # use contextlib.suppress
"SIM108", # use ternary operator
"SIM117", # use single 'with' statement "SIM117", # use single 'with' statement
] ]
external = [ # Whitelist for RUF100 unkown code warnings external = [ # Whitelist for RUF100 unkown code warnings

View File

@ -401,9 +401,12 @@ class EpubBuilder(StandaloneHTMLBuilder):
the format and resizing the image if necessary/possible. the format and resizing the image if necessary/possible.
""" """
ensuredir(path.join(self.outdir, self.imagedir)) ensuredir(path.join(self.outdir, self.imagedir))
for src in status_iterator(self.images, __('copying images... '), "brown", converted_images = {*self.env.original_image_uri.values()}
len(self.images), self.app.verbosity): for src in status_iterator(self.env.images, __('copying images... '), "brown",
dest = self.images[src] len(self.env.images), self.app.verbosity):
if src in converted_images:
continue
_docnames, dest = self.env.images[src]
try: try:
img = Image.open(path.join(self.srcdir, src)) img = Image.open(path.join(self.srcdir, src))
except OSError: except OSError:
@ -438,7 +441,7 @@ class EpubBuilder(StandaloneHTMLBuilder):
"""Copy image files to destination directory. """Copy image files to destination directory.
This overwritten method can use Pillow to convert image files. This overwritten method can use Pillow to convert image files.
""" """
if self.images: if self.env.images:
if self.config.epub_fix_images or self.config.epub_max_image_width: if self.config.epub_fix_images or self.config.epub_max_image_width:
if not Image: if not Image:
logger.warning(__('Pillow not found - copying image files')) logger.warning(__('Pillow not found - copying image files'))

View File

@ -764,13 +764,16 @@ class StandaloneHTMLBuilder(Builder):
self.handle_page(indexname, indexcontext, 'domainindex.html') self.handle_page(indexname, indexcontext, 'domainindex.html')
def copy_image_files(self) -> None: def copy_image_files(self) -> None:
if self.images: if self.env.images:
converted_images = {*self.env.original_image_uri.values()}
stringify_func = ImageAdapter(self.app.env).get_original_image_uri stringify_func = ImageAdapter(self.app.env).get_original_image_uri
ensuredir(path.join(self.outdir, self.imagedir)) ensuredir(path.join(self.outdir, self.imagedir))
for src in status_iterator(self.images, __('copying images... '), "brown", for src in status_iterator(self.env.images, __('copying images... '), "brown",
len(self.images), self.app.verbosity, len(self.env.images), self.app.verbosity,
stringify_func=stringify_func): stringify_func=stringify_func):
dest = self.images[src] if src in converted_images:
continue
_docnames, dest = self.env.images[src]
try: try:
copyfile(path.join(self.srcdir, src), copyfile(path.join(self.srcdir, src),
path.join(self.outdir, self.imagedir, dest)) path.join(self.outdir, self.imagedir, dest))

View File

@ -413,12 +413,15 @@ class LaTeXBuilder(Builder):
copy_asset_file(path.join(self.confdir, filename), self.outdir) copy_asset_file(path.join(self.confdir, filename), self.outdir)
def copy_image_files(self) -> None: def copy_image_files(self) -> None:
if self.images: if self.env.images:
converted_images = {*self.env.original_image_uri.values()}
stringify_func = ImageAdapter(self.app.env).get_original_image_uri stringify_func = ImageAdapter(self.app.env).get_original_image_uri
for src in status_iterator(self.images, __('copying images... '), "brown", for src in status_iterator(self.env.images, __('copying images... '), "brown",
len(self.images), self.app.verbosity, len(self.env.images), self.app.verbosity,
stringify_func=stringify_func): stringify_func=stringify_func):
dest = self.images[src] if src in converted_images:
continue
_docnames, dest = self.env.images[src]
try: try:
copy_asset_file(path.join(self.srcdir, src), copy_asset_file(path.join(self.srcdir, src),
path.join(self.outdir, dest)) path.join(self.outdir, dest))

View File

@ -173,12 +173,15 @@ class TexinfoBuilder(Builder):
self.copy_support_files() self.copy_support_files()
def copy_image_files(self, targetname: str) -> None: def copy_image_files(self, targetname: str) -> None:
if self.images: if self.env.images:
converted_images = {*self.env.original_image_uri.values()}
stringify_func = ImageAdapter(self.app.env).get_original_image_uri stringify_func = ImageAdapter(self.app.env).get_original_image_uri
for src in status_iterator(self.images, __('copying images... '), "brown", for src in status_iterator(self.env.images, __('copying images... '), "brown",
len(self.images), self.app.verbosity, len(self.env.images), self.app.verbosity,
stringify_func=stringify_func): stringify_func=stringify_func):
dest = self.images[src] if src in converted_images:
continue
_docnames, dest = self.env.images[src]
try: try:
imagedir = path.join(self.outdir, targetname + '-figures') imagedir = path.join(self.outdir, targetname + '-figures')
ensuredir(imagedir) ensuredir(imagedir)

View File

@ -2,6 +2,7 @@
import os import os
import subprocess import subprocess
from pathlib import Path
from subprocess import CalledProcessError from subprocess import CalledProcessError
from xml.etree import ElementTree from xml.etree import ElementTree
@ -390,3 +391,22 @@ def test_xml_name_pattern_check():
assert _XML_NAME_PATTERN.match('id-pub') assert _XML_NAME_PATTERN.match('id-pub')
assert _XML_NAME_PATTERN.match('webpage') assert _XML_NAME_PATTERN.match('webpage')
assert not _XML_NAME_PATTERN.match('1bfda21') assert not _XML_NAME_PATTERN.match('1bfda21')
@pytest.mark.sphinx('epub', testroot='images')
def test_copy_images(app, status, warning):
app.build()
images_dir = Path(app.outdir) / '_images'
images = {image.name for image in images_dir.rglob('*')}
assert images == {
'img.gif',
'img.pdf',
'img.png',
'python-logo.png',
'rimg.png',
'rimg1.png',
'svgimg.pdf',
'svgimg.svg',
'testimäge.png',
}

View File

@ -3,6 +3,7 @@
import os import os
import re import re
from itertools import chain, cycle from itertools import chain, cycle
from pathlib import Path
from unittest.mock import ANY, call, patch from unittest.mock import ANY, call, patch
import pytest import pytest
@ -1770,3 +1771,21 @@ def test_theme_having_multiple_stylesheets(app):
assert '<link rel="stylesheet" type="text/css" href="_static/mytheme.css" />' in content assert '<link rel="stylesheet" type="text/css" href="_static/mytheme.css" />' in content
assert '<link rel="stylesheet" type="text/css" href="_static/extra.css" />' in content assert '<link rel="stylesheet" type="text/css" href="_static/extra.css" />' in content
@pytest.mark.sphinx('html', testroot='images')
def test_copy_images(app, status, warning):
app.build()
images_dir = Path(app.outdir) / '_images'
images = {image.name for image in images_dir.rglob('*')}
assert images == {
'img.gif',
'img.pdf',
'img.png',
'rimg.png',
'rimg1.png',
'svgimg.pdf',
'svgimg.svg',
'testimäge.png',
}

View File

@ -4,6 +4,7 @@ import os
import re import re
import subprocess import subprocess
from itertools import product from itertools import product
from pathlib import Path
from shutil import copyfile from shutil import copyfile
from subprocess import CalledProcessError from subprocess import CalledProcessError
@ -1670,3 +1671,25 @@ def test_latex_code_role(app):
common_content + '%\n}} code block') in content common_content + '%\n}} code block') in content
assert (r'\begin{sphinxVerbatim}[commandchars=\\\{\}]' + assert (r'\begin{sphinxVerbatim}[commandchars=\\\{\}]' +
'\n' + common_content + '\n' + r'\end{sphinxVerbatim}') in content '\n' + common_content + '\n' + r'\end{sphinxVerbatim}') in content
@pytest.mark.sphinx('latex', testroot='images')
def test_copy_images(app, status, warning):
app.build()
test_dir = Path(app.outdir)
images = {
image.name for image in test_dir.rglob('*')
if image.suffix in {'.gif', '.pdf', '.png', '.svg'}
}
assert images == {
'img.gif',
'img.pdf',
'img.png',
'python-logo.png',
'rimg.png',
'rimg1.png',
'svgimg.pdf',
'svgimg.svg',
'testimäge.png',
}

View File

@ -3,6 +3,7 @@
import os import os
import re import re
import subprocess import subprocess
from pathlib import Path
from subprocess import CalledProcessError from subprocess import CalledProcessError
from unittest.mock import Mock from unittest.mock import Mock
@ -137,3 +138,22 @@ def test_texinfo_samp_with_variable(app, status, warning):
assert '@code{@var{variable_only}}' in output assert '@code{@var{variable_only}}' in output
assert '@code{@var{variable} and text}' in output assert '@code{@var{variable} and text}' in output
assert '@code{Show @var{variable} in the middle}' in output assert '@code{Show @var{variable} in the middle}' in output
@pytest.mark.sphinx('texinfo', testroot='images')
def test_copy_images(app, status, warning):
app.build()
images_dir = Path(app.outdir) / 'python-figures'
images = {image.name for image in images_dir.rglob('*')}
assert images == {
'img.gif',
'img.pdf',
'img.png',
'python-logo.png',
'rimg.png',
'rimg1.png',
'svgimg.pdf',
'svgimg.svg',
'testimäge.png',
}