37
40
_localedir = os.environ.get('heat'.upper() + '_LOCALEDIR')
38
41
_t = gettext.translation('heat', localedir=_localedir, fallback=True)
40
_AVAILABLE_LANGUAGES = []
43
_AVAILABLE_LANGUAGES = {}
48
"""Convenience function for configuring _() to use lazy gettext
50
Call this at the start of execution to enable the gettextutils._
51
function to use lazy gettext functionality. This is useful if
52
your project is importing _ directly instead of using the
53
gettextutils.install() way of importing the _ function.
44
return _t.ugettext(msg)
61
return Message(msg, 'heat')
64
return _t.gettext(msg)
65
return _t.ugettext(msg)
47
68
def install(domain, lazy=False):
87
108
return Message(msg, domain)
90
__builtin__.__dict__['_'] = _lazy_gettext
110
from six import moves
111
moves.builtins.__dict__['_'] = _lazy_gettext
92
113
localedir = '%s_LOCALEDIR' % domain.upper()
93
gettext.install(domain,
94
localedir=os.environ.get(localedir),
98
class Message(UserString.UserString, object):
115
gettext.install(domain,
116
localedir=os.environ.get(localedir))
118
gettext.install(domain,
119
localedir=os.environ.get(localedir),
123
class Message(_userString.UserString, object):
99
124
"""Class used to encapsulate translatable messages."""
100
125
def __init__(self, msg, domain):
101
126
# _msg is the gettext msgid and should never change
103
128
self._left_extra_msg = ''
104
129
self._right_extra_msg = ''
105
131
self.params = None
107
132
self.domain = domain
133
163
return six.text_type(full_msg)
170
def locale(self, value):
175
# This Message object may have been constructed with one or more
176
# Message objects as substitution parameters, given as a single
177
# Message, or a tuple or Map containing some, so when setting the
178
# locale for this Message we need to set it for those Messages too.
179
if isinstance(self.params, Message):
180
self.params.locale = value
182
if isinstance(self.params, tuple):
183
for param in self.params:
184
if isinstance(param, Message):
187
if isinstance(self.params, dict):
188
for param in self.params.values():
189
if isinstance(param, Message):
135
192
def _save_dictionary_parameter(self, dict_param):
136
193
full_msg = self.data
137
194
# look for %(blah) fields in string;
138
195
# ignore %% and deal with the
139
196
# case where % is first character on the line
140
keys = re.findall('(?:[^%]|^)%\((\w*)\)[a-z]', full_msg)
197
keys = re.findall('(?:[^%]|^)?%\((\w*)\)[a-z]', full_msg)
142
199
# if we don't find any %(blah) blocks but have a %s
143
200
if not keys and re.findall('(?:[^%]|^)%[a-z]', full_msg):
180
237
def __str__(self):
239
return self.__unicode__()
181
240
return self.data.encode('utf-8')
183
242
def __getstate__(self):
184
243
to_copy = ['_msg', '_right_extra_msg', '_left_extra_msg',
185
'domain', 'params', 'locale']
244
'domain', 'params', '_locale']
186
245
new_dict = self.__dict__.fromkeys(to_copy)
187
246
for attr in to_copy:
188
247
new_dict[attr] = copy.deepcopy(self.__dict__[attr])
237
296
return getattr(self.data, name)
239
return UserString.UserString.__getattribute__(self, name)
298
return _userString.UserString.__getattribute__(self, name)
242
301
def get_available_languages(domain):
245
304
:param domain: the domain to get languages for
247
if _AVAILABLE_LANGUAGES:
248
return _AVAILABLE_LANGUAGES
306
if domain in _AVAILABLE_LANGUAGES:
307
return copy.copy(_AVAILABLE_LANGUAGES[domain])
250
309
localedir = '%s_LOCALEDIR' % domain.upper()
251
310
find = lambda x: gettext.find(domain,
255
314
# NOTE(mrodden): en_US should always be available (and first in case
256
315
# order matters) since our in-line message strings are en_US
257
_AVAILABLE_LANGUAGES.append('en_US')
316
language_list = ['en_US']
258
317
# NOTE(luisg): Babel <1.0 used a function called list(), which was
259
318
# renamed to locale_identifiers() in >=1.0, the requirements master list
260
319
# requires >=0.9.6, uncapped, so defensively work with both. We can remove
264
323
locale_identifiers = list_identifiers()
265
324
for i in locale_identifiers:
266
325
if find(i) is not None:
267
_AVAILABLE_LANGUAGES.append(i)
268
return _AVAILABLE_LANGUAGES
326
language_list.append(i)
327
_AVAILABLE_LANGUAGES[domain] = language_list
328
return copy.copy(language_list)
271
331
def get_localized_message(message, user_locale):
272
332
"""Gets a localized version of the given message in the given locale."""
273
if (isinstance(message, Message)):
333
if isinstance(message, Message):
275
335
message.locale = user_locale
276
return unicode(message)
336
return six.text_type(message)