from datetime import datetime from typing import Literal from pydantic import BaseModel, EmailStr, Field class AdminUserOut(BaseModel): id: str email: EmailStr display_name: str | None is_admin: bool is_active: bool verified: bool # Nie angemeldet, oder seit wann nicht mehr last_seen_at: datetime | None deactivated_at: datetime | None created_at: datetime # Wie viele Listen gehoeren dem Konto, in wie vielen ist es Mitglied owned_lists: int memberships: int # Laeuft gerade eine Adressaenderung? pending_email: str | None = None class AdminStatsOut(BaseModel): total: int active: int inactive: int unverified: int admins: int # Konten, die beim naechsten Durchlauf deaktiviert bzw. geloescht # wuerden - damit die Automatik nicht ueberrascht. due_deactivation: int due_deletion: int class UserCreateIn(BaseModel): email: EmailStr display_name: str | None = Field(default=None, max_length=80) is_admin: bool = False class EmailChangeIn(BaseModel): new_email: EmailStr class DeleteUserIn(BaseModel): """Wie mit den Listen des Kontos verfahren werden soll. "refuse" bricht ab, wenn dem Konto Listen gehoeren - die Voreinstellung, damit nichts unbeabsichtigt verschwindet. "handover" uebertraegt geteilte Listen an das diensthaelteste andere Mitglied und loescht nur die, die niemand sonst nutzt. """ lists: Literal["refuse", "handover"] = "refuse" # Sicherheitsabfrage: die Adresse muss zum Konto passen confirm_email: EmailStr class AdminSettingsOut(BaseModel): allow_self_registration: bool locked_by_env: bool # 0 = abgeschaltet auto_deactivate_months: int auto_delete_months: int # Listen: archivieren nach Nichtbenutzung, loeschen nach Archivdauer auto_archive_months: int archive_delete_months: int class AdminSettingsIn(BaseModel): allow_self_registration: bool | None = None auto_deactivate_months: int | None = Field(default=None, ge=0, le=600) auto_delete_months: int | None = Field(default=None, ge=0, le=600) auto_archive_months: int | None = Field(default=None, ge=0, le=600) archive_delete_months: int | None = Field(default=None, ge=0, le=600) class WelcomeCompleteIn(BaseModel): token: str = Field(max_length=128) password: str = Field(min_length=12, max_length=256) display_name: str | None = Field(default=None, max_length=80) class WelcomePreviewOut(BaseModel): email: EmailStr display_name: str | None