Restructure into backend/ and frontend/ subprojects

- backend/ uses proper Python src layout (src/media_library_viewer_api/)
  with pyproject.toml, hatchling build, and PYTHONPATH=src convention
- frontend/ is a Vite + React + TypeScript SPA
- archive/ preserves the original Streamlit prototype for reference
- Cleaned up root to only contain docs, license, and subproject dirs
- Updated README for the new dual-subproject architecture
This commit is contained in:
2026-04-30 21:48:46 +02:00
parent 3c432473e5
commit 51b10438a9
47 changed files with 127 additions and 130 deletions
@@ -0,0 +1,63 @@
"""Backend configuration using pydantic-settings.
Reads from environment variables and .env file automatically.
"""
from __future__ import annotations
from pathlib import Path
from pydantic_settings import BaseSettings
class JellyfinSettings(BaseSettings):
url: str = ""
api_key: str = ""
user_id: str = ""
model_config = {"env_prefix": "JELLYFIN_"}
class SSHSettings(BaseSettings):
host: str = ""
username: str = ""
port: int = 22
key_filename: str = str(Path.home() / ".ssh" / "id_rsa")
password: str = ""
media_root: str = ""
path_prefix: str = ""
model_config = {"env_prefix": "SSH_"}
class RemoteSettings(BaseSettings):
"""Extra remote settings that don't fit the SSH_ prefix."""
media_root: str = ""
path_prefix: str = ""
model_config = {"env_prefix": "REMOTE_"}
class Settings(BaseSettings):
"""Top-level application settings."""
jellyfin: JellyfinSettings = JellyfinSettings()
ssh: SSHSettings = SSHSettings()
remote: RemoteSettings = RemoteSettings()
# Derived convenience properties
@property
def media_root(self) -> str:
return self.remote.media_root or self.ssh.media_root or ""
@property
def path_prefix(self) -> str:
return self.remote.path_prefix or self.ssh.path_prefix or ""
model_config = {"env_file": ".env", "env_file_encoding": "utf-8", "extra": "ignore"}
def get_settings() -> Settings:
"""Create a Settings instance (reads env/.env on each call)."""
return Settings()