Improve docs and security defaults

This commit is contained in:
2025-10-22 15:22:58 +02:00
parent ebb0769ed4
commit 92795cf9b3
16 changed files with 283 additions and 180 deletions

View File

@@ -1,3 +1,4 @@
import secrets
from typing import Optional
from pydantic import Field
@@ -7,15 +8,20 @@ from pydantic_settings import BaseSettings
class Settings(BaseSettings):
"""Application settings from environment variables."""
jwt_secret_key: str = Field(
default="your-secret-key-here", env="JWT_SECRET_KEY"
default_factory=lambda: secrets.token_urlsafe(32),
env="JWT_SECRET_KEY",
)
password_salt: str = Field(default="default-salt", env="PASSWORD_SALT")
master_password_hash: Optional[str] = Field(
default=None, env="MASTER_PASSWORD_HASH"
)
# For development
# For development only. Never rely on this in production deployments.
master_password: Optional[str] = Field(
default=None, env="MASTER_PASSWORD"
default=None,
env="MASTER_PASSWORD",
description=(
"Development-only master password; do not enable in production."
),
)
token_expiry_hours: int = Field(
default=24, env="SESSION_TIMEOUT_HOURS"
@@ -27,7 +33,10 @@ class Settings(BaseSettings):
database_url: str = Field(
default="sqlite:///./data/aniworld.db", env="DATABASE_URL"
)
cors_origins: str = Field(default="*", env="CORS_ORIGINS")
cors_origins: str = Field(
default="http://localhost:3000",
env="CORS_ORIGINS",
)
api_rate_limit: int = Field(default=100, env="API_RATE_LIMIT")
default_provider: str = Field(
default="aniworld.to", env="DEFAULT_PROVIDER"
@@ -35,6 +44,25 @@ class Settings(BaseSettings):
provider_timeout: int = Field(default=30, env="PROVIDER_TIMEOUT")
retry_attempts: int = Field(default=3, env="RETRY_ATTEMPTS")
@property
def allowed_origins(self) -> list[str]:
"""Return the list of allowed CORS origins.
The environment variable should contain a comma-separated list.
When ``*`` is provided we fall back to a safe local development
default instead of allowing every origin in production.
"""
raw = (self.cors_origins or "").strip()
if not raw:
return []
if raw == "*":
return [
"http://localhost:3000",
"http://localhost:8000",
]
return [origin.strip() for origin in raw.split(",") if origin.strip()]
class Config:
env_file = ".env"
extra = "ignore"