Merge "Add ensure_thread_contain_context() to task_manager"

This commit is contained in:
Jenkins 2016-03-21 21:25:15 +00:00 committed by Gerrit Code Review
commit 649e45eaef
2 changed files with 40 additions and 0 deletions

View File

@ -96,6 +96,7 @@ raised in the background thread.):
import futurist
from oslo_config import cfg
from oslo_context import context as oslo_context
from oslo_log import log as logging
from oslo_utils import excutils
from oslo_utils import timeutils
@ -134,6 +135,9 @@ def require_exclusive_lock(f):
task = args[0]
if task.shared:
raise exception.ExclusiveLockRequired()
# NOTE(lintan): This is a workaround to set the context of async tasks,
# which should contain an exclusive lock.
ensure_thread_contain_context(task.context)
return f(*args, **kwargs)
return wrapper
@ -151,10 +155,26 @@ def acquire(context, node_id, shared=False, driver_name=None,
:returns: An instance of :class:`TaskManager`.
"""
# NOTE(lintan): This is a workaround to set the context of periodic tasks.
ensure_thread_contain_context(context)
return TaskManager(context, node_id, shared=shared,
driver_name=driver_name, purpose=purpose)
def ensure_thread_contain_context(context):
"""Ensure threading contains context
For async/periodic tasks, the context of local thread is missing.
Set it with request context and this is useful to log the request_id
in log messages.
:param context: Request context
"""
if oslo_context.get_current():
return
context.update_store()
class TaskManager(object):
"""Context manager for tasks.

View File

@ -19,8 +19,10 @@
import futurist
import mock
from oslo_context import context as oslo_context
from oslo_utils import uuidutils
from ironic.common import context
from ironic.common import driver_factory
from ironic.common import exception
from ironic.common import fsm
@ -657,6 +659,7 @@ class ExclusiveLockDecoratorTestCase(tests_base.TestCase):
def setUp(self):
super(ExclusiveLockDecoratorTestCase, self).setUp()
self.task = mock.Mock(spec=task_manager.TaskManager)
self.task.context = self.context
self.args_task_first = (self.task, 1, 2)
self.args_task_second = (1, self.task, 2)
self.kwargs = dict(cat='meow', dog='wuff')
@ -736,3 +739,20 @@ class ThreadExceptionTestCase(tests_base.TestCase):
self.future_mock.exception.assert_called_once_with()
self.assertIsNone(self.node.last_error)
self.assertTrue(log_mock.called)
@mock.patch.object(oslo_context, 'get_current')
class TaskManagerContextTestCase(tests_base.TestCase):
def setUp(self):
super(TaskManagerContextTestCase, self).setUp()
self.context = mock.Mock(spec=context.RequestContext)
def test_thread_without_context(self, context_get_mock):
context_get_mock.return_value = False
task_manager.ensure_thread_contain_context(self.context)
self.assertTrue(self.context.update_store.called)
def test_thread_with_context(self, context_get_mock):
context_get_mock.return_value = True
task_manager.ensure_thread_contain_context(self.context)
self.assertFalse(self.context.update_store.called)