# Streaming-Implementationsliste (Option 2) – Storage Modul

Ziel: Dedizierte Streaming-Methoden in der Object Storage API implementieren – ohne externe Dependencies. Fokus auf speichereffiziente Downloads/Uploads großer Dateien via Streams (memory-safe).

## 1) Interface-Erweiterung (ObjectStorage)
- Ergänze folgende Methoden im ObjectStorage-Interface:
  - get(string $bucket, string $key): string
  - put(string $bucket, string $key, string|mixed $body, array $opts = []): ObjectInfo
  - getToStream(string $bucket, string $key, mixed $destination): int
    - Erwartet eine schreibbare PHP-Stream-Resource als $destination
    - Rückgabewert: Anzahl geschriebener Bytes
  - putFromStream(string $bucket, string $key, mixed $source, array $opts = []): ObjectInfo
    - Erwartet eine lesbare PHP-Stream-Resource als $source
  - openReadStream(string $bucket, string $key)
    - Gibt eine lesbare PHP-Stream-Resource zurück
  - head(string $bucket, string $key): ObjectInfo
  - delete(string $bucket, string $key): void
  - exists(string $bucket, string $key): bool
  - url(string $bucket, string $key): ?string
  - temporaryUrl(string $bucket, string $key, \DateInterval $ttl, array $opts = []): string

Hinweise:
- Signaturen mit mixed für Stream-Parameter (PHP-Resource), genaue Validierung in den Implementierungen.
- Bestehende Methoden get/put bleiben kompatibel; Streaming ist ergänzend.

## 2) Filesystem-Adapter (lokales Backend)
Ziel: ObjectStorage-Implementierung auf Basis des bestehenden Filesystem-Backends.

- Neue Klasse: src/Framework/Storage/FilesystemObjectStorage.php
- Verantwortlichkeiten:
  - Pfadaufbau: basePath/bucket/key
  - get/put über Filesystem (kleine Dateien)
  - Streaming:
    - getToStream: Datei lesen und via stream_copy_to_stream in $destination schreiben
    - putFromStream: Stream-Inhalt in Datei schreiben (Chunked Copy)
    - openReadStream: lesbaren Stream auf die Datei öffnen
  - head/exists/delete/url/temporaryUrl:
    - head: Dateigröße, mtime, mimetype (falls verfügbar)
    - url: für lokales Storage in der Regel null (oder optionaler lokaler URL-Generator)
    - temporaryUrl: nicht unterstützt -> Exception oder leer lassen mit Doku
- Fehlerbehandlung:
  - File not found, Permission, Read/Write-Errors sauber abbilden
- Performance:
  - Buffersize bei stream_copy_to_stream kontrollierbar machen (Optionen)

## 3) MinIO-Backend (ohne Dependencies)
Ziel: S3-kompatibler MinIO-Client mittels nativer PHP-Funktionen (HTTP-Streams und AWS SigV4) + ObjectStorage-Adapter.

- Dateien:
  - src/Framework/Storage/Clients/MinioClient.php
    - Funktionen: putObject, getObject, headObject, deleteObject, createPresignedUrl
    - Streaming-Funktionen:
      - getObjectToStream($bucket, $key, $destination): int
      - putObjectFromStream($bucket, $key, $source, array $opts = []): array
      - openStream($bucket, $key) -> resource
    - Interne Helfer:
      - AWS SigV4 Signierung (kanonische Anfrage, Header, Query, Hashes)
      - Response-Parsing (Headers, Status, Fehler-XML)
      - Chunked Transfer wenn keine Content-Length verfügbar
  - src/Framework/Storage/MinioObjectStorage.php
    - Implementiert ObjectStorage
    - get/put: kleinere Dateien
    - getToStream/putFromStream/openReadStream: nutzen die Streaming-APIs des MinioClient
    - head/delete/exists/url/temporaryUrl: 
      - temporaryUrl via createPresignedUrl
- Sicherheit:
  - TTL-Limits für temporaryUrl (z. B. max 24h)
  - Path-Style vs. Virtual Host Style konfigurierbar
  - Keine externen Pakete

## 4) Manager/Factory/DI
- Option A: StorageManager für ObjectStorage-Driver (local/minio)
  - src/Framework/Storage/StorageManager.php
    - driver(string $name): ObjectStorage
    - bucket(string $name): Bucket (Convenience)
- Option B (einfach): Container-Bindings direkt
  - Default ObjectStorage anhand ENV
- Initializer:
  - src/Framework/Storage/StorageInitializer.php
    - Konfig aus ENV (DEFAULT_DRIVER, MINIO_ENDPOINT, KEYS, LOCAL_ROOT, PATH_STYLE etc.)
    - Registriere:
      - FilesystemObjectStorage (als "local")
      - MinioClient + MinioObjectStorage (als "minio")
      - ObjectStorage (Default: ENV)
- Bucket-API (optional aber DX-freundlich):
  - src/Framework/Storage/Bucket.php
    - wrappt ObjectStorage für festen Bucket-Namen

## 5) Konfiguration
- ENV Variablen vorschlagen (Beispiele):
  - STORAGE_DRIVER=local|minio
  - STORAGE_LOCAL_ROOT=/var/www/html/storage/objects
  - MINIO_ENDPOINT=http://minio:9000
  - MINIO_ACCESS_KEY=...
  - MINIO_SECRET_KEY=...
  - MINIO_REGION=us-east-1
  - MINIO_USE_PATH_STYLE=true
- StorageConfig Klasse (optional) für strukturierte Konfig-Verwaltung

## 6) Tests (kritisch, da streaming-sensitiv)
- Unit-Tests FilesystemObjectStorage:
  - put/get mit Strings
  - putFromStream/getToStream mit temp Streams (php://temp)
  - openReadStream und sequentielles Lesen
  - head/exists/delete
- Unit-Tests MinioClient (Signierung) – isoliert:
  - Signatur-Konsistenz (Golden Master)
  - Parsing von Fehlern/Headers
- Integration-Tests (optional, per docker-compose mit MinIO):
  - Upload/Download großer Dateien (z. B. >100MB) per Streams
  - temporaryUrl Zugriff (GET) mit TTL
- Edge Cases:
  - fehlende Read-/Write-Berechtigungen (Filesystem)
  - Netzwerkfehler (MinIO)
  - Nicht existierende Objekte
  - Streams ohne bekannte Länge (Chunked Transfer)

## 7) Fehler- und Ausnahmebehandlung
- Konsistente Exceptions im Storage-Namespace (z. B. StorageException)
- Filesystem-spezifische Fehler sauber mappen
- Aussagekräftige Meldungen (inkl. Pfad/Bucket/Key)

## 8) Performance/Robustheit
- Stream-Buffer konfigurierbar (z. B. 8192 Bytes Default)
- Keine vollständigen Dateiladungen in Memory bei Streams
- Zeitouts/Retry-Strategie (MinIO) minimal vorsehen (optional)
- Sauberes Schließen aller Streams (try/finally)

## 9) Sicherheit
- Path-Sanitizing im Filesystem-Adapter (keine Directory-Traversal)
- Eindeutige Handhabung von public URL vs. presigned URL
- Limitierung der Presign-Dauer und Validierung von Eingaben

## 10) Dokumentation
- README/HowTo:
  - Beispiel für lokale und MinIO-Nutzung
  - Beispiele für Streaming (Upload/Download)
  - Hinweise zu großen Dateien, Memory-Effizienz
- PHPDoc ausführlich an allen Public-APIs

## 11) Milestones (Reihenfolge)
1. Interface-Änderungen (ObjectStorage)
2. FilesystemObjectStorage (inkl. Streaming)
3. MinioClient (Basis + Signierung)
4. MinioObjectStorage (inkl. Streaming)
5. Initializer/DI und Konfig
6. Tests (Unit), danach optional Integration
7. Doku + Beispiele

## 12) Definition of Done
- Alle neuen Methoden implementiert und getestet
- Große Dateien via Streams funktionieren, ohne OOM
- Kein externer Dependency-Einsatz
- Doku und Beispiele vorhanden
- CI-Tests grün (Unit; Integration optional)
