diff --git a/novaclient/openstack/common/gettextutils.py b/novaclient/openstack/common/gettextutils.py index 210d2bd1e..01a4ce59a 100644 --- a/novaclient/openstack/common/gettextutils.py +++ b/novaclient/openstack/common/gettextutils.py @@ -26,10 +26,13 @@ Usual usage in an openstack.common module: import copy import gettext -import logging.handlers +import logging import os import re -import UserString +try: + import UserString as _userString +except ImportError: + import collections as _userString from babel import localedata import six @@ -37,11 +40,27 @@ import six _localedir = os.environ.get('novaclient'.upper() + '_LOCALEDIR') _t = gettext.translation('novaclient', localedir=_localedir, fallback=True) -_AVAILABLE_LANGUAGES = [] +_AVAILABLE_LANGUAGES = {} +USE_LAZY = False + + +def enable_lazy(): + """Convenience function for configuring _() to use lazy gettext + + Call this at the start of execution to enable the gettextutils._ + function to use lazy gettext functionality. This is useful if + your project is importing _ directly instead of using the + gettextutils.install() way of importing the _ function. + """ + global USE_LAZY + USE_LAZY = True def _(msg): - return _t.ugettext(msg) + if USE_LAZY: + return Message(msg, 'novaclient') + else: + return _t.ugettext(msg) def install(domain, lazy=False): @@ -95,7 +114,7 @@ def install(domain, lazy=False): unicode=True) -class Message(UserString.UserString, object): +class Message(_userString.UserString, object): """Class used to encapsulate translatable messages.""" def __init__(self, msg, domain): # _msg is the gettext msgid and should never change @@ -236,7 +255,7 @@ class Message(UserString.UserString, object): if name in ops: return getattr(self.data, name) else: - return UserString.UserString.__getattribute__(self, name) + return _userString.UserString.__getattribute__(self, name) def get_available_languages(domain): @@ -244,8 +263,8 @@ def get_available_languages(domain): :param domain: the domain to get languages for """ - if _AVAILABLE_LANGUAGES: - return _AVAILABLE_LANGUAGES + if domain in _AVAILABLE_LANGUAGES: + return copy.copy(_AVAILABLE_LANGUAGES[domain]) localedir = '%s_LOCALEDIR' % domain.upper() find = lambda x: gettext.find(domain, @@ -254,7 +273,7 @@ def get_available_languages(domain): # NOTE(mrodden): en_US should always be available (and first in case # order matters) since our in-line message strings are en_US - _AVAILABLE_LANGUAGES.append('en_US') + language_list = ['en_US'] # NOTE(luisg): Babel <1.0 used a function called list(), which was # renamed to locale_identifiers() in >=1.0, the requirements master list # requires >=0.9.6, uncapped, so defensively work with both. We can remove @@ -264,13 +283,14 @@ def get_available_languages(domain): locale_identifiers = list_identifiers() for i in locale_identifiers: if find(i) is not None: - _AVAILABLE_LANGUAGES.append(i) - return _AVAILABLE_LANGUAGES + language_list.append(i) + _AVAILABLE_LANGUAGES[domain] = language_list + return copy.copy(language_list) def get_localized_message(message, user_locale): """Gets a localized version of the given message in the given locale.""" - if (isinstance(message, Message)): + if isinstance(message, Message): if user_locale: message.locale = user_locale return unicode(message) diff --git a/novaclient/openstack/common/py3kcompat/urlutils.py b/novaclient/openstack/common/py3kcompat/urlutils.py index 447102170..04b3418da 100644 --- a/novaclient/openstack/common/py3kcompat/urlutils.py +++ b/novaclient/openstack/common/py3kcompat/urlutils.py @@ -17,7 +17,7 @@ # """ -Python2/Python3 compatibility layer for openstack +Python2/Python3 compatibility layer for OpenStack """ import six @@ -27,6 +27,7 @@ if six.PY3: import urllib.parse urlencode = urllib.parse.urlencode + urljoin = urllib.parse.urljoin quote = urllib.parse.quote parse_qsl = urllib.parse.parse_qsl urlparse = urllib.parse.urlparse @@ -42,6 +43,7 @@ else: parse = urlparse parse_qsl = parse.parse_qsl + urljoin = parse.urljoin urlparse = parse.urlparse urlsplit = parse.urlsplit urlunsplit = parse.urlunsplit diff --git a/novaclient/openstack/common/timeutils.py b/novaclient/openstack/common/timeutils.py index aa9f70807..60f02bcb9 100644 --- a/novaclient/openstack/common/timeutils.py +++ b/novaclient/openstack/common/timeutils.py @@ -21,6 +21,7 @@ Time related utilities and helper functions. import calendar import datetime +import time import iso8601 import six @@ -90,6 +91,11 @@ def is_newer_than(after, seconds): def utcnow_ts(): """Timestamp version of our utcnow function.""" + if utcnow.override_time is None: + # NOTE(kgriffs): This is several times faster + # than going through calendar.timegm(...) + return int(time.time()) + return calendar.timegm(utcnow().timetuple())