From f7dc4be726082f8389965a9e62afc55ceac0e6da Mon Sep 17 00:00:00 2001 From: daedalus <44623501+ComfortablyCoding@users.noreply.github.com> Date: Sat, 15 Jan 2022 22:25:13 -0500 Subject: [PATCH 01/31] fix(plugin generator): support valid package names for pluginId Update the current replace regex to support both scoped package and old strapi plugin names. --- .../generators/lib/files/plugin/admin/src/pluginId.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/packages/generators/generators/lib/files/plugin/admin/src/pluginId.js b/packages/generators/generators/lib/files/plugin/admin/src/pluginId.js index f604a009da..3c66397d54 100644 --- a/packages/generators/generators/lib/files/plugin/admin/src/pluginId.js +++ b/packages/generators/generators/lib/files/plugin/admin/src/pluginId.js @@ -1,5 +1,5 @@ const pluginPkg = require('../../package.json'); -const pluginId = pluginPkg.name.replace(/^@strapi\/plugin-/i, ''); +const pluginId = pluginPkg.name.replace(/^(@[^-,.][\w,-]+\/|strapi-)plugin-/i, ''); module.exports = pluginId; From 1028fefb7ff7c25b3233498a9fe3e56e0e707a39 Mon Sep 17 00:00:00 2001 From: Marlon Baeten Date: Mon, 7 Mar 2022 16:08:47 +0100 Subject: [PATCH 02/31] Add SERVER_URL variable to user e-mail templates --- packages/plugins/users-permissions/server/controllers/auth.js | 1 + packages/plugins/users-permissions/server/services/user.js | 1 + 2 files changed, 2 insertions(+) diff --git a/packages/plugins/users-permissions/server/controllers/auth.js b/packages/plugins/users-permissions/server/controllers/auth.js index 1db1766932..f541ca622e 100644 --- a/packages/plugins/users-permissions/server/controllers/auth.js +++ b/packages/plugins/users-permissions/server/controllers/auth.js @@ -240,6 +240,7 @@ module.exports = { settings.message = await getService('users-permissions').template(settings.message, { URL: advanced.email_reset_password, + SERVER_URL: getAbsoluteServerUrl(strapi.config), USER: userInfo, TOKEN: resetPasswordToken, }); diff --git a/packages/plugins/users-permissions/server/services/user.js b/packages/plugins/users-permissions/server/services/user.js index 777d4777e5..0d4bc03f8f 100644 --- a/packages/plugins/users-permissions/server/services/user.js +++ b/packages/plugins/users-permissions/server/services/user.js @@ -118,6 +118,7 @@ module.exports = ({ strapi }) => ({ const apiPrefix = strapi.config.get('api.rest.prefix'); settings.message = await userPermissionService.template(settings.message, { URL: urlJoin(getAbsoluteServerUrl(strapi.config), apiPrefix, '/auth/email-confirmation'), + SERVER_URL: getAbsoluteServerUrl(strapi.config), USER: sanitizedUserInfo, CODE: confirmationToken, }); From 2e7acfce8d0660b37ae04b85c236e5ff128e6dd8 Mon Sep 17 00:00:00 2001 From: Marlon Baeten Date: Mon, 7 Mar 2022 16:15:48 +0100 Subject: [PATCH 03/31] Added SERVER_URL to allowed template variables --- .../server/controllers/validation/email-template.js | 10 +++++++++- 1 file changed, 9 insertions(+), 1 deletion(-) diff --git a/packages/plugins/users-permissions/server/controllers/validation/email-template.js b/packages/plugins/users-permissions/server/controllers/validation/email-template.js index ce455b59b8..58fe0d7d86 100644 --- a/packages/plugins/users-permissions/server/controllers/validation/email-template.js +++ b/packages/plugins/users-permissions/server/controllers/validation/email-template.js @@ -3,7 +3,15 @@ const _ = require('lodash'); const invalidPatternsRegexes = [/<%[^=]([^<>%]*)%>/m, /\${([^{}]*)}/m]; -const authorizedKeys = ['URL', 'CODE', 'USER', 'USER.email', 'USER.username', 'TOKEN']; +const authorizedKeys = [ + 'URL', + 'SERVER_URL', + 'CODE', + 'USER', + 'USER.email', + 'USER.username', + 'TOKEN', +]; const matchAll = (pattern, src) => { const matches = []; From bc4ab36d086e3402ea0ddc46292597fa52e7675a Mon Sep 17 00:00:00 2001 From: Gustav Hansen Date: Wed, 9 Mar 2022 13:24:03 +0100 Subject: [PATCH 04/31] Media Library: improve microcopy --- .../admin/src/components/AssetDialog/SelectedStep/index.js | 4 ++-- .../UploadAssetDialog/PendingAssetStep/PendingAssetStep.js | 4 ++-- .../tests/__snapshots__/PendingAssetStep.test.js.snap | 2 +- .../UploadAssetDialog/tests/UploadAssetDialog.test.js | 4 ++-- packages/core/upload/admin/src/translations/en.json | 2 +- 5 files changed, 8 insertions(+), 8 deletions(-) diff --git a/packages/core/upload/admin/src/components/AssetDialog/SelectedStep/index.js b/packages/core/upload/admin/src/components/AssetDialog/SelectedStep/index.js index be0faf46de..d4082cd625 100644 --- a/packages/core/upload/admin/src/components/AssetDialog/SelectedStep/index.js +++ b/packages/core/upload/admin/src/components/AssetDialog/SelectedStep/index.js @@ -17,7 +17,7 @@ export const SelectedStep = ({ selectedAssets, onSelectAsset, onReorderAsset }) { id: getTrad('list.assets.selected'), defaultMessage: - '{number, plural, =0 {No asset} one {1 asset} other {# assets}} selected', + '{number, plural, =0 {No asset} one {1 asset} other {# assets}} ready to upload', }, { number: selectedAssets.length } )} @@ -25,7 +25,7 @@ export const SelectedStep = ({ selectedAssets, onSelectAsset, onReorderAsset }) {formatMessage({ id: getTrad('modal.upload-list.sub-header-subtitle'), - defaultMessage: 'Manage the assets before uploading them to the Media Library', + defaultMessage: 'Manage the assets before adding them to the Media Library', })} diff --git a/packages/core/upload/admin/src/components/UploadAssetDialog/PendingAssetStep/PendingAssetStep.js b/packages/core/upload/admin/src/components/UploadAssetDialog/PendingAssetStep/PendingAssetStep.js index e3e84354c4..d4345adf51 100644 --- a/packages/core/upload/admin/src/components/UploadAssetDialog/PendingAssetStep/PendingAssetStep.js +++ b/packages/core/upload/admin/src/components/UploadAssetDialog/PendingAssetStep/PendingAssetStep.js @@ -78,7 +78,7 @@ export const PendingAssetStep = ({ { id: getTrad('list.assets.selected'), defaultMessage: - '{number, plural, =0 {No asset} one {1 asset} other {# assets}} selected', + '{number, plural, =0 {No asset} one {1 asset} other {# assets}} ready to upload', }, { number: assets.length } )} @@ -86,7 +86,7 @@ export const PendingAssetStep = ({ {formatMessage({ id: getTrad('modal.upload-list.sub-header-subtitle'), - defaultMessage: 'Manage the assets before uploading them to the Media Library', + defaultMessage: 'Manage the assets before adding them to the Media Library', })} diff --git a/packages/core/upload/admin/src/components/UploadAssetDialog/PendingAssetStep/tests/__snapshots__/PendingAssetStep.test.js.snap b/packages/core/upload/admin/src/components/UploadAssetDialog/PendingAssetStep/tests/__snapshots__/PendingAssetStep.test.js.snap index 14e0dba49e..00ad99b679 100644 --- a/packages/core/upload/admin/src/components/UploadAssetDialog/PendingAssetStep/tests/__snapshots__/PendingAssetStep.test.js.snap +++ b/packages/core/upload/admin/src/components/UploadAssetDialog/PendingAssetStep/tests/__snapshots__/PendingAssetStep.test.js.snap @@ -765,7 +765,7 @@ exports[`PendingAssetStep snapshots the component with valid cards 1`] = ` - Manage the assets before uploading them to the Media Library + Manage the assets before adding them to the Media Library diff --git a/packages/core/content-type-builder/admin/src/translations/en.json b/packages/core/content-type-builder/admin/src/translations/en.json index a2ab0ab01d..4d6da94b02 100644 --- a/packages/core/content-type-builder/admin/src/translations/en.json +++ b/packages/core/content-type-builder/admin/src/translations/en.json @@ -76,9 +76,9 @@ "form.attribute.component.option.single.description": "Best for grouping fields like full address, main information, etc...", "form.attribute.item.customColumnName": "Custom column names", "form.attribute.item.customColumnName.description": "This is useful to rename database column names in a more comprehensive format for the API's responses", - "form.attribute.item.date.type.datee": "date", - "form.attribute.item.date.type.datetimee": "datetime", - "form.attribute.item.date.type.timee": "time", + "form.attribute.item.date.type.date": "date (ex: 01/01/{currentYear})", + "form.attribute.item.date.type.datetime": "datetime (ex: 01/01/{currentYear} 00:00 AM)", + "form.attribute.item.date.type.time": "time (ex: 00:00 AM)", "form.attribute.item.defineRelation.fieldName": "Field name", "form.attribute.item.enumeration.graphql": "Name override for GraphQL", "form.attribute.item.enumeration.graphql.description": "Allows you to override the default generated name for GraphQL", From 77ff0d1bae2d3f4ad5bfa34343f38e1a3f8f851a Mon Sep 17 00:00:00 2001 From: soupette Date: Thu, 17 Mar 2022 09:13:18 +0100 Subject: [PATCH 24/31] Fix snapshots Signed-off-by: soupette --- .../core/admin/admin/src/pages/HomePage/tests/index.test.js | 4 ---- 1 file changed, 4 deletions(-) diff --git a/packages/core/admin/admin/src/pages/HomePage/tests/index.test.js b/packages/core/admin/admin/src/pages/HomePage/tests/index.test.js index faa20ade50..b6836df0bb 100644 --- a/packages/core/admin/admin/src/pages/HomePage/tests/index.test.js +++ b/packages/core/admin/admin/src/pages/HomePage/tests/index.test.js @@ -633,10 +633,6 @@ describe('Homepage', () => { fill: #ff4500; } - .c52 > path:last-child { - fill: #ffffff; - } - .c55 > path:first-child { fill: #8e75ff; } From a497261283f0b703a49cfd7f56376702b74eaa09 Mon Sep 17 00:00:00 2001 From: ronronscelestes Date: Wed, 16 Mar 2022 19:06:58 +0100 Subject: [PATCH 25/31] fix: update homepage snapshots: Reddit's icon --- .../core/admin/admin/src/pages/HomePage/tests/index.test.js | 4 ---- 1 file changed, 4 deletions(-) diff --git a/packages/core/admin/admin/src/pages/HomePage/tests/index.test.js b/packages/core/admin/admin/src/pages/HomePage/tests/index.test.js index faa20ade50..b6836df0bb 100644 --- a/packages/core/admin/admin/src/pages/HomePage/tests/index.test.js +++ b/packages/core/admin/admin/src/pages/HomePage/tests/index.test.js @@ -633,10 +633,6 @@ describe('Homepage', () => { fill: #ff4500; } - .c52 > path:last-child { - fill: #ffffff; - } - .c55 > path:first-child { fill: #8e75ff; } From 26a2786b84fe75f8adc8e21fd76880197a5995e1 Mon Sep 17 00:00:00 2001 From: Gustav Hansen Date: Thu, 17 Mar 2022 10:41:19 +0100 Subject: [PATCH 26/31] ML: Fix format of video duration --- .../src/components/AssetCard/VideoAssetCard.js | 3 ++- .../core/upload/admin/src/utils/formatDuration.js | 15 ++++++--------- 2 files changed, 8 insertions(+), 10 deletions(-) diff --git a/packages/core/upload/admin/src/components/AssetCard/VideoAssetCard.js b/packages/core/upload/admin/src/components/AssetCard/VideoAssetCard.js index 59643e4f91..b626c06924 100644 --- a/packages/core/upload/admin/src/components/AssetCard/VideoAssetCard.js +++ b/packages/core/upload/admin/src/components/AssetCard/VideoAssetCard.js @@ -48,7 +48,8 @@ export const VideoAssetCard = ({ }) => { const { formatMessage } = useIntl(); const [duration, setDuration] = useState(); - const formattedDuration = duration ? formatDuration(duration) : undefined; + + const formattedDuration = duration && formatDuration(duration); return ( diff --git a/packages/core/upload/admin/src/utils/formatDuration.js b/packages/core/upload/admin/src/utils/formatDuration.js index 98a84b2bb7..710e0b6f5f 100644 --- a/packages/core/upload/admin/src/utils/formatDuration.js +++ b/packages/core/upload/admin/src/utils/formatDuration.js @@ -1,12 +1,9 @@ +import { intervalToDuration } from 'date-fns'; + +const zeroPad = num => String(num).padStart(2, '0'); + export const formatDuration = durationInSecond => { - const formatter = new Intl.DateTimeFormat('default', { - hour: 'numeric', - minute: 'numeric', - second: 'numeric', - }); + const duration = intervalToDuration({ start: 0, end: durationInSecond * 1000 }); - const date = new Date(1970, 0, 1); - date.setSeconds(durationInSecond); - - return formatter.format(date); + return `${zeroPad(duration.hours)}:${zeroPad(duration.minutes)}:${zeroPad(duration.seconds)}`; }; From 71d2c70b62c8448627970c58eb26ab0f9e6c5459 Mon Sep 17 00:00:00 2001 From: Gustav Hansen Date: Thu, 17 Mar 2022 10:42:10 +0100 Subject: [PATCH 27/31] formatDuration: add tests --- .../upload/admin/src/utils/tests/formatDuration.test.js | 9 +++++++++ 1 file changed, 9 insertions(+) create mode 100644 packages/core/upload/admin/src/utils/tests/formatDuration.test.js diff --git a/packages/core/upload/admin/src/utils/tests/formatDuration.test.js b/packages/core/upload/admin/src/utils/tests/formatDuration.test.js new file mode 100644 index 0000000000..9a385b305d --- /dev/null +++ b/packages/core/upload/admin/src/utils/tests/formatDuration.test.js @@ -0,0 +1,9 @@ +import { formatDuration } from '../formatDuration'; + +describe('formatDuration', () => { + test('properly format seconds', () => { + expect(formatDuration(1)).toBe('00:00:01'); + expect(formatDuration(60)).toBe('00:01:00'); + expect(formatDuration(3600)).toBe('01:00:00'); + }); +}); From a296a55334338ef07ebb9731221d9a556b7cefa4 Mon Sep 17 00:00:00 2001 From: Convly Date: Thu, 17 Mar 2022 11:42:33 +0100 Subject: [PATCH 28/31] Remove DB examples folder --- packages/core/database/examples/.gitignore | 1 - .../core/database/examples/connections.js | 36 -- .../core/database/examples/docker-compose.yml | 29 -- packages/core/database/examples/index.js | 73 ---- packages/core/database/examples/models.js | 341 ------------------ packages/core/database/examples/typings.ts | 17 - 6 files changed, 497 deletions(-) delete mode 100644 packages/core/database/examples/.gitignore delete mode 100644 packages/core/database/examples/connections.js delete mode 100644 packages/core/database/examples/docker-compose.yml delete mode 100644 packages/core/database/examples/index.js delete mode 100644 packages/core/database/examples/models.js delete mode 100644 packages/core/database/examples/typings.ts diff --git a/packages/core/database/examples/.gitignore b/packages/core/database/examples/.gitignore deleted file mode 100644 index 1269488f7f..0000000000 --- a/packages/core/database/examples/.gitignore +++ /dev/null @@ -1 +0,0 @@ -data diff --git a/packages/core/database/examples/connections.js b/packages/core/database/examples/connections.js deleted file mode 100644 index 10dc81f4d7..0000000000 --- a/packages/core/database/examples/connections.js +++ /dev/null @@ -1,36 +0,0 @@ -'use strict'; - -const postgres = { - client: 'postgres', - connection: { - database: 'strapi', - user: 'strapi', - password: 'strapi', - }, - // debug: true, -}; - -const mysql = { - client: 'mysql', - connection: { - database: 'strapi', - user: 'strapi', - password: 'strapi', - }, - // debug: true, -}; - -const sqlite = { - client: 'sqlite', - connection: { - filename: 'data.sqlite', - }, - useNullAsDefault: true, - // debug: true, -}; - -module.exports = { - sqlite, - postgres, - mysql, -}; diff --git a/packages/core/database/examples/docker-compose.yml b/packages/core/database/examples/docker-compose.yml deleted file mode 100644 index 8569a61080..0000000000 --- a/packages/core/database/examples/docker-compose.yml +++ /dev/null @@ -1,29 +0,0 @@ -version: '3' - -services: - postgres: - image: postgres - restart: always - volumes: - - ./data/postgresql:/var/lib/postgresql/data - environment: - POSTGRES_USER: strapi - POSTGRES_PASSWORD: strapi - POSTGRES_DB: strapi - ports: - - '5432:5432' - - mysql: - image: mysql - restart: always - command: --default-authentication-plugin=mysql_native_password - environment: - MYSQL_DATABASE: strapi - MYSQL_USER: strapi - MYSQL_PASSWORD: strapi - MYSQL_ROOT_HOST: '%' - MYSQL_ROOT_PASSWORD: strapi - volumes: - - ./data/mysql:/var/lib/mysql - ports: - - '3306:3306' diff --git a/packages/core/database/examples/index.js b/packages/core/database/examples/index.js deleted file mode 100644 index 604b2fbbe0..0000000000 --- a/packages/core/database/examples/index.js +++ /dev/null @@ -1,73 +0,0 @@ -'use strict'; - -const util = require('util'); - -const { Database } = require('../lib/index'); -const models = require('./models'); -const connections = require('./connections'); - -async function main(connection) { - const orm = await Database.init({ - connection, - models: Database.transformContentTypes(models), - }); - - try { - // await orm.schema.drop(); - // await orm.schema.create(); - - await orm.schema.reset(); - - let res; - - const c1 = await orm.query('comment').create({ - data: { - title: 'coucou', - }, - }); - - const c2 = await orm.query('video-comment').create({ - data: { - title: 'coucou', - }, - }); - - res = await orm.query('article').create({ - data: { - dz: [ - { - __type: 'comment', - id: c1.id, - }, - { - __type: 'video-comment', - id: c2.id, - }, - ], - }, - populate: { - dz: true, - }, - }); - - log(res); - - res = await orm.query('article').findMany({ - populate: { - dz: true, - }, - }); - - log(res); - - // await tests(orm); - } finally { - orm.destroy(); - } -} - -function log(res) { - console.log(util.inspect(res, null, null, true)); -} - -main(connections.sqlite); diff --git a/packages/core/database/examples/models.js b/packages/core/database/examples/models.js deleted file mode 100644 index e86741ce06..0000000000 --- a/packages/core/database/examples/models.js +++ /dev/null @@ -1,341 +0,0 @@ -'use strict'; - -const category = { - modelName: 'category', - uid: 'category', - collectionName: 'categories', - attributes: { - title: { - type: 'string', - }, - price: { - type: 'integer', - required: true, - default: 12, - - column: { - unique: true, - nonNullable: true, - unsigned: true, - defaultTo: 12, - }, - }, - articles: { - type: 'relation', - relation: 'oneToMany', - target: 'article', - mappedBy: 'category', - }, - compo: { - type: 'component', - component: 'compo', - }, - }, -}; - -const article = { - modelName: 'article', - uid: 'article', - collectionName: 'articles', - attributes: { - title: { - type: 'string', - }, - category: { - type: 'relation', - relation: 'manyToOne', - target: 'category', - inversedBy: 'articles', - // useJoinTable: false, - }, - // tags: { - // type: 'relation', - // relation: 'manyToMany', - // target: 'tag', - // inversedBy: 'articles', - // }, - // compo: { - // type: 'component', - // component: 'compo', - // // repeatable: true, - // }, - // cover: { - // type: 'media', - // single: true, - // }, - // gallery: { - // type: 'media', - // multiple: true, - // }, - }, -}; - -const tags = { - modelName: 'tag', - uid: 'tag', - collectionName: 'tags', - attributes: { - name: { - type: 'string', - }, - articles: { - type: 'relation', - relation: 'manyToMany', - target: 'article', - mappedBy: 'tag', - }, - }, -}; - -const compo = { - modelName: 'compo', - uid: 'compo', - collectionName: 'compos', - attributes: { - key: { - type: 'string', - }, - value: { - type: 'string', - }, - }, -}; - -const user = { - modelName: 'user', - uid: 'user', - collectionName: 'users', - attributes: { - address: { - type: 'relation', - relation: 'oneToOne', - target: 'address', - inversedBy: 'user', - // useJoinTable: false, - }, - }, -}; - -const address = { - modelName: 'address', - uid: 'address', - collectionName: 'addresses', - attributes: { - name: { - type: 'string', - }, - user: { - type: 'relation', - relation: 'oneToOne', - target: 'user', - mappedBy: 'address', - }, - }, -}; - -const file = { - modelName: 'file', - uid: 'file', - collectionName: 'files', - attributes: { - name: { - type: 'string', - }, - alternativeText: { - type: 'string', - }, - caption: { - type: 'string', - }, - width: { - type: 'integer', - }, - height: { - type: 'integer', - }, - formats: { - type: 'json', - }, - hash: { - type: 'string', - }, - ext: { - type: 'string', - }, - mime: { - type: 'string', - }, - size: { - type: 'decimal', - }, - url: { - type: 'string', - }, - previewUrl: { - type: 'string', - }, - provider: { - type: 'string', - }, - provider_metadata: { - type: 'json', - }, - // related: { - // type: 'relation', - // relation: 'oneToMany', - // target: 'file_morph', - // mappedBy: 'file', - // }, - // related: { - // type: 'relation', - // realtion: 'morphTo', - // }, - }, -}; - -const fileMorph = { - modelName: 'file-morph', - uid: 'file-morph', - collectionName: 'file_morphs', - attributes: { - // file: { - // type: 'relation', - // relation: 'manyToOne', - // target: 'file', - // inversedBy: 'related', - // useJoinTable: false, - // }, - }, -}; - -const blogPost = { - modelName: 'blogPost', - uid: 'blogPost', - collectionName: 'blog_posts', - attributes: { - passwordField: { - type: 'password', - }, - emailField: { - type: 'email', - }, - stringField: { - type: 'string', - }, - uidField: { - type: 'uid', - }, - richtextField: { - type: 'richtext', - }, - textField: { - type: 'text', - }, - enumerationField: { - type: 'enumeration', - enum: ['A', 'B'], - }, - jsonField: { - type: 'json', - }, - bigintegerField: { - type: 'biginteger', - }, - integerField: { - type: 'integer', - }, - floatField: { - type: 'float', - }, - decimalField: { - type: 'decimal', - }, - dateField: { - type: 'date', - }, - timeField: { - type: 'time', - }, - datetimeField: { - type: 'datetime', - }, - timestampField: { - type: 'timestamp', - }, - booleanField: { - type: 'boolean', - }, - }, -}; - -module.exports = [category, article, tags, compo, user, address, file, fileMorph, blogPost]; - -// const article = { -// modelName: 'article', -// uid: 'article', -// collectionName: 'articles', -// attributes: { -// commentable: { -// type: 'relation', -// relation: 'morphToOne', -// }, -// reportables: { -// type: 'relation', -// relation: 'morphToMany', -// }, -// dz: { -// type: 'dynamiczone', -// components: ['comment', 'video-comment'], -// }, -// }, -// }; - -// const comment = { -// modelName: 'comment', -// uid: 'comment', -// collectionName: 'comments', -// attributes: { -// article: { -// type: 'relation', -// relation: 'morphOne', -// target: 'article', -// morphBy: 'commentable', -// }, -// title: { -// type: 'string', -// }, -// }, -// }; - -// const videoComment = { -// modelName: 'video-comment', -// uid: 'video-comment', -// collectionName: 'video_comments', -// attributes: { -// articles: { -// type: 'relation', -// relation: 'morphMany', -// target: 'article', -// morphBy: 'commentable', -// }, -// title: { -// type: 'string', -// }, -// }, -// }; - -// const folder = { -// modelName: 'folder', -// uid: 'folder', -// collectionName: 'folders', -// attributes: { -// articles: { -// type: 'relation', -// relation: 'morphMany', -// target: 'article', -// morphBy: 'reportables', -// }, -// }, -// }; - -// module.exports = [article, comment, videoComment, folder]; diff --git a/packages/core/database/examples/typings.ts b/packages/core/database/examples/typings.ts deleted file mode 100644 index b716efed8d..0000000000 --- a/packages/core/database/examples/typings.ts +++ /dev/null @@ -1,17 +0,0 @@ -type ID = number | string; - -interface Category { - id: ID; - title: string; -} - -interface Article { - id: ID; - title: string; - category: Category | ID; -} - -interface AllTypes { - article: Article; - category: Category; -} From 0a5ce6f34a41f9549ba9fa9e4e0276f0e953b088 Mon Sep 17 00:00:00 2001 From: Mattias van den Belt Date: Sat, 19 Mar 2022 01:47:49 +0100 Subject: [PATCH 29/31] Add footer to DynamicTable component --- .../lib/src/components/DynamicTable/index.js | 11 +++++++---- 1 file changed, 7 insertions(+), 4 deletions(-) diff --git a/packages/core/helper-plugin/lib/src/components/DynamicTable/index.js b/packages/core/helper-plugin/lib/src/components/DynamicTable/index.js index 83c9fdf43c..ecf5f2e84d 100644 --- a/packages/core/helper-plugin/lib/src/components/DynamicTable/index.js +++ b/packages/core/helper-plugin/lib/src/components/DynamicTable/index.js @@ -23,10 +23,11 @@ const BlockActions = styled(Flex)` `; const Table = ({ + action, children, contentType, components, - action, + footer, headers, isLoading, onConfirmDeleteAll, @@ -159,7 +160,7 @@ const Table = ({ )} - + {}, @@ -224,13 +226,14 @@ Table.defaultProps = { }; Table.propTypes = { + action: PropTypes.node, children: PropTypes.node, contentType: PropTypes.string.isRequired, components: PropTypes.shape({ ConfirmDialogDelete: PropTypes.oneOfType([PropTypes.func, PropTypes.element]), ConfirmDialogDeleteAll: PropTypes.oneOfType([PropTypes.func, PropTypes.element]), }), - action: PropTypes.node, + footer: PropTypes.node, headers: PropTypes.arrayOf( PropTypes.shape({ cellFormatter: PropTypes.func, From 5fab3b5e7a8a11b57193fdde22b29cef35c0614a Mon Sep 17 00:00:00 2001 From: Mattias van den Belt Date: Sat, 19 Mar 2022 02:02:23 +0100 Subject: [PATCH 30/31] Add DynamicTable with footer Canvas to storybook --- .../DynamicTable/DynamicTable.stories.mdx | 39 ++++++++++++++++++- 1 file changed, 38 insertions(+), 1 deletion(-) diff --git a/packages/core/helper-plugin/lib/src/components/DynamicTable/DynamicTable.stories.mdx b/packages/core/helper-plugin/lib/src/components/DynamicTable/DynamicTable.stories.mdx index 49bc7ecc00..6e882b4b7a 100644 --- a/packages/core/helper-plugin/lib/src/components/DynamicTable/DynamicTable.stories.mdx +++ b/packages/core/helper-plugin/lib/src/components/DynamicTable/DynamicTable.stories.mdx @@ -8,7 +8,7 @@ import { Box } from '@strapi/design-system/Box'; import { Flex } from '@strapi/design-system/Flex'; import { BaseCheckbox } from '@strapi/design-system/BaseCheckbox'; import { Dialog, DialogBody, DialogFooter } from '@strapi/design-system/Dialog'; -import { Tbody, Td, Tr } from '@strapi/design-system/Table'; +import { Tbody, Td, Tr, TFooter } from '@strapi/design-system/Table'; import { Typography } from '@strapi/design-system/Typography'; import { IconButton } from '@strapi/design-system/IconButton'; import { Plus, Pencil, Trash } from '@strapi/icons'; @@ -93,6 +93,43 @@ import { DynamicTable } from '@strapi/helper-plugin'; +## Usage No content with footer + + + + {() => { + const headers = [ + { + name: 'firstname', + metadatas: { label: 'Firstname', sortable: false }, + key: '__firstname_key__', + }, + { + name: 'lastname', + metadatas: { label: 'Email', sortable: false }, + key: '__lastname_key__', + }, + { + name: 'email', + metadatas: { label: 'Email', sortable: false }, + key: '__email_key__', + }, + ]; + const [{ query }, setQuery] = useQueryParams(); + useEffect(() => { + setQuery({ filters: { $and: [{ firstname: { $eq: 'soupette' } }] } }); + }, []); + return ( +
+ + }>Add another user}/> + +
+ ); + }} +
+
+ ## Usage No content with filters From 03028a763fa04943cfa79b94bacad6a6214e1f54 Mon Sep 17 00:00:00 2001 From: Marlon Baeten Date: Mon, 21 Mar 2022 11:04:54 +0100 Subject: [PATCH 31/31] Added ADMIN_URL to email templates --- .../users-permissions/server/controllers/auth.js | 10 +++++++--- .../server/controllers/validation/email-template.js | 1 + .../plugins/users-permissions/server/services/user.js | 3 ++- 3 files changed, 10 insertions(+), 4 deletions(-) diff --git a/packages/plugins/users-permissions/server/controllers/auth.js b/packages/plugins/users-permissions/server/controllers/auth.js index 400a0db5ac..4953e0e8ff 100644 --- a/packages/plugins/users-permissions/server/controllers/auth.js +++ b/packages/plugins/users-permissions/server/controllers/auth.js @@ -17,7 +17,7 @@ const { validateSendEmailConfirmationBody, } = require('./validation/auth'); -const { getAbsoluteServerUrl, sanitize } = utils; +const { getAbsoluteAdminUrl, getAbsoluteServerUrl, sanitize } = utils; const { ApplicationError, ValidationError } = utils.errors; const emailRegExp = /^(([^<>()\[\]\\.,;:\s@"]+(\.[^<>()\[\]\\.,;:\s@"]+)*)|(".+"))@((\[[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\])|(([a-zA-Z\-0-9]+\.)+[a-zA-Z]{2,}))$/; @@ -137,7 +137,10 @@ module.exports = { throw new ValidationError('Incorrect code provided'); } - await getService('user').edit(user.id, { resetPasswordToken: null, password: params.password }); + await getService('user').edit(user.id, { + resetPasswordToken: null, + password: params.password, + }); // Update the user. ctx.send({ jwt: getService('jwt').issue({ id: user.id }), @@ -241,6 +244,7 @@ module.exports = { settings.message = await getService('users-permissions').template(settings.message, { URL: advanced.email_reset_password, SERVER_URL: getAbsoluteServerUrl(strapi.config), + ADMIN_URL: getAbsoluteAdminUrl(strapi.config), USER: userInfo, TOKEN: resetPasswordToken, }); @@ -339,7 +343,7 @@ module.exports = { params.confirmed = true; } - const user = await getService('user').add(params); + const user = await getService('user').add(params); const sanitizedUser = await sanitizeUser(user, ctx); diff --git a/packages/plugins/users-permissions/server/controllers/validation/email-template.js b/packages/plugins/users-permissions/server/controllers/validation/email-template.js index 58fe0d7d86..8f3581d7b1 100644 --- a/packages/plugins/users-permissions/server/controllers/validation/email-template.js +++ b/packages/plugins/users-permissions/server/controllers/validation/email-template.js @@ -5,6 +5,7 @@ const _ = require('lodash'); const invalidPatternsRegexes = [/<%[^=]([^<>%]*)%>/m, /\${([^{}]*)}/m]; const authorizedKeys = [ 'URL', + 'ADMIN_URL', 'SERVER_URL', 'CODE', 'USER', diff --git a/packages/plugins/users-permissions/server/services/user.js b/packages/plugins/users-permissions/server/services/user.js index 0d4bc03f8f..296838c729 100644 --- a/packages/plugins/users-permissions/server/services/user.js +++ b/packages/plugins/users-permissions/server/services/user.js @@ -10,7 +10,7 @@ const crypto = require('crypto'); const bcrypt = require('bcryptjs'); const urlJoin = require('url-join'); -const { getAbsoluteServerUrl, sanitize } = require('@strapi/utils'); +const { getAbsoluteAdminUrl, getAbsoluteServerUrl, sanitize } = require('@strapi/utils'); const { getService } = require('../utils'); module.exports = ({ strapi }) => ({ @@ -119,6 +119,7 @@ module.exports = ({ strapi }) => ({ settings.message = await userPermissionService.template(settings.message, { URL: urlJoin(getAbsoluteServerUrl(strapi.config), apiPrefix, '/auth/email-confirmation'), SERVER_URL: getAbsoluteServerUrl(strapi.config), + ADMIN_URL: getAbsoluteAdminUrl(strapi.config), USER: sanitizedUserInfo, CODE: confirmationToken, });