@webiny/api-aco 5.41.0-dbt.0 → 5.41.1-beta.0

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.
@@ -50,11 +50,11 @@ const setupAcoContext = async (context, setupAcoContextParams) => {
50
50
  });
51
51
  const folderLevelPermissions = new _FolderLevelPermissions.FolderLevelPermissions({
52
52
  getIdentity: () => security.getIdentity(),
53
- getIdentityTeam: async () => {
53
+ listIdentityTeams: async () => {
54
54
  return security.withoutAuthorization(async () => {
55
55
  const identity = security.getIdentity();
56
56
  if (!identity) {
57
- return null;
57
+ return [];
58
58
  }
59
59
  const adminUser = await context.adminUsers.getUser({
60
60
  where: {
@@ -62,16 +62,17 @@ const setupAcoContext = async (context, setupAcoContextParams) => {
62
62
  }
63
63
  });
64
64
  if (!adminUser) {
65
- return null;
65
+ return [];
66
66
  }
67
- if (!adminUser.team) {
68
- return null;
67
+ const hasTeams = adminUser.teams && adminUser.teams.length > 0;
68
+ if (hasTeams) {
69
+ return context.security.listTeams({
70
+ where: {
71
+ id_in: adminUser.teams
72
+ }
73
+ });
69
74
  }
70
- return context.security.getTeam({
71
- where: {
72
- id: adminUser.team
73
- }
74
- });
75
+ return [];
75
76
  });
76
77
  },
77
78
  listPermissions: () => security.listPermissions(),
@@ -1 +1 @@
1
- {"version":3,"names":["_error","_interopRequireDefault","require","_api","_apiHeadlessCms","_createAcoHooks","_createAcoStorageOperations","_folder","_record","_apps","_record2","_plugins","_FolderLevelPermissions","_CmsEntriesCrudDecorators","_folder2","_createOperationsWrapper","_pickEntryFieldValues","_filter","setupAcoContext","context","setupAcoContextParams","tenancy","security","i18n","getLocale","locale","getContentLocale","WebinyError","getTenant","getCurrentTenant","storageOperations","createAcoStorageOperations","cms","getCmsContext","folderLevelPermissions","FolderLevelPermissions","getIdentity","getIdentityTeam","withoutAuthorization","identity","adminUser","adminUsers","getUser","where","id","team","getTeam","listPermissions","listAllFolders","type","withModel","createOperationsWrapper","modelName","FOLDER_MODEL_ID","model","results","entries","list","limit","latest","sort","items","map","pickEntryFieldValues","ex","message","canUseTeams","wcp","canUseFolderLevelPermissions","useFolderLevelPermissions","isAuthorizationEnabled","params","defaultRecordModel","getModel","SEARCH_RECORD_MODEL_ID","apps","AcoApps","plugins","byType","AcoAppRegisterPlugin","plugin","register","app","listAdminUsers","listUsers","listTeams","aco","folder","createFolderCrudMethods","search","createSearchRecordCrudMethods","filter","createFilterCrudMethods","getApp","name","get","listApps","registerApp","CmsEntriesCrudDecorators","decorate","createAcoContext","ContextPlugin","isHeadlessCmsReady","benchmark","measure","createAcoHooks","exports"],"sources":["createAcoContext.ts"],"sourcesContent":["import WebinyError from \"@webiny/error\";\nimport { ContextPlugin } from \"@webiny/api\";\nimport { I18NLocale } from \"@webiny/api-i18n/types\";\nimport { Tenant } from \"@webiny/api-tenancy/types\";\nimport { isHeadlessCmsReady } from \"@webiny/api-headless-cms\";\nimport { createAcoHooks } from \"~/createAcoHooks\";\nimport { createAcoStorageOperations } from \"~/createAcoStorageOperations\";\nimport { AcoContext, CreateAcoParams, Folder, IAcoAppRegisterParams } from \"~/types\";\nimport { createFolderCrudMethods } from \"~/folder/folder.crud\";\nimport { createSearchRecordCrudMethods } from \"~/record/record.crud\";\nimport { AcoApps } from \"./apps\";\nimport { SEARCH_RECORD_MODEL_ID } from \"~/record/record.model\";\nimport { AcoAppRegisterPlugin } from \"~/plugins\";\nimport { FolderLevelPermissions } from \"~/utils/FolderLevelPermissions\";\nimport { CmsEntriesCrudDecorators } from \"~/utils/decorators/CmsEntriesCrudDecorators\";\nimport { FOLDER_MODEL_ID } from \"~/folder/folder.model\";\nimport { createOperationsWrapper } from \"~/utils/createOperationsWrapper\";\nimport { pickEntryFieldValues } from \"~/utils/pickEntryFieldValues\";\nimport { createFilterCrudMethods } from \"~/filter/filter.crud\";\n\ninterface CreateAcoContextParams {\n useFolderLevelPermissions?: boolean;\n}\n\nconst setupAcoContext = async (\n context: AcoContext,\n setupAcoContextParams: CreateAcoContextParams\n): Promise<void> => {\n const { tenancy, security, i18n } = context;\n\n const getLocale = (): I18NLocale => {\n const locale = i18n.getContentLocale();\n if (!locale) {\n throw new WebinyError(\n \"Missing content locale in api-aco/plugins/context.ts\",\n \"LOCALE_ERROR\"\n );\n }\n\n return locale;\n };\n\n const getTenant = (): Tenant => {\n return tenancy.getCurrentTenant();\n };\n\n const storageOperations = createAcoStorageOperations({\n /**\n * TODO: We need to figure out a way to pass \"cms\" from outside (e.g. apps/api/graphql)\n */\n cms: context.cms,\n /**\n * TODO: This is required for \"entryFieldFromStorageTransform\" which access plugins from context.\n */\n getCmsContext: () => context,\n security\n });\n\n const folderLevelPermissions = new FolderLevelPermissions({\n getIdentity: () => security.getIdentity(),\n getIdentityTeam: async () => {\n return security.withoutAuthorization(async () => {\n const identity = security.getIdentity();\n if (!identity) {\n return null;\n }\n\n const adminUser = await context.adminUsers.getUser({ where: { id: identity.id } });\n if (!adminUser) {\n return null;\n }\n\n if (!adminUser.team) {\n return null;\n }\n\n return context.security.getTeam({ where: { id: adminUser.team } });\n });\n },\n listPermissions: () => security.listPermissions(),\n listAllFolders: type => {\n // When retrieving a list of all folders, we want to do it in the\n // fastest way and that is by directly using CMS's storage operations.\n const { withModel } = createOperationsWrapper({\n modelName: FOLDER_MODEL_ID,\n cms: context.cms,\n getCmsContext: () => context,\n security\n });\n\n return withModel(async model => {\n try {\n const results = await context.cms.storageOperations.entries.list(model, {\n limit: 100_000,\n where: {\n type,\n\n // Folders always work with latest entries. We never publish them.\n latest: true\n },\n sort: [\"title_ASC\"]\n });\n\n return results.items.map(pickEntryFieldValues<Folder>);\n } catch (ex) {\n /**\n * Skip throwing an error if the error is related to the search phase execution.\n * This is a temporary solution to avoid breaking the entire system when no entries were ever inserted in the index.\n *\n * TODO: figure out better way to handle this.\n */\n if (ex.message === \"search_phase_execution_exception\") {\n return [];\n }\n throw ex;\n }\n });\n },\n canUseTeams: () => context.wcp.canUseTeams(),\n canUseFolderLevelPermissions: () => {\n if (setupAcoContextParams.useFolderLevelPermissions === false) {\n return false;\n }\n\n return context.wcp.canUseFolderLevelPermissions();\n },\n isAuthorizationEnabled: () => context.security.isAuthorizationEnabled()\n });\n\n const params: CreateAcoParams = {\n getLocale,\n getTenant,\n storageOperations,\n folderLevelPermissions\n };\n\n const defaultRecordModel = await context.security.withoutAuthorization(async () => {\n return context.cms.getModel(SEARCH_RECORD_MODEL_ID);\n });\n\n if (!defaultRecordModel) {\n throw new WebinyError(`There is no default record model in ${SEARCH_RECORD_MODEL_ID}`);\n }\n\n /**\n * First we need to create all the apps.\n */\n const apps = new AcoApps(context, params);\n const plugins = context.plugins.byType<AcoAppRegisterPlugin>(AcoAppRegisterPlugin.type);\n for (const plugin of plugins) {\n await apps.register({\n model: defaultRecordModel,\n ...plugin.app\n });\n }\n\n const listAdminUsers = () => {\n return security.withoutAuthorization(async () => {\n return context.adminUsers.listUsers();\n });\n };\n const listTeams = () => {\n return security.withoutAuthorization(async () => {\n return context.security.listTeams();\n });\n };\n\n context.aco = {\n folder: createFolderCrudMethods({\n ...params,\n listAdminUsers,\n listTeams\n }),\n search: createSearchRecordCrudMethods(params),\n folderLevelPermissions,\n filter: createFilterCrudMethods(params),\n apps,\n getApp: (name: string) => apps.get(name),\n listApps: () => apps.list(),\n registerApp: async (params: IAcoAppRegisterParams) => {\n return apps.register({\n model: defaultRecordModel,\n ...params\n });\n }\n };\n\n if (context.wcp.canUseFolderLevelPermissions()) {\n new CmsEntriesCrudDecorators({ context }).decorate();\n\n // PB decorators registered here: packages/api-page-builder-aco/src/index.ts\n // new PageBuilderCrudDecorators({ context }).decorate();\n }\n};\n\nexport const createAcoContext = (params: CreateAcoContextParams = {}) => {\n const plugin = new ContextPlugin<AcoContext>(async context => {\n /**\n * We can skip the ACO initialization if the installation is pending.\n */\n if (!(await isHeadlessCmsReady(context))) {\n return;\n }\n\n await context.benchmark.measure(\"aco.context.setup\", async () => {\n await setupAcoContext(context, params);\n });\n\n await context.benchmark.measure(\"aco.context.hooks\", async () => {\n await createAcoHooks(context);\n });\n });\n\n plugin.name = \"aco.createContext\";\n\n return plugin;\n};\n"],"mappings":"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","ignoreList":[]}
1
+ {"version":3,"names":["_error","_interopRequireDefault","require","_api","_apiHeadlessCms","_createAcoHooks","_createAcoStorageOperations","_folder","_record","_apps","_record2","_plugins","_FolderLevelPermissions","_CmsEntriesCrudDecorators","_folder2","_createOperationsWrapper","_pickEntryFieldValues","_filter","setupAcoContext","context","setupAcoContextParams","tenancy","security","i18n","getLocale","locale","getContentLocale","WebinyError","getTenant","getCurrentTenant","storageOperations","createAcoStorageOperations","cms","getCmsContext","folderLevelPermissions","FolderLevelPermissions","getIdentity","listIdentityTeams","withoutAuthorization","identity","adminUser","adminUsers","getUser","where","id","hasTeams","teams","length","listTeams","id_in","listPermissions","listAllFolders","type","withModel","createOperationsWrapper","modelName","FOLDER_MODEL_ID","model","results","entries","list","limit","latest","sort","items","map","pickEntryFieldValues","ex","message","canUseTeams","wcp","canUseFolderLevelPermissions","useFolderLevelPermissions","isAuthorizationEnabled","params","defaultRecordModel","getModel","SEARCH_RECORD_MODEL_ID","apps","AcoApps","plugins","byType","AcoAppRegisterPlugin","plugin","register","app","listAdminUsers","listUsers","aco","folder","createFolderCrudMethods","search","createSearchRecordCrudMethods","filter","createFilterCrudMethods","getApp","name","get","listApps","registerApp","CmsEntriesCrudDecorators","decorate","createAcoContext","ContextPlugin","isHeadlessCmsReady","benchmark","measure","createAcoHooks","exports"],"sources":["createAcoContext.ts"],"sourcesContent":["import WebinyError from \"@webiny/error\";\nimport { ContextPlugin } from \"@webiny/api\";\nimport { I18NLocale } from \"@webiny/api-i18n/types\";\nimport { Tenant } from \"@webiny/api-tenancy/types\";\nimport { isHeadlessCmsReady } from \"@webiny/api-headless-cms\";\nimport { createAcoHooks } from \"~/createAcoHooks\";\nimport { createAcoStorageOperations } from \"~/createAcoStorageOperations\";\nimport { AcoContext, CreateAcoParams, Folder, IAcoAppRegisterParams } from \"~/types\";\nimport { createFolderCrudMethods } from \"~/folder/folder.crud\";\nimport { createSearchRecordCrudMethods } from \"~/record/record.crud\";\nimport { AcoApps } from \"./apps\";\nimport { SEARCH_RECORD_MODEL_ID } from \"~/record/record.model\";\nimport { AcoAppRegisterPlugin } from \"~/plugins\";\nimport { FolderLevelPermissions } from \"~/utils/FolderLevelPermissions\";\nimport { CmsEntriesCrudDecorators } from \"~/utils/decorators/CmsEntriesCrudDecorators\";\nimport { FOLDER_MODEL_ID } from \"~/folder/folder.model\";\nimport { createOperationsWrapper } from \"~/utils/createOperationsWrapper\";\nimport { pickEntryFieldValues } from \"~/utils/pickEntryFieldValues\";\nimport { createFilterCrudMethods } from \"~/filter/filter.crud\";\n\ninterface CreateAcoContextParams {\n useFolderLevelPermissions?: boolean;\n}\n\nconst setupAcoContext = async (\n context: AcoContext,\n setupAcoContextParams: CreateAcoContextParams\n): Promise<void> => {\n const { tenancy, security, i18n } = context;\n\n const getLocale = (): I18NLocale => {\n const locale = i18n.getContentLocale();\n if (!locale) {\n throw new WebinyError(\n \"Missing content locale in api-aco/plugins/context.ts\",\n \"LOCALE_ERROR\"\n );\n }\n\n return locale;\n };\n\n const getTenant = (): Tenant => {\n return tenancy.getCurrentTenant();\n };\n\n const storageOperations = createAcoStorageOperations({\n /**\n * TODO: We need to figure out a way to pass \"cms\" from outside (e.g. apps/api/graphql)\n */\n cms: context.cms,\n /**\n * TODO: This is required for \"entryFieldFromStorageTransform\" which access plugins from context.\n */\n getCmsContext: () => context,\n security\n });\n\n const folderLevelPermissions = new FolderLevelPermissions({\n getIdentity: () => security.getIdentity(),\n listIdentityTeams: async () => {\n return security.withoutAuthorization(async () => {\n const identity = security.getIdentity();\n if (!identity) {\n return [];\n }\n\n const adminUser = await context.adminUsers.getUser({ where: { id: identity.id } });\n if (!adminUser) {\n return [];\n }\n\n const hasTeams = adminUser.teams && adminUser.teams.length > 0;\n if (hasTeams) {\n return context.security.listTeams({ where: { id_in: adminUser.teams } });\n }\n\n return [];\n });\n },\n listPermissions: () => security.listPermissions(),\n listAllFolders: type => {\n // When retrieving a list of all folders, we want to do it in the\n // fastest way and that is by directly using CMS's storage operations.\n const { withModel } = createOperationsWrapper({\n modelName: FOLDER_MODEL_ID,\n cms: context.cms,\n getCmsContext: () => context,\n security\n });\n\n return withModel(async model => {\n try {\n const results = await context.cms.storageOperations.entries.list(model, {\n limit: 100_000,\n where: {\n type,\n\n // Folders always work with latest entries. We never publish them.\n latest: true\n },\n sort: [\"title_ASC\"]\n });\n\n return results.items.map(pickEntryFieldValues<Folder>);\n } catch (ex) {\n /**\n * Skip throwing an error if the error is related to the search phase execution.\n * This is a temporary solution to avoid breaking the entire system when no entries were ever inserted in the index.\n *\n * TODO: figure out better way to handle this.\n */\n if (ex.message === \"search_phase_execution_exception\") {\n return [];\n }\n throw ex;\n }\n });\n },\n canUseTeams: () => context.wcp.canUseTeams(),\n canUseFolderLevelPermissions: () => {\n if (setupAcoContextParams.useFolderLevelPermissions === false) {\n return false;\n }\n\n return context.wcp.canUseFolderLevelPermissions();\n },\n isAuthorizationEnabled: () => context.security.isAuthorizationEnabled()\n });\n\n const params: CreateAcoParams = {\n getLocale,\n getTenant,\n storageOperations,\n folderLevelPermissions\n };\n\n const defaultRecordModel = await context.security.withoutAuthorization(async () => {\n return context.cms.getModel(SEARCH_RECORD_MODEL_ID);\n });\n\n if (!defaultRecordModel) {\n throw new WebinyError(`There is no default record model in ${SEARCH_RECORD_MODEL_ID}`);\n }\n\n /**\n * First we need to create all the apps.\n */\n const apps = new AcoApps(context, params);\n const plugins = context.plugins.byType<AcoAppRegisterPlugin>(AcoAppRegisterPlugin.type);\n for (const plugin of plugins) {\n await apps.register({\n model: defaultRecordModel,\n ...plugin.app\n });\n }\n\n const listAdminUsers = () => {\n return security.withoutAuthorization(async () => {\n return context.adminUsers.listUsers();\n });\n };\n const listTeams = () => {\n return security.withoutAuthorization(async () => {\n return context.security.listTeams();\n });\n };\n\n context.aco = {\n folder: createFolderCrudMethods({\n ...params,\n listAdminUsers,\n listTeams\n }),\n search: createSearchRecordCrudMethods(params),\n folderLevelPermissions,\n filter: createFilterCrudMethods(params),\n apps,\n getApp: (name: string) => apps.get(name),\n listApps: () => apps.list(),\n registerApp: async (params: IAcoAppRegisterParams) => {\n return apps.register({\n model: defaultRecordModel,\n ...params\n });\n }\n };\n\n if (context.wcp.canUseFolderLevelPermissions()) {\n new CmsEntriesCrudDecorators({ context }).decorate();\n\n // PB decorators registered here: packages/api-page-builder-aco/src/index.ts\n // new PageBuilderCrudDecorators({ context }).decorate();\n }\n};\n\nexport const createAcoContext = (params: CreateAcoContextParams = {}) => {\n const plugin = new ContextPlugin<AcoContext>(async context => {\n /**\n * We can skip the ACO initialization if the installation is pending.\n */\n if (!(await isHeadlessCmsReady(context))) {\n return;\n }\n\n await context.benchmark.measure(\"aco.context.setup\", async () => {\n await setupAcoContext(context, params);\n });\n\n await context.benchmark.measure(\"aco.context.hooks\", async () => {\n await createAcoHooks(context);\n });\n });\n\n plugin.name = \"aco.createContext\";\n\n return plugin;\n};\n"],"mappings":"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","ignoreList":[]}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@webiny/api-aco",
3
- "version": "5.41.0-dbt.0",
3
+ "version": "5.41.1-beta.0",
4
4
  "main": "index.js",
5
5
  "keywords": [
6
6
  "aco:base"
@@ -22,18 +22,18 @@
22
22
  "directory": "dist"
23
23
  },
24
24
  "dependencies": {
25
- "@webiny/api": "5.41.0-dbt.0",
26
- "@webiny/api-authentication": "5.41.0-dbt.0",
27
- "@webiny/api-headless-cms": "5.41.0-dbt.0",
28
- "@webiny/api-i18n": "5.41.0-dbt.0",
29
- "@webiny/api-security": "5.41.0-dbt.0",
30
- "@webiny/api-tenancy": "5.41.0-dbt.0",
31
- "@webiny/error": "5.41.0-dbt.0",
32
- "@webiny/handler": "5.41.0-dbt.0",
33
- "@webiny/handler-graphql": "5.41.0-dbt.0",
34
- "@webiny/pubsub": "5.41.0-dbt.0",
35
- "@webiny/utils": "5.41.0-dbt.0",
36
- "@webiny/validation": "5.41.0-dbt.0",
25
+ "@webiny/api": "5.41.1-beta.0",
26
+ "@webiny/api-authentication": "5.41.1-beta.0",
27
+ "@webiny/api-headless-cms": "5.41.1-beta.0",
28
+ "@webiny/api-i18n": "5.41.1-beta.0",
29
+ "@webiny/api-security": "5.41.1-beta.0",
30
+ "@webiny/api-tenancy": "5.41.1-beta.0",
31
+ "@webiny/error": "5.41.1-beta.0",
32
+ "@webiny/handler": "5.41.1-beta.0",
33
+ "@webiny/handler-graphql": "5.41.1-beta.0",
34
+ "@webiny/pubsub": "5.41.1-beta.0",
35
+ "@webiny/utils": "5.41.1-beta.0",
36
+ "@webiny/validation": "5.41.1-beta.0",
37
37
  "lodash": "4.17.21"
38
38
  },
39
39
  "devDependencies": {
@@ -42,22 +42,22 @@
42
42
  "@babel/preset-env": "7.24.3",
43
43
  "@babel/preset-typescript": "7.24.1",
44
44
  "@babel/runtime": "7.24.1",
45
- "@webiny/api-admin-users": "5.41.0-dbt.0",
46
- "@webiny/api-file-manager": "5.41.0-dbt.0",
47
- "@webiny/api-i18n-ddb": "5.41.0-dbt.0",
48
- "@webiny/api-security-so-ddb": "5.41.0-dbt.0",
49
- "@webiny/api-tenancy-so-ddb": "5.41.0-dbt.0",
50
- "@webiny/api-wcp": "5.41.0-dbt.0",
51
- "@webiny/cli": "5.41.0-dbt.0",
52
- "@webiny/handler-aws": "5.41.0-dbt.0",
53
- "@webiny/plugins": "5.41.0-dbt.0",
54
- "@webiny/project-utils": "5.41.0-dbt.0",
55
- "@webiny/wcp": "5.41.0-dbt.0",
45
+ "@webiny/api-admin-users": "5.41.1-beta.0",
46
+ "@webiny/api-file-manager": "5.41.1-beta.0",
47
+ "@webiny/api-i18n-ddb": "5.41.1-beta.0",
48
+ "@webiny/api-security-so-ddb": "5.41.1-beta.0",
49
+ "@webiny/api-tenancy-so-ddb": "5.41.1-beta.0",
50
+ "@webiny/api-wcp": "5.41.1-beta.0",
51
+ "@webiny/cli": "5.41.1-beta.0",
52
+ "@webiny/handler-aws": "5.41.1-beta.0",
53
+ "@webiny/plugins": "5.41.1-beta.0",
54
+ "@webiny/project-utils": "5.41.1-beta.0",
55
+ "@webiny/wcp": "5.41.1-beta.0",
56
56
  "graphql": "15.8.0",
57
57
  "prettier": "2.8.8",
58
58
  "rimraf": "5.0.5",
59
59
  "ttypescript": "1.5.15",
60
60
  "typescript": "4.9.5"
61
61
  },
62
- "gitHead": "bbaec4dd1685579548c08bbde386aee5d96b80f8"
62
+ "gitHead": "004f3d7a2022be14f14bd2f9342d009d7974ccd0"
63
63
  }
@@ -1,6 +1,6 @@
1
1
  import { AcoBaseFields, ListMeta } from "../types";
2
2
  import { Topic } from "@webiny/pubsub/types";
3
- import { CmsModel } from "@webiny/api-headless-cms/types";
3
+ import { CmsEntryListSort, CmsModel } from "@webiny/api-headless-cms/types";
4
4
  export type GenericSearchData = {
5
5
  [key: string]: any;
6
6
  };
@@ -32,7 +32,7 @@ export interface ListSearchRecordsWhere<TData extends GenericSearchData = Generi
32
32
  export interface ListSearchRecordsParams {
33
33
  where?: ListSearchRecordsWhere;
34
34
  search?: string;
35
- sort?: string[];
35
+ sort?: CmsEntryListSort;
36
36
  limit?: number;
37
37
  after?: string | null;
38
38
  }
@@ -1 +1 @@
1
- {"version":3,"names":[],"sources":["record.types.ts"],"sourcesContent":["import { AcoBaseFields, ListMeta } from \"~/types\";\nimport { Topic } from \"@webiny/pubsub/types\";\nimport { CmsModel } from \"@webiny/api-headless-cms/types\";\n\nexport type GenericSearchData = {\n [key: string]: any;\n};\n\nexport interface Location {\n folderId: string;\n}\n\nexport interface SearchRecord<TData extends GenericSearchData = GenericSearchData>\n extends AcoBaseFields {\n type: string;\n title: string;\n content?: string;\n location: Location;\n data: TData;\n tags: string[];\n}\n\nexport interface SearchRecordTag {\n tag: string;\n count: number;\n}\n\nexport interface ListSearchRecordsWhere<TData extends GenericSearchData = GenericSearchData> {\n type: string;\n location?: {\n folderId: string;\n };\n tags_in?: string[];\n tags_startsWith?: string;\n tags_not_startsWith?: string;\n data?: TData;\n}\n\nexport interface ListSearchRecordsParams {\n where?: ListSearchRecordsWhere;\n search?: string;\n sort?: string[];\n limit?: number;\n after?: string | null;\n}\n\nexport type CreateSearchRecordParams<TData extends GenericSearchData = GenericSearchData> = Pick<\n SearchRecord<TData>,\n \"id\" | \"title\" | \"content\" | \"type\" | \"location\" | \"data\" | \"tags\"\n>;\n\nexport interface UpdateSearchRecordParams<TData extends GenericSearchData> {\n title?: string;\n content?: string;\n location?: Location;\n data?: TData;\n tags?: string[];\n}\n\nexport interface DeleteSearchRecordParams {\n id: string;\n}\n\nexport interface ListSearchRecordTagsWhere {\n type: string;\n}\n\nexport interface ListSearchRecordTagsParams {\n where?: ListSearchRecordTagsWhere;\n}\n\nexport interface StorageOperationsGetSearchRecordParams {\n id: string;\n}\n\nexport type StorageOperationsListSearchRecordsParams = ListSearchRecordsParams;\nexport type StorageOperationsListSearchRecordTagsParams = ListSearchRecordTagsParams;\n\nexport interface StorageOperationsCreateSearchRecordParams<\n TData extends GenericSearchData = GenericSearchData\n> {\n data: CreateSearchRecordParams<TData>;\n}\n\nexport interface StorageOperationsUpdateSearchRecordParams<\n TData extends GenericSearchData = GenericSearchData\n> {\n id: string;\n data: UpdateSearchRecordParams<TData>;\n}\n\nexport interface StorageOperationsMoveSearchRecordParams {\n id: string;\n folderId?: string | null;\n}\n\nexport type StorageOperationsDeleteSearchRecordParams = DeleteSearchRecordParams;\n\nexport interface OnSearchRecordBeforeCreateTopicParams<\n TData extends GenericSearchData = GenericSearchData\n> {\n model: CmsModel;\n input: CreateSearchRecordParams<TData>;\n}\n\nexport interface OnSearchRecordAfterCreateTopicParams<\n TData extends GenericSearchData = GenericSearchData\n> {\n model: CmsModel;\n record: SearchRecord<TData>;\n}\n\nexport interface OnSearchRecordBeforeUpdateTopicParams<\n TData extends GenericSearchData = GenericSearchData\n> {\n model: CmsModel;\n original: SearchRecord<TData>;\n input: Record<string, any>;\n}\n\nexport interface OnSearchRecordBeforeMoveTopicParams<\n TData extends GenericSearchData = GenericSearchData\n> {\n model: CmsModel;\n original: SearchRecord<TData>;\n folderId?: string | null;\n}\n\nexport interface OnSearchRecordAfterMoveTopicParams<\n TData extends GenericSearchData = GenericSearchData\n> {\n model: CmsModel;\n original: SearchRecord<TData>;\n folderId?: string | null;\n}\n\nexport interface OnSearchRecordAfterUpdateTopicParams<\n TData extends GenericSearchData = GenericSearchData\n> {\n model: CmsModel;\n original: SearchRecord<TData>;\n record: SearchRecord<TData>;\n input: Record<string, any>;\n}\n\nexport interface OnSearchRecordBeforeDeleteTopicParams<\n TData extends GenericSearchData = GenericSearchData\n> {\n model: CmsModel;\n record: SearchRecord<TData>;\n}\n\nexport interface OnSearchRecordAfterDeleteTopicParams<\n TData extends GenericSearchData = GenericSearchData\n> {\n model: CmsModel;\n record: SearchRecord<TData>;\n}\n\nexport interface AcoSearchRecordCrudBase {\n get<TData extends GenericSearchData = GenericSearchData>(\n id: string\n ): Promise<SearchRecord<TData>>;\n list<TData extends GenericSearchData = GenericSearchData>(\n params: ListSearchRecordsParams\n ): Promise<[SearchRecord<TData>[], ListMeta]>;\n listTags(params: ListSearchRecordTagsParams): Promise<[SearchRecordTag[], ListMeta]>;\n create<TData extends GenericSearchData = GenericSearchData>(\n data: CreateSearchRecordParams<TData>\n ): Promise<SearchRecord<TData>>;\n update<TData extends GenericSearchData = GenericSearchData>(\n id: string,\n data: UpdateSearchRecordParams<TData>\n ): Promise<SearchRecord<TData>>;\n move(id: string, folderId?: string | null): Promise<boolean>;\n delete(id: string): Promise<boolean>;\n}\n\nexport interface AcoSearchRecordCrud\n extends Omit<\n AcoSearchRecordCrudBase,\n \"get\" | \"list\" | \"create\" | \"update\" | \"delete\" | \"listTags\" | \"move\"\n > {\n get<TData extends GenericSearchData = GenericSearchData>(\n model: CmsModel,\n id: string\n ): Promise<SearchRecord<TData>>;\n list<TData extends GenericSearchData = GenericSearchData>(\n model: CmsModel,\n params: ListSearchRecordsParams\n ): Promise<[SearchRecord<TData>[], ListMeta]>;\n listTags(\n model: CmsModel,\n params: ListSearchRecordTagsParams\n ): Promise<[SearchRecordTag[], ListMeta]>;\n create<TData extends GenericSearchData = GenericSearchData>(\n model: CmsModel,\n data: CreateSearchRecordParams<TData>\n ): Promise<SearchRecord<TData>>;\n update<TData extends GenericSearchData = GenericSearchData>(\n model: CmsModel,\n id: string,\n data: UpdateSearchRecordParams<TData>\n ): Promise<SearchRecord<TData>>;\n move(model: CmsModel, id: string, folderId?: string | null): Promise<boolean>;\n delete(model: CmsModel, id: string): Promise<boolean>;\n onSearchRecordBeforeCreate: Topic<OnSearchRecordBeforeCreateTopicParams>;\n onSearchRecordAfterCreate: Topic<OnSearchRecordAfterCreateTopicParams>;\n onSearchRecordBeforeUpdate: Topic<OnSearchRecordBeforeUpdateTopicParams>;\n onSearchRecordAfterUpdate: Topic<OnSearchRecordAfterUpdateTopicParams>;\n onSearchRecordBeforeMove: Topic<OnSearchRecordBeforeMoveTopicParams>;\n onSearchRecordAfterMove: Topic<OnSearchRecordAfterMoveTopicParams>;\n onSearchRecordBeforeDelete: Topic<OnSearchRecordBeforeDeleteTopicParams>;\n onSearchRecordAfterDelete: Topic<OnSearchRecordAfterDeleteTopicParams>;\n}\n\nexport interface AcoSearchRecordStorageOperations {\n getRecord<TData extends GenericSearchData = GenericSearchData>(\n model: CmsModel,\n params: StorageOperationsGetSearchRecordParams\n ): Promise<SearchRecord<TData>>;\n listRecords<TData extends GenericSearchData = GenericSearchData>(\n model: CmsModel,\n params: StorageOperationsListSearchRecordsParams\n ): Promise<[SearchRecord<TData>[], ListMeta]>;\n listTags(\n model: CmsModel,\n params: StorageOperationsListSearchRecordTagsParams\n ): Promise<[SearchRecordTag[], ListMeta]>;\n createRecord<TData extends GenericSearchData = GenericSearchData>(\n model: CmsModel,\n params: StorageOperationsCreateSearchRecordParams<TData>\n ): Promise<SearchRecord<TData>>;\n updateRecord<TData extends GenericSearchData = GenericSearchData>(\n model: CmsModel,\n params: StorageOperationsUpdateSearchRecordParams<TData>\n ): Promise<SearchRecord<TData>>;\n moveRecord(model: CmsModel, params: StorageOperationsMoveSearchRecordParams): Promise<boolean>;\n deleteRecord(\n model: CmsModel,\n params: StorageOperationsDeleteSearchRecordParams\n ): Promise<boolean>;\n}\n"],"mappings":"","ignoreList":[]}
1
+ {"version":3,"names":[],"sources":["record.types.ts"],"sourcesContent":["import { AcoBaseFields, ListMeta } from \"~/types\";\nimport { Topic } from \"@webiny/pubsub/types\";\nimport { CmsEntryListSort, CmsModel } from \"@webiny/api-headless-cms/types\";\n\nexport type GenericSearchData = {\n [key: string]: any;\n};\n\nexport interface Location {\n folderId: string;\n}\n\nexport interface SearchRecord<TData extends GenericSearchData = GenericSearchData>\n extends AcoBaseFields {\n type: string;\n title: string;\n content?: string;\n location: Location;\n data: TData;\n tags: string[];\n}\n\nexport interface SearchRecordTag {\n tag: string;\n count: number;\n}\n\nexport interface ListSearchRecordsWhere<TData extends GenericSearchData = GenericSearchData> {\n type: string;\n location?: {\n folderId: string;\n };\n tags_in?: string[];\n tags_startsWith?: string;\n tags_not_startsWith?: string;\n data?: TData;\n}\n\nexport interface ListSearchRecordsParams {\n where?: ListSearchRecordsWhere;\n search?: string;\n sort?: CmsEntryListSort;\n limit?: number;\n after?: string | null;\n}\n\nexport type CreateSearchRecordParams<TData extends GenericSearchData = GenericSearchData> = Pick<\n SearchRecord<TData>,\n \"id\" | \"title\" | \"content\" | \"type\" | \"location\" | \"data\" | \"tags\"\n>;\n\nexport interface UpdateSearchRecordParams<TData extends GenericSearchData> {\n title?: string;\n content?: string;\n location?: Location;\n data?: TData;\n tags?: string[];\n}\n\nexport interface DeleteSearchRecordParams {\n id: string;\n}\n\nexport interface ListSearchRecordTagsWhere {\n type: string;\n}\n\nexport interface ListSearchRecordTagsParams {\n where?: ListSearchRecordTagsWhere;\n}\n\nexport interface StorageOperationsGetSearchRecordParams {\n id: string;\n}\n\nexport type StorageOperationsListSearchRecordsParams = ListSearchRecordsParams;\nexport type StorageOperationsListSearchRecordTagsParams = ListSearchRecordTagsParams;\n\nexport interface StorageOperationsCreateSearchRecordParams<\n TData extends GenericSearchData = GenericSearchData\n> {\n data: CreateSearchRecordParams<TData>;\n}\n\nexport interface StorageOperationsUpdateSearchRecordParams<\n TData extends GenericSearchData = GenericSearchData\n> {\n id: string;\n data: UpdateSearchRecordParams<TData>;\n}\n\nexport interface StorageOperationsMoveSearchRecordParams {\n id: string;\n folderId?: string | null;\n}\n\nexport type StorageOperationsDeleteSearchRecordParams = DeleteSearchRecordParams;\n\nexport interface OnSearchRecordBeforeCreateTopicParams<\n TData extends GenericSearchData = GenericSearchData\n> {\n model: CmsModel;\n input: CreateSearchRecordParams<TData>;\n}\n\nexport interface OnSearchRecordAfterCreateTopicParams<\n TData extends GenericSearchData = GenericSearchData\n> {\n model: CmsModel;\n record: SearchRecord<TData>;\n}\n\nexport interface OnSearchRecordBeforeUpdateTopicParams<\n TData extends GenericSearchData = GenericSearchData\n> {\n model: CmsModel;\n original: SearchRecord<TData>;\n input: Record<string, any>;\n}\n\nexport interface OnSearchRecordBeforeMoveTopicParams<\n TData extends GenericSearchData = GenericSearchData\n> {\n model: CmsModel;\n original: SearchRecord<TData>;\n folderId?: string | null;\n}\n\nexport interface OnSearchRecordAfterMoveTopicParams<\n TData extends GenericSearchData = GenericSearchData\n> {\n model: CmsModel;\n original: SearchRecord<TData>;\n folderId?: string | null;\n}\n\nexport interface OnSearchRecordAfterUpdateTopicParams<\n TData extends GenericSearchData = GenericSearchData\n> {\n model: CmsModel;\n original: SearchRecord<TData>;\n record: SearchRecord<TData>;\n input: Record<string, any>;\n}\n\nexport interface OnSearchRecordBeforeDeleteTopicParams<\n TData extends GenericSearchData = GenericSearchData\n> {\n model: CmsModel;\n record: SearchRecord<TData>;\n}\n\nexport interface OnSearchRecordAfterDeleteTopicParams<\n TData extends GenericSearchData = GenericSearchData\n> {\n model: CmsModel;\n record: SearchRecord<TData>;\n}\n\nexport interface AcoSearchRecordCrudBase {\n get<TData extends GenericSearchData = GenericSearchData>(\n id: string\n ): Promise<SearchRecord<TData>>;\n list<TData extends GenericSearchData = GenericSearchData>(\n params: ListSearchRecordsParams\n ): Promise<[SearchRecord<TData>[], ListMeta]>;\n listTags(params: ListSearchRecordTagsParams): Promise<[SearchRecordTag[], ListMeta]>;\n create<TData extends GenericSearchData = GenericSearchData>(\n data: CreateSearchRecordParams<TData>\n ): Promise<SearchRecord<TData>>;\n update<TData extends GenericSearchData = GenericSearchData>(\n id: string,\n data: UpdateSearchRecordParams<TData>\n ): Promise<SearchRecord<TData>>;\n move(id: string, folderId?: string | null): Promise<boolean>;\n delete(id: string): Promise<boolean>;\n}\n\nexport interface AcoSearchRecordCrud\n extends Omit<\n AcoSearchRecordCrudBase,\n \"get\" | \"list\" | \"create\" | \"update\" | \"delete\" | \"listTags\" | \"move\"\n > {\n get<TData extends GenericSearchData = GenericSearchData>(\n model: CmsModel,\n id: string\n ): Promise<SearchRecord<TData>>;\n list<TData extends GenericSearchData = GenericSearchData>(\n model: CmsModel,\n params: ListSearchRecordsParams\n ): Promise<[SearchRecord<TData>[], ListMeta]>;\n listTags(\n model: CmsModel,\n params: ListSearchRecordTagsParams\n ): Promise<[SearchRecordTag[], ListMeta]>;\n create<TData extends GenericSearchData = GenericSearchData>(\n model: CmsModel,\n data: CreateSearchRecordParams<TData>\n ): Promise<SearchRecord<TData>>;\n update<TData extends GenericSearchData = GenericSearchData>(\n model: CmsModel,\n id: string,\n data: UpdateSearchRecordParams<TData>\n ): Promise<SearchRecord<TData>>;\n move(model: CmsModel, id: string, folderId?: string | null): Promise<boolean>;\n delete(model: CmsModel, id: string): Promise<boolean>;\n onSearchRecordBeforeCreate: Topic<OnSearchRecordBeforeCreateTopicParams>;\n onSearchRecordAfterCreate: Topic<OnSearchRecordAfterCreateTopicParams>;\n onSearchRecordBeforeUpdate: Topic<OnSearchRecordBeforeUpdateTopicParams>;\n onSearchRecordAfterUpdate: Topic<OnSearchRecordAfterUpdateTopicParams>;\n onSearchRecordBeforeMove: Topic<OnSearchRecordBeforeMoveTopicParams>;\n onSearchRecordAfterMove: Topic<OnSearchRecordAfterMoveTopicParams>;\n onSearchRecordBeforeDelete: Topic<OnSearchRecordBeforeDeleteTopicParams>;\n onSearchRecordAfterDelete: Topic<OnSearchRecordAfterDeleteTopicParams>;\n}\n\nexport interface AcoSearchRecordStorageOperations {\n getRecord<TData extends GenericSearchData = GenericSearchData>(\n model: CmsModel,\n params: StorageOperationsGetSearchRecordParams\n ): Promise<SearchRecord<TData>>;\n listRecords<TData extends GenericSearchData = GenericSearchData>(\n model: CmsModel,\n params: StorageOperationsListSearchRecordsParams\n ): Promise<[SearchRecord<TData>[], ListMeta]>;\n listTags(\n model: CmsModel,\n params: StorageOperationsListSearchRecordTagsParams\n ): Promise<[SearchRecordTag[], ListMeta]>;\n createRecord<TData extends GenericSearchData = GenericSearchData>(\n model: CmsModel,\n params: StorageOperationsCreateSearchRecordParams<TData>\n ): Promise<SearchRecord<TData>>;\n updateRecord<TData extends GenericSearchData = GenericSearchData>(\n model: CmsModel,\n params: StorageOperationsUpdateSearchRecordParams<TData>\n ): Promise<SearchRecord<TData>>;\n moveRecord(model: CmsModel, params: StorageOperationsMoveSearchRecordParams): Promise<boolean>;\n deleteRecord(\n model: CmsModel,\n params: StorageOperationsDeleteSearchRecordParams\n ): Promise<boolean>;\n}\n"],"mappings":"","ignoreList":[]}
@@ -34,7 +34,7 @@ interface ListFolderPermissionsParams {
34
34
  }
35
35
  export interface FolderLevelPermissionsParams {
36
36
  getIdentity: Authentication["getIdentity"];
37
- getIdentityTeam: () => Promise<Team | null>;
37
+ listIdentityTeams: () => Promise<Team[]>;
38
38
  listPermissions: () => Promise<SecurityPermission[]>;
39
39
  listAllFolders: (folderType: string) => Promise<Folder[]>;
40
40
  canUseTeams: () => boolean;
@@ -44,7 +44,7 @@ export interface FolderLevelPermissionsParams {
44
44
  export declare class FolderLevelPermissions {
45
45
  canUseFolderLevelPermissions: () => boolean;
46
46
  private readonly getIdentity;
47
- private readonly getIdentityTeam;
47
+ private readonly listIdentityTeams;
48
48
  private readonly listPermissions;
49
49
  private readonly listAllFoldersCallback;
50
50
  private readonly canUseTeams;
@@ -10,7 +10,7 @@ class FolderLevelPermissions {
10
10
  foldersPermissionsLists = {};
11
11
  constructor(params) {
12
12
  this.getIdentity = params.getIdentity;
13
- this.getIdentityTeam = params.getIdentityTeam;
13
+ this.listIdentityTeams = params.listIdentityTeams;
14
14
  this.listPermissions = params.listPermissions;
15
15
  this.listAllFoldersCallback = params.listAllFolders;
16
16
  this.canUseTeams = params.canUseTeams;
@@ -81,7 +81,6 @@ class FolderLevelPermissions {
81
81
  if (!this.canUseFolderLevelPermissions() || !this.isAuthorizationEnabled()) {
82
82
  resolve([]);
83
83
  return;
84
- // return [];
85
84
  }
86
85
  const {
87
86
  folderType,
@@ -90,9 +89,9 @@ class FolderLevelPermissions {
90
89
  const allFolders = foldersList || (await this.listAllFolders(folderType));
91
90
  const identity = this.getIdentity();
92
91
  const permissions = await this.listPermissions();
93
- let identityTeam;
92
+ let identityTeams;
94
93
  if (this.canUseTeams()) {
95
- identityTeam = await this.getIdentityTeam();
94
+ identityTeams = await this.listIdentityTeams();
96
95
  }
97
96
  const processedFolderPermissions = [];
98
97
  const processFolderPermissions = folder => {
@@ -186,15 +185,17 @@ class FolderLevelPermissions {
186
185
  level: "owner",
187
186
  inheritedFrom: "role:full-access"
188
187
  };
189
- } else if (identityTeam) {
190
- // 2. Check the team user belongs to grants access to the folder.
191
- const teamPermission = currentFolderPermissions.permissions.find(p => p.target === `team:${identityTeam.id}`);
192
- if (teamPermission) {
193
- currentIdentityPermission = {
194
- target: `admin:${identity.id}`,
195
- level: teamPermission.level,
196
- inheritedFrom: "team:" + identityTeam.id
197
- };
188
+ } else if (identityTeams.length) {
189
+ // 2. Check the teams user belongs to and that grant access to the folder.
190
+ for (const identityTeam of identityTeams) {
191
+ const teamPermission = currentFolderPermissions.permissions.find(p => p.target === `team:${identityTeam.id}`);
192
+ if (teamPermission) {
193
+ currentIdentityPermission = {
194
+ target: `admin:${identity.id}`,
195
+ level: teamPermission.level,
196
+ inheritedFrom: "team:" + identityTeam.id
197
+ };
198
+ }
198
199
  }
199
200
  }
200
201
  if (currentIdentityPermission) {
@@ -1 +1 @@
1
- {"version":3,"names":["_apiSecurity","require","FolderLevelPermissions","allFolders","foldersPermissionsLists","constructor","params","getIdentity","getIdentityTeam","listPermissions","listAllFoldersCallback","listAllFolders","canUseTeams","canUseFolderLevelPermissions","identity","type","isAuthorizationEnabled","folderType","structuredClone","listAllFoldersWithPermissions","folders","filteredFoldersWithPermissions","filterFolders","rwd","assignFolderPermissions","invalidateFoldersCache","invalidateFoldersPermissionsListCache","updateFoldersCache","modifier","foldersClone","listFoldersPermissions","existingFoldersPermissionsList","Promise","resolve","foldersList","permissions","identityTeam","processedFolderPermissions","processFolderPermissions","folder","some","fp","folderId","id","currentFolderPermissions","map","permission","parentId","parentFolder","find","f","processedParentFolderPermissions","isPublicParentFolder","p","level","mustInherit","length","inheritedPermissions","inheritedFrom","push","currentIdentityIncludedInPermissions","target","hasFullAccess","name","currentIdentityPermissionIndex","findIndex","currentIdentityPermission","splice","unshift","accessInheritedFrom","teamPermission","mustAddPublicPermission","i","getFolderPermissions","folderPermissionsList","canAccessFolder","folderPermissions","managePermissions","ensureCanAccessFolder","NotAuthorizedError","canManageFolderPermissions","canManageFolderStructure","canManageFolderContent","canAccessFolderContent","ensureCanAccessFolderContent","canCreateFolderInRoot","filteredFolders","Array","isArray","permissionsIncludeNonInheritedPermissions","exports"],"sources":["FolderLevelPermissions.ts"],"sourcesContent":["import { Authentication } from \"@webiny/api-authentication/types\";\nimport { SecurityPermission, Team } from \"@webiny/api-security/types\";\nimport { Folder } from \"~/folder/folder.types\";\nimport { NotAuthorizedError } from \"@webiny/api-security\";\n\nexport type FolderAccessLevel = \"owner\" | \"viewer\" | \"editor\" | \"public\";\n\nexport interface FolderPermission {\n target: string;\n level: FolderAccessLevel;\n inheritedFrom?: string;\n}\n\nexport interface FolderPermissionsListItem {\n folderId: string;\n permissions: FolderPermission[];\n}\n\nexport type FolderPermissionsList = FolderPermissionsListItem[];\n\nexport interface CanAccessFolderContentParams {\n folder: Pick<Folder, \"id\" | \"type\" | \"parentId\">;\n rwd?: \"r\" | \"w\" | \"d\";\n foldersList?: Folder[];\n}\n\nexport interface CanAccessFolderParams extends CanAccessFolderContentParams {\n managePermissions?: boolean;\n}\n\ninterface FilterFoldersParams {\n folders: Array<Folder>;\n rwd?: \"r\" | \"w\" | \"d\";\n}\n\ninterface GetFolderPermissionsParams {\n folder: Pick<Folder, \"id\" | \"type\">;\n foldersList?: Folder[];\n}\n\ninterface ListFolderPermissionsParams {\n folderType: string;\n foldersList?: Folder[];\n}\n\nexport interface FolderLevelPermissionsParams {\n getIdentity: Authentication[\"getIdentity\"];\n getIdentityTeam: () => Promise<Team | null>;\n listPermissions: () => Promise<SecurityPermission[]>;\n listAllFolders: (folderType: string) => Promise<Folder[]>;\n canUseTeams: () => boolean;\n canUseFolderLevelPermissions: () => boolean;\n isAuthorizationEnabled: () => boolean;\n}\n\nexport class FolderLevelPermissions {\n canUseFolderLevelPermissions: () => boolean;\n\n private readonly getIdentity: Authentication[\"getIdentity\"];\n private readonly getIdentityTeam: () => Promise<Team | null>;\n private readonly listPermissions: () => Promise<SecurityPermission[]>;\n private readonly listAllFoldersCallback: (folderType: string) => Promise<Folder[]>;\n private readonly canUseTeams: () => boolean;\n private readonly isAuthorizationEnabled: () => boolean;\n private allFolders: Record<string, Folder[]> = {};\n private foldersPermissionsLists: Record<string, Promise<FolderPermissionsList> | null> = {};\n\n constructor(params: FolderLevelPermissionsParams) {\n this.getIdentity = params.getIdentity;\n this.getIdentityTeam = params.getIdentityTeam;\n this.listPermissions = params.listPermissions;\n this.listAllFoldersCallback = params.listAllFolders;\n this.canUseTeams = params.canUseTeams;\n this.canUseFolderLevelPermissions = () => {\n const identity = this.getIdentity();\n\n // FLPs only work with authenticated identities (logged-in users).\n if (!identity) {\n return false;\n }\n\n // At the moment, we only want FLP to be used with identities of type \"admin\".\n // This temporarily addresses the issue of API keys not being able to access content, because\n // FLPs doesn't work with them. Once we start adding FLPs to API keys, we can remove this check.\n if (identity.type !== \"admin\") {\n return false;\n }\n\n return params.canUseFolderLevelPermissions();\n };\n\n this.isAuthorizationEnabled = params.isAuthorizationEnabled;\n }\n\n async listAllFolders(folderType: string): Promise<Folder[]> {\n if (folderType in this.allFolders) {\n return structuredClone(this.allFolders[folderType]);\n }\n\n this.allFolders[folderType] = await this.listAllFoldersCallback(folderType);\n return structuredClone(this.allFolders[folderType]);\n }\n\n async listAllFoldersWithPermissions(folderType: string) {\n const folders = await this.listAllFolders(folderType);\n\n // Filter folders based on permissions and assign permissions to each folder.\n const filteredFoldersWithPermissions = await this.filterFolders({\n folders,\n rwd: \"r\"\n });\n\n await this.assignFolderPermissions(filteredFoldersWithPermissions);\n\n return filteredFoldersWithPermissions;\n }\n\n invalidateFoldersCache(folderType?: string) {\n if (folderType) {\n if (folderType in this.allFolders) {\n delete this.allFolders[folderType];\n }\n } else {\n this.allFolders = {};\n }\n }\n\n invalidateFoldersPermissionsListCache(folderType?: string) {\n if (folderType) {\n if (folderType in this.foldersPermissionsLists) {\n delete this.foldersPermissionsLists[folderType];\n }\n } else {\n this.allFolders = {};\n }\n }\n\n updateFoldersCache(folderType: string, modifier: (folders: Folder[]) => Folder[]) {\n const foldersClone = structuredClone(this.allFolders[folderType]) || [];\n this.allFolders[folderType] = modifier(foldersClone);\n }\n\n async listFoldersPermissions(\n params: ListFolderPermissionsParams\n ): Promise<FolderPermissionsList> {\n const existingFoldersPermissionsList = this.foldersPermissionsLists[params.folderType];\n if (existingFoldersPermissionsList) {\n return existingFoldersPermissionsList;\n }\n\n this.foldersPermissionsLists[params.folderType] = new Promise(async resolve => {\n if (!this.canUseFolderLevelPermissions() || !this.isAuthorizationEnabled()) {\n resolve([]);\n return;\n // return [];\n }\n\n const { folderType, foldersList } = params;\n\n const allFolders = foldersList || (await this.listAllFolders(folderType));\n const identity = this.getIdentity();\n const permissions = await this.listPermissions();\n\n let identityTeam: Team | null;\n if (this.canUseTeams()) {\n identityTeam = await this.getIdentityTeam();\n }\n\n const processedFolderPermissions: FolderPermissionsListItem[] = [];\n\n const processFolderPermissions = (folder: Folder) => {\n if (processedFolderPermissions.some(fp => fp.folderId === folder.id)) {\n return;\n }\n\n // Copy permissions, so we don't modify the original object.\n const currentFolderPermissions: FolderPermissionsListItem = {\n folderId: folder.id,\n // On new folders, permissions can be `null`. Guard against that.\n permissions: folder.permissions?.map(permission => ({ ...permission })) || []\n };\n\n // Check for permissions inherited from parent folder.\n if (folder.parentId) {\n const parentFolder = allFolders!.find(f => f.id === folder.parentId)!;\n if (parentFolder) {\n // First check if the parent folder has already been processed.\n let processedParentFolderPermissions = processedFolderPermissions.find(\n fp => fp.folderId === parentFolder.id\n );\n\n // If not, process the parent folder.\n if (!processedParentFolderPermissions) {\n processFolderPermissions(parentFolder);\n processedParentFolderPermissions = processedFolderPermissions.find(\n fp => fp.folderId === folder.parentId\n );\n }\n\n // If the parent folder has permissions, let's add them to the current folder.\n if (processedParentFolderPermissions) {\n const isPublicParentFolder =\n processedParentFolderPermissions.permissions.some(\n p => p.level === \"public\"\n );\n\n // We inherit parent permissions if:\n // 1. the parent folder is not public or...\n // 2. ...the parent folder is public, but the current folder doesn't have any permissions set\n const mustInherit =\n !isPublicParentFolder ||\n currentFolderPermissions.permissions.length === 0;\n\n if (mustInherit) {\n const inheritedPermissions =\n processedParentFolderPermissions.permissions.map(p => {\n return {\n ...p,\n inheritedFrom:\n \"parent:\" +\n processedParentFolderPermissions!.folderId\n };\n });\n\n currentFolderPermissions.permissions.push(...inheritedPermissions);\n }\n }\n }\n }\n\n // Let's ensure current identity's permission is included in the permissions array.\n // We first check if the current identity is already included in the permissions array.\n // If not, we check if the user has full access or if the team user belongs to has access.\n const currentIdentityIncludedInPermissions =\n currentFolderPermissions.permissions.some(\n p => p.target === `admin:${identity.id}`\n );\n\n const hasFullAccess = permissions.some(p => p.name === \"*\");\n\n if (currentIdentityIncludedInPermissions) {\n // 1. Ensure existing identity permission is always the first one in the array.\n const currentIdentityPermissionIndex =\n currentFolderPermissions.permissions.findIndex(\n p => p.target === `admin:${identity.id}`\n );\n\n if (currentIdentityPermissionIndex > 0) {\n const [currentIdentityPermission] =\n currentFolderPermissions.permissions.splice(\n currentIdentityPermissionIndex,\n 1\n );\n currentFolderPermissions.permissions.unshift(currentIdentityPermission);\n }\n\n // 2. We must ensure current identity has the \"owner\" level if they possess full access\n // based on security permissions. This protects us from non-full-access users restricting\n // access to full-access users. This should not happen. Full-access users should always\n // be in control of the permissions for a folder.\n if (hasFullAccess) {\n const accessInheritedFrom =\n currentFolderPermissions.permissions[0].inheritedFrom;\n\n // Why are we checking for non-existence of `accessInheritedFrom`?\n // Because if it doesn't exist, it means the permission is not inherited from\n // a parent folder, which means it's a direct permission set on the folder.\n // In this case, we must ensure the permission is set to \"owner\".\n if (!accessInheritedFrom) {\n currentFolderPermissions.permissions[0] = {\n target: `admin:${identity.id}`,\n level: \"owner\",\n inheritedFrom: \"role:full-access\"\n };\n }\n }\n } else {\n // Current identity not included in permissions? Let's add it.\n let currentIdentityPermission: FolderPermission | null = null;\n\n // 1. Check if the user has full access.\n if (hasFullAccess) {\n currentIdentityPermission = {\n target: `admin:${identity.id}`,\n level: \"owner\",\n inheritedFrom: \"role:full-access\"\n };\n } else if (identityTeam) {\n // 2. Check the team user belongs to grants access to the folder.\n const teamPermission = currentFolderPermissions.permissions.find(\n p => p.target === `team:${identityTeam!.id}`\n );\n\n if (teamPermission) {\n currentIdentityPermission = {\n target: `admin:${identity.id}`,\n level: teamPermission.level,\n inheritedFrom: \"team:\" + identityTeam!.id\n };\n }\n }\n\n if (currentIdentityPermission) {\n // If permission is found, let's add it to the beginning of the array.\n // We're doing this just because it looks nicer in the UI.\n currentFolderPermissions.permissions.unshift(currentIdentityPermission);\n }\n }\n\n // Note that this can only happen with root folders. All other (child) folders will\n // always have at least one permission (inherited from parent).\n const mustAddPublicPermission = currentFolderPermissions.permissions.length === 0;\n if (mustAddPublicPermission) {\n currentFolderPermissions.permissions = [\n {\n target: `admin:${identity.id}`,\n level: \"public\",\n inheritedFrom: \"public\"\n }\n ];\n }\n\n processedFolderPermissions.push(currentFolderPermissions);\n };\n\n for (let i = 0; i < allFolders!.length; i++) {\n const folder = allFolders![i];\n processFolderPermissions(folder);\n }\n\n resolve(processedFolderPermissions);\n return;\n //return processedFolderPermissions;\n });\n\n return this.foldersPermissionsLists[params.folderType]!;\n }\n\n async getFolderPermissions(\n params: GetFolderPermissionsParams\n ): Promise<FolderPermissionsListItem | undefined> {\n const { folder, foldersList } = params;\n const folderPermissionsList = await this.listFoldersPermissions({\n folderType: folder.type,\n foldersList\n });\n\n return folderPermissionsList.find(fp => fp.folderId === folder.id);\n }\n\n async canAccessFolder(params: CanAccessFolderParams) {\n if (!this.canUseFolderLevelPermissions() || !this.isAuthorizationEnabled()) {\n return true;\n }\n\n const { folder } = params;\n\n const folderPermissions = await this.getFolderPermissions({\n folder,\n foldersList: params.foldersList\n });\n\n const identity = this.getIdentity();\n const currentIdentityPermission = folderPermissions?.permissions.find(p => {\n return p.target === `admin:${identity.id}`;\n });\n\n if (!currentIdentityPermission) {\n return false;\n }\n\n const { level } = currentIdentityPermission;\n\n if (params.managePermissions) {\n return level === \"owner\";\n }\n\n // Checking for \"write\" or \"delete\" access. Allow only if the\n // user is an owner or the folder is public (no FLP assigned).\n if (params.rwd !== \"r\") {\n return level === \"owner\" || level === \"public\";\n }\n\n return true;\n }\n\n async ensureCanAccessFolder(params: CanAccessFolderParams) {\n const canAccessFolder = await this.canAccessFolder(params);\n if (!canAccessFolder) {\n throw new NotAuthorizedError();\n }\n }\n\n canManageFolderPermissions(folder: Folder) {\n if (!this.canUseFolderLevelPermissions()) {\n return false;\n }\n\n if (!this.isAuthorizationEnabled()) {\n return true;\n }\n\n return this.canAccessFolder({ folder, rwd: \"w\", managePermissions: true });\n }\n\n canManageFolderStructure(folder: Folder) {\n if (!this.canUseFolderLevelPermissions() || !this.isAuthorizationEnabled()) {\n return true;\n }\n\n return this.canAccessFolder({ folder, rwd: \"w\" });\n }\n\n canManageFolderContent(folder: Folder) {\n if (!this.canUseFolderLevelPermissions() || !this.isAuthorizationEnabled()) {\n return true;\n }\n\n return this.canAccessFolderContent({ folder, rwd: \"w\" });\n }\n\n async canAccessFolderContent(params: CanAccessFolderContentParams) {\n if (!this.canUseFolderLevelPermissions() || !this.isAuthorizationEnabled()) {\n return true;\n }\n\n const { folder, foldersList } = params;\n\n const folderPermissions = await this.getFolderPermissions({\n folder,\n foldersList\n });\n\n const identity = this.getIdentity();\n const currentIdentityPermission = folderPermissions?.permissions.find(p => {\n return p.target === `admin:${identity.id}`;\n });\n\n if (!currentIdentityPermission) {\n return false;\n }\n\n // If the user is not an owner and we're checking for \"write\" or\n // \"delete\" access, then we can immediately return false.\n if (params.rwd !== \"r\") {\n const { level } = currentIdentityPermission;\n return level !== \"viewer\";\n }\n\n return true;\n }\n\n async ensureCanAccessFolderContent(params: CanAccessFolderContentParams) {\n const canAccessFolderContent = await this.canAccessFolderContent(params);\n if (!canAccessFolderContent) {\n throw new NotAuthorizedError();\n }\n }\n\n async canCreateFolderInRoot() {\n return true;\n }\n\n async filterFolders(params: FilterFoldersParams) {\n const filteredFolders: Folder[] = [];\n\n const { folders, rwd } = params;\n for (let i = 0; i < folders.length; i++) {\n const folder = folders[i];\n const canAccessFolder = await this.canAccessFolder({ folder, rwd });\n if (canAccessFolder) {\n filteredFolders.push(folder);\n }\n }\n\n return filteredFolders;\n }\n\n async assignFolderPermissions(folder: Folder | Folder[]) {\n const folders = Array.isArray(folder) ? folder : [folder];\n\n for (let i = 0; i < folders.length; i++) {\n const folder = folders[i];\n const folderPermissions = await this.getFolderPermissions({ folder });\n if (folderPermissions) {\n folder.permissions = folderPermissions.permissions;\n } else {\n folder.permissions = [];\n }\n }\n }\n\n permissionsIncludeNonInheritedPermissions(folderPermissionsList?: FolderPermission[]) {\n return folderPermissionsList?.some(p => !p.inheritedFrom);\n }\n}\n"],"mappings":"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","ignoreList":[]}
1
+ {"version":3,"names":["_apiSecurity","require","FolderLevelPermissions","allFolders","foldersPermissionsLists","constructor","params","getIdentity","listIdentityTeams","listPermissions","listAllFoldersCallback","listAllFolders","canUseTeams","canUseFolderLevelPermissions","identity","type","isAuthorizationEnabled","folderType","structuredClone","listAllFoldersWithPermissions","folders","filteredFoldersWithPermissions","filterFolders","rwd","assignFolderPermissions","invalidateFoldersCache","invalidateFoldersPermissionsListCache","updateFoldersCache","modifier","foldersClone","listFoldersPermissions","existingFoldersPermissionsList","Promise","resolve","foldersList","permissions","identityTeams","processedFolderPermissions","processFolderPermissions","folder","some","fp","folderId","id","currentFolderPermissions","map","permission","parentId","parentFolder","find","f","processedParentFolderPermissions","isPublicParentFolder","p","level","mustInherit","length","inheritedPermissions","inheritedFrom","push","currentIdentityIncludedInPermissions","target","hasFullAccess","name","currentIdentityPermissionIndex","findIndex","currentIdentityPermission","splice","unshift","accessInheritedFrom","identityTeam","teamPermission","mustAddPublicPermission","i","getFolderPermissions","folderPermissionsList","canAccessFolder","folderPermissions","managePermissions","ensureCanAccessFolder","NotAuthorizedError","canManageFolderPermissions","canManageFolderStructure","canManageFolderContent","canAccessFolderContent","ensureCanAccessFolderContent","canCreateFolderInRoot","filteredFolders","Array","isArray","permissionsIncludeNonInheritedPermissions","exports"],"sources":["FolderLevelPermissions.ts"],"sourcesContent":["import { Authentication } from \"@webiny/api-authentication/types\";\nimport { SecurityPermission, Team } from \"@webiny/api-security/types\";\nimport { Folder } from \"~/folder/folder.types\";\nimport { NotAuthorizedError } from \"@webiny/api-security\";\n\nexport type FolderAccessLevel = \"owner\" | \"viewer\" | \"editor\" | \"public\";\n\nexport interface FolderPermission {\n target: string;\n level: FolderAccessLevel;\n inheritedFrom?: string;\n}\n\nexport interface FolderPermissionsListItem {\n folderId: string;\n permissions: FolderPermission[];\n}\n\nexport type FolderPermissionsList = FolderPermissionsListItem[];\n\nexport interface CanAccessFolderContentParams {\n folder: Pick<Folder, \"id\" | \"type\" | \"parentId\">;\n rwd?: \"r\" | \"w\" | \"d\";\n foldersList?: Folder[];\n}\n\nexport interface CanAccessFolderParams extends CanAccessFolderContentParams {\n managePermissions?: boolean;\n}\n\ninterface FilterFoldersParams {\n folders: Array<Folder>;\n rwd?: \"r\" | \"w\" | \"d\";\n}\n\ninterface GetFolderPermissionsParams {\n folder: Pick<Folder, \"id\" | \"type\">;\n foldersList?: Folder[];\n}\n\ninterface ListFolderPermissionsParams {\n folderType: string;\n foldersList?: Folder[];\n}\n\nexport interface FolderLevelPermissionsParams {\n getIdentity: Authentication[\"getIdentity\"];\n listIdentityTeams: () => Promise<Team[]>;\n listPermissions: () => Promise<SecurityPermission[]>;\n listAllFolders: (folderType: string) => Promise<Folder[]>;\n canUseTeams: () => boolean;\n canUseFolderLevelPermissions: () => boolean;\n isAuthorizationEnabled: () => boolean;\n}\n\nexport class FolderLevelPermissions {\n canUseFolderLevelPermissions: () => boolean;\n\n private readonly getIdentity: Authentication[\"getIdentity\"];\n private readonly listIdentityTeams: () => Promise<Team[]>;\n private readonly listPermissions: () => Promise<SecurityPermission[]>;\n private readonly listAllFoldersCallback: (folderType: string) => Promise<Folder[]>;\n private readonly canUseTeams: () => boolean;\n private readonly isAuthorizationEnabled: () => boolean;\n private allFolders: Record<string, Folder[]> = {};\n private foldersPermissionsLists: Record<string, Promise<FolderPermissionsList> | null> = {};\n\n constructor(params: FolderLevelPermissionsParams) {\n this.getIdentity = params.getIdentity;\n this.listIdentityTeams = params.listIdentityTeams;\n this.listPermissions = params.listPermissions;\n this.listAllFoldersCallback = params.listAllFolders;\n this.canUseTeams = params.canUseTeams;\n this.canUseFolderLevelPermissions = () => {\n const identity = this.getIdentity();\n\n // FLPs only work with authenticated identities (logged-in users).\n if (!identity) {\n return false;\n }\n\n // At the moment, we only want FLP to be used with identities of type \"admin\".\n // This temporarily addresses the issue of API keys not being able to access content, because\n // FLPs doesn't work with them. Once we start adding FLPs to API keys, we can remove this check.\n if (identity.type !== \"admin\") {\n return false;\n }\n\n return params.canUseFolderLevelPermissions();\n };\n\n this.isAuthorizationEnabled = params.isAuthorizationEnabled;\n }\n\n async listAllFolders(folderType: string): Promise<Folder[]> {\n if (folderType in this.allFolders) {\n return structuredClone(this.allFolders[folderType]);\n }\n\n this.allFolders[folderType] = await this.listAllFoldersCallback(folderType);\n return structuredClone(this.allFolders[folderType]);\n }\n\n async listAllFoldersWithPermissions(folderType: string) {\n const folders = await this.listAllFolders(folderType);\n\n // Filter folders based on permissions and assign permissions to each folder.\n const filteredFoldersWithPermissions = await this.filterFolders({\n folders,\n rwd: \"r\"\n });\n\n await this.assignFolderPermissions(filteredFoldersWithPermissions);\n\n return filteredFoldersWithPermissions;\n }\n\n invalidateFoldersCache(folderType?: string) {\n if (folderType) {\n if (folderType in this.allFolders) {\n delete this.allFolders[folderType];\n }\n } else {\n this.allFolders = {};\n }\n }\n\n invalidateFoldersPermissionsListCache(folderType?: string) {\n if (folderType) {\n if (folderType in this.foldersPermissionsLists) {\n delete this.foldersPermissionsLists[folderType];\n }\n } else {\n this.allFolders = {};\n }\n }\n\n updateFoldersCache(folderType: string, modifier: (folders: Folder[]) => Folder[]) {\n const foldersClone = structuredClone(this.allFolders[folderType]) || [];\n this.allFolders[folderType] = modifier(foldersClone);\n }\n\n async listFoldersPermissions(\n params: ListFolderPermissionsParams\n ): Promise<FolderPermissionsList> {\n const existingFoldersPermissionsList = this.foldersPermissionsLists[params.folderType];\n if (existingFoldersPermissionsList) {\n return existingFoldersPermissionsList;\n }\n\n this.foldersPermissionsLists[params.folderType] = new Promise(async resolve => {\n if (!this.canUseFolderLevelPermissions() || !this.isAuthorizationEnabled()) {\n resolve([]);\n return;\n }\n\n const { folderType, foldersList } = params;\n\n const allFolders = foldersList || (await this.listAllFolders(folderType));\n const identity = this.getIdentity();\n const permissions = await this.listPermissions();\n\n let identityTeams: Team[];\n if (this.canUseTeams()) {\n identityTeams = await this.listIdentityTeams();\n }\n\n const processedFolderPermissions: FolderPermissionsListItem[] = [];\n\n const processFolderPermissions = (folder: Folder) => {\n if (processedFolderPermissions.some(fp => fp.folderId === folder.id)) {\n return;\n }\n\n // Copy permissions, so we don't modify the original object.\n const currentFolderPermissions: FolderPermissionsListItem = {\n folderId: folder.id,\n // On new folders, permissions can be `null`. Guard against that.\n permissions: folder.permissions?.map(permission => ({ ...permission })) || []\n };\n\n // Check for permissions inherited from parent folder.\n if (folder.parentId) {\n const parentFolder = allFolders!.find(f => f.id === folder.parentId)!;\n if (parentFolder) {\n // First check if the parent folder has already been processed.\n let processedParentFolderPermissions = processedFolderPermissions.find(\n fp => fp.folderId === parentFolder.id\n );\n\n // If not, process the parent folder.\n if (!processedParentFolderPermissions) {\n processFolderPermissions(parentFolder);\n processedParentFolderPermissions = processedFolderPermissions.find(\n fp => fp.folderId === folder.parentId\n );\n }\n\n // If the parent folder has permissions, let's add them to the current folder.\n if (processedParentFolderPermissions) {\n const isPublicParentFolder =\n processedParentFolderPermissions.permissions.some(\n p => p.level === \"public\"\n );\n\n // We inherit parent permissions if:\n // 1. the parent folder is not public or...\n // 2. ...the parent folder is public, but the current folder doesn't have any permissions set\n const mustInherit =\n !isPublicParentFolder ||\n currentFolderPermissions.permissions.length === 0;\n\n if (mustInherit) {\n const inheritedPermissions =\n processedParentFolderPermissions.permissions.map(p => {\n return {\n ...p,\n inheritedFrom:\n \"parent:\" +\n processedParentFolderPermissions!.folderId\n };\n });\n\n currentFolderPermissions.permissions.push(...inheritedPermissions);\n }\n }\n }\n }\n\n // Let's ensure current identity's permission is included in the permissions array.\n // We first check if the current identity is already included in the permissions array.\n // If not, we check if the user has full access or if the team user belongs to has access.\n const currentIdentityIncludedInPermissions =\n currentFolderPermissions.permissions.some(\n p => p.target === `admin:${identity.id}`\n );\n\n const hasFullAccess = permissions.some(p => p.name === \"*\");\n\n if (currentIdentityIncludedInPermissions) {\n // 1. Ensure existing identity permission is always the first one in the array.\n const currentIdentityPermissionIndex =\n currentFolderPermissions.permissions.findIndex(\n p => p.target === `admin:${identity.id}`\n );\n\n if (currentIdentityPermissionIndex > 0) {\n const [currentIdentityPermission] =\n currentFolderPermissions.permissions.splice(\n currentIdentityPermissionIndex,\n 1\n );\n currentFolderPermissions.permissions.unshift(currentIdentityPermission);\n }\n\n // 2. We must ensure current identity has the \"owner\" level if they possess full access\n // based on security permissions. This protects us from non-full-access users restricting\n // access to full-access users. This should not happen. Full-access users should always\n // be in control of the permissions for a folder.\n if (hasFullAccess) {\n const accessInheritedFrom =\n currentFolderPermissions.permissions[0].inheritedFrom;\n\n // Why are we checking for non-existence of `accessInheritedFrom`?\n // Because if it doesn't exist, it means the permission is not inherited from\n // a parent folder, which means it's a direct permission set on the folder.\n // In this case, we must ensure the permission is set to \"owner\".\n if (!accessInheritedFrom) {\n currentFolderPermissions.permissions[0] = {\n target: `admin:${identity.id}`,\n level: \"owner\",\n inheritedFrom: \"role:full-access\"\n };\n }\n }\n } else {\n // Current identity not included in permissions? Let's add it.\n let currentIdentityPermission: FolderPermission | null = null;\n\n // 1. Check if the user has full access.\n if (hasFullAccess) {\n currentIdentityPermission = {\n target: `admin:${identity.id}`,\n level: \"owner\",\n inheritedFrom: \"role:full-access\"\n };\n } else if (identityTeams.length) {\n // 2. Check the teams user belongs to and that grant access to the folder.\n for (const identityTeam of identityTeams) {\n const teamPermission = currentFolderPermissions.permissions.find(\n p => p.target === `team:${identityTeam!.id}`\n );\n\n if (teamPermission) {\n currentIdentityPermission = {\n target: `admin:${identity.id}`,\n level: teamPermission.level,\n inheritedFrom: \"team:\" + identityTeam!.id\n };\n }\n }\n }\n\n if (currentIdentityPermission) {\n // If permission is found, let's add it to the beginning of the array.\n // We're doing this just because it looks nicer in the UI.\n currentFolderPermissions.permissions.unshift(currentIdentityPermission);\n }\n }\n\n // Note that this can only happen with root folders. All other (child) folders will\n // always have at least one permission (inherited from parent).\n const mustAddPublicPermission = currentFolderPermissions.permissions.length === 0;\n if (mustAddPublicPermission) {\n currentFolderPermissions.permissions = [\n {\n target: `admin:${identity.id}`,\n level: \"public\",\n inheritedFrom: \"public\"\n }\n ];\n }\n\n processedFolderPermissions.push(currentFolderPermissions);\n };\n\n for (let i = 0; i < allFolders!.length; i++) {\n const folder = allFolders![i];\n processFolderPermissions(folder);\n }\n\n resolve(processedFolderPermissions);\n return;\n //return processedFolderPermissions;\n });\n\n return this.foldersPermissionsLists[params.folderType]!;\n }\n\n async getFolderPermissions(\n params: GetFolderPermissionsParams\n ): Promise<FolderPermissionsListItem | undefined> {\n const { folder, foldersList } = params;\n const folderPermissionsList = await this.listFoldersPermissions({\n folderType: folder.type,\n foldersList\n });\n\n return folderPermissionsList.find(fp => fp.folderId === folder.id);\n }\n\n async canAccessFolder(params: CanAccessFolderParams) {\n if (!this.canUseFolderLevelPermissions() || !this.isAuthorizationEnabled()) {\n return true;\n }\n\n const { folder } = params;\n\n const folderPermissions = await this.getFolderPermissions({\n folder,\n foldersList: params.foldersList\n });\n\n const identity = this.getIdentity();\n const currentIdentityPermission = folderPermissions?.permissions.find(p => {\n return p.target === `admin:${identity.id}`;\n });\n\n if (!currentIdentityPermission) {\n return false;\n }\n\n const { level } = currentIdentityPermission;\n\n if (params.managePermissions) {\n return level === \"owner\";\n }\n\n // Checking for \"write\" or \"delete\" access. Allow only if the\n // user is an owner or the folder is public (no FLP assigned).\n if (params.rwd !== \"r\") {\n return level === \"owner\" || level === \"public\";\n }\n\n return true;\n }\n\n async ensureCanAccessFolder(params: CanAccessFolderParams) {\n const canAccessFolder = await this.canAccessFolder(params);\n if (!canAccessFolder) {\n throw new NotAuthorizedError();\n }\n }\n\n canManageFolderPermissions(folder: Folder) {\n if (!this.canUseFolderLevelPermissions()) {\n return false;\n }\n\n if (!this.isAuthorizationEnabled()) {\n return true;\n }\n\n return this.canAccessFolder({ folder, rwd: \"w\", managePermissions: true });\n }\n\n canManageFolderStructure(folder: Folder) {\n if (!this.canUseFolderLevelPermissions() || !this.isAuthorizationEnabled()) {\n return true;\n }\n\n return this.canAccessFolder({ folder, rwd: \"w\" });\n }\n\n canManageFolderContent(folder: Folder) {\n if (!this.canUseFolderLevelPermissions() || !this.isAuthorizationEnabled()) {\n return true;\n }\n\n return this.canAccessFolderContent({ folder, rwd: \"w\" });\n }\n\n async canAccessFolderContent(params: CanAccessFolderContentParams) {\n if (!this.canUseFolderLevelPermissions() || !this.isAuthorizationEnabled()) {\n return true;\n }\n\n const { folder, foldersList } = params;\n\n const folderPermissions = await this.getFolderPermissions({\n folder,\n foldersList\n });\n\n const identity = this.getIdentity();\n const currentIdentityPermission = folderPermissions?.permissions.find(p => {\n return p.target === `admin:${identity.id}`;\n });\n\n if (!currentIdentityPermission) {\n return false;\n }\n\n // If the user is not an owner and we're checking for \"write\" or\n // \"delete\" access, then we can immediately return false.\n if (params.rwd !== \"r\") {\n const { level } = currentIdentityPermission;\n return level !== \"viewer\";\n }\n\n return true;\n }\n\n async ensureCanAccessFolderContent(params: CanAccessFolderContentParams) {\n const canAccessFolderContent = await this.canAccessFolderContent(params);\n if (!canAccessFolderContent) {\n throw new NotAuthorizedError();\n }\n }\n\n async canCreateFolderInRoot() {\n return true;\n }\n\n async filterFolders(params: FilterFoldersParams) {\n const filteredFolders: Folder[] = [];\n\n const { folders, rwd } = params;\n for (let i = 0; i < folders.length; i++) {\n const folder = folders[i];\n const canAccessFolder = await this.canAccessFolder({ folder, rwd });\n if (canAccessFolder) {\n filteredFolders.push(folder);\n }\n }\n\n return filteredFolders;\n }\n\n async assignFolderPermissions(folder: Folder | Folder[]) {\n const folders = Array.isArray(folder) ? folder : [folder];\n\n for (let i = 0; i < folders.length; i++) {\n const folder = folders[i];\n const folderPermissions = await this.getFolderPermissions({ folder });\n if (folderPermissions) {\n folder.permissions = folderPermissions.permissions;\n } else {\n folder.permissions = [];\n }\n }\n }\n\n permissionsIncludeNonInheritedPermissions(folderPermissionsList?: FolderPermission[]) {\n return folderPermissionsList?.some(p => !p.inheritedFrom);\n }\n}\n"],"mappings":"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","ignoreList":[]}
@@ -1,2 +1,3 @@
1
1
  import { ListSort } from "../types";
2
- export declare const createListSort: (sort?: ListSort) => string[] | undefined;
2
+ import { CmsEntryListSort } from "@webiny/api-headless-cms/types";
3
+ export declare const createListSort: (sort?: ListSort) => CmsEntryListSort | undefined;
@@ -8,7 +8,9 @@ const createListSort = sort => {
8
8
  if (!sort) {
9
9
  return;
10
10
  }
11
- return Object.keys(sort).map(key => `${key}_${sort[key]}`);
11
+ return Object.keys(sort).map(key => {
12
+ return `${key}_${sort[key]}`;
13
+ });
12
14
  };
13
15
  exports.createListSort = createListSort;
14
16
 
@@ -1 +1 @@
1
- {"version":3,"names":["createListSort","sort","Object","keys","map","key","exports"],"sources":["createListSort.ts"],"sourcesContent":["import { ListSort } from \"~/types\";\n\nexport const createListSort = (sort?: ListSort): string[] | undefined => {\n if (!sort) {\n return;\n }\n\n return Object.keys(sort).map(key => `${key}_${sort[key]}`);\n};\n"],"mappings":";;;;;;AAEO,MAAMA,cAAc,GAAIC,IAAe,IAA2B;EACrE,IAAI,CAACA,IAAI,EAAE;IACP;EACJ;EAEA,OAAOC,MAAM,CAACC,IAAI,CAACF,IAAI,CAAC,CAACG,GAAG,CAACC,GAAG,IAAK,GAAEA,GAAI,IAAGJ,IAAI,CAACI,GAAG,CAAE,EAAC,CAAC;AAC9D,CAAC;AAACC,OAAA,CAAAN,cAAA,GAAAA,cAAA","ignoreList":[]}
1
+ {"version":3,"names":["createListSort","sort","Object","keys","map","key","exports"],"sources":["createListSort.ts"],"sourcesContent":["import { ListSort } from \"~/types\";\nimport {\n CmsEntryListSort,\n CmsEntryListSortAsc,\n CmsEntryListSortDesc\n} from \"@webiny/api-headless-cms/types\";\n\nexport const createListSort = (sort?: ListSort): CmsEntryListSort | undefined => {\n if (!sort) {\n return;\n }\n\n return Object.keys(sort).map(key => {\n return `${key}_${sort[key]}` as CmsEntryListSortAsc | CmsEntryListSortDesc;\n });\n};\n"],"mappings":";;;;;;AAOO,MAAMA,cAAc,GAAIC,IAAe,IAAmC;EAC7E,IAAI,CAACA,IAAI,EAAE;IACP;EACJ;EAEA,OAAOC,MAAM,CAACC,IAAI,CAACF,IAAI,CAAC,CAACG,GAAG,CAACC,GAAG,IAAI;IAChC,OAAQ,GAAEA,GAAI,IAAGJ,IAAI,CAACI,GAAG,CAAE,EAAC;EAChC,CAAC,CAAC;AACN,CAAC;AAACC,OAAA,CAAAN,cAAA,GAAAA,cAAA","ignoreList":[]}
@@ -14,7 +14,7 @@ type FilterModelMethods<T> = {
14
14
  * E.g., `getEntryManager` has `model` typed as `CmsModel | string`.
15
15
  * Ideally, we would filter those out in the previous utility type, but I'm not sure how to achieve that.
16
16
  */
17
- type ModelMethods<T> = Omit<FilterModelMethods<T>, "getEntryManager">;
17
+ type ModelMethods<T> = Omit<FilterModelMethods<T>, "getEntryManager" | "getSingletonEntryManager">;
18
18
  /**
19
19
  * Decorator takes the decoratee as the _first_ parameter, and then forwards the rest of the parameters.
20
20
  */
@@ -1 +1 @@
1
- {"version":3,"names":["modelAuthorizationDisabled","model","authorization","flp","decorateIfModelAuthorizationEnabled","root","method","decorator","decoratee","bind","params","rest","exports"],"sources":["decorateIfModelAuthorizationEnabled.ts"],"sourcesContent":["import { CmsModel, HeadlessCms } from \"@webiny/api-headless-cms/types\";\n\n/**\n * This type matches any function that has a CmsModel as the first parameter.\n */\ntype ModelCallable = (model: CmsModel, ...params: any[]) => any;\n\n/**\n * This type filters only `ModelCallable` methods.\n */\ntype FilterModelMethods<T> = {\n [K in keyof T as ModelCallable extends T[K] ? K : never]: T[K];\n};\n\n/**\n * This type omits methods that have a more complex `model` type.\n * E.g., `getEntryManager` has `model` typed as `CmsModel | string`.\n * Ideally, we would filter those out in the previous utility type, but I'm not sure how to achieve that.\n */\ntype ModelMethods<T> = Omit<FilterModelMethods<T>, \"getEntryManager\">;\n\n/**\n * Decorator takes the decoratee as the _first_ parameter, and then forwards the rest of the parameters.\n */\ntype Decorator<T extends ModelCallable> = (decoratee: T, ...args: Parameters<T>) => ReturnType<T>;\n\nconst modelAuthorizationDisabled = (model: CmsModel) => {\n if (typeof model.authorization === \"object\") {\n return model?.authorization?.flp === false;\n }\n\n return model.authorization === false;\n};\n\nexport const decorateIfModelAuthorizationEnabled = <\n /**\n * This allows us to only have an auto-complete of `ModelCallable` methods.\n */\n M extends keyof ModelMethods<HeadlessCms>,\n D extends Decorator<ModelMethods<HeadlessCms>[M]>\n>(\n root: ModelMethods<HeadlessCms>,\n method: M,\n decorator: D\n) => {\n /**\n * We cast to `ModelCallable` because within the generic function, we only know that the first\n * parameter is a `CmsModel`, and we forward the rest.\n */\n const decoratee = root[method].bind(root) as ModelCallable;\n root[method] = ((...params: Parameters<ModelMethods<HeadlessCms>[M]>) => {\n const [model, ...rest] = params;\n if (modelAuthorizationDisabled(model)) {\n return decoratee(model, ...rest);\n }\n\n return decorator(decoratee, ...params);\n }) as ModelCallable;\n};\n"],"mappings":";;;;;;AAEA;AACA;AACA;;AAGA;AACA;AACA;;AAKA;AACA;AACA;AACA;AACA;;AAGA;AACA;AACA;;AAGA,MAAMA,0BAA0B,GAAIC,KAAe,IAAK;EACpD,IAAI,OAAOA,KAAK,CAACC,aAAa,KAAK,QAAQ,EAAE;IACzC,OAAOD,KAAK,EAAEC,aAAa,EAAEC,GAAG,KAAK,KAAK;EAC9C;EAEA,OAAOF,KAAK,CAACC,aAAa,KAAK,KAAK;AACxC,CAAC;AAEM,MAAME,mCAAmC,GAAGA,CAO/CC,IAA+B,EAC/BC,MAAS,EACTC,SAAY,KACX;EACD;AACJ;AACA;AACA;EACI,MAAMC,SAAS,GAAGH,IAAI,CAACC,MAAM,CAAC,CAACG,IAAI,CAACJ,IAAI,CAAkB;EAC1DA,IAAI,CAACC,MAAM,CAAC,GAAI,CAAC,GAAGI,MAAgD,KAAK;IACrE,MAAM,CAACT,KAAK,EAAE,GAAGU,IAAI,CAAC,GAAGD,MAAM;IAC/B,IAAIV,0BAA0B,CAACC,KAAK,CAAC,EAAE;MACnC,OAAOO,SAAS,CAACP,KAAK,EAAE,GAAGU,IAAI,CAAC;IACpC;IAEA,OAAOJ,SAAS,CAACC,SAAS,EAAE,GAAGE,MAAM,CAAC;EAC1C,CAAmB;AACvB,CAAC;AAACE,OAAA,CAAAR,mCAAA,GAAAA,mCAAA","ignoreList":[]}
1
+ {"version":3,"names":["modelAuthorizationDisabled","model","authorization","flp","decorateIfModelAuthorizationEnabled","root","method","decorator","decoratee","bind","params","rest","exports"],"sources":["decorateIfModelAuthorizationEnabled.ts"],"sourcesContent":["import { CmsModel, HeadlessCms } from \"@webiny/api-headless-cms/types\";\n\n/**\n * This type matches any function that has a CmsModel as the first parameter.\n */\ntype ModelCallable = (model: CmsModel, ...params: any[]) => any;\n\n/**\n * This type filters only `ModelCallable` methods.\n */\ntype FilterModelMethods<T> = {\n [K in keyof T as ModelCallable extends T[K] ? K : never]: T[K];\n};\n\n/**\n * This type omits methods that have a more complex `model` type.\n * E.g., `getEntryManager` has `model` typed as `CmsModel | string`.\n * Ideally, we would filter those out in the previous utility type, but I'm not sure how to achieve that.\n */\ntype ModelMethods<T> = Omit<FilterModelMethods<T>, \"getEntryManager\" | \"getSingletonEntryManager\">;\n\n/**\n * Decorator takes the decoratee as the _first_ parameter, and then forwards the rest of the parameters.\n */\ntype Decorator<T extends ModelCallable> = (decoratee: T, ...args: Parameters<T>) => ReturnType<T>;\n\nconst modelAuthorizationDisabled = (model: CmsModel) => {\n if (typeof model.authorization === \"object\") {\n return model?.authorization?.flp === false;\n }\n\n return model.authorization === false;\n};\n\nexport const decorateIfModelAuthorizationEnabled = <\n /**\n * This allows us to only have an auto-complete of `ModelCallable` methods.\n */\n M extends keyof ModelMethods<HeadlessCms>,\n D extends Decorator<ModelMethods<HeadlessCms>[M]>\n>(\n root: ModelMethods<HeadlessCms>,\n method: M,\n decorator: D\n) => {\n /**\n * We cast to `ModelCallable` because within the generic function, we only know that the first\n * parameter is a `CmsModel`, and we forward the rest.\n */\n const decoratee = root[method].bind(root) as ModelCallable;\n root[method] = ((...params: Parameters<ModelMethods<HeadlessCms>[M]>) => {\n const [model, ...rest] = params;\n if (modelAuthorizationDisabled(model)) {\n return decoratee(model, ...rest);\n }\n\n return decorator(decoratee, ...params);\n }) as ModelCallable;\n};\n"],"mappings":";;;;;;AAEA;AACA;AACA;;AAGA;AACA;AACA;;AAKA;AACA;AACA;AACA;AACA;;AAGA;AACA;AACA;;AAGA,MAAMA,0BAA0B,GAAIC,KAAe,IAAK;EACpD,IAAI,OAAOA,KAAK,CAACC,aAAa,KAAK,QAAQ,EAAE;IACzC,OAAOD,KAAK,EAAEC,aAAa,EAAEC,GAAG,KAAK,KAAK;EAC9C;EAEA,OAAOF,KAAK,CAACC,aAAa,KAAK,KAAK;AACxC,CAAC;AAEM,MAAME,mCAAmC,GAAGA,CAO/CC,IAA+B,EAC/BC,MAAS,EACTC,SAAY,KACX;EACD;AACJ;AACA;AACA;EACI,MAAMC,SAAS,GAAGH,IAAI,CAACC,MAAM,CAAC,CAACG,IAAI,CAACJ,IAAI,CAAkB;EAC1DA,IAAI,CAACC,MAAM,CAAC,GAAI,CAAC,GAAGI,MAAgD,KAAK;IACrE,MAAM,CAACT,KAAK,EAAE,GAAGU,IAAI,CAAC,GAAGD,MAAM;IAC/B,IAAIV,0BAA0B,CAACC,KAAK,CAAC,EAAE;MACnC,OAAOO,SAAS,CAACP,KAAK,EAAE,GAAGU,IAAI,CAAC;IACpC;IAEA,OAAOJ,SAAS,CAACC,SAAS,EAAE,GAAGE,MAAM,CAAC;EAC1C,CAAmB;AACvB,CAAC;AAACE,OAAA,CAAAR,mCAAA,GAAAA,mCAAA","ignoreList":[]}
@@ -1,3 +1,3 @@
1
1
  import { ErrorResponse, ListResponse, Response } from "@webiny/handler-graphql";
2
- export declare const resolve: (fn: () => Promise<any>) => Promise<ErrorResponse | Response<any>>;
2
+ export declare const resolve: (fn: () => Promise<any>) => Promise<Response<any> | ErrorResponse>;
3
3
  export declare const resolveList: (fn: () => Promise<any>) => Promise<ErrorResponse | ListResponse<unknown, any>>;