diff --git a/lib/extensions/map.dart b/lib/extensions/map.dart new file mode 100644 index 000000000..48f2935c2 --- /dev/null +++ b/lib/extensions/map.dart @@ -0,0 +1,15 @@ +extension CastDeepMaps on Map { + Map castKeyDeep() { + return cast().map((key, value) { + if (value is Map) { + return MapEntry(key, value.castKeyDeep()); + } else if (value is List) { + return MapEntry( + key, + value.map((e) => e is Map ? e.castKeyDeep() : e).toList(), + ); + } + return MapEntry(key, value); + }); + } +} diff --git a/lib/extensions/page.dart b/lib/extensions/page.dart new file mode 100644 index 000000000..34343fb5c --- /dev/null +++ b/lib/extensions/page.dart @@ -0,0 +1,61 @@ +import 'package:spotify/spotify.dart'; + +extension CursorPageJson on CursorPage { + static CursorPage fromJson( + Map json, + T Function(dynamic json) itemFromJson, + ) { + final metadata = Paging.fromJson(json["metadata"]); + final paging = CursorPaging(); + paging.cursors = Cursor.fromJson(json["metadata"])..after = json["after"]; + paging.href = metadata.href; + paging.itemsNative = paging.itemsNative; + paging.limit = metadata.limit; + paging.next = metadata.next; + return CursorPage( + paging, + itemFromJson, + ); + } + + Map toJson() { + return { + "after": after, + "metadata": metadata.toJson(), + }; + } +} + +extension PagingToJson on Paging { + Map toJson() { + return { + "items": itemsNative, + "total": total, + "next": next, + "previous": previous, + "limit": limit, + "offset": offset, + "href": href, + }; + } +} + +extension PageJson on Page { + static Page fromJson( + Map json, + T Function(dynamic json) itemFromJson, + ) { + return Page( + Paging.fromJson( + Map.castFrom(json["metadata"]), + ), + itemFromJson, + ); + } + + Map toJson() { + return { + "metadata": metadata.toJson(), + }; + } +} diff --git a/lib/services/queries/category.dart b/lib/services/queries/category.dart index 4f646b13d..c4e8d188d 100644 --- a/lib/services/queries/category.dart +++ b/lib/services/queries/category.dart @@ -1,6 +1,8 @@ import 'package:fl_query/fl_query.dart'; import 'package:hooks_riverpod/hooks_riverpod.dart'; import 'package:spotify/spotify.dart'; +import 'package:spotube/extensions/map.dart'; +import 'package:spotube/extensions/page.dart'; import 'package:spotube/hooks/use_spotify_infinite_query.dart'; class CategoryQueries { @@ -24,6 +26,15 @@ class CategoryQueries { } return lastPageData.nextOffset; }, + jsonConfig: JsonConfig>( + toJson: (page) => page.toJson(), + fromJson: (json) => PageJson.fromJson( + json, + (json) { + return Category.fromJson((json as Map).castKeyDeep()); + }, + ), + ), ref: ref, ); } diff --git a/lib/services/queries/playlist.dart b/lib/services/queries/playlist.dart index 55e4ed6f4..06f8d952b 100644 --- a/lib/services/queries/playlist.dart +++ b/lib/services/queries/playlist.dart @@ -2,6 +2,8 @@ import 'package:catcher/catcher.dart'; import 'package:fl_query/fl_query.dart'; import 'package:hooks_riverpod/hooks_riverpod.dart'; import 'package:spotify/spotify.dart'; +import 'package:spotube/extensions/map.dart'; +import 'package:spotube/extensions/track.dart'; import 'package:spotube/hooks/use_spotify_infinite_query.dart'; import 'package:spotube/hooks/use_spotify_query.dart'; @@ -51,6 +53,18 @@ class PlaylistQueries { return useSpotifyQuery, dynamic>( "playlist-tracks/$playlistId", (spotify) => tracksOf(playlistId, spotify), + jsonConfig: playlistId == "user-liked-tracks" + ? JsonConfig( + toJson: (tracks) => { + 'tracks': tracks.map((e) => e.toJson()).toList() + }, + fromJson: (json) => (json['tracks'] as List) + .map((e) => Track.fromJson( + (e as Map).castKeyDeep(), + )) + .toList(), + ) + : null, ref: ref, ); } diff --git a/pubspec.lock b/pubspec.lock index 10fbc3442..709564da0 100644 --- a/pubspec.lock +++ b/pubspec.lock @@ -535,7 +535,7 @@ packages: description: path: "packages/fl_query" ref: new-architecture - resolved-ref: cf2550a2909d0cb957324fe114acacb431a5f33a + resolved-ref: "64d661779a88c845e5280f3da99a2bd90bdc586b" url: "https://github.com/KRTirtho/fl-query.git" source: git version: "0.3.1" @@ -544,7 +544,7 @@ packages: description: path: "packages/fl_query_hooks" ref: new-architecture - resolved-ref: cf2550a2909d0cb957324fe114acacb431a5f33a + resolved-ref: "64d661779a88c845e5280f3da99a2bd90bdc586b" url: "https://github.com/KRTirtho/fl-query.git" source: git version: "0.3.1"