@webiny/app-admin 6.1.0 → 6.2.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.
Files changed (126) hide show
  1. package/base/Admin.js +2 -0
  2. package/base/Admin.js.map +1 -1
  3. package/base/Base/DefaultFieldRenderers.d.ts +2 -0
  4. package/base/Base/DefaultFieldRenderers.js +15 -0
  5. package/base/Base/DefaultFieldRenderers.js.map +1 -0
  6. package/base/Base/FieldRenderers/SelectRenderer.d.ts +5 -0
  7. package/base/Base/FieldRenderers/SelectRenderer.js +24 -0
  8. package/base/Base/FieldRenderers/SelectRenderer.js.map +1 -0
  9. package/base/Base/FieldRenderers/TextRenderer.d.ts +5 -0
  10. package/base/Base/FieldRenderers/TextRenderer.js +21 -0
  11. package/base/Base/FieldRenderers/TextRenderer.js.map +1 -0
  12. package/base/Base/Menus.js +7 -0
  13. package/base/Base/Menus.js.map +1 -1
  14. package/base/Base.js +2 -1
  15. package/base/Base.js.map +1 -1
  16. package/base/createRootContainer.js +2 -0
  17. package/base/createRootContainer.js.map +1 -1
  18. package/components/Dialogs/DialogParamsContext.d.ts +6 -0
  19. package/components/Dialogs/DialogParamsContext.js +11 -0
  20. package/components/Dialogs/DialogParamsContext.js.map +1 -0
  21. package/components/Dialogs/DialogsContext.d.ts +2 -0
  22. package/components/Dialogs/DialogsContext.js +32 -4
  23. package/components/Dialogs/DialogsContext.js.map +1 -1
  24. package/components/OptionsMenu/OptionsMenu.d.ts +6 -0
  25. package/components/OptionsMenu/OptionsMenu.js +3 -3
  26. package/components/OptionsMenu/OptionsMenu.js.map +1 -1
  27. package/components/RegisterFeature.js +5 -5
  28. package/components/RegisterFeature.js.map +1 -1
  29. package/components/Wcp.d.ts +2 -0
  30. package/components/Wcp.js +7 -0
  31. package/components/Wcp.js.map +1 -1
  32. package/config/AdminConfig/Dialog.d.ts +10 -0
  33. package/config/AdminConfig/Dialog.js +21 -0
  34. package/config/AdminConfig/Dialog.js.map +1 -0
  35. package/config/AdminConfig/FieldRenderer.d.ts +11 -0
  36. package/config/AdminConfig/FieldRenderer.js +21 -0
  37. package/config/AdminConfig/FieldRenderer.js.map +1 -0
  38. package/config/AdminConfig/Form.d.ts +3 -0
  39. package/config/AdminConfig/Form.js +6 -0
  40. package/config/AdminConfig/Form.js.map +1 -0
  41. package/config/AdminConfig.d.ts +10 -0
  42. package/config/AdminConfig.js +7 -1
  43. package/config/AdminConfig.js.map +1 -1
  44. package/exports/admin/security.d.ts +6 -0
  45. package/exports/admin/security.js +5 -0
  46. package/exports/admin/security.js.map +1 -1
  47. package/exports/admin/ui.d.ts +2 -0
  48. package/exports/admin/ui.js +2 -0
  49. package/exports/admin/ui.js.map +1 -1
  50. package/exports/admin.d.ts +0 -3
  51. package/exports/admin.js +0 -3
  52. package/exports/admin.js.map +1 -1
  53. package/features/formModel/Field.d.ts +52 -0
  54. package/features/formModel/Field.js +201 -0
  55. package/features/formModel/Field.js.map +1 -0
  56. package/features/formModel/FieldBuilder.d.ts +45 -0
  57. package/features/formModel/FieldBuilder.js +158 -0
  58. package/features/formModel/FieldBuilder.js.map +1 -0
  59. package/features/formModel/FieldBuilder.test.js +106 -0
  60. package/features/formModel/FieldBuilder.test.js.map +1 -0
  61. package/features/formModel/FormModel.d.ts +61 -0
  62. package/features/formModel/FormModel.js +573 -0
  63. package/features/formModel/FormModel.js.map +1 -0
  64. package/features/formModel/FormModel.test.d.ts +1 -0
  65. package/features/formModel/FormModel.test.js +1140 -0
  66. package/features/formModel/FormModel.test.js.map +1 -0
  67. package/features/formModel/FormModelFactory.d.ts +9 -0
  68. package/features/formModel/FormModelFactory.js +13 -0
  69. package/features/formModel/FormModelFactory.js.map +1 -0
  70. package/features/formModel/FormView.d.ts +23 -0
  71. package/features/formModel/FormView.js +138 -0
  72. package/features/formModel/FormView.js.map +1 -0
  73. package/features/formModel/abstractions.d.ts +286 -0
  74. package/features/formModel/abstractions.js +54 -0
  75. package/features/formModel/abstractions.js.map +1 -0
  76. package/features/formModel/feature.d.ts +3 -0
  77. package/features/formModel/feature.js +16 -0
  78. package/features/formModel/feature.js.map +1 -0
  79. package/features/formModel/index.d.ts +10 -0
  80. package/features/formModel/index.js +14 -0
  81. package/features/formModel/index.js.map +1 -0
  82. package/features/formModel/useFieldRenderers.d.ts +2 -0
  83. package/features/formModel/useFieldRenderers.js +19 -0
  84. package/features/formModel/useFieldRenderers.js.map +1 -0
  85. package/features/security/LogIn/LogInGateway.d.ts +2 -2
  86. package/features/security/LogIn/LogInGateway.js +2 -2
  87. package/features/security/LogIn/LogInGateway.js.map +1 -1
  88. package/features/wcp/WcpGateway.d.ts +2 -2
  89. package/features/wcp/WcpGateway.js +2 -2
  90. package/features/wcp/WcpGateway.js.map +1 -1
  91. package/hooks/index.d.ts +1 -0
  92. package/hooks/index.js +1 -0
  93. package/hooks/index.js.map +1 -1
  94. package/hooks/useDialog.d.ts +9 -29
  95. package/hooks/useDialog.js +16 -24
  96. package/hooks/useDialog.js.map +1 -1
  97. package/hooks/useOpenDialog.d.ts +7 -0
  98. package/hooks/useOpenDialog.js +18 -0
  99. package/hooks/useOpenDialog.js.map +1 -0
  100. package/index.d.ts +5 -0
  101. package/index.js +5 -0
  102. package/index.js.map +1 -1
  103. package/package.json +30 -30
  104. package/permissions/createHasPermission.d.ts +3 -2
  105. package/permissions/createHasPermission.js +4 -8
  106. package/permissions/createHasPermission.js.map +1 -1
  107. package/permissions/createPermissions.d.ts +6 -0
  108. package/permissions/createPermissions.js +201 -0
  109. package/permissions/createPermissions.js.map +1 -0
  110. package/permissions/createPermissions.test.d.ts +1 -0
  111. package/permissions/createPermissions.test.js +177 -0
  112. package/permissions/createPermissions.test.js.map +1 -0
  113. package/permissions/index.d.ts +1 -0
  114. package/permissions/index.js +1 -0
  115. package/permissions/index.js.map +1 -1
  116. package/permissions/types.d.ts +5 -0
  117. package/permissions/types.js.map +1 -1
  118. package/permissions/usePermissions.d.ts +2 -1
  119. package/permissions/usePermissions.js +4 -175
  120. package/permissions/usePermissions.js.map +1 -1
  121. package/presentation/installation/presenters/SystemInstaller/SystemInstallerGateway.d.ts +2 -2
  122. package/presentation/installation/presenters/SystemInstaller/SystemInstallerGateway.js +2 -2
  123. package/presentation/installation/presenters/SystemInstaller/SystemInstallerGateway.js.map +1 -1
  124. package/permissions/createHasPermission.test.js +0 -206
  125. package/permissions/createHasPermission.test.js.map +0 -1
  126. /package/{permissions/createHasPermission.test.d.ts → features/formModel/FieldBuilder.test.d.ts} +0 -0
@@ -1,28 +1,20 @@
1
- import { useUi } from "@webiny/app/hooks/useUi.js";
2
- const useDialog = () => {
3
- const ui = useUi();
4
- return {
5
- showDialog: (message, options) => {
6
- ui.setState(ui => {
7
- return {
8
- ...ui,
9
- dialog: {
10
- message,
11
- options
12
- }
13
- };
14
- });
15
- },
16
- hideDialog: () => {
17
- ui.setState(ui => {
18
- return {
19
- ...ui,
20
- dialog: null
21
- };
22
- });
1
+ import { useMemo } from "react";
2
+ import { useDialogParamsContext } from "../components/Dialogs/DialogParamsContext.js";
3
+ export function useDialog(schema) {
4
+ const {
5
+ params: rawParams,
6
+ closeDialog
7
+ } = useDialogParamsContext();
8
+ const params = useMemo(() => {
9
+ if (schema) {
10
+ return schema.parse(rawParams);
23
11
  }
12
+ return rawParams;
13
+ }, [rawParams, schema]);
14
+ return {
15
+ params,
16
+ closeDialog
24
17
  };
25
- };
26
- export { useDialog };
18
+ }
27
19
 
28
20
  //# sourceMappingURL=useDialog.js.map
@@ -1 +1 @@
1
- {"version":3,"names":["useUi","useDialog","ui","showDialog","message","options","setState","dialog","hideDialog"],"sources":["useDialog.ts"],"sourcesContent":["import type React from \"react\";\nimport { useUi } from \"@webiny/app/hooks/useUi.js\";\n\ninterface AcceptAction {\n label: string;\n onClick?: () => void;\n}\ninterface CancelAction {\n label: string;\n onClick?: () => void;\n}\n\nexport interface UseDialogResponseShowDialogOptions {\n dataTestId?: string;\n title: string;\n loading?: boolean;\n actions?: {\n accept?: AcceptAction;\n cancel?: CancelAction;\n };\n style?: {\n [key: string]: any;\n };\n onClose?: () => void;\n [key: string]: any;\n}\ninterface UseDialogResponse {\n showDialog: (message: React.ReactNode, options?: UseDialogResponseShowDialogOptions) => void;\n hideDialog: () => void;\n}\nconst useDialog = (): UseDialogResponse => {\n const ui = useUi();\n return {\n showDialog: (message, options) => {\n ui.setState(ui => {\n return { ...ui, dialog: { message, options } };\n });\n },\n hideDialog: () => {\n ui.setState(ui => {\n return { ...ui, dialog: null };\n });\n }\n };\n};\n\nexport { useDialog };\n"],"mappings":"AACA,SAASA,KAAK,QAAQ,4BAA4B;AA6BlD,MAAMC,SAAS,GAAGA,CAAA,KAAyB;EACvC,MAAMC,EAAE,GAAGF,KAAK,CAAC,CAAC;EAClB,OAAO;IACHG,UAAU,EAAEA,CAACC,OAAO,EAAEC,OAAO,KAAK;MAC9BH,EAAE,CAACI,QAAQ,CAACJ,EAAE,IAAI;QACd,OAAO;UAAE,GAAGA,EAAE;UAAEK,MAAM,EAAE;YAAEH,OAAO;YAAEC;UAAQ;QAAE,CAAC;MAClD,CAAC,CAAC;IACN,CAAC;IACDG,UAAU,EAAEA,CAAA,KAAM;MACdN,EAAE,CAACI,QAAQ,CAACJ,EAAE,IAAI;QACd,OAAO;UAAE,GAAGA,EAAE;UAAEK,MAAM,EAAE;QAAK,CAAC;MAClC,CAAC,CAAC;IACN;EACJ,CAAC;AACL,CAAC;AAED,SAASN,SAAS","ignoreList":[]}
1
+ {"version":3,"names":["useMemo","useDialogParamsContext","useDialog","schema","params","rawParams","closeDialog","parse"],"sources":["useDialog.ts"],"sourcesContent":["import { useMemo } from \"react\";\nimport type { z } from \"zod\";\nimport { useDialogParamsContext } from \"~/components/Dialogs/DialogParamsContext.js\";\n\nexport function useDialog<T extends z.ZodTypeAny>(\n schema: T\n): { params: z.infer<T>; closeDialog: () => void };\nexport function useDialog(): { params: Record<string, unknown>; closeDialog: () => void };\nexport function useDialog(schema?: z.ZodTypeAny) {\n const { params: rawParams, closeDialog } = useDialogParamsContext();\n\n const params = useMemo(() => {\n if (schema) {\n return schema.parse(rawParams);\n }\n return rawParams;\n }, [rawParams, schema]);\n\n return { params, closeDialog };\n}\n"],"mappings":"AAAA,SAASA,OAAO,QAAQ,OAAO;AAE/B,SAASC,sBAAsB;AAM/B,OAAO,SAASC,SAASA,CAACC,MAAqB,EAAE;EAC7C,MAAM;IAAEC,MAAM,EAAEC,SAAS;IAAEC;EAAY,CAAC,GAAGL,sBAAsB,CAAC,CAAC;EAEnE,MAAMG,MAAM,GAAGJ,OAAO,CAAC,MAAM;IACzB,IAAIG,MAAM,EAAE;MACR,OAAOA,MAAM,CAACI,KAAK,CAACF,SAAS,CAAC;IAClC;IACA,OAAOA,SAAS;EACpB,CAAC,EAAE,CAACA,SAAS,EAAEF,MAAM,CAAC,CAAC;EAEvB,OAAO;IAAEC,MAAM;IAAEE;EAAY,CAAC;AAClC","ignoreList":[]}
@@ -0,0 +1,7 @@
1
+ import type { z } from "zod";
2
+ export declare function useOpenDialog<T extends z.ZodTypeAny>(schema: T): {
3
+ openDialog: (name: string, params: z.infer<T>) => void;
4
+ };
5
+ export declare function useOpenDialog(): {
6
+ openDialog: (name: string, params: Record<string, unknown>) => void;
7
+ };
@@ -0,0 +1,18 @@
1
+ import { useCallback } from "react";
2
+ import { useDialogs } from "../components/Dialogs/useDialogs.js";
3
+ export function useOpenDialog(schema) {
4
+ const {
5
+ openNamedDialog
6
+ } = useDialogs();
7
+ const openDialog = useCallback((name, params) => {
8
+ if (schema) {
9
+ schema.parse(params);
10
+ }
11
+ openNamedDialog(name, params);
12
+ }, [openNamedDialog, schema]);
13
+ return {
14
+ openDialog
15
+ };
16
+ }
17
+
18
+ //# sourceMappingURL=useOpenDialog.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"names":["useCallback","useDialogs","useOpenDialog","schema","openNamedDialog","openDialog","name","params","parse"],"sources":["useOpenDialog.ts"],"sourcesContent":["import { useCallback } from \"react\";\nimport type { z } from \"zod\";\nimport { useDialogs } from \"~/components/Dialogs/useDialogs.js\";\n\nexport function useOpenDialog<T extends z.ZodTypeAny>(\n schema: T\n): { openDialog: (name: string, params: z.infer<T>) => void };\nexport function useOpenDialog(): {\n openDialog: (name: string, params: Record<string, unknown>) => void;\n};\nexport function useOpenDialog(schema?: z.ZodTypeAny) {\n const { openNamedDialog } = useDialogs();\n\n const openDialog = useCallback(\n (name: string, params: Record<string, unknown>) => {\n if (schema) {\n schema.parse(params);\n }\n openNamedDialog(name, params);\n },\n [openNamedDialog, schema]\n );\n\n return { openDialog };\n}\n"],"mappings":"AAAA,SAASA,WAAW,QAAQ,OAAO;AAEnC,SAASC,UAAU;AAQnB,OAAO,SAASC,aAAaA,CAACC,MAAqB,EAAE;EACjD,MAAM;IAAEC;EAAgB,CAAC,GAAGH,UAAU,CAAC,CAAC;EAExC,MAAMI,UAAU,GAAGL,WAAW,CAC1B,CAACM,IAAY,EAAEC,MAA+B,KAAK;IAC/C,IAAIJ,MAAM,EAAE;MACRA,MAAM,CAACK,KAAK,CAACD,MAAM,CAAC;IACxB;IACAH,eAAe,CAACE,IAAI,EAAEC,MAAM,CAAC;EACjC,CAAC,EACD,CAACH,eAAe,EAAED,MAAM,CAC5B,CAAC;EAED,OAAO;IAAEE;EAAW,CAAC;AACzB","ignoreList":[]}
package/index.d.ts CHANGED
@@ -35,3 +35,8 @@ export { useAuthentication } from "./presentation/security/hooks/useAuthenticati
35
35
  export { useBuildParams } from "./presentation/buildParams/useBuildParams.js";
36
36
  export { useSecurity } from "./presentation/security/hooks/useSecurity.js";
37
37
  export * from "@webiny/app/renderApp.js";
38
+ export { FormModelFactory, FormModel } from "./features/formModel/abstractions.js";
39
+ export type { IFormModelFactory, IFormModelConfig, ILayoutBuilder, IFieldBuilder, ISelectFieldBuilder, IFieldBuilderRegistry, IFormModel, IField, ISelectField, FieldTypeMap, IFieldConfig, IFieldVM, IFieldValidation, IFormVM, IFormError, IValueOption, IRowNode, IRowNodeVM, LayoutNode, LayoutNodeVM, LayoutPosition, IPositionedLayoutNode, ILayoutNodeHandle, ILayoutModifier, IFormModifier, BeforeChangeCallback, AfterChangeCallback, AfterSetValueCallback } from "./features/formModel/abstractions.js";
40
+ export { FormView } from "./features/formModel/FormView.js";
41
+ export { useFieldRenderers } from "./features/formModel/useFieldRenderers.js";
42
+ export type { FieldRenderers, FieldRendererComponent } from "./features/formModel/FormView.js";
package/index.js CHANGED
@@ -44,4 +44,9 @@ export { useBuildParams } from "./presentation/buildParams/useBuildParams.js";
44
44
  export { useSecurity } from "./presentation/security/hooks/useSecurity.js";
45
45
  export * from "@webiny/app/renderApp.js";
46
46
 
47
+ // FormModel
48
+ export { FormModelFactory, FormModel } from "./features/formModel/abstractions.js";
49
+ export { FormView } from "./features/formModel/FormView.js";
50
+ export { useFieldRenderers } from "./features/formModel/useFieldRenderers.js";
51
+
47
52
  //# sourceMappingURL=index.js.map
package/index.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"names":["Admin","HasPermission","SecureRoute","FileManager","FileManagerRenderer","SystemInstallerProvider","BuildParamsFeature","useWcp","useTenantContext","useIdentity","useAuthentication","useBuildParams","useSecurity"],"sources":["index.ts"],"sourcesContent":["export * from \"@webiny/app\";\nexport type { HigherOrderComponent, ProviderProps, ComposeProps } from \"@webiny/app\";\n// UI components\nexport * from \"./base/ui/Tags.js\";\nexport * from \"./base/ui/Layout.js\";\nexport * from \"./base/ui/TenantSelector.js\";\nexport type { LayoutProps } from \"./base/ui/Layout.js\";\nexport * from \"./base/ui/Navigation.js\";\nexport * from \"./base/ui/Brand.js\";\nexport * from \"./base/ui/Logo.js\";\nexport * from \"./base/ui/UserMenu.js\";\nexport * from \"./base/ui/LoginScreen.js\";\nexport * from \"./base/ui/CenteredView.js\";\nexport * from \"./base/ui/Dashboard.js\";\nexport * from \"./base/ui/NotFound.js\";\n\n// Base admin app\nexport { Admin } from \"./base/Admin.js\";\nexport * from \"./config/AdminConfig.js\";\n\nexport type { AdminProps } from \"./base/Admin.js\";\n\n// Plugins\nexport * from \"./base/plugins/AddGraphQLQuerySelection.js\";\n\n// Permissions\nexport * from \"./permissions/index.js\";\n\n// Components\nexport * from \"./components/index.js\";\nexport type { RichTextValueWithHtml } from \"./components/index.js\";\nexport { HasPermission } from \"./presentation/security/components/HasPermission.js\";\nexport { SecureRoute } from \"./presentation/security/components/SecureRoute.js\";\n\nexport { FileManager, FileManagerRenderer } from \"./base/ui/FileManager.js\";\nexport type {\n FileManagerProps,\n FileManagerRendererProps,\n FileManagerFileItem,\n FileManagerOnChange\n} from \"./base/ui/FileManager.js\";\n\nexport { SystemInstallerProvider } from \"./presentation/installation/components/SystemInstaller/index.js\";\n\n// Feature types\nexport type { AaclPermission } from \"./features/wcp/types.js\";\nexport type { Tenant } from \"./features/tenancy/types.js\";\n\nexport { BuildParamsFeature } from \"./features/buildParams/feature.js\";\n\n// Hooks\nexport * from \"./hooks/index.js\";\nexport { useWcp } from \"./presentation/wcp/useWcp.js\";\nexport { useTenantContext } from \"./presentation/tenancy/useTenantContext.js\";\nexport { useIdentity } from \"./presentation/security/hooks/useIdentity.js\";\nexport { useAuthentication } from \"./presentation/security/hooks/useAuthentication.js\";\nexport { useBuildParams } from \"./presentation/buildParams/useBuildParams.js\";\n\n// Legacy hook for easier migration\nexport { useSecurity } from \"./presentation/security/hooks/useSecurity.js\";\n\nexport * from \"@webiny/app/renderApp.js\";\n"],"mappings":"AAAA,cAAc,aAAa;AAE3B;AACA;AACA;AACA;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA,SAASA,KAAK;AACd;AAIA;AACA;;AAEA;AACA;;AAEA;AACA;AAEA,SAASC,aAAa;AACtB,SAASC,WAAW;AAEpB,SAASC,WAAW,EAAEC,mBAAmB;AAQzC,SAASC,uBAAuB;;AAEhC;;AAIA,SAASC,kBAAkB;;AAE3B;AACA;AACA,SAASC,MAAM;AACf,SAASC,gBAAgB;AACzB,SAASC,WAAW;AACpB,SAASC,iBAAiB;AAC1B,SAASC,cAAc;;AAEvB;AACA,SAASC,WAAW;AAEpB,cAAc,0BAA0B","ignoreList":[]}
1
+ {"version":3,"names":["Admin","HasPermission","SecureRoute","FileManager","FileManagerRenderer","SystemInstallerProvider","BuildParamsFeature","useWcp","useTenantContext","useIdentity","useAuthentication","useBuildParams","useSecurity","FormModelFactory","FormModel","FormView","useFieldRenderers"],"sources":["index.ts"],"sourcesContent":["export * from \"@webiny/app\";\nexport type { HigherOrderComponent, ProviderProps, ComposeProps } from \"@webiny/app\";\n// UI components\nexport * from \"./base/ui/Tags.js\";\nexport * from \"./base/ui/Layout.js\";\nexport * from \"./base/ui/TenantSelector.js\";\nexport type { LayoutProps } from \"./base/ui/Layout.js\";\nexport * from \"./base/ui/Navigation.js\";\nexport * from \"./base/ui/Brand.js\";\nexport * from \"./base/ui/Logo.js\";\nexport * from \"./base/ui/UserMenu.js\";\nexport * from \"./base/ui/LoginScreen.js\";\nexport * from \"./base/ui/CenteredView.js\";\nexport * from \"./base/ui/Dashboard.js\";\nexport * from \"./base/ui/NotFound.js\";\n\n// Base admin app\nexport { Admin } from \"./base/Admin.js\";\nexport * from \"./config/AdminConfig.js\";\n\nexport type { AdminProps } from \"./base/Admin.js\";\n\n// Plugins\nexport * from \"./base/plugins/AddGraphQLQuerySelection.js\";\n\n// Permissions\nexport * from \"./permissions/index.js\";\n\n// Components\nexport * from \"./components/index.js\";\nexport type { RichTextValueWithHtml } from \"./components/index.js\";\nexport { HasPermission } from \"./presentation/security/components/HasPermission.js\";\nexport { SecureRoute } from \"./presentation/security/components/SecureRoute.js\";\n\nexport { FileManager, FileManagerRenderer } from \"./base/ui/FileManager.js\";\nexport type {\n FileManagerProps,\n FileManagerRendererProps,\n FileManagerFileItem,\n FileManagerOnChange\n} from \"./base/ui/FileManager.js\";\n\nexport { SystemInstallerProvider } from \"./presentation/installation/components/SystemInstaller/index.js\";\n\n// Feature types\nexport type { AaclPermission } from \"./features/wcp/types.js\";\nexport type { Tenant } from \"./features/tenancy/types.js\";\n\nexport { BuildParamsFeature } from \"./features/buildParams/feature.js\";\n\n// Hooks\nexport * from \"./hooks/index.js\";\nexport { useWcp } from \"./presentation/wcp/useWcp.js\";\nexport { useTenantContext } from \"./presentation/tenancy/useTenantContext.js\";\nexport { useIdentity } from \"./presentation/security/hooks/useIdentity.js\";\nexport { useAuthentication } from \"./presentation/security/hooks/useAuthentication.js\";\nexport { useBuildParams } from \"./presentation/buildParams/useBuildParams.js\";\n\n// Legacy hook for easier migration\nexport { useSecurity } from \"./presentation/security/hooks/useSecurity.js\";\n\nexport * from \"@webiny/app/renderApp.js\";\n\n// FormModel\nexport { FormModelFactory, FormModel } from \"./features/formModel/abstractions.js\";\nexport type {\n IFormModelFactory,\n IFormModelConfig,\n ILayoutBuilder,\n IFieldBuilder,\n ISelectFieldBuilder,\n IFieldBuilderRegistry,\n IFormModel,\n IField,\n ISelectField,\n FieldTypeMap,\n IFieldConfig,\n IFieldVM,\n IFieldValidation,\n IFormVM,\n IFormError,\n IValueOption,\n IRowNode,\n IRowNodeVM,\n LayoutNode,\n LayoutNodeVM,\n LayoutPosition,\n IPositionedLayoutNode,\n ILayoutNodeHandle,\n ILayoutModifier,\n IFormModifier,\n BeforeChangeCallback,\n AfterChangeCallback,\n AfterSetValueCallback\n} from \"./features/formModel/abstractions.js\";\nexport { FormView } from \"./features/formModel/FormView.js\";\nexport { useFieldRenderers } from \"./features/formModel/useFieldRenderers.js\";\nexport type { FieldRenderers, FieldRendererComponent } from \"./features/formModel/FormView.js\";\n"],"mappings":"AAAA,cAAc,aAAa;AAE3B;AACA;AACA;AACA;AAEA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;;AAEA;AACA,SAASA,KAAK;AACd;AAIA;AACA;;AAEA;AACA;;AAEA;AACA;AAEA,SAASC,aAAa;AACtB,SAASC,WAAW;AAEpB,SAASC,WAAW,EAAEC,mBAAmB;AAQzC,SAASC,uBAAuB;;AAEhC;;AAIA,SAASC,kBAAkB;;AAE3B;AACA;AACA,SAASC,MAAM;AACf,SAASC,gBAAgB;AACzB,SAASC,WAAW;AACpB,SAASC,iBAAiB;AAC1B,SAASC,cAAc;;AAEvB;AACA,SAASC,WAAW;AAEpB,cAAc,0BAA0B;;AAExC;AACA,SAASC,gBAAgB,EAAEC,SAAS;AA+BpC,SAASC,QAAQ;AACjB,SAASC,iBAAiB","ignoreList":[]}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@webiny/app-admin",
3
- "version": "6.1.0",
3
+ "version": "6.2.0",
4
4
  "type": "module",
5
5
  "main": "index.js",
6
6
  "description": "A collection of plugins that together form a complete admin interface, customizable and extensible with Webiny apps and plugins.",
@@ -16,26 +16,26 @@
16
16
  "@emotion/css": "11.13.5",
17
17
  "@emotion/react": "11.14.0",
18
18
  "@emotion/styled": "11.14.1",
19
- "@iconify/json": "2.2.455",
19
+ "@iconify/json": "2.2.462",
20
20
  "@svgr/webpack": "8.1.0",
21
- "@types/react": "18.2.79",
22
- "@webiny/admin-ui": "6.1.0",
23
- "@webiny/app": "6.1.0",
21
+ "@types/react": "18.3.28",
22
+ "@webiny/admin-ui": "6.2.0",
23
+ "@webiny/app": "6.2.0",
24
24
  "@webiny/di": "0.2.3",
25
- "@webiny/feature": "6.1.0",
26
- "@webiny/form": "6.1.0",
27
- "@webiny/icons": "6.1.0",
28
- "@webiny/lexical-converter": "6.1.0",
29
- "@webiny/lexical-editor": "6.1.0",
30
- "@webiny/lexical-theme": "6.1.0",
31
- "@webiny/plugins": "6.1.0",
32
- "@webiny/react-composition": "6.1.0",
33
- "@webiny/react-properties": "6.1.0",
34
- "@webiny/telemetry": "6.1.0",
35
- "@webiny/ui": "6.1.0",
36
- "@webiny/utils": "6.1.0",
37
- "@webiny/validation": "6.1.0",
38
- "@webiny/wcp": "6.1.0",
25
+ "@webiny/feature": "6.2.0",
26
+ "@webiny/form": "6.2.0",
27
+ "@webiny/icons": "6.2.0",
28
+ "@webiny/lexical-converter": "6.2.0",
29
+ "@webiny/lexical-editor": "6.2.0",
30
+ "@webiny/lexical-theme": "6.2.0",
31
+ "@webiny/plugins": "6.2.0",
32
+ "@webiny/react-composition": "6.2.0",
33
+ "@webiny/react-properties": "6.2.0",
34
+ "@webiny/telemetry": "6.2.0",
35
+ "@webiny/ui": "6.2.0",
36
+ "@webiny/utils": "6.2.0",
37
+ "@webiny/validation": "6.2.0",
38
+ "@webiny/wcp": "6.2.0",
39
39
  "apollo-cache": "1.3.5",
40
40
  "apollo-client": "2.6.10",
41
41
  "apollo-link": "1.2.14",
@@ -46,21 +46,21 @@
46
46
  "graphql-tag": "2.12.6",
47
47
  "history": "5.3.0",
48
48
  "is-hotkey": "0.2.0",
49
- "lodash": "4.17.23",
50
- "markdown-to-jsx": "9.7.13",
51
- "minimatch": "10.2.4",
49
+ "lodash": "4.18.1",
50
+ "markdown-to-jsx": "9.7.15",
51
+ "minimatch": "10.2.5",
52
52
  "mobx": "6.15.0",
53
53
  "mobx-react-lite": "4.1.1",
54
54
  "monaco-editor": "0.53.0",
55
- "prop-types": "15.8.1",
56
- "react": "18.2.0",
57
- "react-dom": "18.2.0",
58
- "react-resizable-panels": "4.7.6",
55
+ "react": "18.3.1",
56
+ "react-dom": "18.3.1",
57
+ "react-resizable-panels": "4.10.0",
59
58
  "react-transition-group": "4.4.5",
60
59
  "react-virtualized": "9.22.6",
61
60
  "reset-css": "5.0.2",
62
61
  "tinycolor2": "1.6.0",
63
- "unicode-emoji-json": "0.8.0"
62
+ "unicode-emoji-json": "0.8.0",
63
+ "zod": "4.3.6"
64
64
  },
65
65
  "devDependencies": {
66
66
  "@emotion/babel-plugin": "11.13.5",
@@ -72,10 +72,10 @@
72
72
  "@types/react-transition-group": "4.4.12",
73
73
  "@types/store": "2.0.5",
74
74
  "@types/tinycolor2": "1.4.6",
75
- "@webiny/build-tools": "6.1.0",
75
+ "@webiny/build-tools": "6.2.0",
76
76
  "rimraf": "6.1.3",
77
77
  "typescript": "5.9.3",
78
- "vitest": "4.1.2"
78
+ "vitest": "4.1.4"
79
79
  },
80
80
  "publishConfig": {
81
81
  "access": "public",
@@ -98,5 +98,5 @@
98
98
  ]
99
99
  }
100
100
  },
101
- "gitHead": "65e0ac1889b3392c99b8cac6cde508e1e831c715"
101
+ "gitHead": "3d3148358b6febbc857371930871743bec3b3939"
102
102
  }
@@ -1,3 +1,4 @@
1
1
  import React from "react";
2
- import type { HasPermissionProps, PermissionSchemaConfig } from "./types.js";
3
- export declare function createHasPermission<const S extends PermissionSchemaConfig>(schema: S): React.FC<HasPermissionProps<S>>;
2
+ import type { Abstraction } from "@webiny/di";
3
+ import type { HasPermissionProps, PermissionSchemaConfig, UsePermissionsResult } from "./types.js";
4
+ export declare function createHasPermission<const S extends PermissionSchemaConfig>(abstraction: Abstraction<UsePermissionsResult<S>>): React.FC<HasPermissionProps<S>>;
@@ -1,5 +1,5 @@
1
1
  import React from "react";
2
- import { createUsePermissions } from "./usePermissions.js";
2
+ import { useContainer } from "@webiny/app";
3
3
  const BUILT_IN_ACTIONS = {
4
4
  read: "canRead",
5
5
  create: "canCreate",
@@ -8,13 +8,13 @@ const BUILT_IN_ACTIONS = {
8
8
  publish: "canPublish",
9
9
  unpublish: "canUnpublish"
10
10
  };
11
- export function createHasPermission(schema) {
12
- const usePermissions = createUsePermissions(schema);
11
+ export function createHasPermission(abstraction) {
13
12
  return function HasPermission({
14
13
  children,
15
14
  ...props
16
15
  }) {
17
- const permissions = usePermissions();
16
+ const container = useContainer();
17
+ const permissions = container.resolve(abstraction);
18
18
  const action = props.action;
19
19
  const someActions = props.someActions;
20
20
  const allActions = props.allActions;
@@ -28,10 +28,6 @@ export function createHasPermission(schema) {
28
28
  if (method && typeof permissions[method] === "function") {
29
29
  return permissions[method](entityId);
30
30
  }
31
- /**
32
- * // TODO cant be typed properly because of the dynamic nature of custom actions.
33
- */
34
- // @ts-expect-error
35
31
  return permissions.canAction(singleAction, entityId);
36
32
  };
37
33
  const check = entityId => {
@@ -1 +1 @@
1
- {"version":3,"names":["React","createUsePermissions","BUILT_IN_ACTIONS","read","create","edit","delete","publish","unpublish","createHasPermission","schema","usePermissions","HasPermission","children","props","permissions","action","someActions","allActions","entities","entity","any","all","requireAll","checkAction","entityId","singleAction","canAccess","method","canAction","check","every","act","some","allowed","createElement","Fragment"],"sources":["createHasPermission.tsx"],"sourcesContent":["import React from \"react\";\nimport { createUsePermissions } from \"./usePermissions.js\";\nimport type { HasPermissionProps, PermissionSchemaConfig } from \"./types.js\";\n\nconst BUILT_IN_ACTIONS: Record<string, string> = {\n read: \"canRead\",\n create: \"canCreate\",\n edit: \"canEdit\",\n delete: \"canDelete\",\n publish: \"canPublish\",\n unpublish: \"canUnpublish\"\n};\n\nexport function createHasPermission<const S extends PermissionSchemaConfig>(\n schema: S\n): React.FC<HasPermissionProps<S>> {\n const usePermissions = createUsePermissions(schema);\n\n return function HasPermission({ children, ...props }) {\n const permissions = usePermissions();\n\n const action = props.action as string | undefined;\n const someActions = props.someActions as string[] | undefined;\n const allActions = props.allActions as string[] | undefined;\n const entities: string[] = props.entity ? [props.entity] : (props.any ?? props.all ?? []);\n const requireAll = !!props.all;\n\n const checkAction = (entityId: string, singleAction: string | undefined): boolean => {\n if (!singleAction) {\n return permissions.canAccess(entityId);\n }\n const method = BUILT_IN_ACTIONS[singleAction] as keyof typeof permissions;\n if (method && typeof permissions[method] === \"function\") {\n return permissions[method](entityId);\n }\n /**\n * // TODO cant be typed properly because of the dynamic nature of custom actions.\n */\n // @ts-expect-error\n return permissions.canAction(singleAction, entityId);\n };\n\n const check = (entityId: string): boolean => {\n if (allActions) {\n return allActions.every(act => checkAction(entityId, act));\n }\n if (someActions) {\n return someActions.some(act => checkAction(entityId, act));\n }\n return checkAction(entityId, action);\n };\n\n const allowed = requireAll ? entities.every(check) : entities.some(check);\n\n return allowed ? <>{children}</> : null;\n };\n}\n"],"mappings":"AAAA,OAAOA,KAAK,MAAM,OAAO;AACzB,SAASC,oBAAoB;AAG7B,MAAMC,gBAAwC,GAAG;EAC7CC,IAAI,EAAE,SAAS;EACfC,MAAM,EAAE,WAAW;EACnBC,IAAI,EAAE,SAAS;EACfC,MAAM,EAAE,WAAW;EACnBC,OAAO,EAAE,YAAY;EACrBC,SAAS,EAAE;AACf,CAAC;AAED,OAAO,SAASC,mBAAmBA,CAC/BC,MAAS,EACsB;EAC/B,MAAMC,cAAc,GAAGV,oBAAoB,CAACS,MAAM,CAAC;EAEnD,OAAO,SAASE,aAAaA,CAAC;IAAEC,QAAQ;IAAE,GAAGC;EAAM,CAAC,EAAE;IAClD,MAAMC,WAAW,GAAGJ,cAAc,CAAC,CAAC;IAEpC,MAAMK,MAAM,GAAGF,KAAK,CAACE,MAA4B;IACjD,MAAMC,WAAW,GAAGH,KAAK,CAACG,WAAmC;IAC7D,MAAMC,UAAU,GAAGJ,KAAK,CAACI,UAAkC;IAC3D,MAAMC,QAAkB,GAAGL,KAAK,CAACM,MAAM,GAAG,CAACN,KAAK,CAACM,MAAM,CAAC,GAAIN,KAAK,CAACO,GAAG,IAAIP,KAAK,CAACQ,GAAG,IAAI,EAAG;IACzF,MAAMC,UAAU,GAAG,CAAC,CAACT,KAAK,CAACQ,GAAG;IAE9B,MAAME,WAAW,GAAGA,CAACC,QAAgB,EAAEC,YAAgC,KAAc;MACjF,IAAI,CAACA,YAAY,EAAE;QACf,OAAOX,WAAW,CAACY,SAAS,CAACF,QAAQ,CAAC;MAC1C;MACA,MAAMG,MAAM,GAAG1B,gBAAgB,CAACwB,YAAY,CAA6B;MACzE,IAAIE,MAAM,IAAI,OAAOb,WAAW,CAACa,MAAM,CAAC,KAAK,UAAU,EAAE;QACrD,OAAOb,WAAW,CAACa,MAAM,CAAC,CAACH,QAAQ,CAAC;MACxC;MACA;AACZ;AACA;MACY;MACA,OAAOV,WAAW,CAACc,SAAS,CAACH,YAAY,EAAED,QAAQ,CAAC;IACxD,CAAC;IAED,MAAMK,KAAK,GAAIL,QAAgB,IAAc;MACzC,IAAIP,UAAU,EAAE;QACZ,OAAOA,UAAU,CAACa,KAAK,CAACC,GAAG,IAAIR,WAAW,CAACC,QAAQ,EAAEO,GAAG,CAAC,CAAC;MAC9D;MACA,IAAIf,WAAW,EAAE;QACb,OAAOA,WAAW,CAACgB,IAAI,CAACD,GAAG,IAAIR,WAAW,CAACC,QAAQ,EAAEO,GAAG,CAAC,CAAC;MAC9D;MACA,OAAOR,WAAW,CAACC,QAAQ,EAAET,MAAM,CAAC;IACxC,CAAC;IAED,MAAMkB,OAAO,GAAGX,UAAU,GAAGJ,QAAQ,CAACY,KAAK,CAACD,KAAK,CAAC,GAAGX,QAAQ,CAACc,IAAI,CAACH,KAAK,CAAC;IAEzE,OAAOI,OAAO,gBAAGlC,KAAA,CAAAmC,aAAA,CAAAnC,KAAA,CAAAoC,QAAA,QAAGvB,QAAW,CAAC,GAAG,IAAI;EAC3C,CAAC;AACL","ignoreList":[]}
1
+ {"version":3,"names":["React","useContainer","BUILT_IN_ACTIONS","read","create","edit","delete","publish","unpublish","createHasPermission","abstraction","HasPermission","children","props","container","permissions","resolve","action","someActions","allActions","entities","entity","any","all","requireAll","checkAction","entityId","singleAction","canAccess","method","canAction","check","every","act","some","allowed","createElement","Fragment"],"sources":["createHasPermission.tsx"],"sourcesContent":["import React from \"react\";\nimport type { Abstraction } from \"@webiny/di\";\nimport type { HasPermissionProps, PermissionSchemaConfig, UsePermissionsResult } from \"./types.js\";\nimport { useContainer } from \"@webiny/app\";\n\nconst BUILT_IN_ACTIONS: Record<string, string> = {\n read: \"canRead\",\n create: \"canCreate\",\n edit: \"canEdit\",\n delete: \"canDelete\",\n publish: \"canPublish\",\n unpublish: \"canUnpublish\"\n};\n\nexport function createHasPermission<const S extends PermissionSchemaConfig>(\n abstraction: Abstraction<UsePermissionsResult<S>>\n): React.FC<HasPermissionProps<S>> {\n return function HasPermission({ children, ...props }) {\n const container = useContainer();\n const permissions = container.resolve(abstraction);\n\n const action = props.action as string | undefined;\n const someActions = props.someActions as string[] | undefined;\n const allActions = props.allActions as string[] | undefined;\n const entities: string[] = props.entity ? [props.entity] : (props.any ?? props.all ?? []);\n const requireAll = !!props.all;\n\n const checkAction = (entityId: string, singleAction: string | undefined): boolean => {\n if (!singleAction) {\n return permissions.canAccess(entityId);\n }\n const method = BUILT_IN_ACTIONS[singleAction] as keyof typeof permissions;\n if (method && typeof permissions[method] === \"function\") {\n return (permissions[method] as (entityId: string) => boolean)(entityId);\n }\n return (permissions.canAction as (action: string, entityId: string) => boolean)(\n singleAction,\n entityId\n );\n };\n\n const check = (entityId: string): boolean => {\n if (allActions) {\n return allActions.every(act => checkAction(entityId, act));\n }\n if (someActions) {\n return someActions.some(act => checkAction(entityId, act));\n }\n return checkAction(entityId, action);\n };\n\n const allowed = requireAll ? entities.every(check) : entities.some(check);\n\n return allowed ? <>{children}</> : null;\n };\n}\n"],"mappings":"AAAA,OAAOA,KAAK,MAAM,OAAO;AAGzB,SAASC,YAAY,QAAQ,aAAa;AAE1C,MAAMC,gBAAwC,GAAG;EAC7CC,IAAI,EAAE,SAAS;EACfC,MAAM,EAAE,WAAW;EACnBC,IAAI,EAAE,SAAS;EACfC,MAAM,EAAE,WAAW;EACnBC,OAAO,EAAE,YAAY;EACrBC,SAAS,EAAE;AACf,CAAC;AAED,OAAO,SAASC,mBAAmBA,CAC/BC,WAAiD,EAClB;EAC/B,OAAO,SAASC,aAAaA,CAAC;IAAEC,QAAQ;IAAE,GAAGC;EAAM,CAAC,EAAE;IAClD,MAAMC,SAAS,GAAGb,YAAY,CAAC,CAAC;IAChC,MAAMc,WAAW,GAAGD,SAAS,CAACE,OAAO,CAACN,WAAW,CAAC;IAElD,MAAMO,MAAM,GAAGJ,KAAK,CAACI,MAA4B;IACjD,MAAMC,WAAW,GAAGL,KAAK,CAACK,WAAmC;IAC7D,MAAMC,UAAU,GAAGN,KAAK,CAACM,UAAkC;IAC3D,MAAMC,QAAkB,GAAGP,KAAK,CAACQ,MAAM,GAAG,CAACR,KAAK,CAACQ,MAAM,CAAC,GAAIR,KAAK,CAACS,GAAG,IAAIT,KAAK,CAACU,GAAG,IAAI,EAAG;IACzF,MAAMC,UAAU,GAAG,CAAC,CAACX,KAAK,CAACU,GAAG;IAE9B,MAAME,WAAW,GAAGA,CAACC,QAAgB,EAAEC,YAAgC,KAAc;MACjF,IAAI,CAACA,YAAY,EAAE;QACf,OAAOZ,WAAW,CAACa,SAAS,CAACF,QAAQ,CAAC;MAC1C;MACA,MAAMG,MAAM,GAAG3B,gBAAgB,CAACyB,YAAY,CAA6B;MACzE,IAAIE,MAAM,IAAI,OAAOd,WAAW,CAACc,MAAM,CAAC,KAAK,UAAU,EAAE;QACrD,OAAQd,WAAW,CAACc,MAAM,CAAC,CAAmCH,QAAQ,CAAC;MAC3E;MACA,OAAQX,WAAW,CAACe,SAAS,CACzBH,YAAY,EACZD,QACJ,CAAC;IACL,CAAC;IAED,MAAMK,KAAK,GAAIL,QAAgB,IAAc;MACzC,IAAIP,UAAU,EAAE;QACZ,OAAOA,UAAU,CAACa,KAAK,CAACC,GAAG,IAAIR,WAAW,CAACC,QAAQ,EAAEO,GAAG,CAAC,CAAC;MAC9D;MACA,IAAIf,WAAW,EAAE;QACb,OAAOA,WAAW,CAACgB,IAAI,CAACD,GAAG,IAAIR,WAAW,CAACC,QAAQ,EAAEO,GAAG,CAAC,CAAC;MAC9D;MACA,OAAOR,WAAW,CAACC,QAAQ,EAAET,MAAM,CAAC;IACxC,CAAC;IAED,MAAMkB,OAAO,GAAGX,UAAU,GAAGJ,QAAQ,CAACY,KAAK,CAACD,KAAK,CAAC,GAAGX,QAAQ,CAACc,IAAI,CAACH,KAAK,CAAC;IAEzE,OAAOI,OAAO,gBAAGnC,KAAA,CAAAoC,aAAA,CAAApC,KAAA,CAAAqC,QAAA,QAAGzB,QAAW,CAAC,GAAG,IAAI;EAC3C,CAAC;AACL","ignoreList":[]}
@@ -0,0 +1,6 @@
1
+ import type { Abstraction } from "@webiny/di";
2
+ import type { PermissionSchemaConfig, UsePermissionsResult } from "./types.js";
3
+ export declare function createPermissionsAbstraction<const S extends PermissionSchemaConfig>(schema: S): Abstraction<UsePermissionsResult<S>>;
4
+ export declare function createPermissionsFeature<const S extends PermissionSchemaConfig>(schema: S, abstraction: Abstraction<UsePermissionsResult<S>>): import("@webiny/feature/admin").FeatureDefinition<{
5
+ permissions: UsePermissionsResult<S>;
6
+ }, []>;
@@ -0,0 +1,201 @@
1
+ import { createAbstraction } from "@webiny/feature/admin";
2
+ import { createFeature } from "@webiny/feature/admin";
3
+ import { IdentityContext } from "../features/security/IdentityContext/abstractions.js";
4
+ function buildEntityMap(schema) {
5
+ const map = new Map();
6
+ for (const entity of schema.entities ?? []) {
7
+ const actions = new Set();
8
+ for (const action of entity.actions ?? []) {
9
+ actions.add(action.name);
10
+ }
11
+ map.set(entity.id, {
12
+ permission: entity.permission,
13
+ actions,
14
+ hasOwn: entity.scopes.includes("own")
15
+ });
16
+ }
17
+ return map;
18
+ }
19
+ function getEntity(entityMap, entityId) {
20
+ const entity = entityMap.get(entityId);
21
+ if (!entity) {
22
+ throw new Error(`Unknown entity "${entityId}" in permission schema.`);
23
+ }
24
+ return entity;
25
+ }
26
+
27
+ /**
28
+ * Check whether the identity has unrestricted full access for the given schema prefix.
29
+ * Stricter than the legacy check: `{ name: "wb.*", rwd: "r" }` is NOT full access.
30
+ */
31
+ function hasFullSchemaAccess(identity, prefix) {
32
+ const fullAccessName = `${prefix}.*`;
33
+ const permission = identity.getPermission(fullAccessName);
34
+ if (!permission) {
35
+ return false;
36
+ }
37
+ // If any restricting keys are present, this is not full access.
38
+ if (typeof permission.rwd === "string" || typeof permission.pw === "string") {
39
+ return false;
40
+ }
41
+ return true;
42
+ }
43
+ class SchemaPermissions {
44
+ constructor(schema, identityContext) {
45
+ this.schema = schema;
46
+ this.entityMap = buildEntityMap(schema);
47
+ this.identityContext = identityContext;
48
+ }
49
+ get identity() {
50
+ return this.identityContext.getIdentity();
51
+ }
52
+ get fullAccess() {
53
+ return hasFullSchemaAccess(this.identity, this.schema.prefix);
54
+ }
55
+ canAccess = entityId => {
56
+ if (this.fullAccess) {
57
+ return true;
58
+ }
59
+ const entity = getEntity(this.entityMap, entityId);
60
+ return this.identity.getPermissions(entity.permission).length > 0;
61
+ };
62
+ canRead = entityId => {
63
+ if (this.fullAccess) {
64
+ return true;
65
+ }
66
+ const entity = getEntity(this.entityMap, entityId);
67
+ const permissions = this.identity.getPermissions(entity.permission);
68
+ if (!permissions.length) {
69
+ return false;
70
+ }
71
+ return permissions.some(permission => {
72
+ if (typeof permission.rwd !== "string") {
73
+ return true;
74
+ }
75
+ return permission.rwd.includes("r");
76
+ });
77
+ };
78
+ canCreate = entityId => {
79
+ if (this.fullAccess) {
80
+ return true;
81
+ }
82
+ const entity = getEntity(this.entityMap, entityId);
83
+ const permissions = this.identity.getPermissions(entity.permission);
84
+ if (!permissions.length) {
85
+ return false;
86
+ }
87
+ return permissions.some(permission => {
88
+ if (typeof permission.rwd !== "string") {
89
+ return true;
90
+ }
91
+ return permission.rwd.includes("w");
92
+ });
93
+ };
94
+ canEdit = (entityId, item) => {
95
+ if (this.fullAccess) {
96
+ return true;
97
+ }
98
+ const entity = getEntity(this.entityMap, entityId);
99
+ const permissions = this.identity.getPermissions(entity.permission);
100
+ if (!permissions.length) {
101
+ return false;
102
+ }
103
+ return permissions.some(permission => {
104
+ if (permission.own) {
105
+ if (!item?.createdBy) {
106
+ return true;
107
+ }
108
+ return item.createdBy.id === this.identity.id;
109
+ }
110
+ if (typeof permission.rwd !== "string") {
111
+ return true;
112
+ }
113
+ return permission.rwd.includes("w");
114
+ });
115
+ };
116
+ canDelete = (entityId, item) => {
117
+ if (this.fullAccess) {
118
+ return true;
119
+ }
120
+ const entity = getEntity(this.entityMap, entityId);
121
+ const permissions = this.identity.getPermissions(entity.permission);
122
+ if (!permissions.length) {
123
+ return false;
124
+ }
125
+ return permissions.some(permission => {
126
+ if (permission.own) {
127
+ return item?.createdBy?.id === this.identity.id;
128
+ }
129
+ if (typeof permission.rwd !== "string") {
130
+ return true;
131
+ }
132
+ return permission.rwd.includes("d");
133
+ });
134
+ };
135
+ canPublish = entityId => {
136
+ if (this.fullAccess) {
137
+ return true;
138
+ }
139
+ const entity = getEntity(this.entityMap, entityId);
140
+ const permissions = this.identity.getPermissions(entity.permission);
141
+ if (!permissions.length) {
142
+ return false;
143
+ }
144
+ return permissions.some(permission => {
145
+ return permission.pw?.includes("p");
146
+ });
147
+ };
148
+ canUnpublish = entityId => {
149
+ if (this.fullAccess) {
150
+ return true;
151
+ }
152
+ const entity = getEntity(this.entityMap, entityId);
153
+ const permissions = this.identity.getPermissions(entity.permission);
154
+ if (!permissions.length) {
155
+ return false;
156
+ }
157
+ return permissions.some(permission => {
158
+ return permission.pw?.includes("u");
159
+ });
160
+ };
161
+ canAction = (action, entityId) => {
162
+ if (this.fullAccess) {
163
+ return true;
164
+ }
165
+ const entity = getEntity(this.entityMap, entityId);
166
+ const permissions = this.identity.getPermissions(entity.permission);
167
+ if (!permissions.length) {
168
+ return false;
169
+ }
170
+ return permissions.some(permission => {
171
+ return permission[action] === true;
172
+ });
173
+ };
174
+ }
175
+ export function createPermissionsAbstraction(schema) {
176
+ return createAbstraction(`${schema.prefix}:Permissions`);
177
+ }
178
+ export function createPermissionsFeature(schema, abstraction) {
179
+ class PermissionsImpl extends SchemaPermissions {
180
+ constructor(identityContext) {
181
+ super(schema, identityContext);
182
+ }
183
+ }
184
+ const Implementation = abstraction.createImplementation({
185
+ implementation: PermissionsImpl,
186
+ dependencies: [IdentityContext]
187
+ });
188
+ return createFeature({
189
+ name: `${schema.prefix}:Permissions`,
190
+ register(container) {
191
+ container.register(Implementation).inSingletonScope();
192
+ },
193
+ resolve(container) {
194
+ return {
195
+ permissions: container.resolve(abstraction)
196
+ };
197
+ }
198
+ });
199
+ }
200
+
201
+ //# sourceMappingURL=createPermissions.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"names":["createAbstraction","createFeature","IdentityContext","buildEntityMap","schema","map","Map","entity","entities","actions","Set","action","add","name","set","id","permission","hasOwn","scopes","includes","getEntity","entityMap","entityId","get","Error","hasFullSchemaAccess","identity","prefix","fullAccessName","getPermission","rwd","pw","SchemaPermissions","constructor","identityContext","getIdentity","fullAccess","canAccess","getPermissions","length","canRead","permissions","some","canCreate","canEdit","item","own","createdBy","canDelete","canPublish","canUnpublish","canAction","createPermissionsAbstraction","createPermissionsFeature","abstraction","PermissionsImpl","Implementation","createImplementation","implementation","dependencies","register","container","inSingletonScope","resolve"],"sources":["createPermissions.ts"],"sourcesContent":["import { createAbstraction } from \"@webiny/feature/admin\";\nimport { createFeature } from \"@webiny/feature/admin\";\nimport { IdentityContext } from \"~/features/security/IdentityContext/abstractions.js\";\nimport type { IIdentityContext } from \"~/features/security/IdentityContext/abstractions.js\";\nimport type { Identity } from \"~/domain/Identity.js\";\nimport type { Abstraction } from \"@webiny/di\";\nimport type { PermissionSchemaConfig, OwnableItem, UsePermissionsResult } from \"./types.js\";\n\ninterface EntityLookup {\n permission: string;\n actions: Set<string>;\n hasOwn: boolean;\n}\n\nfunction buildEntityMap(schema: PermissionSchemaConfig): Map<string, EntityLookup> {\n const map = new Map<string, EntityLookup>();\n for (const entity of schema.entities ?? []) {\n const actions = new Set<string>();\n for (const action of entity.actions ?? []) {\n actions.add(action.name);\n }\n map.set(entity.id, {\n permission: entity.permission,\n actions,\n hasOwn: entity.scopes.includes(\"own\")\n });\n }\n return map;\n}\n\nfunction getEntity(entityMap: Map<string, EntityLookup>, entityId: string): EntityLookup {\n const entity = entityMap.get(entityId);\n if (!entity) {\n throw new Error(`Unknown entity \"${entityId}\" in permission schema.`);\n }\n return entity;\n}\n\n/**\n * Check whether the identity has unrestricted full access for the given schema prefix.\n * Stricter than the legacy check: `{ name: \"wb.*\", rwd: \"r\" }` is NOT full access.\n */\nfunction hasFullSchemaAccess(identity: Identity, prefix: string): boolean {\n const fullAccessName = `${prefix}.*`;\n const permission = identity.getPermission(fullAccessName);\n if (!permission) {\n return false;\n }\n // If any restricting keys are present, this is not full access.\n if (typeof permission.rwd === \"string\" || typeof permission.pw === \"string\") {\n return false;\n }\n return true;\n}\n\nclass SchemaPermissions<S extends PermissionSchemaConfig> {\n private readonly schema: S;\n private readonly entityMap: Map<string, EntityLookup>;\n private readonly identityContext: IIdentityContext;\n\n constructor(schema: S, identityContext: IIdentityContext) {\n this.schema = schema;\n this.entityMap = buildEntityMap(schema);\n this.identityContext = identityContext;\n }\n\n private get identity(): Identity {\n return this.identityContext.getIdentity();\n }\n\n private get fullAccess(): boolean {\n return hasFullSchemaAccess(this.identity, this.schema.prefix);\n }\n\n canAccess = (entityId: string): boolean => {\n if (this.fullAccess) {\n return true;\n }\n const entity = getEntity(this.entityMap, entityId);\n return this.identity.getPermissions(entity.permission).length > 0;\n };\n\n canRead = (entityId: string): boolean => {\n if (this.fullAccess) {\n return true;\n }\n const entity = getEntity(this.entityMap, entityId);\n const permissions = this.identity.getPermissions(entity.permission);\n if (!permissions.length) {\n return false;\n }\n return permissions.some(permission => {\n if (typeof permission.rwd !== \"string\") {\n return true;\n }\n return permission.rwd.includes(\"r\");\n });\n };\n\n canCreate = (entityId: string): boolean => {\n if (this.fullAccess) {\n return true;\n }\n const entity = getEntity(this.entityMap, entityId);\n const permissions = this.identity.getPermissions(entity.permission);\n if (!permissions.length) {\n return false;\n }\n return permissions.some(permission => {\n if (typeof permission.rwd !== \"string\") {\n return true;\n }\n return permission.rwd.includes(\"w\");\n });\n };\n\n canEdit = (entityId: string, item?: OwnableItem): boolean => {\n if (this.fullAccess) {\n return true;\n }\n const entity = getEntity(this.entityMap, entityId);\n const permissions = this.identity.getPermissions(entity.permission);\n if (!permissions.length) {\n return false;\n }\n return permissions.some(permission => {\n if (permission.own) {\n if (!item?.createdBy) {\n return true;\n }\n return item.createdBy.id === this.identity.id;\n }\n if (typeof permission.rwd !== \"string\") {\n return true;\n }\n return permission.rwd.includes(\"w\");\n });\n };\n\n canDelete = (entityId: string, item?: OwnableItem): boolean => {\n if (this.fullAccess) {\n return true;\n }\n const entity = getEntity(this.entityMap, entityId);\n const permissions = this.identity.getPermissions(entity.permission);\n if (!permissions.length) {\n return false;\n }\n return permissions.some(permission => {\n if (permission.own) {\n return item?.createdBy?.id === this.identity.id;\n }\n if (typeof permission.rwd !== \"string\") {\n return true;\n }\n return permission.rwd.includes(\"d\");\n });\n };\n\n canPublish = (entityId: string): boolean => {\n if (this.fullAccess) {\n return true;\n }\n const entity = getEntity(this.entityMap, entityId);\n const permissions = this.identity.getPermissions(entity.permission);\n if (!permissions.length) {\n return false;\n }\n return permissions.some(permission => {\n return permission.pw?.includes(\"p\");\n });\n };\n\n canUnpublish = (entityId: string): boolean => {\n if (this.fullAccess) {\n return true;\n }\n const entity = getEntity(this.entityMap, entityId);\n const permissions = this.identity.getPermissions(entity.permission);\n if (!permissions.length) {\n return false;\n }\n return permissions.some(permission => {\n return permission.pw?.includes(\"u\");\n });\n };\n\n canAction = (action: string, entityId: string): boolean => {\n if (this.fullAccess) {\n return true;\n }\n const entity = getEntity(this.entityMap, entityId);\n const permissions = this.identity.getPermissions(entity.permission);\n if (!permissions.length) {\n return false;\n }\n return permissions.some(permission => {\n return permission[action] === true;\n });\n };\n}\n\nexport function createPermissionsAbstraction<const S extends PermissionSchemaConfig>(schema: S) {\n return createAbstraction<UsePermissionsResult<S>>(`${schema.prefix}:Permissions`);\n}\n\nexport function createPermissionsFeature<const S extends PermissionSchemaConfig>(\n schema: S,\n abstraction: Abstraction<UsePermissionsResult<S>>\n) {\n class PermissionsImpl extends SchemaPermissions<S> {\n constructor(identityContext: IIdentityContext) {\n super(schema, identityContext);\n }\n }\n\n const Implementation = abstraction.createImplementation({\n implementation: PermissionsImpl,\n dependencies: [IdentityContext]\n });\n\n return createFeature({\n name: `${schema.prefix}:Permissions`,\n register(container) {\n container.register(Implementation).inSingletonScope();\n },\n resolve(container) {\n return { permissions: container.resolve(abstraction) };\n }\n });\n}\n"],"mappings":"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","ignoreList":[]}
@@ -0,0 +1 @@
1
+ export {};