From 9e87d645ab56ad84e80b2f9614f149c004f1de6b Mon Sep 17 00:00:00 2001 From: kim Date: Thu, 8 Aug 2024 18:04:30 +0200 Subject: [PATCH 01/10] feat: update for item login --- cypress/support/server.ts | 7 +- package.json | 6 +- src/components/common/Chatbox.tsx | 2 +- src/components/item/ItemMemberships.tsx | 6 +- .../item/sharing/ConfirmMembership.tsx | 4 +- .../item/sharing/CreateItemMembershipForm.tsx | 4 +- .../csvImport/DisplayInvitationSummary.tsx | 13 +- src/utils/item.test.ts | 33 ++- src/utils/membership.ts | 10 +- yarn.lock | 207 ++++-------------- 10 files changed, 95 insertions(+), 197 deletions(-) diff --git a/cypress/support/server.ts b/cypress/support/server.ts index 32619e1c9..205a9754e 100644 --- a/cypress/support/server.ts +++ b/cypress/support/server.ts @@ -1,5 +1,6 @@ import { API_ROUTES } from '@graasp/query-client'; import { + AccountType, App, Category, ChatMention, @@ -649,7 +650,7 @@ export const mockPostManyItemMemberships = ( memberId: string; }) => { const thisM = itemMemberships?.find( - ({ member }) => m.memberId === member.id, + ({ account }) => m.memberId === account.id, ); if (thisM) { result.errors.push({ @@ -1092,7 +1093,7 @@ export const mockGetItemMembershipsForItem = ( // if the defined memberships does not contain currentMember, it should throw const currentMemberHasMembership = memberships?.find( - ({ member }) => member.id === currentMember?.id, + ({ account }) => account.id === currentMember?.id, ); // no membership if (!currentMemberHasMembership && !isCreator) { @@ -1103,7 +1104,7 @@ export const mockGetItemMembershipsForItem = ( result.data[id] = memberships || [ { permission: PermissionLevel.Admin, - member: creator, + account: { ...creator, type: AccountType.Individual }, item, id: v4(), createdAt: '2021-08-11T12:56:36.834Z', diff --git a/package.json b/package.json index 736518c0c..fce8afd9c 100644 --- a/package.json +++ b/package.json @@ -20,10 +20,10 @@ "@emotion/styled": "11.13.0", "@graasp/chatbox": "3.1.0", "@graasp/map": "1.17.0", - "@graasp/query-client": "3.21.0", - "@graasp/sdk": "4.22.0", + "@graasp/query-client": "github:graasp/graasp-query-client#update-for-item-login", + "@graasp/sdk": "github:graasp/graasp-sdk#568-new-membertype", "@graasp/translations": "1.33.0", - "@graasp/ui": "4.23.0", + "@graasp/ui": "github:graasp/graasp-ui#update-sdk", "@mui/icons-material": "5.16.4", "@mui/lab": "5.0.0-alpha.172", "@mui/material": "5.16.4", diff --git a/src/components/common/Chatbox.tsx b/src/components/common/Chatbox.tsx index 938afe4f5..4e0e861f9 100644 --- a/src/components/common/Chatbox.tsx +++ b/src/components/common/Chatbox.tsx @@ -20,7 +20,7 @@ const Chatbox = ({ item }: Props): JSX.Element | null => { const { data: chatMessages, isLoading: isChatLoading } = useItemChat(item.id); const { data: itemPermissions, isLoading: isLoadingItemPermissions } = useItemMemberships(item.id); - const members = itemPermissions?.map(({ member }) => member); + const members = itemPermissions?.map(({ account }) => account); const { data: currentMember, isLoading: isLoadingCurrentMember } = hooks.useCurrentMember(); const { mutate: sendMessage } = usePostItemChatMessage(); diff --git a/src/components/item/ItemMemberships.tsx b/src/components/item/ItemMemberships.tsx index a0e691e10..0851be6d5 100644 --- a/src/components/item/ItemMemberships.tsx +++ b/src/components/item/ItemMemberships.tsx @@ -48,7 +48,7 @@ const ItemMemberships = ({ id, maxAvatar = 2 }: Props): JSX.Element | null => { aria-label={translateBuilder(BUILDER.SHARED_MEMBERS_LABEL)} > - {filteredMemberships.map(({ member, permission }) => { + {filteredMemberships.map(({ account, permission }) => { const badgeContent = permission === PermissionLevel.Read ? ( @@ -58,7 +58,7 @@ const ItemMemberships = ({ id, maxAvatar = 2 }: Props): JSX.Element | null => { return ( { badgeContent={badgeContent} sx={{ border: 'none' }} > - + ); })} diff --git a/src/components/item/sharing/ConfirmMembership.tsx b/src/components/item/sharing/ConfirmMembership.tsx index 406e999e3..0fb9ec567 100644 --- a/src/components/item/sharing/ConfirmMembership.tsx +++ b/src/components/item/sharing/ConfirmMembership.tsx @@ -56,13 +56,13 @@ const DeleteItemDialog = ({ // incase of deleting the only admin if (isDeletingLastAdmin) { dialogText = translateBuilder(BUILDER.DELETE_LAST_ADMIN_ALERT_MESSAGE); - } else if (member?.id === membershipToDelete?.member?.id) { + } else if (member?.id === membershipToDelete?.account?.id) { // deleting yourself dialogText = translateBuilder(BUILDER.DELETE_OWN_MEMBERSHIP_MESSAGE); } else { // delete other members dialogText = translateBuilder(BUILDER.DELETE_MEMBERSHIP_MESSAGE, { - name: membershipToDelete?.member.name, + name: membershipToDelete?.account.name, permissionLevel: membershipToDelete?.permission, }); } diff --git a/src/components/item/sharing/CreateItemMembershipForm.tsx b/src/components/item/sharing/CreateItemMembershipForm.tsx index 0e6fe2314..5b2dab18c 100644 --- a/src/components/item/sharing/CreateItemMembershipForm.tsx +++ b/src/components/item/sharing/CreateItemMembershipForm.tsx @@ -10,6 +10,7 @@ import { } from '@mui/material'; import { + AccountType, DiscriminatedItem, Invitation, ItemMembership, @@ -74,7 +75,8 @@ const CreateItemMembershipForm = ({ // check mail does not already exist if ( memberships.find( - ({ member: { email: thisEmail } }) => thisEmail === email, + ({ account }) => + account.type === AccountType.Individual && account.email === email, ) ) { return translateBuilder( diff --git a/src/components/item/sharing/csvImport/DisplayInvitationSummary.tsx b/src/components/item/sharing/csvImport/DisplayInvitationSummary.tsx index b0dda37aa..324831193 100644 --- a/src/components/item/sharing/csvImport/DisplayInvitationSummary.tsx +++ b/src/components/item/sharing/csvImport/DisplayInvitationSummary.tsx @@ -1,6 +1,11 @@ import { Alert, AlertTitle, Stack, Typography } from '@mui/material'; -import { Invitation, ItemMembership, PermissionLevel } from '@graasp/sdk'; +import { + AccountType, + Invitation, + ItemMembership, + PermissionLevel, +} from '@graasp/sdk'; import { FAILURE_MESSAGES } from '@graasp/translations'; import { AxiosError } from 'axios'; @@ -80,7 +85,11 @@ const DisplayInvitationSummary = ({ {memberships.map((m) => ( ))} diff --git a/src/utils/item.test.ts b/src/utils/item.test.ts index 5ee6d1a22..96e3a166f 100644 --- a/src/utils/item.test.ts +++ b/src/utils/item.test.ts @@ -1,4 +1,9 @@ -import { DiscriminatedItem, PermissionLevel } from '@graasp/sdk'; +import { + DiscriminatedItem, + ItemMembership, + MemberFactory, + PermissionLevel, +} from '@graasp/sdk'; import { describe, expect, it } from 'vitest'; @@ -111,11 +116,15 @@ describe('item utils', () => { }); it('returns closest permission when only one permission', () => { - const member = { id: '1234', name: 'bob', email: 'bob@graasp.org' }; + const account = MemberFactory({ + id: '1234', + name: 'bob', + email: 'bob@graasp.org', + }); const item = { path: '1234' } as DiscriminatedItem; const membership = { id: 'membership-123', - member, + account, item, permission: PermissionLevel.Read, creator: null, @@ -124,7 +133,7 @@ describe('item utils', () => { }; expect( getHighestPermissionForMemberFromMemberships({ - memberId: member.id, + memberId: account.id, itemPath: item.path, memberships: [membership], }), @@ -132,21 +141,25 @@ describe('item utils', () => { }); it('returns closest permission when multiple permissions', () => { - const member = { id: '1234', name: 'bob', email: 'bob@graasp.org' }; + const account = MemberFactory({ + id: '1234', + name: 'bob', + email: 'bob@graasp.org', + }); const item1 = { path: '1234' } as DiscriminatedItem; const item2 = { path: '1234.5678' } as DiscriminatedItem; - const membership1 = { + const membership1: ItemMembership = { id: 'membership-123', - member, + account, item: item1, permission: PermissionLevel.Read, creator: null, createdAt: new Date().toISOString(), updatedAt: new Date().toISOString(), }; - const membership2 = { + const membership2: ItemMembership = { id: 'membership-123', - member, + account, item: item2, permission: PermissionLevel.Read, creator: null, @@ -155,7 +168,7 @@ describe('item utils', () => { }; expect( getHighestPermissionForMemberFromMemberships({ - memberId: member.id, + memberId: account.id, itemPath: item2.path, memberships: [membership1, membership2], }), diff --git a/src/utils/membership.ts b/src/utils/membership.ts index 1e42add3e..a11c1ce98 100644 --- a/src/utils/membership.ts +++ b/src/utils/membership.ts @@ -10,7 +10,7 @@ export const membershipsWithoutUser = ( memberships: ItemMembership[], userId?: string, ): ItemMembership[] => - memberships?.filter(({ member: { id: memberId } }) => memberId !== userId); + memberships?.filter(({ account: { id: memberId } }) => memberId !== userId); interface PermissionMap { [key: string]: ItemMembership; @@ -20,13 +20,13 @@ export const selectHighestMemberships = ( memberships: ItemMembership[], ): ItemMembership[] => { const permissionMap = memberships.reduce((acc, curr) => { - const { member, permission } = curr; + const { account, permission } = curr; if ( - !acc[member.id] || - PermissionLevelCompare.gt(permission, acc[member.id].permission) + !acc[account.id] || + PermissionLevelCompare.gt(permission, acc[account.id].permission) ) { - acc[member.id] = curr; + acc[account.id] = curr; } return acc; }, {}); diff --git a/yarn.lock b/yarn.lock index 6d540b857..8100c347b 100644 --- a/yarn.lock +++ b/yarn.lock @@ -1857,9 +1857,9 @@ __metadata: languageName: node linkType: hard -"@graasp/query-client@npm:3.21.0": - version: 3.21.0 - resolution: "@graasp/query-client@npm:3.21.0" +"@graasp/query-client@github:graasp/graasp-query-client#update-for-item-login": + version: 3.22.0 + resolution: "@graasp/query-client@https://github.com/graasp/graasp-query-client.git#commit=0efb6ac09f5bd77d0b127c7c29fa9c784a8dd75f" dependencies: "@tanstack/react-query": "npm:4.36.1" "@tanstack/react-query-devtools": "npm:4.36.1" @@ -1869,13 +1869,13 @@ __metadata: "@graasp/sdk": ^4.0.0 "@graasp/translations": "*" react: ^18.0.0 - checksum: 10/801a1e1b45f985f82468b2527adc2cda8b2541aac3549a22fde81dc40387867e9f7c46dee001f77d23f4b6a4de19c0d2ea85b0a2f1499e848c880ece69a34177 + checksum: 10/4441cf9c2cae35fcb166d5eb6e7b5a7a14ebbf6e00fa0b2dc020cc9b8538e4ef2ef04d6d79341bc5847aa1867df16d184b5613b52f6c32d617e6050ab9ec932c languageName: node linkType: hard -"@graasp/sdk@npm:4.22.0": +"@graasp/sdk@github:graasp/graasp-sdk#568-new-membertype": version: 4.22.0 - resolution: "@graasp/sdk@npm:4.22.0" + resolution: "@graasp/sdk@https://github.com/graasp/graasp-sdk.git#commit=a0d7ecefb93de3004c15841706603afa305164e7" dependencies: "@faker-js/faker": "npm:8.4.1" filesize: "npm:10.1.4" @@ -1885,7 +1885,7 @@ __metadata: peerDependencies: date-fns: ^3 uuid: ^9 || ^10.0.0 - checksum: 10/c1e81d401f51a9c22eb4f5bc12057aa3ea249771701c390a11dc7c1609b814d9222926bbb7d9b19f70fda67bccb854f42045d890dd850f71bf4f9f8629fcb799 + checksum: 10/205a6510b0f794d9c4c323b134ef58a55451e8b682e4ecfcacd7c5332d37aa54f0ed5c0e6b0dbb4d4b49648030e61a37ace5da1015a509507af4c5c400c92069 languageName: node linkType: hard @@ -1922,76 +1922,76 @@ __metadata: languageName: node linkType: hard -"@graasp/ui@npm:4.20.0": - version: 4.20.0 - resolution: "@graasp/ui@npm:4.20.0" +"@graasp/ui@github:graasp/graasp-ui#update-sdk": + version: 4.24.0 + resolution: "@graasp/ui@https://github.com/graasp/graasp-ui.git#commit=a3d0fcd9e860de63c469f547c87aaf4d103494be" dependencies: "@ag-grid-community/client-side-row-model": "npm:31.3.2" - "@ag-grid-community/react": "npm:^31.3.1" - "@ag-grid-community/styles": "npm:^31.3.1" - "@storybook/react-vite": "npm:8.1.10" + "@ag-grid-community/react": "npm:^31.3.2" + "@ag-grid-community/styles": "npm:^31.3.2" + "@storybook/react-vite": "npm:8.1.11" http-status-codes: "npm:2.3.0" interweave: "npm:13.1.0" - katex: "npm:0.16.10" + katex: "npm:0.16.11" lodash.truncate: "npm:4.4.2" - lucide-react: "npm:0.395.0" + lucide-react: "npm:0.408.0" react-cookie-consent: "npm:9.0.0" react-dnd: "npm:16.0.1" react-dnd-html5-backend: "npm:16.0.1" react-quill: "npm:2.0.0" react-rnd: "npm:10.4.11" - react-text-mask: "npm:5.5.0" uuid: "npm:10.0.0" - vitest: "npm:1.6.0" + vitest: "npm:2.0.4" peerDependencies: - "@emotion/cache": ~11.10.7 || ~11.11.0 - "@emotion/react": ~11.10.6 || ~11.11.0 - "@emotion/styled": ~11.10.6 || ~11.11.0 + "@emotion/cache": ~11.10.7 || ~11.11.0 || ~11.13.0 + "@emotion/react": ~11.10.6 || ~11.11.0 || ~11.13.0 + "@emotion/styled": ~11.10.6 || ~11.11.0 || ~11.13.0 "@graasp/sdk": ^4.14.0 "@graasp/translations": ^1.23.0 - "@mui/icons-material": ~5.14.0 || ~5.15.0 + "@mui/icons-material": ~5.14.0 || ~5.15.0 || ~5.16.0 "@mui/lab": ~5.0.0-alpha.150 - "@mui/material": ~5.14.0 || ~5.15.0 + "@mui/material": ~5.14.0 || ~5.15.0 || ~5.16.0 i18next: ^22.4.15 || ^23.0.0 react: ^18.0.0 react-dom: ^18.0.0 - react-i18next: ^13.0.0 || ^14.0.0 + react-i18next: ^13.0.0 || ^14.0.0 || ^15.0.0 react-router-dom: ^6.11.0 stylis: ^4.1.3 stylis-plugin-rtl: ^2.1.1 - checksum: 10/2259b603ddffb00187f5684215a9e16e91a192612a84f7807759f385b7121fe198bdb20ae17fc978b1996a0b921dd2381283f22a3a84ad40c3b8a0031efdaf05 + checksum: 10/2e832ce12987ed9959047c066bab780e89fd814d24c7152919420a9ae62cbbb49037bff8e9c827ecc5eb38e6fad0163fcaac355ac28f028ba7a868cbc9495eff languageName: node linkType: hard -"@graasp/ui@npm:4.23.0": - version: 4.23.0 - resolution: "@graasp/ui@npm:4.23.0" +"@graasp/ui@npm:4.20.0": + version: 4.20.0 + resolution: "@graasp/ui@npm:4.20.0" dependencies: "@ag-grid-community/client-side-row-model": "npm:31.3.2" - "@ag-grid-community/react": "npm:^31.3.2" - "@ag-grid-community/styles": "npm:^31.3.2" - "@storybook/react-vite": "npm:8.1.11" + "@ag-grid-community/react": "npm:^31.3.1" + "@ag-grid-community/styles": "npm:^31.3.1" + "@storybook/react-vite": "npm:8.1.10" http-status-codes: "npm:2.3.0" interweave: "npm:13.1.0" - katex: "npm:0.16.11" + katex: "npm:0.16.10" lodash.truncate: "npm:4.4.2" - lucide-react: "npm:0.408.0" + lucide-react: "npm:0.395.0" react-cookie-consent: "npm:9.0.0" react-dnd: "npm:16.0.1" react-dnd-html5-backend: "npm:16.0.1" react-quill: "npm:2.0.0" react-rnd: "npm:10.4.11" + react-text-mask: "npm:5.5.0" uuid: "npm:10.0.0" - vitest: "npm:2.0.2" + vitest: "npm:1.6.0" peerDependencies: "@emotion/cache": ~11.10.7 || ~11.11.0 "@emotion/react": ~11.10.6 || ~11.11.0 "@emotion/styled": ~11.10.6 || ~11.11.0 "@graasp/sdk": ^4.14.0 "@graasp/translations": ^1.23.0 - "@mui/icons-material": ~5.14.0 || ~5.15.0 || ~5.16.0 + "@mui/icons-material": ~5.14.0 || ~5.15.0 "@mui/lab": ~5.0.0-alpha.150 - "@mui/material": ~5.14.0 || ~5.15.0 || ~5.16.0 + "@mui/material": ~5.14.0 || ~5.15.0 i18next: ^22.4.15 || ^23.0.0 react: ^18.0.0 react-dom: ^18.0.0 @@ -1999,7 +1999,7 @@ __metadata: react-router-dom: ^6.11.0 stylis: ^4.1.3 stylis-plugin-rtl: ^2.1.1 - checksum: 10/26d99acd179daee8315b632b28590c10b13e991ef6c66fcda916937e6fff6ce6d8f424fdd2499beba6ef0c3f91d705181b73ec6fe0e551d4b50f1615d1fadb64 + checksum: 10/2259b603ddffb00187f5684215a9e16e91a192612a84f7807759f385b7121fe198bdb20ae17fc978b1996a0b921dd2381283f22a3a84ad40c3b8a0031efdaf05 languageName: node linkType: hard @@ -4343,18 +4343,6 @@ __metadata: languageName: node linkType: hard -"@vitest/expect@npm:2.0.2": - version: 2.0.2 - resolution: "@vitest/expect@npm:2.0.2" - dependencies: - "@vitest/spy": "npm:2.0.2" - "@vitest/utils": "npm:2.0.2" - chai: "npm:^5.1.1" - tinyrainbow: "npm:^1.2.0" - checksum: 10/67ebe5dcc083cbaf152fa1845da5ab4cd5a37fcc8657caaec214878c145516cf270998ad300ab9c3e7d8b4fc9ab41cbc4606af3341ae06d08c5cf44354ba5a56 - languageName: node - linkType: hard - "@vitest/expect@npm:2.0.4": version: 2.0.4 resolution: "@vitest/expect@npm:2.0.4" @@ -4367,16 +4355,7 @@ __metadata: languageName: node linkType: hard -"@vitest/pretty-format@npm:2.0.2": - version: 2.0.2 - resolution: "@vitest/pretty-format@npm:2.0.2" - dependencies: - tinyrainbow: "npm:^1.2.0" - checksum: 10/30ae021ea3b36271e00aac5a49084de9403900ae574b1ce1c26385ee792a7fed700f2deb2cd841b64724a4e428e908a5d3ffc1b4e6ca83daa351d76de925e9a6 - languageName: node - linkType: hard - -"@vitest/pretty-format@npm:2.0.4, @vitest/pretty-format@npm:^2.0.2, @vitest/pretty-format@npm:^2.0.4": +"@vitest/pretty-format@npm:2.0.4, @vitest/pretty-format@npm:^2.0.4": version: 2.0.4 resolution: "@vitest/pretty-format@npm:2.0.4" dependencies: @@ -4396,16 +4375,6 @@ __metadata: languageName: node linkType: hard -"@vitest/runner@npm:2.0.2": - version: 2.0.2 - resolution: "@vitest/runner@npm:2.0.2" - dependencies: - "@vitest/utils": "npm:2.0.2" - pathe: "npm:^1.1.2" - checksum: 10/f3f9f15b5a3d0b5fe5815ed0ad04bd3fceab0768c441baf20931d78f2599261c172724955e9de35020ff79950e1fd5398d0d5aad2c5ee8a91e4cc2b85943ac81 - languageName: node - linkType: hard - "@vitest/runner@npm:2.0.4": version: 2.0.4 resolution: "@vitest/runner@npm:2.0.4" @@ -4427,17 +4396,6 @@ __metadata: languageName: node linkType: hard -"@vitest/snapshot@npm:2.0.2": - version: 2.0.2 - resolution: "@vitest/snapshot@npm:2.0.2" - dependencies: - "@vitest/pretty-format": "npm:2.0.2" - magic-string: "npm:^0.30.10" - pathe: "npm:^1.1.2" - checksum: 10/c0d41c3ff71ada909b34a8cbfe4ae9d59126fdae243b89e4eba5110db8eeb41234897159de20050a18aac2cbb7694e3fddd94bf7c79c1e9b169f1f4cf642bf07 - languageName: node - linkType: hard - "@vitest/snapshot@npm:2.0.4": version: 2.0.4 resolution: "@vitest/snapshot@npm:2.0.4" @@ -4458,15 +4416,6 @@ __metadata: languageName: node linkType: hard -"@vitest/spy@npm:2.0.2": - version: 2.0.2 - resolution: "@vitest/spy@npm:2.0.2" - dependencies: - tinyspy: "npm:^3.0.0" - checksum: 10/feca3d26b824350d2f4f11a1e5881f1c7eeba5b903399ee8fbc2aceb4bf4201da61088783cf56bd5a2850b3e2380905f69128106655d7d849c62c52861b5af1a - languageName: node - linkType: hard - "@vitest/spy@npm:2.0.4": version: 2.0.4 resolution: "@vitest/spy@npm:2.0.4" @@ -4488,18 +4437,6 @@ __metadata: languageName: node linkType: hard -"@vitest/utils@npm:2.0.2": - version: 2.0.2 - resolution: "@vitest/utils@npm:2.0.2" - dependencies: - "@vitest/pretty-format": "npm:2.0.2" - estree-walker: "npm:^3.0.3" - loupe: "npm:^3.1.1" - tinyrainbow: "npm:^1.2.0" - checksum: 10/771a1579c9d11bf02ed5d641619bdb9ee06f4096a2965183298c8610476316f899561dabf48e589eecccd76c75155131dc7a90d98d7519e07483b7ed09e0a5b9 - languageName: node - linkType: hard - "@vitest/utils@npm:2.0.4": version: 2.0.4 resolution: "@vitest/utils@npm:2.0.4" @@ -8145,10 +8082,10 @@ __metadata: "@emotion/styled": "npm:11.13.0" "@graasp/chatbox": "npm:3.1.0" "@graasp/map": "npm:1.17.0" - "@graasp/query-client": "npm:3.21.0" - "@graasp/sdk": "npm:4.22.0" + "@graasp/query-client": "github:graasp/graasp-query-client#update-for-item-login" + "@graasp/sdk": "github:graasp/graasp-sdk#568-new-membertype" "@graasp/translations": "npm:1.33.0" - "@graasp/ui": "npm:4.23.0" + "@graasp/ui": "github:graasp/graasp-ui#update-sdk" "@mui/icons-material": "npm:5.16.4" "@mui/lab": "npm:5.0.0-alpha.172" "@mui/material": "npm:5.16.4" @@ -14218,21 +14155,6 @@ __metadata: languageName: node linkType: hard -"vite-node@npm:2.0.2": - version: 2.0.2 - resolution: "vite-node@npm:2.0.2" - dependencies: - cac: "npm:^6.7.14" - debug: "npm:^4.3.5" - pathe: "npm:^1.1.2" - tinyrainbow: "npm:^1.2.0" - vite: "npm:^5.0.0" - bin: - vite-node: vite-node.mjs - checksum: 10/9335168dc5a20c1d0c6b53cf20f098875c7556b0eb1e1ae871aedcc796edd5906f06ab259d9b57ec12719041838cac8186e54e597c0012ee77b03a4e2be84722 - languageName: node - linkType: hard - "vite-node@npm:2.0.4": version: 2.0.4 resolution: "vite-node@npm:2.0.4" @@ -14446,55 +14368,6 @@ __metadata: languageName: node linkType: hard -"vitest@npm:2.0.2": - version: 2.0.2 - resolution: "vitest@npm:2.0.2" - dependencies: - "@ampproject/remapping": "npm:^2.3.0" - "@vitest/expect": "npm:2.0.2" - "@vitest/pretty-format": "npm:^2.0.2" - "@vitest/runner": "npm:2.0.2" - "@vitest/snapshot": "npm:2.0.2" - "@vitest/spy": "npm:2.0.2" - "@vitest/utils": "npm:2.0.2" - chai: "npm:^5.1.1" - debug: "npm:^4.3.5" - execa: "npm:^8.0.1" - magic-string: "npm:^0.30.10" - pathe: "npm:^1.1.2" - std-env: "npm:^3.7.0" - tinybench: "npm:^2.8.0" - tinypool: "npm:^1.0.0" - tinyrainbow: "npm:^1.2.0" - vite: "npm:^5.0.0" - vite-node: "npm:2.0.2" - why-is-node-running: "npm:^2.2.2" - peerDependencies: - "@edge-runtime/vm": "*" - "@types/node": ^18.0.0 || >=20.0.0 - "@vitest/browser": 2.0.2 - "@vitest/ui": 2.0.2 - happy-dom: "*" - jsdom: "*" - peerDependenciesMeta: - "@edge-runtime/vm": - optional: true - "@types/node": - optional: true - "@vitest/browser": - optional: true - "@vitest/ui": - optional: true - happy-dom: - optional: true - jsdom: - optional: true - bin: - vitest: vitest.mjs - checksum: 10/d92053b0d6e3e800d56cbe5eb860625fb9d50e66857da189ac19a68e511bbb0c59baf6a6b3a8ecb0b46c011567723e16e550136655e93767f228fb91caf4e16f - languageName: node - linkType: hard - "vitest@npm:2.0.4": version: 2.0.4 resolution: "vitest@npm:2.0.4" From fd1468dda7144a65909bb9766b23debcfe33dedc Mon Sep 17 00:00:00 2001 From: kim Date: Fri, 9 Aug 2024 13:36:57 +0200 Subject: [PATCH 02/10] refactor: apply changes --- cypress/e2e/item/hide/hideItem.cy.ts | 4 +- cypress/e2e/item/view/viewDocument.cy.ts | 2 +- cypress/e2e/item/view/viewLink.cy.ts | 6 +- cypress/e2e/memberships/viewMemberships.cy.ts | 8 +- cypress/fixtures/chatbox.ts | 6 +- cypress/fixtures/invitations.ts | 6 +- cypress/fixtures/items.ts | 18 +-- cypress/fixtures/members.ts | 16 +-- cypress/fixtures/memberships.ts | 26 +++-- package.json | 2 +- src/components/common/Chatbox.tsx | 1 - .../sharing/ItemLoginMembershipsTable.tsx | 4 +- .../item/sharing/ItemMembershipsTable.tsx | 109 +++++++++--------- .../item/sharing/ItemSharingTab.tsx | 23 ++-- src/utils/item.ts | 2 +- yarn.lock | 8 +- 16 files changed, 125 insertions(+), 116 deletions(-) diff --git a/cypress/e2e/item/hide/hideItem.cy.ts b/cypress/e2e/item/hide/hideItem.cy.ts index acd5524ab..bb5efd3f8 100644 --- a/cypress/e2e/item/hide/hideItem.cy.ts +++ b/cypress/e2e/item/hide/hideItem.cy.ts @@ -23,7 +23,7 @@ const HIDDEN_ITEM: ItemForTest = { { item: hiddenItem, permission: PermissionLevel.Admin, - member: MEMBERS.ANNA, + account: MEMBERS.ANNA, creator: MEMBERS.ANNA, id: 'ecbfbd2a-5688-12db-ae93-0242ac130002', createdAt: '2021-08-11T12:56:36.834Z', @@ -32,7 +32,7 @@ const HIDDEN_ITEM: ItemForTest = { { item: hiddenItem, permission: PermissionLevel.Read, - member: MEMBERS.BOB, + account: MEMBERS.BOB, creator: MEMBERS.ANNA, id: 'ecbfbd2a-5688-12db-ae93-0242ac130002', createdAt: '2021-08-11T12:56:36.834Z', diff --git a/cypress/e2e/item/view/viewDocument.cy.ts b/cypress/e2e/item/view/viewDocument.cy.ts index d07793007..cc27b1169 100644 --- a/cypress/e2e/item/view/viewDocument.cy.ts +++ b/cypress/e2e/item/view/viewDocument.cy.ts @@ -17,7 +17,7 @@ describe('View Document', () => { memberships: [ buildItemMembership({ item: DOCUMENT, - member: CURRENT_USER, + account: CURRENT_USER, }), ], }, diff --git a/cypress/e2e/item/view/viewLink.cy.ts b/cypress/e2e/item/view/viewLink.cy.ts index c97b9e723..0b8c94a25 100644 --- a/cypress/e2e/item/view/viewLink.cy.ts +++ b/cypress/e2e/item/view/viewLink.cy.ts @@ -17,7 +17,7 @@ describe('Links', () => { memberships: [ buildItemMembership({ item: GRAASP_LINK_ITEM, - member: CURRENT_USER, + account: CURRENT_USER, }), ], }, @@ -26,7 +26,7 @@ describe('Links', () => { memberships: [ buildItemMembership({ item: GRAASP_LINK_ITEM_IFRAME_ONLY, - member: CURRENT_USER, + account: CURRENT_USER, }), ], }, @@ -35,7 +35,7 @@ describe('Links', () => { memberships: [ buildItemMembership({ item: YOUTUBE_LINK_ITEM, - member: CURRENT_USER, + account: CURRENT_USER, }), ], }, diff --git a/cypress/e2e/memberships/viewMemberships.cy.ts b/cypress/e2e/memberships/viewMemberships.cy.ts index 171bcc290..d87cb0685 100644 --- a/cypress/e2e/memberships/viewMemberships.cy.ts +++ b/cypress/e2e/memberships/viewMemberships.cy.ts @@ -30,9 +30,9 @@ describe('View Memberships', () => { // panel only contains 2 avatars: one user, one +x // check contains member avatar - for (const { permission, member, id } of filteredMemberships) { + for (const { permission, account, id } of filteredMemberships) { const { name, email } = Object.values(MEMBERS).find( - ({ id: mId }) => mId === member.id, + ({ id: mId }) => mId === account.id, ); // check name and mail cy.get(buildItemMembershipRowSelector(id)) @@ -66,9 +66,9 @@ describe('View Memberships Read-Only Mode', () => { cy.get(`#${buildShareButtonId(item.id)}`).click(); // check contains member avatar - for (const { permission, member, id } of memberships) { + for (const { permission, account, id } of memberships) { const { name, email } = Object.values(MEMBERS).find( - ({ id: mId }) => mId === member.id, + ({ id: mId }) => mId === account.id, ); // check name, mail and permission cy.get(buildItemMembershipRowSelector(id)) diff --git a/cypress/fixtures/chatbox.ts b/cypress/fixtures/chatbox.ts index 13cccbe86..b77ded1ef 100644 --- a/cypress/fixtures/chatbox.ts +++ b/cypress/fixtures/chatbox.ts @@ -30,7 +30,7 @@ export const ITEM_WITH_CHATBOX_MESSAGES: ItemForTest = { { item, permission: PermissionLevel.Write, - member: MEMBERS.ANNA, + account: MEMBERS.ANNA, creator: MEMBERS.ANNA, createdAt: '2021-09-11T12:56:36.834Z', updatedAt: '2021-09-11T12:56:36.834Z', @@ -72,7 +72,7 @@ const ITEM_WITH_CHATBOX_MESSAGES_AND_ADMIN: ItemForTest = { { item: items[0], permission: PermissionLevel.Admin, - member: MEMBERS.ANNA, + account: MEMBERS.ANNA, creator: MEMBERS.ANNA, createdAt: '2021-08-11T12:56:36.834Z', id: '78ad2166-3862-4593-a13c-d380e7b66674', @@ -110,7 +110,7 @@ export const ITEM_WITHOUT_CHATBOX_MESSAGES: ItemForTest = { export const SAMPLE_MENTIONS: ChatMention[] = [ { id: '7062d5e6-a4a0-4828-b4b9-8bc9e21f7abd', - member: CURRENT_USER, + account: CURRENT_USER, createdAt: '2021-08-11T12:56:36.834Z', // '2022-07-18T07:48:05.008Z', updatedAt: '2021-08-11T12:56:36.834Z', // '2022-07-18T07:48:05.008Z', status: MentionStatus.Unread, diff --git a/cypress/fixtures/invitations.ts b/cypress/fixtures/invitations.ts index 139d4389a..ab3b95c69 100644 --- a/cypress/fixtures/invitations.ts +++ b/cypress/fixtures/invitations.ts @@ -54,7 +54,7 @@ export const ITEMS_WITH_INVITATIONS: ApiConfig = { id: 'ecafbd2a-5688-11eb-be93-0242ac130002', item: itemsWithInvitations[0], permission: PermissionLevel.Admin, - member: MEMBERS.FANNY, + account: MEMBERS.FANNY, createdAt: '2021-08-11T12:56:36.834Z', updatedAt: '2021-08-11T12:56:36.834Z', creator: MEMBERS.ANNA, @@ -63,7 +63,7 @@ export const ITEMS_WITH_INVITATIONS: ApiConfig = { id: 'ecafbd2a-5688-11eb-be93-0212ac130002', item: itemsWithInvitations[0], permission: PermissionLevel.Admin, - member: MEMBERS.ANNA, + account: MEMBERS.ANNA, createdAt: '2021-08-11T12:56:36.834Z', updatedAt: '2021-08-11T12:56:36.834Z', creator: MEMBERS.ANNA, @@ -132,7 +132,7 @@ export const ITEM_WITH_INVITATIONS_WRITE_ACCESS: ApiConfig = { id: 'ecafbd2a-5688-11eb-be93-0242ac130002', item: itemsWithInvitationsWriteAccess[0], permission: PermissionLevel.Write, - member: MEMBERS.ANNA, + account: MEMBERS.ANNA, createdAt: '2021-08-11T12:56:36.834Z', updatedAt: '2021-08-11T12:56:36.834Z', creator: MEMBERS.ANNA, diff --git a/cypress/fixtures/items.ts b/cypress/fixtures/items.ts index a0165474e..36e8c1dae 100644 --- a/cypress/fixtures/items.ts +++ b/cypress/fixtures/items.ts @@ -45,7 +45,7 @@ export const generateOwnItems = (number: number): ItemForTest[] => { { item, permission: PermissionLevel.Admin, - member: MEMBERS.ANNA, + account: MEMBERS.ANNA, creator: MEMBERS.ANNA, createdAt: '2021-08-11T12:56:36.834Z', updatedAt: '2021-08-11T12:56:36.834Z', @@ -118,7 +118,7 @@ export const SAMPLE_PUBLIC_ITEMS: ApiConfig = { { item: samplePublicItems[0], permission: PermissionLevel.Admin, - member: MEMBERS.ANNA, + account: MEMBERS.ANNA, creator: MEMBERS.ANNA, id: 'ecbfbd2a-5688-12db-ae93-0242ac130032', createdAt: '2021-08-11T12:56:36.834Z', @@ -127,7 +127,7 @@ export const SAMPLE_PUBLIC_ITEMS: ApiConfig = { { item: samplePublicItems[0], permission: PermissionLevel.Read, - member: MEMBERS.BOB, + account: MEMBERS.BOB, creator: MEMBERS.ANNA, id: 'ecbfbd2a-5688-12db-ae91-0242ac130002', createdAt: '2021-08-11T12:56:36.834Z', @@ -141,7 +141,7 @@ export const SAMPLE_PUBLIC_ITEMS: ApiConfig = { { item: samplePublicItems[1], permission: PermissionLevel.Admin, - member: MEMBERS.ANNA, + account: MEMBERS.ANNA, creator: MEMBERS.ANNA, id: 'ecbfbd2a-5688-121b-ae93-0242ac130002', createdAt: '2021-08-11T12:56:36.834Z', @@ -164,7 +164,7 @@ export const SAMPLE_PUBLIC_ITEMS: ApiConfig = { { item: samplePublicItems[2], permission: PermissionLevel.Admin, - member: MEMBERS.ANNA, + account: MEMBERS.ANNA, creator: MEMBERS.ANNA, id: 'ecbfbd1a-5688-12db-ae93-0242ac130002', createdAt: '2021-08-11T12:56:36.834Z', @@ -187,7 +187,7 @@ export const SAMPLE_PUBLIC_ITEMS: ApiConfig = { { item: samplePublicItems[1], permission: PermissionLevel.Admin, - member: MEMBERS.ANNA, + account: MEMBERS.ANNA, creator: MEMBERS.ANNA, id: 'ecbfbd2a-5644-12db-ae93-0242ac130002', createdAt: '2021-08-11T12:56:36.834Z', @@ -196,7 +196,7 @@ export const SAMPLE_PUBLIC_ITEMS: ApiConfig = { { item: samplePublicItems[1], permission: PermissionLevel.Read, - member: MEMBERS.BOB, + account: MEMBERS.BOB, creator: MEMBERS.ANNA, id: 'ecbfbd2a-5338-12db-ae93-0242ac130002', createdAt: '2021-08-11T12:56:36.834Z', @@ -283,7 +283,7 @@ export const PUBLISHED_ITEM: ItemForTest = { { item, permission: PermissionLevel.Admin, - member: MEMBERS.ANNA, + account: MEMBERS.ANNA, creator: MEMBERS.ANNA, id: 'ecbfbd2a-5688-12db-ae93-0242ac130002', createdAt: '2021-08-11T12:56:36.834Z', @@ -292,7 +292,7 @@ export const PUBLISHED_ITEM: ItemForTest = { { item, permission: PermissionLevel.Read, - member: MEMBERS.BOB, + account: MEMBERS.BOB, creator: MEMBERS.ANNA, id: 'ecbfbd2a-5688-12db-ae93-0242ac130002', createdAt: '2021-08-11T12:56:36.834Z', diff --git a/cypress/fixtures/members.ts b/cypress/fixtures/members.ts index ce31db532..2cac2be21 100644 --- a/cypress/fixtures/members.ts +++ b/cypress/fixtures/members.ts @@ -1,4 +1,4 @@ -import { CompleteMember, MemberFactory, MemberType } from '@graasp/sdk'; +import { AccountType, CompleteMember, MemberFactory } from '@graasp/sdk'; import { MemberForTest } from '../support/types'; import { AVATAR_LINK } from './thumbnails/links'; @@ -9,7 +9,7 @@ export const MEMBERS: Record = { ANNA: MemberFactory({ id: 'ecafbd2a-5642-31fb-ae93-0242ac130002', name: 'anna', - type: MemberType.Individual, + type: AccountType.Individual, email: 'anna@email.com', createdAt: '2021-04-13 14:56:34.749946', updatedAt: '2021-04-13 14:56:34.749946', @@ -23,7 +23,7 @@ export const MEMBERS: Record = { ...MemberFactory({ id: 'ecafbd2a-5642-31fb-ae93-0242ac130004', name: 'bob', - type: MemberType.Individual, + type: AccountType.Individual, email: 'bob@email.com', createdAt: '2021-04-13 14:56:34.749946', updatedAt: '2021-04-13 14:56:34.749946', @@ -36,7 +36,7 @@ export const MEMBERS: Record = { ...MemberFactory({ id: 'ecafbd2a-5642-31fb-ae93-0242ac130006', name: 'cedric', - type: MemberType.Individual, + type: AccountType.Individual, extra: {}, email: 'cedric@email.com', createdAt: '2021-04-13 14:56:34.749946', @@ -49,7 +49,7 @@ export const MEMBERS: Record = { DAVID: MemberFactory({ id: 'ecafbd2a-5642-31fb-ae93-0242ac130062', name: 'david', - type: MemberType.Individual, + type: AccountType.Individual, email: 'david@email.com', createdAt: '2021-04-13 14:56:34.749946', updatedAt: '2021-04-13 14:56:34.749946', @@ -58,7 +58,7 @@ export const MEMBERS: Record = { EVAN: MemberFactory({ id: 'ecafbd2a-5642-31fb-ae93-0242ac130022', name: 'evan', - type: MemberType.Individual, + type: AccountType.Individual, email: 'evan@email.com', createdAt: '2021-04-13 14:56:34.749946', updatedAt: '2021-04-13 14:56:34.749946', @@ -68,7 +68,7 @@ export const MEMBERS: Record = { id: 'ecafbd2a-5642-31fb-ae93-0242ac130012', name: 'fanny', extra: {}, - type: MemberType.Individual, + type: AccountType.Individual, email: 'fanny@email.com', createdAt: '2021-04-13 14:56:34.749946', updatedAt: '2021-04-13 14:56:34.749946', @@ -77,7 +77,7 @@ export const MEMBERS: Record = { id: 'ecafbd2a-5642-31fb-ae93-0242ac130412', name: 'garry', extra: {}, - type: MemberType.Individual, + type: AccountType.Individual, email: 'garry@email.com', createdAt: '2021-04-13 14:56:34.749946', updatedAt: '2021-04-13 14:56:34.749946', diff --git a/cypress/fixtures/memberships.ts b/cypress/fixtures/memberships.ts index 319ef5be0..79d0c408f 100644 --- a/cypress/fixtures/memberships.ts +++ b/cypress/fixtures/memberships.ts @@ -1,7 +1,9 @@ import { + Account, DiscriminatedItem, ItemMembership, Member, + MemberFactory, PackedFolderItemFactory, PermissionLevel, } from '@graasp/sdk'; @@ -15,13 +17,13 @@ import { MEMBERS } from './members'; export const buildItemMembership = (args: { permission?: PermissionLevel; item: DiscriminatedItem; - member: Member; + account: Partial; creator?: Member; }): ItemMembership => ({ permission: args.permission ?? PermissionLevel.Admin, - member: args.member, + account: MemberFactory(args.account), item: args.item, - creator: args.creator ?? args.member, + creator: MemberFactory(args.creator ?? args.account), createdAt: '2021-08-11T12:56:36.834Z', updatedAt: '2021-08-11T12:56:36.834Z', id: v4(), @@ -55,7 +57,7 @@ export const ITEMS_WITH_MEMBERSHIPS: ApiConfig = { id: 'ecafbd2a-5688-11eb-be93-0242ac130002', item: sampleItems[0], permission: PermissionLevel.Admin, - member: MEMBERS.ANNA, + account: MEMBERS.ANNA, creator: MEMBERS.ANNA, updatedAt: '2021-08-11T12:56:36.834Z', createdAt: '2021-08-11T12:56:36.834Z', @@ -64,7 +66,7 @@ export const ITEMS_WITH_MEMBERSHIPS: ApiConfig = { id: 'ecafbd2a-5688-11eb-be92-0242ac130002', item: sampleItems[0], permission: PermissionLevel.Write, - member: MEMBERS.BOB, + account: MEMBERS.BOB, creator: MEMBERS.ANNA, updatedAt: '2021-08-11T12:56:36.834Z', createdAt: '2021-08-11T12:56:36.834Z', @@ -73,7 +75,7 @@ export const ITEMS_WITH_MEMBERSHIPS: ApiConfig = { id: 'ecafbd1a-5688-11eb-be93-0242ac130002', item: sampleItems[0], permission: PermissionLevel.Write, - member: MEMBERS.CEDRIC, + account: MEMBERS.CEDRIC, updatedAt: '2021-08-11T12:56:36.834Z', createdAt: '2021-08-11T12:56:36.834Z', creator: MEMBERS.ANNA, @@ -82,7 +84,7 @@ export const ITEMS_WITH_MEMBERSHIPS: ApiConfig = { id: 'ecbfbd2a-5688-11eb-be93-0242ac130002', item: sampleItems[0], permission: PermissionLevel.Read, - member: MEMBERS.DAVID, + account: MEMBERS.DAVID, creator: MEMBERS.ANNA, updatedAt: '2021-08-11T12:56:36.834Z', createdAt: '2021-08-11T12:56:36.834Z', @@ -96,7 +98,7 @@ export const ITEMS_WITH_MEMBERSHIPS: ApiConfig = { id: 'ecafbd2a-5688-11eb-be93-0242ac130002', item: sampleItems[1], permission: PermissionLevel.Admin, - member: MEMBERS.ANNA, + account: MEMBERS.ANNA, creator: MEMBERS.ANNA, updatedAt: '2021-08-11T12:56:36.834Z', createdAt: '2021-08-11T12:56:36.834Z', @@ -105,7 +107,7 @@ export const ITEMS_WITH_MEMBERSHIPS: ApiConfig = { id: 'ecafbd2a-5688-11eb-be92-0242ac130002', item: sampleItems[0], permission: PermissionLevel.Write, - member: MEMBERS.BOB, + account: MEMBERS.BOB, creator: MEMBERS.ANNA, updatedAt: '2021-08-11T12:56:36.834Z', createdAt: '2021-08-11T12:56:36.834Z', @@ -138,7 +140,7 @@ export const ITEM_WITH_WRITE_ACCESS: ApiConfig = { id: 'ecafbd2a-5688-11eb-be93-0242ac130002', item: sampleItemsWithWriteAccess[0], permission: PermissionLevel.Admin, - member: MEMBERS.BOB, + account: MEMBERS.BOB, creator: MEMBERS.ANNA, updatedAt: '2021-08-11T12:56:36.834Z', createdAt: '2021-08-11T12:56:36.834Z', @@ -147,7 +149,7 @@ export const ITEM_WITH_WRITE_ACCESS: ApiConfig = { id: 'ecafbd2a-5688-11eb-be92-0242ac130002', item: sampleItemsWithWriteAccess[0], permission: PermissionLevel.Write, - member: MEMBERS.ANNA, + account: MEMBERS.ANNA, creator: MEMBERS.ANNA, updatedAt: '2021-08-11T12:56:36.834Z', createdAt: '2021-08-11T12:56:36.834Z', @@ -156,7 +158,7 @@ export const ITEM_WITH_WRITE_ACCESS: ApiConfig = { id: 'ecafbd1a-5688-11eb-be93-0242ac130002', item: sampleItemsWithWriteAccess[0], permission: PermissionLevel.Read, - member: MEMBERS.CEDRIC, + account: MEMBERS.CEDRIC, creator: MEMBERS.ANNA, updatedAt: '2021-08-11T12:56:36.834Z', createdAt: '2021-08-11T12:56:36.834Z', diff --git a/package.json b/package.json index fce8afd9c..3e8d86172 100644 --- a/package.json +++ b/package.json @@ -18,7 +18,7 @@ "@emotion/cache": "11.13.0", "@emotion/react": "11.13.0", "@emotion/styled": "11.13.0", - "@graasp/chatbox": "3.1.0", + "@graasp/chatbox": "github:graasp/graasp-chatbox#update-for-item-login", "@graasp/map": "1.17.0", "@graasp/query-client": "github:graasp/graasp-query-client#update-for-item-login", "@graasp/sdk": "github:graasp/graasp-sdk#568-new-membertype", diff --git a/src/components/common/Chatbox.tsx b/src/components/common/Chatbox.tsx index 4e0e861f9..740ea1834 100644 --- a/src/components/common/Chatbox.tsx +++ b/src/components/common/Chatbox.tsx @@ -32,7 +32,6 @@ const Chatbox = ({ item }: Props): JSX.Element | null => { } // only signed in member can see the chat - // TODO: allow public?? if (!currentMember) { return null; } diff --git a/src/components/item/sharing/ItemLoginMembershipsTable.tsx b/src/components/item/sharing/ItemLoginMembershipsTable.tsx index bd54e4f6e..25290f15c 100644 --- a/src/components/item/sharing/ItemLoginMembershipsTable.tsx +++ b/src/components/item/sharing/ItemLoginMembershipsTable.tsx @@ -34,7 +34,9 @@ const ItemLoginMembershipsTable = ({ + im1.account.name > im2.account.name ? 1 : -1, + )} emptyMessage={translateBuilder( BUILDER.SHARING_AUTHENTICATED_MEMBERS_EMPTY_MESSAGE, )} diff --git a/src/components/item/sharing/ItemMembershipsTable.tsx b/src/components/item/sharing/ItemMembershipsTable.tsx index fcaf84798..717e10e71 100644 --- a/src/components/item/sharing/ItemMembershipsTable.tsx +++ b/src/components/item/sharing/ItemMembershipsTable.tsx @@ -11,6 +11,7 @@ import { } from '@mui/material'; import { + AccountType, DiscriminatedItem, ItemMembership, PermissionLevel, @@ -72,10 +73,10 @@ const ItemMembershipsTable = ({ permission, itemId: item.id, }); - } else { + } else if (im.account.type === AccountType.Individual) { shareItem({ id: item.id, - email: im.member.email, + email: im.account.email, permission, }); } @@ -116,64 +117,66 @@ const ItemMembershipsTable = ({ - {memberships - .sort((im1, im2) => (im1.member.email > im2.member.email ? 1 : -1)) - .map((row) => ( - - {showEmail && ( - - {row.member.email} - - )} - - {row.member.name} + {memberships.map((row) => ( + + {showEmail && ( + + + {row.account.type === AccountType.Individual + ? row.account.email + : ''} + + )} + + {row.account.name} + + + + + {!readOnly && ( - onDelete(row)} + id={buildItemMembershipRowDeleteButtonId(row.id)} + tooltip={translateBuilder( + BUILDER.ITEM_MEMBERSHIPS_TABLE_CANNOT_DELETE_PARENT_TOOLTIP, + )} + disabled={ + // cannot delete if not for current item + row.item.path !== item.path || + // cannot delete if is the only admin (hasOnlyOneAdmin && row.permission === PermissionLevel.Admin) } - allowDowngrade={ - // can downgrade for same item - row.item.path === item.path && - // cannot downgrade your own membership - row.member.id !== currentMember?.id - } /> - {!readOnly && ( - - onDelete(row)} - id={buildItemMembershipRowDeleteButtonId(row.id)} - tooltip={translateBuilder( - BUILDER.ITEM_MEMBERSHIPS_TABLE_CANNOT_DELETE_PARENT_TOOLTIP, - )} - disabled={ - // cannot delete if not for current item - row.item.path !== item.path || - // cannot delete if is the only admin - (hasOnlyOneAdmin && - row.permission === PermissionLevel.Admin) - } - /> - - )} - - ))} + )} + + ))} {open && ( diff --git a/src/components/item/sharing/ItemSharingTab.tsx b/src/components/item/sharing/ItemSharingTab.tsx index 9fc016f15..f7f87ccde 100644 --- a/src/components/item/sharing/ItemSharingTab.tsx +++ b/src/components/item/sharing/ItemSharingTab.tsx @@ -2,9 +2,7 @@ import { useOutletContext, useParams } from 'react-router-dom'; import { Container, Divider, Grid, Typography } from '@mui/material'; -import { isPseudoMember } from '@graasp/sdk'; - -import partition from 'lodash.partition'; +import { AccountType, isPseudoMember } from '@graasp/sdk'; import { OutletType } from '@/components/pages/item/type'; import { selectHighestMemberships } from '@/utils/membership'; @@ -27,11 +25,6 @@ const ItemSharingTab = (): JSX.Element => { const { data: memberships } = hooks.useItemMemberships(itemId); - const [authenticatedMemberships, authorizedMemberships] = partition( - memberships, - ({ member }) => member?.email && isPseudoMember(member), - ); - const { data: invitations } = hooks.useItemInvitations(item?.id); const renderMembershipSettings = () => { @@ -58,11 +51,21 @@ const ItemSharingTab = (): JSX.Element => { emptyMessage={translateBuilder( BUILDER.SHARING_AUTHORIZED_MEMBERS_EMPTY_MESSAGE, )} - memberships={selectHighestMemberships(authorizedMemberships)} + memberships={selectHighestMemberships(memberships) + ?.filter((m) => m.account.type === AccountType.Individual) + ?.sort((im1, im2) => { + if (im1.account.type !== AccountType.Individual) { + return 1; + } + if (im2.account.type !== AccountType.Individual) { + return -1; + } + return im1.account.email > im2.account.email ? 1 : -1; + })} readOnly={!canAdmin} /> isPseudoMember(m.account))} item={item} /> diff --git a/src/utils/item.ts b/src/utils/item.ts index c4caba8d7..cbbbe5ec5 100644 --- a/src/utils/item.ts +++ b/src/utils/item.ts @@ -143,7 +143,7 @@ export const getHighestPermissionForMemberFromMemberships = ({ } const itemMemberships = memberships?.filter( - ({ item: { path: mPath }, member: { id: mId } }) => + ({ item: { path: mPath }, account: { id: mId } }) => mId === memberId && itemPath.includes(mPath), ); if (!itemMemberships || itemMemberships.length === 0) { diff --git a/yarn.lock b/yarn.lock index 8100c347b..5c47148cc 100644 --- a/yarn.lock +++ b/yarn.lock @@ -1786,9 +1786,9 @@ __metadata: languageName: node linkType: hard -"@graasp/chatbox@npm:3.1.0": +"@graasp/chatbox@github:graasp/graasp-chatbox#update-for-item-login": version: 3.1.0 - resolution: "@graasp/chatbox@npm:3.1.0" + resolution: "@graasp/chatbox@https://github.com/graasp/graasp-chatbox.git#commit=90e883a88c65f7b62cfa327c929d24377d42c707" dependencies: lodash.groupby: "npm:^4.6.0" prism-react-renderer: "npm:^2.3.1" @@ -1812,7 +1812,7 @@ __metadata: react: "*" react-dom: "*" react-i18next: ^13.0.0 || ^14.0.0 - checksum: 10/62a929f400795ab2b47f86133c32bea910a52312a5effde45a5a9506741d65e0d8fb33f67e76ac6b5d3d04aee6207caf6c0a8abbe65c66de4f8ace80b643fec0 + checksum: 10/3f5007a964d1e77fa953e33f8d157d81102997cb537f83b7a7cc92e65e1f88a9899289c9e3ea04b41ff8f5dc719171a25c56e0931470b3698d7cd5061efd2266 languageName: node linkType: hard @@ -8080,7 +8080,7 @@ __metadata: "@emotion/cache": "npm:11.13.0" "@emotion/react": "npm:11.13.0" "@emotion/styled": "npm:11.13.0" - "@graasp/chatbox": "npm:3.1.0" + "@graasp/chatbox": "github:graasp/graasp-chatbox#update-for-item-login" "@graasp/map": "npm:1.17.0" "@graasp/query-client": "github:graasp/graasp-query-client#update-for-item-login" "@graasp/sdk": "github:graasp/graasp-sdk#568-new-membertype" From 4f2e50c3c5c7ae21b2e7fb7a2fa7aaa315b8319c Mon Sep 17 00:00:00 2001 From: kim Date: Fri, 9 Aug 2024 14:26:09 +0200 Subject: [PATCH 03/10] refactor: update --- src/components/item/sharing/ItemSharingTab.tsx | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/components/item/sharing/ItemSharingTab.tsx b/src/components/item/sharing/ItemSharingTab.tsx index f7f87ccde..0092c94e3 100644 --- a/src/components/item/sharing/ItemSharingTab.tsx +++ b/src/components/item/sharing/ItemSharingTab.tsx @@ -52,8 +52,8 @@ const ItemSharingTab = (): JSX.Element => { BUILDER.SHARING_AUTHORIZED_MEMBERS_EMPTY_MESSAGE, )} memberships={selectHighestMemberships(memberships) - ?.filter((m) => m.account.type === AccountType.Individual) - ?.sort((im1, im2) => { + .filter((m) => m.account.type === AccountType.Individual) + .sort((im1, im2) => { if (im1.account.type !== AccountType.Individual) { return 1; } @@ -65,7 +65,7 @@ const ItemSharingTab = (): JSX.Element => { readOnly={!canAdmin} /> isPseudoMember(m.account))} + memberships={memberships.filter((m) => isPseudoMember(m.account))} item={item} /> From 53f14a37192e642a8a997516fd68c53fc6c074a1 Mon Sep 17 00:00:00 2001 From: kim Date: Fri, 9 Aug 2024 15:41:57 +0200 Subject: [PATCH 04/10] refactor: fix tests --- .../e2e/invitations/createInvitation.cy.ts | 4 ++-- cypress/e2e/item/publish/viewPublished.cy.ts | 2 +- .../memberships/createItemMembership.cy.ts | 16 ++++++------- .../memberships/deleteItemMembership.cy.ts | 4 ++-- .../e2e/memberships/editItemMembership.cy.ts | 14 +++++------ cypress/support/commands.ts | 11 +++------ cypress/support/commands/item.ts | 4 ++-- cypress/support/index.ts | 7 +++--- cypress/support/server.ts | 15 ------------ cypress/support/types.ts | 24 ++++++++++++++++--- 10 files changed, 49 insertions(+), 52 deletions(-) diff --git a/cypress/e2e/invitations/createInvitation.cy.ts b/cypress/e2e/invitations/createInvitation.cy.ts index b2b86bcfe..7dbef4f46 100644 --- a/cypress/e2e/invitations/createInvitation.cy.ts +++ b/cypress/e2e/invitations/createInvitation.cy.ts @@ -23,7 +23,7 @@ const inviteItem = ({ cy.get(`#${buildShareButtonId(id)}`).click(); cy.fillShareForm({ - member: { email }, + email, permission, submit, selector: `#${CREATE_MEMBERSHIP_FORM_ID}`, @@ -62,7 +62,7 @@ describe('Create Invitation', () => { memberships: [ { item, - member: MEMBERS.ANNA, + account: MEMBERS.ANNA, permission: PermissionLevel.Admin, }, ], diff --git a/cypress/e2e/item/publish/viewPublished.cy.ts b/cypress/e2e/item/publish/viewPublished.cy.ts index a8341386e..fd8528fe4 100644 --- a/cypress/e2e/item/publish/viewPublished.cy.ts +++ b/cypress/e2e/item/publish/viewPublished.cy.ts @@ -106,7 +106,7 @@ describe('Published Items', () => { cy.setUpApi({ items, publishedItemData, - getPublishedItems: true, + getPublishedItemsError: true, }); cy.visit(PUBLISHED_ITEMS_PATH); diff --git a/cypress/e2e/memberships/createItemMembership.cy.ts b/cypress/e2e/memberships/createItemMembership.cy.ts index dd0e35096..58d24da01 100644 --- a/cypress/e2e/memberships/createItemMembership.cy.ts +++ b/cypress/e2e/memberships/createItemMembership.cy.ts @@ -15,11 +15,11 @@ import { MEMBERS } from '../../fixtures/members'; const shareItem = ({ id, - member, + email, permission, submit, }: { - member: { email: string }; + email: string; permission: PermissionLevel; submit?: boolean; id: string; @@ -27,7 +27,7 @@ const shareItem = ({ cy.get(`#${buildShareButtonId(id)}`).click(); cy.fillShareForm({ - member, + email, permission, submit, selector: `#${CREATE_MEMBERSHIP_FORM_ID}`, @@ -50,7 +50,7 @@ describe('Create Membership', () => { // share const member = MEMBERS.FANNY; const permission = PermissionLevel.Read; - shareItem({ id, member, permission }); + shareItem({ id, email: member.email, permission }); cy.wait('@postInvitations').then( ({ @@ -71,7 +71,7 @@ describe('Create Membership', () => { it('cannot share item twice', () => { const ITEM = PackedFolderItemFactory(); - const member = MEMBERS.ANNA; + const account = MEMBERS.ANNA; cy.setUpApi({ items: [ { @@ -80,7 +80,7 @@ describe('Create Membership', () => { { item: ITEM, permission: PermissionLevel.Read, - member, + account, }, ], }, @@ -94,7 +94,7 @@ describe('Create Membership', () => { // fill const permission = PermissionLevel.Read; - shareItem({ id, member, permission }); + shareItem({ id, email: account.email, permission }); cy.get(`#${SHARE_ITEM_SHARE_BUTTON_ID}`).should('be.disabled'); }); @@ -108,7 +108,7 @@ describe('Create Membership', () => { // fill const permission = PermissionLevel.Read; - shareItem({ id, member: { email: 'wrong' }, permission }); + shareItem({ id, email: 'wrong', permission }); cy.get(`#${SHARE_ITEM_SHARE_BUTTON_ID}`).should('be.disabled'); }); diff --git a/cypress/e2e/memberships/deleteItemMembership.cy.ts b/cypress/e2e/memberships/deleteItemMembership.cy.ts index 599d46805..7b5dc87b7 100644 --- a/cypress/e2e/memberships/deleteItemMembership.cy.ts +++ b/cypress/e2e/memberships/deleteItemMembership.cy.ts @@ -67,12 +67,12 @@ describe('Delete Membership', () => { memberships: [ { permission: PermissionLevel.Admin, - member: CURRENT_USER, + account: CURRENT_USER, item, } as unknown as ItemMembership, { permission: PermissionLevel.Read, - member: MEMBERS.BOB, + account: MEMBERS.BOB, item, } as unknown as ItemMembership, ], diff --git a/cypress/e2e/memberships/editItemMembership.cy.ts b/cypress/e2e/memberships/editItemMembership.cy.ts index 0c5911b86..9689e3286 100644 --- a/cypress/e2e/memberships/editItemMembership.cy.ts +++ b/cypress/e2e/memberships/editItemMembership.cy.ts @@ -1,8 +1,4 @@ -import { - ItemMembership, - PackedFolderItemFactory, - PermissionLevel, -} from '@graasp/sdk'; +import { PackedFolderItemFactory, PermissionLevel } from '@graasp/sdk'; import { buildItemPath, buildItemSharePath } from '../../../src/config/paths'; import { @@ -81,15 +77,17 @@ describe('Edit Membership', () => { const child: ItemForTest = PackedFolderItemFactory(); const memberships = [ { + id: 'membership-0', permission: PermissionLevel.Admin, member: CURRENT_USER, item: child, - } as unknown as ItemMembership, + }, { + id: 'membership-1', permission: PermissionLevel.Write, - member: MEMBERS.BOB, + account: MEMBERS.BOB, item, - } as unknown as ItemMembership, + }, ]; const items = [ { diff --git a/cypress/support/commands.ts b/cypress/support/commands.ts index 7484a9e4e..b2a309c67 100644 --- a/cypress/support/commands.ts +++ b/cypress/support/commands.ts @@ -9,7 +9,6 @@ import { APPS_LIST } from '../fixtures/apps/apps'; import { SAMPLE_CATEGORIES } from '../fixtures/categories'; import { SAMPLE_MENTIONS } from '../fixtures/chatbox'; import { CURRENT_USER, MEMBERS } from '../fixtures/members'; -import { ITEM_VALIDATION_AND_REVIEW } from '../fixtures/validations'; import './commands/item'; import './commands/navigation'; import { @@ -51,7 +50,6 @@ import { mockGetItemMembershipsForItem, mockGetItemTags, mockGetItemThumbnailUrl, - mockGetItemValidationAndReview, mockGetItemValidationGroups, mockGetItems, mockGetItemsTags, @@ -113,7 +111,6 @@ Cypress.Commands.add( currentMember = CURRENT_USER, mentions = SAMPLE_MENTIONS, categories = SAMPLE_CATEGORIES, - itemValidationAndReview = ITEM_VALIDATION_AND_REVIEW, itemValidationGroups = [], itemPublicationStatus = PublicationStatus.Unpublished, deleteItemsError = false, @@ -171,7 +168,7 @@ Cypress.Commands.add( deleteShortLinkError = false, importH5pError = false, getRecycledItemsError = false, - getPublishedItems = false, + getPublishedItemsError = false, } = {}) => { const cachedItems = JSON.parse(JSON.stringify(items)); const cachedMembers = JSON.parse(JSON.stringify(members)); @@ -285,7 +282,7 @@ Cypress.Commands.add( mockGetRecycledItems(recycledItemData, getRecycledItemsError); - mockRestoreItems(recycledItemData, restoreItemsError); + mockRestoreItems(items, restoreItemsError); // mockGetItemThumbnail(items, getItemThumbnailError); mockGetItemThumbnailUrl(items, getItemThumbnailError); @@ -308,8 +305,6 @@ Cypress.Commands.add( mockDeleteItemCategory(deleteItemCategoryError); - mockGetItemValidationAndReview(itemValidationAndReview); - mockGetItemValidationGroups(itemValidationGroups); mockPostItemValidation(); @@ -358,7 +353,7 @@ Cypress.Commands.add( mockImportH5p(importH5pError); - mockGetPublishItemsForMember(publishedItemData, getPublishedItems); + mockGetPublishItemsForMember(publishedItemData, getPublishedItemsError); }, ); diff --git a/cypress/support/commands/item.ts b/cypress/support/commands/item.ts index 6329c10a8..a98291135 100644 --- a/cypress/support/commands/item.ts +++ b/cypress/support/commands/item.ts @@ -36,13 +36,13 @@ import { Cypress.Commands.add( 'fillShareForm', - ({ member, permission, submit = true, selector = '' }) => { + ({ email, permission, submit = true, selector = '' }) => { // select permission cy.get(`${selector} .${ITEM_MEMBERSHIP_PERMISSION_SELECT_CLASS}`).click(); cy.get(`#${buildPermissionOptionId(permission)}`).click(); // input mail - cy.get(`#${SHARE_ITEM_EMAIL_INPUT_ID}`).type(member.email); + cy.get(`#${SHARE_ITEM_EMAIL_INPUT_ID}`).type(email); if (submit) { // wait for email to be validated and enable the button diff --git a/cypress/support/index.ts b/cypress/support/index.ts index 85ce30a14..9e7efd45a 100644 --- a/cypress/support/index.ts +++ b/cypress/support/index.ts @@ -6,13 +6,15 @@ import { PermissionLevel, } from '@graasp/sdk'; +import { ApiConfig } from './types'; + // cypress/support/index.ts declare global { // eslint-disable-next-line @typescript-eslint/no-namespace namespace Cypress { interface Chainable { fillShareForm(args: { - member: { email: string }; + email: string; permission: PermissionLevel; submit?: boolean; selector?: string; @@ -81,8 +83,7 @@ declare global { selectItem(id: DiscriminatedItem['id']): void; - // TODO - setUpApi(args?: any): any; + setUpApi(args?: ApiConfig): any; fillBaseItemModal( item: { name?: string }, diff --git a/cypress/support/server.ts b/cypress/support/server.ts index 205a9754e..cc6bc0d5c 100644 --- a/cypress/support/server.ts +++ b/cypress/support/server.ts @@ -12,7 +12,6 @@ import { ItemPublished, ItemTagType, ItemValidationGroup, - ItemValidationReview, Member, PermissionLevel, PermissionLevelCompare, @@ -1692,20 +1691,6 @@ export const mockDeleteItemCategory = (shouldThrowError: boolean): void => { ).as('deleteItemCategory'); }; -export const mockGetItemValidationAndReview = ( - itemValidationAndReview: ItemValidationReview, -): void => { - cy.intercept( - { - method: HttpMethod.Get, - url: new RegExp(`${API_HOST}/items/validations/status/${ID_FORMAT}`), - }, - ({ reply }) => { - reply(itemValidationAndReview); - }, - ).as('getItemValidationAndReview'); -}; - export const mockGetItemValidationGroups = ( itemValidationGroups: ItemValidationGroup[], ): void => { diff --git a/cypress/support/types.ts b/cypress/support/types.ts index 04ff7e779..e4ae146e3 100644 --- a/cypress/support/types.ts +++ b/cypress/support/types.ts @@ -5,6 +5,7 @@ import { CompleteMember, DiscriminatedItem, Invitation, + ItemBookmark, ItemCategory, ItemLoginSchema, ItemMembership, @@ -12,9 +13,11 @@ import { ItemTag, ItemValidationGroup, LocalFileItemType, - Member, PermissionLevel, + PublicationStatus, + RecycledItemData, S3FileItemType, + ShortLink, } from '@graasp/sdk'; // TODO: not the best way, to change with mirage? @@ -49,11 +52,16 @@ export type ApiConfig = { items?: ItemForTest[]; recycledItems?: DiscriminatedItem[]; members?: MemberForTest[]; - currentMember?: Member; + currentMember?: MemberForTest; mentions?: ChatMention[]; categories?: Category[]; + shortLinks?: ShortLink[]; + itemId?: DiscriminatedItem['id']; + bookmarkedItems?: ItemBookmark[]; + recycledItemData?: RecycledItemData[]; + itemPublicationStatus?: PublicationStatus; + publishedItemData?: ItemPublished[]; // statuses = SAMPLE_STATUSES, - // itemValidationAndReview = ITEM_VALIDATION_AND_REVIEW, itemValidationGroups?: ItemValidationGroup[]; deleteItemsError?: boolean; postItemError?: boolean; @@ -99,4 +107,14 @@ export type ApiConfig = { postAppDataError?: boolean; patchAppDataError?: boolean; deleteAppDataError?: boolean; + getPublishedItemsError?: boolean; + importH5pError?: boolean; + deleteShortLinkError?: boolean; + patchShortLinkError?: boolean; + postShortLinkError?: boolean; + getShortLinkAvailable?: boolean; + getShortLinksItemError?: boolean; + deleteFavoriteError?: boolean; + addFavoriteError?: boolean; + getFavoriteError?: boolean; }; From 12d2cd9795ba62a888ae2280b2d876dd5138c833 Mon Sep 17 00:00:00 2001 From: kim Date: Fri, 9 Aug 2024 16:12:43 +0200 Subject: [PATCH 05/10] refactor: fix tests --- cypress/e2e/memberships/editItemMembership.cy.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/cypress/e2e/memberships/editItemMembership.cy.ts b/cypress/e2e/memberships/editItemMembership.cy.ts index 9689e3286..c6855a0fd 100644 --- a/cypress/e2e/memberships/editItemMembership.cy.ts +++ b/cypress/e2e/memberships/editItemMembership.cy.ts @@ -79,7 +79,7 @@ describe('Edit Membership', () => { { id: 'membership-0', permission: PermissionLevel.Admin, - member: CURRENT_USER, + account: CURRENT_USER, item: child, }, { From d787c312523121706e42cc70e02dea44ea79c23a Mon Sep 17 00:00:00 2001 From: spaenleh Date: Wed, 21 Aug 2024 14:59:27 +0200 Subject: [PATCH 06/10] fix: permission table --- .../item/sharing/ConfirmMembership.tsx | 18 ++- .../item/sharing/InvitationsTable.tsx | 75 +++++----- .../sharing/ItemLoginMembershipsTable.tsx | 28 ++-- .../item/sharing/ItemSharingTab.tsx | 138 +++++++++--------- .../item/sharing/ResendInvitation.tsx | 9 +- src/langs/en.json | 4 +- src/langs/fr.json | 2 +- src/main.tsx | 9 +- yarn.lock | 17 +-- 9 files changed, 165 insertions(+), 135 deletions(-) diff --git a/src/components/item/sharing/ConfirmMembership.tsx b/src/components/item/sharing/ConfirmMembership.tsx index 0fb9ec567..a3cca9635 100644 --- a/src/components/item/sharing/ConfirmMembership.tsx +++ b/src/components/item/sharing/ConfirmMembership.tsx @@ -1,3 +1,5 @@ +import { useNavigate } from 'react-router-dom'; + import { Alert, Dialog, @@ -40,12 +42,23 @@ const DeleteItemDialog = ({ }: Props): JSX.Element => { const { t: translateBuilder } = useBuilderTranslation(); const { data: member } = hooks.useCurrentMember(); + const { mutateAsync: deleteItemMembership } = + mutations.useDeleteItemMembership(); - const { mutate: deleteItemMembership } = mutations.useDeleteItemMembership(); + const navigate = useNavigate(); const onDelete = () => { if (membershipToDelete?.id) { - deleteItemMembership({ id: membershipToDelete.id, itemId: item.id }); + deleteItemMembership({ + id: membershipToDelete.id, + itemId: item.id, + }).then(() => { + // if current user deleted their own membership navigate them to the home + if (membershipToDelete.account.id === member?.id) { + navigate('/'); + } + }); + handleClose(); } }; @@ -66,6 +79,7 @@ const DeleteItemDialog = ({ permissionLevel: membershipToDelete?.permission, }); } + return ( {emptyMessage ?? 'empty'}; } @@ -88,40 +88,47 @@ const InvitationsTable = ({ - {invitations.map((row) => ( - - - {row.email} - - - - - {!readOnly && ( - - onDelete(row)} - id={buildItemInvitationRowDeleteButtonId(row.id)} - tooltip={translateBuilder( - BUILDER.INVITATIONS_TABLE_CANNOT_DELETE_PARENT_TOOLTIP, - )} - disabled={item.path !== row.item.path} + {invitations?.map((row) => { + const isDisabled = item.path !== row.item.path; + return ( + + + {row.email} + + + - - )} - - ))} + {!readOnly && ( + + onDelete(row)} + id={buildItemInvitationRowDeleteButtonId(row.id)} + tooltip={translateBuilder( + BUILDER.INVITATIONS_TABLE_CANNOT_DELETE_PARENT_TOOLTIP, + )} + disabled={isDisabled} + /> + + + )} + + ); + })} diff --git a/src/components/item/sharing/ItemLoginMembershipsTable.tsx b/src/components/item/sharing/ItemLoginMembershipsTable.tsx index 25290f15c..004bab433 100644 --- a/src/components/item/sharing/ItemLoginMembershipsTable.tsx +++ b/src/components/item/sharing/ItemLoginMembershipsTable.tsx @@ -1,8 +1,8 @@ import { useOutletContext } from 'react-router'; -import { Typography } from '@mui/material'; +import { Box, Typography } from '@mui/material'; -import { DiscriminatedItem, ItemMembership } from '@graasp/sdk'; +import { DiscriminatedItem, isPseudoMember } from '@graasp/sdk'; import { OutletType } from '@/components/pages/item/type'; import { useBuilderTranslation } from '@/config/i18n'; @@ -12,42 +12,40 @@ import { selectHighestMemberships } from '@/utils/membership'; import ItemMembershipsTable from './ItemMembershipsTable'; -type Props = { item: DiscriminatedItem; memberships: ItemMembership[] }; +type Props = { item: DiscriminatedItem }; -const ItemLoginMembershipsTable = ({ - item, - memberships, -}: Props): JSX.Element | null => { +const ItemLoginMembershipsTable = ({ item }: Props): JSX.Element | false => { const { t: translateBuilder } = useBuilderTranslation(); const { canAdmin } = useOutletContext(); const { data: itemLoginSchema } = hooks.useItemLoginSchema({ itemId: item.id, }); + const { data: memberships } = hooks.useItemMemberships(item?.id); - if (itemLoginSchema) { + if (itemLoginSchema && memberships) { // show authenticated members if login schema is defined - // todo: show only if item is pseudomized + // todo: show only if item is pseudonymised return ( - <> + {translateBuilder(BUILDER.SHARING_AUTHENTICATED_MEMBERS_TITLE)} - im1.account.name > im2.account.name ? 1 : -1, - )} + memberships={selectHighestMemberships(memberships) + .filter((m) => isPseudoMember(m.account)) + .sort((im1, im2) => (im1.account.name > im2.account.name ? 1 : -1))} emptyMessage={translateBuilder( BUILDER.SHARING_AUTHENTICATED_MEMBERS_EMPTY_MESSAGE, )} showEmail={false} readOnly={!canAdmin} /> - + ); } - return null; + return false; }; export default ItemLoginMembershipsTable; diff --git a/src/components/item/sharing/ItemSharingTab.tsx b/src/components/item/sharing/ItemSharingTab.tsx index 0092c94e3..fbc9a1b00 100644 --- a/src/components/item/sharing/ItemSharingTab.tsx +++ b/src/components/item/sharing/ItemSharingTab.tsx @@ -1,8 +1,8 @@ -import { useOutletContext, useParams } from 'react-router-dom'; +import { useOutletContext } from 'react-router-dom'; -import { Container, Divider, Grid, Typography } from '@mui/material'; +import { Box, Container, Stack, Typography } from '@mui/material'; -import { AccountType, isPseudoMember } from '@graasp/sdk'; +import { AccountType } from '@graasp/sdk'; import { OutletType } from '@/components/pages/item/type'; import { selectHighestMemberships } from '@/utils/membership'; @@ -18,92 +18,96 @@ import VisibilitySelect from './VisibilitySelect'; import ImportUsersWithCSVButton from './csvImport/ImportUsersWithCSVButton'; import ShortLinksRenderer from './shortLink/ShortLinksRenderer'; -const ItemSharingTab = (): JSX.Element => { +const MembershipSettings = (): JSX.Element | null => { const { t: translateBuilder } = useBuilderTranslation(); const { item, canWrite, canAdmin } = useOutletContext(); - const { itemId } = useParams(); - const { data: memberships } = hooks.useItemMemberships(itemId); + const { data: rawMemberships } = hooks.useItemMemberships(item?.id); const { data: invitations } = hooks.useItemInvitations(item?.id); - const renderMembershipSettings = () => { - // do not display settings if cannot access memberships - if (!memberships || !canWrite) { - return null; - } + // do not display settings if cannot access memberships + if (!rawMemberships || !canWrite) { + return null; + } - return ( - <> - + const memberships = selectHighestMemberships(rawMemberships) + .filter((m) => m.account.type === AccountType.Individual) + .sort((im1, im2) => { + if (im1.account.type !== AccountType.Individual) { + return 1; + } + if (im2.account.type !== AccountType.Individual) { + return -1; + } + return im1.account.email > im2.account.email ? 1 : -1; + }); - - - {translateBuilder(BUILDER.SHARING_AUTHORIZED_MEMBERS_TITLE)} - - {canAdmin && } - - {canAdmin && ( + return ( + + {canAdmin && ( + <> - )} + + + )} + + + {translateBuilder(BUILDER.SHARING_AUTHORIZED_MEMBERS_TITLE)} + m.account.type === AccountType.Individual) - .sort((im1, im2) => { - if (im1.account.type !== AccountType.Individual) { - return 1; - } - if (im2.account.type !== AccountType.Individual) { - return -1; - } - return im1.account.email > im2.account.email ? 1 : -1; - })} + memberships={memberships} readOnly={!canAdmin} /> - isPseudoMember(m.account))} + + + + + {translateBuilder(BUILDER.SHARING_INVITATIONS_TITLE)} + + + + + ); +}; + +const ItemSharingTab = (): JSX.Element => { + const { t: translateBuilder } = useBuilderTranslation(); + const { item, canAdmin } = useOutletContext(); - {invitations && Boolean(invitations?.length) && ( - <> - - - {translateBuilder(BUILDER.SHARING_INVITATIONS_TITLE)} - - - - - )} - - ); - }; + const { data: memberships } = hooks.useItemMemberships(item?.id); return ( - - {translateBuilder(BUILDER.SHARING_TITLE)} - - - - {translateBuilder(BUILDER.ITEM_SETTINGS_VISIBILITY_TITLE)} - - - {renderMembershipSettings()} + + + + {translateBuilder(BUILDER.SHARING_TITLE)} + + + + + + {translateBuilder(BUILDER.ITEM_SETTINGS_VISIBILITY_TITLE)} + + + + + ); }; diff --git a/src/components/item/sharing/ResendInvitation.tsx b/src/components/item/sharing/ResendInvitation.tsx index c2a3ff922..54359645b 100644 --- a/src/components/item/sharing/ResendInvitation.tsx +++ b/src/components/item/sharing/ResendInvitation.tsx @@ -10,9 +10,14 @@ import { BUILDER } from '../../../langs/constants'; type Props = { invitationId: string; itemId: string; + disabled?: boolean; }; -const ResendInvitation = ({ itemId, invitationId }: Props): JSX.Element => { +const ResendInvitation = ({ + itemId, + invitationId, + disabled = false, +}: Props): JSX.Element => { const { t: translateBuilder } = useBuilderTranslation(); const { mutate: resendInvitation } = mutations.useResendInvitation(); @@ -27,7 +32,7 @@ const ResendInvitation = ({ itemId, invitationId }: Props): JSX.Element => {