mirror of
https://gitlab.com/nkming2/nc-photos.git
synced 2025-02-25 02:48:54 +01:00
Fix files also shared in other albums being unshared
This commit is contained in:
parent
1586193c83
commit
7c0c4db045
2 changed files with 69 additions and 10 deletions
|
@ -28,14 +28,14 @@ class UnshareFileFromAlbum {
|
||||||
_log.info(
|
_log.info(
|
||||||
"[call] Unshare ${files.length} files from album '${album.name}' with ${unshareWith.length} users");
|
"[call] Unshare ${files.length} files from album '${album.name}' with ${unshareWith.length} users");
|
||||||
// list albums with shares identical to any element in [unshareWith]
|
// list albums with shares identical to any element in [unshareWith]
|
||||||
final otherAlbums = (await ListAlbum(fileRepo, albumRepo)(account)
|
final otherAlbums = await ListAlbum(fileRepo, albumRepo)(account)
|
||||||
.where((event) => event is Album)
|
.where((event) => event is Album)
|
||||||
.cast<Album>()
|
.cast<Album>()
|
||||||
.where((album) =>
|
.where((a) =>
|
||||||
!album.albumFile!.compareServerIdentity(album.albumFile!) &&
|
!a.albumFile!.compareServerIdentity(album.albumFile!) &&
|
||||||
album.provider is AlbumStaticProvider &&
|
a.provider is AlbumStaticProvider &&
|
||||||
album.shares?.any((s) => unshareWith.contains(s.userId)) == true)
|
a.shares?.any((s) => unshareWith.contains(s.userId)) == true)
|
||||||
.toList());
|
.toList();
|
||||||
|
|
||||||
// look for shares that are exclusive to this album
|
// look for shares that are exclusive to this album
|
||||||
final exclusiveShares = <Share>[];
|
final exclusiveShares = <Share>[];
|
||||||
|
@ -49,10 +49,12 @@ class UnshareFileFromAlbum {
|
||||||
e, stackTrace);
|
e, stackTrace);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
_log.fine("[call] Pre-filter shares: $exclusiveShares");
|
||||||
for (final a in otherAlbums) {
|
for (final a in otherAlbums) {
|
||||||
// check if the album is shared with the same users
|
// check if the album is shared with the same users
|
||||||
if (!a.shares!
|
final sharesOfInterest =
|
||||||
.any((as) => exclusiveShares.any((s) => s.shareWith == as.userId))) {
|
a.shares?.where((as) => unshareWith.contains(as.userId)).toList();
|
||||||
|
if (sharesOfInterest == null || sharesOfInterest.isEmpty) {
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
final albumFiles = AlbumStaticProvider.of(a)
|
final albumFiles = AlbumStaticProvider.of(a)
|
||||||
|
@ -60,9 +62,12 @@ class UnshareFileFromAlbum {
|
||||||
.whereType<AlbumFileItem>()
|
.whereType<AlbumFileItem>()
|
||||||
.map((e) => e.file)
|
.map((e) => e.file)
|
||||||
.toList();
|
.toList();
|
||||||
exclusiveShares.removeWhere(
|
// remove files shared as part of this other shared album
|
||||||
(s) => albumFiles.any((element) => element.fileId == s.itemSource));
|
exclusiveShares.removeWhere((s) =>
|
||||||
|
sharesOfInterest.any((i) => i.userId == s.shareWith) &&
|
||||||
|
albumFiles.any((f) => f.fileId == s.itemSource));
|
||||||
}
|
}
|
||||||
|
_log.fine("[call] Post-filter shares: $exclusiveShares");
|
||||||
|
|
||||||
// unshare them
|
// unshare them
|
||||||
await _unshare(account, exclusiveShares, onUnshareFileFailed);
|
await _unshare(account, exclusiveShares, onUnshareFileFailed);
|
||||||
|
|
|
@ -27,6 +27,8 @@ void main() {
|
||||||
test("file w/ shares managed by others",
|
test("file w/ shares managed by others",
|
||||||
_removeFromSharedAlbumOwnedWithOtherShare);
|
_removeFromSharedAlbumOwnedWithOtherShare);
|
||||||
test("file w/ extra share", _removeFromSharedAlbumOwnedLeaveExtraShare);
|
test("file w/ extra share", _removeFromSharedAlbumOwnedLeaveExtraShare);
|
||||||
|
test("file w/ share in other album",
|
||||||
|
_removeFromSharedAlbumOwnedFileInOtherAlbum);
|
||||||
});
|
});
|
||||||
group("shared album (not owned)", () {
|
group("shared album (not owned)", () {
|
||||||
test("file", _removeFromSharedAlbumNotOwned);
|
test("file", _removeFromSharedAlbumNotOwned);
|
||||||
|
@ -396,6 +398,58 @@ Future<void> _removeFromSharedAlbumOwnedLeaveExtraShare() async {
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Remove a file from a shared album (admin -> user1, user2) where the file is
|
||||||
|
/// also shared in other album (admin -> user1)
|
||||||
|
///
|
||||||
|
/// Expect: share (admin -> user2) for the file deleted;
|
||||||
|
/// share (admin -> user1) for the file unchanged
|
||||||
|
Future<void> _removeFromSharedAlbumOwnedFileInOtherAlbum() async {
|
||||||
|
final account = util.buildAccount();
|
||||||
|
final pref = Pref.scoped(PrefMemoryProvider({
|
||||||
|
"isLabEnableSharedAlbum": true,
|
||||||
|
}));
|
||||||
|
final files =
|
||||||
|
(util.FilesBuilder(initialFileId: 2)..addJpeg("admin/test1.jpg")).build();
|
||||||
|
final album1 = (util.AlbumBuilder()
|
||||||
|
..addFileItem(files[0])
|
||||||
|
..addShare("user1")
|
||||||
|
..addShare("user2"))
|
||||||
|
.build();
|
||||||
|
final album2 = (util.AlbumBuilder.ofId(albumId: 1)
|
||||||
|
..addFileItem(files[0])
|
||||||
|
..addShare("user1"))
|
||||||
|
.build();
|
||||||
|
final album1fileItems = util.AlbumBuilder.fileItemsOf(album1);
|
||||||
|
final album1File = album1.albumFile!;
|
||||||
|
final album2File = album2.albumFile!;
|
||||||
|
final appDb = MockAppDb();
|
||||||
|
await appDb.use((db) async {
|
||||||
|
final transaction = db.transaction(AppDb.fileDbStoreName, idbModeReadWrite);
|
||||||
|
final store = transaction.objectStore(AppDb.fileDbStoreName);
|
||||||
|
await store.put(AppDbFileDbEntry.fromFile(account, files[0]).toJson(),
|
||||||
|
AppDbFileDbEntry.toPrimaryKey(account, files[0]));
|
||||||
|
});
|
||||||
|
final albumRepo = MockAlbumMemoryRepo([album1, album2]);
|
||||||
|
final shareRepo = MockShareMemoryRepo([
|
||||||
|
util.buildShare(id: "0", file: album1File, shareWith: "user1"),
|
||||||
|
util.buildShare(id: "1", file: files[0], shareWith: "user1"),
|
||||||
|
util.buildShare(id: "2", file: files[0], shareWith: "user2"),
|
||||||
|
util.buildShare(id: "3", file: album2File, shareWith: "user1"),
|
||||||
|
]);
|
||||||
|
final fileRepo = MockFileMemoryRepo([album1File, album2File, ...files]);
|
||||||
|
|
||||||
|
await RemoveFromAlbum(albumRepo, shareRepo, fileRepo, appDb, pref)(account,
|
||||||
|
albumRepo.findAlbumByPath(album1File.path), [album1fileItems[0]]);
|
||||||
|
expect(
|
||||||
|
shareRepo.shares,
|
||||||
|
[
|
||||||
|
util.buildShare(id: "0", file: album1File, shareWith: "user1"),
|
||||||
|
util.buildShare(id: "1", file: files[0], shareWith: "user1"),
|
||||||
|
util.buildShare(id: "3", file: album2File, shareWith: "user1"),
|
||||||
|
],
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
/// Remove a file from a shared album (user1 -> admin, user2)
|
/// Remove a file from a shared album (user1 -> admin, user2)
|
||||||
///
|
///
|
||||||
/// Expect: shares (admin -> user1, user2) for the file deleted
|
/// Expect: shares (admin -> user1, user2) for the file deleted
|
||||||
|
|
Loading…
Reference in a new issue