Review-Funde: Playlist-Wiederherstellung nach erstem Sync, CHANGELOG korrigiert, Dedup-sicheres songByCloudId

This commit is contained in:
Hermes (Server)
2026-08-27 14:04:28 +02:00
parent b13ed6271d
commit b7c8be6f0f
3 changed files with 17 additions and 10 deletions
+3 -4
View File
@@ -30,10 +30,9 @@ Format angelehnt an [Keep a Changelog](https://keepachangelog.com/de/1.0.0/).
stillschweigend „keine Favoriten". stillschweigend „keine Favoriten".
- ☁️ **Neu: „Auf den Server laden".** Im Auswahl-Modus von „Meine Musik" - ☁️ **Neu: „Auf den Server laden".** Im Auswahl-Modus von „Meine Musik"
(langes Drücken) lassen sich einzelne Titel markieren und gezielt (langes Drücken) lassen sich einzelne Titel markieren und gezielt
hochladen — mit Fortschritt und **Abbrechen**. Titel, die schon oben sind, hochladen. Titel, die schon oben sind, werden übersprungen; einzelne
werden übersprungen; einzelne Fehlschläge stoppen den Rest nicht. Die Fehlschläge stoppen den Rest nicht. Die Aktion erscheint bewusst nur dort
Aktion erscheint bewusst nur dort und nicht bei Favoriten, und nicht bei Favoriten, Wiedergabelisten oder Titellisten.
Wiedergabelisten oder Titellisten.
- ⬇️ **Neu: einzelne Server-Titel offline nehmen.** In der Album- und - ⬇️ **Neu: einzelne Server-Titel offline nehmen.** In der Album- und
Künstler-Ansicht hat jede Zeile jetzt einen Knopf — bisher ging nur „ganzes Künstler-Ansicht hat jede Zeile jetzt einen Knopf — bisher ging nur „ganzes
Album". Schon geladene Titel lassen sich dort auch wieder entfernen. Album". Schon geladene Titel lassen sich dort auch wieder entfernen.
+7 -3
View File
@@ -546,9 +546,13 @@ class MeloDb extends _$MeloDb {
.write(SongsCompanion(cloudId: Value(cloudId))); .write(SongsCompanion(cloudId: Value(cloudId)));
} }
Future<Song?> songByCloudId(String cloudId) => Future<Song?> songByCloudId(String cloudId) async {
(select(songs)..where((s) => s.cloudId.equals(cloudId))) final treffer = await (select(songs)
.getSingleOrNull(); ..where((s) => s.cloudId.equals(cloudId))
..limit(1))
.get();
return treffer.isEmpty ? null : treffer.single;
}
/// Titel, die am Server gelöscht wurden, auch auf dem Gerät als gelöscht /// Titel, die am Server gelöscht wurden, auch auf dem Gerät als gelöscht
/// markieren. Grabstein statt echtem Löschen — sonst legt der nächste Scan /// markieren. Grabstein statt echtem Löschen — sonst legt der nächste Scan
+7 -3
View File
@@ -89,9 +89,6 @@ Future<void> main() async {
_db, _db,
cloud: MeloCloudService(auth: _bakaAuth), cloud: MeloCloudService(auth: _bakaAuth),
); );
// Nur auf einem Gerät ohne eigene Playlisten: nach Neuinstallation oder
// Zurücksetzen holt das die gesicherten Listen zurück.
unawaited(_playlists.stelleWiederHer());
final navidrome = NavidromeService(); final navidrome = NavidromeService();
await navidrome.ladeGespeicherteZugangsdaten(); await navidrome.ladeGespeicherteZugangsdaten();
_downloads = DownloadService(db: _db, navidrome: navidrome); _downloads = DownloadService(db: _db, navidrome: navidrome);
@@ -219,7 +216,14 @@ class _HomeShellState extends State<HomeShell> with WidgetsBindingObserver {
/// Gleicht ab und zeigt danach höchstens einmal den „Was ist neu"-Bericht. /// Gleicht ab und zeigt danach höchstens einmal den „Was ist neu"-Bericht.
Future<void> _gleicheAbUndZeigeBericht() async { Future<void> _gleicheAbUndZeigeBericht() async {
final sync = context.read<SyncService>(); final sync = context.read<SyncService>();
final playlists = context.read<PlaylistService>();
await sync.automatisch(); await sync.automatisch();
// Nur auf einem Gerät ohne eigene Playlisten: nach dem ersten Abgleich
// (der Songs erst cloudIds zuweist) holt das die gesicherten Listen
// zurück. Vor dem Sync liefe jede songByCloudId-Suche ins Leere und
// legte leere Playlisten an, die der countPlaylists()-Riegel dann für
// immer blockierte.
unawaited(playlists.stelleWiederHer());
if (!mounted) return; if (!mounted) return;
final bericht = sync.bericht; final bericht = sync.bericht;
if (bericht == null) return; if (bericht == null) return;