Skip to content

Commit

Permalink
add models to get study as JSON and PGN
Browse files Browse the repository at this point in the history
  • Loading branch information
tom-anders committed Oct 9, 2024
1 parent d1c50db commit 11eca57
Show file tree
Hide file tree
Showing 2 changed files with 134 additions and 0 deletions.
104 changes: 104 additions & 0 deletions lib/src/model/study/study.dart
Original file line number Diff line number Diff line change
@@ -1,11 +1,115 @@
import 'package:collection/collection.dart';
import 'package:dartchess/dartchess.dart';
import 'package:fast_immutable_collections/fast_immutable_collections.dart';
import 'package:freezed_annotation/freezed_annotation.dart';
import 'package:lichess_mobile/src/model/common/chess.dart';
import 'package:lichess_mobile/src/model/common/id.dart';
import 'package:lichess_mobile/src/model/user/user.dart';

part 'study.freezed.dart';
part 'study.g.dart';

@Freezed(fromJson: true)
class Study with _$Study {
const Study._();

const factory Study({
required StudyId id,
required String name,
required ({StudyChapterId chapterId, String path}) position,
required bool liked,
required int likes,
required UserId? ownerId,
required IList<String> topics,
required IList<StudyChapterMeta> chapters,
required StudyChapter chapter,
}) = _Study;

StudyChapterMeta get currentChapterMeta =>
chapters.firstWhere((c) => c.id == chapter.id);

factory Study.fromJson(Map<String, Object?> json) => _$StudyFromJson(json);
}

@Freezed(fromJson: true)
class StudyFeatures with _$StudyFeatures {
const StudyFeatures._();

const factory StudyFeatures({
@JsonKey(defaultValue: false) required bool cloneable,
@JsonKey(defaultValue: false) required bool chat,
@JsonKey(defaultValue: false) required bool sticky,
}) = _StudyFeatures;

factory StudyFeatures.fromJson(Map<String, Object?> json) =>
_$StudyFeaturesFromJson(json);
}

@Freezed(fromJson: true)
class StudyChapter with _$StudyChapter {
const StudyChapter._();

const factory StudyChapter({
required StudyChapterId id,
required StudyChapterSetup setup,
@JsonKey(defaultValue: false) required bool practise,
required int? conceal,
@JsonKey(defaultValue: false) required bool gamebook,
required StudyChapterFeatures features,
}) = _StudyChapter;

factory StudyChapter.fromJson(Map<String, Object?> json) =>
_$StudyChapterFromJson(json);
}

@Freezed(fromJson: true)
class StudyChapterFeatures with _$StudyChapterFeatures {
const StudyChapterFeatures._();

const factory StudyChapterFeatures({
@JsonKey(defaultValue: false) required bool computer,
@JsonKey(defaultValue: false) required bool explorer,
}) = _StudyChapterFeatures;

factory StudyChapterFeatures.fromJson(Map<String, Object?> json) =>
_$StudyChapterFeaturesFromJson(json);
}

@Freezed(fromJson: true)
class StudyChapterSetup with _$StudyChapterSetup {
const StudyChapterSetup._();

const factory StudyChapterSetup({
required GameId? id,
required Side orientation,
@JsonKey(fromJson: _variantFromJson) required Variant variant,
required bool? fromFen,
}) = _StudyChapterSetup;

factory StudyChapterSetup.fromJson(Map<String, Object?> json) =>
_$StudyChapterSetupFromJson(json);
}

Variant _variantFromJson(Map<String, Object?> json) {
return Variant.values.firstWhereOrNull(
(v) => v.name == json['key'],
)!;
}

@Freezed(fromJson: true)
class StudyChapterMeta with _$StudyChapterMeta {
const StudyChapterMeta._();

const factory StudyChapterMeta({
required StudyChapterId id,
required String name,
required String? fen,
}) = _StudyChapterMeta;

factory StudyChapterMeta.fromJson(Map<String, Object?> json) =>
_$StudyChapterMetaFromJson(json);
}

@Freezed(fromJson: true)
class StudyPageData with _$StudyPageData {
const StudyPageData._();
Expand Down
30 changes: 30 additions & 0 deletions lib/src/model/study/study_repository.dart
Original file line number Diff line number Diff line change
@@ -1,6 +1,9 @@
import 'dart:convert';

import 'package:deep_pick/deep_pick.dart';
import 'package:fast_immutable_collections/fast_immutable_collections.dart';
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/network/http.dart';
Expand Down Expand Up @@ -53,4 +56,31 @@ class StudyRepository {
},
);
}

Future<(Study study, String pgn)> getStudy({
required StudyId id,
StudyChapterId? chapterId,
}) async {
final study = await client.readJson(
Uri(
path: (chapterId != null) ? '/study/$id/$chapterId' : '/study/$id',
queryParameters: {
'chapters': '1',
},
),
headers: {'Accept': 'application/json'},
mapper: (Map<String, dynamic> json) {
return Study.fromJson(
pick(json, 'study').asMapOrThrow(),
);
},
);

final pgnBytes = await client.readBytes(
Uri(path: '/api/study/$id/${chapterId ?? study.chapter.id}.pgn'),
headers: {'Accept': 'application/x-chess-pgn'},
);

return (study, utf8.decode(pgnBytes));
}
}

0 comments on commit 11eca57

Please sign in to comment.