From f4d07ef9a1b371527556647a294778b2823fadb9 Mon Sep 17 00:00:00 2001 From: Bryan Van Deusen Date: Mon, 11 May 2026 11:07:24 -0400 Subject: [PATCH] =?UTF-8?q?diag(flutter):=20trace=20playlist=20provider=20?= =?UTF-8?q?=E2=80=94=20wire=20vs=20drift=20vs=20filter?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Web UI shows system playlists; Flutter shows placeholders. Wire shape, adapters, drift schema, and filter constants all line up on inspection, so adding instrumentation to pinpoint where the system rows fall out: - Log what /api/playlists?kind=all actually returns (owned/public counts, including how many of owned are system). - Log what cacheFirst sees on each drift emit: total rows, filtered, how many are system, how many landed in owned vs pub, plus the user.id used for the owned-vs-pub split. Also add the 3s connectivity timeout that albumProvider/artistProvider got — keeps the alwaysRefresh path from blocking on a stalled connectivity stream. Three log lines from one home-screen visit will tell us: - Does the server emit system rows? (wire log: system=N) - Do they land in drift? (drift log: filtered system=N) - Do they survive the user-id filter? (drift log: owned system=N) --- .../lib/playlists/playlists_provider.dart | 19 +++++++++++++++++-- 1 file changed, 17 insertions(+), 2 deletions(-) diff --git a/flutter_client/lib/playlists/playlists_provider.dart b/flutter_client/lib/playlists/playlists_provider.dart index bef6f556..4bc23268 100644 --- a/flutter_client/lib/playlists/playlists_provider.dart +++ b/flutter_client/lib/playlists/playlists_provider.dart @@ -1,4 +1,5 @@ import 'package:drift/drift.dart' as drift; +import 'package:flutter/foundation.dart' show debugPrint; import 'package:flutter_riverpod/flutter_riverpod.dart'; import '../api/endpoints/me.dart'; @@ -36,6 +37,11 @@ final playlistsListProvider = fetchAndPopulate: () async { final api = await ref.read(playlistsApiProvider.future); final fresh = await api.list(kind: kind); + final ownedSysCount = + fresh.owned.where((p) => p.systemVariant != null).length; + debugPrint( + 'playlistsListProvider($kind): wire returned owned=${fresh.owned.length} ' + '(system=$ownedSysCount) public=${fresh.public.length}'); await db.batch((b) { for (final p in fresh.all) { b.insert(db.cachedPlaylists, p.toDrift(), @@ -49,7 +55,7 @@ final playlistsListProvider = if (kind == 'user') return r.systemVariant == null; if (kind == 'system') return r.systemVariant != null; return true; // 'all' - }); + }).toList(); final owned = filtered .where((r) => r.userId == user.id) .map((r) => r.toRef()) @@ -58,9 +64,18 @@ final playlistsListProvider = .where((r) => r.userId != user.id && r.isPublic) .map((r) => r.toRef()) .toList(); + final ownedSys = owned.where((p) => p.isSystem).length; + final driftSys = filtered.where((r) => r.systemVariant != null).length; + debugPrint( + 'playlistsListProvider($kind): drift rows=${rows.length} ' + 'filtered=${filtered.length} (system=$driftSys) ' + 'owned=${owned.length} (system=$ownedSys) pub=${pub.length} ' + 'userId=${user.id}'); return PlaylistsList(owned: owned, public: pub); }, - isOnline: () async => (await ref.read(connectivityProvider.future)), + isOnline: () async => (await ref + .read(connectivityProvider.future) + .timeout(const Duration(seconds: 3), onTimeout: () => true)), // Aggregate list — server may add system playlists (For-You / // Discover) that the per-user delta sync doesn't always emit. // Stale-while-revalidate ensures the home tile row reflects the