def test_get_bottom_mappings_by_top_id(self): for i in xrange(3): pod = { 'pod_id': 'test_pod_uuid_%d' % i, 'pod_name': 'test_pod_%d' % i, 'az_name': 'test_az_uuid_%d' % i } api.create_pod(self.context, pod) route1 = { 'top_id': 'top_uuid', 'pod_id': 'test_pod_uuid_0', 'resource_type': 'port' } route2 = { 'top_id': 'top_uuid', 'pod_id': 'test_pod_uuid_1', 'bottom_id': 'bottom_uuid_1', 'resource_type': 'port' } route3 = { 'top_id': 'top_uuid', 'pod_id': 'test_pod_uuid_2', 'bottom_id': 'bottom_uuid_2', 'resource_type': 'neutron' } routes = [route1, route2, route3] with self.context.session.begin(): for route in routes: core.create_resource(self.context, models.ResourceRouting, route) mappings = api.get_bottom_mappings_by_top_id(self.context, 'top_uuid', 'port') self.assertEqual('test_pod_uuid_1', mappings[0][0]['pod_id']) self.assertEqual('bottom_uuid_1', mappings[0][1])
def test_job_run_expire(self): @xmanager._job_handle('fake_resource') def fake_handle(self, ctx, payload): pass fake_id = uuidutils.generate_uuid() payload = {'fake_resource': fake_id} expired_job = { 'id': uuidutils.generate_uuid(), 'type': 'fake_resource', 'timestamp': datetime.datetime.now() - datetime.timedelta(0, 120), 'status': constants.JS_Running, 'resource_id': fake_id, 'extra_id': constants.SP_EXTRA_ID } core.create_resource(self.context, models.Job, expired_job) fake_handle(None, self.context, payload=payload) jobs = core.query_resource(self.context, models.Job, [], []) expected_status = ['New', 'Fail', 'Success'] job_status = [job['status'] for job in jobs] self.assertItemsEqual(expected_status, job_status) for i in xrange(3): self.assertEqual(fake_id, jobs[i]['resource_id']) self.assertEqual('fake_resource', jobs[i]['type'])
def post(self, **kw): context = t_context.extract_context_from_environ() if 'server' not in kw: return utils.format_nova_error(400, _('server is not set')) az = kw['server'].get('availability_zone', '') pod, b_az = az_ag.get_pod_by_az_tenant(context, az, self.project_id) if not pod: return utils.format_nova_error( 500, _('Pod not configured or scheduling failure')) t_server_dict = kw['server'] self._process_metadata_quota(context, t_server_dict) self._process_injected_file_quota(context, t_server_dict) server_body = self._get_create_server_body(kw['server'], b_az) security_groups = [] if 'security_groups' not in kw['server']: security_groups = ['default'] else: for sg in kw['server']['security_groups']: if 'name' not in sg: return utils.format_nova_error( 400, _('Invalid input for field/attribute')) security_groups.append(sg['name']) server_body['networks'] = [] if 'networks' in kw['server']: for net_info in kw['server']['networks']: if 'uuid' in net_info: nic = {'net-id': net_info['uuid']} server_body['networks'].append(nic) elif 'port' in net_info: nic = {'port-id': net_info['port']} server_body['networks'].append(nic) client = self._get_client(pod['pod_name']) server = client.create_servers(context, name=server_body['name'], image=server_body['imageRef'], flavor=server_body['flavorRef'], nics=server_body['networks'], security_groups=security_groups) with context.session.begin(): core.create_resource( context, models.ResourceRouting, { 'top_id': server['id'], 'bottom_id': server['id'], 'pod_id': pod['pod_id'], 'project_id': self.project_id, 'resource_type': constants.RT_SERVER }) pecan.response.status = 202 return {'server': server}
def _prepare_server(self, pod): t_server_id = uuidutils.generate_uuid() b_server_id = t_server_id with self.context.session.begin(): core.create_resource( self.context, models.ResourceRouting, {'top_id': t_server_id, 'bottom_id': b_server_id, 'pod_id': pod['pod_id'], 'project_id': self.project_id, 'resource_type': constants.RT_SERVER}) return t_server_id
def change_pod_binding(context, pod_binding, pod_id): with context.session.begin(): core.update_resource(context, models.PodBinding, pod_binding['id'], pod_binding) core.create_resource( context, models.PodBinding, { 'id': uuidutils.generate_uuid(), 'tenant_id': pod_binding['tenant_id'], 'pod_id': pod_id, 'is_binding': True })
def test_get_failed_jobs(self): job_dict_list = [ { 'timestamp': datetime.datetime(2000, 1, 1, 12, 0, 0), 'resource_id': 'uuid1', 'type': 'res1', 'status': constants.JS_Fail }, # job_uuid1 { 'timestamp': datetime.datetime(2000, 1, 1, 12, 5, 0), 'resource_id': 'uuid1', 'type': 'res1', 'status': constants.JS_Fail }, # job_uuid3 { 'timestamp': datetime.datetime(2000, 1, 1, 12, 20, 0), 'resource_id': 'uuid2', 'type': 'res2', 'status': constants.JS_Fail }, # job_uuid5 { 'timestamp': datetime.datetime(2000, 1, 1, 12, 15, 0), 'resource_id': 'uuid2', 'type': 'res2', 'status': constants.JS_Fail }, # job_uuid7 { 'timestamp': datetime.datetime(2000, 1, 1, 12, 25, 0), 'resource_id': 'uuid3', 'type': 'res3', 'status': constants.JS_Fail }, # job_uuid9 { 'timestamp': datetime.datetime(2000, 1, 1, 12, 30, 0), 'resource_id': 'uuid3', 'type': 'res3', 'status': constants.JS_Success } ] for i, job_dict in enumerate(job_dict_list, 1): job_dict['id'] = 'job_uuid%d' % (2 * i - 1) job_dict['extra_id'] = 'extra_uuid%d' % (2 * i - 1) core.create_resource(self.context, models.Job, job_dict) job_dict['id'] = 'job_uuid%d' % (2 * i) job_dict['extra_id'] = 'extra_uuid%d' % (2 * i) job_dict['status'] = constants.JS_New core.create_resource(self.context, models.Job, job_dict) # for res3 + uuid3, the latest job's status is "Success", not returned expected_ids = ['job_uuid3', 'job_uuid5'] returned_jobs = db_api.get_latest_failed_jobs(self.context) actual_ids = [job['id'] for job in returned_jobs] self.assertItemsEqual(expected_ids, actual_ids)
def test_delete_error(self, mock_ctx, mock_delete): t_pod, b_pod = self._prepare_pod() mock_ctx.return_value = self.context # pass invalid id res = self.controller.delete('fake_id') self.assertEqual('Server not found', res['Error']['message']) self.assertEqual(404, res['Error']['code']) t_server_id = 't_server_id' b_server_id = 'b_server_id' with self.context.session.begin(): core.create_resource( self.context, models.ResourceRouting, { 'top_id': t_server_id, 'bottom_id': b_server_id, 'pod_id': b_pod['pod_id'], 'project_id': self.project_id, 'resource_type': constants.RT_SERVER }) mock_delete.return_value = None # pass stale server id res = self.controller.delete(t_server_id) self.assertEqual('Server not found', res['Error']['message']) self.assertEqual(404, res['Error']['code']) routes = core.query_resource(self.context, models.ResourceRouting, [{ 'key': 'top_id', 'comparator': 'eq', 'value': t_server_id }], []) # check the stale mapping is deleted self.assertEqual(0, len(routes)) with self.context.session.begin(): core.create_resource( self.context, models.ResourceRouting, { 'top_id': t_server_id, 'bottom_id': b_server_id, 'pod_id': b_pod['pod_id'], 'project_id': self.project_id, 'resource_type': constants.RT_SERVER }) # exception occurs when deleting server mock_delete.side_effect = t_exceptions.PodNotFound('pod2') res = self.controller.delete(t_server_id) self.assertEqual('Pod pod2 could not be found.', res['Error']['message']) self.assertEqual(404, res['Error']['code'])
def get_or_create_route(t_ctx, q_ctx, project_id, pod, ele, _type, list_ele_method): # use configuration option later route_expire_threshold = 30 _id = ele['id'] with t_ctx.session.begin(): routes = core.query_resource(t_ctx, models.ResourceRouting, [{ 'key': 'top_id', 'comparator': 'eq', 'value': _id }, { 'key': 'pod_id', 'comparator': 'eq', 'value': pod['pod_id'] }], []) if routes: route = routes[0] if route['bottom_id']: return route, ALL_DONE else: route_time = route['updated_at'] or route['created_at'] current_time = datetime.datetime.utcnow() delta = current_time - route_time if delta.seconds > route_expire_threshold: # NOTE(zhiyuan) cannot directly remove the route, we have # a race here that other worker is updating this route, we # need to check if the corresponding element has been # created by other worker eles = list_ele_method(t_ctx, q_ctx, pod, ele, _type) if eles: route['bottom_id'] = eles[0]['id'] core.update_resource(t_ctx, models.ResourceRouting, route['id'], route) return route, RES_DONE try: core.delete_resource(t_ctx, models.ResourceRouting, route['id']) except db_exc.ResourceNotFound: pass try: # NOTE(zhiyuan) try/except block inside a with block will cause # problem, so move them out of the block and manually handle the # session context t_ctx.session.begin() route = core.create_resource( t_ctx, models.ResourceRouting, { 'top_id': _id, 'pod_id': pod['pod_id'], 'project_id': project_id, 'resource_type': _type }) t_ctx.session.commit() return route, NONE_DONE except db_exc.DBDuplicateEntry: t_ctx.session.rollback() return None, NONE_DONE finally: t_ctx.session.close()
def test_resources(self): """Create all the resources to test model definition""" try: model_list = [] for _, model_class in inspect.getmembers(models): if inspect.isclass(model_class) and (issubclass( model_class, core.ModelBase)): model_list.append(model_class) for model_class in _sort_model_by_foreign_key(model_list): create_dict = _construct_resource_dict(model_class) with self.context.session.begin(): core.create_resource(self.context, model_class, create_dict) except Exception as e: msg = str(e) self.fail('test_resources raised Exception unexpectedly %s' % msg)
def post(self, **kw): context = t_context.extract_context_from_environ() if not t_context.is_admin_context(context): pecan.abort(400, _('Admin role required to create bindings')) return if 'pod_binding' not in kw: pecan.abort(400, _('Request body not found')) return pod_b = kw['pod_binding'] tenant_id = pod_b.get('tenant_id', '').strip() pod_id = pod_b.get('pod_id', '').strip() _uuid = uuidutils.generate_uuid() if tenant_id == '' or pod_id == '': return Response(_('Tenant_id and pod_id can not be empty'), 422) # the az_pod_map_id should be exist for in the pod map table try: with context.session.begin(): pod = core.get_resource(context, models.Pod, pod_id) if pod.get('az_name') == '': return Response(_('Top region can not be bound'), 422) except t_exc.ResourceNotFound: return Response(_('pod_id not found in pod'), 422) except Exception as e: LOG.exception( _LE('Failed to get_resource for pod_id: ' '%(pod_id)s ,' '%(exception)s '), { 'pod_id': pod_id, 'exception': e }) pecan.abort(500, _('Failed to create pod binding')) return try: with context.session.begin(): pod_binding = core.create_resource(context, models.PodBinding, { 'id': _uuid, 'tenant_id': tenant_id, 'pod_id': pod_id }) except db_exc.DBDuplicateEntry: return Response(_('Pod binding already exists'), 409) except db_exc.DBConstraintError: return Response(_('pod_id not exists in pod'), 422) except db_exc.DBReferenceError: return Response(_('DB reference not exists in pod'), 422) except Exception as e: LOG.exception(_LE('Failed to create pod binding: %(exception)s '), {'exception': e}) pecan.abort(500, _('Failed to create pod binding')) return return {'pod_binding': pod_binding}
def create_ag_az(context, ag_name, az_name): aggregate = core.create_resource(context, models.Aggregate, {'name': ag_name}) core.create_resource( context, models.AggregateMetadata, { 'key': 'availability_zone', 'value': az_name, 'aggregate_id': aggregate['id'] }) extra_fields = { 'availability_zone': az_name, 'metadata': { 'availability_zone': az_name } } aggregate.update(extra_fields) return aggregate
def test_resource_routing_unique_key(self): pod = { 'pod_id': 'test_pod1_uuid', 'pod_name': 'test_pod1', 'az_name': 'test_az1_uuid' } api.create_pod(self.context, pod) routing = { 'top_id': 'top_uuid', 'pod_id': 'test_pod1_uuid', 'resource_type': 'port' } with self.context.session.begin(): core.create_resource(self.context, models.ResourceRouting, routing) self.assertRaises(oslo_db.exception.DBDuplicateEntry, core.create_resource, self.context, models.ResourceRouting, routing)
def get_pod_by_az_tenant(context, az_name, tenant_id): pod_bindings = core.query_resource(context, models.PodBinding, [{ 'key': 'tenant_id', 'comparator': 'eq', 'value': tenant_id }], []) for pod_b in pod_bindings: pod = core.get_resource(context, models.Pod, pod_b['pod_id']) if az_name and pod['az_name'] == az_name: return pod, pod['pod_az_name'] elif az_name == '' and pod['az_name'] != '': # if the az_name is not specified, a defult bottom # pod will be selected return pod, pod['pod_az_name'] else: pass # TODO(joehuang): schedule one dynamically in the future if az_name != '': filters = [{'key': 'az_name', 'comparator': 'eq', 'value': az_name}] else: filters = None # if az_name is valid, select a pod under this az_name # if az_name is '', select the first valid bottom pod. # change to dynamic schedluing in the future pods = db_api.list_pods(context, filters=filters) for pod in pods: if pod['pod_name'] != '' and pod['az_name'] != '': try: with context.session.begin(): core.create_resource( context, models.PodBinding, { 'id': uuidutils.generate_uuid(), 'tenant_id': tenant_id, 'pod_id': pod['pod_id'], 'is_binding': True }) return pod, pod['pod_az_name'] except Exception as e: LOG.error(_LE('Fail to create pod binding: %(exception)s'), {'exception': e}) return None, None return None, None
def create_pod_binding(context, tenant_id, pod_id): with context.session.begin(): return core.create_resource( context, models.PodBinding, { 'id': uuidutils.generate_uuid(), 'tenant_id': tenant_id, 'pod_id': pod_id, 'is_binding': True })
def new_job(context, _type, resource_id): with context.session.begin(): job_dict = {'id': uuidutils.generate_uuid(), 'type': _type, 'status': constants.JS_New, 'resource_id': resource_id, 'extra_id': uuidutils.generate_uuid()} job = core.create_resource(context, models.Job, job_dict) return job
def post(self, **kw): context = t_context.extract_context_from_environ() if not context.is_admin: return utils.format_nova_error( 403, _("Policy doesn't allow os_compute_api:os-flavor-manage " "to be performed.")) required_fields = ['name', 'ram', 'vcpus', 'disk'] if 'flavor' not in kw: utils.format_nova_error(400, _('flavor is not set')) if not utils.validate_required_fields_set(kw['flavor'], required_fields): utils.format_nova_error( 400, _('Invalid input for field/attribute flavor.')) flavor_dict = { 'name': kw['flavor']['name'], 'flavorid': kw['flavor'].get('id'), 'memory_mb': kw['flavor']['ram'], 'vcpus': kw['flavor']['vcpus'], 'root_gb': kw['flavor']['disk'], 'ephemeral_gb': kw['flavor'].get('OS-FLV-EXT-DATA:ephemeral', 0), 'swap': kw['flavor'].get('swap', 0), 'rxtx_factor': kw['flavor'].get('rxtx_factor', 1.0), 'is_public': kw['flavor'].get('os-flavor-access:is_public', True), } try: with context.session.begin(): flavor = core.create_resource(context, models.InstanceTypes, flavor_dict) except db_exc.DBDuplicateEntry as e: if 'flavorid' in e.columns: return utils.format_nova_error( 409, _('Flavor with ID %s already ' 'exists.') % flavor_dict['flavorid']) else: return utils.format_nova_error( 409, _('Flavor with name %s already ' 'exists.') % flavor_dict['name']) except Exception: utils.format_nova_error(500, _('Failed to create flavor')) flavor['id'] = flavor['flavorid'] del flavor['flavorid'] return {'flavor': flavor}
def test_delete(self, mock_ctx, mock_delete): t_pod, b_pod = self._prepare_pod() mock_ctx.return_value = self.context t_server_id = 't_server_id' b_server_id = 'b_server_id' with self.context.session.begin(): core.create_resource( self.context, models.ResourceRouting, { 'top_id': t_server_id, 'bottom_id': b_server_id, 'pod_id': b_pod['pod_id'], 'project_id': self.project_id, 'resource_type': constants.RT_SERVER }) port_id = uuidutils.generate_uuid() server_port = {'id': port_id, 'device_id': t_server_id} TOP_PORTS.append(server_port) mock_delete.return_value = () res = self.controller.delete(t_server_id) mock_delete.assert_called_once_with(self.context, b_server_id) self.assertEqual(204, res.status)
def register_job(context, _type, resource_id): try: context.session.begin() job_dict = {'id': uuidutils.generate_uuid(), 'type': _type, 'status': constants.JS_Running, 'resource_id': resource_id, 'extra_id': constants.SP_EXTRA_ID} job = core.create_resource(context, models.Job, job_dict) context.session.commit() return job except db_exc.DBDuplicateEntry: context.session.rollback() return None except db_exc.DBDeadlock: context.session.rollback() return None finally: context.session.close()
def test_attach_volume(self, mock_context, mock_action): mock_context.return_value = self.context mock_action.return_value = FakeVolume() t_pod, b_pods = self._prepare_pod(bottom_pod_num=2) b_pod1 = b_pods[0] b_pod2 = b_pods[1] t_server_id = uuidutils.generate_uuid() b_server_id = t_server_id with self.context.session.begin(): core.create_resource( self.context, models.ResourceRouting, { 'top_id': t_server_id, 'bottom_id': b_server_id, 'pod_id': b_pod1['pod_id'], 'project_id': self.project_id, 'resource_type': constants.RT_SERVER }) t_volume1_id = uuidutils.generate_uuid() b_volume1_id = t_volume1_id t_volume2_id = uuidutils.generate_uuid() b_volume2_id = t_volume1_id with self.context.session.begin(): core.create_resource( self.context, models.ResourceRouting, { 'top_id': t_volume1_id, 'bottom_id': b_volume1_id, 'pod_id': b_pod1['pod_id'], 'project_id': self.project_id, 'resource_type': constants.RT_VOLUME }) core.create_resource( self.context, models.ResourceRouting, { 'top_id': t_volume2_id, 'bottom_id': b_volume2_id, 'pod_id': b_pod2['pod_id'], 'project_id': self.project_id, 'resource_type': constants.RT_VOLUME }) # success case self.controller.server_id = t_server_id body = {'volumeAttachment': {'volumeId': t_volume1_id}} self.controller.post(**body) body = { 'volumeAttachment': { 'volumeId': t_volume1_id, 'device': '/dev/vdb' } } self.controller.post(**body) calls = [ mock.call('server_volume', self.context, 'create_server_volume', b_server_id, b_volume1_id, None), mock.call('server_volume', self.context, 'create_server_volume', b_server_id, b_volume1_id, '/dev/vdb') ] mock_action.assert_has_calls(calls) # failure case, bad request body = {'volumeAttachment': {'volumeId': t_volume2_id}} res = self.controller.post(**body) self._validate_error_code(res, 400) body = {'fakePara': ''} res = self.controller.post(**body) self._validate_error_code(res, 400) body = {'volumeAttachment': {}} res = self.controller.post(**body) self._validate_error_code(res, 400) # each part of path should not start with digit body = { 'volumeAttachment': { 'volumeId': t_volume1_id, 'device': '/dev/001disk' } } res = self.controller.post(**body) self._validate_error_code(res, 400) # the first part should be "dev", and only two parts are allowed body = { 'volumeAttachment': { 'volumeId': t_volume1_id, 'device': '/dev/vdb/disk' } } res = self.controller.post(**body) self._validate_error_code(res, 400) body = { 'volumeAttachment': { 'volumeId': t_volume1_id, 'device': '/disk/vdb' } } res = self.controller.post(**body) self._validate_error_code(res, 400) # failure case, resource not found body = {'volumeAttachment': {'volumeId': 'fake_volume_id'}} res = self.controller.post(**body) self._validate_error_code(res, 404) self.controller.server_id = 'fake_server_id' body = {'volumeAttachment': {'volumeId': t_volume1_id}} res = self.controller.post(**body) self._validate_error_code(res, 404)
def post(self, **kw): context = t_context.extract_context_from_environ() if not policy.enforce(context, policy.ADMIN_API_PODS_CREATE): pecan.abort(401, _('Unauthorized to create pods')) return if 'pod' not in kw: pecan.abort(400, _('Request body pod not found')) return pod = kw['pod'] # if az_name is null, and there is already one in db pod_name = pod.get('pod_name', '').strip() pod_az_name = pod.get('pod_az_name', '').strip() dc_name = pod.get('dc_name', '').strip() az_name = pod.get('az_name', '').strip() _uuid = uuidutils.generate_uuid() if az_name == '' and pod_name == '': return Response(_('Valid pod_name is required for top region'), 422) if az_name != '' and pod_name == '': return Response(_('Valid pod_name is required for pod'), 422) if pod.get('az_name') is None: if self._get_top_region(context) != '': return Response(_('Top region already exists'), 409) # if az_name is not null, then the pod region name should not # be same as that the top region if az_name != '': if self._get_top_region(context) == pod_name and pod_name != '': return Response( _('Pod region name duplicated with the top region name'), 409) # to create the top region, make the pod_az_name to null value if az_name == '': pod_az_name = '' try: with context.session.begin(): # if not top region, # then add corresponding ag and az for the pod if az_name != '': ag_name = utils.get_ag_name(pod_name) aggregate = az_ag.create_ag_az(context, ag_name=ag_name, az_name=az_name) if aggregate is None: return Response(_('Ag creation failure'), 400) new_pod = core.create_resource( context, models.Pod, { 'pod_id': _uuid, 'pod_name': pod_name, 'pod_az_name': pod_az_name, 'dc_name': dc_name, 'az_name': az_name }) except db_exc.DBDuplicateEntry as e1: LOG.exception( _LE('Record already exists on %(pod_name)s: ' '%(exception)s'), { 'pod_name': pod_name, 'exception': e1 }) return Response(_('Record already exists'), 409) except Exception as e2: LOG.exception( _LE('Failed to create pod: %(pod_name)s,' 'pod_az_name: %(pod_az_name)s,' 'dc_name: %(dc_name)s,' 'az_name: %(az_name)s' '%(exception)s '), { 'pod_name': pod_name, 'pod_az_name': pod_az_name, 'dc_name': dc_name, 'az_name': az_name, 'exception': e2 }) return Response(_('Failed to create pod'), 500) return {'pod': new_pod}
def post(self, **kw): context = t_context.extract_context_from_environ() if 'volume' not in kw: return utils.format_cinder_error( 400, _("Missing required element 'volume' in request body.")) az = kw['volume'].get('availability_zone', '') pod, pod_az = az_ag.get_pod_by_az_tenant(context, az_name=az, tenant_id=self.tenant_id) if not pod: LOG.error(_LE("Pod not configured or scheduling failure")) return utils.format_cinder_error( 500, _('Pod not configured or scheduling failure')) t_pod = db_api.get_top_pod(context) if not t_pod: LOG.error(_LE("Top Pod not configured")) return utils.format_cinder_error(500, _('Top Pod not configured')) # TODO(joehuang): get release from pod configuration, # to convert the content # b_release = pod['release'] # t_release = t_pod['release'] t_release = cons.R_MITAKA b_release = cons.R_MITAKA s_ctx = hclient.get_pod_service_ctx(context, request.url, pod['pod_name'], s_type=cons.ST_CINDER) if s_ctx['b_url'] == '': LOG.error( _LE("Bottom Pod endpoint incorrect %s") % pod['pod_name']) return utils.format_cinder_error( 500, _('Bottom Pod endpoint incorrect')) b_headers = hclient.convert_header(t_release, b_release, request.headers) t_vol = kw['volume'] # add or remove key-value in the request for diff. version b_vol_req = hclient.convert_object(t_release, b_release, t_vol, res_type=cons.RT_VOLUME) # convert az to the configured one # remove the AZ parameter to bottom request for default one b_vol_req['availability_zone'] = pod['pod_az_name'] if b_vol_req['availability_zone'] == '': b_vol_req.pop("availability_zone", None) b_body = jsonutils.dumps({'volume': b_vol_req}) resp = hclient.forward_req(context, 'POST', b_headers, s_ctx['b_url'], b_body) b_status = resp.status_code b_ret_body = jsonutils.loads(resp.content) # build routing and convert response from the bottom pod # for different version. response.status = b_status if b_status == 202: if b_ret_body.get('volume') is not None: b_vol_ret = b_ret_body['volume'] try: with context.session.begin(): core.create_resource( context, models.ResourceRouting, { 'top_id': b_vol_ret['id'], 'bottom_id': b_vol_ret['id'], 'pod_id': pod['pod_id'], 'project_id': self.tenant_id, 'resource_type': cons.RT_VOLUME }) except Exception as e: LOG.exception( _LE('Failed to create volume ' 'resource routing' 'top_id: %(top_id)s ,' 'bottom_id: %(bottom_id)s ,' 'pod_id: %(pod_id)s ,' '%(exception)s '), { 'top_id': b_vol_ret['id'], 'bottom_id': b_vol_ret['id'], 'pod_id': pod['pod_id'], 'exception': e }) return utils.format_cinder_error( 500, _('Failed to create volume resource routing')) ret_vol = hclient.convert_object(b_release, t_release, b_vol_ret, res_type=cons.RT_VOLUME) ret_vol['availability_zone'] = pod['az_name'] return {'volume': ret_vol} return b_ret_body
def test_get_bottom_mappings_by_tenant_pod(self): for i in xrange(3): pod = { 'pod_id': 'test_pod_uuid_%d' % i, 'pod_name': 'test_pod_%d' % i, 'az_name': 'test_az_uuid_%d' % i } api.create_pod(self.context, pod) routes = [{ 'route': { 'top_id': 'top_uuid', 'pod_id': 'test_pod_uuid_0', 'project_id': 'test_project_uuid_0', 'resource_type': 'port' }, }, { 'route': { 'top_id': 'top_uuid_0', 'bottom_id': 'top_uuid_0', 'pod_id': 'test_pod_uuid_0', 'project_id': 'test_project_uuid_0', 'resource_type': 'port' }, }, { 'route': { 'top_id': 'top_uuid_1', 'bottom_id': 'top_uuid_1', 'pod_id': 'test_pod_uuid_0', 'project_id': 'test_project_uuid_0', 'resource_type': 'port' }, }, { 'route': { 'top_id': 'top_uuid_2', 'bottom_id': 'top_uuid_2', 'pod_id': 'test_pod_uuid_0', 'project_id': 'test_project_uuid_1', 'resource_type': 'port' }, }, { 'route': { 'top_id': 'top_uuid_3', 'bottom_id': 'top_uuid_3', 'pod_id': 'test_pod_uuid_1', 'project_id': 'test_project_uuid_1', 'resource_type': 'port' }, }] with self.context.session.begin(): for route in routes: core.create_resource(self.context, models.ResourceRouting, route['route']) routings = api.get_bottom_mappings_by_tenant_pod( self.context, 'test_project_uuid_0', 'test_pod_uuid_0', 'port') self.assertEqual(len(routings), 2) self.assertEqual(routings['top_uuid_0']['top_id'], 'top_uuid_0') self.assertEqual(routings['top_uuid_1']['top_id'], 'top_uuid_1') routings = api.get_bottom_mappings_by_tenant_pod( self.context, 'test_project_uuid_1', 'test_pod_uuid_0', 'port') self.assertEqual(len(routings), 1) self.assertEqual(routings['top_uuid_2']['top_id'], 'top_uuid_2') self.assertEqual(routings['top_uuid_2']['bottom_id'], 'top_uuid_2') routings = api.get_bottom_mappings_by_tenant_pod( self.context, 'test_project_uuid_1', 'test_pod_uuid_1', 'port') self.assertEqual(len(routings), 1) self.assertEqual(routings['top_uuid_3']['top_id'], 'top_uuid_3') self.assertEqual(routings['top_uuid_3']['bottom_id'], 'top_uuid_3')
def create_pod_service_configuration(context, config_dict): with context.session.begin(): return core.create_resource(context, models.PodServiceConfiguration, config_dict)
def create_pod(context, pod_dict): with context.session.begin(): return core.create_resource(context, models.Pod, pod_dict)