From 6b4bd2e59ca59f5074485e0ddcd8bc1911cf6f06 Mon Sep 17 00:00:00 2001 From: kim Date: Wed, 7 Feb 2024 17:11:04 +0100 Subject: [PATCH 1/4] feat: merge metadata and settings, add tags and geoloc --- cypress/fixtures/documents.ts | 71 +-- cypress/fixtures/etherpad.ts | 6 +- cypress/fixtures/files.ts | 249 +++++---- cypress/fixtures/h5p.ts | 8 +- cypress/fixtures/items.ts | 7 +- cypress/fixtures/links.ts | 79 +-- package.json | 6 +- src/components/common/CollapseButton.tsx | 27 +- src/components/common/PinButton.tsx | 19 +- src/components/common/ShowChatboxButton.tsx | 47 ++ .../item/header/ItemHeaderActions.tsx | 7 +- .../item/publish/CustomizedTagsEdit.tsx | 45 +- .../item/publish/ItemPublishTab.tsx | 1 - .../item/settings/AdminChatSettings.tsx | 9 +- .../item/settings/ClearChatButton.tsx | 14 +- src/components/item/settings/FileSettings.tsx | 2 +- .../item/settings/GeolocationPicker.tsx | 139 +++++ .../{ => settings}/ItemMetadataContent.tsx | 40 +- .../item/settings/ItemSettingProperty.tsx | 54 ++ src/components/item/settings/ItemSettings.tsx | 233 +------- .../item/settings/ItemSettingsProperties.tsx | 156 ++++++ .../item/settings/LanguageSelect.tsx | 29 + src/components/item/settings/LinkSettings.tsx | 2 +- src/components/item/settings/hooks.ts | 81 +++ .../pages/item/ItemInformationPage.tsx | 2 +- src/config/constants.ts | 1 - src/enums/index.ts | 14 +- src/langs/constants.ts | 31 ++ src/langs/en.json | 31 +- src/langs/fr.json | 30 +- yarn.lock | 520 ++++++++++++++++-- 31 files changed, 1417 insertions(+), 543 deletions(-) create mode 100644 src/components/common/ShowChatboxButton.tsx create mode 100644 src/components/item/settings/GeolocationPicker.tsx rename src/components/item/{ => settings}/ItemMetadataContent.tsx (79%) create mode 100644 src/components/item/settings/ItemSettingProperty.tsx create mode 100644 src/components/item/settings/ItemSettingsProperties.tsx create mode 100644 src/components/item/settings/LanguageSelect.tsx create mode 100644 src/components/item/settings/hooks.ts diff --git a/cypress/fixtures/documents.ts b/cypress/fixtures/documents.ts index 841045e86..5d0152d2a 100644 --- a/cypress/fixtures/documents.ts +++ b/cypress/fixtures/documents.ts @@ -1,11 +1,16 @@ -import { DocumentItemType, Item, ItemType } from '@graasp/sdk'; +import { + DocumentItemFactory, + DocumentItemType, + Item, + ItemType, +} from '@graasp/sdk'; import { DEFAULT_LANG } from '@graasp/translations'; import { buildDocumentExtra } from '../../src/utils/itemExtra'; import { DEFAULT_FOLDER_ITEM } from './items'; import { CURRENT_USER } from './members'; -export const GRAASP_DOCUMENT_ITEM: DocumentItemType = { +export const GRAASP_DOCUMENT_ITEM: DocumentItemType = DocumentItemFactory({ id: 'ecafbd2a-5688-12eb-ae91-0242ac130002', type: ItemType.DOCUMENT, name: 'graasp text', @@ -19,23 +24,23 @@ export const GRAASP_DOCUMENT_ITEM: DocumentItemType = { extra: buildDocumentExtra({ content: '

Some Title

', }), -}; +}); -export const GRAASP_DOCUMENT_BLANK_NAME_ITEM: DocumentItemType = { - id: 'ecafbd2a-5688-12eb-ae91-0242ac130004', - type: ItemType.DOCUMENT, - name: ' ', - description: 'a description for graasp text', - path: 'ecafbd2a_5688_12eb_ae93_0242ac130002', - settings: {}, - createdAt: '2021-08-11T12:56:36.834Z', - updatedAt: '2021-08-11T12:56:36.834Z', - lang: DEFAULT_LANG, - creator: CURRENT_USER, - extra: buildDocumentExtra({ - content: '

Some Title

', - }), -}; +export const GRAASP_DOCUMENT_BLANK_NAME_ITEM: DocumentItemType = + DocumentItemFactory({ + id: 'ecafbd2a-5688-12eb-ae91-0242ac130004', + type: ItemType.DOCUMENT, + name: ' ', + description: 'a description for graasp text', + path: 'ecafbd2a_5688_12eb_ae93_0242ac130002', + settings: {}, + createdAt: '2021-08-11T12:56:36.834Z', + updatedAt: '2021-08-11T12:56:36.834Z', + creator: CURRENT_USER, + extra: buildDocumentExtra({ + content: '

Some Title

', + }), + }); export const GRAASP_DOCUMENT_PARENT_FOLDER: Item = { ...DEFAULT_FOLDER_ITEM, @@ -44,21 +49,21 @@ export const GRAASP_DOCUMENT_PARENT_FOLDER: Item = { path: 'bdf09f5a_5688_11eb_ae93_0242ac130002', }; -export const GRAASP_DOCUMENT_CHILDREN_ITEM: DocumentItemType = { - id: '1cafbd2a-5688-12eb-ae91-0242ac130002', - type: ItemType.DOCUMENT, - name: 'children graasp text', - description: 'a description for graasp text', - path: 'bdf09f5a_5688_11eb_ae93_0242ac130002.1cafbd2a_5688_12eb_ae93_0242ac130002', - creator: CURRENT_USER, - settings: {}, - lang: DEFAULT_LANG, - createdAt: '2021-08-11T12:56:36.834Z', - updatedAt: '2021-08-11T12:56:36.834Z', - extra: buildDocumentExtra({ - content: '

Some Title

', - }), -}; +export const GRAASP_DOCUMENT_CHILDREN_ITEM: DocumentItemType = + DocumentItemFactory({ + id: '1cafbd2a-5688-12eb-ae91-0242ac130002', + type: ItemType.DOCUMENT, + name: 'children graasp text', + description: 'a description for graasp text', + path: 'bdf09f5a_5688_11eb_ae93_0242ac130002.1cafbd2a_5688_12eb_ae93_0242ac130002', + creator: CURRENT_USER, + settings: {}, + createdAt: '2021-08-11T12:56:36.834Z', + updatedAt: '2021-08-11T12:56:36.834Z', + extra: buildDocumentExtra({ + content: '

Some Title

', + }), + }); export const GRAASP_DOCUMENT_ITEMS_FIXTURE = [ GRAASP_DOCUMENT_ITEM, diff --git a/cypress/fixtures/etherpad.ts b/cypress/fixtures/etherpad.ts index c3a492464..c279ebd2d 100644 --- a/cypress/fixtures/etherpad.ts +++ b/cypress/fixtures/etherpad.ts @@ -1,10 +1,10 @@ -import { EtherpadItemType, ItemType } from '@graasp/sdk'; +import { EtherpadItemFactory, EtherpadItemType, ItemType } from '@graasp/sdk'; import { DEFAULT_LANG } from '@graasp/translations'; import { CURRENT_USER } from './members'; // eslint-disable-next-line import/prefer-default-export -export const GRAASP_ETHERPAD_ITEM: EtherpadItemType = { +export const GRAASP_ETHERPAD_ITEM: EtherpadItemType = EtherpadItemFactory({ id: 'ecaf1d2a-5688-11eb-ae91-0242ac130002', type: ItemType.ETHERPAD, name: 'graasp etherpad', @@ -21,4 +21,4 @@ export const GRAASP_ETHERPAD_ITEM: EtherpadItemType = { groupID: 'groupId', }, }, -}; +}); diff --git a/cypress/fixtures/files.ts b/cypress/fixtures/files.ts index a3d9775b0..657f62ba8 100644 --- a/cypress/fixtures/files.ts +++ b/cypress/fixtures/files.ts @@ -1,5 +1,9 @@ -import { ItemType, MaxWidth, MimeTypes } from '@graasp/sdk'; -import { DEFAULT_LANG } from '@graasp/translations'; +import { + ItemType, + LocalFileItemFactory, + MaxWidth, + MimeTypes, +} from '@graasp/sdk'; import { InternalItemType } from '../../src/config/types'; import { buildFileExtra, buildS3FileExtra } from '../../src/utils/itemExtra'; @@ -12,23 +16,24 @@ export const VIDEO_FILEPATH = 'files/video.mp4'; export const TEXT_FILEPATH = 'files/sometext.txt'; export const IMAGE_ITEM_DEFAULT: LocalFileItemForTest = { - id: 'bd5519a2-5ba9-4305-b221-185facbe6a99', - name: 'icon.png', - description: 'a default image description', - type: ItemType.LOCAL_FILE, - path: 'bd5519a2_5ba9_4305_b221_185facbe6a99', - creator: CURRENT_USER, - createdAt: '2021-03-16T16:00:50.968Z', - updatedAt: '2021-03-16T16:00:52.655Z', - settings: {}, - lang: DEFAULT_LANG, - extra: buildFileExtra({ + ...LocalFileItemFactory({ + id: 'bd5519a2-5ba9-4305-b221-185facbe6a99', name: 'icon.png', - path: '9a95/e2e1/2a7b-1615910428274', - size: 32439, - mimetype: 'image/png', - altText: 'myAltText', - content: '', + description: 'a default image description', + type: ItemType.LOCAL_FILE, + path: 'bd5519a2_5ba9_4305_b221_185facbe6a99', + creator: CURRENT_USER, + createdAt: '2021-03-16T16:00:50.968Z', + updatedAt: '2021-03-16T16:00:52.655Z', + settings: {}, + extra: buildFileExtra({ + name: 'icon.png', + path: '9a95/e2e1/2a7b-1615910428274', + size: 32439, + mimetype: 'image/png', + altText: 'myAltText', + content: '', + }), }), // for testing: creating needs a fixture, reading needs an url createFilepath: ICON_FILEPATH, @@ -36,25 +41,26 @@ export const IMAGE_ITEM_DEFAULT: LocalFileItemForTest = { }; export const IMAGE_ITEM_DEFAULT_WITH_MAX_WIDTH: LocalFileItemForTest = { - id: 'bd5519a2-5ba9-4305-b221-185facbe6a29', - name: 'icon.png', - description: 'a default image description', - type: ItemType.LOCAL_FILE, - path: 'bd5519a2_5ba9_4305_b221_185facbe6a29', - creator: CURRENT_USER, - createdAt: '2021-03-16T16:00:50.968Z', - updatedAt: '2021-03-16T16:00:52.655Z', - settings: { - maxWidth: MaxWidth.Medium, - }, - lang: DEFAULT_LANG, - extra: buildFileExtra({ + ...LocalFileItemFactory({ + id: 'bd5519a2-5ba9-4305-b221-185facbe6a29', name: 'icon.png', - path: '9a95/e2e1/2a7b-1615910428274', - size: 32439, - mimetype: 'image/png', - altText: 'myAltText', - content: '', + description: 'a default image description', + type: ItemType.LOCAL_FILE, + path: 'bd5519a2_5ba9_4305_b221_185facbe6a29', + creator: CURRENT_USER, + createdAt: '2021-03-16T16:00:50.968Z', + updatedAt: '2021-03-16T16:00:52.655Z', + settings: { + maxWidth: MaxWidth.Medium, + }, + extra: buildFileExtra({ + name: 'icon.png', + path: '9a95/e2e1/2a7b-1615910428274', + size: 32439, + mimetype: 'image/png', + altText: 'myAltText', + content: '', + }), }), // for testing: creating needs a fixture, reading needs an url createFilepath: ICON_FILEPATH, @@ -62,23 +68,24 @@ export const IMAGE_ITEM_DEFAULT_WITH_MAX_WIDTH: LocalFileItemForTest = { }; export const VIDEO_ITEM_DEFAULT: LocalFileItemForTest = { - id: 'qd5519a2-5ba9-4305-b221-185facbe6a99', - name: 'video.mp4', - description: 'a default video description', - type: ItemType.LOCAL_FILE, - path: 'qd5519a2_5ba9_4305_b221_185facbe6a99', - creator: CURRENT_USER, - createdAt: '2021-03-16T16:00:50.968Z', - updatedAt: '2021-03-16T16:00:52.655Z', - settings: {}, - lang: DEFAULT_LANG, - extra: buildFileExtra({ + ...LocalFileItemFactory({ + id: 'qd5519a2-5ba9-4305-b221-185facbe6a99', name: 'video.mp4', - path: '9a95/e2e1/2a7b-1615910428274', - size: 52345, - mimetype: MimeTypes.Video.MP4, - altText: 'myAltText', - content: '', + description: 'a default video description', + type: ItemType.LOCAL_FILE, + path: 'qd5519a2_5ba9_4305_b221_185facbe6a99', + creator: CURRENT_USER, + createdAt: '2021-03-16T16:00:50.968Z', + updatedAt: '2021-03-16T16:00:52.655Z', + settings: {}, + extra: buildFileExtra({ + name: 'video.mp4', + path: '9a95/e2e1/2a7b-1615910428274', + size: 52345, + mimetype: MimeTypes.Video.MP4, + altText: 'myAltText', + content: '', + }), }), // for testing: creating needs a fixture, reading needs an url createFilepath: VIDEO_FILEPATH, @@ -86,23 +93,24 @@ export const VIDEO_ITEM_DEFAULT: LocalFileItemForTest = { }; export const PDF_ITEM_DEFAULT: LocalFileItemForTest = { - id: 'cd5519a2-5ba9-4305-b221-185facbe6a99', - name: 'doc.pdf', - description: 'a default pdf description', - type: ItemType.LOCAL_FILE, - path: 'cd5519a2_5ba9_4305_b221_185facbe6a99', - creator: CURRENT_USER, - createdAt: '2021-03-16T16:00:50.968Z', - updatedAt: '2021-03-16T16:00:52.655Z', - settings: {}, - lang: DEFAULT_LANG, - extra: buildFileExtra({ + ...LocalFileItemFactory({ + id: 'cd5519a2-5ba9-4305-b221-185facbe6a99', name: 'doc.pdf', - path: '9a95/e2e1/2a7b-1615910428274', - size: 54321, - mimetype: MimeTypes.PDF, - altText: 'myAltText', - content: '', + description: 'a default pdf description', + type: ItemType.LOCAL_FILE, + path: 'cd5519a2_5ba9_4305_b221_185facbe6a99', + creator: CURRENT_USER, + createdAt: '2021-03-16T16:00:50.968Z', + updatedAt: '2021-03-16T16:00:52.655Z', + settings: {}, + extra: buildFileExtra({ + name: 'doc.pdf', + path: '9a95/e2e1/2a7b-1615910428274', + size: 54321, + mimetype: MimeTypes.PDF, + altText: 'myAltText', + content: '', + }), }), // for testing: creating needs a fixture, reading needs an url createFilepath: ICON_FILEPATH, @@ -115,23 +123,24 @@ export const ZIP_DEFAULT: ZIPInternalItem = { }; export const IMAGE_ITEM_S3: S3FileItemForTest = { - id: 'ad5519a2-5ba9-4305-b221-185facbe6a99', - name: 'icon.png', - description: 'a default image description', - type: ItemType.S3_FILE, - path: 'ad5519a2_5ba9_4305_b221_185facbe6a99', - creator: CURRENT_USER, - createdAt: '2021-03-16T16:00:50.968Z', - updatedAt: '2021-03-16T16:00:52.655Z', - settings: {}, - lang: DEFAULT_LANG, - extra: buildS3FileExtra({ - path: MOCK_IMAGE_URL, // for testing - size: 32439, - mimetype: MimeTypes.Image.PNG, - name: 'myfile', - altText: 'myAltText', - content: '', + ...S3FileItemFactory({ + id: 'ad5519a2-5ba9-4305-b221-185facbe6a99', + name: 'icon.png', + description: 'a default image description', + type: ItemType.S3_FILE, + path: 'ad5519a2_5ba9_4305_b221_185facbe6a99', + creator: CURRENT_USER, + createdAt: '2021-03-16T16:00:50.968Z', + updatedAt: '2021-03-16T16:00:52.655Z', + settings: {}, + extra: buildS3FileExtra({ + path: MOCK_IMAGE_URL, // for testing + size: 32439, + mimetype: MimeTypes.Image.PNG, + name: 'myfile', + altText: 'myAltText', + content: '', + }), }), // for testing: creating needs a fixture, reading needs an url createFilepath: ICON_FILEPATH, @@ -139,23 +148,24 @@ export const IMAGE_ITEM_S3: S3FileItemForTest = { }; export const VIDEO_ITEM_S3: S3FileItemForTest = { - id: 'qd5519a2-5ba9-4305-b221-185facbe6a93', - name: 'video.mp4', - description: 'a default video description', - type: ItemType.S3_FILE, - path: 'qd5519a2_5ba9_4305_b221_185facbe6a93', - creator: CURRENT_USER, - createdAt: '2021-03-16T16:00:50.968Z', - updatedAt: '2021-03-16T16:00:52.655Z', - settings: {}, - lang: DEFAULT_LANG, - extra: buildS3FileExtra({ - path: MOCK_VIDEO_URL, // for testing - size: 52345, - mimetype: MimeTypes.Video.MP4, - name: 'myfile', - altText: 'myAltText', - content: '', + ...S3FileItemFactory({ + id: 'qd5519a2-5ba9-4305-b221-185facbe6a93', + name: 'video.mp4', + description: 'a default video description', + type: ItemType.S3_FILE, + path: 'qd5519a2_5ba9_4305_b221_185facbe6a93', + creator: CURRENT_USER, + createdAt: '2021-03-16T16:00:50.968Z', + updatedAt: '2021-03-16T16:00:52.655Z', + settings: {}, + extra: buildS3FileExtra({ + path: MOCK_VIDEO_URL, // for testing + size: 52345, + mimetype: MimeTypes.Video.MP4, + name: 'myfile', + altText: 'myAltText', + content: '', + }), }), // for testing: creating needs a fixture, reading needs an url createFilepath: VIDEO_FILEPATH, @@ -163,23 +173,24 @@ export const VIDEO_ITEM_S3: S3FileItemForTest = { }; export const PDF_ITEM_S3: S3FileItemForTest = { - id: 'bd5519a2-5ba9-4305-b221-185facbe6a99', - name: 'doc.pdf', - description: 'a default pdf description', - type: ItemType.S3_FILE, - path: 'bd5519a2_5ba9_4305_b221_185facbe6a99', - creator: CURRENT_USER, - createdAt: '2021-03-16T16:00:50.968Z', - updatedAt: '2021-03-16T16:00:52.655Z', - settings: {}, - lang: DEFAULT_LANG, - extra: buildS3FileExtra({ - path: MOCK_PDF_URL, // for testing - size: 54321, - mimetype: MimeTypes.PDF, - name: 'myfile', - altText: 'myAltText', - content: '', + ...S3FileItemFactory({ + id: 'bd5519a2-5ba9-4305-b221-185facbe6a99', + name: 'doc.pdf', + description: 'a default pdf description', + type: ItemType.S3_FILE, + path: 'bd5519a2_5ba9_4305_b221_185facbe6a99', + creator: CURRENT_USER, + createdAt: '2021-03-16T16:00:50.968Z', + updatedAt: '2021-03-16T16:00:52.655Z', + settings: {}, + extra: buildS3FileExtra({ + path: MOCK_PDF_URL, // for testing + size: 54321, + mimetype: MimeTypes.PDF, + name: 'myfile', + altText: 'myAltText', + content: '', + }), }), // for testing: creating needs a fixture, reading needs an url createFilepath: ICON_FILEPATH, diff --git a/cypress/fixtures/h5p.ts b/cypress/fixtures/h5p.ts index e23e07fe0..c7376b316 100644 --- a/cypress/fixtures/h5p.ts +++ b/cypress/fixtures/h5p.ts @@ -1,10 +1,9 @@ -import { H5PItemType, ItemType } from '@graasp/sdk'; -import { DEFAULT_LANG } from '@graasp/translations'; +import { H5PItemFactory, H5PItemType, ItemType } from '@graasp/sdk'; import { CURRENT_USER } from './members'; // eslint-disable-next-line import/prefer-default-export -export const GRAASP_H5P_ITEM: H5PItemType = { +export const GRAASP_H5P_ITEM: H5PItemType = H5PItemFactory({ id: 'ecaf1d2a-5688-11eb-ae91-0242ac130002', type: ItemType.H5P, name: 'graasp h5p', @@ -12,7 +11,6 @@ export const GRAASP_H5P_ITEM: H5PItemType = { path: 'ecafbd2a_5688_11eb_ae93_0242ac130002', creator: CURRENT_USER, settings: {}, - lang: DEFAULT_LANG, createdAt: '2021-08-11T12:56:36.834Z', updatedAt: '2021-08-11T12:56:36.834Z', extra: { @@ -22,4 +20,4 @@ export const GRAASP_H5P_ITEM: H5PItemType = { contentFilePath: 'contentFilePath', }, }, -}; +}); diff --git a/cypress/fixtures/items.ts b/cypress/fixtures/items.ts index 747013676..42c3c612c 100644 --- a/cypress/fixtures/items.ts +++ b/cypress/fixtures/items.ts @@ -1,5 +1,6 @@ import { DiscriminatedItem, + FolderItemFactory, FolderItemType, ItemFavorite, ItemLoginSchemaType, @@ -12,12 +13,11 @@ import { RecycledItemData, ShortcutItemType, } from '@graasp/sdk'; -import { DEFAULT_LANG } from '@graasp/translations'; import { ApiConfig, ItemForTest } from '../support/types'; import { CURRENT_USER, MEMBERS } from './members'; -export const DEFAULT_FOLDER_ITEM: FolderItemType = { +export const DEFAULT_FOLDER_ITEM: FolderItemType = FolderItemFactory({ id: 'folder-id', name: 'folder', path: 'folder-path', @@ -28,8 +28,7 @@ export const DEFAULT_FOLDER_ITEM: FolderItemType = { updatedAt: '2020-01-01T01:01:01Z', description: 'mydescription', settings: {}, - lang: DEFAULT_LANG, -}; +}); export const CREATED_ITEM: Partial = { name: 'created item', diff --git a/cypress/fixtures/links.ts b/cypress/fixtures/links.ts index 8f122e71b..fc0777d0c 100644 --- a/cypress/fixtures/links.ts +++ b/cypress/fixtures/links.ts @@ -1,10 +1,13 @@ -import { EmbeddedLinkItemType, ItemType } from '@graasp/sdk'; -import { DEFAULT_LANG } from '@graasp/translations'; +import { + EmbeddedLinkItemFactory, + EmbeddedLinkItemType, + ItemType, +} from '@graasp/sdk'; import { buildEmbeddedLinkExtra } from '../../src/utils/itemExtra'; import { CURRENT_USER } from './members'; -export const GRAASP_LINK_ITEM: EmbeddedLinkItemType = { +export const GRAASP_LINK_ITEM: EmbeddedLinkItemType = EmbeddedLinkItemFactory({ id: 'ecafbd2a-5688-11eb-ae91-0242ac130002', type: ItemType.LINK, name: 'graasp link', @@ -12,7 +15,6 @@ export const GRAASP_LINK_ITEM: EmbeddedLinkItemType = { path: 'ecafbd2a_5688_11eb_ae93_0242ac130002', creator: CURRENT_USER, settings: {}, - lang: DEFAULT_LANG, createdAt: '2021-08-11T12:56:36.834Z', updatedAt: '2021-08-11T12:56:36.834Z', extra: buildEmbeddedLinkExtra({ @@ -23,45 +25,45 @@ export const GRAASP_LINK_ITEM: EmbeddedLinkItemType = { 'https://graasp.eu/cdn/img/epfl/favicons/favicon-32x32.png?v=yyxJ380oWY', ], }), -}; +}); -export const GRAASP_LINK_ITEM_NO_PROTOCOL: EmbeddedLinkItemType = { - id: 'ecafbd2a-5688-11eb-ae91-0242ac130002', - type: ItemType.LINK, - name: 'graasp link', - description: 'a description for graasp link', - path: 'ecafbd2a_5688_11eb_ae93_0242ac130002', - creator: CURRENT_USER, - settings: {}, - lang: DEFAULT_LANG, - createdAt: '2021-08-11T12:56:36.834Z', - updatedAt: '2021-08-11T12:56:36.834Z', - extra: buildEmbeddedLinkExtra({ - url: 'graasp.eu', - html: '', - thumbnails: ['https://graasp.eu/img/epfl/logo-tile.png'], - icons: [ - 'https://graasp.eu/cdn/img/epfl/favicons/favicon-32x32.png?v=yyxJ380oWY', - ], - }), -}; +export const GRAASP_LINK_ITEM_NO_PROTOCOL: EmbeddedLinkItemType = + EmbeddedLinkItemFactory({ + id: 'ecafbd2a-5688-11eb-ae91-0242ac130002', + type: ItemType.LINK, + name: 'graasp link', + description: 'a description for graasp link', + path: 'ecafbd2a_5688_11eb_ae93_0242ac130002', + creator: CURRENT_USER, + settings: {}, + createdAt: '2021-08-11T12:56:36.834Z', + updatedAt: '2021-08-11T12:56:36.834Z', + extra: buildEmbeddedLinkExtra({ + url: 'graasp.eu', + html: '', + thumbnails: ['https://graasp.eu/img/epfl/logo-tile.png'], + icons: [ + 'https://graasp.eu/cdn/img/epfl/favicons/favicon-32x32.png?v=yyxJ380oWY', + ], + }), + }); -export const GRAASP_LINK_ITEM_IFRAME_ONLY: EmbeddedLinkItemType = { - ...GRAASP_LINK_ITEM, - id: 'ecafbd2a-5688-11eb-ae91-0242ac130122', - settings: { - showLinkIframe: true, - showLinkButton: false, - }, -}; +export const GRAASP_LINK_ITEM_IFRAME_ONLY: EmbeddedLinkItemType = + EmbeddedLinkItemFactory({ + ...GRAASP_LINK_ITEM, + id: 'ecafbd2a-5688-11eb-ae91-0242ac130122', + settings: { + showLinkIframe: true, + showLinkButton: false, + }, + }); -export const YOUTUBE_LINK_ITEM: EmbeddedLinkItemType = { +export const YOUTUBE_LINK_ITEM: EmbeddedLinkItemType = EmbeddedLinkItemFactory({ id: 'gcafbd2a-5688-11eb-ae93-0242ac130002', type: ItemType.LINK, name: 'graasp youtube link', description: 'a description for graasp youtube link', settings: {}, - lang: DEFAULT_LANG, createdAt: '2021-08-11T12:56:36.834Z', updatedAt: '2021-08-11T12:56:36.834Z', creator: CURRENT_USER, @@ -72,15 +74,14 @@ export const YOUTUBE_LINK_ITEM: EmbeddedLinkItemType = { thumbnails: ['https://i.ytimg.com/vi/FmiEgBMTPLo/maxresdefault.jpg'], icons: ['https://www.youtube.com/s/desktop/f0ff6c1d/img/favicon_96.png'], }), -}; +}); -export const INVALID_LINK_ITEM: EmbeddedLinkItemType = { +export const INVALID_LINK_ITEM: EmbeddedLinkItemType = EmbeddedLinkItemFactory({ id: 'gcafbd2a-5688-11eb-ae93-0242ac130001', path: 'gcafbd2a_5688_11eb_ae93_0242ac130001', type: ItemType.LINK, creator: CURRENT_USER, settings: {}, - lang: DEFAULT_LANG, createdAt: '2021-08-11T12:56:36.834Z', updatedAt: '2021-08-11T12:56:36.834Z', name: 'graasp youtube link', @@ -91,4 +92,4 @@ export const INVALID_LINK_ITEM: EmbeddedLinkItemType = { thumbnails: [], icons: [], }), -}; +}); diff --git a/package.json b/package.json index a0bba17e2..991d5b78c 100644 --- a/package.json +++ b/package.json @@ -20,10 +20,10 @@ "@emotion/react": "11.11.3", "@emotion/styled": "11.11.0", "@graasp/chatbox": "3.0.3", - "@graasp/query-client": "2.6.0", + "@graasp/query-client": "github:graasp/graasp-query-client#geolocation-address", "@graasp/sdk": "3.8.1", "@graasp/translations": "1.23.0", - "@graasp/ui": "4.7.0", + "@graasp/ui": "github:graasp/graasp-ui#navigation-icon", "@mui/icons-material": "5.15.8", "@mui/lab": "5.0.0-alpha.162", "@mui/material": "5.15.8", @@ -42,6 +42,7 @@ "filesize": "10.1.0", "http-status-codes": "2.3.0", "katex": "0.16.9", + "leaflet-geosearch": "3.11.0", "lodash.debounce": "4.0.8", "lodash.groupby": "4.6.0", "lodash.isequal": "4.5.0", @@ -113,6 +114,7 @@ "@testing-library/user-event": "^14.5.2", "@trivago/prettier-plugin-sort-imports": "4.3.0", "@types/jest": "29.5.12", + "@types/leaflet": "^1", "@types/lodash.debounce": "4.0.9", "@types/lodash.groupby": "4.6.9", "@types/lodash.isequal": "4.5.8", diff --git a/src/components/common/CollapseButton.tsx b/src/components/common/CollapseButton.tsx index 05659b0a3..0ec037431 100644 --- a/src/components/common/CollapseButton.tsx +++ b/src/components/common/CollapseButton.tsx @@ -3,7 +3,7 @@ import { useEffect, useState } from 'react'; import { ExpandLess, ExpandMore } from '@mui/icons-material'; import { IconButton, ListItemIcon, MenuItem, Tooltip } from '@mui/material'; -import { Item } from '@graasp/sdk'; +import { DiscriminatedItem, ItemType } from '@graasp/sdk'; import { ActionButton, ActionButtonVariant } from '@graasp/ui'; import { useBuilderTranslation } from '../../config/i18n'; @@ -12,15 +12,19 @@ import { COLLAPSE_ITEM_BUTTON_CLASS } from '../../config/selectors'; import { BUILDER } from '../../langs/constants'; type Props = { - item: Item; + item: DiscriminatedItem; type?: ActionButtonVariant; onClick?: () => void; + isCollapsedTextKey?: string; + notCollapsedTextKey?: string; }; const CollapseButton = ({ item, type = ActionButton.ICON_BUTTON, onClick, + isCollapsedTextKey = BUILDER.COLLAPSE_ITEM_UNCOLLAPSE_TEXT, + notCollapsedTextKey = BUILDER.COLLAPSE_ITEM_COLLAPSE_TEXT, }: Props): JSX.Element => { const { t: translateBuilder } = useBuilderTranslation(); @@ -33,6 +37,8 @@ const CollapseButton = ({ setIsCollapsible(item?.settings?.isCollapsible ?? false); }, [item]); + const disabled = item.type === ItemType.FOLDER; + const handleCollapse = () => { editItem({ id: item.id, @@ -44,10 +50,15 @@ const CollapseButton = ({ onClick?.(); }; - const icon = isCollapsible ? : ; - const text = isCollapsible - ? translateBuilder(BUILDER.COLLAPSE_ITEM_UNCOLLAPSE_TEXT) - : translateBuilder(BUILDER.COLLAPSE_ITEM_COLLAPSE_TEXT); + const icon = isCollapsible ? : ; + let text; + if (disabled) { + text = translateBuilder(BUILDER.SETTINGS_COLLAPSE_FOLDER_INFORMATION); + } else { + text = translateBuilder( + isCollapsible ? isCollapsedTextKey : notCollapsedTextKey, + ); + } switch (type) { case ActionButton.MENU_ITEM: @@ -56,17 +67,21 @@ const CollapseButton = ({ key={text} onClick={handleCollapse} className={COLLAPSE_ITEM_BUTTON_CLASS} + disabled={disabled} > {icon} {text} ); + case ActionButton.ICON: + return icon; case ActionButton.ICON_BUTTON: default: return ( void; + pinTextKey?: string; + unPinTextKey?: string; }; -const PinButton = ({ item, type, onClick }: Props): JSX.Element => { +const PinButton = ({ + item, + type, + onClick, + pinTextKey = BUILDER.PIN_ITEM_PIN_TEXT, + unPinTextKey = BUILDER.PIN_ITEM_UNPIN_TEXT, +}: Props): JSX.Element => { const { t: translateBuilder } = useBuilderTranslation(); const editItem = mutations.useEditItem(); @@ -33,11 +41,12 @@ const PinButton = ({ item, type, onClick }: Props): JSX.Element => { onClick?.(); }; - const pinText = translateBuilder(BUILDER.PIN_ITEM_PIN_TEXT); - const unPinText = translateBuilder(BUILDER.PIN_ITEM_UNPIN_TEXT); + const pinText = translateBuilder(pinTextKey); + const unPinText = translateBuilder(unPinTextKey); return ( { + const { t: translateBuilder } = useBuilderTranslation(); + + const editItem = mutations.useEditItem(); + const showChatbox = item?.settings?.showChatbox; + + const onClick = () => { + editItem.mutate({ + id: item.id, + name: item.name, + settings: { + showChatbox: !showChatbox, + }, + }); + }; + + return ( + + ); +}; + +export default ShowChatboxButton; diff --git a/src/components/item/header/ItemHeaderActions.tsx b/src/components/item/header/ItemHeaderActions.tsx index 8dd2ae341..2a7a3b57c 100644 --- a/src/components/item/header/ItemHeaderActions.tsx +++ b/src/components/item/header/ItemHeaderActions.tsx @@ -17,7 +17,6 @@ import { getHighestPermissionForMemberFromMemberships, isItemUpdateAllowedForUser, } from '../../../utils/membership'; -import ItemMetadataButton from '../../common/ItemMetadataButton'; import PublishButton from '../../common/PublishButton'; import ShareButton from '../../common/ShareButton'; import { useCurrentUserContext } from '../../context/CurrentUserContext'; @@ -65,6 +64,7 @@ const ItemHeaderActions = (): JSX.Element => { const activeActions = ( <> {showEditButton && } + {/* prevent moving from top header to avoid confusion */} { { return ( <> {activeActions} - {canEdit && } - + ); } @@ -101,7 +101,6 @@ const ItemHeaderActions = (): JSX.Element => { // show only for content with tables : root or folders (item?.type === ItemType.FOLDER || !item?.id) && } - {item?.id && } ); }; diff --git a/src/components/item/publish/CustomizedTagsEdit.tsx b/src/components/item/publish/CustomizedTagsEdit.tsx index cbc61265d..544e8e9ef 100644 --- a/src/components/item/publish/CustomizedTagsEdit.tsx +++ b/src/components/item/publish/CustomizedTagsEdit.tsx @@ -1,6 +1,6 @@ import { useEffect, useState } from 'react'; -import { Chip, TextField, Typography } from '@mui/material'; +import { Chip, Stack, TextField, Typography } from '@mui/material'; import type { TextFieldProps } from '@mui/material'; import { DiscriminatedItem } from '@graasp/sdk'; @@ -67,27 +67,36 @@ const CustomizedTagsEdit = ({ item, disabled }: Props): JSX.Element => { {translateBuilder(BUILDER.ITEM_TAGS_INFORMATION)} - - + + + + + + + + {settings?.tags?.length && ( <> - + {translateBuilder(BUILDER.ITEM_TAGS_PREVIEW_TITLE)} +
{settings?.tags?.map((tag, index) => ( { const itemId = item.id; + const { t } = useBuilderTranslation(); const { data: itemPermissions, isLoading: isLoadingItemPermissions } = hooks.useItemMemberships(item.id); const { data: currentMember } = useCurrentUserContext(); @@ -29,6 +33,9 @@ const AdminChatSettings = ({ item }: Props): JSX.Element | null => { return ( + + {t(BUILDER.ITEM_SETTINGS_CHAT_SETTINGS_TITLE)} + { const [openConfirmation, setOpenConfirmation] = useState(false); const { t } = useChatboxTranslation(); + const { t: translateBuilder } = useBuilderTranslation(); if (!clearChat) { return null; @@ -83,9 +89,7 @@ const ClearChatButton = ({ {getContent(variant)} - {t( - 'Careful, this will delete all the messages in this item. Make sure you have a backup. You can download a backup from Graasp Analytics.', - )} + {translateBuilder(BUILDER.ITEM_SETTINGS_CLEAR_CHAT_EXPLANATION)} @@ -96,7 +100,7 @@ const ClearChatButton = ({ {t(CHATBOX.CLEAR_ALL_CHAT_CONTENT)}
- {t('You can download a backup from Graasp Analytics.')} + {translateBuilder(BUILDER.ITEM_SETTINGS_CLEAR_CHAT_BACKUP_TEXT)} diff --git a/src/components/item/settings/FileSettings.tsx b/src/components/item/settings/FileSettings.tsx index d5f50f83b..1a10bd42d 100644 --- a/src/components/item/settings/FileSettings.tsx +++ b/src/components/item/settings/FileSettings.tsx @@ -26,7 +26,7 @@ const FileSettings = ({ return ( - + {translateBuilder(BUILDER.SETTINGS_FILE_SETTINGS_TITLE)} diff --git a/src/components/item/settings/GeolocationPicker.tsx b/src/components/item/settings/GeolocationPicker.tsx new file mode 100644 index 000000000..e8d1ed385 --- /dev/null +++ b/src/components/item/settings/GeolocationPicker.tsx @@ -0,0 +1,139 @@ +import { ChangeEventHandler } from 'react'; + +import Clear from '@mui/icons-material/Clear'; +import { + Box, + IconButton, + LinearProgress, + List, + ListItemButton, + Stack, + TextField, + Tooltip, + Typography, +} from '@mui/material'; + +import { DiscriminatedItem } from '@graasp/sdk'; + +import { SearchResult } from 'leaflet-geosearch/dist/providers/provider'; + +import { useBuilderTranslation } from '@/config/i18n'; +import { hooks, mutations } from '@/config/queryClient'; +import { BUILDER } from '@/langs/constants'; + +import { useSearchAddress } from './hooks'; + +const GeolocationPicker = ({ + item, +}: { + item: DiscriminatedItem; +}): JSX.Element => { + const { t } = useBuilderTranslation(); + const { data: geoloc } = hooks.useItemGeolocation(item.id); + const { mutate: putGeoloc } = mutations.usePutItemGeolocation(); + const { mutate: deleteGeoloc } = mutations.useDeleteItemGeolocation(); + + const { + query, + setQuery, + isDebounced, + setResults, + results, + loading, + clearQuery, + } = useSearchAddress({ + lang: item.lang, + geoloc, + }); + + const onChange: ChangeEventHandler = (e) => { + setQuery(e.target.value); + }; + + const onChangeOption = (option: SearchResult): void => { + const { + raw: { lat, lon: lng }, + label, + } = option; + putGeoloc({ + itemId: item.id, + geolocation: { lng, lat, addressLabel: label }, + }); + setResults([]); + }; + + const clearGeoloc = () => { + deleteGeoloc({ itemId: item.id }); + clearQuery(); + }; + + // the input is disabled if the geoloc is defined in parent + // but it should be enabled if the geoloc is not defined + const isDisabled = Boolean(geoloc && geoloc?.item?.id !== item.id); + + return ( + + + + {t(BUILDER.ITEM_SETTINGS_GEOLOCATION_TITLE)} + + + {t(BUILDER.ITEM_SETTINGS_GEOLOCATION_EXPLANATION)} + + + + + + {loading && ( + + + + )} + + {query && !isDisabled && ( + + + + + + + + )} + + {isDisabled && ( + + {t(BUILDER.ITEM_SETTINGS_GEOLOCATION_INHERITED_EXPLANATION)} + + )} + + {results && ( + + {results.map((r) => ( + onChangeOption(r)} + > + {r.label} + + ))} + {!results.length && + query && + query !== geoloc?.addressLabel && + !loading && + !isDebounced && + t(BUILDER.ITEM_SETTINGS_GEOLOCATION_NO_ADDRESS)} + + )} + + + ); +}; + +export default GeolocationPicker; diff --git a/src/components/item/ItemMetadataContent.tsx b/src/components/item/settings/ItemMetadataContent.tsx similarity index 79% rename from src/components/item/ItemMetadataContent.tsx rename to src/components/item/settings/ItemMetadataContent.tsx index c6f4c5d43..ad7d97a18 100644 --- a/src/components/item/ItemMetadataContent.tsx +++ b/src/components/item/settings/ItemMetadataContent.tsx @@ -1,14 +1,11 @@ import { useOutletContext } from 'react-router-dom'; -import { - Container, - Table, - TableBody, - TableCell, - TableContainer, - TableRow, - Typography, -} from '@mui/material'; +import Table from '@mui/material/Table'; +import TableBody from '@mui/material/TableBody'; +import TableCell from '@mui/material/TableCell'; +import TableContainer from '@mui/material/TableContainer'; +import TableRow from '@mui/material/TableRow'; +import Typography from '@mui/material/Typography'; import { ItemType, @@ -21,15 +18,16 @@ import { COMMON } from '@graasp/translations'; import i18n, { useBuilderTranslation, useCommonTranslation, -} from '../../config/i18n'; -import { hooks } from '../../config/queryClient'; +} from '../../../config/i18n'; +import { hooks } from '../../../config/queryClient'; import { ITEM_PANEL_NAME_ID, ITEM_PANEL_TABLE_ID, -} from '../../config/selectors'; -import { BUILDER } from '../../langs/constants'; -import { OutletType } from '../pages/item/type'; -import ThumbnailSetting from './settings/ThumbnailSetting'; +} from '../../../config/selectors'; +import { BUILDER } from '../../../langs/constants'; +import { OutletType } from '../../pages/item/type'; +import LanguageSelect from './LanguageSelect'; +import ThumbnailSetting from './ThumbnailSetting'; const { useMember } = hooks; @@ -71,7 +69,7 @@ const ItemMetadataContent = (): JSX.Element => { }; return ( - + <> @@ -127,10 +125,18 @@ const ItemMetadataContent = (): JSX.Element => { {renderLink()} + + + {translateBuilder(BUILDER.ITEM_METADATA_LANGUAGE_TITLE)} + + + + + - + ); }; diff --git a/src/components/item/settings/ItemSettingProperty.tsx b/src/components/item/settings/ItemSettingProperty.tsx new file mode 100644 index 000000000..7e86307e3 --- /dev/null +++ b/src/components/item/settings/ItemSettingProperty.tsx @@ -0,0 +1,54 @@ +import { Stack, Switch, Typography } from '@mui/material'; + +type Props = { + onClick: (checked: boolean) => void; + title: string; + checked: boolean; + valueText: string; + id?: string; + disabled?: boolean; + icon?: JSX.Element; +}; + +const ItemSettingProperty = ({ + onClick, + title, + checked = false, + id, + disabled, + icon, + valueText, +}: Props): JSX.Element => ( + + + {icon} + + + + {title} + + + + {valueText} + + + + + { + onClick(e.target.checked); + }} + /> + + +); + +export default ItemSettingProperty; diff --git a/src/components/item/settings/ItemSettings.tsx b/src/components/item/settings/ItemSettings.tsx index 7db92a59e..f718b5ba0 100644 --- a/src/components/item/settings/ItemSettings.tsx +++ b/src/components/item/settings/ItemSettings.tsx @@ -1,236 +1,27 @@ -import { useEffect, useState } from 'react'; -import { Trans } from 'react-i18next'; -import { Link, useOutletContext } from 'react-router-dom'; +import { useOutletContext } from 'react-router-dom'; -import { Info } from '@mui/icons-material'; -import { - Alert, - Container, - FormControlLabel, - FormGroup, - Switch, - Tooltip, - Typography, -} from '@mui/material'; - -import { DiscriminatedItem, ItemType } from '@graasp/sdk'; +import Container from '@mui/material/Container'; import { OutletType } from '@/components/pages/item/type'; -import { buildItemInformationPath } from '@/config/paths'; -import { - DEFAULT_COLLAPSIBLE_SETTING, - DEFAULT_PINNED_SETTING, - DEFAULT_RESIZE_SETTING, - DEFAULT_SAVE_ACTIONS_SETTING, - DEFAULT_SHOW_CHATBOX_SETTING, -} from '../../../config/constants'; -import { useBuilderTranslation } from '../../../config/i18n'; -import { mutations } from '../../../config/queryClient'; -import { - SETTINGS_CHATBOX_TOGGLE_ID, - SETTINGS_COLLAPSE_TOGGLE_ID, - SETTINGS_PINNED_TOGGLE_ID, - SETTINGS_RESIZE_TOGGLE_ID, - SETTINGS_SAVE_ACTIONS_TOGGLE_ID, -} from '../../../config/selectors'; -import { BUILDER } from '../../../langs/constants'; +import CustomizedTagsEdit from '../publish/CustomizedTagsEdit'; import AdminChatSettings from './AdminChatSettings'; -import FileSettings from './FileSettings'; -import LinkSettings from './LinkSettings'; +import GeolocationPicker from './GeolocationPicker'; +import ItemMetadataContent from './ItemMetadataContent'; +import ItemSettingsProperties from './ItemSettingsProperties'; const ItemSettings = (): JSX.Element => { - const { t: translateBuilder } = useBuilderTranslation(); const { item } = useOutletContext(); - const { mutate: editItem } = mutations.useEditItem(); - - const { settings } = item; - - const [settingLocal, setSettingLocal] = - useState(settings); - - useEffect( - () => { - if (settings) { - // this is used because we get a response where the setting only contains the modified setting - // so it make the toggles flicker. - // by only overriding keys that changes we are able to remove the flicker effect - - setSettingLocal((previousSettings) => ({ - ...previousSettings, - ...settings, - })); - } - }, - // eslint-disable-next-line react-hooks/exhaustive-deps - [settings], - ); - - const handleOnToggle = ( - event: { target: { checked: boolean } }, - settingKey: string, - ): void => { - const newValue = event.target.checked; - setSettingLocal({ - ...settingLocal, - [settingKey]: newValue, - }); - editItem({ - id: item.id, - name: item.name, - settings: { - [settingKey]: newValue, - }, - }); - }; - - const renderPinSetting = () => { - const control = ( - handleOnToggle(e, 'isPinned')} - checked={settingLocal?.isPinned || DEFAULT_PINNED_SETTING} - color="primary" - /> - ); - return ( - - ); - }; - - const renderChatSetting = () => { - const control = ( - handleOnToggle(e, 'showChatbox')} - checked={settingLocal?.showChatbox || DEFAULT_SHOW_CHATBOX_SETTING} - color="primary" - /> - ); - return ( - - ); - }; - - const renderResizeSetting = () => { - const control = ( - handleOnToggle(e, 'isResizable')} - checked={settingLocal?.isResizable || DEFAULT_RESIZE_SETTING} - color="primary" - /> - ); - return ( - - ); - }; - - const renderCollapseSetting = () => { - const disabled = item.type === ItemType.FOLDER; - const control = ( - handleOnToggle(e, 'isCollapsible')} - checked={settingLocal?.isCollapsible || DEFAULT_COLLAPSIBLE_SETTING} - color="primary" - disabled={disabled} - /> - ); - const formLabel = ( - - ); - const tooltip = disabled ? ( - - - - - - ) : null; - return ( -
- {formLabel} - {tooltip} -
- ); - }; - - const renderSaveActionsSetting = () => { - const control = ( - - - handleOnToggle(e, 'enableSaveActions')} - checked={ - settingLocal?.enableSaveActions ?? DEFAULT_SAVE_ACTIONS_SETTING - } - color="primary" - disabled - /> - - - ); - return ( - - ); - }; + return ( + + + - const renderSettingsPerType = () => { - switch (item.type) { - case ItemType.LINK: - return ; - case ItemType.S3_FILE: - case ItemType.LOCAL_FILE: - return ; - default: - return null; - } - }; + - return ( - - - , - }} - /> - - - {translateBuilder(BUILDER.SETTINGS_TITLE)} - + - - {renderPinSetting()} - {renderCollapseSetting()} - {item.type === ItemType.APP && renderResizeSetting()} - {renderChatSetting()} - {renderSaveActionsSetting()} - - {renderSettingsPerType()} ); diff --git a/src/components/item/settings/ItemSettingsProperties.tsx b/src/components/item/settings/ItemSettingsProperties.tsx new file mode 100644 index 000000000..d121b0771 --- /dev/null +++ b/src/components/item/settings/ItemSettingsProperties.tsx @@ -0,0 +1,156 @@ +import { Typography } from '@mui/material'; + +import { DiscriminatedItem, ItemType } from '@graasp/sdk'; +import { ActionButton, ChatboxButton, PinButton } from '@graasp/ui'; + +import CollapseButton from '@/components/common/CollapseButton'; +import { + DEFAULT_RESIZE_SETTING, + DEFAULT_SAVE_ACTIONS_SETTING, +} from '@/config/constants'; +import { useBuilderTranslation } from '@/config/i18n'; +import { mutations } from '@/config/queryClient'; +import { + SETTINGS_RESIZE_TOGGLE_ID, + SETTINGS_SAVE_ACTIONS_TOGGLE_ID, +} from '@/config/selectors'; +import { BUILDER } from '@/langs/constants'; + +import FileSettings from './FileSettings'; +import ItemSettingProperty from './ItemSettingProperty'; +import LinkSettings from './LinkSettings'; + +type Props = { + item: DiscriminatedItem; +}; + +const ItemSettingsProperties = ({ item }: Props): JSX.Element => { + const { t: translateBuilder } = useBuilderTranslation(); + const { mutate: editItem } = mutations.useEditItem(); + + const { settings } = item; + + const handleOnToggle = ( + event: { target: { checked: boolean } }, + settingKey: string, + ): void => { + const newValue = event.target.checked; + editItem({ + id: item.id, + name: item.name, + settings: { + [settingKey]: newValue, + }, + }); + }; + + const renderSettingsPerType = () => { + switch (item.type) { + case ItemType.LINK: + return ; + case ItemType.S3_FILE: + case ItemType.LOCAL_FILE: + return ; + default: + return null; + } + }; + + return ( + <> + + {translateBuilder(BUILDER.SETTINGS_TITLE)} + + } + checked={Boolean(settings.isCollapsible)} + disabled={item.type === ItemType.FOLDER} + onClick={(checked: boolean): void => { + handleOnToggle({ target: { checked } }, 'isCollapsible'); + }} + valueText={(() => { + if (item.type === ItemType.FOLDER) { + return translateBuilder( + BUILDER.SETTINGS_COLLAPSE_FOLDER_INFORMATION, + ); + } + return settings.isCollapsible + ? translateBuilder(BUILDER.ITEM_SETTINGS_IS_COLLAPSED_ENABLED_TEXT) + : translateBuilder( + BUILDER.ITEM_SETTINGS_IS_COLLAPSED_DISABLED_TEXT, + ); + })()} + /> + + + } + title={translateBuilder(BUILDER.ITEM_SETTINGS_IS_PINNED_TITLE)} + checked={Boolean(settings.isPinned)} + onClick={(checked: boolean): void => { + handleOnToggle({ target: { checked } }, 'isPinned'); + }} + valueText={ + settings.isPinned + ? translateBuilder(BUILDER.ITEM_SETTINGS_IS_PINNED_ENABLED_TEXT) + : translateBuilder(BUILDER.ITEM_SETTINGS_IS_PINNED_DISABLED_TEXT) + } + /> + + + } + title={translateBuilder(BUILDER.ITEM_SETTINGS_SHOW_CHAT_TITLE)} + checked={Boolean(settings.showChatbox)} + onClick={(checked: boolean): void => { + handleOnToggle({ target: { checked } }, 'showChatbox'); + }} + valueText={ + settings.showChatbox + ? translateBuilder(BUILDER.ITEM_SETTINGS_SHOW_CHAT_ENABLED_TEXT) + : translateBuilder(BUILDER.ITEM_SETTINGS_SHOW_CHAT_DISABLED_TEXT) + } + /> + { + handleOnToggle({ target: { checked } }, 'enableAnalytics'); + }} + valueText="Coming soon" + disabled + /> + + {item.type === ItemType.APP && ( + { + handleOnToggle({ target: { checked } }, 'isResizable'); + }} + valueText={ + settings?.isResizable + ? translateBuilder(BUILDER.ITEM_SETTINGS_RESIZABLE_ENABLED_TEXT) + : translateBuilder(BUILDER.ITEM_SETTINGS_RESIZABLE_DISABLED_TEXT) + } + /> + )} + {renderSettingsPerType()} + + ); +}; + +export default ItemSettingsProperties; diff --git a/src/components/item/settings/LanguageSelect.tsx b/src/components/item/settings/LanguageSelect.tsx new file mode 100644 index 000000000..6777b5316 --- /dev/null +++ b/src/components/item/settings/LanguageSelect.tsx @@ -0,0 +1,29 @@ +import { SelectProps } from '@mui/material'; + +import { DiscriminatedItem } from '@graasp/sdk'; +import { langs } from '@graasp/translations'; +import { Select } from '@graasp/ui'; + +import { mutations } from '@/config/queryClient'; + +const LanguageSelect = ({ item }: { item: DiscriminatedItem }): JSX.Element => { + const { mutate: changeLang } = mutations.useEditItem(); + + const onChange: SelectProps['onChange'] = (e) => { + const { value: newLang } = e.target; + changeLang({ id: item.id, lang: newLang as string }); + }; + + const values = Object.entries(langs).map(([k, v]) => ({ value: k, text: v })); + + return ( + { + const { data: memberships, isLoading: isMembershipsLoading } = + hooks.useItemMemberships(item?.id); + const { data: currentMember } = hooks.useCurrentMember(); + + const allowed = isItemUpdateAllowedForUser({ + memberships, + memberId: currentMember?.id, + }); + + return { allowed, memberships, isMembershipsLoading }; +}; diff --git a/yarn.lock b/yarn.lock index 0e12a71b9..f2d4850ba 100644 --- a/yarn.lock +++ b/yarn.lock @@ -1534,11 +1534,11 @@ __metadata: languageName: node linkType: hard -"@graasp/query-client@github:graasp/graasp-query-client#geolocation-address": - version: 2.6.0 - resolution: "@graasp/query-client@https://github.com/graasp/graasp-query-client.git#commit=660f2448ee0348387fab9f5b32bfb30dd8a56eb1" +"@graasp/query-client@npm:2.6.1": + version: 2.6.1 + resolution: "@graasp/query-client@npm:2.6.1" dependencies: - "@graasp/sdk": "npm:3.8.0" + "@graasp/sdk": "npm:3.8.1" "@graasp/translations": "npm:1.23.0" axios: "npm:0.27.2" crypto-js: "npm:4.2.0" @@ -1549,7 +1549,7 @@ __metadata: uuid: "npm:9.0.1" peerDependencies: react: ^17.0.0 || ^18.0.0 - checksum: 10/ebc6e86d6004100b66161f89760c051b8bbce56004b069678ff03af4c36d22be97ccde53066902fdf16bc42d4842221897eb0650f0e3c676f8f2c08191f858b0 + checksum: 10/2de2c09ea80c62e795ffa7fbfee7625ac661b70e68a4c228fd3014edc687ffdc8e647d51ea5b190600b706405e7a7275b0c89a2ec403618d5db089b24bf6e8d1 languageName: node linkType: hard @@ -7633,7 +7633,7 @@ __metadata: "@emotion/react": "npm:11.11.3" "@emotion/styled": "npm:11.11.0" "@graasp/chatbox": "npm:3.0.3" - "@graasp/query-client": "github:graasp/graasp-query-client#geolocation-address" + "@graasp/query-client": "npm:2.6.1" "@graasp/sdk": "npm:3.8.1" "@graasp/translations": "npm:1.23.0" "@graasp/ui": "github:graasp/graasp-ui#navigation-icon" From c7d68c83f5196696527756f46f08b81932104d4b Mon Sep 17 00:00:00 2001 From: kim Date: Thu, 15 Feb 2024 17:33:36 +0100 Subject: [PATCH 3/4] test: fix tests --- cypress/e2e/item/settings/itemSettings.cy.ts | 46 ++++++++++++++++--- .../e2e/item/settings/uploadThumbnail.cy.ts | 6 +-- cypress/fixtures/documents.ts | 3 +- cypress/support/commands.ts | 5 -- cypress/support/index.ts | 2 - cypress/support/viewUtils.ts | 38 +-------------- src/components/common/ItemMetadataButton.tsx | 28 ----------- .../item/header/ItemHeaderActions.tsx | 4 +- src/config/selectors.ts | 1 - 9 files changed, 45 insertions(+), 88 deletions(-) delete mode 100644 src/components/common/ItemMetadataButton.tsx diff --git a/cypress/e2e/item/settings/itemSettings.cy.ts b/cypress/e2e/item/settings/itemSettings.cy.ts index c6088fe82..cd550bc19 100644 --- a/cypress/e2e/item/settings/itemSettings.cy.ts +++ b/cypress/e2e/item/settings/itemSettings.cy.ts @@ -1,6 +1,8 @@ -import { MaxWidth } from '@graasp/sdk'; +import { ItemType, MaxWidth, getFileExtra } from '@graasp/sdk'; import { langs } from '@graasp/translations'; +import { getMemberById } from '@/utils/member'; + import { buildItemPath, buildItemSettingsPath, @@ -70,6 +72,7 @@ describe('Item Settings', () => { ITEM_WITH_CHATBOX_MESSAGES_AND_ADMIN, IMAGE_ITEM_DEFAULT, IMAGE_ITEM_DEFAULT_WITH_MAX_WIDTH, + IMAGE_ITEM_DEFAULT, ], }); }); @@ -83,12 +86,43 @@ describe('Item Settings', () => { cy.get(`#${SETTINGS_CHATBOX_TOGGLE_ID}`).should('be.checked'); }); - it('metadata table', () => { - const { id, name, type } = ITEMS_SETTINGS.items[1]; - cy.visit(buildItemSettingsPath(id)); + describe('Metadata table', () => { + it('folder', () => { + const { id, name, type, creator } = ITEMS_SETTINGS.items[1]; + cy.visit(buildItemSettingsPath(id)); + + cy.get(`#${ITEM_PANEL_NAME_ID}`).contains(name); + cy.get(`#${ITEM_PANEL_NAME_ID}`).contains(type); + + const creatorName = getMemberById( + Object.values(MEMBERS), + creator?.id, + ).name; + + cy.get(`#${ITEM_PANEL_TABLE_ID}`).should('exist').contains(creatorName); + }); + + it('file', () => { + const { id, name, type, extra, creator } = IMAGE_ITEM_DEFAULT; + cy.visit(buildItemSettingsPath(id)); + + cy.get(`#${ITEM_PANEL_NAME_ID}`).contains(name); + cy.get(`#${ITEM_PANEL_NAME_ID}`).contains(type); + + const creatorName = getMemberById( + Object.values(MEMBERS), + creator?.id, + ).name; - cy.get(`#${ITEM_PANEL_NAME_ID}`).should('contain', name); - cy.get(`#${ITEM_PANEL_TABLE_ID}`).should('contain', type); + cy.get(`#${ITEM_PANEL_TABLE_ID}`).should('exist').contains(creatorName); + + if (type === ItemType.LOCAL_FILE || type === ItemType.S3_FILE) { + const { mimetype, size } = getFileExtra(extra); + cy.get(`#${ITEM_PANEL_TABLE_ID}`).contains(mimetype); + + cy.get(`#${ITEM_PANEL_TABLE_ID}`).contains(size); + } + }); }); describe('Language', () => { diff --git a/cypress/e2e/item/settings/uploadThumbnail.cy.ts b/cypress/e2e/item/settings/uploadThumbnail.cy.ts index 77fe38174..1b68a7fda 100644 --- a/cypress/e2e/item/settings/uploadThumbnail.cy.ts +++ b/cypress/e2e/item/settings/uploadThumbnail.cy.ts @@ -1,7 +1,6 @@ -import { buildItemPath } from '../../../../src/config/paths'; +import { buildItemSettingsPath } from '../../../../src/config/paths'; import { CROP_MODAL_CONFIRM_BUTTON_CLASSNAME, - ITEM_INFORMATION_BUTTON_ID, THUMBNAIL_SETTING_UPLOAD_BUTTON_CLASSNAME, } from '../../../../src/config/selectors'; import { @@ -17,8 +16,7 @@ describe('Upload Thumbnails', () => { it(`upload item thumbnail`, () => { const { items } = SAMPLE_ITEMS_WITH_THUMBNAILS; - cy.visit(buildItemPath(items[0].id)); - cy.get(`#${ITEM_INFORMATION_BUTTON_ID}`).click(); + cy.visit(buildItemSettingsPath(items[0].id)); // change item thumbnail // selectFile ??? diff --git a/cypress/fixtures/documents.ts b/cypress/fixtures/documents.ts index 5d0152d2a..91ed8acf9 100644 --- a/cypress/fixtures/documents.ts +++ b/cypress/fixtures/documents.ts @@ -51,11 +51,9 @@ export const GRAASP_DOCUMENT_PARENT_FOLDER: Item = { export const GRAASP_DOCUMENT_CHILDREN_ITEM: DocumentItemType = DocumentItemFactory({ - id: '1cafbd2a-5688-12eb-ae91-0242ac130002', type: ItemType.DOCUMENT, name: 'children graasp text', description: 'a description for graasp text', - path: 'bdf09f5a_5688_11eb_ae93_0242ac130002.1cafbd2a_5688_12eb_ae93_0242ac130002', creator: CURRENT_USER, settings: {}, createdAt: '2021-08-11T12:56:36.834Z', @@ -63,6 +61,7 @@ export const GRAASP_DOCUMENT_CHILDREN_ITEM: DocumentItemType = extra: buildDocumentExtra({ content: '

Some Title

', }), + parentItem: GRAASP_DOCUMENT_PARENT_FOLDER, }); export const GRAASP_DOCUMENT_ITEMS_FIXTURE = [ diff --git a/cypress/support/commands.ts b/cypress/support/commands.ts index 1a1566470..6aaf90c92 100644 --- a/cypress/support/commands.ts +++ b/cypress/support/commands.ts @@ -5,7 +5,6 @@ import 'cypress-localstorage-commands'; import { DEFAULT_ITEM_LAYOUT_MODE } from '../../src/config/constants'; import { - ITEM_INFORMATION_BUTTON_ID, MODE_GRID_BUTTON_ID, MODE_LIST_BUTTON_ID, } from '../../src/config/selectors'; @@ -395,10 +394,6 @@ Cypress.Commands.add( ), ); -Cypress.Commands.add('openMetadataPanel', () => { - cy.get(`#${ITEM_INFORMATION_BUTTON_ID}`).click(); -}); - Cypress.Commands.add('attachFile', (selector, file, options = {}) => { selector.selectFile(`cypress/fixtures/${file}`, options); }); diff --git a/cypress/support/index.ts b/cypress/support/index.ts index b5223cdd9..b0b2573f3 100644 --- a/cypress/support/index.ts +++ b/cypress/support/index.ts @@ -28,8 +28,6 @@ declare global { text: string, ): void; - openMetadataPanel(): void; - attachFile(selector: Chainable, file: string, options?: object): void; attachFiles( selector: Chainable, diff --git a/cypress/support/viewUtils.ts b/cypress/support/viewUtils.ts index 32ec08fbc..92af44c8b 100644 --- a/cypress/support/viewUtils.ts +++ b/cypress/support/viewUtils.ts @@ -2,11 +2,8 @@ import { CompleteMember, DocumentItemType, EmbeddedLinkItemType, - ItemType, getDocumentExtra, getEmbeddedLinkExtra, - getFileExtra, - getS3FileExtra, } from '@graasp/sdk'; import { @@ -17,41 +14,16 @@ import { import { DOCUMENT_ITEM_TEXT_EDITOR_SELECTOR, ITEM_HEADER_ID, - ITEM_PANEL_NAME_ID, - ITEM_PANEL_TABLE_ID, TEXT_EDITOR_CLASS, buildEditButtonId, buildFileItemId, buildSettingsButtonId, buildShareButtonId, } from '../../src/config/selectors'; -import { getMemberById } from '../../src/utils/member'; import { isSettingsEditionAllowedForUser } from '../../src/utils/membership'; -import { CURRENT_USER, MEMBERS } from '../fixtures/members'; +import { CURRENT_USER } from '../fixtures/members'; import { ItemForTest, MemberForTest } from './types'; -const expectPanelLayout = ({ item }: { item: ItemForTest }) => { - cy.openMetadataPanel(); - - const { name, creator } = item; - - cy.get(`#${ITEM_PANEL_NAME_ID}`).contains(name); - - const creatorName = getMemberById(Object.values(MEMBERS), creator?.id).name; - - cy.get(`#${ITEM_PANEL_TABLE_ID}`).should('exist').contains(creatorName); - - if (item.type === ItemType.LOCAL_FILE || item.type === ItemType.S3_FILE) { - const { mimetype = 'invalid-mimetype', size = 'invalid-size' } = - item.type === ItemType.LOCAL_FILE - ? getFileExtra(item.extra) || {} - : getS3FileExtra(item.extra) || {}; - cy.get(`#${ITEM_PANEL_TABLE_ID}`).contains(mimetype); - - cy.get(`#${ITEM_PANEL_TABLE_ID}`).contains(size); - } -}; - export const expectItemHeaderLayout = ({ item: { id, type, memberships }, currentMember, @@ -88,9 +60,6 @@ export const expectDocumentViewScreenLayout = ({ }); expectItemHeaderLayout({ item, currentMember }); - expectPanelLayout({ - item, - }); }; export const expectFileViewScreenLayout = ({ @@ -106,8 +75,6 @@ export const expectFileViewScreenLayout = ({ cy.get(`.${TEXT_EDITOR_CLASS}`).should('contain', item.description); expectItemHeaderLayout({ item, currentMember }); - // table - expectPanelLayout({ item }); }; export const expectLinkViewScreenLayout = ({ @@ -140,8 +107,6 @@ export const expectLinkViewScreenLayout = ({ } expectItemHeaderLayout({ item, currentMember }); - // table - expectPanelLayout({ item }); }; export const expectFolderViewScreenLayout = ({ @@ -153,5 +118,4 @@ export const expectFolderViewScreenLayout = ({ }): void => { // table expectItemHeaderLayout({ item, currentMember }); - expectPanelLayout({ item }); }; diff --git a/src/components/common/ItemMetadataButton.tsx b/src/components/common/ItemMetadataButton.tsx deleted file mode 100644 index 6cc8d8850..000000000 --- a/src/components/common/ItemMetadataButton.tsx +++ /dev/null @@ -1,28 +0,0 @@ -import { Link } from 'react-router-dom'; - -import InfoIcon from '@mui/icons-material/Info'; -import { IconButton, Tooltip } from '@mui/material'; - -import { buildItemInformationPath } from '@/config/paths'; - -import { useBuilderTranslation } from '../../config/i18n'; -import { ITEM_INFORMATION_BUTTON_ID } from '../../config/selectors'; -import { BUILDER } from '../../langs/constants'; - -const ItemMetadataButton = ({ itemId }: { itemId: string }): JSX.Element => { - const { t: translateBuilder } = useBuilderTranslation(); - - return ( - - - - - - ); -}; - -export default ItemMetadataButton; diff --git a/src/components/item/header/ItemHeaderActions.tsx b/src/components/item/header/ItemHeaderActions.tsx index f0fd8add1..14637dd1b 100644 --- a/src/components/item/header/ItemHeaderActions.tsx +++ b/src/components/item/header/ItemHeaderActions.tsx @@ -61,7 +61,7 @@ const ItemHeaderActions = (): JSX.Element => { ITEM_TYPES_WITH_CAPTIONS.includes(item.type) && canEdit; - const activeActions = ( + return ( <> {showEditButton && } @@ -84,8 +84,6 @@ const ItemHeaderActions = (): JSX.Element => { {canEdit && } ); - - return activeActions; } return null; }; diff --git a/src/config/selectors.ts b/src/config/selectors.ts index 1d22da06a..dc97e8a79 100644 --- a/src/config/selectors.ts +++ b/src/config/selectors.ts @@ -138,7 +138,6 @@ export const ITEM_MEMBERSHIP_PERMISSION_SELECT_CLASS = export const buildItemMembershipRowDeleteButtonId = (id: string): string => `itemMembershipRowDeleteButtonId-${id}`; export const ITEM_INFORMATION_ICON_IS_OPEN_CLASS = 'itemInformationIconIsOpen'; -export const ITEM_INFORMATION_BUTTON_ID = 'itemInformationButton'; export const ITEM_SEARCH_INPUT_ID = 'itemSearchInput'; export const ITEMS_GRID_NO_SEARCH_RESULT_ID = 'itemsGridNoSearchResult'; export const ITEMS_GRID_ITEMS_PER_PAGE_SELECT_ID = From 4e535264e8f88e0e661770c8f5aa5fe997983a3c Mon Sep 17 00:00:00 2001 From: kim Date: Fri, 16 Feb 2024 10:50:14 +0100 Subject: [PATCH 4/4] refactor: apply PR requested changes --- cypress/e2e/item/settings/itemSettings.cy.ts | 6 +- package.json | 8 +- src/components/item/form/DocumentForm.tsx | 13 +- .../item/settings/GeolocationPicker.tsx | 14 +- .../item/settings/ItemSettingsProperties.tsx | 35 ++- src/components/item/settings/hooks.ts | 17 +- src/langs/constants.ts | 1 + src/langs/en.json | 3 +- src/langs/fr.json | 2 +- yarn.lock | 266 ++---------------- 10 files changed, 73 insertions(+), 292 deletions(-) diff --git a/cypress/e2e/item/settings/itemSettings.cy.ts b/cypress/e2e/item/settings/itemSettings.cy.ts index cd550bc19..ef537f15e 100644 --- a/cypress/e2e/item/settings/itemSettings.cy.ts +++ b/cypress/e2e/item/settings/itemSettings.cy.ts @@ -92,7 +92,7 @@ describe('Item Settings', () => { cy.visit(buildItemSettingsPath(id)); cy.get(`#${ITEM_PANEL_NAME_ID}`).contains(name); - cy.get(`#${ITEM_PANEL_NAME_ID}`).contains(type); + cy.get(`#${ITEM_PANEL_TABLE_ID}`).contains(type); const creatorName = getMemberById( Object.values(MEMBERS), @@ -102,12 +102,12 @@ describe('Item Settings', () => { cy.get(`#${ITEM_PANEL_TABLE_ID}`).should('exist').contains(creatorName); }); - it('file', () => { + it.only('file', () => { const { id, name, type, extra, creator } = IMAGE_ITEM_DEFAULT; cy.visit(buildItemSettingsPath(id)); cy.get(`#${ITEM_PANEL_NAME_ID}`).contains(name); - cy.get(`#${ITEM_PANEL_NAME_ID}`).contains(type); + cy.get(`#${ITEM_PANEL_TABLE_ID}`).contains(extra.file.mimetype); const creatorName = getMemberById( Object.values(MEMBERS), diff --git a/package.json b/package.json index 5a5e7fcde..1f7ef1659 100644 --- a/package.json +++ b/package.json @@ -21,9 +21,9 @@ "@emotion/styled": "11.11.0", "@graasp/chatbox": "3.0.3", "@graasp/query-client": "2.6.1", - "@graasp/sdk": "3.8.1", + "@graasp/sdk": "3.8.3", "@graasp/translations": "1.23.0", - "@graasp/ui": "github:graasp/graasp-ui#navigation-icon", + "@graasp/ui": "4.8.0", "@mui/icons-material": "5.15.8", "@mui/lab": "5.0.0-alpha.162", "@mui/material": "5.15.8", @@ -114,7 +114,6 @@ "@testing-library/user-event": "^14.5.2", "@trivago/prettier-plugin-sort-imports": "4.3.0", "@types/jest": "29.5.12", - "@types/leaflet": "^1", "@types/lodash.debounce": "4.0.9", "@types/lodash.groupby": "4.6.9", "@types/lodash.isequal": "4.5.8", @@ -151,5 +150,8 @@ "vite-plugin-checker": "0.6.2", "vite-plugin-istanbul": "5.0.0" }, + "resolutions": { + "@graasp/sdk": "3.8.3" + }, "packageManager": "yarn@4.1.0" } diff --git a/src/components/item/form/DocumentForm.tsx b/src/components/item/form/DocumentForm.tsx index 54abc9964..be4e1a32e 100644 --- a/src/components/item/form/DocumentForm.tsx +++ b/src/components/item/form/DocumentForm.tsx @@ -68,12 +68,13 @@ export const DocumentExtraForm = ({ ], ); - const withFlavor = (textView: JSX.Element): JSX.Element => - extra?.flavor ? ( - {textView} - ) : ( - textView - ); + const withFlavor = (textView: JSX.Element): JSX.Element => { + if (!extra.flavor || extra.flavor === DocumentItemExtraFlavor.None) { + return textView; + } + + return {textView}; + }; const handleChangeEditorMode = (mode: string) => { // send editor mode change diff --git a/src/components/item/settings/GeolocationPicker.tsx b/src/components/item/settings/GeolocationPicker.tsx index 54e768155..41f47048d 100644 --- a/src/components/item/settings/GeolocationPicker.tsx +++ b/src/components/item/settings/GeolocationPicker.tsx @@ -15,15 +15,11 @@ import { import { DiscriminatedItem } from '@graasp/sdk'; -// eslint-disable-next-line @typescript-eslint/ban-ts-comment -// @ts-expect-error -import { SearchResult } from 'leaflet-geosearch/dist/providers/provider'; - import { useBuilderTranslation } from '@/config/i18n'; import { hooks, mutations } from '@/config/queryClient'; import { BUILDER } from '@/langs/constants'; -import { useSearchAddress } from './hooks'; +import { OpenStreetMapResult, useSearchAddress } from './hooks'; const GeolocationPicker = ({ item, @@ -52,14 +48,18 @@ const GeolocationPicker = ({ setQuery(e.target.value); }; - const onChangeOption = (option: SearchResult): void => { + const onChangeOption = (option: OpenStreetMapResult): void => { const { raw: { lat, lon: lng }, label, } = option; putGeoloc({ itemId: item.id, - geolocation: { lng, lat, addressLabel: label }, + geolocation: { + lng: parseFloat(lng), + lat: parseFloat(lat), + addressLabel: label, + }, }); setResults([]); }; diff --git a/src/components/item/settings/ItemSettingsProperties.tsx b/src/components/item/settings/ItemSettingsProperties.tsx index 119ee386d..ddf3f723a 100644 --- a/src/components/item/settings/ItemSettingsProperties.tsx +++ b/src/components/item/settings/ItemSettingsProperties.tsx @@ -53,6 +53,26 @@ const ItemSettingsProperties = ({ item }: Props): JSX.Element => { case ItemType.S3_FILE: case ItemType.LOCAL_FILE: return ; + case ItemType.APP: + return ( + { + handleOnToggle({ target: { checked } }, 'isResizable'); + }} + valueText={ + settings?.isResizable + ? translateBuilder(BUILDER.ITEM_SETTINGS_RESIZABLE_ENABLED_TEXT) + : translateBuilder( + BUILDER.ITEM_SETTINGS_RESIZABLE_DISABLED_TEXT, + ) + } + /> + ); default: return null; } @@ -137,21 +157,6 @@ const ItemSettingsProperties = ({ item }: Props): JSX.Element => { disabled /> - {item.type === ItemType.APP && ( - { - handleOnToggle({ target: { checked } }, 'isResizable'); - }} - valueText={ - settings?.isResizable - ? translateBuilder(BUILDER.ITEM_SETTINGS_RESIZABLE_ENABLED_TEXT) - : translateBuilder(BUILDER.ITEM_SETTINGS_RESIZABLE_DISABLED_TEXT) - } - /> - )} {renderSettingsPerType()} ); diff --git a/src/components/item/settings/hooks.ts b/src/components/item/settings/hooks.ts index a8e294221..d6c0ae0fe 100644 --- a/src/components/item/settings/hooks.ts +++ b/src/components/item/settings/hooks.ts @@ -1,15 +1,8 @@ -// eslint-disable-next-line import/no-extraneous-dependencies import { Dispatch, useCallback, useEffect, useMemo, useState } from 'react'; import { ItemGeolocation } from '@graasp/sdk'; import { OpenStreetMapProvider } from 'leaflet-geosearch'; -// eslint-disable-next-line @typescript-eslint/ban-ts-comment -// @ts-expect-error -import { RawResult } from 'leaflet-geosearch/dist/providers/openStreetMapProvider'; -// eslint-disable-next-line @typescript-eslint/ban-ts-comment -// @ts-expect-error -import { SearchResult } from 'leaflet-geosearch/dist/providers/provider'; import useDebouncedCallback from '@/utils/useDebounce'; @@ -20,19 +13,23 @@ type Props = { const DELAY_MS = 1000; +export type OpenStreetMapResult = Awaited< + ReturnType +>[0]; + type ReturnedValue = { clearQuery: () => void; isDebounced: boolean; loading: boolean; query?: string | null; - results: SearchResult[]; + results: OpenStreetMapResult[]; setQuery: Dispatch; - setResults: Dispatch[]>; + setResults: Dispatch; }; // eslint-disable-next-line import/prefer-default-export export const useSearchAddress = ({ lang, geoloc }: Props): ReturnedValue => { - const [results, setResults] = useState[]>([]); + const [results, setResults] = useState([]); const [loading, setLoading] = useState(false); const [query, setQuery] = useState(); diff --git a/src/langs/constants.ts b/src/langs/constants.ts index adbfb0915..44270e31b 100644 --- a/src/langs/constants.ts +++ b/src/langs/constants.ts @@ -45,6 +45,7 @@ export const BUILDER = { DOCUMENT_FLAVOR_NAME: 'DOCUMENT_FLAVOR_NAME', DOCUMENT_FLAVOR_SUCCESS: 'DOCUMENT_FLAVOR_SUCCESS', DOCUMENT_FLAVOR_WARNING: 'DOCUMENT_FLAVOR_WARNING', + DOCUMENT_FLAVOR_NONE: 'DOCUMENT_FLAVOR_NONE', DOWNLOAD_ITEM_BUTTON: 'DOWNLOAD_ITEM_BUTTON', DOCUMENT_EDITOR_MODE_RICH_TEXT: 'DOCUMENT_EDITOR_MODE_RICH_TEXT', DOCUMENT_EDITOR_MODE_RAW: 'DOCUMENT_EDITOR_MODE_RAW', diff --git a/src/langs/en.json b/src/langs/en.json index 06db40e0e..d426a2a61 100644 --- a/src/langs/en.json +++ b/src/langs/en.json @@ -48,6 +48,7 @@ "DOCUMENT_FLAVOR_NAME": "Style", "DOCUMENT_FLAVOR_SUCCESS": "Success", "DOCUMENT_FLAVOR_WARNING": "Warning", + "DOCUMENT_FLAVOR_NONE": "None", "DOCUMENT_EDITOR_MODE_RICH_TEXT": "Rich Text", "DOCUMENT_EDITOR_MODE_RAW": "HTML", "DOCUMENT_EDITOR_MODE_ARIA_LABEL": "Switch document editor mode", @@ -137,7 +138,7 @@ "ITEM_SETTINGS_VISIBILITY_PUBLIC_LABEL": "Public", "ITEM_SETTINGS_VISIBILITY_TITLE": "Visibility", "ITEM_TAGS_INFORMATION": "Please separate tags by comma.", - "ITEM_TAGS_PLACEHOLDER": "Eg. English, Biology, Lab, Plants", + "ITEM_TAGS_PLACEHOLDER": "english, biology, lab, plants, high school", "ITEM_TAGS_LABEL": "Tags", "ITEM_TAGS_PREVIEW_TITLE": "Tags Preview", "ITEM_TAGS_TITLE": "Tags", diff --git a/src/langs/fr.json b/src/langs/fr.json index 57fb03ad6..5c770dd3a 100644 --- a/src/langs/fr.json +++ b/src/langs/fr.json @@ -128,7 +128,7 @@ "ITEM_SETTINGS_VISIBILITY_PSEUDONYMIZED_SCHEMA_PSEUDONYM_LABEL": "Pseudonyme", "ITEM_SETTINGS_VISIBILITY_PSEUDONYMIZED_SCHEMA_SELECT_MESSAGE": "Cet élément est accessible si le visiteur fournit un", "ITEM_SETTINGS_VISIBILITY_PUBLIC_INFORMATIONS": "Cet élément est public. N'importe quel visiteur peut accéder à cet élément.", - "ITEM_TAGS_PLACEHOLDER": "Anglais, Biologie, Plantes", + "ITEM_TAGS_PLACEHOLDER": "biologie, plantes, effet de serre", "ITEM_SETTINGS_VISIBILITY_PUBLIC_LABEL": "Public", "ITEM_SETTINGS_VISIBILITY_TITLE": "Visibilité", "ITEM_TAGS_INFORMATION": "Veuillez séparer les groupes de mots par une virgule. ", diff --git a/yarn.lock b/yarn.lock index f2d4850ba..cb0b72742 100644 --- a/yarn.lock +++ b/yarn.lock @@ -1521,19 +1521,6 @@ __metadata: languageName: node linkType: hard -"@graasp/etherpad-api@npm:2.1.1": - version: 2.1.1 - resolution: "@graasp/etherpad-api@npm:2.1.1" - dependencies: - "@types/sanitize-html": "npm:^2.9.0" - axios: "npm:^1.3.5" - compare-versions: "npm:^3.4.0" - http-errors: "npm:^1.7.1" - sanitize-html: "npm:^2.10.0" - checksum: 10/e78819acfe6a4f28fdc5725129d1b82e26fd271e5f32070e8170b757f79567c5575569373e5d7fd8f3c966c535e5b83b9ef98ab3707666c2029c085564f9dbc9 - languageName: node - linkType: hard - "@graasp/query-client@npm:2.6.1": version: 2.6.1 resolution: "@graasp/query-client@npm:2.6.1" @@ -1553,22 +1540,9 @@ __metadata: languageName: node linkType: hard -"@graasp/sdk@npm:3.3.0": - version: 3.3.0 - resolution: "@graasp/sdk@npm:3.3.0" - dependencies: - "@graasp/etherpad-api": "npm:2.1.1" - date-fns: "npm:2.30.0" - js-cookie: "npm:3.0.5" - uuid: "npm:9.0.1" - validator: "npm:13.11.0" - checksum: 10/12a11bfb2ff35d4fdccc38ad10fab8fe4ee4f7cea2a26ac17040d8758e2cf86070cbfa0c02243bb7efc3410f1abd5d0e18834dc6f6226bb216b33e0f83b19e2d - languageName: node - linkType: hard - -"@graasp/sdk@npm:3.8.0": - version: 3.8.0 - resolution: "@graasp/sdk@npm:3.8.0" +"@graasp/sdk@npm:3.8.3": + version: 3.8.3 + resolution: "@graasp/sdk@npm:3.8.3" dependencies: "@faker-js/faker": "npm:8.4.0" js-cookie: "npm:3.0.5" @@ -1576,33 +1550,7 @@ __metadata: peerDependencies: date-fns: ^3 uuid: ^9 - checksum: 10/d87ad00429c56a8d37e4ceef742b9adca96c7b7729665a113e5da8b656397a3daf219a64e0551e6b464dfe61d76796a0c075f5f00218c63ad059760b661471db - languageName: node - linkType: hard - -"@graasp/sdk@npm:3.8.1": - version: 3.8.1 - resolution: "@graasp/sdk@npm:3.8.1" - dependencies: - "@faker-js/faker": "npm:8.4.0" - js-cookie: "npm:3.0.5" - validator: "npm:13.11.0" - peerDependencies: - date-fns: ^3 - uuid: ^9 - checksum: 10/f97d1472e71a334e34154b3090c37a4dab9cf8072877689536805f9a8a39c81cafe4a7236281a733da0550ed115e002aff2c40b4cc9c1195112b6efd5c90723c - languageName: node - linkType: hard - -"@graasp/sdk@npm:^3.3.0": - version: 3.5.0 - resolution: "@graasp/sdk@npm:3.5.0" - dependencies: - date-fns: "npm:3.2.0" - js-cookie: "npm:3.0.5" - uuid: "npm:9.0.1" - validator: "npm:13.11.0" - checksum: 10/dfbb9977904336214e411c93a33084fca8e07cb73145f655a070dfdb81a772d6a0412849ee07c8ee2e74497d59f960a8ef1989062a4e41d78ad5d22b24e8a8db + checksum: 10/3968defd8bc2eb9c4165ae8a89ae43c0cbe22bef9934f0eb4a2645188b793639c193a79016cb961052068601754f0cc1ef8b2abf23b691231aa9ad0594ad56f2 languageName: node linkType: hard @@ -1624,14 +1572,14 @@ __metadata: languageName: node linkType: hard -"@graasp/ui@github:graasp/graasp-ui#navigation-icon": - version: 4.7.0 - resolution: "@graasp/ui@https://github.com/graasp/graasp-ui.git#commit=95dee601f0327d781d01ed15e6eae276b6b3ab65" +"@graasp/ui@npm:4.8.0": + version: 4.8.0 + resolution: "@graasp/ui@npm:4.8.0" dependencies: "@ag-grid-community/client-side-row-model": "npm:31.0.3" "@ag-grid-community/react": "npm:^31.0.3" "@ag-grid-community/styles": "npm:^31.0.3" - "@graasp/sdk": "npm:3.8.0" + "@graasp/sdk": "npm:3.8.3" "@storybook/react-vite": "npm:7.6.13" http-status-codes: "npm:2.3.0" interweave: "npm:13.1.0" @@ -1657,7 +1605,7 @@ __metadata: react-router-dom: ^6.11.0 stylis: ^4.1.3 stylis-plugin-rtl: ^2.1.1 - checksum: 10/709260a25c1a75399db5b49ce28fa9a7d5834fc1b7fd084934c9afe6e2e242b8b168d9f794414eee55f4a8672a9cdc3267e0e8adbb336dbad141f437c011f7f0 + checksum: 10/30f64867f7b1f42d3fa58bd14dd9ecae4dd574eb54d30486d8a2cb672ca3b6d45f934fb08424fe40afffab0c750d0e7cae424c56104cc57e31ee67bd9278f4a1 languageName: node linkType: hard @@ -3083,13 +3031,6 @@ __metadata: languageName: node linkType: hard -"@types/geojson@npm:*": - version: 7946.0.14 - resolution: "@types/geojson@npm:7946.0.14" - checksum: 10/ae511bee6488ae3bd5a3a3347aedb0371e997b14225b8983679284e22fa4ebd88627c6e3ff8b08bf4cc35068cb29310c89427311ffc9322c255615821a922e71 - languageName: node - linkType: hard - "@types/glob@npm:^7.1.3": version: 7.2.0 resolution: "@types/glob@npm:7.2.0" @@ -3175,15 +3116,6 @@ __metadata: languageName: node linkType: hard -"@types/leaflet@npm:^1": - version: 1.9.8 - resolution: "@types/leaflet@npm:1.9.8" - dependencies: - "@types/geojson": "npm:*" - checksum: 10/c0c68ae0d1ccbed60e08ad82670df48f8bb6f19e3abaf84a9cd0a6cbc6d6efdd46852ee7be56744dfa7f3d8665adb56bb06ab02d09f979d3367c941a1fd90f2f - languageName: node - linkType: hard - "@types/lodash.debounce@npm:4.0.9": version: 4.0.9 resolution: "@types/lodash.debounce@npm:4.0.9" @@ -3455,15 +3387,6 @@ __metadata: languageName: node linkType: hard -"@types/sanitize-html@npm:^2.9.0": - version: 2.9.5 - resolution: "@types/sanitize-html@npm:2.9.5" - dependencies: - htmlparser2: "npm:^8.0.0" - checksum: 10/fd0afee5dac91aa2c42391f0c8c9254204f4ee1f10b902aa04e8f7809043d785e28af2732f75277ef09e46838013ad60abedb02ba1424b6218264f3333437fb5 - languageName: node - linkType: hard - "@types/scheduler@npm:*": version: 0.16.8 resolution: "@types/scheduler@npm:0.16.8" @@ -4528,17 +4451,6 @@ __metadata: languageName: node linkType: hard -"axios@npm:^1.3.5": - version: 1.6.5 - resolution: "axios@npm:1.6.5" - dependencies: - follow-redirects: "npm:^1.15.4" - form-data: "npm:^4.0.0" - proxy-from-env: "npm:^1.1.0" - checksum: 10/465489d9bf8f039b9adbc8103b6299d6a5e26de77b27f0e4173d814d39bca8f4b4659d94e09ee40461aedccd8c2452f1e2b3edace1c9f81220060d2974ff9dc7 - languageName: node - linkType: hard - "axobject-query@npm:^3.2.1": version: 3.2.1 resolution: "axobject-query@npm:3.2.1" @@ -5238,13 +5150,6 @@ __metadata: languageName: node linkType: hard -"compare-versions@npm:^3.4.0": - version: 3.6.0 - resolution: "compare-versions@npm:3.6.0" - checksum: 10/7492a50cdaa2c27f5254eee7c4b38856e1c164991bab3d98d7fd067fe4b570d47123ecb92523b78338be86aa221668fd3868bfe8caa5587dc3ebbe1a03d52b5d - languageName: node - linkType: hard - "concat-map@npm:0.0.1": version: 0.0.1 resolution: "concat-map@npm:0.0.1" @@ -5597,7 +5502,14 @@ __metadata: languageName: node linkType: hard -"date-fns@npm:2.30.0, date-fns@npm:^2.30.0": +"date-fns@npm:3.3.1, date-fns@npm:^3.2.0": + version: 3.3.1 + resolution: "date-fns@npm:3.3.1" + checksum: 10/98231936765dfb6fc6897676319b500a06a39f051b2c3ecbdd541a07ce9b1344b770277b8bfb1049fb7a2f70bf365ac8e6f1e2bb452b10e1a8101d518ca7f95d + languageName: node + linkType: hard + +"date-fns@npm:^2.30.0": version: 2.30.0 resolution: "date-fns@npm:2.30.0" dependencies: @@ -5606,20 +5518,6 @@ __metadata: languageName: node linkType: hard -"date-fns@npm:3.2.0": - version: 3.2.0 - resolution: "date-fns@npm:3.2.0" - checksum: 10/2f36cb9165a066ae90c0b6f0c25b3c70eb75bc52e64ba6dd8680964ebda144851a244ff4ed0b2afb4a6bab796a1af6a0e6c7c2814529d04c72fa434f931d4e81 - languageName: node - linkType: hard - -"date-fns@npm:3.3.1, date-fns@npm:^3.2.0": - version: 3.3.1 - resolution: "date-fns@npm:3.3.1" - checksum: 10/98231936765dfb6fc6897676319b500a06a39f051b2c3ecbdd541a07ce9b1344b770277b8bfb1049fb7a2f70bf365ac8e6f1e2bb452b10e1a8101d518ca7f95d - languageName: node - linkType: hard - "dayjs@npm:1.11.10, dayjs@npm:^1.10.4": version: 1.11.10 resolution: "dayjs@npm:1.11.10" @@ -5739,13 +5637,6 @@ __metadata: languageName: node linkType: hard -"deepmerge@npm:^4.2.2": - version: 4.3.1 - resolution: "deepmerge@npm:4.3.1" - checksum: 10/058d9e1b0ff1a154468bf3837aea436abcfea1ba1d165ddaaf48ca93765fdd01a30d33c36173da8fbbed951dd0a267602bc782fe288b0fc4b7e1e7091afc4529 - languageName: node - linkType: hard - "default-require-extensions@npm:^3.0.0": version: 3.0.1 resolution: "default-require-extensions@npm:3.0.1" @@ -5803,13 +5694,6 @@ __metadata: languageName: node linkType: hard -"depd@npm:~1.1.2": - version: 1.1.2 - resolution: "depd@npm:1.1.2" - checksum: 10/2ed6966fc14463a9e85451db330ab8ba041efed0b9a1a472dbfc6fbf2f82bab66491915f996b25d8517dddc36c8c74e24c30879b34877f3c4410733444a51d1d - languageName: node - linkType: hard - "dequal@npm:^2.0.0, dequal@npm:^2.0.2, dequal@npm:^2.0.3": version: 2.0.3 resolution: "dequal@npm:2.0.3" @@ -5898,44 +5782,6 @@ __metadata: languageName: node linkType: hard -"dom-serializer@npm:^2.0.0": - version: 2.0.0 - resolution: "dom-serializer@npm:2.0.0" - dependencies: - domelementtype: "npm:^2.3.0" - domhandler: "npm:^5.0.2" - entities: "npm:^4.2.0" - checksum: 10/e3bf9027a64450bca0a72297ecdc1e3abb7a2912268a9f3f5d33a2e29c1e2c3502c6e9f860fc6625940bfe0cfb57a44953262b9e94df76872fdfb8151097eeb3 - languageName: node - linkType: hard - -"domelementtype@npm:^2.3.0": - version: 2.3.0 - resolution: "domelementtype@npm:2.3.0" - checksum: 10/ee837a318ff702622f383409d1f5b25dd1024b692ef64d3096ff702e26339f8e345820f29a68bcdcea8cfee3531776b3382651232fbeae95612d6f0a75efb4f6 - languageName: node - linkType: hard - -"domhandler@npm:^5.0.2, domhandler@npm:^5.0.3": - version: 5.0.3 - resolution: "domhandler@npm:5.0.3" - dependencies: - domelementtype: "npm:^2.3.0" - checksum: 10/809b805a50a9c6884a29f38aec0a4e1b4537f40e1c861950ed47d10b049febe6b79ab72adaeeebb3cc8fc1cd33f34e97048a72a9265103426d93efafa78d3e96 - languageName: node - linkType: hard - -"domutils@npm:^3.0.1": - version: 3.1.0 - resolution: "domutils@npm:3.1.0" - dependencies: - dom-serializer: "npm:^2.0.0" - domelementtype: "npm:^2.3.0" - domhandler: "npm:^5.0.3" - checksum: 10/9a169a6e57ac4c738269a73ab4caf785114ed70e46254139c1bbc8144ac3102aacb28a6149508395ae34aa5d6a40081f4fa5313855dc8319c6d8359866b6dfea - languageName: node - linkType: hard - "dot-prop@npm:^5.1.0": version: 5.3.0 resolution: "dot-prop@npm:5.3.0" @@ -6073,13 +5919,6 @@ __metadata: languageName: node linkType: hard -"entities@npm:^4.2.0, entities@npm:^4.4.0": - version: 4.5.0 - resolution: "entities@npm:4.5.0" - checksum: 10/ede2a35c9bce1aeccd055a1b445d41c75a14a2bb1cd22e242f20cf04d236cdcd7f9c859eb83f76885327bfae0c25bf03303665ee1ce3d47c5927b98b0e3e3d48 - languageName: node - linkType: hard - "env-cmd@npm:10.1.0": version: 10.1.0 resolution: "env-cmd@npm:10.1.0" @@ -7634,9 +7473,9 @@ __metadata: "@emotion/styled": "npm:11.11.0" "@graasp/chatbox": "npm:3.0.3" "@graasp/query-client": "npm:2.6.1" - "@graasp/sdk": "npm:3.8.1" + "@graasp/sdk": "npm:3.8.3" "@graasp/translations": "npm:1.23.0" - "@graasp/ui": "github:graasp/graasp-ui#navigation-icon" + "@graasp/ui": "npm:4.8.0" "@mui/icons-material": "npm:5.15.8" "@mui/lab": "npm:5.0.0-alpha.162" "@mui/material": "npm:5.15.8" @@ -7646,7 +7485,6 @@ __metadata: "@testing-library/user-event": "npm:^14.5.2" "@trivago/prettier-plugin-sort-imports": "npm:4.3.0" "@types/jest": "npm:29.5.12" - "@types/leaflet": "npm:^1" "@types/lodash.debounce": "npm:4.0.9" "@types/lodash.groupby": "npm:4.6.9" "@types/lodash.isequal": "npm:4.5.8" @@ -7930,18 +7768,6 @@ __metadata: languageName: node linkType: hard -"htmlparser2@npm:^8.0.0": - version: 8.0.2 - resolution: "htmlparser2@npm:8.0.2" - dependencies: - domelementtype: "npm:^2.3.0" - domhandler: "npm:^5.0.3" - domutils: "npm:^3.0.1" - entities: "npm:^4.4.0" - checksum: 10/ea5512956eee06f5835add68b4291d313c745e8407efa63848f4b8a90a2dee45f498a698bca8614e436f1ee0cfdd609938b71d67c693794545982b76e53e6f11 - languageName: node - linkType: hard - "http-cache-semantics@npm:^4.1.1": version: 4.1.1 resolution: "http-cache-semantics@npm:4.1.1" @@ -7962,19 +7788,6 @@ __metadata: languageName: node linkType: hard -"http-errors@npm:^1.7.1": - version: 1.8.1 - resolution: "http-errors@npm:1.8.1" - dependencies: - depd: "npm:~1.1.2" - inherits: "npm:2.0.4" - setprototypeof: "npm:1.2.0" - statuses: "npm:>= 1.5.0 < 2" - toidentifier: "npm:1.0.1" - checksum: 10/76fc491bd8df2251e21978e080d5dae20d9736cfb29bb72b5b76ec1bcebb1c14f0f58a3a128dd89288934379d2173cfb0421c571d54103e93dd65ef6243d64d8 - languageName: node - linkType: hard - "http-proxy-agent@npm:^7.0.0": version: 7.0.0 resolution: "http-proxy-agent@npm:7.0.0" @@ -8464,7 +8277,7 @@ __metadata: languageName: node linkType: hard -"is-plain-object@npm:5.0.0, is-plain-object@npm:^5.0.0": +"is-plain-object@npm:5.0.0": version: 5.0.0 resolution: "is-plain-object@npm:5.0.0" checksum: 10/e32d27061eef62c0847d303125440a38660517e586f2f3db7c9d179ae5b6674ab0f469d519b2e25c147a1a3bc87156d0d5f4d8821e0ce4a9ee7fe1fcf11ce45c @@ -10952,13 +10765,6 @@ __metadata: languageName: node linkType: hard -"parse-srcset@npm:^1.0.2": - version: 1.0.2 - resolution: "parse-srcset@npm:1.0.2" - checksum: 10/d40c131cfc3ab7bb6333b788d30a30d063d76a83b49fa752229823f96475e36cf29fea09e035ce3b2a634b686e93e2a7429cb8dad0041d8a3a3df622093b9ea1 - languageName: node - linkType: hard - "parseurl@npm:~1.3.3": version: 1.3.3 resolution: "parseurl@npm:1.3.3" @@ -11103,17 +10909,6 @@ __metadata: languageName: node linkType: hard -"postcss@npm:^8.3.11": - version: 8.4.33 - resolution: "postcss@npm:8.4.33" - dependencies: - nanoid: "npm:^3.3.7" - picocolors: "npm:^1.0.0" - source-map-js: "npm:^1.0.2" - checksum: 10/e22a4594c255f26117f38419fb494d7ecab0f596cd409f7aadc8a6173abf180ed7ea970cd13fd366ab12b5840be901d2a09b25197700c2ebcb5a8077326bf519 - languageName: node - linkType: hard - "postcss@npm:^8.4.32": version: 8.4.32 resolution: "postcss@npm:8.4.32" @@ -12353,20 +12148,6 @@ __metadata: languageName: node linkType: hard -"sanitize-html@npm:^2.10.0": - version: 2.11.0 - resolution: "sanitize-html@npm:2.11.0" - dependencies: - deepmerge: "npm:^4.2.2" - escape-string-regexp: "npm:^4.0.0" - htmlparser2: "npm:^8.0.0" - is-plain-object: "npm:^5.0.0" - parse-srcset: "npm:^1.0.2" - postcss: "npm:^8.3.11" - checksum: 10/452029f5b15ef6b41729f7f45ee853d020ed0859388534bd9b959d78bb0df6d9dcaff6103a8c16597a5a21ee63f00127ce387d16b7a6538174081abac9d34031 - languageName: node - linkType: hard - "scheduler@npm:^0.23.0": version: 0.23.0 resolution: "scheduler@npm:0.23.0" @@ -12791,13 +12572,6 @@ __metadata: languageName: node linkType: hard -"statuses@npm:>= 1.5.0 < 2": - version: 1.5.0 - resolution: "statuses@npm:1.5.0" - checksum: 10/c469b9519de16a4bb19600205cffb39ee471a5f17b82589757ca7bd40a8d92ebb6ed9f98b5a540c5d302ccbc78f15dc03cc0280dd6e00df1335568a5d5758a5c - languageName: node - linkType: hard - "std-env@npm:^3.5.0": version: 3.7.0 resolution: "std-env@npm:3.7.0"