mirror of
https://github.com/mealie-recipes/mealie.git
synced 2026-02-06 16:03:12 -05:00
feat: ✨ add user recipe export functionality (#845)
* feat(frontend): ✨ add user recipe export functionality * remove depreciated folders * change/remove depreciated folders * add testing variable in config * add GUID support for group_id * improve testing feedback on 422 errors * remove/cleanup files/folders * initial user export support * delete unused css * update backup page UI * remove depreciated settings * feat: ✨ export download links * fix #813 * remove top level statements * show footer * add export purger to scheduler * update purge glob * fix meal-planner lockout * feat: ✨ add bulk delete/purge exports * style(frontend): 💄 update UI for site settings * feat: ✨ add version checker * update documentation Co-authored-by: hay-kot <hay-kot@pm.me>
This commit is contained in:
41
mealie/core/release_checker.py
Normal file
41
mealie/core/release_checker.py
Normal file
@@ -0,0 +1,41 @@
|
||||
import datetime
|
||||
from functools import lru_cache
|
||||
|
||||
import requests
|
||||
|
||||
_LAST_RESET = None
|
||||
|
||||
|
||||
@lru_cache(maxsize=1)
|
||||
def get_latest_github_release() -> str:
|
||||
"""
|
||||
Gets the latest release from GitHub.
|
||||
|
||||
Returns:
|
||||
str: The latest release from GitHub.
|
||||
"""
|
||||
|
||||
url = "https://api.github.com/repos/hay-kot/mealie/releases/latest"
|
||||
response = requests.get(url)
|
||||
response.raise_for_status()
|
||||
return response.json()["tag_name"]
|
||||
|
||||
|
||||
def get_latest_version() -> str:
|
||||
"""
|
||||
Gets the latest release version.
|
||||
|
||||
Returns:
|
||||
str: The latest release version.
|
||||
"""
|
||||
MAX_DAYS_OLD = 1 # reset cache after 1 day
|
||||
|
||||
global _LAST_RESET
|
||||
|
||||
now = datetime.datetime.now()
|
||||
|
||||
if not _LAST_RESET or now - _LAST_RESET > datetime.timedelta(days=MAX_DAYS_OLD):
|
||||
_LAST_RESET = now
|
||||
get_latest_github_release.cache_clear()
|
||||
|
||||
return get_latest_github_release()
|
||||
@@ -2,30 +2,33 @@ from pathlib import Path
|
||||
|
||||
|
||||
class AppDirectories:
|
||||
def __init__(self, data_dir) -> None:
|
||||
self.DATA_DIR: Path = data_dir
|
||||
self.IMG_DIR: Path = data_dir.joinpath("img")
|
||||
self.BACKUP_DIR: Path = data_dir.joinpath("backups")
|
||||
self.DEBUG_DIR: Path = data_dir.joinpath("debug")
|
||||
self.MIGRATION_DIR: Path = data_dir.joinpath("migration")
|
||||
self.NEXTCLOUD_DIR: Path = self.MIGRATION_DIR.joinpath("nextcloud")
|
||||
self.CHOWDOWN_DIR: Path = self.MIGRATION_DIR.joinpath("chowdown")
|
||||
self.TEMPLATE_DIR: Path = data_dir.joinpath("templates")
|
||||
self.USER_DIR: Path = data_dir.joinpath("users")
|
||||
self.RECIPE_DATA_DIR: Path = data_dir.joinpath("recipes")
|
||||
self.TEMP_DIR: Path = data_dir.joinpath(".temp")
|
||||
def __init__(self, data_dir: Path) -> None:
|
||||
self.DATA_DIR = data_dir
|
||||
self.BACKUP_DIR = data_dir.joinpath("backups")
|
||||
self.USER_DIR = data_dir.joinpath("users")
|
||||
self.RECIPE_DATA_DIR = data_dir.joinpath("recipes")
|
||||
self.TEMPLATE_DIR = data_dir.joinpath("templates")
|
||||
|
||||
self.GROUPS_DIR = self.DATA_DIR.joinpath("groups")
|
||||
|
||||
# Deprecated
|
||||
self._TEMP_DIR = data_dir.joinpath(".temp")
|
||||
self._IMG_DIR = data_dir.joinpath("img")
|
||||
self.ensure_directories()
|
||||
|
||||
@property
|
||||
def IMG_DIR(self):
|
||||
return self._IMG_DIR
|
||||
|
||||
@property
|
||||
def TEMP_DIR(self):
|
||||
return self._TEMP_DIR
|
||||
|
||||
def ensure_directories(self):
|
||||
required_dirs = [
|
||||
self.IMG_DIR,
|
||||
self.GROUPS_DIR,
|
||||
self.BACKUP_DIR,
|
||||
self.DEBUG_DIR,
|
||||
self.MIGRATION_DIR,
|
||||
self.TEMPLATE_DIR,
|
||||
self.NEXTCLOUD_DIR,
|
||||
self.CHOWDOWN_DIR,
|
||||
self.RECIPE_DATA_DIR,
|
||||
self.USER_DIR,
|
||||
]
|
||||
|
||||
@@ -102,6 +102,11 @@ class AppSettings(BaseSettings):
|
||||
not_none = None not in required
|
||||
return self.LDAP_AUTH_ENABLED and not_none
|
||||
|
||||
# ===============================================
|
||||
# Testing Config
|
||||
|
||||
TESTING: bool = False
|
||||
|
||||
class Config:
|
||||
arbitrary_types_allowed = True
|
||||
|
||||
|
||||
Reference in New Issue
Block a user