import itertools import random import re from io import BytesIO from typing import Any, Self, Sequence, TypeVar from fastapi.responses import StreamingResponse from PIL import Image from .config import get_config from .webdav import WebDAV T = TypeVar("T") class Random(random.Random): @classmethod async def get(cls, bonus_salt: Any = "") -> Self: cfg = await get_config() return cls(f"{cfg.puzzle.solution}{cfg.puzzle.random_seed}{bonus_salt}") def shuffled(self, population: Sequence[T]) -> Sequence[T]: return self.sample(population, k=len(population)) def set_len(seq: Sequence[T], len: int) -> Sequence[T]: # `seq` unendlich wiederholen infinite = itertools.cycle(seq) # Die ersten `length` einträge nehmen return list(itertools.islice(infinite, len)) async def list_images_auto() -> list[str]: """ Finde alle Bilddateien im "automatisch"-Verzeichnis """ return await WebDAV.list_files( directory="/images_auto", regex=re.compile(r"\.(gif|jpe?g|tiff?|png|bmp)$", flags=re.IGNORECASE), ) async def load_image(file_name: str) -> Image.Image: """ Versuche, Bild aus Datei zu laden """ if not await WebDAV.file_exists(file_name): raise RuntimeError(f"DAV-File {file_name} does not exist!") return Image.open(BytesIO(await WebDAV.read_bytes(file_name))) async def api_return_image(img: Image.Image) -> StreamingResponse: """ Bild mit API zurückgeben """ # JPEG-Daten in Puffer speichern img_buffer = BytesIO() img.save(img_buffer, format="JPEG", quality=85) img_buffer.seek(0) # zurückgeben return StreamingResponse( media_type="image/jpeg", content=img_buffer, )