@strapi/content-manager 5.46.1 → 5.47.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/admin/history/components/VersionInputRenderer.js +63 -25
- package/dist/admin/history/components/VersionInputRenderer.js.map +1 -1
- package/dist/admin/history/components/VersionInputRenderer.mjs +62 -26
- package/dist/admin/history/components/VersionInputRenderer.mjs.map +1 -1
- package/dist/admin/hooks/useDocument.js +82 -2
- package/dist/admin/hooks/useDocument.js.map +1 -1
- package/dist/admin/hooks/useDocument.mjs +82 -2
- package/dist/admin/hooks/useDocument.mjs.map +1 -1
- package/dist/admin/pages/EditView/EditViewPage.js +3 -2
- package/dist/admin/pages/EditView/EditViewPage.js.map +1 -1
- package/dist/admin/pages/EditView/EditViewPage.mjs +3 -2
- package/dist/admin/pages/EditView/EditViewPage.mjs.map +1 -1
- package/dist/admin/pages/EditView/components/DocumentActions.js +6 -3
- package/dist/admin/pages/EditView/components/DocumentActions.js.map +1 -1
- package/dist/admin/pages/EditView/components/DocumentActions.mjs +6 -3
- package/dist/admin/pages/EditView/components/DocumentActions.mjs.map +1 -1
- package/dist/admin/pages/EditView/components/FormInputs/Component/Repeatable.js +4 -1
- package/dist/admin/pages/EditView/components/FormInputs/Component/Repeatable.js.map +1 -1
- package/dist/admin/pages/EditView/components/FormInputs/Component/Repeatable.mjs +4 -1
- package/dist/admin/pages/EditView/components/FormInputs/Component/Repeatable.mjs.map +1 -1
- package/dist/admin/pages/EditView/components/FormInputs/Relations/Relations.js +4 -4
- package/dist/admin/pages/EditView/components/FormInputs/Relations/Relations.js.map +1 -1
- package/dist/admin/pages/EditView/components/FormInputs/Relations/Relations.mjs +4 -4
- package/dist/admin/pages/EditView/components/FormInputs/Relations/Relations.mjs.map +1 -1
- package/dist/admin/src/history/components/VersionInputRenderer.d.ts +27 -1
- package/dist/admin/translations/sk.json.js +175 -9
- package/dist/admin/translations/sk.json.js.map +1 -1
- package/dist/admin/translations/sk.json.mjs +175 -9
- package/dist/admin/translations/sk.json.mjs.map +1 -1
- package/dist/admin/utils/relations.js +4 -0
- package/dist/admin/utils/relations.js.map +1 -1
- package/dist/admin/utils/relations.mjs +4 -0
- package/dist/admin/utils/relations.mjs.map +1 -1
- package/dist/server/bootstrap.js +4 -0
- package/dist/server/bootstrap.js.map +1 -1
- package/dist/server/bootstrap.mjs +4 -0
- package/dist/server/bootstrap.mjs.map +1 -1
- package/dist/server/controllers/collection-types.js +9 -5
- package/dist/server/controllers/collection-types.js.map +1 -1
- package/dist/server/controllers/collection-types.mjs +10 -6
- package/dist/server/controllers/collection-types.mjs.map +1 -1
- package/dist/server/homepage/services/homepage.js +21 -16
- package/dist/server/homepage/services/homepage.js.map +1 -1
- package/dist/server/homepage/services/homepage.mjs +21 -16
- package/dist/server/homepage/services/homepage.mjs.map +1 -1
- package/dist/server/mcp/derive-content-type-mcp-tools.js +524 -0
- package/dist/server/mcp/derive-content-type-mcp-tools.js.map +1 -0
- package/dist/server/mcp/derive-content-type-mcp-tools.mjs +518 -0
- package/dist/server/mcp/derive-content-type-mcp-tools.mjs.map +1 -0
- package/dist/server/mcp/handlers/collection-handlers.js +404 -0
- package/dist/server/mcp/handlers/collection-handlers.js.map +1 -0
- package/dist/server/mcp/handlers/collection-handlers.mjs +395 -0
- package/dist/server/mcp/handlers/collection-handlers.mjs.map +1 -0
- package/dist/server/mcp/handlers/constants.js +10 -0
- package/dist/server/mcp/handlers/constants.js.map +1 -0
- package/dist/server/mcp/handlers/constants.mjs +6 -0
- package/dist/server/mcp/handlers/constants.mjs.map +1 -0
- package/dist/server/mcp/handlers/single-type-handlers.js +344 -0
- package/dist/server/mcp/handlers/single-type-handlers.js.map +1 -0
- package/dist/server/mcp/handlers/single-type-handlers.mjs +336 -0
- package/dist/server/mcp/handlers/single-type-handlers.mjs.map +1 -0
- package/dist/server/mcp/permissions.js +138 -0
- package/dist/server/mcp/permissions.js.map +1 -0
- package/dist/server/mcp/permissions.mjs +131 -0
- package/dist/server/mcp/permissions.mjs.map +1 -0
- package/dist/server/mcp/register-content-manager-mcp-tools.js +30 -0
- package/dist/server/mcp/register-content-manager-mcp-tools.js.map +1 -0
- package/dist/server/mcp/register-content-manager-mcp-tools.mjs +28 -0
- package/dist/server/mcp/register-content-manager-mcp-tools.mjs.map +1 -0
- package/dist/server/mcp/schemas/blocks-schema.js +124 -0
- package/dist/server/mcp/schemas/blocks-schema.js.map +1 -0
- package/dist/server/mcp/schemas/blocks-schema.mjs +122 -0
- package/dist/server/mcp/schemas/blocks-schema.mjs.map +1 -0
- package/dist/server/mcp/schemas/data-schema.js +252 -0
- package/dist/server/mcp/schemas/data-schema.js.map +1 -0
- package/dist/server/mcp/schemas/data-schema.mjs +248 -0
- package/dist/server/mcp/schemas/data-schema.mjs.map +1 -0
- package/dist/server/mcp/schemas/filters-schema.js +111 -0
- package/dist/server/mcp/schemas/filters-schema.js.map +1 -0
- package/dist/server/mcp/schemas/filters-schema.mjs +107 -0
- package/dist/server/mcp/schemas/filters-schema.mjs.map +1 -0
- package/dist/server/mcp/schemas/input-schemas.js +18 -0
- package/dist/server/mcp/schemas/input-schemas.js.map +1 -0
- package/dist/server/mcp/schemas/input-schemas.mjs +13 -0
- package/dist/server/mcp/schemas/input-schemas.mjs.map +1 -0
- package/dist/server/mcp/schemas/output-schemas.js +48 -0
- package/dist/server/mcp/schemas/output-schemas.js.map +1 -0
- package/dist/server/mcp/schemas/output-schemas.mjs +44 -0
- package/dist/server/mcp/schemas/output-schemas.mjs.map +1 -0
- package/dist/server/mcp/schemas/sort-schema.js +80 -0
- package/dist/server/mcp/schemas/sort-schema.js.map +1 -0
- package/dist/server/mcp/schemas/sort-schema.mjs +76 -0
- package/dist/server/mcp/schemas/sort-schema.mjs.map +1 -0
- package/dist/server/mcp/utils.js +43 -0
- package/dist/server/mcp/utils.js.map +1 -0
- package/dist/server/mcp/utils.mjs +39 -0
- package/dist/server/mcp/utils.mjs.map +1 -0
- package/dist/server/services/document-metadata.js +32 -3
- package/dist/server/services/document-metadata.js.map +1 -1
- package/dist/server/services/document-metadata.mjs +32 -3
- package/dist/server/services/document-metadata.mjs.map +1 -1
- package/dist/server/services/index.js +1 -1
- package/dist/server/services/index.js.map +1 -1
- package/dist/server/services/permission-checker.js +4 -1
- package/dist/server/services/permission-checker.js.map +1 -1
- package/dist/server/services/permission-checker.mjs +1 -1
- package/dist/server/services/permission-checker.mjs.map +1 -1
- package/dist/server/services/utils/populate.js +3 -3
- package/dist/server/services/utils/populate.js.map +1 -1
- package/dist/server/services/utils/populate.mjs +3 -3
- package/dist/server/services/utils/populate.mjs.map +1 -1
- package/dist/server/src/bootstrap.d.ts.map +1 -1
- package/dist/server/src/controllers/collection-types.d.ts.map +1 -1
- package/dist/server/src/homepage/services/homepage.d.ts.map +1 -1
- package/dist/server/src/index.d.ts +3 -3
- package/dist/server/src/mcp/derive-content-type-mcp-tools.d.ts +12 -0
- package/dist/server/src/mcp/derive-content-type-mcp-tools.d.ts.map +1 -0
- package/dist/server/src/mcp/handlers/collection-handlers.d.ts +69 -0
- package/dist/server/src/mcp/handlers/collection-handlers.d.ts.map +1 -0
- package/dist/server/src/mcp/handlers/constants.d.ts +4 -0
- package/dist/server/src/mcp/handlers/constants.d.ts.map +1 -0
- package/dist/server/src/mcp/handlers/index.d.ts +3 -0
- package/dist/server/src/mcp/handlers/index.d.ts.map +1 -0
- package/dist/server/src/mcp/handlers/single-type-handlers.d.ts +66 -0
- package/dist/server/src/mcp/handlers/single-type-handlers.d.ts.map +1 -0
- package/dist/server/src/mcp/permissions.d.ts +49 -0
- package/dist/server/src/mcp/permissions.d.ts.map +1 -0
- package/dist/server/src/mcp/register-content-manager-mcp-tools.d.ts +8 -0
- package/dist/server/src/mcp/register-content-manager-mcp-tools.d.ts.map +1 -0
- package/dist/server/src/mcp/schemas/blocks-schema.d.ts +8 -0
- package/dist/server/src/mcp/schemas/blocks-schema.d.ts.map +1 -0
- package/dist/server/src/mcp/schemas/data-schema.d.ts +36 -0
- package/dist/server/src/mcp/schemas/data-schema.d.ts.map +1 -0
- package/dist/server/src/mcp/schemas/filters-schema.d.ts +22 -0
- package/dist/server/src/mcp/schemas/filters-schema.d.ts.map +1 -0
- package/dist/server/src/mcp/schemas/index.d.ts +7 -0
- package/dist/server/src/mcp/schemas/index.d.ts.map +1 -0
- package/dist/server/src/mcp/schemas/input-schemas.d.ts +10 -0
- package/dist/server/src/mcp/schemas/input-schemas.d.ts.map +1 -0
- package/dist/server/src/mcp/schemas/output-schemas.d.ts +18 -0
- package/dist/server/src/mcp/schemas/output-schemas.d.ts.map +1 -0
- package/dist/server/src/mcp/schemas/sort-schema.d.ts +24 -0
- package/dist/server/src/mcp/schemas/sort-schema.d.ts.map +1 -0
- package/dist/server/src/mcp/types.d.ts +31 -0
- package/dist/server/src/mcp/types.d.ts.map +1 -0
- package/dist/server/src/mcp/utils.d.ts +21 -0
- package/dist/server/src/mcp/utils.d.ts.map +1 -0
- package/dist/server/src/services/document-metadata.d.ts +11 -1
- package/dist/server/src/services/document-metadata.d.ts.map +1 -1
- package/dist/server/src/services/index.d.ts +3 -3
- package/dist/server/src/services/permission-checker.d.ts +13 -3
- package/dist/server/src/services/permission-checker.d.ts.map +1 -1
- package/dist/server/src/services/utils/configuration/index.d.ts +2 -2
- package/dist/server/src/services/utils/configuration/layouts.d.ts +2 -2
- package/dist/server/src/services/utils/populate.d.ts.map +1 -1
- package/package.json +10 -8
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"permission-checker.mjs","sources":["../../../server/src/services/permission-checker.ts"],"sourcesContent":["import { async } from '@strapi/utils';\nimport { isEmpty } from 'lodash/fp';\nimport type { Core, UID, Modules } from '@strapi/types';\n\nconst ACTIONS = {\n read: 'plugin::content-manager.explorer.read',\n create: 'plugin::content-manager.explorer.create',\n update: 'plugin::content-manager.explorer.update',\n delete: 'plugin::content-manager.explorer.delete',\n publish: 'plugin::content-manager.explorer.publish',\n unpublish: 'plugin::content-manager.explorer.publish',\n discard: 'plugin::content-manager.explorer.update',\n} as const;\n\ntype Entity = Modules.EntityService.Result<UID.ContentType>;\ntype Query = {\n page?: string;\n pageSize?: string;\n sort?: string;\n};\n\nconst createPermissionChecker =\n (strapi: Core.Strapi) =>\n ({ userAbility, model }: { userAbility: any; model: string }) => {\n const permissionsManager = strapi.service('admin::permission').createPermissionsManager({\n ability: userAbility,\n model,\n });\n\n const { actionProvider } = strapi.service('admin::permission');\n\n const toSubject = (entity?: Entity) => {\n return entity ? permissionsManager.toSubject(entity, model) : model;\n };\n\n // @ts-expect-error preserve the parameter order\n // eslint-disable-next-line @typescript-eslint/default-param-last\n const can = (action: string, entity?: Entity, field: string) => {\n const subject = toSubject(entity);\n const aliases = actionProvider.unstable_aliases(action, model) as string[];\n\n return (\n // Test the original action to see if it passes\n userAbility.can(action, subject, field) ||\n // Else try every known alias if at least one of them succeed, then the user \"can\"\n aliases.some((alias) => userAbility.can(alias, subject, field))\n );\n };\n\n // @ts-expect-error preserve the parameter order\n // eslint-disable-next-line @typescript-eslint/default-param-last\n const cannot = (action: string, entity?: Entity, field: string) => {\n const subject = toSubject(entity);\n const aliases = actionProvider.unstable_aliases(action, model) as string[];\n\n return (\n // Test both the original action\n userAbility.cannot(action, subject, field) &&\n // and every known alias, if all of them fail (cannot), then the user truly \"cannot\"\n aliases.every((alias) => userAbility.cannot(alias, subject, field))\n );\n };\n\n const sanitizeOutput = (data: Entity, { action = ACTIONS.read }: { action?: string } = {}) => {\n return permissionsManager.sanitizeOutput(data, { subject: toSubject(data), action });\n };\n\n const getRulesForAction = (action: string) => {\n if (typeof userAbility.rulesFor !== 'function') {\n return [];\n }\n\n const aliases = actionProvider.unstable_aliases(action, model) as string[];\n const actions = [action, ...aliases];\n\n return actions.flatMap((actionName) => userAbility.rulesFor(actionName, model));\n };\n\n // Tell callers if we need the full entity to check access\n const requiresEntity = (action: string) => {\n if (typeof userAbility.rulesFor !== 'function') {\n return true;\n }\n\n const rules = getRulesForAction(action);\n\n return rules.some((rule: any) => rule.conditions && !isEmpty(rule.conditions));\n };\n\n const sanitizeQuery = (query: Query, { action = ACTIONS.read }: { action?: string } = {}) => {\n return permissionsManager.sanitizeQuery(query, { subject: model, action });\n };\n\n const sanitizeInput = (action: string, data: any, entity?: Entity) => {\n return permissionsManager.sanitizeInput(data, {\n subject: entity ? toSubject(entity) : model,\n action,\n });\n };\n\n const validateQuery = (query: Query, { action = ACTIONS.read }: { action?: string } = {}) => {\n return permissionsManager.validateQuery(query, { subject: model, action });\n };\n\n const validateInput = (action: string, data: any, entity?: Entity) => {\n return permissionsManager.validateInput(data, {\n subject: entity ? toSubject(entity) : model,\n action,\n });\n };\n\n const sanitizeCreateInput = (data: any) => sanitizeInput(ACTIONS.create, data);\n const sanitizeUpdateInput = (entity: Entity) => (data: any) =>\n sanitizeInput(ACTIONS.update, data, entity);\n\n const buildPermissionQuery = (query: Query, action: { action?: string } = {}) => {\n return permissionsManager.addPermissionsQueryTo(query, action);\n };\n\n const sanitizedQuery = (query: Query, action: { action?: string } = {}) => {\n return async.pipe(\n (q: Query) => sanitizeQuery(q, action),\n (q: Query) => buildPermissionQuery(q, action)\n )(query);\n };\n\n // Sanitized queries shortcuts\n Object.keys(ACTIONS).forEach((action) => {\n // @ts-expect-error TODO\n sanitizedQuery[action] = (query: Query) => sanitizedQuery(query, ACTIONS[action]);\n });\n\n // Permission utils shortcuts\n Object.keys(ACTIONS).forEach((action) => {\n // @ts-expect-error TODO\n can[action] = (...args: any) => can(ACTIONS[action], ...args);\n // @ts-expect-error TODO\n cannot[action] = (...args: any) => cannot(ACTIONS[action], ...args);\n // @ts-expect-error TODO\n requiresEntity[action] = () => requiresEntity(ACTIONS[action]);\n });\n\n return {\n // Permission utils\n can, // check if you have the permission\n cannot, // check if you don't have the permission\n requiresEntity, // check if entity data is needed for permission evaluation\n // Sanitizers\n sanitizeOutput,\n sanitizeQuery,\n sanitizeCreateInput,\n sanitizeUpdateInput,\n // Validators\n validateQuery,\n validateInput,\n // Queries Builder\n sanitizedQuery,\n };\n };\n\nexport default ({ strapi }: { strapi: Core.Strapi }) => ({\n create: createPermissionChecker(strapi),\n});\n"],"names":["ACTIONS","read","create","update","delete","publish","unpublish","discard","createPermissionChecker","strapi","userAbility","model","permissionsManager","service","createPermissionsManager","ability","actionProvider","toSubject","entity","can","action","field","subject","aliases","unstable_aliases","some","alias","cannot","every","sanitizeOutput","data","getRulesForAction","rulesFor","actions","flatMap","actionName","requiresEntity","rules","rule","conditions","isEmpty","sanitizeQuery","query","sanitizeInput","validateQuery","validateInput","sanitizeCreateInput","sanitizeUpdateInput","buildPermissionQuery","addPermissionsQueryTo","sanitizedQuery","async","pipe","q","Object","keys","forEach","args"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"permission-checker.mjs","sources":["../../../server/src/services/permission-checker.ts"],"sourcesContent":["import type { Ability } from '@casl/ability';\nimport { async } from '@strapi/utils';\nimport { isEmpty } from 'lodash/fp';\nimport type { Core, UID, Modules } from '@strapi/types';\n\nexport const ACTIONS = {\n read: 'plugin::content-manager.explorer.read',\n create: 'plugin::content-manager.explorer.create',\n update: 'plugin::content-manager.explorer.update',\n delete: 'plugin::content-manager.explorer.delete',\n publish: 'plugin::content-manager.explorer.publish',\n unpublish: 'plugin::content-manager.explorer.publish',\n discard: 'plugin::content-manager.explorer.update',\n} as const;\n\ntype Entity = Modules.EntityService.Result<UID.ContentType>;\ntype Query = {\n page?: string;\n pageSize?: string;\n sort?: string;\n};\n\nconst createPermissionChecker =\n (strapi: Core.Strapi) =>\n ({ userAbility, model }: { userAbility: Ability; model: string }) => {\n const permissionsManager = strapi.service('admin::permission').createPermissionsManager({\n ability: userAbility,\n model,\n });\n\n const { actionProvider } = strapi.service('admin::permission');\n\n const toSubject = (entity?: Entity) => {\n return entity ? permissionsManager.toSubject(entity, model) : model;\n };\n\n // @ts-expect-error preserve the parameter order\n // eslint-disable-next-line @typescript-eslint/default-param-last\n const can = (action: string, entity?: Entity, field: string) => {\n const subject = toSubject(entity);\n const aliases = actionProvider.unstable_aliases(action, model) as string[];\n\n return (\n // Test the original action to see if it passes\n userAbility.can(action, subject, field) ||\n // Else try every known alias if at least one of them succeed, then the user \"can\"\n aliases.some((alias) => userAbility.can(alias, subject, field))\n );\n };\n\n // @ts-expect-error preserve the parameter order\n // eslint-disable-next-line @typescript-eslint/default-param-last\n const cannot = (action: string, entity?: Entity, field: string) => {\n const subject = toSubject(entity);\n const aliases = actionProvider.unstable_aliases(action, model) as string[];\n\n return (\n // Test both the original action\n userAbility.cannot(action, subject, field) &&\n // and every known alias, if all of them fail (cannot), then the user truly \"cannot\"\n aliases.every((alias) => userAbility.cannot(alias, subject, field))\n );\n };\n\n const sanitizeOutput = (data: Entity, { action = ACTIONS.read }: { action?: string } = {}) => {\n return permissionsManager.sanitizeOutput(data, { subject: toSubject(data), action });\n };\n\n const getRulesForAction = (action: string) => {\n if (typeof userAbility.rulesFor !== 'function') {\n return [];\n }\n\n const aliases = actionProvider.unstable_aliases(action, model) as string[];\n const actions = [action, ...aliases];\n\n return actions.flatMap((actionName) => userAbility.rulesFor(actionName, model));\n };\n\n // Tell callers if we need the full entity to check access\n const requiresEntity = (action: string) => {\n if (typeof userAbility.rulesFor !== 'function') {\n return true;\n }\n\n const rules = getRulesForAction(action);\n\n return rules.some((rule: any) => rule.conditions && !isEmpty(rule.conditions));\n };\n\n const sanitizeQuery = (query: Query, { action = ACTIONS.read }: { action?: string } = {}) => {\n return permissionsManager.sanitizeQuery(query, { subject: model, action });\n };\n\n const sanitizeInput = (action: string, data: any, entity?: Entity) => {\n return permissionsManager.sanitizeInput(data, {\n subject: entity ? toSubject(entity) : model,\n action,\n });\n };\n\n const validateQuery = (query: Query, { action = ACTIONS.read }: { action?: string } = {}) => {\n return permissionsManager.validateQuery(query, { subject: model, action });\n };\n\n const validateInput = (action: string, data: any, entity?: Entity) => {\n return permissionsManager.validateInput(data, {\n subject: entity ? toSubject(entity) : model,\n action,\n });\n };\n\n const sanitizeCreateInput = (data: any) => sanitizeInput(ACTIONS.create, data);\n const sanitizeUpdateInput = (entity: Entity) => (data: any) =>\n sanitizeInput(ACTIONS.update, data, entity);\n\n const buildPermissionQuery = (query: Query, action: { action?: string } = {}) => {\n return permissionsManager.addPermissionsQueryTo(query, action);\n };\n\n const sanitizedQuery = (query: Query, action: { action?: string } = {}) => {\n return async.pipe(\n (q: Query) => sanitizeQuery(q, action),\n (q: Query) => buildPermissionQuery(q, action)\n )(query);\n };\n\n // Sanitized queries shortcuts\n Object.keys(ACTIONS).forEach((action) => {\n // @ts-expect-error TODO\n sanitizedQuery[action] = (query: Query) => sanitizedQuery(query, ACTIONS[action]);\n });\n\n // Permission utils shortcuts\n Object.keys(ACTIONS).forEach((action) => {\n // @ts-expect-error TODO\n can[action] = (...args: any) => can(ACTIONS[action], ...args);\n // @ts-expect-error TODO\n cannot[action] = (...args: any) => cannot(ACTIONS[action], ...args);\n // @ts-expect-error TODO\n requiresEntity[action] = () => requiresEntity(ACTIONS[action]);\n });\n\n return {\n // Permission utils\n can, // check if you have the permission\n cannot, // check if you don't have the permission\n requiresEntity, // check if entity data is needed for permission evaluation\n // Sanitizers\n sanitizeOutput,\n sanitizeQuery,\n sanitizeCreateInput,\n sanitizeUpdateInput,\n // Validators\n validateQuery,\n validateInput,\n // Queries Builder\n sanitizedQuery,\n };\n };\n\nexport default ({ strapi }: { strapi: Core.Strapi }) => ({\n create: createPermissionChecker(strapi),\n});\n"],"names":["ACTIONS","read","create","update","delete","publish","unpublish","discard","createPermissionChecker","strapi","userAbility","model","permissionsManager","service","createPermissionsManager","ability","actionProvider","toSubject","entity","can","action","field","subject","aliases","unstable_aliases","some","alias","cannot","every","sanitizeOutput","data","getRulesForAction","rulesFor","actions","flatMap","actionName","requiresEntity","rules","rule","conditions","isEmpty","sanitizeQuery","query","sanitizeInput","validateQuery","validateInput","sanitizeCreateInput","sanitizeUpdateInput","buildPermissionQuery","addPermissionsQueryTo","sanitizedQuery","async","pipe","q","Object","keys","forEach","args"],"mappings":"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"}
|
|
@@ -4,7 +4,7 @@ var fp = require('lodash/fp');
|
|
|
4
4
|
var strapiUtils = require('@strapi/utils');
|
|
5
5
|
var index = require('../../utils/index.js');
|
|
6
6
|
|
|
7
|
-
const { isVisibleAttribute, isScalarAttribute, getDoesAttributeRequireValidation, hasDraftAndPublish } = strapiUtils.contentTypes;
|
|
7
|
+
const { isVisibleAttribute, isScalarAttribute, getDoesAttributeRequireValidation, isPrivateAttribute, hasDraftAndPublish } = strapiUtils.contentTypes;
|
|
8
8
|
const { isAnyToMany } = strapiUtils.relations;
|
|
9
9
|
const { PUBLISHED_AT_ATTRIBUTE } = strapiUtils.contentTypes.constants;
|
|
10
10
|
const isMorphToRelation = (attribute)=>isRelation(attribute) && attribute.relation.includes('morphTo');
|
|
@@ -140,14 +140,14 @@ const getPopulateForValidation = (uid)=>{
|
|
|
140
140
|
const result = Object.entries(model.attributes).reduce((populateAcc, [attributeName, attribute])=>{
|
|
141
141
|
if (isScalarAttribute(attribute)) {
|
|
142
142
|
// If the scalar attribute requires validation, add it to the fields array
|
|
143
|
-
if (getDoesAttributeRequireValidation(attribute)) {
|
|
143
|
+
if (getDoesAttributeRequireValidation(attribute) && !isPrivateAttribute(model, attributeName)) {
|
|
144
144
|
populateAcc.fields = populateAcc.fields || [];
|
|
145
145
|
populateAcc.fields.push(attributeName);
|
|
146
146
|
}
|
|
147
147
|
return populateAcc;
|
|
148
148
|
}
|
|
149
149
|
if (isMedia(attribute)) {
|
|
150
|
-
if (getDoesAttributeRequireValidation(attribute)) {
|
|
150
|
+
if (getDoesAttributeRequireValidation(attribute) && !isPrivateAttribute(model, attributeName)) {
|
|
151
151
|
populateAcc.populate = populateAcc.populate || {};
|
|
152
152
|
populateAcc.populate[attributeName] = {
|
|
153
153
|
populate: {
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"populate.js","sources":["../../../../server/src/services/utils/populate.ts"],"sourcesContent":["import { merge, isEmpty, set, propEq } from 'lodash/fp';\nimport strapiUtils from '@strapi/utils';\nimport type { UID, Schema, Modules } from '@strapi/types';\nimport { getService } from '../../utils';\n\nconst {\n isVisibleAttribute,\n isScalarAttribute,\n getDoesAttributeRequireValidation,\n hasDraftAndPublish,\n} = strapiUtils.contentTypes;\nconst { isAnyToMany } = strapiUtils.relations;\nconst { PUBLISHED_AT_ATTRIBUTE } = strapiUtils.contentTypes.constants;\n\nconst isMorphToRelation = (attribute: any) =>\n isRelation(attribute) && attribute.relation.includes('morphTo');\nconst isMedia = propEq('type', 'media');\nconst isRelation = propEq('type', 'relation');\nconst isComponent = propEq('type', 'component');\nconst isDynamicZone = propEq('type', 'dynamiczone');\n\n// TODO: Import from @strapi/types when it's available there\ntype Model = Parameters<typeof isVisibleAttribute>[0];\nexport type Populate = Modules.EntityService.Params.Populate.Any<UID.Schema>;\n\ntype PopulateOptions = {\n initialPopulate?: Populate;\n countMany?: boolean;\n countOne?: boolean;\n maxLevel?: number;\n};\n\n/**\n * Populate the model for relation\n * @param attribute - Attribute containing a relation\n * @param attribute.relation - type of relation\n * @param model - Model of the populated entity\n * @param attributeName\n * @param options - Options to apply while populating\n */\nfunction getPopulateForRelation(\n attribute: Schema.Attribute.AnyAttribute,\n model: Model,\n attributeName: string,\n { countMany, countOne, initialPopulate }: PopulateOptions\n) {\n const isManyRelation = isAnyToMany(attribute);\n\n // Use initialPopulate when explicitly provided (including `false` to suppress population)\n if (initialPopulate !== undefined) {\n return initialPopulate;\n }\n\n // If populating localizations attribute, also include validatable fields\n // Mainly needed for bulk locale publishing, so the Client has all the information necessary to perform validations\n if (attributeName === 'localizations') {\n const validationPopulate = getPopulateForValidation(model.uid as UID.Schema);\n\n return {\n populate: validationPopulate.populate,\n };\n }\n\n // always populate createdBy, updatedBy, localizations etc.\n if (!isVisibleAttribute(model, attributeName)) {\n return true;\n }\n\n if ((isManyRelation && countMany) || (!isManyRelation && countOne)) {\n return { count: true };\n }\n\n return true;\n}\n\n/**\n * Populate the model for Dynamic Zone components\n * @param attribute - Attribute containing the components\n * @param attribute.components - IDs of components\n * @param options - Options to apply while populating\n */\nfunction getPopulateForDZ(\n attribute: Schema.Attribute.DynamicZone,\n options: PopulateOptions,\n level: number\n) {\n // Use fragments to populate the dynamic zone components\n const populatedComponents = (attribute.components || []).reduce(\n (acc: any, componentUID: UID.Component) => ({\n ...acc,\n [componentUID]: {\n populate: getDeepPopulate(componentUID, options, level + 1),\n },\n }),\n {}\n );\n\n return { on: populatedComponents };\n}\n\n/**\n * Get the populated value based on the type of the attribute\n * @param attributeName - Name of the attribute\n * @param model - Model of the populated entity\n * @param model.attributes\n * @param options - Options to apply while populating\n * @param options.countMany\n * @param options.countOne\n * @param options.maxLevel\n * @param level\n */\nfunction getPopulateFor(\n attributeName: string,\n model: any,\n options: PopulateOptions,\n level: number\n): { [key: string]: boolean | object } {\n const attribute = model.attributes[attributeName];\n\n switch (attribute.type) {\n case 'relation':\n // @ts-expect-error - TODO: support populate count typing\n return {\n [attributeName]: getPopulateForRelation(attribute, model, attributeName, options),\n };\n case 'component':\n return {\n [attributeName]: {\n populate: getDeepPopulate(attribute.component, options, level + 1),\n },\n };\n case 'media':\n return {\n [attributeName]: {\n populate: {\n folder: true,\n },\n },\n };\n case 'dynamiczone':\n return {\n [attributeName]: getPopulateForDZ(attribute, options, level),\n };\n default:\n return {};\n }\n}\n\n/**\n * Deeply populate a model based on UID\n * @param uid - Unique identifier of the model\n * @param options - Options to apply while populating\n * @param level - Current level of nested call\n */\nconst getDeepPopulate = (\n uid: UID.Schema,\n {\n initialPopulate = {} as any,\n countMany = false,\n countOne = false,\n maxLevel = Infinity,\n }: PopulateOptions = {},\n level = 1\n) => {\n if (level > maxLevel) {\n return {};\n }\n\n const model = strapi.getModel(uid);\n\n if (!model) {\n return {};\n }\n\n return Object.keys(model.attributes).reduce(\n (populateAcc, attributeName: string) =>\n merge(\n populateAcc,\n getPopulateFor(\n attributeName,\n model,\n {\n // @ts-expect-error - improve types\n initialPopulate: initialPopulate?.[attributeName],\n countMany,\n countOne,\n maxLevel,\n },\n level\n )\n ),\n {}\n );\n};\n\n/**\n * Deeply populate a model based on UID. Only populating fields that require validation.\n * @param uid - Unique identifier of the model\n * @param options - Options to apply while populating\n * @param level - Current level of nested call\n */\nconst validationPopulateCache = new Map<string, Record<string, any>>();\n\nconst getPopulateForValidation = (uid: UID.Schema): Record<string, any> => {\n const cached = validationPopulateCache.get(uid);\n if (cached) {\n return cached;\n }\n\n const model = strapi.getModel(uid);\n if (!model) {\n return {};\n }\n\n const result = Object.entries(model.attributes).reduce(\n (populateAcc: any, [attributeName, attribute]) => {\n if (isScalarAttribute(attribute)) {\n // If the scalar attribute requires validation, add it to the fields array\n if (getDoesAttributeRequireValidation(attribute)) {\n populateAcc.fields = populateAcc.fields || [];\n populateAcc.fields.push(attributeName);\n }\n return populateAcc;\n }\n\n if (isMedia(attribute)) {\n if (getDoesAttributeRequireValidation(attribute)) {\n populateAcc.populate = populateAcc.populate || {};\n populateAcc.populate[attributeName] = {\n populate: {\n folder: true,\n },\n };\n return populateAcc;\n }\n }\n\n if (isComponent(attribute)) {\n // @ts-expect-error - should be a component\n const component = attribute.component;\n\n // Get the validation result for this component\n const componentResult = getPopulateForValidation(component);\n\n if (Object.keys(componentResult).length > 0) {\n populateAcc.populate = populateAcc.populate || {};\n populateAcc.populate[attributeName] = componentResult;\n }\n\n return populateAcc;\n }\n\n if (isDynamicZone(attribute)) {\n const components = (attribute as Schema.Attribute.DynamicZone).components;\n // Handle dynamic zone components\n const componentsResult = (components || []).reduce(\n (acc, componentUID) => {\n // Get validation populate for this component\n const componentResult = getPopulateForValidation(componentUID);\n\n // Only include component if it has fields requiring validation\n if (Object.keys(componentResult).length > 0) {\n acc[componentUID] = componentResult;\n }\n\n return acc;\n },\n {} as Record<string, any>\n );\n\n // Only add to populate if we have components requiring validation\n if (Object.keys(componentsResult).length > 0) {\n populateAcc.populate = populateAcc.populate || {};\n populateAcc.populate[attributeName] = { on: componentsResult };\n }\n }\n\n return populateAcc;\n },\n {}\n );\n\n validationPopulateCache.set(uid, result);\n return result;\n};\n\n/**\n * getDeepPopulateDraftCount works recursively on the attributes of a model\n * creating a populated object to count all the unpublished relations within the model\n * These relations can be direct to this content type or contained within components/dynamic zones\n * @param uid of the model\n * @returns result\n * @returns result.populate\n * @returns result.hasRelations\n */\nconst draftCountPopulateCache = new Map<string, { populate: any; hasRelations: boolean }>();\n\nconst getDeepPopulateDraftCount = (uid: UID.Schema) => {\n const cached = draftCountPopulateCache.get(uid);\n if (cached) {\n return cached;\n }\n\n const model = strapi.getModel(uid);\n if (!model) {\n return { populate: {}, hasRelations: false };\n }\n let hasRelations = false;\n\n const populate = Object.keys(model.attributes).reduce((populateAcc: any, attributeName) => {\n const attribute: Schema.Attribute.AnyAttribute = model.attributes[attributeName];\n\n switch (attribute.type) {\n case 'relation': {\n // TODO: Support polymorphic relations\n const isMorphRelation = attribute.relation.toLowerCase().startsWith('morph');\n if (isMorphRelation) {\n break;\n }\n\n // Skip relations to content types without draft & publish,\n // as they don't have a publishedAt attribute and can't have drafts\n if (!('target' in attribute)) {\n break;\n }\n\n const targetModel = strapi.getModel(attribute.target);\n if (!targetModel || !hasDraftAndPublish(targetModel)) {\n break;\n }\n\n if (isVisibleAttribute(model, attributeName)) {\n populateAcc[attributeName] = {\n count: true,\n filters: { [PUBLISHED_AT_ATTRIBUTE]: { $null: true } },\n };\n hasRelations = true;\n }\n break;\n }\n case 'component': {\n const { populate, hasRelations: childHasRelations } = getDeepPopulateDraftCount(\n attribute.component\n );\n if (childHasRelations) {\n populateAcc[attributeName] = {\n populate,\n };\n hasRelations = true;\n }\n break;\n }\n case 'dynamiczone': {\n const dzPopulateFragment = attribute.components?.reduce((acc, componentUID) => {\n const { populate: componentPopulate, hasRelations: componentHasRelations } =\n getDeepPopulateDraftCount(componentUID);\n\n if (componentHasRelations) {\n hasRelations = true;\n\n return { ...acc, [componentUID]: { populate: componentPopulate } };\n }\n\n return acc;\n }, {});\n\n if (!isEmpty(dzPopulateFragment)) {\n populateAcc[attributeName] = { on: dzPopulateFragment };\n }\n break;\n }\n default:\n }\n\n return populateAcc;\n }, {});\n\n const result = { populate, hasRelations };\n draftCountPopulateCache.set(uid, result);\n return result;\n};\n\n/**\n * Create a Strapi populate object which populates all attribute fields of a Strapi query.\n */\nconst getQueryPopulate = async (uid: UID.Schema, query: object): Promise<Populate> => {\n let populateQuery: Populate = {};\n\n await strapiUtils.traverse.traverseQueryFilters(\n /**\n *\n * @param {Object} param0\n * @param {string} param0.key - Attribute name\n * @param {Object} param0.attribute - Attribute definition\n * @param {string} param0.path - Content Type path to the attribute\n * @returns\n */\n ({ attribute, path }: any) => {\n // TODO: handle dynamic zones and morph relations\n if (!attribute || isDynamicZone(attribute) || isMorphToRelation(attribute)) {\n return;\n }\n\n // Populate all relations, components and media\n if (isRelation(attribute) || isMedia(attribute) || isComponent(attribute)) {\n const populatePath = path.attribute.replace(/\\./g, '.populate.');\n // @ts-expect-error - lodash doesn't resolve the Populate type correctly\n populateQuery = set(populatePath, {}, populateQuery);\n }\n },\n { schema: strapi.getModel(uid), getModel: strapi.getModel.bind(strapi) },\n query\n );\n\n return populateQuery;\n};\n\nconst deepPopulateCache = new Map<string, object>();\n\nconst buildDeepPopulate = async (uid: UID.CollectionType) => {\n const cached = deepPopulateCache.get(uid);\n if (cached) {\n return cached;\n }\n\n const result = await getService('populate-builder')(uid)\n .populateDeep(Infinity)\n .countRelations()\n .build();\n\n deepPopulateCache.set(uid, result);\n\n return result;\n};\n\n/**\n * Restrict localizations populate to only metadata fields for localized content types.\n * Returns an empty object for non-localized content types.\n *\n * By default, localizations are deeply populated which includes all relations and\n * components for every locale — this is expensive and unnecessary for CM responses.\n * The CM only needs these fields from localizations:\n * - locale: to identify which locales exist\n * - documentId: to link to the localized document\n * - publishedAt: to determine published/draft status\n * - updatedAt: to support the modified state indicator in the UI\n */\nconst getPopulateForLocalizations = (model: UID.Schema) => {\n const modelSchema = strapi.getModel(model);\n if (\n (modelSchema as unknown as { pluginOptions: { i18n: { localized?: boolean } } }).pluginOptions\n ?.i18n?.localized\n ) {\n return { localizations: { fields: ['locale', 'documentId', 'publishedAt', 'updatedAt'] } };\n }\n\n return {};\n};\n\nexport {\n getDeepPopulate,\n getDeepPopulateDraftCount,\n getPopulateForValidation,\n getQueryPopulate,\n buildDeepPopulate,\n getPopulateForLocalizations,\n};\n"],"names":["isVisibleAttribute","isScalarAttribute","getDoesAttributeRequireValidation","hasDraftAndPublish","strapiUtils","contentTypes","isAnyToMany","relations","PUBLISHED_AT_ATTRIBUTE","constants","isMorphToRelation","attribute","isRelation","relation","includes","isMedia","propEq","isComponent","isDynamicZone","getPopulateForRelation","model","attributeName","countMany","countOne","initialPopulate","isManyRelation","undefined","validationPopulate","getPopulateForValidation","uid","populate","count","getPopulateForDZ","options","level","populatedComponents","components","reduce","acc","componentUID","getDeepPopulate","on","getPopulateFor","attributes","type","component","folder","maxLevel","Infinity","strapi","getModel","Object","keys","populateAcc","merge","validationPopulateCache","Map","cached","get","result","entries","fields","push","componentResult","length","componentsResult","set","draftCountPopulateCache","getDeepPopulateDraftCount","hasRelations","isMorphRelation","toLowerCase","startsWith","targetModel","target","filters","$null","childHasRelations","dzPopulateFragment","componentPopulate","componentHasRelations","isEmpty","getQueryPopulate","query","populateQuery","traverse","traverseQueryFilters","path","populatePath","replace","schema","bind","deepPopulateCache","buildDeepPopulate","getService","populateDeep","countRelations","build","getPopulateForLocalizations","modelSchema","pluginOptions","i18n","localized","localizations"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"populate.js","sources":["../../../../server/src/services/utils/populate.ts"],"sourcesContent":["import { merge, isEmpty, set, propEq } from 'lodash/fp';\nimport strapiUtils from '@strapi/utils';\nimport type { UID, Schema, Modules } from '@strapi/types';\nimport { getService } from '../../utils';\n\nconst {\n isVisibleAttribute,\n isScalarAttribute,\n getDoesAttributeRequireValidation,\n isPrivateAttribute,\n hasDraftAndPublish,\n} = strapiUtils.contentTypes;\nconst { isAnyToMany } = strapiUtils.relations;\nconst { PUBLISHED_AT_ATTRIBUTE } = strapiUtils.contentTypes.constants;\n\nconst isMorphToRelation = (attribute: any) =>\n isRelation(attribute) && attribute.relation.includes('morphTo');\nconst isMedia = propEq('type', 'media');\nconst isRelation = propEq('type', 'relation');\nconst isComponent = propEq('type', 'component');\nconst isDynamicZone = propEq('type', 'dynamiczone');\n\n// TODO: Import from @strapi/types when it's available there\ntype Model = Parameters<typeof isVisibleAttribute>[0];\nexport type Populate = Modules.EntityService.Params.Populate.Any<UID.Schema>;\n\ntype PopulateOptions = {\n initialPopulate?: Populate;\n countMany?: boolean;\n countOne?: boolean;\n maxLevel?: number;\n};\n\n/**\n * Populate the model for relation\n * @param attribute - Attribute containing a relation\n * @param attribute.relation - type of relation\n * @param model - Model of the populated entity\n * @param attributeName\n * @param options - Options to apply while populating\n */\nfunction getPopulateForRelation(\n attribute: Schema.Attribute.AnyAttribute,\n model: Model,\n attributeName: string,\n { countMany, countOne, initialPopulate }: PopulateOptions\n) {\n const isManyRelation = isAnyToMany(attribute);\n\n // Use initialPopulate when explicitly provided (including `false` to suppress population)\n if (initialPopulate !== undefined) {\n return initialPopulate;\n }\n\n // If populating localizations attribute, also include validatable fields\n // Mainly needed for bulk locale publishing, so the Client has all the information necessary to perform validations\n if (attributeName === 'localizations') {\n const validationPopulate = getPopulateForValidation(model.uid as UID.Schema);\n\n return {\n populate: validationPopulate.populate,\n };\n }\n\n // always populate createdBy, updatedBy, localizations etc.\n if (!isVisibleAttribute(model, attributeName)) {\n return true;\n }\n\n if ((isManyRelation && countMany) || (!isManyRelation && countOne)) {\n return { count: true };\n }\n\n return true;\n}\n\n/**\n * Populate the model for Dynamic Zone components\n * @param attribute - Attribute containing the components\n * @param attribute.components - IDs of components\n * @param options - Options to apply while populating\n */\nfunction getPopulateForDZ(\n attribute: Schema.Attribute.DynamicZone,\n options: PopulateOptions,\n level: number\n) {\n // Use fragments to populate the dynamic zone components\n const populatedComponents = (attribute.components || []).reduce(\n (acc: any, componentUID: UID.Component) => ({\n ...acc,\n [componentUID]: {\n populate: getDeepPopulate(componentUID, options, level + 1),\n },\n }),\n {}\n );\n\n return { on: populatedComponents };\n}\n\n/**\n * Get the populated value based on the type of the attribute\n * @param attributeName - Name of the attribute\n * @param model - Model of the populated entity\n * @param model.attributes\n * @param options - Options to apply while populating\n * @param options.countMany\n * @param options.countOne\n * @param options.maxLevel\n * @param level\n */\nfunction getPopulateFor(\n attributeName: string,\n model: any,\n options: PopulateOptions,\n level: number\n): { [key: string]: boolean | object } {\n const attribute = model.attributes[attributeName];\n\n switch (attribute.type) {\n case 'relation':\n // @ts-expect-error - TODO: support populate count typing\n return {\n [attributeName]: getPopulateForRelation(attribute, model, attributeName, options),\n };\n case 'component':\n return {\n [attributeName]: {\n populate: getDeepPopulate(attribute.component, options, level + 1),\n },\n };\n case 'media':\n return {\n [attributeName]: {\n populate: {\n folder: true,\n },\n },\n };\n case 'dynamiczone':\n return {\n [attributeName]: getPopulateForDZ(attribute, options, level),\n };\n default:\n return {};\n }\n}\n\n/**\n * Deeply populate a model based on UID\n * @param uid - Unique identifier of the model\n * @param options - Options to apply while populating\n * @param level - Current level of nested call\n */\nconst getDeepPopulate = (\n uid: UID.Schema,\n {\n initialPopulate = {} as any,\n countMany = false,\n countOne = false,\n maxLevel = Infinity,\n }: PopulateOptions = {},\n level = 1\n) => {\n if (level > maxLevel) {\n return {};\n }\n\n const model = strapi.getModel(uid);\n\n if (!model) {\n return {};\n }\n\n return Object.keys(model.attributes).reduce(\n (populateAcc, attributeName: string) =>\n merge(\n populateAcc,\n getPopulateFor(\n attributeName,\n model,\n {\n // @ts-expect-error - improve types\n initialPopulate: initialPopulate?.[attributeName],\n countMany,\n countOne,\n maxLevel,\n },\n level\n )\n ),\n {}\n );\n};\n\n/**\n * Deeply populate a model based on UID. Only populating fields that require validation.\n * @param uid - Unique identifier of the model\n * @param options - Options to apply while populating\n * @param level - Current level of nested call\n */\nconst validationPopulateCache = new Map<string, Record<string, any>>();\n\nconst getPopulateForValidation = (uid: UID.Schema): Record<string, any> => {\n const cached = validationPopulateCache.get(uid);\n if (cached) {\n return cached;\n }\n\n const model = strapi.getModel(uid);\n if (!model) {\n return {};\n }\n\n const result = Object.entries(model.attributes).reduce(\n (populateAcc: any, [attributeName, attribute]) => {\n if (isScalarAttribute(attribute)) {\n // If the scalar attribute requires validation, add it to the fields array\n if (\n getDoesAttributeRequireValidation(attribute) &&\n !isPrivateAttribute(model, attributeName)\n ) {\n populateAcc.fields = populateAcc.fields || [];\n populateAcc.fields.push(attributeName);\n }\n return populateAcc;\n }\n\n if (isMedia(attribute)) {\n if (\n getDoesAttributeRequireValidation(attribute) &&\n !isPrivateAttribute(model, attributeName)\n ) {\n populateAcc.populate = populateAcc.populate || {};\n populateAcc.populate[attributeName] = {\n populate: {\n folder: true,\n },\n };\n return populateAcc;\n }\n }\n\n if (isComponent(attribute)) {\n // @ts-expect-error - should be a component\n const component = attribute.component;\n\n // Get the validation result for this component\n const componentResult = getPopulateForValidation(component);\n\n if (Object.keys(componentResult).length > 0) {\n populateAcc.populate = populateAcc.populate || {};\n populateAcc.populate[attributeName] = componentResult;\n }\n\n return populateAcc;\n }\n\n if (isDynamicZone(attribute)) {\n const components = (attribute as Schema.Attribute.DynamicZone).components;\n // Handle dynamic zone components\n const componentsResult = (components || []).reduce(\n (acc, componentUID) => {\n // Get validation populate for this component\n const componentResult = getPopulateForValidation(componentUID);\n\n // Only include component if it has fields requiring validation\n if (Object.keys(componentResult).length > 0) {\n acc[componentUID] = componentResult;\n }\n\n return acc;\n },\n {} as Record<string, any>\n );\n\n // Only add to populate if we have components requiring validation\n if (Object.keys(componentsResult).length > 0) {\n populateAcc.populate = populateAcc.populate || {};\n populateAcc.populate[attributeName] = { on: componentsResult };\n }\n }\n\n return populateAcc;\n },\n {}\n );\n\n validationPopulateCache.set(uid, result);\n return result;\n};\n\n/**\n * getDeepPopulateDraftCount works recursively on the attributes of a model\n * creating a populated object to count all the unpublished relations within the model\n * These relations can be direct to this content type or contained within components/dynamic zones\n * @param uid of the model\n * @returns result\n * @returns result.populate\n * @returns result.hasRelations\n */\nconst draftCountPopulateCache = new Map<string, { populate: any; hasRelations: boolean }>();\n\nconst getDeepPopulateDraftCount = (uid: UID.Schema) => {\n const cached = draftCountPopulateCache.get(uid);\n if (cached) {\n return cached;\n }\n\n const model = strapi.getModel(uid);\n if (!model) {\n return { populate: {}, hasRelations: false };\n }\n let hasRelations = false;\n\n const populate = Object.keys(model.attributes).reduce((populateAcc: any, attributeName) => {\n const attribute: Schema.Attribute.AnyAttribute = model.attributes[attributeName];\n\n switch (attribute.type) {\n case 'relation': {\n // TODO: Support polymorphic relations\n const isMorphRelation = attribute.relation.toLowerCase().startsWith('morph');\n if (isMorphRelation) {\n break;\n }\n\n // Skip relations to content types without draft & publish,\n // as they don't have a publishedAt attribute and can't have drafts\n if (!('target' in attribute)) {\n break;\n }\n\n const targetModel = strapi.getModel(attribute.target);\n if (!targetModel || !hasDraftAndPublish(targetModel)) {\n break;\n }\n\n if (isVisibleAttribute(model, attributeName)) {\n populateAcc[attributeName] = {\n count: true,\n filters: { [PUBLISHED_AT_ATTRIBUTE]: { $null: true } },\n };\n hasRelations = true;\n }\n break;\n }\n case 'component': {\n const { populate, hasRelations: childHasRelations } = getDeepPopulateDraftCount(\n attribute.component\n );\n if (childHasRelations) {\n populateAcc[attributeName] = {\n populate,\n };\n hasRelations = true;\n }\n break;\n }\n case 'dynamiczone': {\n const dzPopulateFragment = attribute.components?.reduce((acc, componentUID) => {\n const { populate: componentPopulate, hasRelations: componentHasRelations } =\n getDeepPopulateDraftCount(componentUID);\n\n if (componentHasRelations) {\n hasRelations = true;\n\n return { ...acc, [componentUID]: { populate: componentPopulate } };\n }\n\n return acc;\n }, {});\n\n if (!isEmpty(dzPopulateFragment)) {\n populateAcc[attributeName] = { on: dzPopulateFragment };\n }\n break;\n }\n default:\n }\n\n return populateAcc;\n }, {});\n\n const result = { populate, hasRelations };\n draftCountPopulateCache.set(uid, result);\n return result;\n};\n\n/**\n * Create a Strapi populate object which populates all attribute fields of a Strapi query.\n */\nconst getQueryPopulate = async (uid: UID.Schema, query: object): Promise<Populate> => {\n let populateQuery: Populate = {};\n\n await strapiUtils.traverse.traverseQueryFilters(\n /**\n *\n * @param {Object} param0\n * @param {string} param0.key - Attribute name\n * @param {Object} param0.attribute - Attribute definition\n * @param {string} param0.path - Content Type path to the attribute\n * @returns\n */\n ({ attribute, path }: any) => {\n // TODO: handle dynamic zones and morph relations\n if (!attribute || isDynamicZone(attribute) || isMorphToRelation(attribute)) {\n return;\n }\n\n // Populate all relations, components and media\n if (isRelation(attribute) || isMedia(attribute) || isComponent(attribute)) {\n const populatePath = path.attribute.replace(/\\./g, '.populate.');\n // @ts-expect-error - lodash doesn't resolve the Populate type correctly\n populateQuery = set(populatePath, {}, populateQuery);\n }\n },\n { schema: strapi.getModel(uid), getModel: strapi.getModel.bind(strapi) },\n query\n );\n\n return populateQuery;\n};\n\nconst deepPopulateCache = new Map<string, object>();\n\nconst buildDeepPopulate = async (uid: UID.CollectionType) => {\n const cached = deepPopulateCache.get(uid);\n if (cached) {\n return cached;\n }\n\n const result = await getService('populate-builder')(uid)\n .populateDeep(Infinity)\n .countRelations()\n .build();\n\n deepPopulateCache.set(uid, result);\n\n return result;\n};\n\n/**\n * Restrict localizations populate to only metadata fields for localized content types.\n * Returns an empty object for non-localized content types.\n *\n * By default, localizations are deeply populated which includes all relations and\n * components for every locale — this is expensive and unnecessary for CM responses.\n * The CM only needs these fields from localizations:\n * - locale: to identify which locales exist\n * - documentId: to link to the localized document\n * - publishedAt: to determine published/draft status\n * - updatedAt: to support the modified state indicator in the UI\n */\nconst getPopulateForLocalizations = (model: UID.Schema) => {\n const modelSchema = strapi.getModel(model);\n if (\n (modelSchema as unknown as { pluginOptions: { i18n: { localized?: boolean } } }).pluginOptions\n ?.i18n?.localized\n ) {\n return { localizations: { fields: ['locale', 'documentId', 'publishedAt', 'updatedAt'] } };\n }\n\n return {};\n};\n\nexport {\n getDeepPopulate,\n getDeepPopulateDraftCount,\n getPopulateForValidation,\n getQueryPopulate,\n buildDeepPopulate,\n getPopulateForLocalizations,\n};\n"],"names":["isVisibleAttribute","isScalarAttribute","getDoesAttributeRequireValidation","isPrivateAttribute","hasDraftAndPublish","strapiUtils","contentTypes","isAnyToMany","relations","PUBLISHED_AT_ATTRIBUTE","constants","isMorphToRelation","attribute","isRelation","relation","includes","isMedia","propEq","isComponent","isDynamicZone","getPopulateForRelation","model","attributeName","countMany","countOne","initialPopulate","isManyRelation","undefined","validationPopulate","getPopulateForValidation","uid","populate","count","getPopulateForDZ","options","level","populatedComponents","components","reduce","acc","componentUID","getDeepPopulate","on","getPopulateFor","attributes","type","component","folder","maxLevel","Infinity","strapi","getModel","Object","keys","populateAcc","merge","validationPopulateCache","Map","cached","get","result","entries","fields","push","componentResult","length","componentsResult","set","draftCountPopulateCache","getDeepPopulateDraftCount","hasRelations","isMorphRelation","toLowerCase","startsWith","targetModel","target","filters","$null","childHasRelations","dzPopulateFragment","componentPopulate","componentHasRelations","isEmpty","getQueryPopulate","query","populateQuery","traverse","traverseQueryFilters","path","populatePath","replace","schema","bind","deepPopulateCache","buildDeepPopulate","getService","populateDeep","countRelations","build","getPopulateForLocalizations","modelSchema","pluginOptions","i18n","localized","localizations"],"mappings":"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"}
|
|
@@ -2,7 +2,7 @@ import { propEq, isEmpty, merge, set } from 'lodash/fp';
|
|
|
2
2
|
import strapiUtils from '@strapi/utils';
|
|
3
3
|
import { getService } from '../../utils/index.mjs';
|
|
4
4
|
|
|
5
|
-
const { isVisibleAttribute, isScalarAttribute, getDoesAttributeRequireValidation, hasDraftAndPublish } = strapiUtils.contentTypes;
|
|
5
|
+
const { isVisibleAttribute, isScalarAttribute, getDoesAttributeRequireValidation, isPrivateAttribute, hasDraftAndPublish } = strapiUtils.contentTypes;
|
|
6
6
|
const { isAnyToMany } = strapiUtils.relations;
|
|
7
7
|
const { PUBLISHED_AT_ATTRIBUTE } = strapiUtils.contentTypes.constants;
|
|
8
8
|
const isMorphToRelation = (attribute)=>isRelation(attribute) && attribute.relation.includes('morphTo');
|
|
@@ -138,14 +138,14 @@ const getPopulateForValidation = (uid)=>{
|
|
|
138
138
|
const result = Object.entries(model.attributes).reduce((populateAcc, [attributeName, attribute])=>{
|
|
139
139
|
if (isScalarAttribute(attribute)) {
|
|
140
140
|
// If the scalar attribute requires validation, add it to the fields array
|
|
141
|
-
if (getDoesAttributeRequireValidation(attribute)) {
|
|
141
|
+
if (getDoesAttributeRequireValidation(attribute) && !isPrivateAttribute(model, attributeName)) {
|
|
142
142
|
populateAcc.fields = populateAcc.fields || [];
|
|
143
143
|
populateAcc.fields.push(attributeName);
|
|
144
144
|
}
|
|
145
145
|
return populateAcc;
|
|
146
146
|
}
|
|
147
147
|
if (isMedia(attribute)) {
|
|
148
|
-
if (getDoesAttributeRequireValidation(attribute)) {
|
|
148
|
+
if (getDoesAttributeRequireValidation(attribute) && !isPrivateAttribute(model, attributeName)) {
|
|
149
149
|
populateAcc.populate = populateAcc.populate || {};
|
|
150
150
|
populateAcc.populate[attributeName] = {
|
|
151
151
|
populate: {
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"populate.mjs","sources":["../../../../server/src/services/utils/populate.ts"],"sourcesContent":["import { merge, isEmpty, set, propEq } from 'lodash/fp';\nimport strapiUtils from '@strapi/utils';\nimport type { UID, Schema, Modules } from '@strapi/types';\nimport { getService } from '../../utils';\n\nconst {\n isVisibleAttribute,\n isScalarAttribute,\n getDoesAttributeRequireValidation,\n hasDraftAndPublish,\n} = strapiUtils.contentTypes;\nconst { isAnyToMany } = strapiUtils.relations;\nconst { PUBLISHED_AT_ATTRIBUTE } = strapiUtils.contentTypes.constants;\n\nconst isMorphToRelation = (attribute: any) =>\n isRelation(attribute) && attribute.relation.includes('morphTo');\nconst isMedia = propEq('type', 'media');\nconst isRelation = propEq('type', 'relation');\nconst isComponent = propEq('type', 'component');\nconst isDynamicZone = propEq('type', 'dynamiczone');\n\n// TODO: Import from @strapi/types when it's available there\ntype Model = Parameters<typeof isVisibleAttribute>[0];\nexport type Populate = Modules.EntityService.Params.Populate.Any<UID.Schema>;\n\ntype PopulateOptions = {\n initialPopulate?: Populate;\n countMany?: boolean;\n countOne?: boolean;\n maxLevel?: number;\n};\n\n/**\n * Populate the model for relation\n * @param attribute - Attribute containing a relation\n * @param attribute.relation - type of relation\n * @param model - Model of the populated entity\n * @param attributeName\n * @param options - Options to apply while populating\n */\nfunction getPopulateForRelation(\n attribute: Schema.Attribute.AnyAttribute,\n model: Model,\n attributeName: string,\n { countMany, countOne, initialPopulate }: PopulateOptions\n) {\n const isManyRelation = isAnyToMany(attribute);\n\n // Use initialPopulate when explicitly provided (including `false` to suppress population)\n if (initialPopulate !== undefined) {\n return initialPopulate;\n }\n\n // If populating localizations attribute, also include validatable fields\n // Mainly needed for bulk locale publishing, so the Client has all the information necessary to perform validations\n if (attributeName === 'localizations') {\n const validationPopulate = getPopulateForValidation(model.uid as UID.Schema);\n\n return {\n populate: validationPopulate.populate,\n };\n }\n\n // always populate createdBy, updatedBy, localizations etc.\n if (!isVisibleAttribute(model, attributeName)) {\n return true;\n }\n\n if ((isManyRelation && countMany) || (!isManyRelation && countOne)) {\n return { count: true };\n }\n\n return true;\n}\n\n/**\n * Populate the model for Dynamic Zone components\n * @param attribute - Attribute containing the components\n * @param attribute.components - IDs of components\n * @param options - Options to apply while populating\n */\nfunction getPopulateForDZ(\n attribute: Schema.Attribute.DynamicZone,\n options: PopulateOptions,\n level: number\n) {\n // Use fragments to populate the dynamic zone components\n const populatedComponents = (attribute.components || []).reduce(\n (acc: any, componentUID: UID.Component) => ({\n ...acc,\n [componentUID]: {\n populate: getDeepPopulate(componentUID, options, level + 1),\n },\n }),\n {}\n );\n\n return { on: populatedComponents };\n}\n\n/**\n * Get the populated value based on the type of the attribute\n * @param attributeName - Name of the attribute\n * @param model - Model of the populated entity\n * @param model.attributes\n * @param options - Options to apply while populating\n * @param options.countMany\n * @param options.countOne\n * @param options.maxLevel\n * @param level\n */\nfunction getPopulateFor(\n attributeName: string,\n model: any,\n options: PopulateOptions,\n level: number\n): { [key: string]: boolean | object } {\n const attribute = model.attributes[attributeName];\n\n switch (attribute.type) {\n case 'relation':\n // @ts-expect-error - TODO: support populate count typing\n return {\n [attributeName]: getPopulateForRelation(attribute, model, attributeName, options),\n };\n case 'component':\n return {\n [attributeName]: {\n populate: getDeepPopulate(attribute.component, options, level + 1),\n },\n };\n case 'media':\n return {\n [attributeName]: {\n populate: {\n folder: true,\n },\n },\n };\n case 'dynamiczone':\n return {\n [attributeName]: getPopulateForDZ(attribute, options, level),\n };\n default:\n return {};\n }\n}\n\n/**\n * Deeply populate a model based on UID\n * @param uid - Unique identifier of the model\n * @param options - Options to apply while populating\n * @param level - Current level of nested call\n */\nconst getDeepPopulate = (\n uid: UID.Schema,\n {\n initialPopulate = {} as any,\n countMany = false,\n countOne = false,\n maxLevel = Infinity,\n }: PopulateOptions = {},\n level = 1\n) => {\n if (level > maxLevel) {\n return {};\n }\n\n const model = strapi.getModel(uid);\n\n if (!model) {\n return {};\n }\n\n return Object.keys(model.attributes).reduce(\n (populateAcc, attributeName: string) =>\n merge(\n populateAcc,\n getPopulateFor(\n attributeName,\n model,\n {\n // @ts-expect-error - improve types\n initialPopulate: initialPopulate?.[attributeName],\n countMany,\n countOne,\n maxLevel,\n },\n level\n )\n ),\n {}\n );\n};\n\n/**\n * Deeply populate a model based on UID. Only populating fields that require validation.\n * @param uid - Unique identifier of the model\n * @param options - Options to apply while populating\n * @param level - Current level of nested call\n */\nconst validationPopulateCache = new Map<string, Record<string, any>>();\n\nconst getPopulateForValidation = (uid: UID.Schema): Record<string, any> => {\n const cached = validationPopulateCache.get(uid);\n if (cached) {\n return cached;\n }\n\n const model = strapi.getModel(uid);\n if (!model) {\n return {};\n }\n\n const result = Object.entries(model.attributes).reduce(\n (populateAcc: any, [attributeName, attribute]) => {\n if (isScalarAttribute(attribute)) {\n // If the scalar attribute requires validation, add it to the fields array\n if (getDoesAttributeRequireValidation(attribute)) {\n populateAcc.fields = populateAcc.fields || [];\n populateAcc.fields.push(attributeName);\n }\n return populateAcc;\n }\n\n if (isMedia(attribute)) {\n if (getDoesAttributeRequireValidation(attribute)) {\n populateAcc.populate = populateAcc.populate || {};\n populateAcc.populate[attributeName] = {\n populate: {\n folder: true,\n },\n };\n return populateAcc;\n }\n }\n\n if (isComponent(attribute)) {\n // @ts-expect-error - should be a component\n const component = attribute.component;\n\n // Get the validation result for this component\n const componentResult = getPopulateForValidation(component);\n\n if (Object.keys(componentResult).length > 0) {\n populateAcc.populate = populateAcc.populate || {};\n populateAcc.populate[attributeName] = componentResult;\n }\n\n return populateAcc;\n }\n\n if (isDynamicZone(attribute)) {\n const components = (attribute as Schema.Attribute.DynamicZone).components;\n // Handle dynamic zone components\n const componentsResult = (components || []).reduce(\n (acc, componentUID) => {\n // Get validation populate for this component\n const componentResult = getPopulateForValidation(componentUID);\n\n // Only include component if it has fields requiring validation\n if (Object.keys(componentResult).length > 0) {\n acc[componentUID] = componentResult;\n }\n\n return acc;\n },\n {} as Record<string, any>\n );\n\n // Only add to populate if we have components requiring validation\n if (Object.keys(componentsResult).length > 0) {\n populateAcc.populate = populateAcc.populate || {};\n populateAcc.populate[attributeName] = { on: componentsResult };\n }\n }\n\n return populateAcc;\n },\n {}\n );\n\n validationPopulateCache.set(uid, result);\n return result;\n};\n\n/**\n * getDeepPopulateDraftCount works recursively on the attributes of a model\n * creating a populated object to count all the unpublished relations within the model\n * These relations can be direct to this content type or contained within components/dynamic zones\n * @param uid of the model\n * @returns result\n * @returns result.populate\n * @returns result.hasRelations\n */\nconst draftCountPopulateCache = new Map<string, { populate: any; hasRelations: boolean }>();\n\nconst getDeepPopulateDraftCount = (uid: UID.Schema) => {\n const cached = draftCountPopulateCache.get(uid);\n if (cached) {\n return cached;\n }\n\n const model = strapi.getModel(uid);\n if (!model) {\n return { populate: {}, hasRelations: false };\n }\n let hasRelations = false;\n\n const populate = Object.keys(model.attributes).reduce((populateAcc: any, attributeName) => {\n const attribute: Schema.Attribute.AnyAttribute = model.attributes[attributeName];\n\n switch (attribute.type) {\n case 'relation': {\n // TODO: Support polymorphic relations\n const isMorphRelation = attribute.relation.toLowerCase().startsWith('morph');\n if (isMorphRelation) {\n break;\n }\n\n // Skip relations to content types without draft & publish,\n // as they don't have a publishedAt attribute and can't have drafts\n if (!('target' in attribute)) {\n break;\n }\n\n const targetModel = strapi.getModel(attribute.target);\n if (!targetModel || !hasDraftAndPublish(targetModel)) {\n break;\n }\n\n if (isVisibleAttribute(model, attributeName)) {\n populateAcc[attributeName] = {\n count: true,\n filters: { [PUBLISHED_AT_ATTRIBUTE]: { $null: true } },\n };\n hasRelations = true;\n }\n break;\n }\n case 'component': {\n const { populate, hasRelations: childHasRelations } = getDeepPopulateDraftCount(\n attribute.component\n );\n if (childHasRelations) {\n populateAcc[attributeName] = {\n populate,\n };\n hasRelations = true;\n }\n break;\n }\n case 'dynamiczone': {\n const dzPopulateFragment = attribute.components?.reduce((acc, componentUID) => {\n const { populate: componentPopulate, hasRelations: componentHasRelations } =\n getDeepPopulateDraftCount(componentUID);\n\n if (componentHasRelations) {\n hasRelations = true;\n\n return { ...acc, [componentUID]: { populate: componentPopulate } };\n }\n\n return acc;\n }, {});\n\n if (!isEmpty(dzPopulateFragment)) {\n populateAcc[attributeName] = { on: dzPopulateFragment };\n }\n break;\n }\n default:\n }\n\n return populateAcc;\n }, {});\n\n const result = { populate, hasRelations };\n draftCountPopulateCache.set(uid, result);\n return result;\n};\n\n/**\n * Create a Strapi populate object which populates all attribute fields of a Strapi query.\n */\nconst getQueryPopulate = async (uid: UID.Schema, query: object): Promise<Populate> => {\n let populateQuery: Populate = {};\n\n await strapiUtils.traverse.traverseQueryFilters(\n /**\n *\n * @param {Object} param0\n * @param {string} param0.key - Attribute name\n * @param {Object} param0.attribute - Attribute definition\n * @param {string} param0.path - Content Type path to the attribute\n * @returns\n */\n ({ attribute, path }: any) => {\n // TODO: handle dynamic zones and morph relations\n if (!attribute || isDynamicZone(attribute) || isMorphToRelation(attribute)) {\n return;\n }\n\n // Populate all relations, components and media\n if (isRelation(attribute) || isMedia(attribute) || isComponent(attribute)) {\n const populatePath = path.attribute.replace(/\\./g, '.populate.');\n // @ts-expect-error - lodash doesn't resolve the Populate type correctly\n populateQuery = set(populatePath, {}, populateQuery);\n }\n },\n { schema: strapi.getModel(uid), getModel: strapi.getModel.bind(strapi) },\n query\n );\n\n return populateQuery;\n};\n\nconst deepPopulateCache = new Map<string, object>();\n\nconst buildDeepPopulate = async (uid: UID.CollectionType) => {\n const cached = deepPopulateCache.get(uid);\n if (cached) {\n return cached;\n }\n\n const result = await getService('populate-builder')(uid)\n .populateDeep(Infinity)\n .countRelations()\n .build();\n\n deepPopulateCache.set(uid, result);\n\n return result;\n};\n\n/**\n * Restrict localizations populate to only metadata fields for localized content types.\n * Returns an empty object for non-localized content types.\n *\n * By default, localizations are deeply populated which includes all relations and\n * components for every locale — this is expensive and unnecessary for CM responses.\n * The CM only needs these fields from localizations:\n * - locale: to identify which locales exist\n * - documentId: to link to the localized document\n * - publishedAt: to determine published/draft status\n * - updatedAt: to support the modified state indicator in the UI\n */\nconst getPopulateForLocalizations = (model: UID.Schema) => {\n const modelSchema = strapi.getModel(model);\n if (\n (modelSchema as unknown as { pluginOptions: { i18n: { localized?: boolean } } }).pluginOptions\n ?.i18n?.localized\n ) {\n return { localizations: { fields: ['locale', 'documentId', 'publishedAt', 'updatedAt'] } };\n }\n\n return {};\n};\n\nexport {\n getDeepPopulate,\n getDeepPopulateDraftCount,\n getPopulateForValidation,\n getQueryPopulate,\n buildDeepPopulate,\n getPopulateForLocalizations,\n};\n"],"names":["isVisibleAttribute","isScalarAttribute","getDoesAttributeRequireValidation","hasDraftAndPublish","strapiUtils","contentTypes","isAnyToMany","relations","PUBLISHED_AT_ATTRIBUTE","constants","isMorphToRelation","attribute","isRelation","relation","includes","isMedia","propEq","isComponent","isDynamicZone","getPopulateForRelation","model","attributeName","countMany","countOne","initialPopulate","isManyRelation","undefined","validationPopulate","getPopulateForValidation","uid","populate","count","getPopulateForDZ","options","level","populatedComponents","components","reduce","acc","componentUID","getDeepPopulate","on","getPopulateFor","attributes","type","component","folder","maxLevel","Infinity","strapi","getModel","Object","keys","populateAcc","merge","validationPopulateCache","Map","cached","get","result","entries","fields","push","componentResult","length","componentsResult","set","draftCountPopulateCache","getDeepPopulateDraftCount","hasRelations","isMorphRelation","toLowerCase","startsWith","targetModel","target","filters","$null","childHasRelations","dzPopulateFragment","componentPopulate","componentHasRelations","isEmpty","getQueryPopulate","query","populateQuery","traverse","traverseQueryFilters","path","populatePath","replace","schema","bind","deepPopulateCache","buildDeepPopulate","getService","populateDeep","countRelations","build","getPopulateForLocalizations","modelSchema","pluginOptions","i18n","localized","localizations"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"populate.mjs","sources":["../../../../server/src/services/utils/populate.ts"],"sourcesContent":["import { merge, isEmpty, set, propEq } from 'lodash/fp';\nimport strapiUtils from '@strapi/utils';\nimport type { UID, Schema, Modules } from '@strapi/types';\nimport { getService } from '../../utils';\n\nconst {\n isVisibleAttribute,\n isScalarAttribute,\n getDoesAttributeRequireValidation,\n isPrivateAttribute,\n hasDraftAndPublish,\n} = strapiUtils.contentTypes;\nconst { isAnyToMany } = strapiUtils.relations;\nconst { PUBLISHED_AT_ATTRIBUTE } = strapiUtils.contentTypes.constants;\n\nconst isMorphToRelation = (attribute: any) =>\n isRelation(attribute) && attribute.relation.includes('morphTo');\nconst isMedia = propEq('type', 'media');\nconst isRelation = propEq('type', 'relation');\nconst isComponent = propEq('type', 'component');\nconst isDynamicZone = propEq('type', 'dynamiczone');\n\n// TODO: Import from @strapi/types when it's available there\ntype Model = Parameters<typeof isVisibleAttribute>[0];\nexport type Populate = Modules.EntityService.Params.Populate.Any<UID.Schema>;\n\ntype PopulateOptions = {\n initialPopulate?: Populate;\n countMany?: boolean;\n countOne?: boolean;\n maxLevel?: number;\n};\n\n/**\n * Populate the model for relation\n * @param attribute - Attribute containing a relation\n * @param attribute.relation - type of relation\n * @param model - Model of the populated entity\n * @param attributeName\n * @param options - Options to apply while populating\n */\nfunction getPopulateForRelation(\n attribute: Schema.Attribute.AnyAttribute,\n model: Model,\n attributeName: string,\n { countMany, countOne, initialPopulate }: PopulateOptions\n) {\n const isManyRelation = isAnyToMany(attribute);\n\n // Use initialPopulate when explicitly provided (including `false` to suppress population)\n if (initialPopulate !== undefined) {\n return initialPopulate;\n }\n\n // If populating localizations attribute, also include validatable fields\n // Mainly needed for bulk locale publishing, so the Client has all the information necessary to perform validations\n if (attributeName === 'localizations') {\n const validationPopulate = getPopulateForValidation(model.uid as UID.Schema);\n\n return {\n populate: validationPopulate.populate,\n };\n }\n\n // always populate createdBy, updatedBy, localizations etc.\n if (!isVisibleAttribute(model, attributeName)) {\n return true;\n }\n\n if ((isManyRelation && countMany) || (!isManyRelation && countOne)) {\n return { count: true };\n }\n\n return true;\n}\n\n/**\n * Populate the model for Dynamic Zone components\n * @param attribute - Attribute containing the components\n * @param attribute.components - IDs of components\n * @param options - Options to apply while populating\n */\nfunction getPopulateForDZ(\n attribute: Schema.Attribute.DynamicZone,\n options: PopulateOptions,\n level: number\n) {\n // Use fragments to populate the dynamic zone components\n const populatedComponents = (attribute.components || []).reduce(\n (acc: any, componentUID: UID.Component) => ({\n ...acc,\n [componentUID]: {\n populate: getDeepPopulate(componentUID, options, level + 1),\n },\n }),\n {}\n );\n\n return { on: populatedComponents };\n}\n\n/**\n * Get the populated value based on the type of the attribute\n * @param attributeName - Name of the attribute\n * @param model - Model of the populated entity\n * @param model.attributes\n * @param options - Options to apply while populating\n * @param options.countMany\n * @param options.countOne\n * @param options.maxLevel\n * @param level\n */\nfunction getPopulateFor(\n attributeName: string,\n model: any,\n options: PopulateOptions,\n level: number\n): { [key: string]: boolean | object } {\n const attribute = model.attributes[attributeName];\n\n switch (attribute.type) {\n case 'relation':\n // @ts-expect-error - TODO: support populate count typing\n return {\n [attributeName]: getPopulateForRelation(attribute, model, attributeName, options),\n };\n case 'component':\n return {\n [attributeName]: {\n populate: getDeepPopulate(attribute.component, options, level + 1),\n },\n };\n case 'media':\n return {\n [attributeName]: {\n populate: {\n folder: true,\n },\n },\n };\n case 'dynamiczone':\n return {\n [attributeName]: getPopulateForDZ(attribute, options, level),\n };\n default:\n return {};\n }\n}\n\n/**\n * Deeply populate a model based on UID\n * @param uid - Unique identifier of the model\n * @param options - Options to apply while populating\n * @param level - Current level of nested call\n */\nconst getDeepPopulate = (\n uid: UID.Schema,\n {\n initialPopulate = {} as any,\n countMany = false,\n countOne = false,\n maxLevel = Infinity,\n }: PopulateOptions = {},\n level = 1\n) => {\n if (level > maxLevel) {\n return {};\n }\n\n const model = strapi.getModel(uid);\n\n if (!model) {\n return {};\n }\n\n return Object.keys(model.attributes).reduce(\n (populateAcc, attributeName: string) =>\n merge(\n populateAcc,\n getPopulateFor(\n attributeName,\n model,\n {\n // @ts-expect-error - improve types\n initialPopulate: initialPopulate?.[attributeName],\n countMany,\n countOne,\n maxLevel,\n },\n level\n )\n ),\n {}\n );\n};\n\n/**\n * Deeply populate a model based on UID. Only populating fields that require validation.\n * @param uid - Unique identifier of the model\n * @param options - Options to apply while populating\n * @param level - Current level of nested call\n */\nconst validationPopulateCache = new Map<string, Record<string, any>>();\n\nconst getPopulateForValidation = (uid: UID.Schema): Record<string, any> => {\n const cached = validationPopulateCache.get(uid);\n if (cached) {\n return cached;\n }\n\n const model = strapi.getModel(uid);\n if (!model) {\n return {};\n }\n\n const result = Object.entries(model.attributes).reduce(\n (populateAcc: any, [attributeName, attribute]) => {\n if (isScalarAttribute(attribute)) {\n // If the scalar attribute requires validation, add it to the fields array\n if (\n getDoesAttributeRequireValidation(attribute) &&\n !isPrivateAttribute(model, attributeName)\n ) {\n populateAcc.fields = populateAcc.fields || [];\n populateAcc.fields.push(attributeName);\n }\n return populateAcc;\n }\n\n if (isMedia(attribute)) {\n if (\n getDoesAttributeRequireValidation(attribute) &&\n !isPrivateAttribute(model, attributeName)\n ) {\n populateAcc.populate = populateAcc.populate || {};\n populateAcc.populate[attributeName] = {\n populate: {\n folder: true,\n },\n };\n return populateAcc;\n }\n }\n\n if (isComponent(attribute)) {\n // @ts-expect-error - should be a component\n const component = attribute.component;\n\n // Get the validation result for this component\n const componentResult = getPopulateForValidation(component);\n\n if (Object.keys(componentResult).length > 0) {\n populateAcc.populate = populateAcc.populate || {};\n populateAcc.populate[attributeName] = componentResult;\n }\n\n return populateAcc;\n }\n\n if (isDynamicZone(attribute)) {\n const components = (attribute as Schema.Attribute.DynamicZone).components;\n // Handle dynamic zone components\n const componentsResult = (components || []).reduce(\n (acc, componentUID) => {\n // Get validation populate for this component\n const componentResult = getPopulateForValidation(componentUID);\n\n // Only include component if it has fields requiring validation\n if (Object.keys(componentResult).length > 0) {\n acc[componentUID] = componentResult;\n }\n\n return acc;\n },\n {} as Record<string, any>\n );\n\n // Only add to populate if we have components requiring validation\n if (Object.keys(componentsResult).length > 0) {\n populateAcc.populate = populateAcc.populate || {};\n populateAcc.populate[attributeName] = { on: componentsResult };\n }\n }\n\n return populateAcc;\n },\n {}\n );\n\n validationPopulateCache.set(uid, result);\n return result;\n};\n\n/**\n * getDeepPopulateDraftCount works recursively on the attributes of a model\n * creating a populated object to count all the unpublished relations within the model\n * These relations can be direct to this content type or contained within components/dynamic zones\n * @param uid of the model\n * @returns result\n * @returns result.populate\n * @returns result.hasRelations\n */\nconst draftCountPopulateCache = new Map<string, { populate: any; hasRelations: boolean }>();\n\nconst getDeepPopulateDraftCount = (uid: UID.Schema) => {\n const cached = draftCountPopulateCache.get(uid);\n if (cached) {\n return cached;\n }\n\n const model = strapi.getModel(uid);\n if (!model) {\n return { populate: {}, hasRelations: false };\n }\n let hasRelations = false;\n\n const populate = Object.keys(model.attributes).reduce((populateAcc: any, attributeName) => {\n const attribute: Schema.Attribute.AnyAttribute = model.attributes[attributeName];\n\n switch (attribute.type) {\n case 'relation': {\n // TODO: Support polymorphic relations\n const isMorphRelation = attribute.relation.toLowerCase().startsWith('morph');\n if (isMorphRelation) {\n break;\n }\n\n // Skip relations to content types without draft & publish,\n // as they don't have a publishedAt attribute and can't have drafts\n if (!('target' in attribute)) {\n break;\n }\n\n const targetModel = strapi.getModel(attribute.target);\n if (!targetModel || !hasDraftAndPublish(targetModel)) {\n break;\n }\n\n if (isVisibleAttribute(model, attributeName)) {\n populateAcc[attributeName] = {\n count: true,\n filters: { [PUBLISHED_AT_ATTRIBUTE]: { $null: true } },\n };\n hasRelations = true;\n }\n break;\n }\n case 'component': {\n const { populate, hasRelations: childHasRelations } = getDeepPopulateDraftCount(\n attribute.component\n );\n if (childHasRelations) {\n populateAcc[attributeName] = {\n populate,\n };\n hasRelations = true;\n }\n break;\n }\n case 'dynamiczone': {\n const dzPopulateFragment = attribute.components?.reduce((acc, componentUID) => {\n const { populate: componentPopulate, hasRelations: componentHasRelations } =\n getDeepPopulateDraftCount(componentUID);\n\n if (componentHasRelations) {\n hasRelations = true;\n\n return { ...acc, [componentUID]: { populate: componentPopulate } };\n }\n\n return acc;\n }, {});\n\n if (!isEmpty(dzPopulateFragment)) {\n populateAcc[attributeName] = { on: dzPopulateFragment };\n }\n break;\n }\n default:\n }\n\n return populateAcc;\n }, {});\n\n const result = { populate, hasRelations };\n draftCountPopulateCache.set(uid, result);\n return result;\n};\n\n/**\n * Create a Strapi populate object which populates all attribute fields of a Strapi query.\n */\nconst getQueryPopulate = async (uid: UID.Schema, query: object): Promise<Populate> => {\n let populateQuery: Populate = {};\n\n await strapiUtils.traverse.traverseQueryFilters(\n /**\n *\n * @param {Object} param0\n * @param {string} param0.key - Attribute name\n * @param {Object} param0.attribute - Attribute definition\n * @param {string} param0.path - Content Type path to the attribute\n * @returns\n */\n ({ attribute, path }: any) => {\n // TODO: handle dynamic zones and morph relations\n if (!attribute || isDynamicZone(attribute) || isMorphToRelation(attribute)) {\n return;\n }\n\n // Populate all relations, components and media\n if (isRelation(attribute) || isMedia(attribute) || isComponent(attribute)) {\n const populatePath = path.attribute.replace(/\\./g, '.populate.');\n // @ts-expect-error - lodash doesn't resolve the Populate type correctly\n populateQuery = set(populatePath, {}, populateQuery);\n }\n },\n { schema: strapi.getModel(uid), getModel: strapi.getModel.bind(strapi) },\n query\n );\n\n return populateQuery;\n};\n\nconst deepPopulateCache = new Map<string, object>();\n\nconst buildDeepPopulate = async (uid: UID.CollectionType) => {\n const cached = deepPopulateCache.get(uid);\n if (cached) {\n return cached;\n }\n\n const result = await getService('populate-builder')(uid)\n .populateDeep(Infinity)\n .countRelations()\n .build();\n\n deepPopulateCache.set(uid, result);\n\n return result;\n};\n\n/**\n * Restrict localizations populate to only metadata fields for localized content types.\n * Returns an empty object for non-localized content types.\n *\n * By default, localizations are deeply populated which includes all relations and\n * components for every locale — this is expensive and unnecessary for CM responses.\n * The CM only needs these fields from localizations:\n * - locale: to identify which locales exist\n * - documentId: to link to the localized document\n * - publishedAt: to determine published/draft status\n * - updatedAt: to support the modified state indicator in the UI\n */\nconst getPopulateForLocalizations = (model: UID.Schema) => {\n const modelSchema = strapi.getModel(model);\n if (\n (modelSchema as unknown as { pluginOptions: { i18n: { localized?: boolean } } }).pluginOptions\n ?.i18n?.localized\n ) {\n return { localizations: { fields: ['locale', 'documentId', 'publishedAt', 'updatedAt'] } };\n }\n\n return {};\n};\n\nexport {\n getDeepPopulate,\n getDeepPopulateDraftCount,\n getPopulateForValidation,\n getQueryPopulate,\n buildDeepPopulate,\n getPopulateForLocalizations,\n};\n"],"names":["isVisibleAttribute","isScalarAttribute","getDoesAttributeRequireValidation","isPrivateAttribute","hasDraftAndPublish","strapiUtils","contentTypes","isAnyToMany","relations","PUBLISHED_AT_ATTRIBUTE","constants","isMorphToRelation","attribute","isRelation","relation","includes","isMedia","propEq","isComponent","isDynamicZone","getPopulateForRelation","model","attributeName","countMany","countOne","initialPopulate","isManyRelation","undefined","validationPopulate","getPopulateForValidation","uid","populate","count","getPopulateForDZ","options","level","populatedComponents","components","reduce","acc","componentUID","getDeepPopulate","on","getPopulateFor","attributes","type","component","folder","maxLevel","Infinity","strapi","getModel","Object","keys","populateAcc","merge","validationPopulateCache","Map","cached","get","result","entries","fields","push","componentResult","length","componentsResult","set","draftCountPopulateCache","getDeepPopulateDraftCount","hasRelations","isMorphRelation","toLowerCase","startsWith","targetModel","target","filters","$null","childHasRelations","dzPopulateFragment","componentPopulate","componentHasRelations","isEmpty","getQueryPopulate","query","populateQuery","traverse","traverseQueryFilters","path","populatePath","replace","schema","bind","deepPopulateCache","buildDeepPopulate","getService","populateDeep","countRelations","build","getPopulateForLocalizations","modelSchema","pluginOptions","i18n","localized","localizations"],"mappings":"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"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"bootstrap.d.ts","sourceRoot":"","sources":["../../../server/src/bootstrap.ts"],"names":[],"mappings":";
|
|
1
|
+
{"version":3,"file":"bootstrap.d.ts","sourceRoot":"","sources":["../../../server/src/bootstrap.ts"],"names":[],"mappings":";AAMA,wBAcE"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"collection-types.d.ts","sourceRoot":"","sources":["../../../../server/src/controllers/collection-types.ts"],"names":[],"mappings":";
|
|
1
|
+
{"version":3,"file":"collection-types.d.ts","sourceRoot":"","sources":["../../../../server/src/controllers/collection-types.ts"],"names":[],"mappings":";cAoTkB,GAAG;iBAmIA,GAAG;gBA2DJ,GAAG;gBA0BH,GAAG;eAYJ,GAAG;mBA4CC,GAAG;gBAmBN,GAAG;IAoCrB;;;OAGG;iBACgB,GAAG;+BA+FW,GAAG;qBA4Bb,GAAG;uBA8CD,GAAG;mBAyCP,GAAG;iBAyDL,GAAG;oBAwCA,GAAG;6BA6CM,GAAG;wCA2CQ,GAAG;;AAvtB/C,wBAkvBE"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"homepage.d.ts","sourceRoot":"","sources":["../../../../../server/src/homepage/services/homepage.ts"],"names":[],"mappings":";AACA,OAAO,KAAK,EAAE,IAAI,EAAmB,MAAM,eAAe,CAAC;AAG3D,OAAO,KAAK,EACV,iBAAiB,EACjB,kBAAkB,EAClB,cAAc,EACf,MAAM,uCAAuC,CAAC;AAE/C,QAAA,MAAM,qBAAqB,eAAgB;IAAE,MAAM,EAAE,KAAK,MAAM,CAAA;CAAE;oCA+HxB,cAAc,EAAE,GAAG,QAAQ,cAAc,EAAE,CAAC;+CAgCxD,OAAO,MAAM,EAAE,OAAO,CAAC,wBACzB,OAAO,GAC5B,QAAQ,cAAc,EAAE,CAAC;qCAmDW,QAAQ,2BAA2B,CAAC,MAAM,CAAC,CAAC;mCAY9C,QAAQ,2BAA2B,CAAC,MAAM,CAAC,CAAC;yBAQtD,QAAQ,0BAA0B,CAAC,MAAM,CAAC,CAAC;
|
|
1
|
+
{"version":3,"file":"homepage.d.ts","sourceRoot":"","sources":["../../../../../server/src/homepage/services/homepage.ts"],"names":[],"mappings":";AACA,OAAO,KAAK,EAAE,IAAI,EAAmB,MAAM,eAAe,CAAC;AAG3D,OAAO,KAAK,EACV,iBAAiB,EACjB,kBAAkB,EAClB,cAAc,EACf,MAAM,uCAAuC,CAAC;AAE/C,QAAA,MAAM,qBAAqB,eAAgB;IAAE,MAAM,EAAE,KAAK,MAAM,CAAA;CAAE;oCA+HxB,cAAc,EAAE,GAAG,QAAQ,cAAc,EAAE,CAAC;+CAgCxD,OAAO,MAAM,EAAE,OAAO,CAAC,wBACzB,OAAO,GAC5B,QAAQ,cAAc,EAAE,CAAC;qCAmDW,QAAQ,2BAA2B,CAAC,MAAM,CAAC,CAAC;mCAY9C,QAAQ,2BAA2B,CAAC,MAAM,CAAC,CAAC;yBAQtD,QAAQ,0BAA0B,CAAC,MAAM,CAAC,CAAC;CAkEzE,CAAC;AAEF,OAAO,EAAE,qBAAqB,EAAE,CAAC"}
|
|
@@ -284,19 +284,19 @@ declare const _default: () => {
|
|
|
284
284
|
strapi: import("@strapi/types/dist/core").Strapi;
|
|
285
285
|
}) => {
|
|
286
286
|
create: ({ userAbility, model }: {
|
|
287
|
-
userAbility: any
|
|
287
|
+
userAbility: import("@casl/ability").Ability<import("@casl/ability").AbilityTuple, any>;
|
|
288
288
|
model: string;
|
|
289
289
|
}) => {
|
|
290
290
|
can: (action: string, entity?: ({
|
|
291
291
|
id: import("@strapi/types/dist/data").ID;
|
|
292
292
|
} & {
|
|
293
293
|
[key: string]: any;
|
|
294
|
-
}) | undefined, field: string) =>
|
|
294
|
+
}) | undefined, field: string) => boolean;
|
|
295
295
|
cannot: (action: string, entity?: ({
|
|
296
296
|
id: import("@strapi/types/dist/data").ID;
|
|
297
297
|
} & {
|
|
298
298
|
[key: string]: any;
|
|
299
|
-
}) | undefined, field: string) =>
|
|
299
|
+
}) | undefined, field: string) => boolean;
|
|
300
300
|
requiresEntity: (action: string) => boolean;
|
|
301
301
|
sanitizeOutput: (data: {
|
|
302
302
|
id: import("@strapi/types/dist/data").ID;
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
import type { Core } from '@strapi/types';
|
|
2
|
+
import type { ContentManagerModelForMcp, McpToolsBuildContext, DerivedTool } from './types';
|
|
3
|
+
export type { ContentManagerModelForMcp };
|
|
4
|
+
export { slugifyUidForMcpToolName } from './utils';
|
|
5
|
+
export { buildSortSchema, buildFiltersSchema, buildDataSchema } from './schemas';
|
|
6
|
+
export { getComponentLeafPaths } from './permissions';
|
|
7
|
+
/**
|
|
8
|
+
* Builds MCP tool definitions for displayed content-manager models.
|
|
9
|
+
* Visibility is enforced separately via static auth on each tool and MCP session capability sync.
|
|
10
|
+
*/
|
|
11
|
+
export declare const deriveDisplayedContentTypeMcpToolDefinitions: (strapi: Core.Strapi, models: ContentManagerModelForMcp[], ctx?: McpToolsBuildContext) => DerivedTool[];
|
|
12
|
+
//# sourceMappingURL=derive-content-type-mcp-tools.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"derive-content-type-mcp-tools.d.ts","sourceRoot":"","sources":["../../../../server/src/mcp/derive-content-type-mcp-tools.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,IAAI,EAAgB,MAAM,eAAe,CAAC;AAIxD,OAAO,KAAK,EAAE,yBAAyB,EAAE,oBAAoB,EAAE,WAAW,EAAE,MAAM,SAAS,CAAC;AAmC5F,YAAY,EAAE,yBAAyB,EAAE,CAAC;AAC1C,OAAO,EAAE,wBAAwB,EAAE,MAAM,SAAS,CAAC;AACnD,OAAO,EAAE,eAAe,EAAE,kBAAkB,EAAE,eAAe,EAAE,MAAM,WAAW,CAAC;AACjF,OAAO,EAAE,qBAAqB,EAAE,MAAM,eAAe,CAAC;AA2dtD;;;GAGG;AACH,eAAO,MAAM,4CAA4C,WAC/C,KAAK,MAAM,UACX,yBAAyB,EAAE,QAC9B,oBAAoB,KACxB,WAAW,EAYb,CAAC"}
|
|
@@ -0,0 +1,69 @@
|
|
|
1
|
+
import type { Core, Modules, UID } from '@strapi/types';
|
|
2
|
+
type CollectionListArgs = {
|
|
3
|
+
locale?: string;
|
|
4
|
+
status?: 'draft' | 'published';
|
|
5
|
+
page?: number;
|
|
6
|
+
pageSize?: number;
|
|
7
|
+
sort?: unknown;
|
|
8
|
+
filters?: unknown;
|
|
9
|
+
};
|
|
10
|
+
/**
|
|
11
|
+
* Creates a handler for listing (paginated) documents of a collection-type.
|
|
12
|
+
* Enforces RBAC read permission and sanitizes query + output via permissionChecker.
|
|
13
|
+
*/
|
|
14
|
+
export declare const createCollectionListHandler: (uid: UID.CollectionType) => (strapi: Core.Strapi, context: Modules.MCP.McpHandlerContext) => ({ args }: {
|
|
15
|
+
args: CollectionListArgs;
|
|
16
|
+
}) => Promise<Modules.MCP.McpToolHandlerReturn>;
|
|
17
|
+
/**
|
|
18
|
+
* Creates a handler for fetching a single collection-type document by `documentId`.
|
|
19
|
+
* Enforces RBAC read permission; returns available locale metadata when the locale is missing.
|
|
20
|
+
*/
|
|
21
|
+
export declare const createCollectionGetHandler: (uid: UID.CollectionType) => (_strapi: Core.Strapi, context: Modules.MCP.McpHandlerContext) => ({ args, }: {
|
|
22
|
+
args: Record<string, unknown>;
|
|
23
|
+
}) => Promise<Modules.MCP.McpToolHandlerReturn>;
|
|
24
|
+
/**
|
|
25
|
+
* Creates a handler for creating a new collection-type document.
|
|
26
|
+
* Enforces RBAC create permission; sanitizes input and stamps creator fields.
|
|
27
|
+
*/
|
|
28
|
+
export declare const createCollectionCreateHandler: (uid: UID.CollectionType) => (strapi: Core.Strapi, context: Modules.MCP.McpHandlerContext) => ({ args, }: {
|
|
29
|
+
args: Record<string, unknown>;
|
|
30
|
+
}) => Promise<Modules.MCP.McpToolHandlerReturn>;
|
|
31
|
+
/**
|
|
32
|
+
* Creates a handler for updating an existing collection-type document draft.
|
|
33
|
+
* Creates a new locale version when the target locale does not yet exist for the document.
|
|
34
|
+
* Enforces RBAC update (or create) permission accordingly.
|
|
35
|
+
*/
|
|
36
|
+
export declare const createCollectionUpdateHandler: (uid: UID.CollectionType) => (strapi: Core.Strapi, context: Modules.MCP.McpHandlerContext) => ({ args, }: {
|
|
37
|
+
args: Record<string, unknown>;
|
|
38
|
+
}) => Promise<Modules.MCP.McpToolHandlerReturn>;
|
|
39
|
+
/**
|
|
40
|
+
* Creates a handler for deleting a collection-type document (or a specific locale).
|
|
41
|
+
* Enforces RBAC delete permission on every locale version before deletion.
|
|
42
|
+
*/
|
|
43
|
+
export declare const createCollectionDeleteHandler: (uid: UID.CollectionType) => (strapi: Core.Strapi, context: Modules.MCP.McpHandlerContext) => ({ args, }: {
|
|
44
|
+
args: Record<string, unknown>;
|
|
45
|
+
}) => Promise<Modules.MCP.McpToolHandlerReturn>;
|
|
46
|
+
/**
|
|
47
|
+
* Creates a handler for publishing a collection-type document draft.
|
|
48
|
+
* Enforces RBAC publish permission; throws NotFound when the draft or document is missing.
|
|
49
|
+
*/
|
|
50
|
+
export declare const createCollectionPublishHandler: (uid: UID.CollectionType) => (strapi: Core.Strapi, context: Modules.MCP.McpHandlerContext) => ({ args, }: {
|
|
51
|
+
args: Record<string, unknown>;
|
|
52
|
+
}) => Promise<Modules.MCP.McpToolHandlerReturn>;
|
|
53
|
+
/**
|
|
54
|
+
* Creates a handler for unpublishing a collection-type document.
|
|
55
|
+
* Optionally discards the draft in the same transaction when `discardDraft` is true.
|
|
56
|
+
* Enforces RBAC unpublish (and discard) permission.
|
|
57
|
+
*/
|
|
58
|
+
export declare const createCollectionUnpublishHandler: (uid: UID.CollectionType) => (strapi: Core.Strapi, context: Modules.MCP.McpHandlerContext) => ({ args, }: {
|
|
59
|
+
args: Record<string, unknown>;
|
|
60
|
+
}) => Promise<Modules.MCP.McpToolHandlerReturn>;
|
|
61
|
+
/**
|
|
62
|
+
* Creates a handler for discarding the draft of a collection-type document.
|
|
63
|
+
* Restores the published version as the draft. Enforces RBAC discard permission.
|
|
64
|
+
*/
|
|
65
|
+
export declare const createCollectionDiscardDraftHandler: (uid: UID.CollectionType) => (_strapi: Core.Strapi, context: Modules.MCP.McpHandlerContext) => ({ args, }: {
|
|
66
|
+
args: Record<string, unknown>;
|
|
67
|
+
}) => Promise<Modules.MCP.McpToolHandlerReturn>;
|
|
68
|
+
export {};
|
|
69
|
+
//# sourceMappingURL=collection-handlers.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"collection-handlers.d.ts","sourceRoot":"","sources":["../../../../../server/src/mcp/handlers/collection-handlers.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,IAAI,EAAE,OAAO,EAAE,GAAG,EAAE,MAAM,eAAe,CAAC;AA+BxD,KAAK,kBAAkB,GAAG;IACxB,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,MAAM,CAAC,EAAE,OAAO,GAAG,WAAW,CAAC;IAC/B,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,IAAI,CAAC,EAAE,OAAO,CAAC;IACf,OAAO,CAAC,EAAE,OAAO,CAAC;CACnB,CAAC;AA4BF;;;GAGG;AACH,eAAO,MAAM,2BAA2B,QAChC,IAAI,cAAc,cACf,KAAK,MAAM,WAAW,QAAQ,GAAG,CAAC,iBAAiB,gBAC3C;IAAE,IAAI,EAAE,kBAAkB,CAAA;CAAE,KAAG,QAAQ,QAAQ,GAAG,CAAC,oBAAoB,CA6DvF,CAAC;AAEJ;;;GAGG;AACH,eAAO,MAAM,0BAA0B,QAC/B,IAAI,cAAc,eACd,KAAK,MAAM,WAAW,QAAQ,GAAG,CAAC,iBAAiB,iBAG1D;IACD,IAAI,EAAE,OAAO,MAAM,EAAE,OAAO,CAAC,CAAC;CAC/B,KAAG,QAAQ,QAAQ,GAAG,CAAC,oBAAoB,CAyD3C,CAAC;AAEJ;;;GAGG;AACH,eAAO,MAAM,6BAA6B,QAClC,IAAI,cAAc,cACf,KAAK,MAAM,WAAW,QAAQ,GAAG,CAAC,iBAAiB,iBAGzD;IACD,IAAI,EAAE,OAAO,MAAM,EAAE,OAAO,CAAC,CAAC;CAC/B,KAAG,QAAQ,QAAQ,GAAG,CAAC,oBAAoB,CAgC3C,CAAC;AAEJ;;;;GAIG;AACH,eAAO,MAAM,6BAA6B,QAClC,IAAI,cAAc,cACf,KAAK,MAAM,WAAW,QAAQ,GAAG,CAAC,iBAAiB,iBAGzD;IACD,IAAI,EAAE,OAAO,MAAM,EAAE,OAAO,CAAC,CAAC;CAC/B,KAAG,QAAQ,QAAQ,GAAG,CAAC,oBAAoB,CA6D3C,CAAC;AAEJ;;;GAGG;AACH,eAAO,MAAM,6BAA6B,QAClC,IAAI,cAAc,cACf,KAAK,MAAM,WAAW,QAAQ,GAAG,CAAC,iBAAiB,iBAGzD;IACD,IAAI,EAAE,OAAO,MAAM,EAAE,OAAO,CAAC,CAAC;CAC/B,KAAG,QAAQ,QAAQ,GAAG,CAAC,oBAAoB,CAyC3C,CAAC;AAEJ;;;GAGG;AACH,eAAO,MAAM,8BAA8B,QACnC,IAAI,cAAc,cACf,KAAK,MAAM,WAAW,QAAQ,GAAG,CAAC,iBAAiB,iBAGzD;IACD,IAAI,EAAE,OAAO,MAAM,EAAE,OAAO,CAAC,CAAC;CAC/B,KAAG,QAAQ,QAAQ,GAAG,CAAC,oBAAoB,CA+C3C,CAAC;AAEJ;;;;GAIG;AACH,eAAO,MAAM,gCAAgC,QACrC,IAAI,cAAc,cACf,KAAK,MAAM,WAAW,QAAQ,GAAG,CAAC,iBAAiB,iBAGzD;IACD,IAAI,EAAE,OAAO,MAAM,EAAE,OAAO,CAAC,CAAC;CAC/B,KAAG,QAAQ,QAAQ,GAAG,CAAC,oBAAoB,CAoD3C,CAAC;AAEJ;;;GAGG;AACH,eAAO,MAAM,mCAAmC,QACxC,IAAI,cAAc,eACd,KAAK,MAAM,WAAW,QAAQ,GAAG,CAAC,iBAAiB,iBAG1D;IACD,IAAI,EAAE,OAAO,MAAM,EAAE,OAAO,CAAC,CAAC;CAC/B,KAAG,QAAQ,QAAQ,GAAG,CAAC,oBAAoB,CAuC3C,CAAC"}
|
|
@@ -0,0 +1,4 @@
|
|
|
1
|
+
export declare const MCP_NOT_FOUND_DOCUMENT = "Document not found.";
|
|
2
|
+
export declare const MCP_NOT_FOUND_LOCALE = "Document locale not found.";
|
|
3
|
+
export declare const MCP_NOT_FOUND_OR_PUBLISHED = "Document not found or already published.";
|
|
4
|
+
//# sourceMappingURL=constants.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"constants.d.ts","sourceRoot":"","sources":["../../../../../server/src/mcp/handlers/constants.ts"],"names":[],"mappings":"AAAA,eAAO,MAAM,sBAAsB,wBAAwB,CAAC;AAC5D,eAAO,MAAM,oBAAoB,+BAA+B,CAAC;AACjE,eAAO,MAAM,0BAA0B,6CAA6C,CAAC"}
|
|
@@ -0,0 +1,3 @@
|
|
|
1
|
+
export { createCollectionListHandler, createCollectionGetHandler, createCollectionCreateHandler, createCollectionUpdateHandler, createCollectionDeleteHandler, createCollectionPublishHandler, createCollectionUnpublishHandler, createCollectionDiscardDraftHandler, } from './collection-handlers';
|
|
2
|
+
export { singleCreateOrUpdate, createSingleGetHandler, createSingleWriteHandler, createSingleDeleteHandler, createSinglePublishHandler, createSingleUnpublishHandler, createSingleDiscardDraftHandler, } from './single-type-handlers';
|
|
3
|
+
//# sourceMappingURL=index.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../../../server/src/mcp/handlers/index.ts"],"names":[],"mappings":"AAAA,OAAO,EACL,2BAA2B,EAC3B,0BAA0B,EAC1B,6BAA6B,EAC7B,6BAA6B,EAC7B,6BAA6B,EAC7B,8BAA8B,EAC9B,gCAAgC,EAChC,mCAAmC,GACpC,MAAM,uBAAuB,CAAC;AAE/B,OAAO,EACL,oBAAoB,EACpB,sBAAsB,EACtB,wBAAwB,EACxB,yBAAyB,EACzB,0BAA0B,EAC1B,4BAA4B,EAC5B,+BAA+B,GAChC,MAAM,wBAAwB,CAAC"}
|
|
@@ -0,0 +1,66 @@
|
|
|
1
|
+
import type { Core, Modules, UID } from '@strapi/types';
|
|
2
|
+
type SingleLocaleArgs = {
|
|
3
|
+
locale?: string;
|
|
4
|
+
};
|
|
5
|
+
type SingleGetArgs = SingleLocaleArgs & {
|
|
6
|
+
status?: 'draft' | 'published';
|
|
7
|
+
};
|
|
8
|
+
type SingleUnpublishArgs = SingleLocaleArgs & {
|
|
9
|
+
discardDraft?: boolean;
|
|
10
|
+
};
|
|
11
|
+
type SingleWriteArgs = {
|
|
12
|
+
data: Record<string, unknown>;
|
|
13
|
+
locale?: string;
|
|
14
|
+
};
|
|
15
|
+
/**
|
|
16
|
+
* Core write logic shared by the single-type write handler.
|
|
17
|
+
* Creates the document when none exists; updates the existing draft otherwise.
|
|
18
|
+
* Enforces RBAC create/update permission and sanitizes input + output.
|
|
19
|
+
*/
|
|
20
|
+
export declare const singleCreateOrUpdate: (strapi: Core.Strapi, uid: UID.SingleType, context: Modules.MCP.McpHandlerContext, args: SingleWriteArgs) => Promise<Modules.MCP.McpToolHandlerReturn>;
|
|
21
|
+
/**
|
|
22
|
+
* Creates a handler for reading the single-type document.
|
|
23
|
+
* Returns available locale metadata when the requested locale version does not exist.
|
|
24
|
+
* Enforces RBAC read permission.
|
|
25
|
+
*/
|
|
26
|
+
export declare const createSingleGetHandler: (uid: UID.SingleType) => (strapi: Core.Strapi, context: Modules.MCP.McpHandlerContext) => ({ args }: {
|
|
27
|
+
args: SingleGetArgs;
|
|
28
|
+
}) => Promise<Modules.MCP.McpToolHandlerReturn>;
|
|
29
|
+
/**
|
|
30
|
+
* Creates a handler for creating or updating the single-type document.
|
|
31
|
+
* Delegates to `singleCreateOrUpdate`; enforces RBAC create/update permission.
|
|
32
|
+
*/
|
|
33
|
+
export declare const createSingleWriteHandler: (uid: UID.SingleType) => (strapi: Core.Strapi, context: Modules.MCP.McpHandlerContext) => ({ args, }: {
|
|
34
|
+
args: Record<string, unknown>;
|
|
35
|
+
}) => Promise<Modules.MCP.McpToolHandlerReturn>;
|
|
36
|
+
/**
|
|
37
|
+
* Creates a handler for deleting the single-type document (or a specific locale).
|
|
38
|
+
* Enforces RBAC delete permission on every locale version before deletion.
|
|
39
|
+
*/
|
|
40
|
+
export declare const createSingleDeleteHandler: (uid: UID.SingleType) => (strapi: Core.Strapi, context: Modules.MCP.McpHandlerContext) => ({ args }: {
|
|
41
|
+
args: SingleLocaleArgs;
|
|
42
|
+
}) => Promise<Modules.MCP.McpToolHandlerReturn>;
|
|
43
|
+
/**
|
|
44
|
+
* Creates a handler for publishing the single-type document draft.
|
|
45
|
+
* Enforces RBAC publish permission; throws NotFound when the draft is missing.
|
|
46
|
+
*/
|
|
47
|
+
export declare const createSinglePublishHandler: (uid: UID.SingleType) => (strapi: Core.Strapi, context: Modules.MCP.McpHandlerContext) => ({ args }: {
|
|
48
|
+
args: SingleLocaleArgs;
|
|
49
|
+
}) => Promise<Modules.MCP.McpToolHandlerReturn>;
|
|
50
|
+
/**
|
|
51
|
+
* Creates a handler for unpublishing the single-type document.
|
|
52
|
+
* Optionally discards the draft in the same transaction when `discardDraft` is true.
|
|
53
|
+
* Enforces RBAC unpublish (and discard) permission.
|
|
54
|
+
*/
|
|
55
|
+
export declare const createSingleUnpublishHandler: (uid: UID.SingleType) => (strapi: Core.Strapi, context: Modules.MCP.McpHandlerContext) => ({ args }: {
|
|
56
|
+
args: SingleUnpublishArgs;
|
|
57
|
+
}) => Promise<Modules.MCP.McpToolHandlerReturn>;
|
|
58
|
+
/**
|
|
59
|
+
* Creates a handler for discarding the draft of the single-type document.
|
|
60
|
+
* Restores the published version as the draft. Enforces RBAC discard permission.
|
|
61
|
+
*/
|
|
62
|
+
export declare const createSingleDiscardDraftHandler: (uid: UID.SingleType) => (_strapi: Core.Strapi, context: Modules.MCP.McpHandlerContext) => ({ args }: {
|
|
63
|
+
args: SingleLocaleArgs;
|
|
64
|
+
}) => Promise<Modules.MCP.McpToolHandlerReturn>;
|
|
65
|
+
export {};
|
|
66
|
+
//# sourceMappingURL=single-type-handlers.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"single-type-handlers.d.ts","sourceRoot":"","sources":["../../../../../server/src/mcp/handlers/single-type-handlers.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,IAAI,EAAE,OAAO,EAAE,GAAG,EAAE,MAAM,eAAe,CAAC;AA0BxD,KAAK,gBAAgB,GAAG;IAAE,MAAM,CAAC,EAAE,MAAM,CAAA;CAAE,CAAC;AAC5C,KAAK,aAAa,GAAG,gBAAgB,GAAG;IAAE,MAAM,CAAC,EAAE,OAAO,GAAG,WAAW,CAAA;CAAE,CAAC;AAC3E,KAAK,mBAAmB,GAAG,gBAAgB,GAAG;IAAE,YAAY,CAAC,EAAE,OAAO,CAAA;CAAE,CAAC;AACzE,KAAK,eAAe,GAAG;IAAE,IAAI,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;IAAC,MAAM,CAAC,EAAE,MAAM,CAAA;CAAE,CAAC;AAM1E;;;;GAIG;AACH,eAAO,MAAM,oBAAoB,WACvB,KAAK,MAAM,OACd,IAAI,UAAU,WACV,QAAQ,GAAG,CAAC,iBAAiB,QAChC,eAAe,KACpB,QAAQ,QAAQ,GAAG,CAAC,oBAAoB,CAiF1C,CAAC;AAMF;;;;GAIG;AACH,eAAO,MAAM,sBAAsB,QAC3B,IAAI,UAAU,cACX,KAAK,MAAM,WAAW,QAAQ,GAAG,CAAC,iBAAiB,gBAC3C;IAAE,IAAI,EAAE,aAAa,CAAA;CAAE,KAAG,QAAQ,QAAQ,GAAG,CAAC,oBAAoB,CAuElF,CAAC;AAEJ;;;GAGG;AACH,eAAO,MAAM,wBAAwB,QAC7B,IAAI,UAAU,cACX,KAAK,MAAM,WAAW,QAAQ,GAAG,CAAC,iBAAiB,iBAGzD;IACD,IAAI,EAAE,OAAO,MAAM,EAAE,OAAO,CAAC,CAAC;CAC/B,KAAG,QAAQ,QAAQ,GAAG,CAAC,oBAAoB,CAE3C,CAAC;AAEJ;;;GAGG;AACH,eAAO,MAAM,yBAAyB,QAC9B,IAAI,UAAU,cACX,KAAK,MAAM,WAAW,QAAQ,GAAG,CAAC,iBAAiB,gBAC3C;IAAE,IAAI,EAAE,gBAAgB,CAAA;CAAE,KAAG,QAAQ,QAAQ,GAAG,CAAC,oBAAoB,CAqDrF,CAAC;AAEJ;;;GAGG;AACH,eAAO,MAAM,0BAA0B,QAC/B,IAAI,UAAU,cACX,KAAK,MAAM,WAAW,QAAQ,GAAG,CAAC,iBAAiB,gBAC3C;IAAE,IAAI,EAAE,gBAAgB,CAAA;CAAE,KAAG,QAAQ,QAAQ,GAAG,CAAC,oBAAoB,CAgDrF,CAAC;AAEJ;;;;GAIG;AACH,eAAO,MAAM,4BAA4B,QACjC,IAAI,UAAU,cACX,KAAK,MAAM,WAAW,QAAQ,GAAG,CAAC,iBAAiB,gBAC3C;IAAE,IAAI,EAAE,mBAAmB,CAAA;CAAE,KAAG,QAAQ,QAAQ,GAAG,CAAC,oBAAoB,CAwDxF,CAAC;AAEJ;;;GAGG;AACH,eAAO,MAAM,+BAA+B,QACpC,IAAI,UAAU,eACV,KAAK,MAAM,WAAW,QAAQ,GAAG,CAAC,iBAAiB,gBAC5C;IAAE,IAAI,EAAE,gBAAgB,CAAA;CAAE,KAAG,QAAQ,QAAQ,GAAG,CAAC,oBAAoB,CA4CrF,CAAC"}
|