diff options
Diffstat (limited to 'tests/test_build_latex.py')
-rw-r--r-- | tests/test_build_latex.py | 251 |
1 files changed, 232 insertions, 19 deletions
diff --git a/tests/test_build_latex.py b/tests/test_build_latex.py index a8179284c..b2cfd6cbb 100644 --- a/tests/test_build_latex.py +++ b/tests/test_build_latex.py @@ -14,12 +14,14 @@ import os import re from itertools import product from subprocess import Popen, PIPE +from shutil import copyfile from six import PY3 import pytest from sphinx.errors import SphinxError from sphinx.util.osutil import cd, ensuredir +from sphinx.util import docutils from sphinx.writers.latex import LaTeXTranslator from util import SkipTest, remove_unicode_literals, strip_escseq, skip_if @@ -66,6 +68,9 @@ def compile_latex_document(app): with cd(app.outdir): try: ensuredir(app.config.latex_engine) + # keep a copy of latex file for this engine in case test fails + copyfile('SphinxTests.tex', + app.config.latex_engine + '/SphinxTests.tex') p = Popen([app.config.latex_engine, '--interaction=nonstopmode', '-output-directory=%s' % app.config.latex_engine, @@ -479,12 +484,16 @@ def test_footnote(app, status, warning): '{\\phantomsection\\label{\\detokenize{footnote:bar}} ' '\ncite\n}') in result assert '\\caption{Table caption \\sphinxfootnotemark[4]' in result - assert 'name \\sphinxfootnotemark[5]' in result - assert ('\\end{threeparttable}\n\n%\n' - '\\begin{footnotetext}[4]\sphinxAtStartFootnote\n' - 'footnotes in table caption\n%\n\\end{footnotetext}%\n' - '\\begin{footnotetext}[5]\sphinxAtStartFootnote\n' - 'footnotes in table\n%\n\\end{footnotetext}') in result + assert ('\\hline%\n\\begin{footnotetext}[4]\\sphinxAtStartFootnote\n' + 'footnote in table caption\n%\n\\end{footnotetext}\\ignorespaces %\n' + '\\begin{footnotetext}[5]\\sphinxAtStartFootnote\n' + 'footnote in table header\n%\n\\end{footnotetext}\\ignorespaces \n' + 'VIDIOC\\_CROPCAP\n&\n') in result + assert ('Information about VIDIOC\\_CROPCAP %\n' + '\\begin{footnote}[6]\\sphinxAtStartFootnote\n' + 'footnote in table not in header\n%\n\\end{footnote}\n\\\\\n\\hline\n' + '\\end{tabulary}\n\\end{threeparttable}\n' + '\\par\n\\sphinxattableend\\end{savenotes}\n') in result @pytest.mark.sphinx('latex', testroot='footnotes') @@ -506,21 +515,25 @@ def test_reference_in_caption_and_codeblock_in_footnote(app, status, warning): '%\n\\begin{footnotetext}[4]\\sphinxAtStartFootnote\n' 'Footnote in section\n%\n\\end{footnotetext}') in result assert ('\\caption{This is the figure caption with a footnote to ' - '\\sphinxfootnotemark[6].}\label{\\detokenize{index:id27}}\end{figure}\n' + '\\sphinxfootnotemark[6].}\\label{\\detokenize{index:id27}}\\end{figure}\n' '%\n\\begin{footnotetext}[6]\\sphinxAtStartFootnote\n' 'Footnote in caption\n%\n\\end{footnotetext}')in result assert ('\\caption{footnote \\sphinxfootnotemark[7] ' 'in caption of normal table}\\label{\\detokenize{index:id28}}') in result assert ('\\caption{footnote \\sphinxfootnotemark[8] ' - 'in caption \sphinxfootnotemark[9] of longtable}') in result - assert ('\end{longtable}\n\n%\n\\begin{footnotetext}[8]' - '\sphinxAtStartFootnote\n' - 'Foot note in longtable\n%\n\\end{footnotetext}' in result) + 'in caption \\sphinxfootnotemark[9] of longtable\\strut}') in result + assert ('\\endlastfoot\n%\n\\begin{footnotetext}[8]\\sphinxAtStartFootnote\n' + 'Foot note in longtable\n%\n\\end{footnotetext}\\ignorespaces %\n' + '\\begin{footnotetext}[9]\\sphinxAtStartFootnote\n' + 'Second footnote in caption of longtable\n') in result assert ('This is a reference to the code-block in the footnote:\n' - '{\hyperref[\\detokenize{index:codeblockinfootnote}]' + '{\\hyperref[\\detokenize{index:codeblockinfootnote}]' '{\\sphinxcrossref{\\DUrole{std,std-ref}{I am in a footnote}}}}') in result - assert ('&\nThis is one more footnote with some code in it ' - '\\sphinxfootnotemark[10].\n\\\\') in result + assert ('&\nThis is one more footnote with some code in it %\n' + '\\begin{footnote}[10]\\sphinxAtStartFootnote\n' + 'Third footnote in longtable\n') in result + assert ('\\end{sphinxVerbatim}\n\\let\\sphinxVerbatimTitle\\empty\n' + '\\let\\sphinxLiteralBlockLabel\\empty\n%\n\\end{footnote}.\n') in result assert '\\begin{sphinxVerbatim}[commandchars=\\\\\\{\\}]' in result @@ -560,7 +573,8 @@ def test_latex_show_urls_is_inline(app, status, warning): '(http://sphinx-doc.org/)}] \\leavevmode\nDescription' in result) assert ('\\item[{Footnote in term \\sphinxfootnotemark[5]}] ' '\\leavevmode%\n\\begin{footnotetext}[5]\\sphinxAtStartFootnote\n' - 'Footnote in term\n%\n\\end{footnotetext}\nDescription') in result + 'Footnote in term\n%\n\\end{footnotetext}\\ignorespaces \n' + 'Description') in result assert ('\\item[{\\sphinxhref{http://sphinx-doc.org/}{Term in deflist} ' '(http://sphinx-doc.org/)}] \\leavevmode\nDescription') in result assert '\\sphinxurl{https://github.com/sphinx-doc/sphinx}\n' in result @@ -606,15 +620,16 @@ def test_latex_show_urls_is_footnote(app, status, warning): '{URL in term}\\sphinxfootnotemark[8]}] ' '\\leavevmode%\n\\begin{footnotetext}[8]\\sphinxAtStartFootnote\n' '\\sphinxnolinkurl{http://sphinx-doc.org/}\n%\n' - '\\end{footnotetext}\nDescription') in result + '\\end{footnotetext}\\ignorespaces \nDescription') in result assert ('\\item[{Footnote in term \\sphinxfootnotemark[10]}] ' '\\leavevmode%\n\\begin{footnotetext}[10]\\sphinxAtStartFootnote\n' - 'Footnote in term\n%\n\\end{footnotetext}\nDescription') in result + 'Footnote in term\n%\n\\end{footnotetext}\\ignorespaces \n' + 'Description') in result assert ('\\item[{\\sphinxhref{http://sphinx-doc.org/}{Term in deflist}' '\\sphinxfootnotemark[9]}] ' '\\leavevmode%\n\\begin{footnotetext}[9]\\sphinxAtStartFootnote\n' '\\sphinxnolinkurl{http://sphinx-doc.org/}\n%\n' - '\\end{footnotetext}\nDescription') in result + '\\end{footnotetext}\\ignorespaces \nDescription') in result assert ('\\sphinxurl{https://github.com/sphinx-doc/sphinx}\n' in result) assert ('\\sphinxhref{mailto:sphinx-dev@googlegroups.com}' '{sphinx-dev@googlegroups.com}\n') in result @@ -654,7 +669,8 @@ def test_latex_show_urls_is_no(app, status, warning): '\\leavevmode\nDescription') in result assert ('\\item[{Footnote in term \\sphinxfootnotemark[5]}] ' '\\leavevmode%\n\\begin{footnotetext}[5]\\sphinxAtStartFootnote\n' - 'Footnote in term\n%\n\\end{footnotetext}\nDescription') in result + 'Footnote in term\n%\n\\end{footnotetext}\\ignorespaces \n' + 'Description') in result assert ('\\item[{\\sphinxhref{http://sphinx-doc.org/}{Term in deflist}}] ' '\\leavevmode\nDescription') in result assert ('\\sphinxurl{https://github.com/sphinx-doc/sphinx}\n' in result) @@ -814,3 +830,200 @@ def test_maxlistdepth_at_ten(app, status, warning): print(status.getvalue()) print(warning.getvalue()) compile_latex_document(app) + + +@pytest.mark.skipif(docutils.__version_info__ < (0, 13), + reason='docutils-0.13 or above is required') +@pytest.mark.sphinx('latex', testroot='latex-table') +@pytest.mark.test_params(shared_result='test_latex_table') +def test_latex_table_tabulars(app, status, warning): + app.builder.build_all() + result = (app.outdir / 'test.tex').text(encoding='utf8') + tables = {} + for chap in re.split(r'\\section{', result)[1:]: + sectname, content = chap.split('}', 1) + tables[sectname] = content.strip() + + # simple_table + table = tables['simple table'] + assert ('\\begin{savenotes}\\sphinxattablestart\n\\centering\n' + '\\begin{tabulary}{\\linewidth}[t]{|T|T|}' in table) + assert ('\\hline\n' + '\\sphinxstylethead{\\relax \nheader1\n\\unskip}\\relax &' + '\\sphinxstylethead{\\relax \nheader2\n\\unskip}\\relax' in table) + assert ('\\hline\ncell1-1\n&\ncell1-2\n\\\\' in table) + assert ('\\hline\ncell2-1\n&\ncell2-2\n\\\\' in table) + assert ('\\hline\ncell3-1\n&\ncell3-2\n\\\\' in table) + assert ('\\hline\n\\end{tabulary}\n\\par\n' + '\\sphinxattableend\\end{savenotes}' in table) + + # table having :widths: option + table = tables['table having :widths: option'] + assert ('\\begin{savenotes}\\sphinxattablestart\n\\centering\n' + '\\begin{tabular}[t]{|\\X{30}{100}|\\X{70}{100}|}' in table) + assert ('\\hline\n\\end{tabular}\n\\par\n' + '\\sphinxattableend\\end{savenotes}' in table) + + # table having :align: option (tabulary) + table = tables['table having :align: option (tabulary)'] + assert ('\\begin{savenotes}\\sphinxattablestart\n\\raggedleft\n' + '\\begin{tabulary}{\\linewidth}[t]{|T|T|}\n' in table) + assert ('\\hline\n\\end{tabulary}\n\\par\n' + '\\sphinxattableend\\end{savenotes}' in table) + + # table having :align: option (tabular) + table = tables['table having :align: option (tabular)'] + assert ('\\begin{savenotes}\\sphinxattablestart\n\\raggedright\n' + '\\begin{tabular}[t]{|\\X{30}{100}|\\X{70}{100}|}\n' in table) + assert ('\\hline\n\\end{tabular}\n\\par\n' + '\\sphinxattableend\\end{savenotes}' in table) + + # table with tabularcolumn + table = tables['table with tabularcolumn'] + assert ('\\begin{tabulary}{\\linewidth}[t]{|c|c|}' in table) + + # table having caption + table = tables['table having caption'] + assert ('\\begin{savenotes}\\sphinxattablestart\n\\centering\n' + '\\begin{threeparttable}\n\\capstart\\caption{caption for table}' + '\\label{\\detokenize{tabular:id1}}' in table) + assert ('\\begin{tabulary}{\\linewidth}[t]{|T|T|}' in table) + assert ('\\hline\n\\end{tabulary}\n\\end{threeparttable}' + '\n\\par\n\\sphinxattableend\\end{savenotes}' in table) + + # table having verbatim + table = tables['table having verbatim'] + assert ('\\begin{tabular}[t]{|*{2}{\\X{1}{2}|}}\n\\hline' in table) + + # table having problematic cell + table = tables['table having problematic cell'] + assert ('\\begin{tabular}[t]{|*{2}{\\X{1}{2}|}}\n\\hline' in table) + + # table having both :widths: and problematic cell + table = tables['table having both :widths: and problematic cell'] + assert ('\\begin{tabular}[t]{|\\X{30}{100}|\\X{70}{100}|}' in table) + + +@pytest.mark.skipif(docutils.__version_info__ < (0, 13), + reason='docutils-0.13 or above is required') +@pytest.mark.sphinx('latex', testroot='latex-table') +@pytest.mark.test_params(shared_result='test_latex_table') +def test_latex_table_longtable(app, status, warning): + app.builder.build_all() + result = (app.outdir / 'test.tex').text(encoding='utf8') + tables = {} + for chap in re.split(r'\\section{', result)[1:]: + sectname, content = chap.split('}', 1) + tables[sectname] = content.strip() + + # longtable + table = tables['longtable'] + assert ('\\begin{savenotes}\\sphinxatlongtablestart' + '\\begin{longtable}{|l|l|}\n\\hline' in table) + assert ('\\hline\n' + '\\sphinxstylethead{\\relax \nheader1\n\\unskip}\\relax &' + '\\sphinxstylethead{\\relax \nheader2\n\\unskip}\\relax \\\\\n' + '\\hline\n\\endfirsthead' in table) + assert ('\\multicolumn{2}{c}%\n' + '{\\makebox[0pt]{\\sphinxtablecontinued{\\tablename\\ \\thetable{} -- ' + 'continued from previous page}}}\\\\\n\\hline\n' + '\\sphinxstylethead{\\relax \nheader1\n\\unskip}\\relax &' + '\\sphinxstylethead{\\relax \nheader2\n\\unskip}\\relax \\\\\n' + '\\hline\n\\endhead' in table) + assert ('\\hline\n\\multicolumn{2}{r}' + '{\\makebox[0pt][r]{\\sphinxtablecontinued{Continued on next page}}}\\\\\n' + '\\endfoot\n\n\\endlastfoot' in table) + assert ('\ncell1-1\n&\ncell1-2\n\\\\' in table) + assert ('\\hline\ncell2-1\n&\ncell2-2\n\\\\' in table) + assert ('\\hline\ncell3-1\n&\ncell3-2\n\\\\' in table) + assert ('\\hline\n\\end{longtable}\\sphinxatlongtableend\\end{savenotes}' in table) + + # longtable having :widths: option + table = tables['longtable having :widths: option'] + assert ('\\begin{longtable}{|\\X{30}{100}|\\X{70}{100}|}' in table) + + # longtable having :align: option + table = tables['longtable having :align: option'] + assert ('\\begin{longtable}[r]{|l|l|}\n' in table) + assert ('\\hline\n\\end{longtable}' in table) + + # longtable with tabularcolumn + table = tables['longtable with tabularcolumn'] + assert ('\\begin{longtable}{|c|c|}' in table) + + # longtable having caption + table = tables['longtable having caption'] + assert ('\\begin{longtable}{|l|l|}\n\\caption{caption for longtable\\strut}' + '\\label{\\detokenize{longtable:id1}}' + '\\\\*[\\sphinxlongtablecapskipadjust]\n\\hline' in table) + + # longtable having verbatim + table = tables['longtable having verbatim'] + assert ('\\begin{longtable}{|*{2}{\\X{1}{2}|}}\n\\hline' in table) + + # longtable having problematic cell + table = tables['longtable having problematic cell'] + assert ('\\begin{longtable}{|*{2}{\\X{1}{2}|}}\n\\hline' in table) + + # longtable having both :widths: and problematic cell + table = tables['longtable having both :widths: and problematic cell'] + assert ('\\begin{longtable}{|\\X{30}{100}|\\X{70}{100}|}' in table) + + +@pytest.mark.skipif(docutils.__version_info__ < (0, 13), + reason='docutils-0.13 or above is required') +@pytest.mark.sphinx('latex', testroot='latex-table') +@pytest.mark.test_params(shared_result='test_latex_table') +def test_latex_table_complex_tables(app, status, warning): + app.builder.build_all() + result = (app.outdir / 'test.tex').text(encoding='utf8') + tables = {} + for chap in re.split(r'\\section{', result)[1:]: + sectname, content = chap.split('}', 1) + tables[sectname] = content.strip() + + # grid table + table = tables['grid table'] + assert ('\\begin{tabulary}{\\linewidth}[t]{|T|T|T|}' in table) + assert ('\\hline\n' + '\\sphinxstylethead{\\relax \nheader1\n\\unskip}\\relax &' + '\\sphinxstylethead{\\relax \nheader2\n\\unskip}\\relax &' + '\\sphinxstylethead{\\relax \nheader3\n\\unskip}\\relax \\\\' in table) + assert ('\\hline\ncell1-1\n&\\sphinxmultirow{2}{5}{%\n\\begin{varwidth}[t]' + '{\\sphinxcolwidth{1}{3}}\n' + 'cell1-2\n\\par\n' in table) + assert ('\\cline{1-1}\\cline{3-3}\\sphinxmultirow{2}{7}{%\n' in table) + assert ('&\\sphinxtablestrut{5}&\ncell2-3\n\\\\\n' + '\\cline{2-3}\\sphinxtablestrut{7}&\\sphinxstartmulticolumn{2}%\n' + '\\sphinxmultirow{2}{9}{%\n\\begin{varwidth}' in table) + assert ('\\cline{1-1}\ncell4-1\n&\\multicolumn{2}{l|}' + '{\\sphinxtablestrut{9}}\\\\' in table) + assert ('\\hline\\sphinxstartmulticolumn{3}%\n' + in table) + + # complex spanning cell + table = tables['complex spanning cell'] + assert ('\\begin{tabulary}{\\linewidth}[t]{|T|T|T|T|T|}' in table) + assert ('\\sphinxmultirow{3}{1}{%\n' + '\\begin{varwidth}[t]{\\sphinxcolwidth{1}{5}}\n' + 'cell1-1\n\\par\n\\vskip-\\baselineskip\\strut\\end{varwidth}%\n' + '}%\n' + '&\\sphinxmultirow{3}{2}{%\n' + '\\begin{varwidth}[t]{\\sphinxcolwidth{1}{5}}\n' + 'cell1-2\n\\par\n\\vskip-\\baselineskip\\strut\\end{varwidth}%\n' + '}%\n&\ncell1-3\n&\\sphinxmultirow{3}{4}{%\n' + '\\begin{varwidth}[t]{\\sphinxcolwidth{1}{5}}\n' + 'cell1-4\n\\par\n\\vskip-\\baselineskip\\strut\\end{varwidth}%\n' + '}%\n' + '&\\sphinxmultirow{2}{5}{%\n' + '\\begin{varwidth}[t]{\\sphinxcolwidth{1}{5}}\n' + 'cell1-5\n' + in table) + assert ('\\cline{3-3}\\sphinxtablestrut{1}&\\sphinxtablestrut{2}&' + '\\sphinxmultirow{2}{6}{%\n' + in table) + assert ('&\\sphinxtablestrut{4}&\\sphinxtablestrut{5}\\\\\n' + '\\cline{5-5}\\sphinxtablestrut{1}&\\sphinxtablestrut{2}&' + '\\sphinxtablestrut{6}&\\sphinxtablestrut{4}&\ncell3-5\n' + '\\\\\n\\hline\n\\end{tabulary}\n' + in table) |