From 3406322bd31f4d44ffa2fed39ca09d2c3bffb0e6 Mon Sep 17 00:00:00 2001 From: Alexander Rose Date: Wed, 6 Mar 2024 17:05:06 +0100 Subject: [PATCH 1/5] read overrides from po files --- mkdocs_static_i18n/config.py | 10 ++++ mkdocs_static_i18n/reconfigure.py | 85 +++++++++++++++++++++---------- 2 files changed, 69 insertions(+), 26 deletions(-) diff --git a/mkdocs_static_i18n/config.py b/mkdocs_static_i18n/config.py index 7717a85..061a635 100644 --- a/mkdocs_static_i18n/config.py +++ b/mkdocs_static_i18n/config.py @@ -80,6 +80,15 @@ def validate(self): return failed, warnings +class I18nPoOverridesConfig(Config): + """configure the user overrides which should be read from a po file""" + + po_dir = config_options.Type(str, default="") + override = config_options.Optional( + config_options.ListOfItems(config_options.Type(str)) + ) + + class I18nPluginConfig(Config): """ """ @@ -91,6 +100,7 @@ class I18nPluginConfig(Config): languages = config_options.ListOfItems( config_options.SubConfig(I18nPluginLanguage, validate=True) ) + po_overrides = config_options.SubConfig(I18nPoOverridesConfig, validate=True) def validate(self): failed, warnings = super().validate() diff --git a/mkdocs_static_i18n/reconfigure.py b/mkdocs_static_i18n/reconfigure.py index 682fd8f..abede23 100644 --- a/mkdocs_static_i18n/reconfigure.py +++ b/mkdocs_static_i18n/reconfigure.py @@ -1,9 +1,11 @@ from collections import defaultdict from copy import deepcopy +from os import path from pathlib import Path, PurePath from typing import Union from urllib.parse import urlsplit +from babel.messages import pofile from mkdocs import localization from mkdocs.config.base import LegacyConfig from mkdocs.config.defaults import MkDocsConfig @@ -77,6 +79,32 @@ log.warning("Unable to detect lunr languages from mkdocs distribution") MKDOCS_THEMES = ["mkdocs", "readthedocs"] +# some config overrides are forbidden as they make no sense +FORBIDDEN_CONFIG_OVERRIDES = [ + "dev_addr", + "docs_dir", + "edit_uri_template", + "edit_uri", + "exclude_docs", + "extra_css", + "extra_javascript", + "extra_templates", + "hooks", + "markdown_extensions", + "mdx_configs", + "not_in_nav", + "plugins", + "remote_branch", + "remote_name", + "repo_name", + "repo_url", + "site_dir", + "strict", + "use_directory_urls", + "validation", + "watch", +] + class ExtendedPlugin(BasePlugin[I18nPluginConfig]): def __init__(self, *args, **kwargs): @@ -197,37 +225,42 @@ def apply_user_overrides(self, config: MkDocsConfig): # altered by a previous build config = self.reset_to_original_config(config) - # some config overrides are forbidden as they make no sense - forbidden_config_overrides = [ - "dev_addr", - "docs_dir", - "edit_uri_template", - "edit_uri", - "exclude_docs", - "extra_css", - "extra_javascript", - "extra_templates", - "hooks", - "markdown_extensions", - "mdx_configs", - "not_in_nav", - "plugins", - "remote_branch", - "remote_name", - "repo_name", - "repo_url", - "site_dir", - "strict", - "use_directory_urls", - "validation", - "watch", - ] + overrides = dict() + # read po file if configured and override array is not empty + if self.config.po_overrides is not None and self.config.po_overrides.override: + po_file = path.join(self.config.po_overrides, self.current_language + ".po") + if path.exists(po_file): + with open(po_file, "r") as fs: + catalog = pofile.read_po(fs) + + for key in self.config.po_overrides.override: + if key in FORBIDDEN_CONFIG_OVERRIDES: + log.warning( + f"Ignoring forbidden '{self.current_language}' po override '{key}'" + ) + continue + translation = catalog.get(key) + if translation: + overrides[key] = translation + else: + log.warning(f"translation for \"'{key}'\" not found in catalog '{po_file}'") + else: + log.warning(f"translation catalog '{po_file}' not found") + + # read explicitly configured overrides for lang_key, lang_override in self.current_language_config.items(): - if lang_key in forbidden_config_overrides: + if lang_key in FORBIDDEN_CONFIG_OVERRIDES: log.warning( f"Ignoring forbidden '{self.current_language}' config override '{lang_key}'" ) continue + if lang_key in overrides: + log.warning( + f"Overwriting po override '{lang_key}' with explicitly configured version" + ) + overrides[lang_key] = lang_override + + for lang_key, lang_override in overrides.items(): if lang_key in config.data and lang_override is not None: mkdocs_config_option_type = type(config.data[lang_key]) # support special Theme object overrides From 413ca945658237687fc40485392270e15bfc29ee Mon Sep 17 00:00:00 2001 From: Alexander Rose Date: Thu, 7 Mar 2024 08:20:05 +0100 Subject: [PATCH 2/5] make po_dir relative to config file path --- mkdocs_static_i18n/reconfigure.py | 8 +++++--- 1 file changed, 5 insertions(+), 3 deletions(-) diff --git a/mkdocs_static_i18n/reconfigure.py b/mkdocs_static_i18n/reconfigure.py index abede23..61a1974 100644 --- a/mkdocs_static_i18n/reconfigure.py +++ b/mkdocs_static_i18n/reconfigure.py @@ -1,6 +1,6 @@ from collections import defaultdict from copy import deepcopy -from os import path +import os.path from pathlib import Path, PurePath from typing import Union from urllib.parse import urlsplit @@ -228,8 +228,10 @@ def apply_user_overrides(self, config: MkDocsConfig): overrides = dict() # read po file if configured and override array is not empty if self.config.po_overrides is not None and self.config.po_overrides.override: - po_file = path.join(self.config.po_overrides, self.current_language + ".po") - if path.exists(po_file): + po_file = os.path.normpath( + os.path.join(config.config_file_path, self.config.po_overrides, self.current_language + ".po") + ) + if os.path.exists(po_file): with open(po_file, "r") as fs: catalog = pofile.read_po(fs) From d6b1158903f78be6c03618eca050317238a47c32 Mon Sep 17 00:00:00 2001 From: Alexander Rose Date: Thu, 7 Mar 2024 08:23:23 +0100 Subject: [PATCH 3/5] fix building po file path --- mkdocs_static_i18n/reconfigure.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/mkdocs_static_i18n/reconfigure.py b/mkdocs_static_i18n/reconfigure.py index 61a1974..f43f7ef 100644 --- a/mkdocs_static_i18n/reconfigure.py +++ b/mkdocs_static_i18n/reconfigure.py @@ -229,7 +229,7 @@ def apply_user_overrides(self, config: MkDocsConfig): # read po file if configured and override array is not empty if self.config.po_overrides is not None and self.config.po_overrides.override: po_file = os.path.normpath( - os.path.join(config.config_file_path, self.config.po_overrides, self.current_language + ".po") + os.path.join(config.config_file_path, self.config.po_overrides.po_dir, self.current_language + ".po") ) if os.path.exists(po_file): with open(po_file, "r") as fs: From e927f6e90b34086668f849b94e1369e596eaaf23 Mon Sep 17 00:00:00 2001 From: Alexander Rose Date: Thu, 7 Mar 2024 11:25:02 +0100 Subject: [PATCH 4/5] fix code style --- mkdocs_static_i18n/config.py | 4 +--- mkdocs_static_i18n/reconfigure.py | 38 +++++++++++++++++++++---------- 2 files changed, 27 insertions(+), 15 deletions(-) diff --git a/mkdocs_static_i18n/config.py b/mkdocs_static_i18n/config.py index 061a635..0052add 100644 --- a/mkdocs_static_i18n/config.py +++ b/mkdocs_static_i18n/config.py @@ -84,9 +84,7 @@ class I18nPoOverridesConfig(Config): """configure the user overrides which should be read from a po file""" po_dir = config_options.Type(str, default="") - override = config_options.Optional( - config_options.ListOfItems(config_options.Type(str)) - ) + override = config_options.Optional(config_options.ListOfItems(config_options.Type(str))) class I18nPluginConfig(Config): diff --git a/mkdocs_static_i18n/reconfigure.py b/mkdocs_static_i18n/reconfigure.py index f43f7ef..6430753 100644 --- a/mkdocs_static_i18n/reconfigure.py +++ b/mkdocs_static_i18n/reconfigure.py @@ -1,6 +1,6 @@ +import os.path from collections import defaultdict from copy import deepcopy -import os.path from pathlib import Path, PurePath from typing import Union from urllib.parse import urlsplit @@ -229,10 +229,14 @@ def apply_user_overrides(self, config: MkDocsConfig): # read po file if configured and override array is not empty if self.config.po_overrides is not None and self.config.po_overrides.override: po_file = os.path.normpath( - os.path.join(config.config_file_path, self.config.po_overrides.po_dir, self.current_language + ".po") + os.path.join( + os.path.dirname(config.config_file_path), + self.config.po_overrides.po_dir, + self.current_language + ".po", + ) ) if os.path.exists(po_file): - with open(po_file, "r") as fs: + with open(po_file, "r", encoding="utf-8") as fs: catalog = pofile.read_po(fs) for key in self.config.po_overrides.override: @@ -241,11 +245,20 @@ def apply_user_overrides(self, config: MkDocsConfig): f"Ignoring forbidden '{self.current_language}' po override '{key}'" ) continue - translation = catalog.get(key) - if translation: - overrides[key] = translation + # get original value + if config.__contains__(key) and config[key]: + msgid = config[key] + translation = catalog.get(msgid) + if translation is not None: + overrides[key] = translation.string + else: + log.warning( + f"MsgId '{msgid}' for config '{key}' not found in catalog '{po_file}'" + ) else: - log.warning(f"translation for \"'{key}'\" not found in catalog '{po_file}'") + log.warning( + f"no original value set for config '{key}', cannot look up translation" + ) else: log.warning(f"translation catalog '{po_file}' not found") @@ -256,11 +269,12 @@ def apply_user_overrides(self, config: MkDocsConfig): f"Ignoring forbidden '{self.current_language}' config override '{lang_key}'" ) continue - if lang_key in overrides: - log.warning( - f"Overwriting po override '{lang_key}' with explicitly configured version" - ) - overrides[lang_key] = lang_override + if lang_override is not None: + if lang_key in overrides: + log.warning( + f"Overwriting override '{lang_key}' from PO file with explicitly configured string '{lang_override}'" + ) + overrides[lang_key] = lang_override for lang_key, lang_override in overrides.items(): if lang_key in config.data and lang_override is not None: From 92052dd31b843a682416b926c2c88d36938d9839 Mon Sep 17 00:00:00 2001 From: Alexander Rose Date: Thu, 7 Mar 2024 11:39:35 +0100 Subject: [PATCH 5/5] discard untranslated items --- mkdocs_static_i18n/reconfigure.py | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/mkdocs_static_i18n/reconfigure.py b/mkdocs_static_i18n/reconfigure.py index 6430753..c7cfdbe 100644 --- a/mkdocs_static_i18n/reconfigure.py +++ b/mkdocs_static_i18n/reconfigure.py @@ -250,7 +250,12 @@ def apply_user_overrides(self, config: MkDocsConfig): msgid = config[key] translation = catalog.get(msgid) if translation is not None: - overrides[key] = translation.string + if translation.string: + overrides[key] = translation.string + else: + log.warning( + f"MsgId '{msgid}' is not translated, discarding override" + ) else: log.warning( f"MsgId '{msgid}' for config '{key}' not found in catalog '{po_file}'"