From 2d8738146e63cdecb470835cdb8b7e1580455bff Mon Sep 17 00:00:00 2001 From: Ming Ming Date: Wed, 8 Dec 2021 02:42:25 +0800 Subject: [PATCH] Overhaul how dependencies are injected to clients --- lib/bloc/list_album.dart | 56 +++++++++++++++---- lib/bloc/list_importable_album.dart | 27 +++++---- lib/bloc/list_sharing.dart | 49 ++++++++-------- lib/di_container.dart | 23 ++++++++ lib/use_case/compat/v25.dart | 18 ++++-- lib/use_case/find_file.dart | 9 ++- lib/use_case/import_pending_shared_album.dart | 17 ++++-- .../import_potential_shared_album.dart | 18 ++++-- lib/use_case/list_album.dart | 20 ++++--- lib/use_case/list_share.dart | 9 +-- lib/use_case/list_share_with_me.dart | 9 ++- lib/use_case/ls_single_file.dart | 9 ++- lib/use_case/move.dart | 16 ++++-- lib/use_case/remove.dart | 7 +-- lib/use_case/restore_trashbin.dart | 11 +++- lib/use_case/unimport_shared_album.dart | 11 +++- lib/use_case/unshare_file_from_album.dart | 8 +-- lib/widget/album_browser.dart | 6 +- lib/widget/album_browser_mixin.dart | 10 ++-- lib/widget/album_importer.dart | 4 +- lib/widget/album_picker_dialog.dart | 18 +----- lib/widget/album_search_delegate.dart | 11 ++-- lib/widget/home.dart | 13 +++-- lib/widget/home_albums.dart | 23 +------- lib/widget/root_picker.dart | 7 +-- lib/widget/sharing_browser.dart | 13 +++-- lib/widget/trashbin_browser.dart | 7 ++- lib/widget/trashbin_viewer.dart | 8 +-- test/use_case/find_file_test.dart | 21 ++++--- 29 files changed, 272 insertions(+), 186 deletions(-) diff --git a/lib/bloc/list_album.dart b/lib/bloc/list_album.dart index 6d63b574..83952a64 100644 --- a/lib/bloc/list_album.dart +++ b/lib/bloc/list_album.dart @@ -1,7 +1,8 @@ import 'package:bloc/bloc.dart'; +import 'package:kiwi/kiwi.dart'; import 'package:logging/logging.dart'; import 'package:nc_photos/account.dart'; -import 'package:nc_photos/app_db.dart'; +import 'package:nc_photos/di_container.dart'; import 'package:nc_photos/entity/album.dart'; import 'package:nc_photos/entity/file.dart'; import 'package:nc_photos/entity/file/data_source.dart'; @@ -10,6 +11,7 @@ import 'package:nc_photos/entity/share.dart'; import 'package:nc_photos/event/event.dart'; import 'package:nc_photos/exception.dart'; import 'package:nc_photos/exception_event.dart'; +import 'package:nc_photos/or_null.dart'; import 'package:nc_photos/remote_storage_util.dart' as remote_storage_util; import 'package:nc_photos/throttler.dart'; import 'package:nc_photos/use_case/list_album.dart'; @@ -102,7 +104,19 @@ class ListAlbumBlocInconsistent extends ListAlbumBlocState { } class ListAlbumBloc extends Bloc { - ListAlbumBloc() : super(const ListAlbumBlocInit()) { + /// Constructor + /// + /// If [offlineC] is not null, this [DiContainer] will be used when requesting + /// offline contents, otherwise [_c] will be used + ListAlbumBloc( + this._c, [ + DiContainer? offlineC, + ]) : _offlineC = offlineC ?? _c, + assert(require(_c)), + assert(offlineC == null || require(offlineC)), + assert(ListAlbum.require(_c)), + assert(offlineC == null || ListAlbum.require(offlineC)), + super(const ListAlbumBlocInit()) { _albumUpdatedListener = AppEventListener(_onAlbumUpdatedEvent); _fileRemovedListener = @@ -124,6 +138,28 @@ class ListAlbumBloc extends Bloc { ); } + static bool require(DiContainer c) => true; + + static ListAlbumBloc of(Account account) { + final id = "${account.scheme}://${account.username}@${account.address}"; + try { + _log.fine("[of] Resolving bloc for '$id'"); + return KiwiContainer().resolve("ListAlbumBloc($id)"); + } catch (_) { + // no created instance for this account, make a new one + _log.info("[of] New bloc instance for account: $account"); + final c = KiwiContainer().resolve(); + final offlineC = c.copyWith( + fileRepo: OrNull(FileRepo(FileAppDbDataSource(c.appDb))), + albumRepo: OrNull(AlbumRepo(AlbumAppDbDataSource(c.appDb))), + ); + final bloc = ListAlbumBloc(c, offlineC); + KiwiContainer() + .registerInstance(bloc, name: "ListAlbumBloc($id)"); + return bloc; + } + } + @override mapEventToState(ListAlbumBlocEvent event) async* { _log.info("[mapEventToState] $event"); @@ -249,20 +285,17 @@ class ListAlbumBloc extends Bloc { } Future _queryOffline(ListAlbumBlocQuery ev) => - _queryWithAlbumDataSource( - ev, FileAppDbDataSource(AppDb()), AlbumAppDbDataSource(AppDb())); + _queryWithAlbumDataSource(_offlineC, ev); Future _queryOnline(ListAlbumBlocQuery ev) => - _queryWithAlbumDataSource( - ev, FileCachedDataSource(AppDb()), AlbumCachedDataSource(AppDb())); + _queryWithAlbumDataSource(_c, ev); - Future _queryWithAlbumDataSource(ListAlbumBlocQuery ev, - FileDataSource fileDataSource, AlbumDataSource albumDataSrc) async { + Future _queryWithAlbumDataSource( + DiContainer c, ListAlbumBlocQuery ev) async { try { final albums = []; final errors = []; - await for (final result in ListAlbum( - FileRepo(fileDataSource), AlbumRepo(albumDataSrc))(ev.account)) { + await for (final result in ListAlbum(c)(ev.account)) { if (result is ExceptionEvent) { if (result.error is CacheNotFoundException) { _log.info( @@ -292,6 +325,9 @@ class ListAlbumBloc extends Bloc { bool _isAccountOfInterest(Account account) => state.account == null || state.account!.compareServerIdentity(account); + final DiContainer _c; + final DiContainer _offlineC; + late AppEventListener _albumUpdatedListener; late AppEventListener _fileRemovedListener; late AppEventListener _albumCreatedListener; diff --git a/lib/bloc/list_importable_album.dart b/lib/bloc/list_importable_album.dart index bec40674..63bdc1b2 100644 --- a/lib/bloc/list_importable_album.dart +++ b/lib/bloc/list_importable_album.dart @@ -1,12 +1,11 @@ import 'package:bloc/bloc.dart'; import 'package:logging/logging.dart'; import 'package:nc_photos/account.dart'; -import 'package:nc_photos/app_db.dart'; import 'package:nc_photos/debug_util.dart'; +import 'package:nc_photos/di_container.dart'; import 'package:nc_photos/entity/album.dart'; import 'package:nc_photos/entity/album/provider.dart'; import 'package:nc_photos/entity/file.dart'; -import 'package:nc_photos/entity/file/data_source.dart'; import 'package:nc_photos/entity/file_util.dart' as file_util; import 'package:nc_photos/iterable_extension.dart'; import 'package:nc_photos/use_case/list_album.dart'; @@ -87,7 +86,12 @@ class ListImportableAlbumBlocFailure extends ListImportableAlbumBlocState { /// Return all directories that potentially could be a new album class ListImportableAlbumBloc extends Bloc { - ListImportableAlbumBloc() : super(ListImportableAlbumBlocInit()); + ListImportableAlbumBloc(this._c) + : assert(require(_c)), + assert(ListAlbum.require(_c)), + super(ListImportableAlbumBlocInit()); + + static bool require(DiContainer c) => DiContainer.has(c, DiType.fileRepo); @override mapEventToState(ListImportableAlbumBlocEvent event) async* { @@ -101,9 +105,7 @@ class ListImportableAlbumBloc ListImportableAlbumBlocQuery ev) async* { yield const ListImportableAlbumBlocLoading([]); try { - final fileRepo = FileRepo(FileCachedDataSource(AppDb())); - final albumRepo = AlbumRepo(AlbumCachedDataSource(AppDb())); - final albums = (await ListAlbum(fileRepo, albumRepo)(ev.account) + final albums = (await ListAlbum(_c)(ev.account) .where((event) => event is Album) .toList()) .cast(); @@ -119,8 +121,7 @@ class ListImportableAlbumBloc final products = []; int count = 0; for (final r in ev.roots) { - await for (final ev - in _queryDir(fileRepo, ev.account, importedDirs, r)) { + await for (final ev in _queryDir(ev.account, importedDirs, r)) { if (ev is Exception || ev is Error) { throw ev; } else if (ev is ListImportableAlbumBlocItem) { @@ -142,13 +143,13 @@ class ListImportableAlbumBloc /// Query [dir] and emit all conforming dirs recursively (including [dir]) /// /// Emit ListImportableAlbumBlocItem or Exception - Stream _queryDir(FileRepo fileRepo, Account account, - List importedDirs, File dir) async* { + Stream _queryDir( + Account account, List importedDirs, File dir) async* { try { if (importedDirs.containsIf(dir, (a, b) => a.path == b.path)) { return; } - final files = await Ls(fileRepo)(account, dir); + final files = await Ls(_c.fileRepo)(account, dir); // check number of supported files in this directory final count = files.where((f) => file_util.isSupportedFormat(f)).length; // arbitrary number @@ -156,7 +157,7 @@ class ListImportableAlbumBloc yield ListImportableAlbumBlocItem(dir, count); } for (final d in files.where((f) => f.isCollection == true)) { - yield* _queryDir(fileRepo, account, importedDirs, d); + yield* _queryDir(account, importedDirs, d); } } catch (e, stacktrace) { _log.shout( @@ -167,6 +168,8 @@ class ListImportableAlbumBloc } } + final DiContainer _c; + static final _log = Logger("bloc.list_importable_album.ListImportableAlbumBloc"); } diff --git a/lib/bloc/list_sharing.dart b/lib/bloc/list_sharing.dart index e78156c9..2c94d4b2 100644 --- a/lib/bloc/list_sharing.dart +++ b/lib/bloc/list_sharing.dart @@ -2,13 +2,11 @@ import 'package:bloc/bloc.dart'; import 'package:kiwi/kiwi.dart'; import 'package:logging/logging.dart'; import 'package:nc_photos/account.dart'; -import 'package:nc_photos/app_db.dart'; +import 'package:nc_photos/di_container.dart'; import 'package:nc_photos/entity/album.dart'; import 'package:nc_photos/entity/file.dart'; -import 'package:nc_photos/entity/file/data_source.dart'; import 'package:nc_photos/entity/file_util.dart' as file_util; import 'package:nc_photos/entity/share.dart'; -import 'package:nc_photos/entity/share/data_source.dart'; import 'package:nc_photos/event/event.dart'; import 'package:nc_photos/iterable_extension.dart'; import 'package:nc_photos/remote_storage_util.dart' as remote_storage_util; @@ -152,7 +150,12 @@ class ListSharingBlocFailure extends ListSharingBlocState { /// List shares to be shown in [SharingBrowser] class ListSharingBloc extends Bloc { - ListSharingBloc() : super(ListSharingBlocInit()) { + ListSharingBloc(this._c) + : assert(require(_c)), + assert(FindFile.require(_c)), + assert(ListShareWithMe.require(_c)), + assert(LsSingleFile.require(_c)), + super(ListSharingBlocInit()) { _shareRemovedListener.begin(); _fileMovedEventListener.begin(); @@ -164,6 +167,11 @@ class ListSharingBloc extends Bloc { ); } + static bool require(DiContainer c) => + DiContainer.has(c, DiType.albumRepo) && + DiContainer.has(c, DiType.fileRepo) && + DiContainer.has(c, DiType.shareRepo); + static ListSharingBloc of(Account account) { final id = "${account.scheme}://${account.username}@${account.address}?${account.roots.join('&')}"; @@ -173,7 +181,7 @@ class ListSharingBloc extends Bloc { } catch (_) { // no created instance for this account, make a new one _log.info("[of] New bloc instance for account: $account"); - final bloc = ListSharingBloc(); + final bloc = ListSharingBloc(KiwiContainer().resolve()); KiwiContainer().registerInstance(bloc, name: "ListSharingBloc($id)"); return bloc; @@ -234,14 +242,10 @@ class ListSharingBloc extends Bloc { final items = List.of(state.items); items.removeWhere( (i) => i is ListSharingAlbum && i.share.path == ev.file.strippedPath); - final fileRepo = FileRepo(FileCachedDataSource(AppDb())); - final albumRepo = AlbumRepo(AlbumCachedDataSource(AppDb())); - final shareRepo = ShareRepo(ShareRemoteDataSource()); - final newShares = await ListShareWithMe(shareRepo)( - ev.account, File(path: ev.destination)); - final newAlbumFile = - await LsSingleFile(fileRepo)(ev.account, ev.destination); - final newAlbum = await albumRepo.get(ev.account, newAlbumFile); + final newShares = + await ListShareWithMe(_c)(ev.account, File(path: ev.destination)); + final newAlbumFile = await LsSingleFile(_c)(ev.account, ev.destination); + final newAlbum = await _c.albumRepo.get(ev.account, newAlbumFile); for (final s in newShares) { items.add(ListSharingAlbum(s, newAlbum)); } @@ -282,8 +286,7 @@ class ListSharingBloc extends Bloc { } Future> _query(ListSharingBlocQuery ev) async { - final fileRepo = FileRepo(FileCachedDataSource(AppDb())); - final sharedAlbumFiles = await Ls(fileRepo)( + final sharedAlbumFiles = await Ls(_c.fileRepo)( ev.account, File( path: remote_storage_util.getRemoteAlbumsDir(ev.account), @@ -297,8 +300,7 @@ class ListSharingBloc extends Bloc { Future> _querySharesByMe( ListSharingBlocQuery ev, List sharedAlbumFiles) async { - final shareRepo = ShareRepo(ShareRemoteDataSource()); - final shares = await shareRepo.listAll(ev.account); + final shares = await _c.shareRepo.listAll(ev.account); final futures = shares.map((s) async { final webdavPath = file_util.unstripPath(ev.account, s.path); // include link share dirs @@ -344,7 +346,7 @@ class ListSharingBloc extends Bloc { } try { - final file = await FindFile(AppDb())(ev.account, s.itemSource); + final file = await FindFile(_c)(ev.account, s.itemSource); return ListSharingFile(s, file); } catch (e, stackTrace) { _log.severe("[_querySharesByMe] File not found: ${s.itemSource}", e, @@ -357,15 +359,13 @@ class ListSharingBloc extends Bloc { Future> _querySharesWithMe( ListSharingBlocQuery ev, List sharedAlbumFiles) async { - final fileRepo = FileRepo(FileCachedDataSource(AppDb())); - final pendingSharedAlbumFiles = await Ls(fileRepo)( + final pendingSharedAlbumFiles = await Ls(_c.fileRepo)( ev.account, File( path: remote_storage_util.getRemotePendingSharedAlbumsDir(ev.account), )); - final shareRepo = ShareRepo(ShareRemoteDataSource()); - final shares = await shareRepo.reverseListAll(ev.account); + final shares = await _c.shareRepo.reverseListAll(ev.account); final futures = shares.map((s) async { final webdavPath = file_util.unstripPath(ev.account, s.path); // include pending shared albums @@ -405,8 +405,7 @@ class ListSharingBloc extends Bloc { Future _querySharedAlbum( ListSharingBlocQuery ev, Share share, File albumFile) async { try { - final albumRepo = AlbumRepo(AlbumCachedDataSource(AppDb())); - final album = await albumRepo.get(ev.account, albumFile); + final album = await _c.albumRepo.get(ev.account, albumFile); return ListSharingAlbum(share, album); } catch (e, stackTrace) { _log.shout( @@ -418,6 +417,8 @@ class ListSharingBloc extends Bloc { bool _isAccountOfInterest(Account account) => state.account == null || state.account!.compareServerIdentity(account); + final DiContainer _c; + late final _shareRemovedListener = AppEventListener(_onShareRemovedEvent); late final _fileMovedEventListener = diff --git a/lib/di_container.dart b/lib/di_container.dart index b62c561d..386fd87d 100644 --- a/lib/di_container.dart +++ b/lib/di_container.dart @@ -5,6 +5,7 @@ import 'package:nc_photos/entity/file.dart'; import 'package:nc_photos/entity/person.dart'; import 'package:nc_photos/entity/share.dart'; import 'package:nc_photos/entity/sharee.dart'; +import 'package:nc_photos/or_null.dart'; import 'package:nc_photos/pref.dart'; enum DiType { @@ -58,6 +59,28 @@ class DiContainer { } } + DiContainer copyWith({ + OrNull? albumRepo, + OrNull? faceRepo, + OrNull? fileRepo, + OrNull? personRepo, + OrNull? shareRepo, + OrNull? shareeRepo, + OrNull? appDb, + OrNull? pref, + }) { + return DiContainer( + albumRepo: albumRepo == null ? this.albumRepo : albumRepo.obj, + faceRepo: faceRepo == null ? this.faceRepo : faceRepo.obj, + fileRepo: fileRepo == null ? this.fileRepo : fileRepo.obj, + personRepo: personRepo == null ? this.personRepo : personRepo.obj, + shareRepo: shareRepo == null ? this.shareRepo : shareRepo.obj, + shareeRepo: shareeRepo == null ? this.shareeRepo : shareeRepo.obj, + appDb: appDb == null ? this.appDb : appDb.obj, + pref: pref == null ? this.pref : pref.obj, + ); + } + AlbumRepo get albumRepo => _albumRepo!; FaceRepo get faceRepo => _faceRepo!; FileRepo get fileRepo => _fileRepo!; diff --git a/lib/use_case/compat/v25.dart b/lib/use_case/compat/v25.dart index a455922e..ee3c696a 100644 --- a/lib/use_case/compat/v25.dart +++ b/lib/use_case/compat/v25.dart @@ -1,5 +1,6 @@ import 'package:logging/logging.dart'; import 'package:nc_photos/account.dart'; +import 'package:nc_photos/di_container.dart'; import 'package:nc_photos/entity/file.dart'; import 'package:nc_photos/use_case/move.dart'; import 'package:path/path.dart' as path; @@ -12,12 +13,16 @@ class CompatV25 { /// Migrate an album file to the new naming scheme static Future migrateAlbumFile( - FileRepo fileRepo, Account account, File albumFile) => - _MigrateAlbumFile(fileRepo)(account, albumFile); + DiContainer c, Account account, File albumFile) => + _MigrateAlbumFile(c)(account, albumFile); } class _MigrateAlbumFile { - _MigrateAlbumFile(this.fileRepo); + _MigrateAlbumFile(this._c) + : assert(require(_c)), + assert(Move.require(_c)); + + static bool require(DiContainer c) => true; Future call(Account account, File albumFile) async { assert(CompatV25.isAlbumFileNeedMigration(albumFile)); @@ -25,12 +30,13 @@ class _MigrateAlbumFile { "/" + path.basenameWithoutExtension(albumFile.path) + ".nc_album.json"; - _log.info("[call] Migrate album file from '${albumFile.path}' to '$newPath'"); - await Move(fileRepo)(account, albumFile, newPath); + _log.info( + "[call] Migrate album file from '${albumFile.path}' to '$newPath'"); + await Move(_c)(account, albumFile, newPath); return albumFile.copyWith(path: newPath); } - final FileRepo fileRepo; + final DiContainer _c; static final _log = Logger("use_case.compat.v25._MigrateAlbumFile"); } diff --git a/lib/use_case/find_file.dart b/lib/use_case/find_file.dart index d20ee2ec..62ff1010 100644 --- a/lib/use_case/find_file.dart +++ b/lib/use_case/find_file.dart @@ -1,15 +1,18 @@ import 'package:idb_shim/idb_client.dart'; import 'package:nc_photos/account.dart'; import 'package:nc_photos/app_db.dart'; +import 'package:nc_photos/di_container.dart'; import 'package:nc_photos/entity/file.dart'; import 'package:nc_photos/entity/file_util.dart' as file_util; class FindFile { - const FindFile(this.appDb); + FindFile(this._c) : assert(require(_c)); + + static bool require(DiContainer c) => DiContainer.has(c, DiType.appDb); /// Find the [File] in the DB by [fileId] Future call(Account account, int fileId) async { - return await appDb.use((db) async { + return await _c.appDb.use((db) async { final transaction = db.transaction(AppDb.fileDbStoreName, idbModeReadOnly); final store = transaction.objectStore(AppDb.fileDbStoreName); @@ -27,5 +30,5 @@ class FindFile { }); } - final AppDb appDb; + final DiContainer _c; } diff --git a/lib/use_case/import_pending_shared_album.dart b/lib/use_case/import_pending_shared_album.dart index ae1045e0..9d430327 100644 --- a/lib/use_case/import_pending_shared_album.dart +++ b/lib/use_case/import_pending_shared_album.dart @@ -1,4 +1,5 @@ import 'package:nc_photos/account.dart'; +import 'package:nc_photos/di_container.dart'; import 'package:nc_photos/entity/album.dart'; import 'package:nc_photos/entity/file.dart'; import 'package:nc_photos/remote_storage_util.dart' as remote_storage_util; @@ -7,22 +8,26 @@ import 'package:nc_photos/use_case/move.dart'; /// Import a shared album from the pending dir to the library class ImportPendingSharedAlbum { - const ImportPendingSharedAlbum(this.fileRepo, this.albumRepo); + ImportPendingSharedAlbum(this._c) + : assert(require(_c)), + assert(LsSingleFile.require(_c)), + assert(Move.require(_c)); + + static bool require(DiContainer c) => DiContainer.has(c, DiType.albumRepo); Future call(Account account, Album album) async { final destination = "${remote_storage_util.getRemoteAlbumsDir(account)}/${album.albumFile!.filename}"; - await Move(fileRepo)( + await Move(_c)( account, album.albumFile!, destination, shouldCreateMissingDir: true, ); - final newAlbumFile = await LsSingleFile(fileRepo)(account, destination); - final newAlbum = await albumRepo.get(account, newAlbumFile); + final newAlbumFile = await LsSingleFile(_c)(account, destination); + final newAlbum = await _c.albumRepo.get(account, newAlbumFile); return newAlbum; } - final FileRepo fileRepo; - final AlbumRepo albumRepo; + final DiContainer _c; } diff --git a/lib/use_case/import_potential_shared_album.dart b/lib/use_case/import_potential_shared_album.dart index e1fd6b73..33de6f91 100644 --- a/lib/use_case/import_potential_shared_album.dart +++ b/lib/use_case/import_potential_shared_album.dart @@ -1,5 +1,6 @@ import 'package:logging/logging.dart'; import 'package:nc_photos/account.dart'; +import 'package:nc_photos/di_container.dart'; import 'package:nc_photos/entity/album.dart'; import 'package:nc_photos/entity/file.dart'; import 'package:nc_photos/pref.dart'; @@ -9,20 +10,26 @@ import 'package:nc_photos/use_case/move.dart'; /// Import new shared albums to the pending dir class ImportPotentialSharedAlbum { - ImportPotentialSharedAlbum(this.fileRepo, this.albumRepo); + ImportPotentialSharedAlbum(this._c) + : assert(require(_c)), + assert(Move.require(_c)); + + static bool require(DiContainer c) => + DiContainer.has(c, DiType.albumRepo) && + DiContainer.has(c, DiType.fileRepo); Future> call(Account account, AccountPref accountPref) async { _log.info("[call] $account"); final products = []; final files = - await ListPotentialSharedAlbum(fileRepo)(account, accountPref); + await ListPotentialSharedAlbum(_c.fileRepo)(account, accountPref); for (final f in files) { // check if the file is actually an album try { - final album = await albumRepo.get(account, f); + final album = await _c.albumRepo.get(account, f); _log.info("[call] New shared album: ${album.name}, file: ${f.path}"); // move this file to the pending dir - await Move(fileRepo)( + await Move(_c)( account, f, "${remote_storage_util.getRemotePendingSharedAlbumsDir(account)}/${f.filename}", @@ -36,8 +43,7 @@ class ImportPotentialSharedAlbum { return products; } - final FileRepo fileRepo; - final AlbumRepo albumRepo; + final DiContainer _c; static final _log = Logger( "user_case.import_potential_shared_album.ImportPotentialSharedAlbum"); diff --git a/lib/use_case/list_album.dart b/lib/use_case/list_album.dart index 8e87fbb0..81ba9bae 100644 --- a/lib/use_case/list_album.dart +++ b/lib/use_case/list_album.dart @@ -1,5 +1,6 @@ import 'package:logging/logging.dart'; import 'package:nc_photos/account.dart'; +import 'package:nc_photos/di_container.dart'; import 'package:nc_photos/entity/album.dart'; import 'package:nc_photos/entity/file.dart'; import 'package:nc_photos/exception.dart'; @@ -10,7 +11,11 @@ import 'package:nc_photos/use_case/compat/v25.dart'; import 'package:nc_photos/use_case/ls.dart'; class ListAlbum { - ListAlbum(this.fileRepo, this.albumRepo); + ListAlbum(this._c) : assert(require(_c)); + + static bool require(DiContainer c) => + DiContainer.has(c, DiType.albumRepo) && + DiContainer.has(c, DiType.fileRepo); /// List all albums associated with [account] /// @@ -22,7 +27,7 @@ class ListAlbum { yield result; } if (!hasAlbum) { - if (await CompatV15.migrateAlbumFiles(account, fileRepo)) { + if (await CompatV15.migrateAlbumFiles(account, _c.fileRepo)) { // migrated, try again yield* _call(account); } @@ -32,7 +37,7 @@ class ListAlbum { Stream _call(Account account) async* { List ls; try { - ls = await Ls(fileRepo)( + ls = await Ls(_c.fileRepo)( account, File( path: remote_storage_util.getRemoteAlbumsDir(account), @@ -51,16 +56,16 @@ class ListAlbum { var f = albumFiles[i]; try { if (CompatV25.isAlbumFileNeedMigration(f)) { - f = await CompatV25.migrateAlbumFile(fileRepo, account, f); + f = await CompatV25.migrateAlbumFile(_c, account, f); } albumFiles[i] = f; - yield await albumRepo.get(account, f); + yield await _c.albumRepo.get(account, f); } catch (e, stackTrace) { yield ExceptionEvent(e, stackTrace); } } try { - albumRepo.cleanUp( + _c.albumRepo.cleanUp( account, remote_storage_util.getRemoteAlbumsDir(account), albumFiles); } catch (e, stacktrace) { // not important, log and ignore @@ -68,8 +73,7 @@ class ListAlbum { } } - final FileRepo fileRepo; - final AlbumRepo albumRepo; + final DiContainer _c; static final _log = Logger("use_case.list_album.ListAlbum"); } diff --git a/lib/use_case/list_share.dart b/lib/use_case/list_share.dart index 2f1e427d..d40f1bda 100644 --- a/lib/use_case/list_share.dart +++ b/lib/use_case/list_share.dart @@ -9,10 +9,11 @@ import 'package:nc_photos/use_case/find_file.dart'; /// List all shares from a given file class ListShare { - ListShare(this._c) : assert(require(_c)); + ListShare(this._c) + : assert(require(_c)), + assert(FindFile.require(_c)); - static bool require(DiContainer c) => - DiContainer.has(c, DiType.shareRepo) && DiContainer.has(c, DiType.appDb); + static bool require(DiContainer c) => DiContainer.has(c, DiType.shareRepo); Future> call( Account account, @@ -21,7 +22,7 @@ class ListShare { }) async { try { if (file_util.getUserDirName(file) != account.username) { - file = await FindFile(_c.appDb)(account, file.fileId!); + file = await FindFile(_c)(account, file.fileId!); } } catch (_) { // file not found diff --git a/lib/use_case/list_share_with_me.dart b/lib/use_case/list_share_with_me.dart index bd716b0f..1b43f275 100644 --- a/lib/use_case/list_share_with_me.dart +++ b/lib/use_case/list_share_with_me.dart @@ -1,13 +1,16 @@ import 'package:nc_photos/account.dart'; +import 'package:nc_photos/di_container.dart'; import 'package:nc_photos/entity/file.dart'; import 'package:nc_photos/entity/share.dart'; /// List all shares by other users from a given file class ListShareWithMe { - ListShareWithMe(this.shareRepo); + ListShareWithMe(this._c) : assert(require(_c)); + + static bool require(DiContainer c) => DiContainer.has(c, DiType.shareRepo); Future> call(Account account, File file) => - shareRepo.reverseList(account, file); + _c.shareRepo.reverseList(account, file); - final ShareRepo shareRepo; + final DiContainer _c; } diff --git a/lib/use_case/ls_single_file.dart b/lib/use_case/ls_single_file.dart index 457c7123..8c5f938a 100644 --- a/lib/use_case/ls_single_file.dart +++ b/lib/use_case/ls_single_file.dart @@ -1,11 +1,14 @@ import 'package:nc_photos/account.dart'; +import 'package:nc_photos/di_container.dart'; import 'package:nc_photos/entity/file.dart'; class LsSingleFile { - LsSingleFile(this.fileRepo); + LsSingleFile(this._c) : assert(require(_c)); + + static bool require(DiContainer c) => DiContainer.has(c, DiType.fileRepo); Future call(Account account, String path) => - fileRepo.listSingle(account, File(path: path)); + _c.fileRepo.listSingle(account, File(path: path)); - final FileRepo fileRepo; + final DiContainer _c; } diff --git a/lib/use_case/move.dart b/lib/use_case/move.dart index 4d6bf9f1..f00c62b7 100644 --- a/lib/use_case/move.dart +++ b/lib/use_case/move.dart @@ -2,6 +2,7 @@ import 'package:event_bus/event_bus.dart'; import 'package:kiwi/kiwi.dart'; import 'package:logging/logging.dart'; import 'package:nc_photos/account.dart'; +import 'package:nc_photos/di_container.dart'; import 'package:nc_photos/entity/file.dart'; import 'package:nc_photos/entity/file_util.dart' as file_util; import 'package:nc_photos/event/event.dart'; @@ -10,7 +11,9 @@ import 'package:nc_photos/use_case/create_dir.dart'; import 'package:path/path.dart' as path; class Move { - Move(this.fileRepo); + Move(this._c) : assert(require(_c)); + + static bool require(DiContainer c) => DiContainer.has(c, DiType.fileRepo); /// Move a file from its original location to [destination] Future call( @@ -44,15 +47,16 @@ class Move { _log.info("[call] Retry with: '$to'"); } try { - await fileRepo.move(account, file, to, shouldOverwrite: shouldOverwrite); + await _c.fileRepo + .move(account, file, to, shouldOverwrite: shouldOverwrite); } catch (e) { if (e is ApiException) { if (e.response.statusCode == 409 && shouldCreateMissingDir) { // no dir _log.info("[call] Auto creating parent dirs"); - await CreateDir(fileRepo)(account, path.dirname(to)); - await fileRepo.move(account, file, to, - shouldOverwrite: shouldOverwrite); + await CreateDir(_c.fileRepo)(account, path.dirname(to)); + await _c.fileRepo + .move(account, file, to, shouldOverwrite: shouldOverwrite); } else if (e.response.statusCode == 412 && shouldRenameOnOverwrite) { return _doWork( account, @@ -84,7 +88,7 @@ class Move { return "${path.dirname(destination)}/$newName"; } - final FileRepo fileRepo; + final DiContainer _c; static final _log = Logger("use_case.move.Move"); } diff --git a/lib/use_case/remove.dart b/lib/use_case/remove.dart index 7fe105c9..b75e458e 100644 --- a/lib/use_case/remove.dart +++ b/lib/use_case/remove.dart @@ -19,14 +19,13 @@ import 'package:nc_photos/use_case/remove_share.dart'; class Remove { Remove(this._c) : assert(require(_c)), + assert(ListAlbum.require(_c)), assert(ListShare.require(_c)), assert(RemoveFromAlbum.require(_c)); static bool require(DiContainer c) => - DiContainer.has(c, DiType.albumRepo) && DiContainer.has(c, DiType.fileRepo) && - DiContainer.has(c, DiType.shareRepo) && - DiContainer.has(c, DiType.appDb); + DiContainer.has(c, DiType.shareRepo); /// Remove files Future call( @@ -55,7 +54,7 @@ class Remove { } Future _cleanUpAlbums(Account account, List removes) async { - final albums = await ListAlbum(_c.fileRepo, _c.albumRepo)(account) + final albums = await ListAlbum(_c)(account) .where((event) => event is Album) .cast() .toList(); diff --git a/lib/use_case/restore_trashbin.dart b/lib/use_case/restore_trashbin.dart index 44e36494..ef99b4ef 100644 --- a/lib/use_case/restore_trashbin.dart +++ b/lib/use_case/restore_trashbin.dart @@ -1,15 +1,20 @@ import 'package:event_bus/event_bus.dart'; import 'package:kiwi/kiwi.dart'; import 'package:nc_photos/account.dart'; +import 'package:nc_photos/di_container.dart'; import 'package:nc_photos/entity/file.dart'; import 'package:nc_photos/event/event.dart'; import 'package:nc_photos/use_case/move.dart'; class RestoreTrashbin { - RestoreTrashbin(this.fileRepo); + RestoreTrashbin(this._c) + : assert(require(_c)), + assert(Move.require(_c)); + + static bool require(DiContainer c) => true; Future call(Account account, File file) async { - await Move(fileRepo)( + await Move(_c)( account, file, "remote.php/dav/trashbin/${account.username}/restore/${file.filename}", @@ -20,5 +25,5 @@ class RestoreTrashbin { .fire(FileTrashbinRestoredEvent(account, file)); } - final FileRepo fileRepo; + final DiContainer _c; } diff --git a/lib/use_case/unimport_shared_album.dart b/lib/use_case/unimport_shared_album.dart index 5b041fbf..dfe588ec 100644 --- a/lib/use_case/unimport_shared_album.dart +++ b/lib/use_case/unimport_shared_album.dart @@ -1,4 +1,5 @@ import 'package:nc_photos/account.dart'; +import 'package:nc_photos/di_container.dart'; import 'package:nc_photos/entity/album.dart'; import 'package:nc_photos/entity/file.dart'; import 'package:nc_photos/remote_storage_util.dart' as remote_storage_util; @@ -6,12 +7,16 @@ import 'package:nc_photos/use_case/move.dart'; /// Unimport a shared album from the library class UnimportSharedAlbum { - const UnimportSharedAlbum(this.fileRepo); + UnimportSharedAlbum(this._c) + : assert(require(_c)), + assert(Move.require(_c)); + + static bool require(DiContainer c) => true; Future call(Account account, Album album) async { final destination = "${remote_storage_util.getRemotePendingSharedAlbumsDir(account)}/${album.albumFile!.filename}"; - await Move(fileRepo)( + await Move(_c)( account, album.albumFile!, destination, @@ -19,5 +24,5 @@ class UnimportSharedAlbum { ); } - final FileRepo fileRepo; + final DiContainer _c; } diff --git a/lib/use_case/unshare_file_from_album.dart b/lib/use_case/unshare_file_from_album.dart index abd2fca1..c060e05b 100644 --- a/lib/use_case/unshare_file_from_album.dart +++ b/lib/use_case/unshare_file_from_album.dart @@ -15,12 +15,10 @@ import 'package:nc_photos/use_case/remove_share.dart'; class UnshareFileFromAlbum { UnshareFileFromAlbum(this._c) : assert(require(_c)), + assert(ListAlbum.require(_c)), assert(ListShare.require(_c)); - static bool require(DiContainer c) => - DiContainer.has(c, DiType.albumRepo) && - DiContainer.has(c, DiType.fileRepo) && - DiContainer.has(c, DiType.shareRepo); + static bool require(DiContainer c) => DiContainer.has(c, DiType.shareRepo); /// Remove file shares created for an album /// @@ -36,7 +34,7 @@ class UnshareFileFromAlbum { _log.info( "[call] Unshare ${files.length} files from album '${album.name}' with ${unshareWith.length} users"); // list albums with shares identical to any element in [unshareWith] - final otherAlbums = await ListAlbum(_c.fileRepo, _c.albumRepo)(account) + final otherAlbums = await ListAlbum(_c)(account) .where((event) => event is Album) .cast() .where((a) => diff --git a/lib/widget/album_browser.dart b/lib/widget/album_browser.dart index 9fa338de..3de06a12 100644 --- a/lib/widget/album_browser.dart +++ b/lib/widget/album_browser.dart @@ -15,7 +15,6 @@ import 'package:nc_photos/entity/album/item.dart'; import 'package:nc_photos/entity/album/provider.dart'; import 'package:nc_photos/entity/album/sort_provider.dart'; import 'package:nc_photos/entity/file.dart'; -import 'package:nc_photos/entity/file/data_source.dart'; import 'package:nc_photos/entity/file_util.dart' as file_util; import 'package:nc_photos/event/event.dart'; import 'package:nc_photos/exception_util.dart' as exception_util; @@ -185,9 +184,8 @@ class _AlbumBrowserState extends State var album = await albumRepo.get(widget.account, widget.album.albumFile!); if (widget.album.shares?.isNotEmpty == true) { try { - final fileRepo = FileRepo(FileCachedDataSource(AppDb())); - final file = - await LsSingleFile(fileRepo)(widget.account, album.albumFile!.path); + final file = await LsSingleFile(KiwiContainer().resolve())( + widget.account, album.albumFile!.path); if (file.etag != album.albumFile!.etag) { _log.info("[_initAlbum] Album modified in remote, forcing download"); album = await albumRepo.get(widget.account, File(path: file.path)); diff --git a/lib/widget/album_browser_mixin.dart b/lib/widget/album_browser_mixin.dart index 75908bd3..92717cc4 100644 --- a/lib/widget/album_browser_mixin.dart +++ b/lib/widget/album_browser_mixin.dart @@ -1,16 +1,16 @@ import 'package:flutter/foundation.dart'; import 'package:flutter/material.dart'; import 'package:flutter/widgets.dart'; +import 'package:kiwi/kiwi.dart'; import 'package:logging/logging.dart'; import 'package:nc_photos/account.dart'; import 'package:nc_photos/api/api_util.dart' as api_util; import 'package:nc_photos/app_db.dart'; import 'package:nc_photos/app_localizations.dart'; import 'package:nc_photos/debug_util.dart'; +import 'package:nc_photos/di_container.dart'; import 'package:nc_photos/entity/album.dart'; import 'package:nc_photos/entity/album/cover_provider.dart'; -import 'package:nc_photos/entity/file.dart'; -import 'package:nc_photos/entity/file/data_source.dart'; import 'package:nc_photos/k.dart' as k; import 'package:nc_photos/notified_action.dart'; import 'package:nc_photos/pref.dart'; @@ -236,10 +236,8 @@ mixin AlbumBrowserMixin try { await NotifiedAction( () async { - final fileRepo = FileRepo(FileCachedDataSource(AppDb())); - final albumRepo = AlbumRepo(AlbumCachedDataSource(AppDb())); - newAlbum = await ImportPendingSharedAlbum(fileRepo, albumRepo)( - account, album); + newAlbum = await ImportPendingSharedAlbum( + KiwiContainer().resolve())(account, album); }, L10n.global().addToCollectionProcessingNotification(album.name), L10n.global().addToCollectionSuccessNotification(album.name), diff --git a/lib/widget/album_importer.dart b/lib/widget/album_importer.dart index 529d29a7..e16b2c4d 100644 --- a/lib/widget/album_importer.dart +++ b/lib/widget/album_importer.dart @@ -1,11 +1,13 @@ import 'package:flutter/material.dart'; import 'package:flutter/widgets.dart'; import 'package:flutter_bloc/flutter_bloc.dart'; +import 'package:kiwi/kiwi.dart'; import 'package:logging/logging.dart'; import 'package:nc_photos/account.dart'; import 'package:nc_photos/app_db.dart'; import 'package:nc_photos/app_localizations.dart'; import 'package:nc_photos/bloc/list_importable_album.dart'; +import 'package:nc_photos/di_container.dart'; import 'package:nc_photos/entity/album.dart'; import 'package:nc_photos/entity/album/cover_provider.dart'; import 'package:nc_photos/entity/album/provider.dart'; @@ -79,7 +81,7 @@ class _AlbumImporterState extends State { void _initBloc() { _log.info("[_initBloc] Initialize bloc"); - _bloc = ListImportableAlbumBloc(); + _bloc = ListImportableAlbumBloc(KiwiContainer().resolve()); _bloc.add(ListImportableAlbumBlocQuery( widget.account, widget.account.roots diff --git a/lib/widget/album_picker_dialog.dart b/lib/widget/album_picker_dialog.dart index 1aa2d81f..1c7853d0 100644 --- a/lib/widget/album_picker_dialog.dart +++ b/lib/widget/album_picker_dialog.dart @@ -1,7 +1,6 @@ import 'package:flutter/material.dart'; import 'package:flutter/widgets.dart'; import 'package:flutter_bloc/flutter_bloc.dart'; -import 'package:kiwi/kiwi.dart'; import 'package:logging/logging.dart'; import 'package:nc_photos/account.dart'; import 'package:nc_photos/app_localizations.dart'; @@ -48,21 +47,6 @@ class _AlbumPickerDialogState extends State { } void _initBloc() { - ListAlbumBloc bloc; - final blocId = - "${widget.account.scheme}://${widget.account.username}@${widget.account.address}"; - try { - _log.fine("[_initBloc] Resolving bloc for '$blocId'"); - bloc = KiwiContainer().resolve("ListAlbumBloc($blocId)"); - } catch (_) { - // no created instance for this account, make a new one - _log.info("[_initBloc] New bloc instance for account: ${widget.account}"); - bloc = ListAlbumBloc(); - KiwiContainer().registerInstance(bloc, - name: "ListAlbumBloc($blocId)"); - } - - _bloc = bloc; if (_bloc.state is ListAlbumBlocInit) { _log.info("[_initBloc] Initialize bloc"); _reqQuery(); @@ -171,7 +155,7 @@ class _AlbumPickerDialogState extends State { _bloc.add(ListAlbumBlocQuery(widget.account)); } - late ListAlbumBloc _bloc; + late final _bloc = ListAlbumBloc.of(widget.account); final _items = []; diff --git a/lib/widget/album_search_delegate.dart b/lib/widget/album_search_delegate.dart index f9f8df68..fb35e10b 100644 --- a/lib/widget/album_search_delegate.dart +++ b/lib/widget/album_search_delegate.dart @@ -1,15 +1,14 @@ import 'package:flutter/material.dart'; import 'package:flutter_bloc/flutter_bloc.dart'; import 'package:flutter_staggered_grid_view/flutter_staggered_grid_view.dart'; +import 'package:kiwi/kiwi.dart'; import 'package:nc_photos/account.dart'; -import 'package:nc_photos/app_db.dart'; import 'package:nc_photos/app_localizations.dart'; import 'package:nc_photos/bloc/album_search.dart'; import 'package:nc_photos/bloc/search_suggestion.dart'; import 'package:nc_photos/ci_string.dart'; +import 'package:nc_photos/di_container.dart'; import 'package:nc_photos/entity/album.dart'; -import 'package:nc_photos/entity/file.dart'; -import 'package:nc_photos/entity/file/data_source.dart'; import 'package:nc_photos/theme.dart'; import 'package:nc_photos/use_case/list_album.dart'; import 'package:nc_photos/widget/builder/album_grid_item_builder.dart'; @@ -22,9 +21,9 @@ class AlbumSearchDelegate extends SearchDelegate { : super( searchFieldLabel: L10n.global().albumSearchTextFieldHint, ) { - final fileRepo = FileRepo(FileCachedDataSource(AppDb())); - final albumRepo = AlbumRepo(AlbumCachedDataSource(AppDb())); - ListAlbum(fileRepo, albumRepo)(account).toList().then((value) { + ListAlbum(KiwiContainer().resolve())(account) + .toList() + .then((value) { final albums = value.whereType().toList(); _searchBloc.add(AlbumSearchBlocUpdateItemsEvent(albums)); _suggestionBloc.add(SearchSuggestionBlocUpdateItemsEvent(albums)); diff --git a/lib/widget/home.dart b/lib/widget/home.dart index f720fe51..073b13b5 100644 --- a/lib/widget/home.dart +++ b/lib/widget/home.dart @@ -1,12 +1,15 @@ import 'package:flutter/material.dart'; import 'package:flutter/widgets.dart'; +import 'package:kiwi/kiwi.dart'; import 'package:logging/logging.dart'; import 'package:nc_photos/account.dart'; import 'package:nc_photos/app_localizations.dart'; +import 'package:nc_photos/di_container.dart'; import 'package:nc_photos/entity/album.dart'; import 'package:nc_photos/entity/file.dart'; import 'package:nc_photos/entity/file/data_source.dart'; import 'package:nc_photos/k.dart' as k; +import 'package:nc_photos/or_null.dart'; import 'package:nc_photos/pref.dart'; import 'package:nc_photos/theme.dart'; import 'package:nc_photos/use_case/import_potential_shared_album.dart'; @@ -126,11 +129,13 @@ class _HomeState extends State { } Future> _importPotentialSharedAlbum() async { - const fileRepo = FileRepo(FileWebdavDataSource()); - // don't want the potential albums to be cached at this moment - final albumRepo = AlbumRepo(AlbumRemoteDataSource()); + final c = KiwiContainer().resolve().copyWith( + // don't want the potential albums to be cached at this moment + fileRepo: OrNull(const FileRepo(FileWebdavDataSource())), + albumRepo: OrNull(AlbumRepo(AlbumRemoteDataSource())), + ); try { - return await ImportPotentialSharedAlbum(fileRepo, albumRepo)( + return await ImportPotentialSharedAlbum(c)( widget.account, AccountPref.of(widget.account)); } catch (e, stacktrace) { _log.shout( diff --git a/lib/widget/home_albums.dart b/lib/widget/home_albums.dart index 6b20bedf..2ef9666b 100644 --- a/lib/widget/home_albums.dart +++ b/lib/widget/home_albums.dart @@ -6,14 +6,12 @@ import 'package:flutter_staggered_grid_view/flutter_staggered_grid_view.dart'; import 'package:kiwi/kiwi.dart'; import 'package:logging/logging.dart'; import 'package:nc_photos/account.dart'; -import 'package:nc_photos/app_db.dart'; import 'package:nc_photos/app_localizations.dart'; import 'package:nc_photos/bloc/list_album.dart'; import 'package:nc_photos/di_container.dart'; import 'package:nc_photos/entity/album.dart'; import 'package:nc_photos/entity/album/provider.dart'; import 'package:nc_photos/entity/file.dart'; -import 'package:nc_photos/entity/file/data_source.dart'; import 'package:nc_photos/event/event.dart'; import 'package:nc_photos/exception_util.dart' as exception_util; import 'package:nc_photos/iterable_extension.dart'; @@ -83,21 +81,6 @@ class _HomeAlbumsState extends State } void _initBloc() { - ListAlbumBloc bloc; - final blocId = - "${widget.account.scheme}://${widget.account.username}@${widget.account.address}"; - try { - _log.fine("[_initBloc] Resolving bloc for '$blocId'"); - bloc = KiwiContainer().resolve("ListAlbumBloc($blocId)"); - } catch (e) { - // no created instance for this account, make a new one - _log.info("[_initBloc] New bloc instance for account: ${widget.account}"); - bloc = ListAlbumBloc(); - KiwiContainer().registerInstance(bloc, - name: "ListAlbumBloc($blocId)"); - } - - _bloc = bloc; if (_bloc.state is ListAlbumBlocInit) { _log.info("[_initBloc] Initialize bloc"); _reqQuery(); @@ -406,7 +389,6 @@ class _HomeAlbumsState extends State setState(() { clearSelectedItems(); }); - final fileRepo = FileRepo(FileCachedDataSource(AppDb())); final failures = []; for (final a in selected) { try { @@ -416,7 +398,8 @@ class _HomeAlbumsState extends State widget.account, a); } else { // remove shared albums from collection - await UnimportSharedAlbum(fileRepo)(widget.account, a); + await UnimportSharedAlbum(KiwiContainer().resolve())( + widget.account, a); } } catch (e, stackTrace) { _log.shout( @@ -512,7 +495,7 @@ class _HomeAlbumsState extends State } } - late ListAlbumBloc _bloc; + late final _bloc = ListAlbumBloc.of(widget.account); late final _accountPrefUpdatedEventListener = AppEventListener(_onAccountPrefUpdatedEvent); diff --git a/lib/widget/root_picker.dart b/lib/widget/root_picker.dart index f36f04ca..d1995c6b 100644 --- a/lib/widget/root_picker.dart +++ b/lib/widget/root_picker.dart @@ -2,13 +2,13 @@ import 'package:flutter/foundation.dart'; import 'package:flutter/material.dart'; import 'package:flutter/scheduler.dart'; import 'package:flutter/widgets.dart'; +import 'package:kiwi/kiwi.dart'; import 'package:logging/logging.dart'; import 'package:nc_photos/account.dart'; import 'package:nc_photos/api/api_util.dart' as api_util; -import 'package:nc_photos/app_db.dart'; import 'package:nc_photos/app_localizations.dart'; +import 'package:nc_photos/di_container.dart'; import 'package:nc_photos/entity/file.dart'; -import 'package:nc_photos/entity/file/data_source.dart'; import 'package:nc_photos/entity/file_util.dart' as file_util; import 'package:nc_photos/exception_util.dart' as exception_util; import 'package:nc_photos/k.dart' as k; @@ -58,12 +58,11 @@ class _RootPickerState extends State { void _initAccount() async { try { - final fileRepo = FileRepo(FileCachedDataSource(AppDb())); final files = []; for (final r in widget.account.roots) { if (r.isNotEmpty) { _ensureInitDialog(); - files.add(await LsSingleFile(fileRepo)( + files.add(await LsSingleFile(KiwiContainer().resolve())( widget.account, file_util.unstripPath(widget.account, r))); } } diff --git a/lib/widget/sharing_browser.dart b/lib/widget/sharing_browser.dart index 709bc46e..66bde6ab 100644 --- a/lib/widget/sharing_browser.dart +++ b/lib/widget/sharing_browser.dart @@ -3,6 +3,7 @@ import 'package:flutter/material.dart'; import 'package:flutter/widgets.dart'; import 'package:flutter_bloc/flutter_bloc.dart'; import 'package:intl/intl.dart'; +import 'package:kiwi/kiwi.dart'; import 'package:logging/logging.dart'; import 'package:nc_photos/account.dart'; import 'package:nc_photos/api/api.dart'; @@ -10,6 +11,7 @@ import 'package:nc_photos/api/api_util.dart' as api_util; import 'package:nc_photos/app_localizations.dart'; import 'package:nc_photos/bloc/list_sharing.dart'; import 'package:nc_photos/cache_manager_util.dart'; +import 'package:nc_photos/di_container.dart'; import 'package:nc_photos/entity/album.dart'; import 'package:nc_photos/entity/file.dart'; import 'package:nc_photos/entity/file/data_source.dart'; @@ -18,6 +20,7 @@ import 'package:nc_photos/exception_util.dart' as exception_util; import 'package:nc_photos/iterable_extension.dart'; import 'package:nc_photos/k.dart' as k; import 'package:nc_photos/object_extension.dart'; +import 'package:nc_photos/or_null.dart'; import 'package:nc_photos/pref.dart'; import 'package:nc_photos/snack_bar_manager.dart'; import 'package:nc_photos/theme.dart'; @@ -325,11 +328,13 @@ class _SharingBrowserState extends State { } Future> _importPotentialSharedAlbum() async { - const fileRepo = FileRepo(FileWebdavDataSource()); - // don't want the potential albums to be cached at this moment - final albumRepo = AlbumRepo(AlbumRemoteDataSource()); + final c = KiwiContainer().resolve().copyWith( + // don't want the potential albums to be cached at this moment + fileRepo: OrNull(const FileRepo(FileWebdavDataSource())), + albumRepo: OrNull(AlbumRepo(AlbumRemoteDataSource())), + ); try { - return await ImportPotentialSharedAlbum(fileRepo, albumRepo)( + return await ImportPotentialSharedAlbum(c)( widget.account, AccountPref.of(widget.account)); } catch (e, stackTrace) { _log.shout( diff --git a/lib/widget/trashbin_browser.dart b/lib/widget/trashbin_browser.dart index fbcc516c..519c8987 100644 --- a/lib/widget/trashbin_browser.dart +++ b/lib/widget/trashbin_browser.dart @@ -3,14 +3,15 @@ import 'package:flutter/material.dart'; import 'package:flutter/widgets.dart'; import 'package:flutter_bloc/flutter_bloc.dart'; import 'package:flutter_staggered_grid_view/flutter_staggered_grid_view.dart'; +import 'package:kiwi/kiwi.dart'; import 'package:logging/logging.dart'; import 'package:nc_photos/account.dart'; import 'package:nc_photos/api/api_util.dart' as api_util; import 'package:nc_photos/app_localizations.dart'; import 'package:nc_photos/bloc/ls_trashbin.dart'; import 'package:nc_photos/debug_util.dart'; +import 'package:nc_photos/di_container.dart'; import 'package:nc_photos/entity/file.dart'; -import 'package:nc_photos/entity/file/data_source.dart'; import 'package:nc_photos/entity/file_util.dart' as file_util; import 'package:nc_photos/exception_util.dart' as exception_util; import 'package:nc_photos/iterable_extension.dart'; @@ -291,11 +292,11 @@ class _TrashbinBrowserState extends State setState(() { clearSelectedItems(); }); - const fileRepo = FileRepo(FileWebdavDataSource()); final failures = []; for (final f in selectedFiles) { try { - await RestoreTrashbin(fileRepo)(widget.account, f); + await RestoreTrashbin(KiwiContainer().resolve())( + widget.account, f); } catch (e, stacktrace) { _log.shout( "[_onSelectionAppBarRestorePressed] Failed while restoring file: ${logFilename(f.path)}", diff --git a/lib/widget/trashbin_viewer.dart b/lib/widget/trashbin_viewer.dart index 7ef356ad..f66a19b6 100644 --- a/lib/widget/trashbin_viewer.dart +++ b/lib/widget/trashbin_viewer.dart @@ -1,13 +1,13 @@ import 'package:flutter/foundation.dart'; import 'package:flutter/material.dart'; import 'package:flutter/widgets.dart'; +import 'package:kiwi/kiwi.dart'; import 'package:logging/logging.dart'; import 'package:nc_photos/account.dart'; -import 'package:nc_photos/app_db.dart'; import 'package:nc_photos/app_localizations.dart'; import 'package:nc_photos/debug_util.dart'; +import 'package:nc_photos/di_container.dart'; import 'package:nc_photos/entity/file.dart'; -import 'package:nc_photos/entity/file/data_source.dart'; import 'package:nc_photos/entity/file_util.dart' as file_util; import 'package:nc_photos/exception_util.dart' as exception_util; import 'package:nc_photos/k.dart' as k; @@ -166,9 +166,9 @@ class _TrashbinViewerState extends State { controller?.closed.whenComplete(() { controller = null; }); - final fileRepo = FileRepo(FileCachedDataSource(AppDb())); try { - await RestoreTrashbin(fileRepo)(widget.account, file); + await RestoreTrashbin(KiwiContainer().resolve())( + widget.account, file); controller?.close(); SnackBarManager().showSnackBar(SnackBar( content: Text(L10n.global().restoreSuccessNotification), diff --git a/test/use_case/find_file_test.dart b/test/use_case/find_file_test.dart index a56060b3..1bddebcc 100644 --- a/test/use_case/find_file_test.dart +++ b/test/use_case/find_file_test.dart @@ -1,3 +1,5 @@ +import 'package:nc_photos/di_container.dart'; +import 'package:nc_photos/object_extension.dart'; import 'package:nc_photos/use_case/find_file.dart'; import 'package:test/test.dart'; @@ -5,7 +7,6 @@ import '../mock_type.dart'; import '../test_util.dart' as util; void main() { - util.initLog(); group("FindFile", () { test("file", _findFile); test("missing file", _findMissingFile); @@ -21,10 +22,13 @@ Future _findFile() async { ..addJpeg("admin/test1.jpg") ..addJpeg("admin/test2.jpg")) .build(); - final appDb = MockAppDb(); - await util.fillAppDb(appDb, account, files); + final c = DiContainer( + appDb: await MockAppDb().applyFuture((obj) async { + await util.fillAppDb(obj, account, files); + }), + ); - expect(await FindFile(appDb)(account, 1), files[1]); + expect(await FindFile(c)(account, 1), files[1]); } /// Find a file not existing in app db @@ -33,8 +37,11 @@ Future _findFile() async { Future _findMissingFile() async { final account = util.buildAccount(); final files = (util.FilesBuilder()..addJpeg("admin/test1.jpg")).build(); - final appDb = MockAppDb(); - await util.fillAppDb(appDb, account, files); + final c = DiContainer( + appDb: await MockAppDb().applyFuture((obj) async { + await util.fillAppDb(obj, account, files); + }), + ); - expect(() => FindFile(appDb)(account, 1), throwsStateError); + expect(() => FindFile(c)(account, 1), throwsStateError); }