Merge "Use oslo.i18n for translation"
This commit is contained in:
commit
12f0ab6f61
@ -14,9 +14,9 @@
|
|||||||
|
|
||||||
from oslo.config import cfg
|
from oslo.config import cfg
|
||||||
|
|
||||||
|
from murano.common.i18n import _
|
||||||
from murano.common import wsgi
|
from murano.common import wsgi
|
||||||
import murano.context
|
import murano.context
|
||||||
from murano.openstack.common.gettextutils import _
|
|
||||||
import murano.openstack.common.log as logging
|
import murano.openstack.common.log as logging
|
||||||
|
|
||||||
context_opts = [
|
context_opts = [
|
||||||
|
@ -22,7 +22,6 @@ from oslo.config import cfg
|
|||||||
|
|
||||||
from murano.api import versions
|
from murano.api import versions
|
||||||
from murano.common import wsgi
|
from murano.common import wsgi
|
||||||
from murano.openstack.common.gettextutils import _
|
|
||||||
import murano.openstack.common.log as logging
|
import murano.openstack.common.log as logging
|
||||||
|
|
||||||
CONF = cfg.CONF
|
CONF = cfg.CONF
|
||||||
@ -42,8 +41,8 @@ class VersionNegotiationFilter(wsgi.Middleware):
|
|||||||
|
|
||||||
def process_request(self, req):
|
def process_request(self, req):
|
||||||
"""Try to find a version first in the accept header, then the URL."""
|
"""Try to find a version first in the accept header, then the URL."""
|
||||||
msg = _("Determining version of request: %(method)s %(path)s"
|
msg = ("Determining version of request:"
|
||||||
" Accept: %(accept)s")
|
" %(method)s %(path)s Accept: %(accept)s")
|
||||||
args = {'method': req.method, 'path': req.path, 'accept': req.accept}
|
args = {'method': req.method, 'path': req.path, 'accept': req.accept}
|
||||||
LOG.debug(msg % args)
|
LOG.debug(msg % args)
|
||||||
|
|
||||||
|
@ -20,7 +20,7 @@ from murano.db import models
|
|||||||
from murano.db.services import environments as envs
|
from murano.db.services import environments as envs
|
||||||
from murano.db.services import sessions
|
from murano.db.services import sessions
|
||||||
from murano.db import session as db_session
|
from murano.db import session as db_session
|
||||||
from murano.openstack.common.gettextutils import _
|
from murano.common.i18n import _LI, _LE
|
||||||
from murano.openstack.common import log as logging
|
from murano.openstack.common import log as logging
|
||||||
from murano.services import actions
|
from murano.services import actions
|
||||||
from murano.services import states
|
from murano.services import states
|
||||||
@ -39,30 +39,30 @@ class Controller(object):
|
|||||||
environment = unit.query(models.Environment).get(environment_id)
|
environment = unit.query(models.Environment).get(environment_id)
|
||||||
|
|
||||||
if environment is None:
|
if environment is None:
|
||||||
LOG.info(_('Environment <EnvId {0}> '
|
LOG.info(_LI('Environment <EnvId {0}> '
|
||||||
'is not found').format(environment_id))
|
'is not found').format(environment_id))
|
||||||
raise exc.HTTPNotFound
|
raise exc.HTTPNotFound
|
||||||
|
|
||||||
if environment.tenant_id != request.context.tenant:
|
if environment.tenant_id != request.context.tenant:
|
||||||
LOG.info(_('User is not authorized to access '
|
LOG.info(_LI('User is not authorized to access '
|
||||||
'this tenant resources.'))
|
'this tenant resources.'))
|
||||||
raise exc.HTTPUnauthorized
|
raise exc.HTTPUnauthorized
|
||||||
|
|
||||||
# no new session can be opened if environment has deploying status
|
# no new session can be opened if environment has deploying status
|
||||||
env_status = envs.EnvironmentServices.get_status(environment_id)
|
env_status = envs.EnvironmentServices.get_status(environment_id)
|
||||||
if env_status in (states.EnvironmentStatus.DEPLOYING,
|
if env_status in (states.EnvironmentStatus.DEPLOYING,
|
||||||
states.EnvironmentStatus.DELETING):
|
states.EnvironmentStatus.DELETING):
|
||||||
LOG.info(_('Could not open session for environment <EnvId: {0}>,'
|
LOG.info(_LI('Could not open session for environment <EnvId: {0}>,'
|
||||||
'environment has deploying '
|
'environment has deploying '
|
||||||
'status.').format(environment_id))
|
'status.').format(environment_id))
|
||||||
raise exc.HTTPForbidden()
|
raise exc.HTTPForbidden()
|
||||||
|
|
||||||
user_id = request.context.user
|
user_id = request.context.user
|
||||||
session = sessions.SessionServices.create(environment_id, user_id)
|
session = sessions.SessionServices.create(environment_id, user_id)
|
||||||
|
|
||||||
if not sessions.SessionServices.validate(session):
|
if not sessions.SessionServices.validate(session):
|
||||||
LOG.error(_('Session <SessionId {0}> '
|
LOG.error(_LE('Session <SessionId {0}> '
|
||||||
'is invalid').format(session.id))
|
'is invalid').format(session.id))
|
||||||
raise exc.HTTPForbidden()
|
raise exc.HTTPForbidden()
|
||||||
|
|
||||||
actions.ActionServices.execute(action_id, session, unit,
|
actions.ActionServices.execute(action_id, session, unit,
|
||||||
|
@ -27,8 +27,8 @@ from murano.api.v1 import schemas
|
|||||||
from murano.common import policy
|
from murano.common import policy
|
||||||
from murano.common import wsgi
|
from murano.common import wsgi
|
||||||
from murano.db.catalog import api as db_api
|
from murano.db.catalog import api as db_api
|
||||||
|
from murano.common.i18n import _, _LW
|
||||||
from murano.openstack.common import exception
|
from murano.openstack.common import exception
|
||||||
from murano.openstack.common.gettextutils import _
|
|
||||||
from murano.openstack.common import log as logging
|
from murano.openstack.common import log as logging
|
||||||
from murano.packages import exceptions as pkg_exc
|
from murano.packages import exceptions as pkg_exc
|
||||||
from murano.packages import load_utils
|
from murano.packages import load_utils
|
||||||
@ -57,8 +57,8 @@ def _get_filters(query_params):
|
|||||||
for param_pair in query_params:
|
for param_pair in query_params:
|
||||||
k, v = param_pair
|
k, v = param_pair
|
||||||
if k not in SUPPORTED_PARAMS:
|
if k not in SUPPORTED_PARAMS:
|
||||||
LOG.warning(_("Search by parameter '{name}' "
|
LOG.warning(_LW("Search by parameter '{name}' "
|
||||||
"is not supported. Skipping it.").format(name=k))
|
"is not supported. Skipping it.").format(name=k))
|
||||||
continue
|
continue
|
||||||
|
|
||||||
if k in LIST_PARAMS:
|
if k in LIST_PARAMS:
|
||||||
@ -69,9 +69,10 @@ def _get_filters(query_params):
|
|||||||
for i in order_by[:]:
|
for i in order_by[:]:
|
||||||
if ORDER_VALUES and i not in ORDER_VALUES:
|
if ORDER_VALUES and i not in ORDER_VALUES:
|
||||||
filters['order_by'].remove(i)
|
filters['order_by'].remove(i)
|
||||||
LOG.warning(_("Value of 'order_by' parameter is not valid. "
|
LOG.warning(_LW(
|
||||||
"Allowed values are: {0}. Skipping it.").format(
|
"Value of 'order_by' parameter is not valid. "
|
||||||
", ".join(ORDER_VALUES)))
|
"Allowed values are: {0}. Skipping it.").format(
|
||||||
|
", ".join(ORDER_VALUES)))
|
||||||
return filters
|
return filters
|
||||||
|
|
||||||
|
|
||||||
@ -89,15 +90,16 @@ def _validate_body(body):
|
|||||||
size = f.tell()
|
size = f.tell()
|
||||||
f.seek(0)
|
f.seek(0)
|
||||||
if size > pkg_size_limit:
|
if size > pkg_size_limit:
|
||||||
raise exc.HTTPBadRequest('Uploading file is too large.'
|
raise exc.HTTPBadRequest(explanation=_(
|
||||||
' The limit is {0} Mb'.format(mb_limit))
|
'Uploading file is too large.'
|
||||||
|
' The limit is {0} Mb').format(mb_limit))
|
||||||
|
|
||||||
if len(body.keys()) > 2:
|
if len(body.keys()) > 2:
|
||||||
msg = _("'multipart/form-data' request body should contain "
|
msg = _("'multipart/form-data' request body should contain "
|
||||||
"1 or 2 parts: json string and zip archive. Current body "
|
"1 or 2 parts: json string and zip archive. Current body "
|
||||||
"consists of {0} part(s)").format(len(body.keys()))
|
"consists of {0} part(s)").format(len(body.keys()))
|
||||||
LOG.error(msg)
|
LOG.error(msg)
|
||||||
raise exc.HTTPBadRequest(msg)
|
raise exc.HTTPBadRequest(explanation=msg)
|
||||||
|
|
||||||
file_obj = None
|
file_obj = None
|
||||||
package_meta = None
|
package_meta = None
|
||||||
@ -111,7 +113,7 @@ def _validate_body(body):
|
|||||||
if file_obj is None:
|
if file_obj is None:
|
||||||
msg = _('There is no file package with application description')
|
msg = _('There is no file package with application description')
|
||||||
LOG.error(msg)
|
LOG.error(msg)
|
||||||
raise exc.HTTPBadRequest(msg)
|
raise exc.HTTPBadRequest(explanation=msg)
|
||||||
return file_obj, package_meta
|
return file_obj, package_meta
|
||||||
|
|
||||||
|
|
||||||
@ -192,8 +194,9 @@ class Controller(object):
|
|||||||
try:
|
try:
|
||||||
jsonschema.validate(package_meta, schemas.PKG_UPLOAD_SCHEMA)
|
jsonschema.validate(package_meta, schemas.PKG_UPLOAD_SCHEMA)
|
||||||
except jsonschema.ValidationError as e:
|
except jsonschema.ValidationError as e:
|
||||||
LOG.exception(e)
|
msg = _("Package schema is not valid: {0}").format(e)
|
||||||
raise exc.HTTPBadRequest(explanation=e.message)
|
LOG.exception(msg)
|
||||||
|
raise exc.HTTPBadRequest(explanation=msg)
|
||||||
else:
|
else:
|
||||||
package_meta = {}
|
package_meta = {}
|
||||||
|
|
||||||
@ -203,15 +206,16 @@ class Controller(object):
|
|||||||
if not content:
|
if not content:
|
||||||
msg = _("Uploading file can't be empty")
|
msg = _("Uploading file can't be empty")
|
||||||
LOG.error(msg)
|
LOG.error(msg)
|
||||||
raise exc.HTTPBadRequest(msg)
|
raise exc.HTTPBadRequest(explanation=msg)
|
||||||
tempf.write(content)
|
tempf.write(content)
|
||||||
package_meta['archive'] = content
|
package_meta['archive'] = content
|
||||||
try:
|
try:
|
||||||
pkg_to_upload = load_utils.load_from_file(
|
pkg_to_upload = load_utils.load_from_file(
|
||||||
tempf.name, target_dir=None, drop_dir=True)
|
tempf.name, target_dir=None, drop_dir=True)
|
||||||
except pkg_exc.PackageLoadError as e:
|
except pkg_exc.PackageLoadError as e:
|
||||||
LOG.exception(e)
|
msg = _("Couldn't load package from file: {0}").format(e)
|
||||||
raise exc.HTTPBadRequest(e)
|
LOG.exception(msg)
|
||||||
|
raise exc.HTTPBadRequest(explanation=msg)
|
||||||
finally:
|
finally:
|
||||||
LOG.debug("Deleting package archive temporary file")
|
LOG.debug("Deleting package archive temporary file")
|
||||||
os.remove(tempf.name)
|
os.remove(tempf.name)
|
||||||
|
@ -16,12 +16,12 @@ from webob import exc
|
|||||||
|
|
||||||
from murano.api.v1 import request_statistics
|
from murano.api.v1 import request_statistics
|
||||||
from murano.common.helpers import token_sanitizer
|
from murano.common.helpers import token_sanitizer
|
||||||
|
from murano.common.i18n import _LI
|
||||||
from murano.common import policy
|
from murano.common import policy
|
||||||
from murano.common import utils
|
from murano.common import utils
|
||||||
from murano.common import wsgi
|
from murano.common import wsgi
|
||||||
from murano.db import models
|
from murano.db import models
|
||||||
from murano.db import session as db_session
|
from murano.db import session as db_session
|
||||||
from murano.openstack.common.gettextutils import _
|
|
||||||
from murano.openstack.common import log as logging
|
from murano.openstack.common import log as logging
|
||||||
|
|
||||||
LOG = logging.getLogger(__name__)
|
LOG = logging.getLogger(__name__)
|
||||||
@ -81,11 +81,13 @@ class Controller(object):
|
|||||||
def verify_and_get_env(db_session, environment_id, request):
|
def verify_and_get_env(db_session, environment_id, request):
|
||||||
environment = db_session.query(models.Environment).get(environment_id)
|
environment = db_session.query(models.Environment).get(environment_id)
|
||||||
if not environment:
|
if not environment:
|
||||||
LOG.info(_('Environment with id {0} not found').format(environment_id))
|
LOG.info(_LI(
|
||||||
|
'Environment with id {0} not found').format(environment_id))
|
||||||
raise exc.HTTPNotFound
|
raise exc.HTTPNotFound
|
||||||
|
|
||||||
if environment.tenant_id != request.context.tenant:
|
if environment.tenant_id != request.context.tenant:
|
||||||
LOG.info(_('User is not authorized to access this tenant resources.'))
|
LOG.info(_LI(
|
||||||
|
'User is not authorized to access this tenant resources.'))
|
||||||
raise exc.HTTPUnauthorized
|
raise exc.HTTPUnauthorized
|
||||||
return environment
|
return environment
|
||||||
|
|
||||||
@ -98,12 +100,12 @@ def _patch_description(description):
|
|||||||
def verify_and_get_deployment(db_session, environment_id, deployment_id):
|
def verify_and_get_deployment(db_session, environment_id, deployment_id):
|
||||||
deployment = db_session.query(models.Task).get(deployment_id)
|
deployment = db_session.query(models.Task).get(deployment_id)
|
||||||
if not deployment:
|
if not deployment:
|
||||||
LOG.info(_('Deployment with id {0} not found').format(deployment_id))
|
LOG.info(_LI('Deployment with id {0} not found').format(deployment_id))
|
||||||
raise exc.HTTPNotFound
|
raise exc.HTTPNotFound
|
||||||
if deployment.environment_id != environment_id:
|
if deployment.environment_id != environment_id:
|
||||||
LOG.info(_('Deployment with id {0} not found'
|
LOG.info(_LI('Deployment with id {0} not found'
|
||||||
' in environment {1}').format(deployment_id,
|
' in environment {1}').format(deployment_id,
|
||||||
environment_id))
|
environment_id))
|
||||||
raise exc.HTTPBadRequest
|
raise exc.HTTPBadRequest
|
||||||
|
|
||||||
deployment.description = _patch_description(deployment.description)
|
deployment.description = _patch_description(deployment.description)
|
||||||
|
@ -27,7 +27,7 @@ from murano.db import models
|
|||||||
from murano.db.services import core_services
|
from murano.db.services import core_services
|
||||||
from murano.db.services import environments as envs
|
from murano.db.services import environments as envs
|
||||||
from murano.db import session as db_session
|
from murano.db import session as db_session
|
||||||
from murano.openstack.common.gettextutils import _
|
from murano.common.i18n import _, _LI
|
||||||
from murano.openstack.common import log as logging
|
from murano.openstack.common import log as logging
|
||||||
|
|
||||||
LOG = logging.getLogger(__name__)
|
LOG = logging.getLogger(__name__)
|
||||||
@ -63,12 +63,12 @@ class Controller(object):
|
|||||||
except db_exc.DBDuplicateEntry:
|
except db_exc.DBDuplicateEntry:
|
||||||
msg = _('Environment with specified name already exists')
|
msg = _('Environment with specified name already exists')
|
||||||
LOG.exception(msg)
|
LOG.exception(msg)
|
||||||
raise exc.HTTPConflict(msg)
|
raise exc.HTTPConflict(explanation=msg)
|
||||||
else:
|
else:
|
||||||
msg = _('Environment name must contain only alphanumeric '
|
msg = _('Environment name must contain only alphanumeric '
|
||||||
'or "_-." characters, must start with alpha')
|
'or "_-." characters, must start with alpha')
|
||||||
LOG.exception(msg)
|
LOG.exception(msg)
|
||||||
raise exc.HTTPClientError(msg)
|
raise exc.HTTPClientError(explanation=msg)
|
||||||
|
|
||||||
return environment.to_dict()
|
return environment.to_dict()
|
||||||
|
|
||||||
@ -82,13 +82,13 @@ class Controller(object):
|
|||||||
environment = session.query(models.Environment).get(environment_id)
|
environment = session.query(models.Environment).get(environment_id)
|
||||||
|
|
||||||
if environment is None:
|
if environment is None:
|
||||||
LOG.info(_('Environment <EnvId {0}> is not found').format(
|
LOG.info(_LI('Environment <EnvId {0}> is not found').format(
|
||||||
environment_id))
|
environment_id))
|
||||||
raise exc.HTTPNotFound
|
raise exc.HTTPNotFound
|
||||||
|
|
||||||
if environment.tenant_id != request.context.tenant:
|
if environment.tenant_id != request.context.tenant:
|
||||||
LOG.info(_('User is not authorized to access '
|
LOG.info(_LI('User is not authorized to access '
|
||||||
'this tenant resources.'))
|
'this tenant resources.'))
|
||||||
raise exc.HTTPUnauthorized
|
raise exc.HTTPUnauthorized
|
||||||
|
|
||||||
env = environment.to_dict()
|
env = environment.to_dict()
|
||||||
@ -115,13 +115,13 @@ class Controller(object):
|
|||||||
environment = session.query(models.Environment).get(environment_id)
|
environment = session.query(models.Environment).get(environment_id)
|
||||||
|
|
||||||
if environment is None:
|
if environment is None:
|
||||||
LOG.info(_('Environment <EnvId {0}> is not '
|
LOG.info(_LI('Environment <EnvId {0}> not '
|
||||||
'found').format(environment_id))
|
'found').format(environment_id))
|
||||||
raise exc.HTTPNotFound
|
raise exc.HTTPNotFound
|
||||||
|
|
||||||
if environment.tenant_id != request.context.tenant:
|
if environment.tenant_id != request.context.tenant:
|
||||||
LOG.info(_('User is not authorized to access '
|
LOG.info(_LI('User is not authorized to access '
|
||||||
'this tenant resources.'))
|
'this tenant resources.'))
|
||||||
raise exc.HTTPUnauthorized
|
raise exc.HTTPUnauthorized
|
||||||
|
|
||||||
LOG.debug('ENV NAME: {0}>'.format(body['name']))
|
LOG.debug('ENV NAME: {0}>'.format(body['name']))
|
||||||
@ -131,8 +131,8 @@ class Controller(object):
|
|||||||
else:
|
else:
|
||||||
msg = _('Environment name must contain only alphanumeric '
|
msg = _('Environment name must contain only alphanumeric '
|
||||||
'or "_-." characters, must start with alpha')
|
'or "_-." characters, must start with alpha')
|
||||||
LOG.exception(msg)
|
LOG.error(msg)
|
||||||
raise exc.HTTPClientError(msg)
|
raise exc.HTTPClientError(explanation=msg)
|
||||||
|
|
||||||
return environment.to_dict()
|
return environment.to_dict()
|
||||||
|
|
||||||
|
@ -15,12 +15,12 @@
|
|||||||
from webob import exc
|
from webob import exc
|
||||||
|
|
||||||
from murano.api.v1 import request_statistics
|
from murano.api.v1 import request_statistics
|
||||||
|
from murano.common.i18n import _
|
||||||
from murano.common import wsgi
|
from murano.common import wsgi
|
||||||
from murano.db import models
|
from murano.db import models
|
||||||
from murano.db.services import environments as envs
|
from murano.db.services import environments as envs
|
||||||
from murano.db.services import sessions
|
from murano.db.services import sessions
|
||||||
from murano.db import session as db_session
|
from murano.db import session as db_session
|
||||||
from murano.openstack.common.gettextutils import _
|
|
||||||
from murano.openstack.common import log as logging
|
from murano.openstack.common import log as logging
|
||||||
from murano.services import states
|
from murano.services import states
|
||||||
|
|
||||||
|
@ -26,6 +26,7 @@ from oslo.db import exception as db_exception
|
|||||||
|
|
||||||
from murano.common import consts
|
from murano.common import consts
|
||||||
from murano.db.catalog import api as db_catalog_api
|
from murano.db.catalog import api as db_catalog_api
|
||||||
|
from murano.common.i18n import _LI, _LE
|
||||||
from murano.openstack.common import log as logging
|
from murano.openstack.common import log as logging
|
||||||
from murano.packages import load_utils
|
from murano.packages import load_utils
|
||||||
from murano import version
|
from murano import version
|
||||||
@ -40,20 +41,21 @@ class AdminContext(object):
|
|||||||
|
|
||||||
|
|
||||||
def _do_import_package(_dir, categories, update=False):
|
def _do_import_package(_dir, categories, update=False):
|
||||||
LOG.info("Going to import Murano package from {0}".format(_dir))
|
LOG.info(_LI("Going to import Murano package from {0}").format(_dir))
|
||||||
pkg = load_utils.load_from_dir(_dir)
|
pkg = load_utils.load_from_dir(_dir)
|
||||||
|
|
||||||
LOG.info("Checking for existing")
|
LOG.info(_LI("Checking for existing"))
|
||||||
existing = db_catalog_api.package_search(
|
existing = db_catalog_api.package_search(
|
||||||
{'fqn': pkg.full_name},
|
{'fqn': pkg.full_name},
|
||||||
AdminContext())
|
AdminContext())
|
||||||
if existing:
|
if existing:
|
||||||
existing_pkg = existing[0]
|
existing_pkg = existing[0]
|
||||||
if update:
|
if update:
|
||||||
LOG.info("Deleting existing package {0}".format(existing_pkg.id))
|
LOG.info(_LI(
|
||||||
|
"Deleting existing package {0}").format(existing_pkg.id))
|
||||||
db_catalog_api.package_delete(existing_pkg.id, AdminContext())
|
db_catalog_api.package_delete(existing_pkg.id, AdminContext())
|
||||||
else:
|
else:
|
||||||
LOG.error("Package '{0}' exists ({1}). Use --update.".format(
|
LOG.error(_LE("Package '{0}' exists ({1}). Use --update.").format(
|
||||||
pkg.full_name,
|
pkg.full_name,
|
||||||
existing_pkg.id))
|
existing_pkg.id))
|
||||||
return
|
return
|
||||||
@ -81,7 +83,7 @@ def _do_import_package(_dir, categories, update=False):
|
|||||||
# it is a required field in the DB, that's why we pass an empty string
|
# it is a required field in the DB, that's why we pass an empty string
|
||||||
result = db_catalog_api.package_upload(package, '')
|
result = db_catalog_api.package_upload(package, '')
|
||||||
|
|
||||||
LOG.info("Finished import of package {0}".format(result.id))
|
LOG.info(_LI("Finished import of package {0}").format(result.id))
|
||||||
|
|
||||||
|
|
||||||
# TODO(ruhe): proper error handling
|
# TODO(ruhe): proper error handling
|
||||||
@ -154,14 +156,14 @@ def main():
|
|||||||
default_config_files=default_config_files)
|
default_config_files=default_config_files)
|
||||||
logging.setup("murano")
|
logging.setup("murano")
|
||||||
except RuntimeError as e:
|
except RuntimeError as e:
|
||||||
LOG.error("failed to initialize murano-manage: %s" % e)
|
LOG.error(_LE("failed to initialize murano-manage: %s") % e)
|
||||||
sys.exit("ERROR: %s" % e)
|
sys.exit("ERROR: %s" % e)
|
||||||
|
|
||||||
try:
|
try:
|
||||||
CONF.command.func()
|
CONF.command.func()
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
tb = traceback.format_exc()
|
tb = traceback.format_exc()
|
||||||
err_msg = "murano-manage command failed: {0}\n{1}".format(e, tb)
|
err_msg = _LE("murano-manage command failed: {0}\n{1}").format(e, tb)
|
||||||
LOG.error(err_msg)
|
LOG.error(err_msg)
|
||||||
sys.exit(err_msg)
|
sys.exit(err_msg)
|
||||||
|
|
||||||
|
@ -25,7 +25,7 @@ import sys
|
|||||||
from oslo.config import cfg
|
from oslo.config import cfg
|
||||||
from paste import deploy
|
from paste import deploy
|
||||||
|
|
||||||
from murano.openstack.common.gettextutils import _
|
from murano.common.i18n import _
|
||||||
from murano import version
|
from murano import version
|
||||||
|
|
||||||
paste_deploy_opts = [
|
paste_deploy_opts = [
|
||||||
@ -343,8 +343,8 @@ def load_paste_app(app_name=None):
|
|||||||
|
|
||||||
try:
|
try:
|
||||||
logger = logging.getLogger(__name__)
|
logger = logging.getLogger(__name__)
|
||||||
logger.debug(_("Loading %(app_name)s from %(conf_file)s"),
|
logger.debug("Loading %(app_name)s from %(conf_file)s".format(
|
||||||
{'conf_file': conf_file, 'app_name': app_name})
|
conf_file=conf_file, app_name=app_name))
|
||||||
|
|
||||||
app = deploy.loadapp("config:%s" % conf_file, name=app_name)
|
app = deploy.loadapp("config:%s" % conf_file, name=app_name)
|
||||||
|
|
||||||
|
@ -33,7 +33,7 @@ from murano.engine import package_class_loader
|
|||||||
from murano.engine import package_loader
|
from murano.engine import package_loader
|
||||||
from murano.engine.system import status_reporter
|
from murano.engine.system import status_reporter
|
||||||
import murano.engine.system.system_objects as system_objects
|
import murano.engine.system.system_objects as system_objects
|
||||||
from murano.openstack.common.gettextutils import _
|
from murano.common.i18n import _LI, _LE
|
||||||
from murano.openstack.common import log as logging
|
from murano.openstack.common import log as logging
|
||||||
from murano.policy import model_policy_enforcer as enforcer
|
from murano.policy import model_policy_enforcer as enforcer
|
||||||
|
|
||||||
@ -48,7 +48,7 @@ class TaskProcessingEndpoint(object):
|
|||||||
@staticmethod
|
@staticmethod
|
||||||
def handle_task(context, task):
|
def handle_task(context, task):
|
||||||
s_task = token_sanitizer.TokenSanitizer().sanitize(task)
|
s_task = token_sanitizer.TokenSanitizer().sanitize(task)
|
||||||
LOG.info(_('Starting processing task: {task_desc}').format(
|
LOG.info(_LI('Starting processing task: {task_desc}').format(
|
||||||
task_desc=jsonutils.dumps(s_task)))
|
task_desc=jsonutils.dumps(s_task)))
|
||||||
|
|
||||||
result = task['model']
|
result = task['model']
|
||||||
@ -56,7 +56,7 @@ class TaskProcessingEndpoint(object):
|
|||||||
task_executor = TaskExecutor(task)
|
task_executor = TaskExecutor(task)
|
||||||
result = task_executor.execute()
|
result = task_executor.execute()
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
LOG.exception('Error during task execution for tenant %s',
|
LOG.exception(_LE('Error during task execution for tenant %s'),
|
||||||
task['tenant_id'])
|
task['tenant_id'])
|
||||||
msg_env = Environment(task['id'])
|
msg_env = Environment(task['id'])
|
||||||
reporter = status_reporter.StatusReporter()
|
reporter = status_reporter.StatusReporter()
|
||||||
@ -135,7 +135,7 @@ class TaskExecutor(object):
|
|||||||
self._validate_model(obj, self.action, class_loader)
|
self._validate_model(obj, self.action, class_loader)
|
||||||
|
|
||||||
try:
|
try:
|
||||||
# Skip execution of action in case of no action is provided.
|
# Skip execution of action in case no action is provided.
|
||||||
# Model will be just loaded, cleaned-up and unloaded.
|
# Model will be just loaded, cleaned-up and unloaded.
|
||||||
# Most of the time this is used for deletion of environments.
|
# Most of the time this is used for deletion of environments.
|
||||||
if self.action:
|
if self.action:
|
||||||
@ -144,7 +144,10 @@ class TaskExecutor(object):
|
|||||||
if isinstance(e, dsl_exception.MuranoPlException):
|
if isinstance(e, dsl_exception.MuranoPlException):
|
||||||
LOG.error('\n' + e.format(prefix=' '))
|
LOG.error('\n' + e.format(prefix=' '))
|
||||||
else:
|
else:
|
||||||
LOG.exception(e)
|
LOG.exception(
|
||||||
|
_LE("Exception %(exc)s occured"
|
||||||
|
" during invocation of %(method)"),
|
||||||
|
{'exc': e, 'method': self.action['method']})
|
||||||
reporter = status_reporter.StatusReporter()
|
reporter = status_reporter.StatusReporter()
|
||||||
reporter.initialize(obj)
|
reporter.initialize(obj)
|
||||||
reporter.report_error(obj, str(e))
|
reporter.report_error(obj, str(e))
|
||||||
|
34
murano/common/i18n.py
Normal file
34
murano/common/i18n.py
Normal file
@ -0,0 +1,34 @@
|
|||||||
|
# Licensed under the Apache License, Version 2.0 (the "License"); you may
|
||||||
|
# not use this file except in compliance with the License. You may obtain
|
||||||
|
# a copy of the License at
|
||||||
|
#
|
||||||
|
# http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
#
|
||||||
|
# Unless required by applicable law or agreed to in writing, software
|
||||||
|
# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
|
||||||
|
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
|
||||||
|
# License for the specific language governing permissions and limitations
|
||||||
|
# under the License.
|
||||||
|
|
||||||
|
"""oslo.i18n integration module.
|
||||||
|
|
||||||
|
See http://docs.openstack.org/developer/oslo.i18n/usage.html
|
||||||
|
|
||||||
|
"""
|
||||||
|
|
||||||
|
import oslo_i18n
|
||||||
|
|
||||||
|
_translators = oslo_i18n.TranslatorFactory(domain='murano')
|
||||||
|
|
||||||
|
# The primary translation function using the well-known name "_"
|
||||||
|
_ = _translators.primary
|
||||||
|
|
||||||
|
# Translators for log levels.
|
||||||
|
#
|
||||||
|
# The abbreviated names are meant to reflect the usual use of a short
|
||||||
|
# name like '_'. The "L" is for "log" and the other letter comes from
|
||||||
|
# the level.
|
||||||
|
_LI = _translators.log_info
|
||||||
|
_LW = _translators.log_warning
|
||||||
|
_LE = _translators.log_error
|
||||||
|
_LC = _translators.log_critical
|
@ -17,6 +17,7 @@
|
|||||||
from oslo.config import cfg
|
from oslo.config import cfg
|
||||||
from webob import exc as exceptions
|
from webob import exc as exceptions
|
||||||
|
|
||||||
|
from murano.common.i18n import _
|
||||||
import murano.openstack.common.log as logging
|
import murano.openstack.common.log as logging
|
||||||
from murano.openstack.common import policy
|
from murano.openstack.common import policy
|
||||||
|
|
||||||
@ -77,8 +78,10 @@ def check(rule, ctxt, target={}, do_raise=True, exc=exceptions.HTTPForbidden):
|
|||||||
extra = {'policy': {'rule': rule, 'target': target}}
|
extra = {'policy': {'rule': rule, 'target': target}}
|
||||||
|
|
||||||
if result:
|
if result:
|
||||||
LOG.audit("Policy check succeeded for rule '%s' on target %s",
|
LOG.audit(_("Policy check succeeded for rule "
|
||||||
rule, repr(target), extra=extra)
|
"'%(rule)s' on target %(target)s"),
|
||||||
|
{'rule': rule, 'target': repr(target)}, extra=extra)
|
||||||
else:
|
else:
|
||||||
LOG.audit("Policy check failed for rule '%s' on target: %s",
|
LOG.audit(_("Policy check failed for rule "
|
||||||
rule, repr(target), extra=extra)
|
"'%(rule)s' on target: %(target)s"),
|
||||||
|
{'rule': rule, 'target': repr(target)}, extra=extra)
|
||||||
|
@ -26,7 +26,7 @@ from murano.db import models
|
|||||||
from murano.db.services import environments
|
from murano.db.services import environments
|
||||||
from murano.db.services import instances
|
from murano.db.services import instances
|
||||||
from murano.db import session
|
from murano.db import session
|
||||||
from murano.openstack.common.gettextutils import _
|
from murano.common.i18n import _, _LI, _LW
|
||||||
from murano.openstack.common import log as logging
|
from murano.openstack.common import log as logging
|
||||||
from murano.services import states
|
from murano.services import states
|
||||||
|
|
||||||
@ -48,8 +48,8 @@ class ResultEndpoint(object):
|
|||||||
environment = unit.query(models.Environment).get(environment_id)
|
environment = unit.query(models.Environment).get(environment_id)
|
||||||
|
|
||||||
if not environment:
|
if not environment:
|
||||||
LOG.warning(_('Environment result could not be handled, specified '
|
LOG.warning(_LW('Environment result could not be handled, '
|
||||||
'environment was not found in database'))
|
'specified environment not found in database'))
|
||||||
return
|
return
|
||||||
|
|
||||||
if result['Objects'] is None and result.get('ObjectsCopy', {}) is None:
|
if result['Objects'] is None and result.get('ObjectsCopy', {}) is None:
|
||||||
@ -106,10 +106,10 @@ class ResultEndpoint(object):
|
|||||||
conf_session.save(unit)
|
conf_session.save(unit)
|
||||||
|
|
||||||
# output application tracking information
|
# output application tracking information
|
||||||
message = '<EnvId: {0} TenantId: {1} Status: {2} Apps: {3}>'.format(
|
message = _LI('EnvId: {0} TenantId: {1} Status: {2} Apps: {3}').format(
|
||||||
environment.id,
|
environment.id,
|
||||||
environment.tenant_id,
|
environment.tenant_id,
|
||||||
'Failed' if num_errors + num_warnings > 0 else 'Successful',
|
_('Failed') if num_errors + num_warnings > 0 else _('Successful'),
|
||||||
', '.join(map(
|
', '.join(map(
|
||||||
lambda a: a['?']['type'],
|
lambda a: a['?']['type'],
|
||||||
result['Objects']['services']
|
result['Objects']['services']
|
||||||
|
@ -23,8 +23,8 @@ import psutil
|
|||||||
from murano.api import v1
|
from murano.api import v1
|
||||||
from murano.api.v1 import request_statistics
|
from murano.api.v1 import request_statistics
|
||||||
from murano.common import config
|
from murano.common import config
|
||||||
|
from murano.common.i18n import _LE
|
||||||
from murano.db.services import stats as db_stats
|
from murano.db.services import stats as db_stats
|
||||||
from murano.openstack.common.gettextutils import _
|
|
||||||
from murano.openstack.common import log as logging
|
from murano.openstack.common import log as logging
|
||||||
from murano.openstack.common import service
|
from murano.openstack.common import service
|
||||||
|
|
||||||
@ -92,5 +92,5 @@ class StatsCollectingService(service.Service):
|
|||||||
stats.cpu_percent = psutil.cpu_percent()
|
stats.cpu_percent = psutil.cpu_percent()
|
||||||
self._stats_db.update(self._hostname, stats)
|
self._stats_db.update(self._hostname, stats)
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
LOG.error(_("Failed to get statistics object "
|
LOG.exception(_LE("Failed to get statistics object "
|
||||||
"form a database. {0}").format(e))
|
"form a database. %s"), e)
|
||||||
|
@ -19,7 +19,7 @@ import types
|
|||||||
import eventlet
|
import eventlet
|
||||||
import jsonschema
|
import jsonschema
|
||||||
|
|
||||||
from murano.openstack.common.gettextutils import _
|
from murano.common.i18n import _, _LI
|
||||||
from murano.openstack.common import log as logging
|
from murano.openstack.common import log as logging
|
||||||
|
|
||||||
|
|
||||||
@ -240,7 +240,7 @@ def retry(ExceptionToCheck, tries=4, delay=3, backoff=2):
|
|||||||
except ExceptionToCheck as e:
|
except ExceptionToCheck as e:
|
||||||
|
|
||||||
LOG.exception(e)
|
LOG.exception(e)
|
||||||
LOG.info(_("Retrying in {0} seconds...").format(mdelay))
|
LOG.info(_LI("Retrying in {0} seconds...").format(mdelay))
|
||||||
|
|
||||||
eventlet.sleep(mdelay)
|
eventlet.sleep(mdelay)
|
||||||
|
|
||||||
|
@ -36,9 +36,9 @@ import webob.dec
|
|||||||
import webob.exc
|
import webob.exc
|
||||||
|
|
||||||
from murano.api.v1 import schemas
|
from murano.api.v1 import schemas
|
||||||
|
from murano.common.i18n import _
|
||||||
from murano.common import xmlutils
|
from murano.common import xmlutils
|
||||||
from murano.openstack.common import exception
|
from murano.openstack.common import exception
|
||||||
from murano.openstack.common.gettextutils import _
|
|
||||||
from murano.openstack.common import log as logging
|
from murano.openstack.common import log as logging
|
||||||
from murano.openstack.common import service
|
from murano.openstack.common import service
|
||||||
from murano.openstack.common import sslutils
|
from murano.openstack.common import sslutils
|
||||||
@ -660,24 +660,24 @@ class RequestDeserializer(object):
|
|||||||
|
|
||||||
def deserialize_body(self, request, action):
|
def deserialize_body(self, request, action):
|
||||||
if not len(request.body) > 0:
|
if not len(request.body) > 0:
|
||||||
LOG.debug(_("Empty body provided in request"))
|
LOG.debug("Empty body provided in request")
|
||||||
return {}
|
return {}
|
||||||
|
|
||||||
try:
|
try:
|
||||||
content_type = request.get_content_type()
|
content_type = request.get_content_type()
|
||||||
except exception.InvalidContentType as e:
|
except exception.InvalidContentType as e:
|
||||||
msg = _("Unrecognized Content-Type provided in request: {0}")
|
msg = "Unrecognized Content-Type provided in request: {0}"
|
||||||
LOG.debug(unicode(msg).format(str(e)))
|
LOG.debug(unicode(msg).format(str(e)))
|
||||||
raise
|
raise
|
||||||
|
|
||||||
if content_type is None:
|
if content_type is None:
|
||||||
LOG.debug(_("No Content-Type provided in request"))
|
LOG.debug("No Content-Type provided in request")
|
||||||
return {}
|
return {}
|
||||||
|
|
||||||
try:
|
try:
|
||||||
deserializer = self.get_body_deserializer(content_type)
|
deserializer = self.get_body_deserializer(content_type)
|
||||||
except exception.InvalidContentType:
|
except exception.InvalidContentType:
|
||||||
LOG.debug(_("Unable to deserialize body as provided Content-Type"))
|
LOG.debug("Unable to deserialize body as provided Content-Type")
|
||||||
raise
|
raise
|
||||||
|
|
||||||
return deserializer.deserialize(request, action)
|
return deserializer.deserialize(request, action)
|
||||||
@ -939,10 +939,10 @@ class FormDataDeserializer(TextDeserializer):
|
|||||||
def _from_json(self, datastring):
|
def _from_json(self, datastring):
|
||||||
value = datastring
|
value = datastring
|
||||||
try:
|
try:
|
||||||
LOG.debug(_("Trying deserialize '{0}' to json").format(datastring))
|
LOG.debug("Trying deserialize '{0}' to json".format(datastring))
|
||||||
value = jsonutils.loads(datastring)
|
value = jsonutils.loads(datastring)
|
||||||
except ValueError:
|
except ValueError:
|
||||||
LOG.debug(_("Unable deserialize to json, using raw text"))
|
LOG.debug("Unable deserialize to json, using raw text")
|
||||||
return value
|
return value
|
||||||
|
|
||||||
def default(self, request):
|
def default(self, request):
|
||||||
|
@ -21,7 +21,7 @@ from webob import exc
|
|||||||
|
|
||||||
from murano.db import models
|
from murano.db import models
|
||||||
from murano.db import session as db_session
|
from murano.db import session as db_session
|
||||||
from murano.openstack.common.gettextutils import _
|
from murano.common.i18n import _, _LW
|
||||||
from murano.openstack.common import log as logging
|
from murano.openstack.common import log as logging
|
||||||
|
|
||||||
CONF = cfg.CONF
|
CONF = cfg.CONF
|
||||||
@ -54,7 +54,7 @@ def _package_get(package_id_or_name, session):
|
|||||||
msg = _("Package id or name '{0}' not found").\
|
msg = _("Package id or name '{0}' not found").\
|
||||||
format(package_id_or_name)
|
format(package_id_or_name)
|
||||||
LOG.error(msg)
|
LOG.error(msg)
|
||||||
raise exc.HTTPNotFound(msg)
|
raise exc.HTTPNotFound(explanation=msg)
|
||||||
|
|
||||||
return package
|
return package
|
||||||
|
|
||||||
@ -68,12 +68,12 @@ def _authorize_package(package, context, allow_public=False):
|
|||||||
msg = _("Package '{0}' is not owned by "
|
msg = _("Package '{0}' is not owned by "
|
||||||
"tenant '{1}'").format(package.id, context.tenant)
|
"tenant '{1}'").format(package.id, context.tenant)
|
||||||
LOG.error(msg)
|
LOG.error(msg)
|
||||||
raise exc.HTTPForbidden(msg)
|
raise exc.HTTPForbidden(explanation=msg)
|
||||||
if not package.is_public:
|
if not package.is_public:
|
||||||
msg = _("Package '{0}' is not public and not owned by "
|
msg = _("Package '{0}' is not public and not owned by "
|
||||||
"tenant '{1}' ").format(package.id, context.tenant)
|
"tenant '{1}' ").format(package.id, context.tenant)
|
||||||
LOG.error(msg)
|
LOG.error(msg)
|
||||||
raise exc.HTTPForbidden(msg)
|
raise exc.HTTPForbidden(explanation=msg)
|
||||||
|
|
||||||
|
|
||||||
def package_get(package_id_or_name, context):
|
def package_get(package_id_or_name, context):
|
||||||
@ -104,7 +104,7 @@ def _get_categories(category_names, session=None):
|
|||||||
msg = _("Category '{name}' doesn't exist").format(name=ctg_name)
|
msg = _("Category '{name}' doesn't exist").format(name=ctg_name)
|
||||||
LOG.error(msg)
|
LOG.error(msg)
|
||||||
# it's not allowed to specify non-existent categories
|
# it's not allowed to specify non-existent categories
|
||||||
raise exc.HTTPBadRequest(msg)
|
raise exc.HTTPBadRequest(explanation=msg)
|
||||||
|
|
||||||
categories.append(ctg_obj)
|
categories.append(ctg_obj)
|
||||||
return categories
|
return categories
|
||||||
@ -174,8 +174,8 @@ def _do_add(package, change):
|
|||||||
try:
|
try:
|
||||||
getattr(package, path).append(item)
|
getattr(package, path).append(item)
|
||||||
except AssertionError:
|
except AssertionError:
|
||||||
msg = _('One of the specified {0} is already '
|
msg = _LW('One of the specified {0} is already '
|
||||||
'associated with a package. Doing nothing.')
|
'associated with a package. Doing nothing.')
|
||||||
LOG.warning(msg.format(path))
|
LOG.warning(msg.format(path))
|
||||||
return package
|
return package
|
||||||
|
|
||||||
@ -196,7 +196,7 @@ def _do_remove(package, change):
|
|||||||
msg = _("Value '{0}' of property '{1}' "
|
msg = _("Value '{0}' of property '{1}' "
|
||||||
"does not exist.").format(value, path)
|
"does not exist.").format(value, path)
|
||||||
LOG.error(msg)
|
LOG.error(msg)
|
||||||
raise exc.HTTPNotFound(msg)
|
raise exc.HTTPNotFound(explanation=msg)
|
||||||
item_to_remove = find(current_values, lambda i: i.name == value)
|
item_to_remove = find(current_values, lambda i: i.name == value)
|
||||||
current_values.remove(item_to_remove)
|
current_values.remove(item_to_remove)
|
||||||
return package
|
return package
|
||||||
|
@ -22,6 +22,7 @@ import eventlet
|
|||||||
import eventlet.event
|
import eventlet.event
|
||||||
import yaql.context
|
import yaql.context
|
||||||
|
|
||||||
|
from murano.common.i18n import _
|
||||||
import murano.dsl.attribute_store as attribute_store
|
import murano.dsl.attribute_store as attribute_store
|
||||||
import murano.dsl.dsl_exception as dsl_exception
|
import murano.dsl.dsl_exception as dsl_exception
|
||||||
import murano.dsl.expressions as expressions
|
import murano.dsl.expressions as expressions
|
||||||
@ -86,9 +87,9 @@ class MuranoDslExecutor(object):
|
|||||||
# TODO(slagun): check method accessibility from murano_class
|
# TODO(slagun): check method accessibility from murano_class
|
||||||
|
|
||||||
if not external_call and is_special_method:
|
if not external_call and is_special_method:
|
||||||
LOG.deprecated('initialize/destroy methods are called '
|
LOG.deprecated(_('initialize/destroy methods are called '
|
||||||
'automatically by engine. This call is no-op '
|
'automatically by engine. This call is no-op '
|
||||||
'and will become exception in the future')
|
'and will become exception in the future'))
|
||||||
return None
|
return None
|
||||||
|
|
||||||
# restore this from upcast object (no change if there was no upcast)
|
# restore this from upcast object (no change if there was no upcast)
|
||||||
|
@ -24,6 +24,7 @@ from muranoclient.common import exceptions as muranoclient_exc
|
|||||||
import six
|
import six
|
||||||
|
|
||||||
from murano.common import config
|
from murano.common import config
|
||||||
|
from murano.common.i18n import _LE
|
||||||
from murano.dsl import exceptions
|
from murano.dsl import exceptions
|
||||||
from murano.engine import yaql_yaml_loader
|
from murano.engine import yaql_yaml_loader
|
||||||
from murano.openstack.common import log as logging
|
from murano.openstack.common import log as logging
|
||||||
@ -106,7 +107,8 @@ class ApiPackageLoader(PackageLoader):
|
|||||||
package_directory, preload=True,
|
package_directory, preload=True,
|
||||||
loader=yaql_yaml_loader.YaqlYamlLoader)
|
loader=yaql_yaml_loader.YaqlYamlLoader)
|
||||||
except pkg_exc.PackageLoadError:
|
except pkg_exc.PackageLoadError:
|
||||||
LOG.exception('Unable to load package from cache. Clean-up...')
|
LOG.exception(_LE(
|
||||||
|
'Unable to load package from cache. Clean-up...'))
|
||||||
shutil.rmtree(package_directory, ignore_errors=True)
|
shutil.rmtree(package_directory, ignore_errors=True)
|
||||||
try:
|
try:
|
||||||
package_data = self._murano_client_factory().packages.download(
|
package_data = self._murano_client_factory().packages.download(
|
||||||
@ -176,8 +178,8 @@ class DirectoryPackageLoader(PackageLoader):
|
|||||||
folder, preload=True,
|
folder, preload=True,
|
||||||
loader=yaql_yaml_loader.YaqlYamlLoader)
|
loader=yaql_yaml_loader.YaqlYamlLoader)
|
||||||
except pkg_exc.PackageLoadError:
|
except pkg_exc.PackageLoadError:
|
||||||
LOG.exception('Unable to load package from path: '
|
LOG.exception(_LE('Unable to load package from path: '
|
||||||
'{0}'.format(entry))
|
'{0}').format(entry))
|
||||||
continue
|
continue
|
||||||
|
|
||||||
for c in package.classes:
|
for c in package.classes:
|
||||||
|
@ -22,6 +22,7 @@ import murano.common.utils as utils
|
|||||||
import murano.dsl.helpers as helpers
|
import murano.dsl.helpers as helpers
|
||||||
import murano.dsl.murano_class as murano_class
|
import murano.dsl.murano_class as murano_class
|
||||||
import murano.dsl.murano_object as murano_object
|
import murano.dsl.murano_object as murano_object
|
||||||
|
from murano.common.i18n import _LI, _LW
|
||||||
import murano.openstack.common.log as logging
|
import murano.openstack.common.log as logging
|
||||||
|
|
||||||
LOG = logging.getLogger(__name__)
|
LOG = logging.getLogger(__name__)
|
||||||
@ -162,7 +163,7 @@ class HeatStack(murano_object.MuranoObject):
|
|||||||
self._template['description'] = self._description
|
self._template['description'] = self._description
|
||||||
|
|
||||||
template = copy.deepcopy(self._template)
|
template = copy.deepcopy(self._template)
|
||||||
LOG.info('Pushing: {0}'.format(template))
|
LOG.info(_LI('Pushing: {0}').format(template))
|
||||||
|
|
||||||
current_status = self._get_status(_context)
|
current_status = self._get_status(_context)
|
||||||
resources = template.get('Resources') or template.get('resources')
|
resources = template.get('Resources') or template.get('resources')
|
||||||
@ -204,7 +205,7 @@ class HeatStack(murano_object.MuranoObject):
|
|||||||
_context,
|
_context,
|
||||||
lambda status: status in ('DELETE_COMPLETE', 'NOT_FOUND'))
|
lambda status: status in ('DELETE_COMPLETE', 'NOT_FOUND'))
|
||||||
except heat_exc.NotFound:
|
except heat_exc.NotFound:
|
||||||
LOG.warn('Stack {0} already deleted?'.format(self._name))
|
LOG.warn(_LW('Stack {0} already deleted?').format(self._name))
|
||||||
|
|
||||||
self._template = {}
|
self._template = {}
|
||||||
self._applied = True
|
self._applied = True
|
||||||
|
@ -40,6 +40,6 @@ try:
|
|||||||
_LC = _translators.log_critical
|
_LC = _translators.log_critical
|
||||||
except ImportError:
|
except ImportError:
|
||||||
# NOTE(dims): Support for cases where a project wants to use
|
# NOTE(dims): Support for cases where a project wants to use
|
||||||
# code from murano-incubator, but is not ready to be internationalized
|
# code from oslo-incubator, but is not ready to be internationalized
|
||||||
# (like tempest)
|
# (like tempest)
|
||||||
_ = _LI = _LW = _LE = _LC = lambda x: x
|
_ = _LI = _LW = _LE = _LC = lambda x: x
|
||||||
|
@ -21,7 +21,7 @@ Exceptions common to OpenStack projects
|
|||||||
|
|
||||||
import logging
|
import logging
|
||||||
|
|
||||||
from murano.openstack.common.gettextutils import _ # noqa
|
from murano.openstack.common._i18n import _
|
||||||
|
|
||||||
_FATAL_EXCEPTION_FORMAT_ERRORS = False
|
_FATAL_EXCEPTION_FORMAT_ERRORS = False
|
||||||
|
|
||||||
|
@ -1,498 +0,0 @@
|
|||||||
# Copyright 2012 Red Hat, Inc.
|
|
||||||
# Copyright 2013 IBM Corp.
|
|
||||||
# All Rights Reserved.
|
|
||||||
#
|
|
||||||
# Licensed under the Apache License, Version 2.0 (the "License"); you may
|
|
||||||
# not use this file except in compliance with the License. You may obtain
|
|
||||||
# a copy of the License at
|
|
||||||
#
|
|
||||||
# http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
#
|
|
||||||
# Unless required by applicable law or agreed to in writing, software
|
|
||||||
# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
|
|
||||||
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
|
|
||||||
# License for the specific language governing permissions and limitations
|
|
||||||
# under the License.
|
|
||||||
|
|
||||||
"""
|
|
||||||
gettext for openstack-common modules.
|
|
||||||
|
|
||||||
Usual usage in an openstack.common module:
|
|
||||||
|
|
||||||
from murano.openstack.common.gettextutils import _
|
|
||||||
"""
|
|
||||||
|
|
||||||
import copy
|
|
||||||
import functools
|
|
||||||
import gettext
|
|
||||||
import locale
|
|
||||||
from logging import handlers
|
|
||||||
import os
|
|
||||||
|
|
||||||
from babel import localedata
|
|
||||||
import six
|
|
||||||
|
|
||||||
_AVAILABLE_LANGUAGES = {}
|
|
||||||
|
|
||||||
# FIXME(dhellmann): Remove this when moving to oslo.i18n.
|
|
||||||
USE_LAZY = False
|
|
||||||
|
|
||||||
|
|
||||||
class TranslatorFactory(object):
|
|
||||||
"""Create translator functions
|
|
||||||
"""
|
|
||||||
|
|
||||||
def __init__(self, domain, lazy=False, localedir=None):
|
|
||||||
"""Establish a set of translation functions for the domain.
|
|
||||||
|
|
||||||
:param domain: Name of translation domain,
|
|
||||||
specifying a message catalog.
|
|
||||||
:type domain: str
|
|
||||||
:param lazy: Delays translation until a message is emitted.
|
|
||||||
Defaults to False.
|
|
||||||
:type lazy: Boolean
|
|
||||||
:param localedir: Directory with translation catalogs.
|
|
||||||
:type localedir: str
|
|
||||||
"""
|
|
||||||
self.domain = domain
|
|
||||||
self.lazy = lazy
|
|
||||||
if localedir is None:
|
|
||||||
localedir = os.environ.get(domain.upper() + '_LOCALEDIR')
|
|
||||||
self.localedir = localedir
|
|
||||||
|
|
||||||
def _make_translation_func(self, domain=None):
|
|
||||||
"""Return a new translation function ready for use.
|
|
||||||
|
|
||||||
Takes into account whether or not lazy translation is being
|
|
||||||
done.
|
|
||||||
|
|
||||||
The domain can be specified to override the default from the
|
|
||||||
factory, but the localedir from the factory is always used
|
|
||||||
because we assume the log-level translation catalogs are
|
|
||||||
installed in the same directory as the main application
|
|
||||||
catalog.
|
|
||||||
|
|
||||||
"""
|
|
||||||
if domain is None:
|
|
||||||
domain = self.domain
|
|
||||||
if self.lazy:
|
|
||||||
return functools.partial(Message, domain=domain)
|
|
||||||
t = gettext.translation(
|
|
||||||
domain,
|
|
||||||
localedir=self.localedir,
|
|
||||||
fallback=True,
|
|
||||||
)
|
|
||||||
if six.PY3:
|
|
||||||
return t.gettext
|
|
||||||
return t.ugettext
|
|
||||||
|
|
||||||
@property
|
|
||||||
def primary(self):
|
|
||||||
"The default translation function."
|
|
||||||
return self._make_translation_func()
|
|
||||||
|
|
||||||
def _make_log_translation_func(self, level):
|
|
||||||
return self._make_translation_func(self.domain + '-log-' + level)
|
|
||||||
|
|
||||||
@property
|
|
||||||
def log_info(self):
|
|
||||||
"Translate info-level log messages."
|
|
||||||
return self._make_log_translation_func('info')
|
|
||||||
|
|
||||||
@property
|
|
||||||
def log_warning(self):
|
|
||||||
"Translate warning-level log messages."
|
|
||||||
return self._make_log_translation_func('warning')
|
|
||||||
|
|
||||||
@property
|
|
||||||
def log_error(self):
|
|
||||||
"Translate error-level log messages."
|
|
||||||
return self._make_log_translation_func('error')
|
|
||||||
|
|
||||||
@property
|
|
||||||
def log_critical(self):
|
|
||||||
"Translate critical-level log messages."
|
|
||||||
return self._make_log_translation_func('critical')
|
|
||||||
|
|
||||||
|
|
||||||
# NOTE(dhellmann): When this module moves out of the incubator into
|
|
||||||
# oslo.i18n, these global variables can be moved to an integration
|
|
||||||
# module within each application.
|
|
||||||
|
|
||||||
# Create the global translation functions.
|
|
||||||
_translators = TranslatorFactory('murano')
|
|
||||||
|
|
||||||
# The primary translation function using the well-known name "_"
|
|
||||||
_ = _translators.primary
|
|
||||||
|
|
||||||
# Translators for log levels.
|
|
||||||
#
|
|
||||||
# The abbreviated names are meant to reflect the usual use of a short
|
|
||||||
# name like '_'. The "L" is for "log" and the other letter comes from
|
|
||||||
# the level.
|
|
||||||
_LI = _translators.log_info
|
|
||||||
_LW = _translators.log_warning
|
|
||||||
_LE = _translators.log_error
|
|
||||||
_LC = _translators.log_critical
|
|
||||||
|
|
||||||
# NOTE(dhellmann): End of globals that will move to the application's
|
|
||||||
# integration module.
|
|
||||||
|
|
||||||
|
|
||||||
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.
|
|
||||||
"""
|
|
||||||
# FIXME(dhellmann): This function will be removed in oslo.i18n,
|
|
||||||
# because the TranslatorFactory makes it superfluous.
|
|
||||||
global _, _LI, _LW, _LE, _LC, USE_LAZY
|
|
||||||
tf = TranslatorFactory('murano', lazy=True)
|
|
||||||
_ = tf.primary
|
|
||||||
_LI = tf.log_info
|
|
||||||
_LW = tf.log_warning
|
|
||||||
_LE = tf.log_error
|
|
||||||
_LC = tf.log_critical
|
|
||||||
USE_LAZY = True
|
|
||||||
|
|
||||||
|
|
||||||
def install(domain, lazy=False):
|
|
||||||
"""Install a _() function using the given translation domain.
|
|
||||||
|
|
||||||
Given a translation domain, install a _() function using gettext's
|
|
||||||
install() function.
|
|
||||||
|
|
||||||
The main difference from gettext.install() is that we allow
|
|
||||||
overriding the default localedir (e.g. /usr/share/locale) using
|
|
||||||
a translation-domain-specific environment variable (e.g.
|
|
||||||
NOVA_LOCALEDIR).
|
|
||||||
|
|
||||||
:param domain: the translation domain
|
|
||||||
:param lazy: indicates whether or not to install the lazy _() function.
|
|
||||||
The lazy _() introduces a way to do deferred translation
|
|
||||||
of messages by installing a _ that builds Message objects,
|
|
||||||
instead of strings, which can then be lazily translated into
|
|
||||||
any available locale.
|
|
||||||
"""
|
|
||||||
if lazy:
|
|
||||||
from six import moves
|
|
||||||
tf = TranslatorFactory(domain, lazy=True)
|
|
||||||
moves.builtins.__dict__['_'] = tf.primary
|
|
||||||
else:
|
|
||||||
localedir = '%s_LOCALEDIR' % domain.upper()
|
|
||||||
if six.PY3:
|
|
||||||
gettext.install(domain,
|
|
||||||
localedir=os.environ.get(localedir))
|
|
||||||
else:
|
|
||||||
gettext.install(domain,
|
|
||||||
localedir=os.environ.get(localedir),
|
|
||||||
unicode=True)
|
|
||||||
|
|
||||||
|
|
||||||
class Message(six.text_type):
|
|
||||||
"""A Message object is a unicode object that can be translated.
|
|
||||||
|
|
||||||
Translation of Message is done explicitly using the translate() method.
|
|
||||||
For all non-translation intents and purposes, a Message is simply unicode,
|
|
||||||
and can be treated as such.
|
|
||||||
"""
|
|
||||||
|
|
||||||
def __new__(cls, msgid, msgtext=None, params=None,
|
|
||||||
domain='murano', *args):
|
|
||||||
"""Create a new Message object.
|
|
||||||
|
|
||||||
In order for translation to work gettext requires a message ID, this
|
|
||||||
msgid will be used as the base unicode text. It is also possible
|
|
||||||
for the msgid and the base unicode text to be different by passing
|
|
||||||
the msgtext parameter.
|
|
||||||
"""
|
|
||||||
# If the base msgtext is not given, we use the default translation
|
|
||||||
# of the msgid (which is in English) just in case the system locale is
|
|
||||||
# not English, so that the base text will be in that locale by default.
|
|
||||||
if not msgtext:
|
|
||||||
msgtext = Message._translate_msgid(msgid, domain)
|
|
||||||
# We want to initialize the parent unicode with the actual object that
|
|
||||||
# would have been plain unicode if 'Message' was not enabled.
|
|
||||||
msg = super(Message, cls).__new__(cls, msgtext)
|
|
||||||
msg.msgid = msgid
|
|
||||||
msg.domain = domain
|
|
||||||
msg.params = params
|
|
||||||
return msg
|
|
||||||
|
|
||||||
def translate(self, desired_locale=None):
|
|
||||||
"""Translate this message to the desired locale.
|
|
||||||
|
|
||||||
:param desired_locale: The desired locale to translate the message to,
|
|
||||||
if no locale is provided the message will be
|
|
||||||
translated to the system's default locale.
|
|
||||||
|
|
||||||
:returns: the translated message in unicode
|
|
||||||
"""
|
|
||||||
|
|
||||||
translated_message = Message._translate_msgid(self.msgid,
|
|
||||||
self.domain,
|
|
||||||
desired_locale)
|
|
||||||
if self.params is None:
|
|
||||||
# No need for more translation
|
|
||||||
return translated_message
|
|
||||||
|
|
||||||
# This Message object may have been formatted with one or more
|
|
||||||
# Message objects as substitution arguments, given either as a single
|
|
||||||
# argument, part of a tuple, or as one or more values in a dictionary.
|
|
||||||
# When translating this Message we need to translate those Messages too
|
|
||||||
translated_params = _translate_args(self.params, desired_locale)
|
|
||||||
|
|
||||||
translated_message = translated_message % translated_params
|
|
||||||
|
|
||||||
return translated_message
|
|
||||||
|
|
||||||
@staticmethod
|
|
||||||
def _translate_msgid(msgid, domain, desired_locale=None):
|
|
||||||
if not desired_locale:
|
|
||||||
system_locale = locale.getdefaultlocale()
|
|
||||||
# If the system locale is not available to the runtime use English
|
|
||||||
if not system_locale[0]:
|
|
||||||
desired_locale = 'en_US'
|
|
||||||
else:
|
|
||||||
desired_locale = system_locale[0]
|
|
||||||
|
|
||||||
locale_dir = os.environ.get(domain.upper() + '_LOCALEDIR')
|
|
||||||
lang = gettext.translation(domain,
|
|
||||||
localedir=locale_dir,
|
|
||||||
languages=[desired_locale],
|
|
||||||
fallback=True)
|
|
||||||
if six.PY3:
|
|
||||||
translator = lang.gettext
|
|
||||||
else:
|
|
||||||
translator = lang.ugettext
|
|
||||||
|
|
||||||
translated_message = translator(msgid)
|
|
||||||
return translated_message
|
|
||||||
|
|
||||||
def __mod__(self, other):
|
|
||||||
# When we mod a Message we want the actual operation to be performed
|
|
||||||
# by the parent class (i.e. unicode()), the only thing we do here is
|
|
||||||
# save the original msgid and the parameters in case of a translation
|
|
||||||
params = self._sanitize_mod_params(other)
|
|
||||||
unicode_mod = super(Message, self).__mod__(params)
|
|
||||||
modded = Message(self.msgid,
|
|
||||||
msgtext=unicode_mod,
|
|
||||||
params=params,
|
|
||||||
domain=self.domain)
|
|
||||||
return modded
|
|
||||||
|
|
||||||
def _sanitize_mod_params(self, other):
|
|
||||||
"""Sanitize the object being modded with this Message.
|
|
||||||
|
|
||||||
- Add support for modding 'None' so translation supports it
|
|
||||||
- Trim the modded object, which can be a large dictionary, to only
|
|
||||||
those keys that would actually be used in a translation
|
|
||||||
- Snapshot the object being modded, in case the message is
|
|
||||||
translated, it will be used as it was when the Message was created
|
|
||||||
"""
|
|
||||||
if other is None:
|
|
||||||
params = (other,)
|
|
||||||
elif isinstance(other, dict):
|
|
||||||
# Merge the dictionaries
|
|
||||||
# Copy each item in case one does not support deep copy.
|
|
||||||
params = {}
|
|
||||||
if isinstance(self.params, dict):
|
|
||||||
for key, val in self.params.items():
|
|
||||||
params[key] = self._copy_param(val)
|
|
||||||
for key, val in other.items():
|
|
||||||
params[key] = self._copy_param(val)
|
|
||||||
else:
|
|
||||||
params = self._copy_param(other)
|
|
||||||
return params
|
|
||||||
|
|
||||||
def _copy_param(self, param):
|
|
||||||
try:
|
|
||||||
return copy.deepcopy(param)
|
|
||||||
except Exception:
|
|
||||||
# Fallback to casting to unicode this will handle the
|
|
||||||
# python code-like objects that can't be deep-copied
|
|
||||||
return six.text_type(param)
|
|
||||||
|
|
||||||
def __add__(self, other):
|
|
||||||
msg = _('Message objects do not support addition.')
|
|
||||||
raise TypeError(msg)
|
|
||||||
|
|
||||||
def __radd__(self, other):
|
|
||||||
return self.__add__(other)
|
|
||||||
|
|
||||||
if six.PY2:
|
|
||||||
def __str__(self):
|
|
||||||
# NOTE(luisg): Logging in python 2.6 tries to str() log records,
|
|
||||||
# and it expects specifically a UnicodeError in order to proceed.
|
|
||||||
msg = _('Message objects do not support str() because they may '
|
|
||||||
'contain non-ascii characters. '
|
|
||||||
'Please use unicode() or translate() instead.')
|
|
||||||
raise UnicodeError(msg)
|
|
||||||
|
|
||||||
|
|
||||||
def get_available_languages(domain):
|
|
||||||
"""Lists the available languages for the given translation domain.
|
|
||||||
|
|
||||||
:param domain: the domain to get languages for
|
|
||||||
"""
|
|
||||||
if domain in _AVAILABLE_LANGUAGES:
|
|
||||||
return copy.copy(_AVAILABLE_LANGUAGES[domain])
|
|
||||||
|
|
||||||
localedir = '%s_LOCALEDIR' % domain.upper()
|
|
||||||
find = lambda x: gettext.find(domain,
|
|
||||||
localedir=os.environ.get(localedir),
|
|
||||||
languages=[x])
|
|
||||||
|
|
||||||
# NOTE(mrodden): en_US should always be available (and first in case
|
|
||||||
# order matters) since our in-line message strings are 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
|
|
||||||
# this check when the master list updates to >=1.0, and update all projects
|
|
||||||
list_identifiers = (getattr(localedata, 'list', None) or
|
|
||||||
getattr(localedata, 'locale_identifiers'))
|
|
||||||
locale_identifiers = list_identifiers()
|
|
||||||
|
|
||||||
for i in locale_identifiers:
|
|
||||||
if find(i) is not None:
|
|
||||||
language_list.append(i)
|
|
||||||
|
|
||||||
# NOTE(luisg): Babel>=1.0,<1.3 has a bug where some OpenStack supported
|
|
||||||
# locales (e.g. 'zh_CN', and 'zh_TW') aren't supported even though they
|
|
||||||
# are perfectly legitimate locales:
|
|
||||||
# https://github.com/mitsuhiko/babel/issues/37
|
|
||||||
# In Babel 1.3 they fixed the bug and they support these locales, but
|
|
||||||
# they are still not explicitly "listed" by locale_identifiers().
|
|
||||||
# That is why we add the locales here explicitly if necessary so that
|
|
||||||
# they are listed as supported.
|
|
||||||
aliases = {'zh': 'zh_CN',
|
|
||||||
'zh_Hant_HK': 'zh_HK',
|
|
||||||
'zh_Hant': 'zh_TW',
|
|
||||||
'fil': 'tl_PH'}
|
|
||||||
for (locale, alias) in six.iteritems(aliases):
|
|
||||||
if locale in language_list and alias not in language_list:
|
|
||||||
language_list.append(alias)
|
|
||||||
|
|
||||||
_AVAILABLE_LANGUAGES[domain] = language_list
|
|
||||||
return copy.copy(language_list)
|
|
||||||
|
|
||||||
|
|
||||||
def translate(obj, desired_locale=None):
|
|
||||||
"""Gets the translated unicode representation of the given object.
|
|
||||||
|
|
||||||
If the object is not translatable it is returned as-is.
|
|
||||||
If the locale is None the object is translated to the system locale.
|
|
||||||
|
|
||||||
:param obj: the object to translate
|
|
||||||
:param desired_locale: the locale to translate the message to, if None the
|
|
||||||
default system locale will be used
|
|
||||||
:returns: the translated object in unicode, or the original object if
|
|
||||||
it could not be translated
|
|
||||||
"""
|
|
||||||
message = obj
|
|
||||||
if not isinstance(message, Message):
|
|
||||||
# If the object to translate is not already translatable,
|
|
||||||
# let's first get its unicode representation
|
|
||||||
message = six.text_type(obj)
|
|
||||||
if isinstance(message, Message):
|
|
||||||
# Even after unicoding() we still need to check if we are
|
|
||||||
# running with translatable unicode before translating
|
|
||||||
return message.translate(desired_locale)
|
|
||||||
return obj
|
|
||||||
|
|
||||||
|
|
||||||
def _translate_args(args, desired_locale=None):
|
|
||||||
"""Translates all the translatable elements of the given arguments object.
|
|
||||||
|
|
||||||
This method is used for translating the translatable values in method
|
|
||||||
arguments which include values of tuples or dictionaries.
|
|
||||||
If the object is not a tuple or a dictionary the object itself is
|
|
||||||
translated if it is translatable.
|
|
||||||
|
|
||||||
If the locale is None the object is translated to the system locale.
|
|
||||||
|
|
||||||
:param args: the args to translate
|
|
||||||
:param desired_locale: the locale to translate the args to, if None the
|
|
||||||
default system locale will be used
|
|
||||||
:returns: a new args object with the translated contents of the original
|
|
||||||
"""
|
|
||||||
if isinstance(args, tuple):
|
|
||||||
return tuple(translate(v, desired_locale) for v in args)
|
|
||||||
if isinstance(args, dict):
|
|
||||||
translated_dict = {}
|
|
||||||
for (k, v) in six.iteritems(args):
|
|
||||||
translated_v = translate(v, desired_locale)
|
|
||||||
translated_dict[k] = translated_v
|
|
||||||
return translated_dict
|
|
||||||
return translate(args, desired_locale)
|
|
||||||
|
|
||||||
|
|
||||||
class TranslationHandler(handlers.MemoryHandler):
|
|
||||||
"""Handler that translates records before logging them.
|
|
||||||
|
|
||||||
The TranslationHandler takes a locale and a target logging.Handler object
|
|
||||||
to forward LogRecord objects to after translating them. This handler
|
|
||||||
depends on Message objects being logged, instead of regular strings.
|
|
||||||
|
|
||||||
The handler can be configured declaratively in the logging.conf as follows:
|
|
||||||
|
|
||||||
[handlers]
|
|
||||||
keys = translatedlog, translator
|
|
||||||
|
|
||||||
[handler_translatedlog]
|
|
||||||
class = handlers.WatchedFileHandler
|
|
||||||
args = ('/var/log/api-localized.log',)
|
|
||||||
formatter = context
|
|
||||||
|
|
||||||
[handler_translator]
|
|
||||||
class = openstack.common.log.TranslationHandler
|
|
||||||
target = translatedlog
|
|
||||||
args = ('zh_CN',)
|
|
||||||
|
|
||||||
If the specified locale is not available in the system, the handler will
|
|
||||||
log in the default locale.
|
|
||||||
"""
|
|
||||||
|
|
||||||
def __init__(self, locale=None, target=None):
|
|
||||||
"""Initialize a TranslationHandler
|
|
||||||
|
|
||||||
:param locale: locale to use for translating messages
|
|
||||||
:param target: logging.Handler object to forward
|
|
||||||
LogRecord objects to after translation
|
|
||||||
"""
|
|
||||||
# NOTE(luisg): In order to allow this handler to be a wrapper for
|
|
||||||
# other handlers, such as a FileHandler, and still be able to
|
|
||||||
# configure it using logging.conf, this handler has to extend
|
|
||||||
# MemoryHandler because only the MemoryHandlers' logging.conf
|
|
||||||
# parsing is implemented such that it accepts a target handler.
|
|
||||||
handlers.MemoryHandler.__init__(self, capacity=0, target=target)
|
|
||||||
self.locale = locale
|
|
||||||
|
|
||||||
def setFormatter(self, fmt):
|
|
||||||
self.target.setFormatter(fmt)
|
|
||||||
|
|
||||||
def emit(self, record):
|
|
||||||
# We save the message from the original record to restore it
|
|
||||||
# after translation, so other handlers are not affected by this
|
|
||||||
original_msg = record.msg
|
|
||||||
original_args = record.args
|
|
||||||
|
|
||||||
try:
|
|
||||||
self._translate_and_log_record(record)
|
|
||||||
finally:
|
|
||||||
record.msg = original_msg
|
|
||||||
record.args = original_args
|
|
||||||
|
|
||||||
def _translate_and_log_record(self, record):
|
|
||||||
record.msg = translate(record.msg, self.locale)
|
|
||||||
|
|
||||||
# In addition to translating the message, we also need to translate
|
|
||||||
# arguments that were passed to the log method that were not part
|
|
||||||
# of the main message e.g., log.info(_('Some message %s'), this_one))
|
|
||||||
record.args = _translate_args(record.args, self.locale)
|
|
||||||
|
|
||||||
self.target.emit(record)
|
|
@ -46,7 +46,7 @@ from six import moves
|
|||||||
|
|
||||||
_PY26 = sys.version_info[0:2] == (2, 6)
|
_PY26 = sys.version_info[0:2] == (2, 6)
|
||||||
|
|
||||||
from murano.openstack.common._i18n import _
|
from murano.openstack.common._i18n import _, _LI
|
||||||
from murano.openstack.common import local
|
from murano.openstack.common import local
|
||||||
|
|
||||||
|
|
||||||
@ -521,8 +521,9 @@ def _setup_logging_from_conf(project, version):
|
|||||||
if CONF.log_format:
|
if CONF.log_format:
|
||||||
handler.setFormatter(logging.Formatter(fmt=CONF.log_format,
|
handler.setFormatter(logging.Formatter(fmt=CONF.log_format,
|
||||||
datefmt=datefmt))
|
datefmt=datefmt))
|
||||||
log_root.info('Deprecated: log_format is now deprecated and will '
|
log_root.info(_LI(
|
||||||
'be removed in the next release')
|
'Deprecated: log_format is now deprecated and will '
|
||||||
|
'be removed in the next release'))
|
||||||
else:
|
else:
|
||||||
handler.setFormatter(ContextFormatter(project=project,
|
handler.setFormatter(ContextFormatter(project=project,
|
||||||
version=version,
|
version=version,
|
||||||
|
@ -189,7 +189,7 @@ def execute(*cmd, **kwargs):
|
|||||||
break
|
break
|
||||||
obj.stdin.close() # pylint: disable=E1101
|
obj.stdin.close() # pylint: disable=E1101
|
||||||
_returncode = obj.returncode # pylint: disable=E1101
|
_returncode = obj.returncode # pylint: disable=E1101
|
||||||
LOG.log(loglevel, 'Result was %s' % _returncode)
|
LOG.log(loglevel, _('Result was %s'), _returncode)
|
||||||
if not ignore_exit_code and _returncode not in check_exit_code:
|
if not ignore_exit_code and _returncode not in check_exit_code:
|
||||||
(stdout, stderr) = result
|
(stdout, stderr) = result
|
||||||
sanitized_stdout = strutils.mask_password(stdout)
|
sanitized_stdout = strutils.mask_password(stdout)
|
||||||
|
@ -15,7 +15,7 @@
|
|||||||
|
|
||||||
import re
|
import re
|
||||||
|
|
||||||
from murano.openstack.common.gettextutils import _
|
from murano.common.i18n import _, _LI
|
||||||
from murano.openstack.common import log as logging
|
from murano.openstack.common import log as logging
|
||||||
from murano.policy import congress_rules
|
from murano.policy import congress_rules
|
||||||
|
|
||||||
@ -60,7 +60,7 @@ class ModelPolicyEnforcer(object):
|
|||||||
if not client:
|
if not client:
|
||||||
raise ValueError(_('Congress client is not configured!'))
|
raise ValueError(_('Congress client is not configured!'))
|
||||||
|
|
||||||
LOG.info('Validating model')
|
LOG.info(_LI('Validating model'))
|
||||||
LOG.debug(model)
|
LOG.debug(model)
|
||||||
|
|
||||||
rules = congress_rules.CongressRulesManager().convert(
|
rules = congress_rules.CongressRulesManager().convert(
|
||||||
@ -87,11 +87,12 @@ class ModelPolicyEnforcer(object):
|
|||||||
|
|
||||||
if messages:
|
if messages:
|
||||||
result_str = "\n ".join(map(str, messages))
|
result_str = "\n ".join(map(str, messages))
|
||||||
raise ValidationError(
|
msg = _("Murano object model validation failed: {0}").format(
|
||||||
_("Murano object model validation failed:") +
|
|
||||||
"\n " + result_str)
|
"\n " + result_str)
|
||||||
|
LOG.error(msg)
|
||||||
|
raise ValidationError(msg)
|
||||||
else:
|
else:
|
||||||
LOG.info('Model valid')
|
LOG.info(_LI('Model valid'))
|
||||||
|
|
||||||
def _parse_messages(self, env_id, results):
|
def _parse_messages(self, env_id, results):
|
||||||
"""Transforms list of strings in format
|
"""Transforms list of strings in format
|
||||||
|
@ -31,6 +31,7 @@ from alembic import migration
|
|||||||
from alembic import script as alembic_script
|
from alembic import script as alembic_script
|
||||||
from oslo.config import cfg
|
from oslo.config import cfg
|
||||||
|
|
||||||
|
from murano.common.i18n import _LE
|
||||||
import murano.db.migration
|
import murano.db.migration
|
||||||
from murano.openstack.common import log as logging
|
from murano.openstack.common import log as logging
|
||||||
|
|
||||||
@ -178,6 +179,7 @@ class BaseWalkMigrationTestCase(object):
|
|||||||
if check:
|
if check:
|
||||||
check(engine, data)
|
check(engine, data)
|
||||||
except Exception:
|
except Exception:
|
||||||
LOG.error("Failed to migrate to version %s on engine %s" %
|
LOG.error(_LE(
|
||||||
(version, engine))
|
"Failed to migrate to version %(ver)s on engine %(eng)s") %
|
||||||
|
{'ver': version, 'eng': engine})
|
||||||
raise
|
raise
|
||||||
|
@ -16,10 +16,10 @@ import functools
|
|||||||
|
|
||||||
from webob import exc
|
from webob import exc
|
||||||
|
|
||||||
|
from murano.common.i18n import _LI
|
||||||
from murano.db import models
|
from murano.db import models
|
||||||
from murano.db.services import sessions
|
from murano.db.services import sessions
|
||||||
from murano.db import session as db_session
|
from murano.db import session as db_session
|
||||||
from murano.openstack.common.gettextutils import _
|
|
||||||
from murano.openstack.common import log as logging
|
from murano.openstack.common import log as logging
|
||||||
from murano.services import states
|
from murano.services import states
|
||||||
|
|
||||||
@ -32,14 +32,14 @@ def verify_env(func):
|
|||||||
unit = db_session.get_session()
|
unit = db_session.get_session()
|
||||||
environment = unit.query(models.Environment).get(environment_id)
|
environment = unit.query(models.Environment).get(environment_id)
|
||||||
if environment is None:
|
if environment is None:
|
||||||
LOG.info(_("Environment with id '{0}'"
|
LOG.info(_LI("Environment with id '{0}'"
|
||||||
" not found").format(environment_id))
|
" not found").format(environment_id))
|
||||||
raise exc.HTTPNotFound()
|
raise exc.HTTPNotFound()
|
||||||
|
|
||||||
if hasattr(request, 'context'):
|
if hasattr(request, 'context'):
|
||||||
if environment.tenant_id != request.context.tenant:
|
if environment.tenant_id != request.context.tenant:
|
||||||
LOG.info(_('User is not authorized to access'
|
LOG.info(_LI('User is not authorized to access'
|
||||||
' this tenant resources'))
|
' these tenant resources'))
|
||||||
raise exc.HTTPUnauthorized()
|
raise exc.HTTPUnauthorized()
|
||||||
|
|
||||||
return func(self, request, environment_id, *args, **kwargs)
|
return func(self, request, environment_id, *args, **kwargs)
|
||||||
@ -50,7 +50,7 @@ def verify_session(func):
|
|||||||
@functools.wraps(func)
|
@functools.wraps(func)
|
||||||
def __inner(self, request, *args, **kwargs):
|
def __inner(self, request, *args, **kwargs):
|
||||||
if hasattr(request, 'context') and not request.context.session:
|
if hasattr(request, 'context') and not request.context.session:
|
||||||
LOG.info(_('Session is required for this call'))
|
LOG.info(_LI('Session is required for this call'))
|
||||||
raise exc.HTTPForbidden()
|
raise exc.HTTPForbidden()
|
||||||
|
|
||||||
session_id = request.context.session
|
session_id = request.context.session
|
||||||
@ -59,18 +59,18 @@ def verify_session(func):
|
|||||||
session = unit.query(models.Session).get(session_id)
|
session = unit.query(models.Session).get(session_id)
|
||||||
|
|
||||||
if session is None:
|
if session is None:
|
||||||
LOG.info(_('Session <SessionId {0}> '
|
LOG.info(_LI('Session <SessionId {0}> '
|
||||||
'is not found').format(session_id))
|
'is not found').format(session_id))
|
||||||
raise exc.HTTPForbidden()
|
raise exc.HTTPForbidden()
|
||||||
|
|
||||||
if not sessions.SessionServices.validate(session):
|
if not sessions.SessionServices.validate(session):
|
||||||
LOG.info(_('Session <SessionId {0}> '
|
LOG.info(_LI('Session <SessionId {0}> '
|
||||||
'is invalid').format(session_id))
|
'is invalid').format(session_id))
|
||||||
raise exc.HTTPForbidden()
|
raise exc.HTTPForbidden()
|
||||||
|
|
||||||
if session.state == states.SessionState.DEPLOYING:
|
if session.state == states.SessionState.DEPLOYING:
|
||||||
LOG.info(_('Session <SessionId {0}> is already in '
|
LOG.info(_LI('Session <SessionId {0}> is already in '
|
||||||
'deployment state').format(session_id))
|
'deployment state').format(session_id))
|
||||||
raise exc.HTTPForbidden()
|
raise exc.HTTPForbidden()
|
||||||
return func(self, request, *args, **kwargs)
|
return func(self, request, *args, **kwargs)
|
||||||
return __inner
|
return __inner
|
||||||
|
@ -2,7 +2,6 @@
|
|||||||
|
|
||||||
# The list of modules to copy from openstack-common
|
# The list of modules to copy from openstack-common
|
||||||
module=exception
|
module=exception
|
||||||
module=gettextutils
|
|
||||||
module=lockutils
|
module=lockutils
|
||||||
module=log
|
module=log
|
||||||
module=policy
|
module=policy
|
||||||
|
@ -33,6 +33,7 @@ oslo.config>=1.4.0 # Apache-2.0
|
|||||||
oslo.messaging>=1.4.0,!=1.5.0
|
oslo.messaging>=1.4.0,!=1.5.0
|
||||||
oslo.serialization>=1.0.0 # Apache-2.0
|
oslo.serialization>=1.0.0 # Apache-2.0
|
||||||
oslo.utils>=1.1.0 # Apache-2.0
|
oslo.utils>=1.1.0 # Apache-2.0
|
||||||
|
oslo.i18n>=1.3.0
|
||||||
|
|
||||||
# not listed in global requirements
|
# not listed in global requirements
|
||||||
yaql>=0.2.3,<0.3
|
yaql>=0.2.3,<0.3
|
||||||
|
4
tox.ini
4
tox.ini
@ -48,5 +48,5 @@ builtins = _
|
|||||||
exclude=.venv,.git,.tox,dist,doc,*openstack/common*,*lib/python*,*egg,tools
|
exclude=.venv,.git,.tox,dist,doc,*openstack/common*,*lib/python*,*egg,tools
|
||||||
|
|
||||||
[hacking]
|
[hacking]
|
||||||
import_exceptions = murano.openstack.common.gettextutils,
|
import_exceptions = oslo.db.sqlalchemy.test_base,
|
||||||
oslo.db.sqlalchemy.test_base
|
murano.common.i18n
|
||||||
|
Loading…
Reference in New Issue
Block a user