mnemo_cards/lib/features/packs/pack_manager.dart

127 lines
4.2 KiB
Dart
Raw Normal View History

2024-05-22 20:48:44 +00:00
import 'dart:async';
import 'dart:developer';
2024-05-28 21:25:51 +00:00
import 'package:mnemo_cards/di/locator.dart';
2024-08-18 16:52:03 +00:00
import 'package:mnemo_cards/features/packs/loading_packs_holder.dart';
2024-05-22 20:48:44 +00:00
import 'package:mnemo_cards/features/packs/pack_cache_manager.dart';
import 'package:mnemo_cards/features/packs/packs_api.dart';
import 'package:mnemo_cards/features/packs/preview_pack_holder.dart';
import 'package:mnemo_cards/managers/repository/repository.dart';
import 'package:mnemo_cards_common/mnemo_cards_common.dart';
import 'package:rxdart/rxdart.dart';
import 'pack_holder.dart';
class PackManager {
final Repository _repository;
final PacksApi _packsApi;
final PackHolder _packHolder;
final PreviewPackHolder _previewPackHolder;
2024-08-18 16:52:03 +00:00
final LoadingPacksHolder _loadingPacksHolder;
2024-05-22 20:48:44 +00:00
final PackCacheManager _cacheManager;
PackManager(
this._repository,
this._packsApi,
this._packHolder,
this._previewPackHolder,
2024-08-18 16:52:03 +00:00
this._loadingPacksHolder,
2024-05-22 20:48:44 +00:00
this._cacheManager,
);
Future<void> init() async {
2024-08-18 16:52:03 +00:00
final packs = await _cacheManager.loadAllPacks();
_packHolder.setPacksWithCards(packs.map((p) => p.id).toList());
2024-05-22 20:48:44 +00:00
// _repository.userStream.map((u) => u.packs).distinct().listen((packs) async {
// final savedPacks = await savedPacksIds;
// for (final p in packs) {
// if (savedPacks.contains(p)) {
// final loaded = await loadPackFromCache(p);
// if (loaded.cards.isEmpty) {
// await downloadPackById(p);
// }
// } else {
// await downloadPackById(p);
// }
// }
// });
}
2024-05-28 21:25:51 +00:00
Stream<GetCardPackResponse> getCardPackStream(
2024-08-18 16:52:03 +00:00
CardPackPreviewDto preview,
2024-05-28 21:25:51 +00:00
) async* {
2024-08-18 16:52:03 +00:00
final loadingDto = CardPackLoadingDto.fromPreviewDto(preview);
final isAvailable = preview.isAvailable;
final id = preview.id;
2024-05-28 21:25:51 +00:00
if (isAvailable) {
2024-05-22 20:48:44 +00:00
try {
2024-05-28 21:25:51 +00:00
yield await _cacheManager.loadPackFromCache(id);
2024-05-22 20:48:44 +00:00
} catch (err) {
2024-08-18 16:52:03 +00:00
yield loadingDto;
2024-05-28 21:25:51 +00:00
log('Cant load pack from cache, fetching pack', error: err);
try {
await locator.packUpdater.updatePackAndSaveImages(id);
yield await _cacheManager.loadPackFromCache(id);
} on Object catch (e, s) {
log('Cant fetch pack', error: e, stackTrace: s);
}
}
} else {
2024-08-18 16:52:03 +00:00
yield loadingDto;
2024-05-28 21:25:51 +00:00
final buyDto = await _packsApi.getPackBuy(id).catchError((_) => null);
if (buyDto != null) {
yield buyDto;
2024-08-18 16:52:03 +00:00
_packHolder.removePackWithCards(id);
2024-05-28 21:25:51 +00:00
} else {
log('Buy dto is null, fetching pack');
try {
await locator.packUpdater.updatePackAndSaveImages(id);
yield await _cacheManager.loadPackFromCache(id);
} on Object catch (e, s) {
log('Cant fetch pack', error: e, stackTrace: s);
}
2024-05-22 20:48:44 +00:00
}
}
2024-08-18 16:52:03 +00:00
yield* Rx.combineLatest2(
_packHolder.asStream
.map(
(state) =>
state.packsWithCards.firstWhereOrNull((packId) => packId == id),
)
.asyncMap(
(packId) async => packId == null
? null
: await _cacheManager.loadPackFromCache(packId),
),
_loadingPacksHolder.asStream
.map((state) => state?.packs.firstWhereOrNull((p) => p.id == id)),
(dto, isLoadingResponse) => isLoadingResponse ?? dto,
).whereNotNull();
2024-05-22 20:48:44 +00:00
}
Future<void> clearCache() async {
_packHolder.clear();
await _cacheManager.clearCache();
}
Stream<List<CardPackPreviewDto>?> get packsPreviewStream =>
_previewPackHolder.asStream
.map((event) => event?.previewPacks)
.whereNotNull()
.distinct((prev, next) {
if (prev.length != next.length) return false;
for (int i = 0; i < prev.length; i++) {
2024-08-18 16:52:03 +00:00
if (prev[i] != next[i]) return false;
// if (prev[i].isAvailable != next[i].isAvailable) return false;
// if (prev[i].id != next[i].id) return false;
// if (prev[i].version != next[i].version) return false;
// if (prev[i].price != next[i].price) return false;
// if (prev[i].price != next[i].price) return false;
// if (prev[i].cards != next[i].cards) return false;
2024-05-22 20:48:44 +00:00
}
return true;
});
}