From d5d374c311cab90f63958458d0819e890bf4456e Mon Sep 17 00:00:00 2001 From: Anthony LC Date: Fri, 24 May 2024 17:39:28 +0200 Subject: [PATCH] =?UTF-8?q?=F0=9F=9B=82(frontend)=20right=20pad=20editor?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Manage the right on the pad editor. If a use cannot edit a pad, the pad editor will be read-only. It will not save automatically. A message will be displayed to the user. --- .../__tests__/app-impress/pad-editor.spec.ts | 29 +++++++++++++++++++ .../pad-editor/components/BlockNoteEditor.tsx | 8 +++-- .../pads/pad-editor/components/PadEditor.tsx | 8 +++++ .../pads/pad-editor/hook/useSavePad.tsx | 10 +++++-- .../eslint-config-impress/playwright.js | 1 + 5 files changed, 51 insertions(+), 5 deletions(-) diff --git a/src/frontend/apps/e2e/__tests__/app-impress/pad-editor.spec.ts b/src/frontend/apps/e2e/__tests__/app-impress/pad-editor.spec.ts index 035bb9dd..9785259d 100644 --- a/src/frontend/apps/e2e/__tests__/app-impress/pad-editor.spec.ts +++ b/src/frontend/apps/e2e/__tests__/app-impress/pad-editor.spec.ts @@ -168,4 +168,33 @@ test.describe('Pad Editor', () => { await expect(page.getByText('Hello World Pad persisted 2')).toBeVisible(); }); + + test('it cannot edit if not the owner', async ({ page, browserName }) => { + const [padName] = await createPad( + page, + 'pad-right-edit', + browserName, + 1, + true, + ); + + await page.getByText('My account').click(); + await page.getByText('Logout').first().click(); + + await page.getByLabel('Restart login').click(); + + const browserNames = ['chromium', 'webkit']; + const newBrowserName = browserNames.find((name) => name !== browserName)!; + + await keyCloakSignIn(page, newBrowserName); + + const panel = page.getByLabel('Pads panel').first(); + await panel.getByText(padName).click(); + + await expect( + page.getByText( + "Read only, you don't have the right to update this document.", + ), + ).toBeVisible(); + }); }); diff --git a/src/frontend/apps/impress/src/features/pads/pad-editor/components/BlockNoteEditor.tsx b/src/frontend/apps/impress/src/features/pads/pad-editor/components/BlockNoteEditor.tsx index 74f36bd2..096844c6 100644 --- a/src/frontend/apps/impress/src/features/pads/pad-editor/components/BlockNoteEditor.tsx +++ b/src/frontend/apps/impress/src/features/pads/pad-editor/components/BlockNoteEditor.tsx @@ -38,7 +38,7 @@ interface BlockNoteContentProps { export const BlockNoteContent = ({ pad, provider }: BlockNoteContentProps) => { const { userData } = useAuthStore(); const { setEditor, padsStore } = usePadStore(); - useSavePad(pad.id, provider.doc); + useSavePad(pad.id, provider.doc, pad.abilities.partial_update); const storedEditor = padsStore?.[pad.id]?.editor; const editor = useMemo(() => { @@ -70,7 +70,11 @@ export const BlockNoteContent = ({ pad, provider }: BlockNoteContentProps) => { }; `} > - + diff --git a/src/frontend/apps/impress/src/features/pads/pad-editor/components/PadEditor.tsx b/src/frontend/apps/impress/src/features/pads/pad-editor/components/PadEditor.tsx index c09896b2..8d039870 100644 --- a/src/frontend/apps/impress/src/features/pads/pad-editor/components/PadEditor.tsx +++ b/src/frontend/apps/impress/src/features/pads/pad-editor/components/PadEditor.tsx @@ -1,3 +1,4 @@ +import { Alert, VariantType } from '@openfun/cunningham-react'; import React from 'react'; import { Box, Card, Text } from '@/components'; @@ -24,6 +25,13 @@ export const PadEditor = ({ pad }: PadEditorProps) => { + {!pad.abilities.partial_update && ( + + {`Read only, you don't have the right to update this document.`} + + )} { +const useSavePad = (padId: string, doc: Y.Doc, canSave: boolean) => { const { mutate: updatePad } = useUpdatePad(); const [initialDoc, setInitialDoc] = useState( toBase64(Y.encodeStateAsUpdate(doc)), ); + useEffect(() => { + setInitialDoc(toBase64(Y.encodeStateAsUpdate(doc))); + }, [doc]); + /** * Update initial doc when doc is updated by other users, * so only the user typing will trigger the save. @@ -42,7 +46,7 @@ const useSavePad = (padId: string, doc: Y.Doc) => { /** * Save only if the doc has changed. */ - if (initialDoc === newDoc) { + if (initialDoc === newDoc || !canSave) { return; } @@ -52,7 +56,7 @@ const useSavePad = (padId: string, doc: Y.Doc) => { id: padId, content: newDoc, }); - }, [initialDoc, padId, doc, updatePad]); + }, [initialDoc, padId, doc, updatePad, canSave]); const timeout = useRef(); const router = useRouter(); diff --git a/src/frontend/packages/eslint-config-impress/playwright.js b/src/frontend/packages/eslint-config-impress/playwright.js index 5fe67a80..c51edc5a 100644 --- a/src/frontend/packages/eslint-config-impress/playwright.js +++ b/src/frontend/packages/eslint-config-impress/playwright.js @@ -28,6 +28,7 @@ module.exports = { rules: { '@typescript-eslint/no-unsafe-member-access': 'off', '@typescript-eslint/no-unsafe-assignment': 'off', + '@typescript-eslint/no-non-null-assertion': 'off', }, }, ],