async def update_user_image( id: str, profile_image: UploadFile = File(...), current_user: UserInDB = Depends(get_current_user), ): """ Updates a User Image """ extension = profile_image.filename.split(".")[-1] app_dirs.USER_DIR.joinpath(id).mkdir(parents=True, exist_ok=True) try: [ x.unlink() for x in app_dirs.USER_DIR.join(id).glob("profile_image.*") ] except: pass dest = app_dirs.USER_DIR.joinpath(id, f"profile_image.{extension}") with dest.open("wb") as buffer: shutil.copyfileobj(profile_image.file, buffer) if dest.is_file: return SnackResponse.success("File uploaded") else: return SnackResponse.error("Failure uploading file")
def upload_backup_file(archive: UploadFile = File(...)): """ Upload a .zip File to later be imported into Mealie """ dest = app_dirs.BACKUP_DIR.joinpath(archive.filename) with dest.open("wb") as buffer: shutil.copyfileobj(archive.file, buffer) if dest.is_file: return SnackResponse.success("Backup uploaded") else: return SnackResponse.error("Failure uploading file")
async def create_group( group_data: GroupBase, current_user=Depends(get_current_user), session: Session = Depends(generate_session), ): """ Creates a Group in the Database """ try: db.groups.create(session, group_data.dict()) return SnackResponse.success("User Group Created", {"created": True}) except: return SnackResponse.error("User Group Creation Failed")
def delete_backup(file_name: str): """ Removes a database backup from the file system """ try: app_dirs.BACKUP_DIR.joinpath(file_name).unlink() except: HTTPException( status_code=400, detail=SnackResponse.error( "Unable to Delete Backup. See Log File"), ) return SnackResponse.error(f"{file_name} Deleted")
async def delete_user( id: int, current_user: UserInDB = Depends(get_current_user), session: Session = Depends(generate_session), ): """ Removes a user from the database. Must be the current user or a super user""" if id == 1: return SnackResponse.error("Error! Cannot Delete Super User") if current_user.id == id or current_user.admin: db.users.delete(session, id) return SnackResponse.error("User Deleted")
def delete_migration_data(type: str, file_name: str): """ Removes migration data from the file system """ remove_path = app_dirs.MIGRATION_DIR.joinpath(type, file_name) if remove_path.is_file(): remove_path.unlink() elif remove_path.is_dir(): shutil.rmtree(remove_path) else: SnackResponse.error("File/Folder not found.") return SnackResponse.error(f"Migration Data Remove: {remove_path.absolute()}")
def upload_nextcloud_zipfile(type: str, archive: UploadFile = File(...)): """ Upload a .zip File to later be imported into Mealie """ dir = app_dirs.MIGRATION_DIR.joinpath(type) dir.mkdir(parents=True, exist_ok=True) dest = dir.joinpath(archive.filename) with dest.open("wb") as buffer: shutil.copyfileobj(archive.file, buffer) if dest.is_file: return SnackResponse.success("Migration data uploaded") else: return SnackResponse.error("Failure uploading file")
def delete_recipe( recipe_slug: str, session: Session = Depends(generate_session), current_user=Depends(get_current_user), ): """ Deletes a recipe by slug """ try: db.recipes.delete(session, recipe_slug) delete_image(recipe_slug) except: raise HTTPException(status_code=404, detail=SnackResponse.error("Unable to Delete Recipe")) return SnackResponse.error(f"Recipe {recipe_slug} Deleted")
def delete_theme(theme_name: str, session: Session = Depends(generate_session), current_user=Depends(get_current_user)): """ Deletes theme from the database """ db.themes.delete(session, theme_name) return SnackResponse.error(f"Theme Deleted: {theme_name}")
def create_theme(data: SiteTheme, session: Session = Depends(generate_session), current_user=Depends(get_current_user)): """ Creates a site color theme database entry """ db.themes.create(session, data.dict()) return SnackResponse.success("Theme Saved")
def get_token( data: OAuth2PasswordRequestForm = Depends(), session: Session = Depends(generate_session), ): email = data.username password = data.password user = authenticate_user(session, email, password) if not user: raise HTTPException( status_code=status.HTTP_401_UNAUTHORIZED, detail="Incorrect username or password", headers={"WWW-Authenticate": "Bearer"}, ) access_token = security.create_access_token(dict(sub=email), timedelta(hours=2)) return SnackResponse.success( "User Successfully Logged In", { "access_token": access_token, "token_type": "bearer" }, )
def create_meal_plan( data: MealPlanIn, session: Session = Depends(generate_session), current_user=Depends(get_current_user) ): """ Creates a meal plan database entry """ processed_plan = process_meals(session, data) db.meals.create(session, processed_plan.dict()) return SnackResponse.success("Mealplan Created")
def update_settings( data: SiteSettings, session: Session = Depends(generate_session), current_user=Depends(get_current_user), ): """ Returns Site Settings """ db.settings.update(session, 1, data.dict()) return SnackResponse.success("Settings Updated")
async def update_password( id: int, password_change: ChangePassword, current_user: UserInDB = Depends(get_current_user), session: Session = Depends(generate_session), ): """ Resets the User Password""" match_passwords = verify_password(password_change.current_password, current_user.password) match_id = current_user.id == id if match_passwords and match_id: new_password = get_password_hash(password_change.new_password) db.users.update_password(session, id, new_password) return SnackResponse.success("Password Updated") else: return SnackResponse.error("Existing password does not match")
def import_nextcloud_directory(type: str, file_name: str, session: Session = Depends(generate_session)): """ Imports all the recipes in a given directory """ file_path = app_dirs.MIGRATION_DIR.joinpath(type, file_name) if type == "nextcloud": return nextcloud_migrate(session, file_path) elif type == "chowdown": return chowdow_migrate(session, file_path) else: return SnackResponse.error("Incorrect Migration Type Selected")
async def update_multiple_pages( pages: list[CustomPageOut], session: Session = Depends(generate_session), current_user: UserInDB = Depends(get_current_user), ): """ Update multiple custom pages """ for page in pages: db.custom_pages.update(session, page.id, page.dict()) return SnackResponse.success("Pages Updated")
async def download_backup_file(file_name: str): """ Upload a .zip File to later be imported into Mealie """ file = app_dirs.BACKUP_DIR.joinpath(file_name) if file.is_file: return FileResponse(file, media_type="application/octet-stream", filename=file_name) else: return SnackResponse.error("No File Found")
async def delete_user_group(id: int, current_user=Depends(get_current_user), session: Session = Depends(generate_session)): """ Removes a user group from the database """ if id == 1: return SnackResponse.error("Cannot delete default group") group: GroupInDB = db.groups.get(session, id) if not group: return SnackResponse.error("Group not found") if not group.users == []: return SnackResponse.error("Cannot delete group with users") db.groups.delete(session, id) return
async def delete_recipe_category(category: str, session: Session = Depends(generate_session), current_user=Depends(get_current_user)): """Removes a recipe category from the database. Deleting a category does not impact a recipe. The category will be removed from any recipes that contain it""" db.categories.delete(session, category) return SnackResponse.error(f"Category Deleted: {category}")
async def create_new_page( new_page: CustomPageBase, session: Session = Depends(generate_session), current_user: UserInDB = Depends(get_current_user), ): """ Creates a new Custom Page """ db.custom_pages.create(session, new_page.dict()) return SnackResponse.success("New Page Created")
async def update_group_data( id: int, group_data: UpdateGroup, current_user=Depends(get_current_user), session: Session = Depends(generate_session), ): """ Updates a User Group """ db.groups.update(session, id, group_data.dict()) return SnackResponse.success("Group Settings Updated")
def scrape_image_url( recipe_slug: str, url: RecipeURLIn, current_user=Depends(get_current_user), ): """ Removes an existing image and replaces it with the incoming file. """ scrape_image(url.url, recipe_slug) return SnackResponse.success("Recipe Image Updated")
async def delete_recipe_tag(tag: str, session: Session = Depends(generate_session), current_user=Depends(get_current_user)): """Removes a recipe tag from the database. Deleting a tag does not impact a recipe. The tag will be removed from any recipes that contain it""" db.tags.delete(session, tag) return SnackResponse.error(f"Tag Deleted: {tag}")
async def reset_user_password( id: int, current_user: UserInDB = Depends(get_current_user), session: Session = Depends(generate_session), ): new_password = get_password_hash(settings.DEFAULT_PASSWORD) db.users.update_password(session, id, new_password) return SnackResponse.success("Users Password Reset")
async def create_user( new_user: UserIn, current_user=Depends(get_current_user), session: Session = Depends(generate_session), ): new_user.password = get_password_hash(new_user.password) data = db.users.create(session, new_user.dict()) return SnackResponse.success(f"User Created: {new_user.full_name}", data)
def update_theme( theme_name: str, data: SiteTheme, session: Session = Depends(generate_session), current_user=Depends(get_current_user), ): """ Update a theme database entry """ db.themes.update(session, theme_name, data.dict()) return SnackResponse.info(f"Theme Updated: {theme_name}")
async def download_file( file_path: Optional[Path] = Depends(validate_file_token)): """ Uses a file token obtained by an active user to retrieve a file from the operating system. """ print("File Name:", file_path) if file_path.is_file(): return FileResponse(file_path, media_type="application/octet-stream", filename=file_path.name) else: return SnackResponse.error("No File Found")
async def delete_token( token: str, current_user: UserInDB = Depends(get_current_user), session: Session = Depends(generate_session), ): """ Removed a token from the database """ if current_user.admin: db.sign_ups.delete(session, token) return SnackResponse.error("Sign Up Token Deleted") else: return {"details", "not authorized"}
def update_meal_plan( plan_id: str, meal_plan: MealPlanIn, session: Session = Depends(generate_session), current_user=Depends(get_current_user), ): """ Updates a meal plan based off ID """ processed_plan = process_meals(session, meal_plan) processed_plan = MealPlanInDB(uid=plan_id, **processed_plan.dict()) db.meals.update(session, plan_id, processed_plan.dict()) return SnackResponse.info("Mealplan Updated")
def export_database(data: BackupJob, session: Session = Depends(generate_session)): """Generates a backup of the recipe database in json format.""" export_path = backup_all( session=session, tag=data.tag, templates=data.templates, export_recipes=data.options.recipes, export_settings=data.options.settings, export_pages=data.options.pages, export_themes=data.options.themes, export_users=data.options.users, export_groups=data.options.groups, ) try: return SnackResponse.success("Backup Created at " + export_path) except: HTTPException( status_code=400, detail=SnackResponse.error("Error Creating Backup. See Log File"), )