fix #4938: i18n doesn't handle node.title correctly (#4939)

This commit is contained in:
Takayuki SHIMIZUKAWA 2018-05-11 20:51:07 +09:00 committed by GitHub
parent ab101744f2
commit 79650f5827
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
12 changed files with 191 additions and 5 deletions

View File

@ -247,13 +247,32 @@ class Locale(SphinxTransform):
if isinstance(node, LITERAL_TYPE_NODES):
msgstr = '::\n\n' + indent(msgstr, ' ' * 3)
# Structural Subelements phase1
# There is a possibility that only the title node is created.
# see: http://docutils.sourceforge.net/docs/ref/doctree.html#structural-subelements
if isinstance(node, nodes.title):
# This generates: <section ...><title>msgstr</title></section>
msgstr = msgstr + '\n' + '-' * len(msgstr) * 2
patch = publish_msgstr(self.app, msgstr, source,
node.line, self.config, settings)
# XXX doctest and other block markup
if not isinstance(
patch,
(nodes.paragraph,) + LITERAL_TYPE_NODES + IMAGE_TYPE_NODES):
continue # skip for now
# Structural Subelements phase2
if isinstance(node, nodes.title):
# get <title> node that placed as a first child
patch = patch.next_node()
# ignore unexpected markups in translation message
if not isinstance(patch, (
(nodes.paragraph, # expected form of translation
nodes.title, # generated by above "Subelements phase2"
) +
# following types are expected if
# config.gettext_additional_targets is configured
LITERAL_TYPE_NODES +
IMAGE_TYPE_NODES
)):
continue # skip
# auto-numbered foot note reference should use original 'ids'.
def is_autonumber_footnote_ref(node):

View File

@ -47,6 +47,11 @@ def apply_source_workaround(node):
node.rawsource = node.astext() # set 'classifier1' (or 'classifier2')
if isinstance(node, nodes.image) and node.source is None:
node.source, node.line = node.parent.source, node.parent.line
if isinstance(node, nodes.title) and node.source is None:
# Uncomment these lines after merging into master(1.8)
# logger.debug('[i18n] PATCH: %r to have source: %s',
# get_full_module_name(node), repr_domxml(node))
node.source, node.line = node.parent.source, node.parent.line
if isinstance(node, nodes.term):
# strip classifier from rawsource of term
for classifier in reversed(node.parent.traverse(nodes.classifier)):

View File

@ -79,3 +79,6 @@ msgstr "ADMONITION TITLE"
msgid "admonition body"
msgstr "ADMONITION BODY"
msgid "1. admonition title"
msgstr "1. ADMONITION TITLE"

View File

@ -44,3 +44,7 @@ Admonitions
admonition body
.. admonition:: 1. admonition title
admonition body

View File

@ -28,3 +28,5 @@ CONTENTS
docfields
raw
refs
section
topic

View File

@ -0,0 +1,28 @@
# SOME DESCRIPTIVE TITLE.
# Copyright (C) 2018, dev
# This file is distributed under the same license as the sphinx package.
# FIRST AUTHOR <EMAIL@ADDRESS>, 2018.
#
#, fuzzy
msgid ""
msgstr ""
"Project-Id-Version: sphinx 1.0\n"
"Report-Msgid-Bugs-To: \n"
"POT-Creation-Date: 2018-05-06 16:44+0900\n"
"PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n"
"Last-Translator: FULL NAME <EMAIL@ADDRESS>\n"
"Language-Team: LANGUAGE <LL@li.org>\n"
"MIME-Version: 1.0\n"
"Content-Type: text/plain; charset=utf-8\n"
"Content-Transfer-Encoding: 8bit\n"
"Generated-By: Babel 2.4.0\n"
msgid "1. Section"
msgstr "1. SECTION"
msgid "2. Sub Section"
msgstr "2. SUB SECTION"
msgid "3. Contents Title"
msgstr "3. CONTENTS TITLE"

View File

@ -0,0 +1,8 @@
1. Section
==========
.. contents:: 3. Contents Title
:local:
2. Sub Section
--------------

View File

@ -48,3 +48,7 @@ msgstr "TEXT5"
msgid "text6"
msgstr "TEXT6"
msgid "1. table caption"
msgstr "1. TABLE CAPTION"

View File

@ -12,3 +12,9 @@ i18n with table
text3 text4
text5 text6
======= =======
.. table:: 1. table caption
+-----+
|text1|
+-----+

View File

@ -0,0 +1,31 @@
# SOME DESCRIPTIVE TITLE.
# Copyright (C) 2018, dev
# This file is distributed under the same license as the sphinx package.
# FIRST AUTHOR <EMAIL@ADDRESS>, 2018.
#
#, fuzzy
msgid ""
msgstr ""
"Project-Id-Version: sphinx 1.0\n"
"Report-Msgid-Bugs-To: \n"
"POT-Creation-Date: 2018-05-06 16:44+0900\n"
"PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n"
"Last-Translator: FULL NAME <EMAIL@ADDRESS>\n"
"Language-Team: LANGUAGE <LL@li.org>\n"
"MIME-Version: 1.0\n"
"Content-Type: text/plain; charset=utf-8\n"
"Content-Transfer-Encoding: 8bit\n"
"Generated-By: Babel 2.4.0\n"
msgid "i18n with topic"
msgstr "I18N WITH TOPIC"
msgid "Topic Title"
msgstr "TOPIC TITLE"
msgid "Topic Content"
msgstr "TOPIC CONTENT"
msgid "1. Topic Title"
msgstr "1. TOPIC TITLE"

View File

@ -0,0 +1,13 @@
:tocdepth: 2
i18n with topic
================
.. topic:: Topic Title
Topic Content
.. topic:: 1. Topic Title
Topic Content

View File

@ -306,6 +306,30 @@ def test_text_glossary_term_inconsistencies(app, warning):
assert_re_search(expected_warning_expr, warnings)
@sphinx_intl
@pytest.mark.sphinx('gettext')
@pytest.mark.test_params(shared_result='test_intl_gettext')
def test_gettext_section(app):
app.build()
# --- section
expect = read_po(app.srcdir / 'section.po')
actual = read_po(app.outdir / 'section.pot')
for expect_msg in [m for m in expect if m.id]:
assert expect_msg.id in [m.id for m in actual if m.id]
@sphinx_intl
@pytest.mark.sphinx('text')
@pytest.mark.test_params(shared_result='test_intl_basic')
def test_text_section(app):
app.build()
# --- section
result = (app.outdir / 'section.txt').text(encoding='utf-8')
expect = read_po(app.srcdir / 'section.po')
for expect_msg in [m for m in expect if m.id]:
assert expect_msg.string in result
@sphinx_intl
@pytest.mark.sphinx('text')
@pytest.mark.test_params(shared_result='test_intl_basic')
@ -428,6 +452,9 @@ def test_text_admonitions(app):
assert d.upper() + " TITLE" in result
assert d.upper() + " BODY" in result
# for #4938 `1. ` prefixed admonition title
assert "1. ADMONITION TITLE" in result
@sphinx_intl
@pytest.mark.sphinx('gettext')
@ -453,6 +480,42 @@ def test_gettext_table(app):
assert expect_msg.id in [m.id for m in actual if m.id]
@sphinx_intl
@pytest.mark.sphinx('text')
@pytest.mark.test_params(shared_result='test_intl_basic')
def test_text_table(app):
app.build()
# --- toctree
result = (app.outdir / 'table.txt').text(encoding='utf-8')
expect = read_po(app.srcdir / 'table.po')
for expect_msg in [m for m in expect if m.id]:
assert expect_msg.string in result
@sphinx_intl
@pytest.mark.sphinx('gettext')
@pytest.mark.test_params(shared_result='test_intl_gettext')
def test_gettext_topic(app):
app.build()
# --- topic
expect = read_po(app.srcdir / 'topic.po')
actual = read_po(app.outdir / 'topic.pot')
for expect_msg in [m for m in expect if m.id]:
assert expect_msg.id in [m.id for m in actual if m.id]
@sphinx_intl
@pytest.mark.sphinx('text')
@pytest.mark.test_params(shared_result='test_intl_basic')
def test_text_topic(app):
app.build()
# --- topic
result = (app.outdir / 'topic.txt').text(encoding='utf-8')
expect = read_po(app.srcdir / 'topic.po')
for expect_msg in [m for m in expect if m.id]:
assert expect_msg.string in result
@sphinx_intl
@pytest.mark.sphinx('gettext')
@pytest.mark.test_params(shared_result='test_intl_gettext')