async def init_anonymous_folder(commit: bool = True) -> File: """Generate new anonymous files folder for project""" settings = get_settings() id = uuid.uuid4() path = os.path.join(settings.user_data_root, "anonymous") if not os.path.exists(path): os.mkdir(path) async with AsyncRepository() as repo: folder = await repo.get(File, where=[File.path == path]) if not folder: folder = File( # type: ignore id=id, filename="Anonymous Folder", path=path, status=FileStatus.FOLDER, is_folder=True, is_anonymous=True, ) await repo.create(folder) if commit: await repo.commit() folder = await repo.refresh(folder) return folder
def generate_app() -> FastAPI: app = FastAPI() settings = get_settings() app.include_router(files_router, prefix="/f") app.include_router(users_router, prefix="/u") app.add_middleware( CORSMiddleware, allow_origins=settings.backend_cors_origins, allow_credentials=True, allow_methods=["*"], allow_headers=["*"], ) @app.on_event("startup") async def init_db(): await setup_db() @app.on_event("startup") async def create_anonymous_folder(): settings = get_settings() if settings.anonymous_uploads_allowed: await init_anonymous_folder() @app.exception_handler(ValidationError) async def validation_exception_handler(request, exc): """Reraise Pydantic request validation errors as 422""" return await request_validation_exception_handler(request, exc) return app
async def get_current_user(token: Optional[str] = Depends( oauth2_scheme)) -> Optional[User]: """Return current user or None if user is anonymous""" settings = get_settings() credentials_exception = HTTPException( status_code=status.HTTP_401_UNAUTHORIZED, detail="Could not validate credentials", headers={"WWW-Authenticate": "Bearer"}, ) if not token: return None try: payload = jwt.decode(token, settings.secret_key, algorithms=[settings.jwt_algorithm]) username: str = payload.get("sub") if username is None: raise credentials_exception token_data = TokenData(email=username) except JWTError: raise credentials_exception async with AsyncRepository() as repo: user = await repo.get(User, where=[User.email == token_data.email]) if user is None: raise credentials_exception return user
def create_access_token(data: dict, expires_delta: Optional[timedelta] = None): """Generate JWT token based on input data""" to_encode = data.copy() if expires_delta: expire = datetime.utcnow() + expires_delta else: expire = datetime.utcnow() + timedelta(minutes=15) to_encode.update({"exp": expire}) settings = get_settings() encoded_jwt = jwt.encode(to_encode, settings.secret_key, algorithm=settings.jwt_algorithm) return encoded_jwt
async def login(form_data: OAuth2PasswordRequestForm = Depends()): user = await authenticate_user(form_data.username, form_data.password) if not user: raise HTTPException( status_code=status.HTTP_401_UNAUTHORIZED, detail="Incorrect username or password", headers={"WWW-Authenticate": "Bearer"}, ) access_token_expires = timedelta( minutes=get_settings().jwt_token_expire_minutes) access_token = create_access_token(data={"sub": user.email}, expires_delta=access_token_expires) return { "access_token": access_token, "token_type": "bearer", "email": user.email, "user_id": user.id }
async def init_root_folder(owner: User, commit: bool = False) -> File: """ Generate new root folder for new user. If folder_path is supplied, it will be used as path instead """ settings = get_settings() root = settings.user_data_root id = uuid.uuid4() path = os.path.join(root, str(id)) os.mkdir(path) async with AsyncRepository() as repo: file = File( # type: ignore id=id, filename=f"Root {id}", owner_id=owner.id, path=path, status=FileStatus.FOLDER, is_folder=True ) await repo.create(file) if commit: await repo.commit() file = await repo.refresh(file) return file
async def create_anonymous_folder(): settings = get_settings() if settings.anonymous_uploads_allowed: await init_anonymous_folder()