|
1
|
|
|
# -*- coding: utf-8 -*- |
|
2
|
|
|
import json |
|
3
|
|
|
import os |
|
4
|
|
|
|
|
5
|
|
|
from babel.core import default_locale |
|
6
|
|
|
import typing |
|
7
|
|
|
if typing.TYPE_CHECKING: |
|
8
|
|
|
from tracim_backend.config import CFG |
|
9
|
|
|
|
|
10
|
|
|
TRANSLATION_FILENAME = 'backend.json' |
|
11
|
|
|
DEFAULT_FALLBACK_LANG = 'en' |
|
12
|
|
|
|
|
13
|
|
|
|
|
14
|
|
|
class Translator(object): |
|
15
|
|
|
""" |
|
16
|
|
|
Get translation from json file |
|
17
|
|
|
""" |
|
18
|
|
|
|
|
19
|
|
|
def __init__(self, app_config: 'CFG', default_lang: str = None, fallback_lang: str = None): # nopep8 |
|
20
|
|
|
self.config = app_config |
|
21
|
|
|
if not fallback_lang: |
|
22
|
|
|
fallback_lang = DEFAULT_FALLBACK_LANG |
|
23
|
|
|
self.fallback_lang = fallback_lang |
|
24
|
|
|
if not default_lang: |
|
25
|
|
|
default_lang = fallback_lang |
|
26
|
|
|
self.default_lang = default_lang |
|
27
|
|
|
|
|
28
|
|
|
def _get_json_translation_lang_filepath(self, lang: str) -> typing.Optional[str]: # nopep8 |
|
29
|
|
|
i18n_folder = self.config.BACKEND_I18N_FOLDER |
|
30
|
|
|
lang_filepath = os.path.join(i18n_folder, lang, TRANSLATION_FILENAME) |
|
31
|
|
|
if not os.path.isdir(self.config.BACKEND_I18N_FOLDER): |
|
32
|
|
|
return None |
|
33
|
|
|
else: |
|
34
|
|
|
return lang_filepath |
|
35
|
|
|
|
|
36
|
|
|
def _get_translation_from_file(self, filepath: str) -> typing.Optional[typing.Dict[str, str]]: # nopep8 |
|
37
|
|
|
try: |
|
38
|
|
|
with open(filepath) as file: |
|
39
|
|
|
trads = json.load(file) |
|
40
|
|
|
return trads |
|
41
|
|
|
except Exception: |
|
42
|
|
|
return None |
|
43
|
|
|
|
|
44
|
|
|
def _get_translation(self, lang: str, message: str) -> typing.Tuple[str, bool]: |
|
45
|
|
|
try: |
|
46
|
|
|
translation_filepath = self._get_json_translation_lang_filepath(lang) # nopep8 |
|
47
|
|
|
translation = self._get_translation_from_file(translation_filepath) |
|
48
|
|
|
if message in translation and translation[message]: |
|
49
|
|
|
return translation[message], True |
|
50
|
|
|
except Exception: |
|
51
|
|
|
pass |
|
52
|
|
|
return message, False |
|
53
|
|
|
|
|
54
|
|
|
def get_translation(self, message: str, lang: str = None) -> str: |
|
55
|
|
|
""" |
|
56
|
|
|
Return translation according to lang |
|
57
|
|
|
""" |
|
58
|
|
|
if not lang: |
|
59
|
|
|
lang = self.default_lang |
|
60
|
|
|
if lang != self.fallback_lang: |
|
61
|
|
|
new_trad, trad_found = self._get_translation(lang, message) |
|
62
|
|
|
if trad_found: |
|
63
|
|
|
return new_trad |
|
64
|
|
|
new_trad, trad_found = self._get_translation(self.fallback_lang, message) |
|
65
|
|
|
if trad_found: |
|
66
|
|
|
return new_trad |
|
67
|
|
|
return message |
|
68
|
|
|
|
|
69
|
|
|
|
|
70
|
|
|
def get_locale(): |
|
71
|
|
|
# TODO - G.M - 27-03-2018 - [i18n] Reconnect true internationalization |
|
72
|
|
|
return default_locale('LC_TIME') |
|
73
|
|
|
|