Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: add study list screen #990

Merged
merged 16 commits into from
Nov 3, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
53 changes: 53 additions & 0 deletions lib/src/model/study/study_list_paginator.dart
Original file line number Diff line number Diff line change
@@ -0,0 +1,53 @@
import 'package:fast_immutable_collections/fast_immutable_collections.dart';
import 'package:lichess_mobile/src/model/study/study.dart';
import 'package:lichess_mobile/src/model/study/study_filter.dart';
import 'package:lichess_mobile/src/model/study/study_repository.dart';
import 'package:lichess_mobile/src/network/http.dart';
import 'package:riverpod_annotation/riverpod_annotation.dart';

part 'study_list_paginator.g.dart';

typedef StudyList = ({IList<StudyPageData> studies, int? nextPage});

/// Gets a list of studies from the paginated API.
@riverpod
class StudyListPaginator extends _$StudyListPaginator {
@override
Future<StudyList> build({
required StudyFilterState filter,
String? search,
}) async {
return _nextPage();
}

Future<void> next() async {
final studyList = state.requireValue;
if (studyList.nextPage == null) return;

final newStudyPage = await _nextPage();

state = AsyncData(
(
nextPage: newStudyPage.nextPage,
studies: studyList.studies.addAll(newStudyPage.studies),
),
);
}

Future<StudyList> _nextPage() async {
final nextPage = state.value?.nextPage ?? 1;

return await ref.withClient(
(client) => search == null
? StudyRepository(client).getStudies(
category: filter.category,
order: filter.order,
page: nextPage,
)
: StudyRepository(client).searchStudies(
query: search!,
page: nextPage,
),
);
}
}
20 changes: 12 additions & 8 deletions lib/src/model/study/study_repository.dart
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@ import 'package:http/http.dart';
import 'package:lichess_mobile/src/model/common/id.dart';
import 'package:lichess_mobile/src/model/study/study.dart';
import 'package:lichess_mobile/src/model/study/study_filter.dart';
import 'package:lichess_mobile/src/model/study/study_list_paginator.dart';
import 'package:lichess_mobile/src/network/http.dart';
import 'package:riverpod_annotation/riverpod_annotation.dart';

Expand All @@ -22,7 +23,7 @@ class StudyRepository {

final Client client;

Future<IList<StudyPageData>> getStudies({
Future<StudyList> getStudies({
required StudyCategory category,
required StudyListOrder order,
int page = 1,
Expand All @@ -33,7 +34,7 @@ class StudyRepository {
);
}

Future<IList<StudyPageData>> searchStudies({
Future<StudyList> searchStudies({
required String query,
int page = 1,
}) {
Expand All @@ -43,7 +44,7 @@ class StudyRepository {
);
}

Future<IList<StudyPageData>> _requestStudies({
Future<StudyList> _requestStudies({
required String path,
required Map<String, String> queryParameters,
}) {
Expand All @@ -57,11 +58,14 @@ class StudyRepository {
final paginator =
pick(json, 'paginator').asMapOrThrow<String, dynamic>();

return pick(paginator, 'currentPageResults')
.asListOrThrow(
(pick) => StudyPageData.fromJson(pick.asMapOrThrow()),
)
.toIList();
return (
studies: pick(paginator, 'currentPageResults')
.asListOrThrow(
(pick) => StudyPageData.fromJson(pick.asMapOrThrow()),
)
.toIList(),
nextPage: pick(paginator, 'nextPage').asIntOrNull()
);
},
);
}
Expand Down
Loading