def test_post_lifecycle_hook_message(self, mock_zaqar): cfg.CONF.set_override('max_message_size', 8192, 'notification') mock_zc = mock.Mock() mock_zaqar.return_value = mock_zc queue_name = 'my_queue' message = mmod.Message(queue_name) mock_zc.queue_exists.return_value = True lifecycle_action_token = 'ACTION_ID' node_id = 'NODE_ID' resource_id = 'RESOURCE_ID' lifecycle_transition_type = 'TYPE' message.post_lifecycle_hook_message(lifecycle_action_token, node_id, resource_id, lifecycle_transition_type) mock_zc.queue_create.assert_not_called() message_list = [{ "ttl": 300, "body": { "lifecycle_action_token": lifecycle_action_token, "node_id": node_id, "resource_id": resource_id, "lifecycle_transition_type": lifecycle_transition_type } }] mock_zc.message_post.assert_called_once_with(queue_name, message_list)
def test_zaqar_client(self, mock_senlindriver): sd = mock.Mock() zc = mock.Mock() sd.message.return_value = zc mock_senlindriver.return_value = sd message = mmod.Message('myqueue', user='******', project='project1') # cached will be returned message._zaqarclient = zc self.assertEqual(zc, message.zaqar()) # new zaqar client created if no cache found message._zaqarclient = None params = mock.Mock() mock_param = self.patchobject(mmod.Message, '_build_conn_params', return_value=params) res = message.zaqar() self.assertEqual(zc, res) self.assertEqual(zc, message._zaqarclient) mock_param.assert_called_once_with('user1', 'project1') sd.message.assert_called_once_with(params)
def test_post_lifecycle_hook_message_queue_nonexistent(self, mock_zaqar): cfg.CONF.set_override('max_message_size', 8192, 'notification') cfg.CONF.set_override('ttl', 500, 'notification') mock_zc = mock.Mock() mock_zaqar.return_value = mock_zc queue_name = 'my_queue' message = mmod.Message(queue_name) kwargs = { '_max_messages_post_size': 8192, 'description': "Senlin lifecycle hook notification", 'name': queue_name } mock_zc.queue_exists.return_value = False lifecycle_action_token = 'ACTION_ID' node_id = 'NODE_ID' resource_id = 'RESOURCE_ID' lifecycle_transition_type = 'TYPE' message.post_lifecycle_hook_message(lifecycle_action_token, node_id, resource_id, lifecycle_transition_type) mock_zc.queue_create.assert_called_once_with(**kwargs) message_list = [{ "ttl": 500, "body": { "lifecycle_action_token": lifecycle_action_token, "node_id": node_id, "resource_id": resource_id, "lifecycle_transition_type": lifecycle_transition_type } }] mock_zc.message_post.assert_called_once_with(queue_name, message_list)
def test_post_lifecycle_hook_message_queue_retry(self, mock_zaqar): cfg.CONF.set_override('max_message_size', 8192, 'notification') mock_zc = mock.Mock() mock_zaqar.return_value = mock_zc queue_name = 'my_queue' message = mmod.Message(queue_name) mock_zc.queue_exists.return_value = True test_exception = exception.EResourceCreation(type='queue', message="test") mock_zc.message_post.side_effect = [ test_exception, test_exception, None ] lifecycle_action_token = 'ACTION_ID' node_id = 'NODE_ID' resource_id = 'RESOURCE_ID' lifecycle_transition_type = 'TYPE' message.post_lifecycle_hook_message(lifecycle_action_token, node_id, resource_id, lifecycle_transition_type) mock_zc.queue_create.assert_not_called() self.assertEqual(3, mock_zc.message_post.call_count)
def _delete_nodes_with_hook(self, action_name, node_ids, lifecycle_hook): lifecycle_hook_timeout = lifecycle_hook.get('timeout') lifecycle_hook_type = lifecycle_hook.get('type', None) lifecycle_hook_params = lifecycle_hook.get('params') if lifecycle_hook_type == "zaqar": lifecycle_hook_target = lifecycle_hook_params.get('queue') else: # lifecycle_hook_target = lifecycle_hook_params.get('url') return self.RES_ERROR, ("Lifecycle hook type '%s' is not " "implemented") % lifecycle_hook_type child = [] for node_id in node_ids: kwargs = { 'name': 'node_delete_%s' % node_id[:8], 'cause': consts.CAUSE_DERIVED_LCH, } action_id = base.Action.create(self.context, node_id, action_name, **kwargs) child.append((action_id, node_id)) if child: dobj.Dependency.create(self.context, [aid for aid, nid in child], self.id) # lifecycle_hook_type has to be "zaqar" # post message to zaqar kwargs = { 'user': self.context.user_id, 'project': self.context.project_id, 'domain': self.context.domain_id } notifier = msg.Message(lifecycle_hook_target, **kwargs) for action_id, node_id in child: # wait lifecycle complete if node exists and is active node = no.Node.get(self.context, node_id) if not node: LOG.warning( 'Node %s is not found. ' 'Skipping wait for lifecycle completion.', node_id) status = base.Action.READY child.remove((action_id, node_id)) elif node.status != consts.NS_ACTIVE or not node.physical_id: LOG.warning( 'Node %s is not in ACTIVE status. ' 'Skipping wait for lifecycle completion.', node_id) status = base.Action.READY child.remove((action_id, node_id)) else: status = base.Action.WAITING_LIFECYCLE_COMPLETION ao.Action.update(self.context, action_id, {'status': status}) if status == base.Action.WAITING_LIFECYCLE_COMPLETION: notifier.post_lifecycle_hook_message( action_id, node_id, node.physical_id, consts.LIFECYCLE_NODE_TERMINATION) dispatcher.start_action() res, reason = self._wait_for_dependents(lifecycle_hook_timeout) if res == self.RES_LIFECYCLE_HOOK_TIMEOUT: self._handle_lifecycle_timeout(child) if res is None or res == self.RES_LIFECYCLE_HOOK_TIMEOUT: dispatcher.start_action() res, reason = self._wait_for_dependents() return res, reason return self.RES_OK, ''