UX-Simulation, Teil 2: Player-Feinschliff, Downloads, Einstellungen

Zweiter Block aus der UX-Simulation (39 Funde insgesamt):

- Songtext-Icon deaktiviert statt totem Knopf, wenn kein Ziel bekannt ist
- Sleep-Timer-Restzeit jetzt auch im Sheet sichtbar, nicht nur im Tooltip
- Drag-Handle in der Warteschlange, Wisch-nach-unten schließt den
  Vollbild-Player
- Fehlender Tooltip am Songtext-Sheet-Schließen-Knopf ergänzt
- YouTube-Download: Zeitüberschreitung meldet sich anders als toter Server
- Server-Tab zeigte beim Öffnen kurz fälschlich "nicht verbunden"
- Einstellungen: Favoriten-/Playlisten-Sync von "Speicher" zu
  "Musikserver" verschoben, Navidrome-Eintrag erklärt jetzt seinen Zweck
- Kommentar in geteilte_adresse.dart korrigiert (Verhalten unverändert,
  dafür gibt es einen Test)

Bewusst zurückgestellt: ServerFavoriteButton bleibt lokal-only (dokumentierte
Architektur-Entscheidung, siehe G3 im UX-Review), Live-Wischgeste am
Mini-Player, YouTube-Download-Abbrechen, Download-Badge im inaktiven
Unterreiter, Versionsnummer (neue Abhängigkeit nötig).

539 Tests grün (vorher 537), flutter analyze ohne Befund.
This commit is contained in:
Hermes (Server)
2026-08-25 09:49:47 +02:00
parent 07acf77ba4
commit 5645660a2d
8 changed files with 186 additions and 40 deletions
+33
View File
@@ -1,3 +1,4 @@
import 'dart:async';
import 'dart:convert';
import 'dart:io';
@@ -56,6 +57,38 @@ void main() {
expect(aufrufe, 0);
});
test(
'Zeitüberschreitung beim Proxy meldet sich anders als eine tote '
'Verbindung', () async {
final dienst = YtDownloadService(
auth: await _angemeldeteAuth(),
client: MockClient((_) async => throw TimeoutException('zu lange')),
);
final ergebnis = await dienst.herunterladen(
'https://youtu.be/dQw4w9WgXcQ',
zielOrdner: ziel.path);
expect(ergebnis, isNull);
expect(dienst.fehler,
'Der Server braucht zu lange — bitte später erneut versuchen');
});
test('eine tote Verbindung zum Proxy meldet sich anders als ein Timeout',
() async {
final dienst = YtDownloadService(
auth: await _angemeldeteAuth(),
client: MockClient((_) async => throw const SocketException('down')),
);
final ergebnis = await dienst.herunterladen(
'https://youtu.be/dQw4w9WgXcQ',
zielOrdner: ziel.path);
expect(ergebnis, isNull);
expect(dienst.fehler, 'Proxy nicht erreichbar');
});
test('Erfolgreicher Download legt die MP3 im Zielordner ab', () async {
final dienst = YtDownloadService(
auth: await _angemeldeteAuth(),