From 05b11f8aabc9312860edbdd9a4efde1cf022454d Mon Sep 17 00:00:00 2001 From: Konstantinos Bairaktaris Date: Thu, 20 Oct 2022 15:15:25 +0300 Subject: [PATCH] Fluent parser --- openformats/formats/fluent.py | 52 +++++++++++++++++++ openformats/tests/formats/fluent/__init__.py | 0 .../tests/formats/fluent/files/1_en.ftl | 21 ++++++++ requirements.txt | 1 + 4 files changed, 74 insertions(+) create mode 100644 openformats/formats/fluent.py create mode 100644 openformats/tests/formats/fluent/__init__.py create mode 100644 openformats/tests/formats/fluent/files/1_en.ftl diff --git a/openformats/formats/fluent.py b/openformats/formats/fluent.py new file mode 100644 index 00000000..35811714 --- /dev/null +++ b/openformats/formats/fluent.py @@ -0,0 +1,52 @@ +import itertools +import re + +from fluent.syntax import ast, parse +from openformats.strings import OpenString +from openformats.transcribers import Transcriber +from openformats.utils.compilers import OrderedCompilerMixin + +from ..handlers import Handler + + +class FluentHandler(OrderedCompilerMixin, Handler): + name = "FLUENT" + extension = "ftl" + EXTRACTS_RAW = True + + def parse(self, source, is_source=False): + transcriber = Transcriber(source) + source = transcriber.source + parsed = parse(source) + stringset = [] + order = itertools.count() + for item in parsed.body: + if not isinstance(item, (ast.Message, ast.Term)): + continue + key = item.id.name + value = source[item.value.span.start : item.value.span.end] + string = OpenString(key, value, order=next(order)) + stringset.append(string) + transcriber.copy_until(item.value.span.start) + transcriber.add(string.template_replacement) + transcriber.skip(item.value.span.end - item.value.span.start) + transcriber.copy_to_end() + return transcriber.get_destination(), stringset + + @staticmethod + def unescape(string: str): + lines = string.splitlines() + if len(lines) > 1: + indent = re.search("^s*", lines[1]).end() + result = [lines[0].strip()] + for line in lines[1:]: + if not line[:indent].isspace(): + return string + result.append(line[indent:].strip()) + return " ".join(lines) + else: + return string + + @staticmethod + def escape(string): + return string diff --git a/openformats/tests/formats/fluent/__init__.py b/openformats/tests/formats/fluent/__init__.py new file mode 100644 index 00000000..e69de29b diff --git a/openformats/tests/formats/fluent/files/1_en.ftl b/openformats/tests/formats/fluent/files/1_en.ftl new file mode 100644 index 00000000..4b9165ea --- /dev/null +++ b/openformats/tests/formats/fluent/files/1_en.ftl @@ -0,0 +1,21 @@ +## Closing tabs + +tabs-close-button = Close +tabs-close-tooltip = {$tabCount -> + [one] Close {$tabCount} tab + *[other] Close {$tabCount} tabs +} +tabs-close-warning = + You are about to close {$tabCount} tabs. + Are you sure you want to continue? + +## Syncing + +-sync-brand-name = Firefox Account + +sync-dialog-title = {-sync-brand-name} +sync-headline-title = + {-sync-brand-name}: The best way to bring + your data always with you +sync-signedout-title = + Connect with your {-sync-brand-name} diff --git a/requirements.txt b/requirements.txt index 2d422258..dda5d4cf 100644 --- a/requirements.txt +++ b/requirements.txt @@ -6,6 +6,7 @@ pyparsing==2.2.0 six lxml==4.6.2 beautifulsoup4==4.9.3 +fluent.syntax==0.18.1 # InDesign git+https://github.com/kbairak/ucflib@py3_compatibility