fix: MEDIUM+LOW Claude-Audit-Findings (Issues #7-16)

MEDIUM:
- #7 API-Key XOR-obfuskiert in app_config.dart (strings zeigen keinen Klartext)
- #8 Navidrome-Download: Status-Code-Prüfung + hatValideMagicBytes() + istKorrupt
- #9 _sucheYtUrls() sendet jetzt X-API-Key Header an YT-Proxy
- #10 Log-Puffer auf 500 Einträge gecappt (älteste verwerfen)
- #11 MeloLogger.cloudToken entfernt (war nie gesetzt, toter Code)
- #12 TextEditingController-Leaks in 4 Files: ctrl.dispose() nach showDialog
- #13 Cloud-Sync: Last-Write-Wins Konfliktauflösung dokumentiert

LOW:
- #14 API-Versionierung: alle /api/cloud/ → /api/v1/cloud/
- #15 Auto-Scan: nur /Music, /Download, nicht ganz /storage
- #16 2 pre-existing flutter analyze Infos behoben (curly_braces, use_build_context_synchronously)

flutter analyze: No issues found.
This commit is contained in:
Dustin
2026-08-03 01:50:07 +02:00
parent e46ffa76a3
commit 0b8d8ce2f8
11 changed files with 111 additions and 47 deletions
+18 -3
View File
@@ -9,6 +9,7 @@ import 'package:flutter_secure_storage/flutter_secure_storage.dart';
import '../models/song.dart';
import '../database/db_helper.dart';
import '../utils/sanitize.dart';
import '../utils/audio_validator.dart';
/// Ein Song aus der Subsonic-API
class SubsonicSong {
@@ -192,16 +193,29 @@ class NavidromeService {
if (localSong != null) return localSong;
}
// Stream + speichern
// Stream + speichern mit Status-Code- und Integritäts-Prüfung
final uri = streamUrl(s.id);
final response = await http.Client().send(http.Request('GET', uri));
final streamedResponse = await http.Client().send(http.Request('GET', uri));
// Status-Code prüfen
if (streamedResponse.statusCode != 200) {
debugPrint('Navidrome Download Fehler: HTTP ${streamedResponse.statusCode}');
return null;
}
final sink = file.openWrite();
await for (final chunk in response.stream) {
await for (final chunk in streamedResponse.stream) {
sink.add(chunk);
}
await sink.flush();
await sink.close();
// Magic-Byte-Prüfung nach Download
bool istKorrupt = !hatValideMagicBytes(file);
if (istKorrupt) {
debugPrint('Navidrome Download: Korrupte Datei $dateiPfad');
}
final song = Song(
titel: s.titel,
kuenstler: s.kuenstler,
@@ -210,6 +224,7 @@ class NavidromeService {
dateiPfad: dateiPfad,
groesseBytes: await file.length(),
istHeruntergeladen: true,
istKorrupt: istKorrupt,
downloadQuelle: 'server',
);