1""" 2 test_build_gettext 3 ~~~~~~~~~~~~~~~~~~ 4 5 Test the build process with gettext builder with the test root. 6 7 :copyright: Copyright 2007-2021 by the Sphinx team, see AUTHORS. 8 :license: BSD, see LICENSE for details. 9""" 10 11import gettext 12import os 13import re 14import subprocess 15from subprocess import PIPE, CalledProcessError 16 17import pytest 18 19from sphinx.util.osutil import cd 20 21 22@pytest.mark.sphinx('gettext', srcdir='root-gettext') 23def test_build_gettext(app): 24 # Generic build; should fail only when the builder is horribly broken. 25 app.builder.build_all() 26 27 # Do messages end up in the correct location? 28 # top-level documents end up in a message catalog 29 assert (app.outdir / 'extapi.pot').isfile() 30 # directory items are grouped into sections 31 assert (app.outdir / 'subdir.pot').isfile() 32 33 # regression test for issue #960 34 catalog = (app.outdir / 'markup.pot').read_text() 35 assert 'msgid "something, something else, something more"' in catalog 36 37 38@pytest.mark.sphinx('gettext', srcdir='root-gettext') 39def test_msgfmt(app): 40 app.builder.build_all() 41 (app.outdir / 'en' / 'LC_MESSAGES').makedirs() 42 with cd(app.outdir): 43 try: 44 args = ['msginit', '--no-translator', '-i', 'markup.pot', '--locale', 'en_US'] 45 subprocess.run(args, stdout=PIPE, stderr=PIPE, check=True) 46 except OSError: 47 pytest.skip() # most likely msginit was not found 48 except CalledProcessError as exc: 49 print(exc.stdout) 50 print(exc.stderr) 51 assert False, 'msginit exited with return code %s' % exc.returncode 52 53 assert (app.outdir / 'en_US.po').isfile(), 'msginit failed' 54 try: 55 args = ['msgfmt', 'en_US.po', 56 '-o', os.path.join('en', 'LC_MESSAGES', 'test_root.mo')] 57 subprocess.run(args, stdout=PIPE, stderr=PIPE, check=True) 58 except OSError: 59 pytest.skip() # most likely msgfmt was not found 60 except CalledProcessError as exc: 61 print(exc.stdout) 62 print(exc.stderr) 63 assert False, 'msgfmt exited with return code %s' % exc.returncode 64 65 mo = app.outdir / 'en' / 'LC_MESSAGES' / 'test_root.mo' 66 assert mo.isfile(), 'msgfmt failed' 67 68 _ = gettext.translation('test_root', app.outdir, languages=['en']).gettext 69 assert _("Testing various markup") == "Testing various markup" 70 71 72@pytest.mark.sphinx( 73 'gettext', testroot='intl', srcdir='gettext', 74 confoverrides={'gettext_compact': False}) 75def test_gettext_index_entries(app): 76 # regression test for #976 77 app.builder.build(['index_entries']) 78 79 _msgid_getter = re.compile(r'msgid "(.*)"').search 80 81 def msgid_getter(msgid): 82 m = _msgid_getter(msgid) 83 if m: 84 return m.groups()[0] 85 return None 86 87 pot = (app.outdir / 'index_entries.pot').read_text() 88 msgids = [_f for _f in map(msgid_getter, pot.splitlines()) if _f] 89 90 expected_msgids = [ 91 "i18n with index entries", 92 "index target section", 93 "this is :index:`Newsletter` target paragraph.", 94 "various index entries", 95 "That's all.", 96 "Mailing List", 97 "Newsletter", 98 "Recipients List", 99 "First", 100 "Second", 101 "Third", 102 "Entry", 103 "See", 104 "Module", 105 "Keyword", 106 "Operator", 107 "Object", 108 "Exception", 109 "Statement", 110 "Builtin", 111 ] 112 for expect in expected_msgids: 113 assert expect in msgids 114 msgids.remove(expect) 115 116 # unexpected msgid existent 117 assert msgids == [] 118 119 120@pytest.mark.sphinx( 121 'gettext', testroot='intl', srcdir='gettext', 122 confoverrides={'gettext_compact': False, 123 'gettext_additional_targets': []}) 124def test_gettext_disable_index_entries(app): 125 # regression test for #976 126 app.builder.build(['index_entries']) 127 128 _msgid_getter = re.compile(r'msgid "(.*)"').search 129 130 def msgid_getter(msgid): 131 m = _msgid_getter(msgid) 132 if m: 133 return m.groups()[0] 134 return None 135 136 pot = (app.outdir / 'index_entries.pot').read_text() 137 msgids = [_f for _f in map(msgid_getter, pot.splitlines()) if _f] 138 139 expected_msgids = [ 140 "i18n with index entries", 141 "index target section", 142 "this is :index:`Newsletter` target paragraph.", 143 "various index entries", 144 "That's all.", 145 ] 146 for expect in expected_msgids: 147 assert expect in msgids 148 msgids.remove(expect) 149 150 # unexpected msgid existent 151 assert msgids == [] 152 153 154@pytest.mark.sphinx('gettext', testroot='intl', srcdir='gettext') 155def test_gettext_template(app): 156 app.builder.build_all() 157 assert (app.outdir / 'sphinx.pot').isfile() 158 159 result = (app.outdir / 'sphinx.pot').read_text() 160 assert "Welcome" in result 161 assert "Sphinx %(version)s" in result 162 163 164@pytest.mark.sphinx('gettext', testroot='gettext-template') 165def test_gettext_template_msgid_order_in_sphinxpot(app): 166 app.builder.build_all() 167 assert (app.outdir / 'sphinx.pot').isfile() 168 169 result = (app.outdir / 'sphinx.pot').read_text() 170 assert re.search( 171 ('msgid "Template 1".*' 172 'msgid "This is Template 1\\.".*' 173 'msgid "Template 2".*' 174 'msgid "This is Template 2\\.".*'), 175 result, 176 flags=re.S) 177 178 179@pytest.mark.sphinx( 180 'gettext', srcdir='root-gettext', 181 confoverrides={'gettext_compact': 'documentation'}) 182def test_build_single_pot(app): 183 app.builder.build_all() 184 185 assert (app.outdir / 'documentation.pot').isfile() 186 187 result = (app.outdir / 'documentation.pot').read_text() 188 assert re.search( 189 ('msgid "Todo".*' 190 'msgid "Like footnotes.".*' 191 'msgid "The minute.".*' 192 'msgid "Generated section".*'), 193 result, 194 flags=re.S) 195