From 9fa160afa8874988cdc210370d8658f78ca2a57b Mon Sep 17 00:00:00 2001 From: hoangduytranuk Date: Fri, 22 Apr 2022 20:13:02 +0100 Subject: [PATCH 1/2] Addressing problems raised in sphinx_issues #10104 --- sphinx/builders/gettext.py | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/sphinx/builders/gettext.py b/sphinx/builders/gettext.py index e8bc547b77f..4889b69b04d 100644 --- a/sphinx/builders/gettext.py +++ b/sphinx/builders/gettext.py @@ -1,5 +1,5 @@ """The MessageCatalogBuilder class.""" - +import os from codecs import open from collections import OrderedDict, defaultdict from datetime import datetime, timedelta, tzinfo @@ -32,7 +32,7 @@ class Message: """An entry of translatable message.""" def __init__(self, text: str, locations: List[Tuple[str, int]], uuids: List[str]): self.text = text - self.locations = locations + self.locations = list(set(locations)) self.uuids = uuids @@ -57,7 +57,7 @@ def add(self, msg: str, origin: Union[Element, "MsgOrigin"]) -> None: def __iter__(self) -> Generator[Message, None, None]: for message in self.messages: - positions = [(source, line) for source, line, uuid in self.metadata[message]] + positions = [(os.path.relpath(source, start=os.getcwd()), line) for source, line, uuid in self.metadata[message]] uuids = [uuid for source, line, uuid in self.metadata[message]] yield Message(message, positions, uuids) From ac7185827af03d1e781c2de90ef96fe58d5cbc94 Mon Sep 17 00:00:00 2001 From: hoangduytranuk Date: Sun, 24 Apr 2022 16:21:22 +0100 Subject: [PATCH 2/2] Fixed the issue #10104 after the code reviews from Adam Turner and Takeshi Komiya: - Added the class variable 'builder' to Catalog class, so any instances of Catalog can access the information within the builder, including things such as app, config, srcdir, outdir etc.. see MessageCatalogBuilder for details. - Initialise this Catalog.builder as the instance of MessageCatalogBuilder is created, ie. in the init() - As Message class is created, list of locations passing to it will be made singular, using set(), sorted alphabetically for easier searching and identifying origins where the message can be found. - source dir is used within the __iter__ of the Catalog, using sphinx.util.osutil.relpath, for safer functionality, to work out the relative path for each location entry. --- sphinx/builders/gettext.py | 11 +++++++---- 1 file changed, 7 insertions(+), 4 deletions(-) diff --git a/sphinx/builders/gettext.py b/sphinx/builders/gettext.py index 4889b69b04d..2b74e981682 100644 --- a/sphinx/builders/gettext.py +++ b/sphinx/builders/gettext.py @@ -32,13 +32,14 @@ class Message: """An entry of translatable message.""" def __init__(self, text: str, locations: List[Tuple[str, int]], uuids: List[str]): self.text = text - self.locations = list(set(locations)) + self.locations = list(sorted(list(set(locations)))) #make list unique and sorted alphabetically self.uuids = uuids class Catalog: """Catalog of translatable messages.""" - + # make a class var so any instance can share this parent class, where all building info can be found, such as srcdir etc.. + builder = None def __init__(self) -> None: self.messages: List[str] = [] # retain insertion order, a la OrderedDict @@ -56,8 +57,9 @@ def add(self, msg: str, origin: Union[Element, "MsgOrigin"]) -> None: self.metadata[msg].append((origin.source, origin.line, origin.uid)) # type: ignore def __iter__(self) -> Generator[Message, None, None]: + src_dir = Catalog.builder.srcdir for message in self.messages: - positions = [(os.path.relpath(source, start=os.getcwd()), line) for source, line, uuid in self.metadata[message]] + positions = [(relpath(source, start=src_dir), line) for source, line, uuid in self.metadata[message]] uuids = [uuid for source, line, uuid in self.metadata[message]] yield Message(message, positions, uuids) @@ -213,7 +215,8 @@ class MessageCatalogBuilder(I18nBuilder): def init(self) -> None: super().init() self.create_template_bridge() - self.templates.init(self) + self.templates.init(self) + Catalog.builder = self # make the builder visible to instances of catalog def _collect_templates(self) -> Set[str]: template_files = set()