-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
docs: translations: add translations links when they exist
Add a new Sphinx extension that knows about the translations of kernel documentation and can insert links to the translations at the top of the document. It basically works like this: 1. Register a new node type, LanguagesNode. 2. Register a new transform, TranslationsTransform, that inserts a new LanguageNode at the top of every document. The LanguageNode contains "pending references" to translations of the document. The key here is that these are pending (i.e. unresolved) references that may or may not actually exist. 3. Register a 'doctree-resolved' event that iterates over all the LanguageNode nodes. Any unresolved references are filtered out; the list of resolved references is passed to the 'translations.html' template and rendered as an HTML node (if HTML output is selected). Testing: make htmldocs, make latexdocs with Sphinx v4.3.2 and Firefox. v2: - changed bar into a drop-down menu - fixed language labels - fixed hysteresis reported by Akira Yokosawa Cc: Federico Vaga <federico.vaga@vaga.pv.it> Cc: Jani Nikula <jani.nikula@linux.intel.com> Cc: Akira Yokosawa <akiyks@gmail.com> Cc: Yanteng Si <siyanteng@loongson.cn> Signed-off-by: Vegard Nossum <vegard.nossum@oracle.com> Signed-off-by: Jonathan Corbet <corbet@lwn.net> Link: https://lore.kernel.org/r/20231215123701.2712807-1-vegard.nossum@oracle.com
- Loading branch information
Vegard Nossum
authored and
Jonathan Corbet
committed
Dec 19, 2023
1 parent
dcd39fa
commit 7418ec5
Showing
4 changed files
with
170 additions
and
1 deletion.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,15 @@ | ||
<!-- SPDX-License-Identifier: GPL-2.0 --> | ||
<!-- Copyright © 2023, Oracle and/or its affiliates. --> | ||
|
||
{# Create a language menu for translations #} | ||
{% if languages|length > 0: %} | ||
<div class="language-selection"> | ||
{{ current_language }} | ||
|
||
<ul> | ||
{% for ref in languages: %} | ||
<li><a href="{{ ref.refuri }}">{{ ref.astext() }}</a></li> | ||
{% endfor %} | ||
</ul> | ||
</div> | ||
{% endif %} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,101 @@ | ||
# SPDX-License-Identifier: GPL-2.0 | ||
# | ||
# Copyright © 2023, Oracle and/or its affiliates. | ||
# Author: Vegard Nossum <vegard.nossum@oracle.com> | ||
# | ||
# Add translation links to the top of the document. | ||
# | ||
|
||
import os | ||
|
||
from docutils import nodes | ||
from docutils.transforms import Transform | ||
|
||
import sphinx | ||
from sphinx import addnodes | ||
from sphinx.errors import NoUri | ||
|
||
all_languages = { | ||
# English is always first | ||
None: 'English', | ||
|
||
# Keep the rest sorted alphabetically | ||
'zh_CN': 'Chinese (Simplified)', | ||
'zh_TW': 'Chinese (Traditional)', | ||
'it_IT': 'Italian', | ||
'ja_JP': 'Japanese', | ||
'ko_KR': 'Korean', | ||
'sp_SP': 'Spanish', | ||
} | ||
|
||
class LanguagesNode(nodes.Element): | ||
def __init__(self, current_language, *args, **kwargs): | ||
super().__init__(*args, **kwargs) | ||
|
||
self.current_language = current_language | ||
|
||
class TranslationsTransform(Transform): | ||
default_priority = 900 | ||
|
||
def apply(self): | ||
app = self.document.settings.env.app | ||
docname = self.document.settings.env.docname | ||
|
||
this_lang_code = None | ||
components = docname.split(os.sep) | ||
if components[0] == 'translations' and len(components) > 2: | ||
this_lang_code = components[1] | ||
|
||
# normalize docname to be the untranslated one | ||
docname = os.path.join(*components[2:]) | ||
|
||
new_nodes = LanguagesNode(all_languages[this_lang_code]) | ||
|
||
for lang_code, lang_name in all_languages.items(): | ||
if lang_code == this_lang_code: | ||
continue | ||
|
||
if lang_code is None: | ||
target_name = docname | ||
else: | ||
target_name = os.path.join('translations', lang_code, docname) | ||
|
||
pxref = addnodes.pending_xref('', refdomain='std', | ||
reftype='doc', reftarget='/' + target_name, modname=None, | ||
classname=None, refexplicit=True) | ||
pxref += nodes.Text(lang_name) | ||
new_nodes += pxref | ||
|
||
self.document.insert(0, new_nodes) | ||
|
||
def process_languages(app, doctree, docname): | ||
for node in doctree.traverse(LanguagesNode): | ||
if app.builder.format not in ['html']: | ||
node.parent.remove(node) | ||
continue | ||
|
||
languages = [] | ||
|
||
# Iterate over the child nodes; any resolved links will have | ||
# the type 'nodes.reference', while unresolved links will be | ||
# type 'nodes.Text'. | ||
languages = list(filter(lambda xref: | ||
isinstance(xref, nodes.reference), node.children)) | ||
|
||
html_content = app.builder.templates.render('translations.html', | ||
context={ | ||
'current_language': node.current_language, | ||
'languages': languages, | ||
}) | ||
|
||
node.replace_self(nodes.raw('', html_content, format='html')) | ||
|
||
def setup(app): | ||
app.add_node(LanguagesNode) | ||
app.add_transform(TranslationsTransform) | ||
app.connect('doctree-resolved', process_languages) | ||
|
||
return { | ||
'parallel_read_safe': True, | ||
'parallel_write_safe': True, | ||
} |