def __call__(self, environ, start_response): #pass through if no exceptions occur try: return self.application(environ, start_response) # handle HTTP errors except exc.HTTPException as err: log.debug(u"{0} Thrown: {1}".format(err.__class__.__name__, err)) # if the middleware is configured with an error controller # use that to display the errors if self.error_controller: handler = self.error_controller(err, status_code=err.code) try: # try executing error_handler code # otherwise re-raise the exception return handler(environ, start_response) except Exception: log.exception("Exception thrown during error_controller handling") raise else: # HTTPExceptions are also WSGI apps and can be called as such return err(environ, start_response) except Exception as err: log.exception("General Exception thrown") if self.error_controller: handler = self.error_controller(err, message=str(err)) else: # create a generic HTTP server Error webob exception handler = exc.HTTPServerError('General Fault') return handler(environ, start_response)
def delete(self, req, id): """Delete a plan.""" context = req.environ['karbor.context'] LOG.info("Delete plan with id: %s", id, context=context) try: plan = self._plan_get(context, id) except exception.PlanNotFound as error: raise exc.HTTPNotFound(explanation=error.msg) context.can(plan_policy.DELETE_POLICY, target_obj=plan) project_id = plan.project_id try: plan.destroy() except Exception: msg = _("Failed to destroy a plan.") raise exc.HTTPServerError(reason=msg) try: reserve_opts = {'plans': -1} reservations = QUOTAS.reserve(context, project_id=project_id, **reserve_opts) except Exception: LOG.exception("Failed to update usages deleting plan.") else: QUOTAS.commit(context, reservations, project_id=project_id) LOG.info("Delete plan request issued successfully.", resource={'id': plan.id})
def get_by_name(self, req): """ Get one vsm setting by name """ context = req.environ['vsm.context'] search_opts = {} search_opts.update(req.GET) LOG.debug('search options %s' % search_opts) vsm_name = search_opts.pop('name', None) if not vsm_name: raise exc.HTTPBadRequest( explanation=_('Invalid request: vsm name is required.')) try: utils.check_string_length(vsm_name, 'name', min_length=1, max_length=255) setting = db.vsm_settings_get_by_name(context, vsm_name) except db_exc.DBError as e: raise exc.HTTPServerError(explanation=e.message) except exception.InvalidInput as e: raise exc.HTTPBadRequest(explanation=e.message) if not setting: raise exc.HTTPNotFound( explanation=_('The vsm setting(%s) does not exists.' % vsm_name)) return self._view_builder.basic(req, setting)
def _detach_nbs_volume(self, req, server_id, id): """Detach a nbs volume from an instance.""" if FLAGS.nbs_api_server is None: explanation = _("Cannot detach nbs volume, nbs server is None.") raise exc.HTTPServerError(explanation=explanation) context = req.environ['nova.context'] authorize(context) volume_id = id LOG.audit(_("Detach nbs volume %(volume)s from instance %(server)s") % {"volume": volume_id, "server": server_id}, context=context) try: instance = self.compute_api.get(context, server_id) except exception.NotFound: explanation = _("Instance %s not found.") % server_id raise exc.HTTPNotFound(explanation=explanation) try: self.compute_api.detach_nbs_volume(context, instance, volume_id) except exception.VolumeNotFound: explanation = _("Volume not found.") raise exc.HTTPNotFound(explanation=explanation) except exception.Invalid: explanation = _("Volume is not attached.") raise exc.HTTPNotFound(explanation=explanation) else: return {'requestId': context.request_id, 'return': True}
def __call__(self, req): """Handles the HTTP POST request. Attempts to interpret all HTTP POST requests as XML-RPC calls, which are forwarded to the server's _dispatch method for handling. Most code taken from SimpleXMLRPCServer with modifications for wsgi and my custom dispatcher. """ if req.method != 'POST': return exc.HTTPBadRequest() try: data = req.environ['wsgi.input'].read(req.content_length) response = self.dispatcher._marshaled_dispatch( data, self.dispatcher._dispatch) + b'\n' except: # pragma: no cover # This should only happen if the module is buggy # internal error, report as HTTP server error return exc.HTTPServerError() else: # got a valid XML RPC response response = Response(response) response.content_type = 'text/xml' return response
def _create_setting(self, context, setting_dict): try: return db.vsm_settings_update_or_create(context, setting_dict) except db_exc.DBError as e: raise exc.HTTPServerError(explanation=e.message)
def update_phyname_of_network(self, req, body): try: self.db_api.update_phyname_of_network(req.context, body) return {} except exception.NotFound: raise exc.HTTPServerError( explanation="Update database for phyname of network " "table failed!")
def get_all_networks(self, req): params = self._get_query_params(req) try: networks = self.db_api.network_get_all(req.context, **params) except Exception: raise exc.HTTPServerError(explanation="Get all networks failed") return networks
def _create_setting(self, context, setting_dict): try: if setting_dict.get('name') in ['cpu_diamond_collect_interval','ceph_diamond_collect_interval']: self.scheduler_api.reconfig_diamond(context, setting_dict) return db.vsm_settings_update_or_create(context, setting_dict) except db_exc.DBError as e: raise exc.HTTPServerError(explanation=e.message)
def view(self, req): """ View old exception reports """ id = int(req.path_info_pop()) if id not in self.debug_infos: return exc.HTTPServerError( "Traceback by id %s does not exist (maybe " "the server has been restarted?)" % id) debug_info = self.debug_infos[id] return debug_info.wsgi_application
def _generate_get_error(self): """Falcon exception generator to throw from early-exit mocks. Creates an exception that should be raised by GET tests that pass RBAC. This allows such flows to short-circuit normal post-RBAC processing that is not tested in this module. :return: Python exception that should be raised by repo get methods. """ # The 'Read Error' clause needs to match that asserted in # _assert_post_rbac_exception() above. return exc.HTTPServerError(detail='Read Error')
def upload(self, req, body=None): """Upload new file archive for the new package together with package metadata. """ policy.check("upload_package", req.context) _check_content_type(req, 'multipart/form-data') file_obj, package_meta = _validate_body(body) if package_meta: try: jsonschema.validate(package_meta, schemas.PKG_UPLOAD_SCHEMA) except jsonschema.ValidationError as e: LOG.exception(e) raise exc.HTTPBadRequest(explanation=e.message) else: package_meta = {} with tempfile.NamedTemporaryFile(delete=False) as tempf: LOG.debug("Storing package archive in a temporary file") content = file_obj.file.read() if not content: msg = _("Uploading file can't be empty") LOG.error(msg) raise exc.HTTPBadRequest(msg) tempf.write(content) package_meta['archive'] = content try: pkg_to_upload = load_utils.load_from_file(tempf.name, target_dir=None, drop_dir=True) except pkg_exc.PackageLoadError as e: LOG.exception(e) raise exc.HTTPBadRequest(e) finally: LOG.debug("Deleting package archive temporary file") os.remove(tempf.name) # extend dictionary for update db for k, v in PKG_PARAMS_MAP.iteritems(): if hasattr(pkg_to_upload, k): package_meta[v] = getattr(pkg_to_upload, k) if req.params.get('is_public', '').lower() == 'true': policy.check('publicize_image', req.context) package_meta['is_public'] = True try: package = db_api.package_upload(package_meta, req.context.tenant) except db_exc.DBDuplicateEntry: msg = _('Package with specified full name is already registered') LOG.exception(msg) raise exc.HTTPServerError(msg) return package.to_dict()
def __call__(self, req): ''' The ErrorController will return a formatted stack trace if in debug mode, or point to a regular error page otherwise. ''' if 400 <= int(self.status_code) < 500: return req.get_response(self.exception) else: if config.debug: stack_trace = render(template='stack_trace', data={'req': req}) return Response(body=stack_trace, status=self.status_code) else: return req.get_response(exc.HTTPServerError('General Fault'))
def ogcserver_app(environ, start_response): from webob import Request req = Request(environ) try: resp = req.get_response(app) return resp(environ, start_response) except Exception, e: if not debug: log.error('%r: %s', e, e) log.error('%r', environ) from webob import exc return exc.HTTPServerError(str(e))(environ, start_response) else: raise
def _respond(cls, request): try: path_response = cls.__routes.match(request.path_info) if path_response[0] is None: raise exc.HTTPNotFound() endpoint = path_response[0] session = SessionObject( request.environ, **cls.__get_session_config()) try: method = endpoint(request.method) result = method( _Request( session=session, route_params=path_response[1], path_for=cls.__routes.path_for, raw=request ) ) except Exception as e: raise exc.HTTPServerError() response = webob.Response() if session.accessed(): if not session.dirty(): session.save() session.persist() cookie = session.__dict__['_headers']['cookie_out'] if \ session.__dict__['_headers']['set_cookie'] else None if cookie: response.headers.add('Set-Cookie', cookie) if cls.__config['show_x_powered_by']: response.headers.add( 'X-Powered-By', 'Lulu version %s' % _VERSION) if isinstance(result, basestring): response.text = result response.charset = 'utf8' elif type(result) is dict: response.content_type = result['content_type'] if \ 'content_type' in result.keys() else 'text/html' response.body = result['body'] return response except exc.HTTPError as e: return e
def __call__(self, environ, start_response): req = Request(environ) action = req.path.strip('/').replace('/', '_') + '_' + req.method try: if hasattr(self, action): resp = Response(getattr(self, action)(req)) else: resp = Response(exc.HTTPBadRequest('Incorrect path or method')) except exc.HTTPException as e: resp = e except ValueError: resp = exc.HTTPBadRequest('Incorrect data for request') except Exception as e: resp = exc.HTTPServerError(e.message) return resp(environ, start_response)
def _deleteFixedIPs(self, req, id, body): context = req.environ['nova.context'] authorize(context, action='deleteFixedIPs') self._check_body(body, 'deleteFixedIPs') try: net = objects.Network.get_by_uuid(context, id) net.delete_fixed_ips(context) except exception.NotFound: msg = _('Network {net} not found'.format(net=id)) LOG.error(msg) raise exc.HTTPNotFound() except exception.FixedIpAlreadyInUse as e: msg = _('Cannot delete, fixed ip in use: {e}'.format(e=e)) LOG.error(msg) raise exc.HTTPServerError(detail=msg) return Response(status_int=202)
def show(self, req, id): context = req.environ['nova.context'] authorize(context) LOG.debug(_("Listing server status"), context=context, instance_uuid=id) try: instance = self.compute_api.get(context, id) result = self.compute_api.instance_os_boot_ready( context, instance['uuid'], FLAGS.server_heartbeat_period) return result except exception.MemCacheClientNotFound: explanation = _("Memory cache client is not found.") raise exc.HTTPServerError(explanation=explanation) except exception.NotFound: explanation = _("Instance %s not found.") % id raise exc.HTTPNotFound(explanation=explanation)
def render(self, request, map): if request.method == 'POST': raw_data = request.body elif 'q' in request.GET: raw_data = request.GET['q'] else: raise exc.HTTPBadRequest("No 'q' parameter specified").exception try: d = json.loads(raw_data.decode('utf-8')) except: raise exc.HTTPBadRequest('Error parsing JSON').exception try: image, content_type, elapsed = self.nikweb_http.render(map, d) except: raise exc.HTTPServerError('Error rendering').exception resp = Response(body=image, content_type=content_type) resp.headers['X-nikweb-rendertime'] = "%0.3f" % elapsed return resp
def get_debug_info(func): """ A decorator (meant to be used under ``wsgiapp()``) that resolves the ``debugcount`` variable to a ``DebugInfo`` object (or gives an error if it can't be found). """ def debug_info_replacement(self, req): if 'debugcount' not in req.params: return exc.HTTPBadRequest( "You must provide a debugcount parameter") debugcount = req.params['debugcount'] try: debugcount = int(debugcount) except ValueError, e: return exc.HTTPBadRequest("Invalid value for debugcount (%r): %s" % (debugcount, e)) if debugcount not in self.debug_infos: return exc.HTTPServerError( "Debug %s not found (maybe it has expired, or the server was restarted)" % debugcount) req.debug_info = self.debug_infos[debugcount] return func(self, req)
def __call__(self, request): client_name = request.environ.get('REMOTE_USER') if not client_name: raise u2f_error(BadInputException('Client not specified')) try: resp = self.client(request, client_name) if not isinstance(resp, Response): resp = Response(json.dumps(resp), content_type='application/json') return resp except Exception as e: self._session.rollback() if isinstance(e, U2fException): e = u2f_error(e) elif isinstance(e, exc.HTTPException): pass else: log.exception('Server error') e = exc.HTTPServerError(e.args[0]) raise e finally: self._session.commit()
def _attach_nbs_volume(self, req, server_id, body): """Attach a nbs volume to an instance.""" if FLAGS.nbs_api_server is None: explanation = _("Cannot attach nbs volume, nbs server is None.") raise exc.HTTPServerError(explanation=explanation) context = req.environ['nova.context'] authorize(context) if not self.is_valid_body(body, 'volumeAttachment'): explanation = _("Invalid paramater in body.") raise exc.HTTPUnprocessableEntity(explanation=explanation) volume_id = body['volumeAttachment'].get('volumeId') if not volume_id: explanation = _("Invalid paramater in body.") raise exc.HTTPUnprocessableEntity(explanation=explanation) LOG.audit(_("Attach nbs volume %(volume)s to instance %(server)s") % {"volume": volume_id, "server": server_id}, context=context) try: instance = self.compute_api.get(context, server_id) # Check os status if instance is 'ACTIVE' if instance['vm_state'] == vm_states.ACTIVE: os_status = self.compute_api.instance_os_boot_ready(context, instance['uuid'], FLAGS.server_heartbeat_period) if os_status['status'] != "up": explanation = _("Cannot attach volume while instance os " "is starting.") raise exc.HTTPForbidden(explanation=explanation) device = self.compute_api.attach_nbs_volume(context, instance, volume_id) except exception.MemCacheClientNotFound: explanation = _("Memory cache client is not found.") raise exc.HTTPServerError(explanation=explanation) except exception.VolumeNotFound: explanation = _("Volume not found.") raise exc.HTTPNotFound(explanation=explanation) except exception.NotFound: explanation = _("Instance %s not found.") % server_id raise exc.HTTPNotFound(explanation=explanation) except exception.NoFreeDevice: explanation = _("No free device to attach volume.") raise exc.HTTPUnprocessableEntity(explanation=explanation) except exception.Invalid: explanation = _("Volume is not available.") raise exc.HTTPForbidden(explanation=explanation) except exception.NbsAttachForbidden: explanation = _("Instance %s is forbidden to attach " "volume.") % server_id raise exc.HTTPForbidden(explanation=explanation) # The attach is async attachment = {} attachment['instanceId'] = instance['uuid'] attachment['volumeId'] = volume_id attachment['device'] = device attachment['status'] = "attaching" attachment['attachTime'] = long(time.time()) # NOTE(justinsb): And now, we have a problem... # The attach is async, so there's a window in which we don't see # the attachment (until the attachment completes). We could also # get problems with concurrent requests. I think we need an # attachment state, and to write to the DB here, but that's a bigger # change. # For now, we'll probably have to rely on libraries being smart # TODO(justinsb): How do I return "accepted" here? return {'attachment': attachment, 'requestId': context.request_id}
def __call__(self, environ, start_response): req = Request(environ) step = req.path_info.strip('/') try: if step in [i[0] for i in self.steps]: # determine which step we are on index = [i[0] for i in self.steps].index(step) else: # delegate to Trac environ['trac.env_parent_dir'] = self.directory environ['trac.env_index_template'] = self.index # data for index template if req.remote_user and self.remote_user_name: # XXX fails if unicode req.remote_user = str( self.remote_user_name(req.remote_user)) data = { 'remote_user': req.remote_user or '', 'auth': self.auth and 'yes' or '' } environ['trac.template_vars'] = ','.join( ["%s=%s" % (key, value) for key, value in data.items()]) return dispatch_request(environ, start_response) # if self.auth, enforce remote_user to be set if self.auth and not req.remote_user: return exc.HTTPUnauthorized()(environ, start_response) # if POST-ing, validate the request and store needed information errors = [] name, step = self.steps[index] base_url = req.url.rsplit(step.name, 1)[0] project = req.params.get('project') if req.method == 'POST': # check for project existence if not project and index: res = exc.HTTPSeeOther("No session found", location="create-project") return res(environ, start_response) if index: if project not in self.projects: errors.append('Project not found') project_data = self.projects.get(project) errors = step.errors(project_data, req.POST) if not index: project_data = self.projects[project] = {} # set *after* error check so that `create-project` doesn't find itself project_data['base_url'] = base_url if not errors: # success step.transition(project_data, req.POST) # find the next step and redirect to it while True: index += 1 if index == len(self.steps): destination = self.done % self.projects[project][ 'vars'] time.sleep(1) # XXX needed? self.projects.pop( project) # successful project creation break else: name, step = self.steps[index] if step.display(project_data): destination = '%s?project=%s' % ( self.steps[index][0], project) break else: step.transition(project_data, {}) res = exc.HTTPSeeOther(destination, location=destination) return res(environ, start_response) else: # GET project_data = self.projects.get(project, {}) project_data['base_url'] = base_url if index and project not in self.projects: res = exc.HTTPSeeOther("No session found", location="create-project") return res(environ, start_response) # render the template and return the response data = step.data(project_data) data['req'] = req data['errors'] = errors template = self.loader.load(step.template) html = template.generate(**data).render('html', doctype='html') res = Response(content_type='text/html', body=html) return res(environ, start_response) except: # error handling exceptionType, exceptionValue, exceptionTraceback = sys.exc_info() buffer = StringIO() traceback.print_exception(exceptionType, exceptionValue, exceptionTraceback, limit=20, file=buffer) res = exc.HTTPServerError(buffer.getvalue()) return res(environ, start_response)
def _wsgi_remove_object_exc(self, environ, start_response): p = self.Parent.query.get() p.delete() err = exc.HTTPServerError('Test Error') assert False
def _extend_nbs_volume(self, req, id, body): """Extend a exists nbs volume.""" if FLAGS.nbs_api_server is None: explanation = _("Cannot extend nbs volume, nbs server is None.") raise exc.HTTPServerError(explanation=explanation) context = req.environ['nova.context'] authorize(context) if 'size' not in body or not isinstance(body['size'], int): explanation = _("Invalid paramater in body.") raise exc.HTTPUnprocessableEntity(explanation=explanation) LOG.audit(_("Extend nbs volume %s") % id, context=context) size = body['size'] # in GB try: can_extend = self.compute_api.check_nbs_size(context, id, size) if not can_extend: explanation = _("Cannot extend volume, invalid size is given.") raise exc.HTTPForbidden(explanation=explanation) except exception.VolumeNotFound: explanation = _("Volume not found.") raise exc.HTTPNotFound(explanation=explanation) except exception.NbsException: explanation = _("Nbs volume server error.") raise exc.HTTPServerError(explanation=explanation) try: instance_uuid = self.compute_api.check_nbs_attached(context, id) except exception.NotFound: explanation = _("Volume not found.") raise exc.HTTPNotFound(explanation=explanation) except exception.Invalid: LOG.info(_("Volume %s is not attached.") % id) instance_uuid = None if instance_uuid is not None: try: # check instance exists instance = self.compute_api.get(context, instance_uuid) # Check os status if instance is 'ACTIVE' if instance['vm_state'] == vm_states.ACTIVE: server_heartbeat_period = FLAGS.get( 'server_heartbeat_period', 10) os_status = self.compute_api.instance_os_boot_ready( context, instance['uuid'], server_heartbeat_period) if os_status['status'] != "up": explanation = _("Cannot extend volume while instance " "os is starting.") raise exc.HTTPForbidden(explanation=explanation) except exception.MemCacheClientNotFound: explanation = _("Memory cache client is not found.") raise exc.HTTPServerError(explanation=explanation) except exception.NotFound: explanation = _("Instance %s not found.") % instance_uuid raise exc.HTTPNotFound(explanation=explanation) # notify instance about this extension self.compute_api.extend_nbs_volume(context, id, size, instance) else: # call nbs to extend this volume directly self.compute_api.extend_nbs_volume(context, id, size) return {'requestId': context.request_id, 'size': size}
def _update_nbs_qos(self, req, server_id, id, body): """Update QoS parameters of nbs volume.""" if FLAGS.nbs_api_server is None: explanation = _("Cannot update nbs qos info, nbs server is None.") raise exc.HTTPServerError(explanation=explanation) context = req.environ['nova.context'] authorize(context) vol_project = None if context.is_admin: vol_project = req.headers.get('X-Vol-Project') if not vol_project: explanation = _("Project ID of volume is invalid.") raise exc.HTTPUnprocessableEntity(explanation=explanation) iotune_total_bytes = body.get('maxBandWidth') iotune_total_iops = body.get('maxIOPS') iotune_read_bytes = body.get('maxReadBandWidth') iotune_write_bytes = body.get('maxWriteBandWidth') iotune_read_iops = body.get('maxReadIOPS') iotune_write_iops = body.get('maxWriteIOPS') qos_info = {} if (iotune_read_bytes is not None or iotune_write_bytes is not None or iotune_read_iops is not None or iotune_write_iops is not None): if iotune_read_bytes is not None: qos_info['iotune_read_bytes'] = iotune_read_bytes if iotune_write_bytes is not None: qos_info['iotune_write_bytes'] = iotune_write_bytes if iotune_read_iops is not None: qos_info['iotune_read_iops'] = iotune_read_iops if iotune_write_iops is not None: qos_info['iotune_write_iops'] = iotune_write_iops elif (iotune_total_bytes is not None or iotune_total_iops is not None): if iotune_total_bytes is not None: qos_info['iotune_total_bytes'] = iotune_total_bytes if iotune_total_iops is not None: qos_info['iotune_total_iops'] = iotune_total_iops else: explanation = _("Invalid paramater in body.") raise exc.HTTPUnprocessableEntity(explanation=explanation) for value in qos_info.values(): if not isinstance(value, int): explanation = _("Invalid paramater in body.") raise exc.HTTPUnprocessableEntity(explanation=explanation) volume_id = id LOG.audit(_("Update qos info of nbs volume %(volume)s on instance " "%(server)s to %(qos_info)s") % {"volume": volume_id, "server": server_id, "qos_info": qos_info}, context=context) try: instance = self.compute_api.get(context, server_id) except exception.NotFound: explanation = _("Instance %s not found.") % server_id raise exc.HTTPNotFound(explanation=explanation) # FIXME(wangpan): this API is used by nbs admin user, so the context # is belong to nova admin user for updating qos info # of all instances, but while calling the nbs API, # the real project id of volume is needed, so change # it here manually. if context.is_admin and vol_project: context.project_id = vol_project try: self.compute_api.check_nbs_attached(context, volume_id, instance['uuid']) except exception.NotFound: explanation = _("Volume not found.") raise exc.HTTPNotFound(explanation=explanation) except exception.Invalid: explanation = _("Volume is not attached.") raise exc.HTTPNotFound(explanation=explanation) else: self.compute_api.update_nbs_qos(context, instance, volume_id, qos_info) return {'requestId': context.request_id, 'return': True}