def load_json(): """ load json file gvu_stpoelten.json to api """ try: with open(working_directory + "/gvu_stpoelten.json", 'r') as jf: neu_datetime = list() for item in json.load(jf): neu_datetime.append({ 'date': (datetime.strptime(item['date'], '%Y-%m-%d %H:%M')).replace(tzinfo=None), 'garbage_container_type': item['garbage_container_type'] }) return neu_datetime except FileNotFoundError as e: raise exceptions.InternalServerError( description="File Not found. Directory: {0}".format( working_directory)) except Exception as e: raise exceptions.InternalServerError(description=e)
def get_image_id(request): # Get our desired filename. uploading_filename = request.form.get("imageFileName") if not uploading_filename: return exceptions.BadRequest() # Ensure we have an image. if "jpegData" not in request.files: return exceptions.BadRequest() # Sanitize for when we write to disk. filename = secure_filename(uploading_filename) # Necessary as render templates require the original filename with ".jpg" appended. # Nobody here is fond of this. filename += ".jpg" # An image ID has a maximum size of 7. unique_id = generate_unique_id(Images, Images.image_id, 7) if unique_id == "": return exceptions.InternalServerError() # Next, save our file to disk. jpeg_image = request.files["jpegData"] jpeg_image.save(determine_path(current_order.order_id, filename)) # Finally, save state to the database. added_image = Images( image_id=unique_id, order_id=current_order.order_id, filename=filename ) db.session.add(added_image) db.session.commit() return { "imageID": unique_id, }
def _proxy_request(self, remote_address, path_info, query_string): headers = { 'X-Forwarded-For': remote_address, 'X-Instance-ID': self.ip_instance_map.get(remote_address, ''), 'X-Quantum-Network-ID': self.network_id, 'X-Tenant-ID': self.tenant_id } url = urlparse.urlunsplit(( 'http', self.orchestrator_loc, path_info, query_string, '')) response = requests.get(url, headers=headers) if response.status_code == requests.codes.ok: LOG.debug(response) return wrappers.Response(response.content, mimetype='text/plain') elif response.status_code == requests.codes.not_found: return exceptions.NotFound() elif response.status_code == requests.codes.internal_server_error: msg = 'Remote metadata server experienced an error.' return exceptions.InternalServerError(description=unicode(msg)) else: raise Exception('Unexpected response code: %s' % response.status)
def post( body: typing.Dict[str, typing.Any] ) -> typing.Tuple[typing.Dict[str, typing.Any], int]: LOG.info('Received request to create a new user') try: single_user = user.UserDB.query.filter_by( user_name=body['user_name']).one() if single_user: exceptions.Conflict( description='User by this name already exists in the system') except exc.NoResultFound: LOG.info('User doesn\'t exist, system will add it') new_user = user.UserDB(**body) new_user.id = str(uuid.uuid4()) database.db.session.add(new_user) try: database.db.session.commit() LOG.info('Added new user') except Exception: LOG.exception('Failed to add user') database.db.session.rollback() exceptions.InternalServerError( description='Failed to add new user to the system') return user.User( id=str(new_user.id), userName=new_user.user_name, firstName=new_user.first_name, lastName=new_user.last_name, email=new_user.email, address=new_user.address, postalCode=new_user.postal_code, ).dict(), 201
def load_users_json(): """ load users json file """ try: with open(working_directory + "/users.json", 'r') as jf: return json.load(jf)['users'] except FileNotFoundError as e: raise exceptions.InternalServerError( description="File Not found. Directory: {0}".format( working_directory + "/udsers.json")) except Exception as e: raise exceptions.InternalServerError(description=e)
def portfolio_download(human_id, filename): logger.debug('GET ' + request.url) try: # Find the portfolio folio = data_engine.get_portfolio(human_id=human_id) if not folio: raise DoesNotExistError('Portfolio \'%s\' does not exist' % human_id) # Ensure that the user has permission to download the portfolio user = get_session_user() permissions_engine.ensure_portfolio_permitted( folio, FolioPermission.ACCESS_DOWNLOAD, user) # Check that the filename is valid (note: assumes folio.downloads is eager loaded) if not filename: raise DoesNotExistError('No filename specified') folio_exports = [ dl for dl in folio.downloads if dl.filename == filename ] if not folio_exports: raise DoesNotExistError('Download \'%s\' is not available' % filename) folio_export = folio_exports[0] # The physical file should always exist when the data+filename exists # This also checks that the file path lies inside IMAGES_BASE_DIR zip_path = get_portfolio_export_file_path(folio_export) ensure_path_exists(zip_path, require_file=True) # Prepare to serve the file response = send_file( get_abs_path(zip_path), mimetype='application/zip', as_attachment=True, conditional=True, cache_timeout=31536000 # zips never change once created ) # Lastly write an audit record data_engine.add_portfolio_history(folio, user, FolioHistory.ACTION_DOWNLOADED, folio_export.filename) return response except httpexc.HTTPException: # Pass through HTTP 4xx and 5xx raise except SecurityError as e: if app.config['DEBUG']: raise log_security_error(e, request) raise httpexc.Forbidden() except DoesNotExistError as e: logger.warning('404 Not found: ' + str(e)) raise httpexc.NotFound(safe_error_str(e)) except Exception as e: if app.config['DEBUG']: raise logger.error('500 Error for ' + request.url + '\n' + str(e)) raise httpexc.InternalServerError(safe_error_str(e))
def patch_node(node_id): # Parse the request node_id = str2id(node_id) patch = request.get_json() # Find the node type. node = mongo.find_one_or_404('nodes', node_id, projection={'node_type': 1}) try: node_type = node['node_type'] except KeyError: msg = 'Node %s has no node_type property' % node_id log.warning(msg) raise wz_exceptions.InternalServerError(msg) log.debug('User %s wants to PATCH %s node %s', authentication.current_user_id(), node_type, node_id) # Find the PATCH handler for the node type. try: patch_handler = custom.patch_handlers[node_type] except KeyError: log.info('No patch handler for node type %r', node_type) raise wz_exceptions.MethodNotAllowed( 'PATCH on node type %r not allowed' % node_type) # Let the PATCH handler do its thing. return patch_handler(node_id, patch)
def post(self, entity_id): # TODO # - read paramterrs # - start a session # - get a lock of the resource # - actuation # - verify the actuation # - post the updated value to the timeseries database # - close the session - abort the session if anything goes wrong. args = reqparser.parse_args() actuation_value = args.value scheduled_time = args.get('scheduled_time', None) if scheduled_time: # TODO: Implement this raise exceptions.NotImplemented( 'Currently only immediate actuation is implemented.') with self.lock_manager.advisory_lock(entity_id) as lock_acquired: assert lock_acquired, exceptions.BadRequest( 'Lock for {0} cannot be acquired'.format(entity_id)) self.actuation(entity_id, actuation_value) actuated_time = arrow.get() data = [[entity_id, actuated_time.timestamp, actuation_value]] self.ts_db.add_data(data) return None raise exceptions.InternalServerError('This should not be reached.')
def render_region (self, request, image): """ Handle request for an image region """ width = int(request.args['w']) height = int(request.args['h']) x = int(request.args['x']) y = int(request.args['y']) zoom = int(request.args.get('zoom', "0")) # safety limit if width * height > MAX_PIXELS: raise exceptions.BadRequest("Image size: %d * %d > %d" % (width, height, MAX_PIXELS)) if zoom > MAX_ZOOM: raise exceptions.BadRequest("Image zoom: %d > %d" % (zoom, MAX_ZOOM)) x = scale_center(x, width, zoom) y = scale_center(y, height, zoom) try: return image.tile_mem(width, height, x, y, zoom) except pypngtile.Error as error: raise exceptions.InternalServerError(str(error))
def post_node_comment(parent_id: bson.ObjectId, markdown_msg: str, attachments: dict): parent_node = find_node_or_raise( parent_id, 'User %s tried to update comment with bad parent_id %s', current_user.objectid, parent_id) is_reply = parent_node['node_type'] == 'comment' comment = dict( parent=parent_id, project=parent_node['project'], name='Comment', user=current_user.objectid, node_type='comment', properties=dict( content=markdown_msg, status='published', is_reply=is_reply, confidence=0, rating_positive=0, rating_negative=0, attachments=attachments, ), permissions=dict( users=[dict(user=current_user.objectid, methods=['PUT'])])) r, _, _, status = current_app.post_internal('nodes', comment) if status != 201: log.warning('Unable to post comment on %s as %s: %s', parent_id, current_user.objectid, r) raise wz_exceptions.InternalServerError('Unable to create comment') comment_do = get_comment(parent_id, r['_id']) return jsonify_data_object(comment_do), 201
def get_image_id(request): # Get our desired filename. uploading_filename = request.form.get("imageFileName") if not uploading_filename: return exceptions.BadRequest() # Ensure we have an image. if "jpegData" not in request.files: return exceptions.BadRequest() # An image ID has a maximum size of 7. unique_id = generate_unique_id(Images, Images.image_id, 7) if unique_id == "": return exceptions.InternalServerError() filename = f"{unique_id}.jpg" # Next, save our file to disk. jpeg_image = request.files["jpegData"] jpeg_image.save(determine_path(current_order.order_id, filename)) # Finally, save state to the database. added_image = Images(image_id=unique_id, order_id=current_order.order_id, filename=filename) db.session.add(added_image) db.session.commit() return { "imageID": unique_id, }
def _handle_disposition(self, disp: disposition.Disposition): if isinstance(disp, disposition.Redirect): # A simple redirection return flask.redirect(disp.url) if isinstance(disp, disposition.Verified): # The user is verified; log them in self._session.pop(self._prefill_key, None) LOGGER.info("Successful login: %s", disp.identity) if self._session_auth_name is not None: flask.session.permanent = self.make_permanent flask.session[self._session_auth_name] = disp.identity if self._on_verified: response = self._on_verified(disp) if response: return response return flask.redirect(disp.redir) if isinstance(disp, disposition.Notify): # The user needs to take some additional action return self._render_notify(disp.cdata) if isinstance(disp, disposition.Error): # The user's login failed return self.render_login_form(destination=disp.redir, error=disp.message) # unhandled disposition raise http_error.InternalServerError("Unknown disposition type " + str(type(disp)))
def api_create_task(self, job, commands, name, parents=None, priority=50, status='queued', *, task_type: str) -> bson.ObjectId: """Creates a task in MongoDB for the given job, executing commands. Returns the ObjectId of the created task. """ task = { 'job': job['_id'], 'manager': job['manager'], 'user': job['user'], 'name': name, 'status': status, 'job_type': job['job_type'], 'task_type': task_type, 'commands': [cmd.to_dict() for cmd in commands], 'job_priority': job['priority'], 'priority': priority, 'project': job['project'], } # Insertion of None parents is not supported if parents: task['parents'] = parents self._log.info('Creating task %s for manager %s, user %s', name, job['manager'], job['user']) r, _, _, status = current_app.post_internal('flamenco_tasks', task) if status != 201: self._log.error('Error %i creating task %s: %s', status, task, r) raise wz_exceptions.InternalServerError('Unable to create task') return r['_id']
def startup(manager_id, notification): from flamenco import current_flamenco import uuid import datetime log.info('Received startup notification from manager %s %s', manager_id, notification) mngr_coll = current_flamenco.db('managers') update_res = mngr_coll.update_one({'_id': manager_id}, { '$set': { '_updated': datetime.datetime.utcnow(), '_etag': uuid.uuid4().hex, 'url': notification['manager_url'], 'variables': notification['variables'], 'path_replacement': notification['path_replacement'], 'stats.nr_of_workers': notification['nr_of_workers'], } }) if update_res.matched_count != 1: log.warning('Updating manager %s matched %i documents.', manager_id, update_res.matched_count) raise wz_exceptions.InternalServerError( 'Unable to update manager in database.') return '', 204
def _set_latest_revisions(objects): """Set latest revision_id for given child_type. Args: objects: list of snapshot objects with child_id and child_type set. """ pairs = [(o.child_type, o.child_id) for o in objects] query = db.session.query( func.max(revision.Revision.id, name="id", identifier="id"), revision.Revision.resource_type, revision.Revision.resource_id, ).filter( tuple_( revision.Revision.resource_type, revision.Revision.resource_id, ).in_(pairs) ).group_by( revision.Revision.resource_type, revision.Revision.resource_id, ) id_map = {(r_type, r_id): id_ for id_, r_type, r_id in query} for o in objects: o.revision_id = id_map.get((o.child_type, o.child_id)) if o.revision_id is None: raise exceptions.InternalServerError(errors.MISSING_REVISION)
def error_to_json(error): """Converts all errors into proper JSONable exceptions. This is required because by contract Decapod API is JSON API and not JSON data will break their APIs. This catch-em-all error handler is required to fullfil a contract on JSON API. """ if isinstance(error, exceptions.DecapodJSONMixin): return error.get_response() if isinstance(error, werkzeug.exceptions.HTTPException): json_error = exceptions.DecapodJSONMixin() json_error.code = error.code json_error.description = error.description json_error.error_name = str(error) else: LOG.exception("Unmanaged error: %s", error) json_error = exceptions.InternalServerError() exc_info = sys.exc_info() for plugin in plugins.get_alert_plugins(): try: plugin(flask.g.request_id, error, exc_info) except Exception as exc: LOG.error("Cannot execute plugin: %s", exc) return json_error.get_response()
def post(self): parser = reqparse.RequestParser() parser.add_argument(User.username.key, type=str, required=True, help='You have to include the username!') parser.add_argument(User.password.key, type=str, required=True, help='You have to include the password!') args = parser.parse_args() username = args[User.username.key] password = args[User.password.key] try: new_user = self.user_service.add_user(username, password) except SQLAlchemyError as error: db.session.rollback() if User.query.filter_by(username=username).first() is not None: raise exc.BadRequest( 'Username {} already existent.'.format(username)) error = str(error.orig) + " for parameters" + str(error.params) print("An error occurred with the DB.", error) raise exc.InternalServerError(str(error)) return new_user, status.HTTP_201_CREATED
def abort_with_error(status): """Aborts with the given status, or 500 if the status doesn't indicate an error. If the status is < 400, status 500 is used instead. """ abort(status if status // 100 >= 4 else 500) raise wz_exceptions.InternalServerError('abort() should have aborted!')
def testErrorHandlerCanProcessInternalServerError(self): """Test error handler can process HTTP error.""" error_500 = exceptions.InternalServerError() resp = error_handler.handle_error(error_500) resp_obj = json.loads(resp.data[len(ufo.XSSI_PREFIX):]) self.assertEqual(error_500.code, resp_obj['code']) self.assertEqual(error_500.description, resp_obj['message'])
def serve_microservice(self, name): if not self.endpoints: raise exceptions.PreconditionFailed('Not deployed yed!') try: return self.endpoints[name]['func']() except Exception as e: logging.exception('EXC!', exc_info=e) return exceptions.InternalServerError('\n'.join(e.args))
def create_file_doc_for_upload(project_id, uploaded_file): """Creates a secure filename and a document in MongoDB for the file. The (project_id, filename) tuple should be unique. If such a document already exists, it is updated with the new file. :param uploaded_file: file from request.files['form-key'] :type uploaded_file: werkzeug.datastructures.FileStorage :returns: a tuple (file_id, filename, status), where 'filename' is the internal filename used on GCS. """ project_id = ObjectId(project_id) # Hash the filename with path info to get the internal name. This should # be unique for the project. # internal_filename = uploaded_file.filename _, ext = os.path.splitext(uploaded_file.filename) internal_filename = uuid.uuid4().hex + ext # For now, we don't support overwriting files, and create a new one every time. # # See if we can find a pre-existing file doc. # files = current_app.data.driver.db['files'] # file_doc = files.find_one({'project': project_id, # 'name': internal_filename}) file_doc = None # TODO: at some point do name-based and content-based content-type sniffing. new_props = { 'filename': uploaded_file.filename, 'content_type': uploaded_file.mimetype, 'length': uploaded_file.content_length, 'project': project_id, 'status': 'uploading' } if file_doc is None: # Create a file document on MongoDB for this file. file_doc = create_file_doc(name=internal_filename, **new_props) file_fields, _, _, status = current_app.post_internal( 'files', file_doc) else: file_doc.update(new_props) file_fields, _, _, status = current_app.put_internal( 'files', remove_private_keys(file_doc)) if status not in (200, 201): log.error( 'Unable to create new file document in MongoDB, status=%i: %s', status, file_fields) raise wz_exceptions.InternalServerError() log.debug( 'Created file document %s for uploaded file %s; internal name %s', file_fields['_id'], uploaded_file.filename, internal_filename) return file_fields['_id'], internal_filename, status
def error_handler(error): if not isinstance(error, exceptions.HTTPException): error = exceptions.InternalServerError() return response.Response(bootstrap.card(body=_.span[ _.p(style='color:#888')[error.description or ''], _.img(src=flask.url_for('mara_app.static', filename='mara.jpg' ), style='margin-top:30px;max-width:100%;')]), title=f'{error.code} {error.name}', status=error.code)
def ErrorHandlerCanProcessCustomError(self): """Test error handler can process custom error.""" setup_needed_error = SetupNeeded() werkzeug_error = exceptions.InternalServerError(SetupNeeded.message) resp = error_handler.handle_error(setup_needed_error) self.assertEqual(werkzeug_error.code, resp[1]) self.assertTrue(str(werkzeug_error.code) in resp[0].data) self.assertTrue(werkzeug_error.message in resp[0].data)
def delete(user_id: str) -> typing.Tuple[typing.Any, int]: LOG.info('Received request to delete user') single_user = _get_user(user_id) try: database.db.session.delete(single_user) database.db.session.commit() except Exception: LOG.exception('Failed to delete user') exceptions.InternalServerError(description='Failed to delete user') return '', 204
def generate_and_store_short_code(node): nodes_coll = current_app.data.driver.db['nodes'] node_id = node['_id'] log.debug('Creating new short link for node %s', node_id) max_attempts = 10 for attempt in range(1, max_attempts): # Generate a new short code short_code = create_short_code(node) log.debug('Created short code for node %s: %s', node_id, short_code) node['short_code'] = short_code # Store it in MongoDB try: result = nodes_coll.update_one( {'_id': node_id}, {'$set': { 'short_code': short_code }}) break except pymongo.errors.DuplicateKeyError: log.info( 'Duplicate key while creating short code, retrying (attempt %i/%i)', attempt, max_attempts) pass else: log.error( 'Unable to find unique short code for node %s after %i attempts, failing!', node_id, max_attempts) raise wz_exceptions.InternalServerError( 'Unable to create unique short code for node %s' % node_id) # We were able to store a short code, now let's verify the result. if result.matched_count != 1: log.warning('Unable to update node %s with new short_links=%r', node_id, node['short_code']) raise wz_exceptions.InternalServerError( 'Unable to update node %s with new short links' % node_id) return short_code
def __init__(self, limit): self.limit = limit # Set defaults self.code = 429 self.body = self.get_body() self.headers = self.get_headers() # Get the description if limit.error_message: self.description = limit.error_message if not callable( limit.error_message) else limit.error_message() else: self.description = text_type(limit.limit) # If error is given, get body & headers if self.limit.error_code: self.code = limit.error_code exception = exceptions.HTTPException(description=self.description) # Some common error codes, can add more here if self.code == 400: exception = exceptions.BadRequest() elif self.code == 401: exception = exceptions.Unauthorized() elif self.code == 403: exception = exceptions.Forbidden() elif self.code == 404: exception = exceptions.NotFound() elif self.code == 405: exception = exceptions.MethodNotAllowed() elif self.code == 406: exception = exceptions.NotAcceptable() elif self.code == 418: exception = exceptions.ImATeapot() # <3 elif self.code == 500: exception = exceptions.InternalServerError() elif self.code == 501: exception = exceptions.NotImplemented() # Update body & headers self.body = exception.get_body() self.headers = exception.get_headers() else: exception = exceptions.TooManyRequests( description=self.description) # Update body & headers self.body = exception.get_body() self.headers = exception.get_headers() super(RateLimitExceeded, self).__init__(description=self.description, response=Response(self.body, self.code, self.headers))
def testUnknowExceptionTypesAreHandled(self): """Test that unknown exception types are handled (e.g. custom error). setup_config() is not called, thus SetupNeeded error should be thrown. """ setup_needed_error = exceptions.InternalServerError( SetupNeeded.message) resp = self.client.get(flask.url_for('proxyserver_list')) self.assertTrue(str(setup_needed_error.code) in resp.data) self.assertTrue(SetupNeeded.message in resp.data)
def start(self): """Mark the current task as running.""" if self.status == self.PENDING_STATUS: self.status = self.RUNNING_STATUS db.session.add(self) db.session.commit() else: self.status = self.FAILURE_STATUS db.session.add(self) db.session.commit() raise exceptions.InternalServerError( app_errors.PREVIOUS_RUN_FAILED)
def handle_wrapper(*args, **kwargs): """Wrapper for handle exceptions during exporting""" try: return handle_function(*args, **kwargs) except query_exceptions.BadQueryException as exception: raise wzg_exceptions.BadRequest(exception.message) except wzg_exceptions.Unauthorized as ex: raise wzg_exceptions.Unauthorized("%s %s" % (ex.message, app_errors.RELOAD_PAGE)) except errors.HttpError as e: message = json.loads(e.content).get("error").get("message") if e.resp.code == 401: raise wzg_exceptions.Unauthorized("%s %s" % (message, app_errors.RELOAD_PAGE)) raise wzg_exceptions.InternalServerError(message) except Exception as e: # pylint: disable=broad-except logger.exception(e.message) if settings.TESTING: raise raise wzg_exceptions.InternalServerError( app_errors.INTERNAL_SERVER_ERROR.format(job_type="Export"))
def generate_token(manager_id: str): manager_oid = str2id(manager_id) manager = mongo.find_one_or_404('flamenco_managers', manager_oid) # There are three ways in which a user can get here. One is authenticated via # Authorization header (either Bearer token or Basic token:subtoken), and the # other is via an already-existing browser session. # In the latter case it's a redirect from a Flamenco Manager and we need to # check the timeout and HMAC. if not request.headers.get('Authorization'): hasher = current_flamenco.manager_manager.hasher(manager_oid) if hasher is None: raise wz_exceptions.InternalServerError( 'Flamenco Manager not linked to this server') expires = request.args.get('expires', '') string_to_hash = f'{expires}-{manager_id}' hasher.update(string_to_hash.encode('utf8')) actual_hmac = hasher.hexdigest() query_hmac = request.args.get('hmac', '') if not hmac.compare_digest(query_hmac, actual_hmac): raise wz_exceptions.Unauthorized('Bad HMAC') # Only parse the timestamp after we learned we can trust it. expire_timestamp = dateutil.parser.parse(expires) validity_seconds_left = (expire_timestamp - utcnow()).total_seconds() if validity_seconds_left < 0: raise wz_exceptions.Unauthorized('Link expired') if validity_seconds_left > 900: # Flamenco Manager generates links that are valid for less than a minute, so # if it's more than 15 minutes in the future, it's bad. raise wz_exceptions.Unauthorized('Link too far in the future') user = authentication.current_user() if not current_flamenco.manager_manager.user_may_use(mngr_doc=manager): log.warning( 'Account %s called %s for manager %s without access to that manager', user.user_id, request.url, manager_oid) raise wz_exceptions.Unauthorized() jwt = current_flamenco.jwt if not jwt.usable: raise wz_exceptions.NotImplemented( 'JWT keystore is not usable at the moment') log.info('Generating JWT key for user_id=%s manager_id=%s remote_addr=%s', user.user_id, manager_id, request.remote_addr) key_for_manager = jwt.generate_key_for_manager(manager_oid, user.user_id) return Response(key_for_manager, content_type='text/plain')