@jmruthers/pace-core 0.5.76 → 0.5.78
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +8 -0
- package/dist/{RBACService-C4udt_Zp.d.ts → AuthService-Df3IozMG.d.ts} +10 -118
- package/dist/{DataTable-ntgmhO2W.d.ts → DataTable-BE0OXZKQ.d.ts} +9 -2
- package/dist/{DataTable-4GAVPIEG.js → DataTable-ETGVF4Y5.js} +50 -13
- package/dist/{PublicLoadingSpinner-BiNER8F5.d.ts → PublicLoadingSpinner-CnUaz0vG.d.ts} +5 -2
- package/dist/{UnifiedAuthProvider-Bj6YCf7c.d.ts → UnifiedAuthProvider-B391Aqum.d.ts} +42 -45
- package/dist/{UnifiedAuthProvider-3NKDOSOK.js → UnifiedAuthProvider-P5SOJAQ6.js} +4 -5
- package/dist/{api-DDMUKIUD.js → api-KG4A2X7P.js} +9 -3
- package/dist/{audit-6TOCAMKO.js → audit-65VNHEV2.js} +2 -2
- package/dist/{chunk-K34IM5CT.js → chunk-2OGV6IRV.js} +196 -626
- package/dist/chunk-2OGV6IRV.js.map +1 -0
- package/dist/{chunk-NTNILOBC.js → chunk-5BO3MI5Y.js} +4 -4
- package/dist/{chunk-XLZ7U46Z.js → chunk-CVMVPYAL.js} +9 -60
- package/dist/chunk-CVMVPYAL.js.map +1 -0
- package/dist/{chunk-URUTVZ7N.js → chunk-FL4ZCQLD.js} +2 -2
- package/dist/{chunk-LW7MMEAQ.js → chunk-FT2M4R4F.js} +2 -2
- package/dist/{chunk-5BSLGBYI.js → chunk-JCQZ6LA7.js} +2 -8
- package/dist/{chunk-5BSLGBYI.js.map → chunk-JCQZ6LA7.js.map} +1 -1
- package/dist/{chunk-KHJS6VIA.js → chunk-LRQ6RBJC.js} +157 -112
- package/dist/chunk-LRQ6RBJC.js.map +1 -0
- package/dist/{chunk-WN6XJWOS.js → chunk-MNJXXD6C.js} +274 -743
- package/dist/chunk-MNJXXD6C.js.map +1 -0
- package/dist/{chunk-KK73ZB4E.js → chunk-PTR5PMPE.js} +153 -132
- package/dist/chunk-PTR5PMPE.js.map +1 -0
- package/dist/{chunk-B2WTCLCV.js → chunk-Q7APDV6H.js} +18 -8
- package/dist/chunk-Q7APDV6H.js.map +1 -0
- package/dist/{chunk-A4FUBC7B.js → chunk-QGVSOUJ2.js} +2 -4
- package/dist/{chunk-A4FUBC7B.js.map → chunk-QGVSOUJ2.js.map} +1 -1
- package/dist/{chunk-FGMFQSHX.js → chunk-S63MFSY6.js} +500 -551
- package/dist/chunk-S63MFSY6.js.map +1 -0
- package/dist/{chunk-AFGTSUAD.js → chunk-VSOKOFRF.js} +4 -4
- package/dist/chunk-WUXCWRL6.js +20 -0
- package/dist/chunk-WUXCWRL6.js.map +1 -0
- package/dist/{chunk-Y6TXWPJO.js → chunk-YVVGHRGI.js} +105 -31
- package/dist/chunk-YVVGHRGI.js.map +1 -0
- package/dist/{chunk-M5IWZRBT.js → chunk-ZMNXIJP4.js} +2187 -981
- package/dist/chunk-ZMNXIJP4.js.map +1 -0
- package/dist/components.d.ts +6 -6
- package/dist/components.js +14 -18
- package/dist/components.js.map +1 -1
- package/dist/{database-C3Szpi5J.d.ts → database-BXAfr2Y_.d.ts} +18 -0
- package/dist/hooks.d.ts +5 -5
- package/dist/hooks.js +8 -9
- package/dist/hooks.js.map +1 -1
- package/dist/index.d.ts +19 -27
- package/dist/index.js +21 -29
- package/dist/index.js.map +1 -1
- package/dist/{organisation-BtshODVF.d.ts → organisation-D6qRDtbF.d.ts} +1 -1
- package/dist/providers.d.ts +7 -21
- package/dist/providers.js +3 -10
- package/dist/rbac/index.d.ts +71 -221
- package/dist/rbac/index.js +15 -16
- package/dist/{types-CGX9Vyf5.d.ts → types-BDg1mAGG.d.ts} +36 -6
- package/dist/types.d.ts +3 -3
- package/dist/types.js +61 -18
- package/dist/types.js.map +1 -1
- package/dist/{unified-CM7T0aTK.d.ts → unified-DQ4VcT7H.d.ts} +1 -1
- package/dist/{usePublicRouteParams-B-CumWRc.d.ts → usePublicRouteParams-BlgwXweB.d.ts} +3 -3
- package/dist/utils.d.ts +2 -2
- package/dist/utils.js +52 -9
- package/dist/utils.js.map +1 -1
- package/docs/CONTENT_AUDIT_REPORT.md +253 -0
- package/docs/DOCUMENTATION_AUDIT.md +172 -0
- package/docs/README.md +142 -147
- package/docs/STYLE_GUIDE.md +37 -0
- package/docs/api/classes/ColumnFactory.md +17 -17
- package/docs/api/classes/ErrorBoundary.md +1 -1
- package/docs/api/classes/InvalidScopeError.md +4 -4
- package/docs/api/classes/MissingUserContextError.md +4 -4
- package/docs/api/classes/OrganisationContextRequiredError.md +4 -4
- package/docs/api/classes/PermissionDeniedError.md +5 -5
- package/docs/api/classes/PublicErrorBoundary.md +1 -1
- package/docs/api/classes/RBACAuditManager.md +8 -8
- package/docs/api/classes/RBACCache.md +35 -5
- package/docs/api/classes/RBACEngine.md +49 -20
- package/docs/api/classes/RBACError.md +4 -4
- package/docs/api/classes/RBACNotInitializedError.md +4 -4
- package/docs/api/classes/SecureSupabaseClient.md +1 -1
- package/docs/api/classes/StorageUtils.md +1 -1
- package/docs/api/enums/FileCategory.md +1 -1
- package/docs/api/interfaces/AggregateConfig.md +4 -4
- package/docs/api/interfaces/ButtonProps.md +1 -1
- package/docs/api/interfaces/CardProps.md +1 -1
- package/docs/api/interfaces/ColorPalette.md +1 -1
- package/docs/api/interfaces/ColorShade.md +1 -1
- package/docs/api/interfaces/DataAccessRecord.md +1 -1
- package/docs/api/interfaces/DataRecord.md +11 -0
- package/docs/api/interfaces/DataTableAction.md +65 -29
- package/docs/api/interfaces/DataTableColumn.md +36 -23
- package/docs/api/interfaces/DataTableProps.md +80 -38
- package/docs/api/interfaces/DataTableToolbarButton.md +7 -7
- package/docs/api/interfaces/EmptyStateConfig.md +5 -5
- package/docs/api/interfaces/EnhancedNavigationMenuProps.md +1 -1
- package/docs/api/interfaces/EventLogoProps.md +1 -1
- package/docs/api/interfaces/FileDisplayProps.md +1 -1
- package/docs/api/interfaces/FileMetadata.md +1 -1
- package/docs/api/interfaces/FileReference.md +1 -1
- package/docs/api/interfaces/FileSizeLimits.md +1 -1
- package/docs/api/interfaces/FileUploadOptions.md +1 -1
- package/docs/api/interfaces/FileUploadProps.md +1 -1
- package/docs/api/interfaces/FooterProps.md +1 -1
- package/docs/api/interfaces/InactivityWarningModalProps.md +1 -1
- package/docs/api/interfaces/InputProps.md +1 -1
- package/docs/api/interfaces/LabelProps.md +1 -1
- package/docs/api/interfaces/LoginFormProps.md +1 -1
- package/docs/api/interfaces/NavigationAccessRecord.md +11 -11
- package/docs/api/interfaces/NavigationContextType.md +9 -9
- package/docs/api/interfaces/NavigationGuardProps.md +1 -1
- package/docs/api/interfaces/NavigationItem.md +1 -1
- package/docs/api/interfaces/NavigationMenuProps.md +1 -1
- package/docs/api/interfaces/NavigationProviderProps.md +7 -7
- package/docs/api/interfaces/Organisation.md +1 -1
- package/docs/api/interfaces/OrganisationContextType.md +1 -1
- package/docs/api/interfaces/OrganisationMembership.md +1 -1
- package/docs/api/interfaces/OrganisationProviderProps.md +1 -1
- package/docs/api/interfaces/OrganisationSecurityError.md +1 -1
- package/docs/api/interfaces/PaceAppLayoutProps.md +1 -1
- package/docs/api/interfaces/PaceLoginPageProps.md +16 -3
- package/docs/api/interfaces/PageAccessRecord.md +1 -1
- package/docs/api/interfaces/PagePermissionContextType.md +1 -1
- package/docs/api/interfaces/PagePermissionGuardProps.md +2 -2
- package/docs/api/interfaces/PagePermissionProviderProps.md +1 -1
- package/docs/api/interfaces/PaletteData.md +1 -1
- package/docs/api/interfaces/PermissionEnforcerProps.md +4 -4
- package/docs/api/interfaces/PublicErrorBoundaryProps.md +1 -1
- package/docs/api/interfaces/PublicErrorBoundaryState.md +1 -1
- package/docs/api/interfaces/PublicLoadingSpinnerProps.md +1 -1
- package/docs/api/interfaces/PublicPageFooterProps.md +1 -1
- package/docs/api/interfaces/PublicPageHeaderProps.md +1 -1
- package/docs/api/interfaces/PublicPageLayoutProps.md +1 -1
- package/docs/api/interfaces/RBACConfig.md +1 -1
- package/docs/api/interfaces/RBACLogger.md +1 -1
- package/docs/api/interfaces/RoleBasedRouterContextType.md +1 -1
- package/docs/api/interfaces/RoleBasedRouterProps.md +1 -1
- package/docs/api/interfaces/RouteAccessRecord.md +2 -2
- package/docs/api/interfaces/RouteConfig.md +2 -2
- package/docs/api/interfaces/SecureDataContextType.md +1 -1
- package/docs/api/interfaces/SecureDataProviderProps.md +1 -1
- package/docs/api/interfaces/StorageConfig.md +1 -1
- package/docs/api/interfaces/StorageFileInfo.md +1 -1
- package/docs/api/interfaces/StorageFileMetadata.md +1 -1
- package/docs/api/interfaces/StorageListOptions.md +1 -1
- package/docs/api/interfaces/StorageListResult.md +1 -1
- package/docs/api/interfaces/StorageUploadOptions.md +1 -1
- package/docs/api/interfaces/StorageUploadResult.md +1 -1
- package/docs/api/interfaces/StorageUrlOptions.md +1 -1
- package/docs/api/interfaces/StyleImport.md +1 -1
- package/docs/api/interfaces/SwitchProps.md +1 -1
- package/docs/api/interfaces/ToastActionElement.md +1 -1
- package/docs/api/interfaces/ToastProps.md +1 -1
- package/docs/api/interfaces/UnifiedAuthContextType.md +94 -521
- package/docs/api/interfaces/UnifiedAuthProviderProps.md +16 -16
- package/docs/api/interfaces/UseInactivityTrackerOptions.md +1 -1
- package/docs/api/interfaces/UseInactivityTrackerReturn.md +1 -1
- package/docs/api/interfaces/UsePublicEventLogoOptions.md +1 -1
- package/docs/api/interfaces/UsePublicEventLogoReturn.md +1 -1
- package/docs/api/interfaces/UsePublicEventOptions.md +1 -1
- package/docs/api/interfaces/UsePublicEventReturn.md +1 -1
- package/docs/api/interfaces/UsePublicRouteParamsReturn.md +1 -1
- package/docs/api/interfaces/UseResolvedScopeOptions.md +1 -1
- package/docs/api/interfaces/UseResolvedScopeReturn.md +1 -1
- package/docs/api/interfaces/UserEventAccess.md +11 -11
- package/docs/api/interfaces/UserMenuProps.md +1 -1
- package/docs/api/interfaces/UserProfile.md +1 -1
- package/docs/api/modules.md +251 -269
- package/docs/api-reference/components.md +193 -0
- package/docs/api-reference/hooks.md +265 -0
- package/docs/api-reference/providers.md +6 -0
- package/docs/api-reference/types.md +6 -0
- package/docs/api-reference/utilities.md +207 -0
- package/docs/architecture/README.md +6 -0
- package/docs/{database-schema-requirements.md → architecture/database-schema-requirements.md} +6 -0
- package/docs/architecture/rbac-security-architecture.md +258 -0
- package/docs/architecture/services.md +9 -1
- package/docs/best-practices/README.md +6 -0
- package/docs/best-practices/accessibility.md +6 -0
- package/docs/{common-patterns.md → best-practices/common-patterns.md} +6 -0
- package/docs/best-practices/deployment.md +6 -0
- package/docs/best-practices/performance.md +475 -2
- package/docs/best-practices/security.md +6 -0
- package/docs/best-practices/testing.md +6 -0
- package/docs/core-concepts/authentication.md +6 -0
- package/docs/core-concepts/events.md +6 -0
- package/docs/core-concepts/organisations.md +6 -0
- package/docs/core-concepts/permissions.md +6 -0
- package/docs/core-concepts/rbac-system.md +8 -0
- package/docs/documentation-index.md +121 -182
- package/docs/{consuming-app-vite-config.md → getting-started/consuming-app-vite-config.md} +6 -0
- package/docs/getting-started/documentation-index.md +40 -0
- package/docs/getting-started/examples/README.md +878 -35
- package/docs/{faq.md → getting-started/faq.md} +7 -1
- package/docs/getting-started/installation-guide.md +6 -0
- package/docs/{quick-reference.md → getting-started/quick-reference.md} +6 -0
- package/docs/implementation-guides/app-layout.md +6 -0
- package/docs/implementation-guides/authentication.md +1021 -0
- package/docs/implementation-guides/component-styling.md +6 -0
- package/docs/implementation-guides/data-tables.md +1264 -2076
- package/docs/implementation-guides/dynamic-colors.md +6 -0
- package/docs/implementation-guides/event-theming-summary.md +6 -0
- package/docs/{file-reference-system.md → implementation-guides/file-reference-system.md} +6 -0
- package/docs/implementation-guides/file-upload-storage.md +6 -0
- package/docs/implementation-guides/forms.md +6 -0
- package/docs/implementation-guides/inactivity-tracking.md +6 -0
- package/docs/implementation-guides/navigation.md +6 -0
- package/docs/implementation-guides/organisation-security.md +6 -0
- package/docs/implementation-guides/permission-enforcement.md +6 -0
- package/docs/implementation-guides/public-pages-advanced.md +6 -0
- package/docs/implementation-guides/public-pages.md +6 -0
- package/docs/migration/MIGRATION_GUIDE.md +827 -351
- package/docs/migration/README.md +7 -1
- package/docs/migration/organisation-context-timing-fix.md +6 -0
- package/docs/migration/rbac-migration.md +44 -1
- package/docs/migration/service-architecture.md +6 -0
- package/docs/migration/v0.4.15-tailwind-scanning.md +6 -0
- package/docs/migration/v0.4.16-css-first-approach.md +6 -0
- package/docs/migration/v0.4.17-source-path-fix.md +6 -0
- package/docs/rbac/README-rbac-rls-integration.md +6 -0
- package/docs/rbac/README.md +6 -0
- package/docs/rbac/advanced-patterns.md +6 -0
- package/docs/rbac/api-reference.md +7 -1
- package/docs/rbac/breaking-changes-v3.md +222 -0
- package/docs/rbac/examples/rbac-rls-integration-example.md +6 -0
- package/docs/rbac/examples.md +6 -0
- package/docs/rbac/getting-started.md +6 -0
- package/docs/rbac/migration-guide.md +260 -0
- package/docs/rbac/quick-start.md +70 -13
- package/docs/rbac/rbac-rls-integration.md +6 -0
- package/docs/rbac/super-admin-guide.md +6 -0
- package/docs/rbac/troubleshooting.md +6 -0
- package/docs/security/README.md +6 -0
- package/docs/security/checklist.md +6 -0
- package/docs/styles/README.md +7 -1
- package/docs/{usage.md → styles/usage.md} +6 -0
- package/docs/testing/README.md +6 -0
- package/docs/{visual-testing.md → testing/visual-testing.md} +6 -0
- package/docs/troubleshooting/README.md +387 -5
- package/docs/troubleshooting/cake-page-permission-guard-issue-summary.md +6 -0
- package/docs/troubleshooting/common-issues.md +6 -0
- package/docs/troubleshooting/database-view-compatibility.md +6 -0
- package/docs/troubleshooting/organisation-context-setup.md +6 -0
- package/docs/troubleshooting/react-hooks-issue-analysis.md +6 -0
- package/docs/troubleshooting/styling-issues.md +6 -0
- package/docs/troubleshooting/tailwind-content-scanning.md +6 -0
- package/package.json +1 -1
- package/src/__tests__/helpers/__tests__/test-providers.test.tsx +2 -1
- package/src/__tests__/helpers/test-providers.tsx +3 -53
- package/src/components/DataTable/DataTable.test.tsx +319 -0
- package/src/components/DataTable/DataTable.tsx +32 -11
- package/src/components/DataTable/__tests__/{DataTable.comprehensive.test.tsx → DataTable.comprehensive.test.tsx.skip} +6 -4
- package/src/components/DataTable/__tests__/{DataTable.test.tsx → DataTable.test.tsx.skip} +6 -4
- package/src/components/DataTable/__tests__/DataTableCore.test.tsx +31 -9
- package/src/components/DataTable/__tests__/a11y.basic.test.tsx +601 -0
- package/src/components/DataTable/__tests__/keyboard.test.tsx +615 -0
- package/src/components/DataTable/__tests__/pagination.modes.test.tsx +639 -0
- package/src/components/DataTable/__tests__/ssr.strict-mode.test.tsx.skip +330 -0
- package/src/components/DataTable/components/AccessDeniedPage.tsx +2 -2
- package/src/components/DataTable/components/ActionButtons.tsx +88 -104
- package/src/components/DataTable/components/DataTableCore.tsx +309 -337
- package/src/components/DataTable/components/DataTableErrorBoundary.tsx +4 -2
- package/src/components/DataTable/components/DataTableModals.tsx +22 -1
- package/src/components/DataTable/components/EditableRow.tsx +69 -84
- package/src/components/DataTable/components/EmptyState.tsx +5 -1
- package/src/components/DataTable/components/ImportModal.tsx +65 -36
- package/src/components/DataTable/components/PaginationControls.tsx +40 -100
- package/src/components/DataTable/components/UnifiedTableBody.tsx +125 -148
- package/src/components/DataTable/context/DataTableContext.tsx +1 -1
- package/src/components/DataTable/core/ColumnFactory.ts +5 -0
- package/src/components/DataTable/examples/HierarchicalActionsExample.tsx +12 -10
- package/src/components/DataTable/examples/HierarchicalExample.tsx +1 -1
- package/src/components/DataTable/examples/InitialPageSizeExample.tsx +1 -0
- package/src/components/DataTable/examples/PerformanceExample.tsx +1 -0
- package/src/components/DataTable/hooks/__tests__/useColumnOrderPersistence.test.ts +1 -5
- package/src/components/DataTable/hooks/__tests__/useColumnVisibilityPersistence.test.ts +167 -0
- package/src/components/DataTable/hooks/index.ts +7 -0
- package/src/components/DataTable/hooks/useColumnOrderPersistence.ts +32 -15
- package/src/components/DataTable/hooks/useColumnVisibilityPersistence.ts +102 -0
- package/src/components/DataTable/hooks/useDataTableConfiguration.ts +89 -0
- package/src/components/DataTable/hooks/useDataTableDataPipeline.ts +117 -0
- package/src/components/DataTable/hooks/useDataTablePermissions.ts +71 -27
- package/src/components/DataTable/hooks/useDataTableState.ts +39 -11
- package/src/components/DataTable/hooks/useEffectiveColumnOrder.ts +33 -0
- package/src/components/DataTable/hooks/useHierarchicalState.ts +15 -1
- package/src/components/DataTable/hooks/useKeyboardNavigation.ts +447 -0
- package/src/components/DataTable/hooks/useServerSideDataEffect.ts +94 -0
- package/src/components/DataTable/hooks/useTableColumns.ts +10 -7
- package/src/components/DataTable/hooks/useTableHandlers.ts +174 -0
- package/src/components/DataTable/index.ts +12 -3
- package/src/components/DataTable/types.ts +129 -9
- package/src/components/DataTable/utils/__tests__/exportUtils.test.ts +159 -22
- package/src/components/DataTable/utils/__tests__/flexibleImport.test.ts +111 -0
- package/src/components/DataTable/utils/__tests__/rowUtils.test.ts +15 -29
- package/src/components/DataTable/utils/a11yUtils.ts +244 -0
- package/src/components/DataTable/utils/debugTools.ts +609 -0
- package/src/components/DataTable/utils/exportUtils.ts +114 -16
- package/src/components/DataTable/utils/flexibleImport.ts +202 -32
- package/src/components/DataTable/utils/hierarchicalUtils.ts +1 -1
- package/src/components/DataTable/utils/index.ts +2 -0
- package/src/components/DataTable/utils/paginationUtils.ts +350 -0
- package/src/components/DataTable/utils/rowUtils.ts +6 -5
- package/src/components/NavigationMenu/NavigationMenu.test.tsx +19 -24
- package/src/components/NavigationMenu/NavigationMenu.tsx +19 -8
- package/src/components/PaceAppLayout/__tests__/PaceAppLayout.security.test.tsx +1 -23
- package/src/components/PaceLoginPage/PaceLoginPage.test.tsx +56 -6
- package/src/components/PaceLoginPage/PaceLoginPage.tsx +137 -13
- package/src/components/PublicLayout/__tests__/PublicPageHeader.test.tsx +1 -1
- package/src/components/Select/Select.tsx +1 -0
- package/src/components/examples/PermissionExample.tsx +173 -0
- package/src/examples/CorrectPublicPageImplementation.tsx +301 -0
- package/src/examples/PublicEventPage.tsx +274 -0
- package/src/examples/PublicPageApp.tsx +308 -0
- package/src/examples/PublicPageUsageExample.tsx +216 -0
- package/src/hooks/__tests__/useOrganisationPermissions.unit.test.tsx +12 -1
- package/src/hooks/__tests__/useOrganisationSecurity.unit.test.tsx +129 -17
- package/src/hooks/__tests__/useRBAC.unit.test.ts +151 -846
- package/src/hooks/useOrganisationPermissions.test.ts +42 -18
- package/src/hooks/useOrganisationPermissions.ts +12 -6
- package/src/hooks/useOrganisationSecurity.test.ts +138 -85
- package/src/hooks/useOrganisationSecurity.ts +41 -10
- package/src/index.ts +0 -1
- package/src/providers/AuthProvider.simplified.tsx +880 -0
- package/src/providers/UnifiedAuthProvider.test.simple.tsx +8 -8
- package/src/providers/__tests__/UnifiedAuthProvider.test.tsx +29 -19
- package/src/providers/index.ts +0 -1
- package/src/providers/services/EventServiceProvider.tsx +19 -15
- package/src/providers/services/InactivityServiceProvider.tsx +19 -15
- package/src/providers/services/OrganisationServiceProvider.tsx +19 -15
- package/src/providers/services/UnifiedAuthProvider.tsx +156 -127
- package/src/providers/services/__tests__/AuthServiceProvider.integration.test.tsx +1 -1
- package/src/providers/services/__tests__/UnifiedAuthProvider.integration.test.tsx +3 -3
- package/src/rbac/README.md +1 -1
- package/src/rbac/__tests__/adapters.comprehensive.test.tsx +25 -27
- package/src/rbac/__tests__/auth-rbac-security.integration.test.tsx +313 -0
- package/src/rbac/__tests__/engine.comprehensive.test.ts +114 -348
- package/src/rbac/__tests__/rbac-engine-core-logic.test.ts +28 -110
- package/src/rbac/__tests__/rbac-engine-simplified.test.ts +33 -85
- package/src/rbac/__tests__/scenarios.user-role.test.tsx +2 -2
- package/src/rbac/adapters.tsx +26 -69
- package/src/rbac/api.test.ts +90 -27
- package/src/rbac/api.ts +61 -10
- package/src/rbac/audit.test.ts +33 -38
- package/src/rbac/audit.ts +21 -6
- package/src/rbac/cache.ts +33 -1
- package/src/rbac/components/NavigationGuard.tsx +11 -11
- package/src/rbac/components/NavigationProvider.test.tsx +11 -5
- package/src/rbac/components/NavigationProvider.tsx +37 -13
- package/src/rbac/components/PagePermissionGuard.tsx +111 -50
- package/src/rbac/components/PagePermissionProvider.tsx +5 -5
- package/src/rbac/components/PermissionEnforcer.tsx +11 -11
- package/src/rbac/components/RoleBasedRouter.tsx +5 -5
- package/src/rbac/components/SecureDataProvider.tsx +5 -5
- package/src/rbac/components/__tests__/NavigationGuard.test.tsx +8 -8
- package/src/rbac/components/__tests__/PagePermissionGuard.test.tsx +14 -14
- package/src/rbac/components/__tests__/PermissionEnforcer.test.tsx +12 -12
- package/src/rbac/components/__tests__/RoleBasedRouter.test.tsx +6 -6
- package/src/rbac/engine.test.simple.ts +19 -13
- package/src/rbac/engine.test.ts +1 -0
- package/src/rbac/engine.ts +330 -766
- package/src/rbac/errors.ts +156 -0
- package/src/rbac/hooks/usePermissions.ts +32 -10
- package/src/rbac/hooks/useRBAC.test.ts +126 -512
- package/src/rbac/hooks/useRBAC.ts +147 -193
- package/src/rbac/hooks/useResolvedScope.ts +12 -0
- package/src/rbac/index.ts +7 -4
- package/src/rbac/security.ts +109 -18
- package/src/rbac/types.ts +12 -1
- package/src/services/AuthService.ts +2 -15
- package/src/services/EventService.ts +43 -46
- package/src/services/OrganisationService.ts +51 -31
- package/src/services/__tests__/AuthService.test.ts +1 -1
- package/src/services/__tests__/EventService.test.ts +1 -1
- package/src/services/__tests__/OrganisationService.test.ts +1 -1
- package/src/services/base/BaseService.ts +8 -0
- package/src/styles/base.css +208 -0
- package/src/styles/semantic.css +24 -0
- package/src/types/database.generated.ts +7347 -0
- package/src/types/database.ts +20 -0
- package/src/utils/logger.ts +179 -0
- package/src/utils/organisationContext.ts +11 -4
- package/src/utils/storage/__tests__/helpers.unit.test.ts +6 -2
- package/dist/appNameResolver-UURKN7NF.js +0 -22
- package/dist/audit-6TOCAMKO.js.map +0 -1
- package/dist/chunk-B2WTCLCV.js.map +0 -1
- package/dist/chunk-FGMFQSHX.js.map +0 -1
- package/dist/chunk-K34IM5CT.js.map +0 -1
- package/dist/chunk-KHJS6VIA.js.map +0 -1
- package/dist/chunk-KK73ZB4E.js.map +0 -1
- package/dist/chunk-M5IWZRBT.js.map +0 -1
- package/dist/chunk-ULBI5JGB.js +0 -109
- package/dist/chunk-ULBI5JGB.js.map +0 -1
- package/dist/chunk-WN6XJWOS.js.map +0 -1
- package/dist/chunk-XLZ7U46Z.js.map +0 -1
- package/dist/chunk-Y6TXWPJO.js.map +0 -1
- package/docs/DOCUMENTATION_CHECKLIST.md +0 -281
- package/docs/TERMINOLOGY.md +0 -231
- package/docs/api/interfaces/RBACContextType.md +0 -468
- package/docs/api/interfaces/RBACProviderProps.md +0 -107
- package/docs/best-practices/performance-expansion.md +0 -473
- package/docs/breaking-changes.md +0 -179
- package/docs/consuming-app-example.md +0 -290
- package/docs/documentation-templates.md +0 -539
- package/docs/examples/navigation-menu-auth-fix.md +0 -344
- package/docs/getting-started/examples/basic-auth-app.md +0 -520
- package/docs/getting-started/examples/full-featured-app.md +0 -616
- package/docs/getting-started/quick-start.md +0 -376
- package/docs/implementation-guides/datatable-filtering.md +0 -313
- package/docs/implementation-guides/datatable-rbac-usage.md +0 -317
- package/docs/implementation-guides/hierarchical-datatable.md +0 -850
- package/docs/implementation-guides/large-datasets.md +0 -281
- package/docs/implementation-guides/performance.md +0 -403
- package/docs/migration/quick-migration-guide.md +0 -320
- package/docs/migration-guide.md +0 -193
- package/docs/migration-guides/unified-auth-provider-mandatory-timeouts.md +0 -226
- package/docs/performance/README.md +0 -551
- package/docs/style-guide.md +0 -964
- package/docs/troubleshooting/authentication-issues.md +0 -334
- package/docs/troubleshooting/debugging.md +0 -1117
- package/docs/troubleshooting/migration.md +0 -918
- package/src/__tests__/hooks/usePermissions.test.ts +0 -261
- package/src/components/PaceAppLayout/__tests__/PaceAppLayout.rbac.test.tsx +0 -574
- package/src/hooks/__tests__/ServiceHooks.test.tsx +0 -613
- package/src/hooks/services/__tests__/useServiceHooks.test.tsx +0 -137
- package/src/hooks/services/usePermissions.ts +0 -70
- package/src/hooks/services/useRBACService.ts +0 -30
- package/src/hooks/usePermissionCheck.ts +0 -150
- package/src/providers/__tests__/ServiceProviders.test.tsx +0 -477
- package/src/providers/services/RBACServiceProvider.tsx +0 -79
- package/src/rbac/__tests__/integration.authflow.test.tsx +0 -119
- package/src/rbac/__tests__/integration.navigation.test.tsx +0 -69
- package/src/rbac/__tests__/integration.securedata.test.tsx +0 -92
- package/src/rbac/__tests__/integration.smoke.test.tsx +0 -73
- package/src/rbac/providers/RBACProvider.tsx +0 -645
- package/src/rbac/providers/__tests__/RBACProvider.integration.test.tsx +0 -688
- package/src/rbac/providers/__tests__/RBACProvider.test.tsx +0 -1186
- package/src/rbac/providers/index.ts +0 -11
- package/src/services/RBACService.ts +0 -522
- package/src/services/__tests__/RBACService.test.ts +0 -492
- package/src/services/interfaces/IRBACService.ts +0 -62
- package/src/utils/appNameResolver.test 2.ts +0 -494
- /package/dist/{DataTable-4GAVPIEG.js.map → DataTable-ETGVF4Y5.js.map} +0 -0
- /package/dist/{UnifiedAuthProvider-3NKDOSOK.js.map → UnifiedAuthProvider-P5SOJAQ6.js.map} +0 -0
- /package/dist/{api-DDMUKIUD.js.map → api-KG4A2X7P.js.map} +0 -0
- /package/dist/{appNameResolver-UURKN7NF.js.map → audit-65VNHEV2.js.map} +0 -0
- /package/dist/{chunk-NTNILOBC.js.map → chunk-5BO3MI5Y.js.map} +0 -0
- /package/dist/{chunk-URUTVZ7N.js.map → chunk-FL4ZCQLD.js.map} +0 -0
- /package/dist/{chunk-LW7MMEAQ.js.map → chunk-FT2M4R4F.js.map} +0 -0
- /package/dist/{chunk-AFGTSUAD.js.map → chunk-VSOKOFRF.js.map} +0 -0
- /package/docs/{app.css.example → styles/app.css.example} +0 -0
|
@@ -2,34 +2,25 @@ import {
|
|
|
2
2
|
createScopeFromEvent,
|
|
3
3
|
useAccessLevel,
|
|
4
4
|
useCan
|
|
5
|
-
} from "./chunk-
|
|
5
|
+
} from "./chunk-LRQ6RBJC.js";
|
|
6
6
|
import {
|
|
7
7
|
OrganisationContextRequiredError,
|
|
8
8
|
RBACCache,
|
|
9
9
|
getRBACLogger,
|
|
10
10
|
rbacCache
|
|
11
|
-
} from "./chunk-
|
|
11
|
+
} from "./chunk-S63MFSY6.js";
|
|
12
12
|
import {
|
|
13
13
|
useSecureDataAccess
|
|
14
|
-
} from "./chunk-
|
|
14
|
+
} from "./chunk-5BO3MI5Y.js";
|
|
15
15
|
import {
|
|
16
16
|
init_UnifiedAuthProvider
|
|
17
|
-
} from "./chunk-
|
|
17
|
+
} from "./chunk-FL4ZCQLD.js";
|
|
18
18
|
import {
|
|
19
19
|
useUnifiedAuth
|
|
20
|
-
} from "./chunk-
|
|
20
|
+
} from "./chunk-MNJXXD6C.js";
|
|
21
21
|
import {
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
} from "./chunk-ULBI5JGB.js";
|
|
25
|
-
import {
|
|
26
|
-
getCurrentAppName,
|
|
27
|
-
init_appNameResolver
|
|
28
|
-
} from "./chunk-5BSLGBYI.js";
|
|
29
|
-
import {
|
|
30
|
-
DebugLogger,
|
|
31
|
-
init_debugLogger
|
|
32
|
-
} from "./chunk-XLZ7U46Z.js";
|
|
22
|
+
getCurrentAppName
|
|
23
|
+
} from "./chunk-JCQZ6LA7.js";
|
|
33
24
|
|
|
34
25
|
// src/rbac/secureClient.ts
|
|
35
26
|
import { createClient } from "@supabase/supabase-js";
|
|
@@ -171,17 +162,17 @@ function PagePermissionProvider({
|
|
|
171
162
|
onStrictModeViolation,
|
|
172
163
|
maxHistorySize = 1e3
|
|
173
164
|
}) {
|
|
174
|
-
const { user,
|
|
165
|
+
const { user, selectedOrganisation, selectedEvent } = useUnifiedAuth();
|
|
175
166
|
const [pageAccessHistory, setPageAccessHistory] = useState([]);
|
|
176
167
|
const [isEnabled, setIsEnabled] = useState(true);
|
|
177
168
|
const currentScope = useMemo(() => {
|
|
178
|
-
if (!
|
|
169
|
+
if (!selectedOrganisation) return null;
|
|
179
170
|
return {
|
|
180
|
-
organisationId:
|
|
181
|
-
eventId:
|
|
171
|
+
organisationId: selectedOrganisation.id,
|
|
172
|
+
eventId: selectedEvent?.event_id || void 0,
|
|
182
173
|
appId: void 0
|
|
183
174
|
};
|
|
184
|
-
}, [
|
|
175
|
+
}, [selectedOrganisation, selectedEvent]);
|
|
185
176
|
const hasPagePermission = useCallback((pageName, operation, pageId, scope) => {
|
|
186
177
|
if (!isEnabled) return true;
|
|
187
178
|
if (!user?.id) return false;
|
|
@@ -257,7 +248,6 @@ function usePagePermissions() {
|
|
|
257
248
|
// src/rbac/components/PagePermissionGuard.tsx
|
|
258
249
|
import { useMemo as useMemo2, useEffect as useEffect2, useState as useState2, useRef } from "react";
|
|
259
250
|
init_UnifiedAuthProvider();
|
|
260
|
-
init_appNameResolver();
|
|
261
251
|
import { Fragment, jsx as jsx2, jsxs } from "react/jsx-runtime";
|
|
262
252
|
var PagePermissionGuardComponent = ({
|
|
263
253
|
pageName,
|
|
@@ -274,10 +264,11 @@ var PagePermissionGuardComponent = ({
|
|
|
274
264
|
const instanceId = useMemo2(() => Math.random().toString(36).substr(2, 9), []);
|
|
275
265
|
const renderCountRef = useRef(0);
|
|
276
266
|
renderCountRef.current += 1;
|
|
277
|
-
const { user,
|
|
267
|
+
const { user, selectedOrganisation, selectedEvent, supabase } = useUnifiedAuth();
|
|
278
268
|
const [hasChecked, setHasChecked] = useState2(false);
|
|
279
269
|
const [checkError, setCheckError] = useState2(null);
|
|
280
270
|
const [resolvedScope, setResolvedScope] = useState2(null);
|
|
271
|
+
const scopeResolutionAbortRef = useRef(null);
|
|
281
272
|
const supabaseRef = useRef(supabase);
|
|
282
273
|
supabaseRef.current = supabase;
|
|
283
274
|
const lastScopeRef = useRef(null);
|
|
@@ -304,9 +295,27 @@ var PagePermissionGuardComponent = ({
|
|
|
304
295
|
}
|
|
305
296
|
const stableScope = stableScopeRef.current;
|
|
306
297
|
useEffect2(() => {
|
|
298
|
+
const abortController = new AbortController();
|
|
299
|
+
scopeResolutionAbortRef.current?.abort();
|
|
300
|
+
scopeResolutionAbortRef.current = abortController;
|
|
301
|
+
const { signal } = abortController;
|
|
302
|
+
const safeSetResolvedScope = (value) => {
|
|
303
|
+
if (!signal.aborted) {
|
|
304
|
+
setResolvedScope(value);
|
|
305
|
+
}
|
|
306
|
+
};
|
|
307
|
+
const safeSetCheckError = (value) => {
|
|
308
|
+
if (!signal.aborted) {
|
|
309
|
+
setCheckError(value);
|
|
310
|
+
}
|
|
311
|
+
};
|
|
307
312
|
const resolveScope = async () => {
|
|
313
|
+
if (signal.aborted) {
|
|
314
|
+
return;
|
|
315
|
+
}
|
|
308
316
|
if (scope) {
|
|
309
|
-
|
|
317
|
+
safeSetResolvedScope(scope);
|
|
318
|
+
safeSetCheckError(null);
|
|
310
319
|
return;
|
|
311
320
|
}
|
|
312
321
|
let appId = void 0;
|
|
@@ -315,9 +324,18 @@ var PagePermissionGuardComponent = ({
|
|
|
315
324
|
if (appName) {
|
|
316
325
|
try {
|
|
317
326
|
const { data: app, error: error2 } = await supabaseRef.current.from("rbac_apps").select("id, name, is_active").eq("name", appName).eq("is_active", true).single();
|
|
327
|
+
if (signal.aborted) {
|
|
328
|
+
return;
|
|
329
|
+
}
|
|
318
330
|
if (error2) {
|
|
319
331
|
console.error("[PagePermissionGuard] Database error resolving app ID:", error2);
|
|
332
|
+
if (signal.aborted) {
|
|
333
|
+
return;
|
|
334
|
+
}
|
|
320
335
|
const { data: inactiveApp } = await supabaseRef.current.from("rbac_apps").select("id, name, is_active").eq("name", appName).single();
|
|
336
|
+
if (signal.aborted) {
|
|
337
|
+
return;
|
|
338
|
+
}
|
|
321
339
|
if (inactiveApp) {
|
|
322
340
|
console.error(`[PagePermissionGuard] App "${appName}" exists but is inactive (is_active: ${inactiveApp.is_active})`);
|
|
323
341
|
} else {
|
|
@@ -329,20 +347,26 @@ var PagePermissionGuardComponent = ({
|
|
|
329
347
|
console.error("[PagePermissionGuard] No app data returned for:", appName);
|
|
330
348
|
}
|
|
331
349
|
} catch (error2) {
|
|
350
|
+
if (signal.aborted) {
|
|
351
|
+
return;
|
|
352
|
+
}
|
|
332
353
|
console.error("[PagePermissionGuard] Unexpected error resolving app ID:", error2);
|
|
333
354
|
}
|
|
334
355
|
} else {
|
|
335
356
|
console.error("[PagePermissionGuard] No app name found. Make sure to call setRBACAppName() in your app setup.");
|
|
336
357
|
}
|
|
337
358
|
}
|
|
338
|
-
if (
|
|
359
|
+
if (signal.aborted) {
|
|
360
|
+
return;
|
|
361
|
+
}
|
|
362
|
+
if (selectedOrganisation && selectedEvent) {
|
|
339
363
|
if (!appId) {
|
|
340
364
|
if (import.meta.env.MODE === "test") {
|
|
341
365
|
console.warn("[PagePermissionGuard] App ID not resolved in test environment, proceeding without it");
|
|
342
366
|
} else {
|
|
343
367
|
console.error("[PagePermissionGuard] CRITICAL: App ID not resolved. Check console for details.");
|
|
344
|
-
|
|
345
|
-
|
|
368
|
+
safeSetCheckError(new Error("App ID not resolved. Check console for database errors."));
|
|
369
|
+
safeSetResolvedScope(null);
|
|
346
370
|
return;
|
|
347
371
|
}
|
|
348
372
|
}
|
|
@@ -350,28 +374,31 @@ var PagePermissionGuardComponent = ({
|
|
|
350
374
|
const uuidRegex = /^[0-9a-f]{8}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{12}$/i;
|
|
351
375
|
if (!uuidRegex.test(appId)) {
|
|
352
376
|
console.error("[PagePermissionGuard] CRITICAL: App ID is not a valid UUID:", appId);
|
|
353
|
-
|
|
354
|
-
|
|
377
|
+
safeSetCheckError(new Error(`Invalid app ID format: ${appId}. Expected UUID.`));
|
|
378
|
+
safeSetResolvedScope(null);
|
|
355
379
|
return;
|
|
356
380
|
}
|
|
357
381
|
}
|
|
358
|
-
const
|
|
359
|
-
organisationId:
|
|
360
|
-
eventId:
|
|
382
|
+
const resolvedContext = {
|
|
383
|
+
organisationId: selectedOrganisation.id,
|
|
384
|
+
eventId: selectedEvent.event_id,
|
|
361
385
|
appId
|
|
362
386
|
};
|
|
363
|
-
|
|
364
|
-
|
|
387
|
+
safeSetResolvedScope(resolvedContext);
|
|
388
|
+
safeSetCheckError(null);
|
|
389
|
+
return;
|
|
390
|
+
}
|
|
391
|
+
if (signal.aborted) {
|
|
365
392
|
return;
|
|
366
393
|
}
|
|
367
|
-
if (
|
|
394
|
+
if (selectedOrganisation) {
|
|
368
395
|
if (!appId) {
|
|
369
396
|
if (import.meta.env.MODE === "test") {
|
|
370
397
|
console.warn("[PagePermissionGuard] App ID not resolved in test environment, proceeding without it");
|
|
371
398
|
} else {
|
|
372
399
|
console.error("[PagePermissionGuard] CRITICAL: App ID not resolved. Check console for details.");
|
|
373
|
-
|
|
374
|
-
|
|
400
|
+
safeSetCheckError(new Error("App ID not resolved. Check console for database errors."));
|
|
401
|
+
safeSetResolvedScope(null);
|
|
375
402
|
return;
|
|
376
403
|
}
|
|
377
404
|
}
|
|
@@ -379,51 +406,69 @@ var PagePermissionGuardComponent = ({
|
|
|
379
406
|
const uuidRegex = /^[0-9a-f]{8}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{12}$/i;
|
|
380
407
|
if (!uuidRegex.test(appId)) {
|
|
381
408
|
console.error("[PagePermissionGuard] CRITICAL: App ID is not a valid UUID:", appId);
|
|
382
|
-
|
|
383
|
-
|
|
409
|
+
safeSetCheckError(new Error(`Invalid app ID format: ${appId}. Expected UUID.`));
|
|
410
|
+
safeSetResolvedScope(null);
|
|
384
411
|
return;
|
|
385
412
|
}
|
|
386
413
|
}
|
|
387
|
-
const
|
|
388
|
-
organisationId:
|
|
389
|
-
eventId:
|
|
414
|
+
const resolvedContext = {
|
|
415
|
+
organisationId: selectedOrganisation.id,
|
|
416
|
+
eventId: selectedEvent?.event_id || void 0,
|
|
390
417
|
appId
|
|
391
418
|
};
|
|
392
|
-
|
|
393
|
-
|
|
419
|
+
safeSetResolvedScope(resolvedContext);
|
|
420
|
+
safeSetCheckError(null);
|
|
394
421
|
return;
|
|
395
422
|
}
|
|
396
|
-
if (
|
|
423
|
+
if (signal.aborted) {
|
|
424
|
+
return;
|
|
425
|
+
}
|
|
426
|
+
if (selectedEvent && supabaseRef.current) {
|
|
397
427
|
try {
|
|
398
|
-
const eventScope = await createScopeFromEvent(supabaseRef.current,
|
|
428
|
+
const eventScope = await createScopeFromEvent(supabaseRef.current, selectedEvent.event_id);
|
|
429
|
+
if (signal.aborted) {
|
|
430
|
+
return;
|
|
431
|
+
}
|
|
399
432
|
if (!eventScope) {
|
|
400
|
-
|
|
401
|
-
|
|
433
|
+
safeSetCheckError(new Error("Could not resolve organization from event context"));
|
|
434
|
+
safeSetResolvedScope(null);
|
|
402
435
|
return;
|
|
403
436
|
}
|
|
404
|
-
|
|
437
|
+
safeSetResolvedScope({
|
|
405
438
|
...eventScope,
|
|
406
439
|
appId: appId || eventScope.appId
|
|
407
440
|
});
|
|
408
|
-
|
|
441
|
+
safeSetCheckError(null);
|
|
409
442
|
} catch (error2) {
|
|
410
|
-
|
|
411
|
-
|
|
443
|
+
if (signal.aborted) {
|
|
444
|
+
return;
|
|
445
|
+
}
|
|
446
|
+
safeSetCheckError(error2);
|
|
447
|
+
safeSetResolvedScope(null);
|
|
412
448
|
}
|
|
413
449
|
return;
|
|
414
450
|
}
|
|
415
|
-
|
|
451
|
+
if (signal.aborted) {
|
|
452
|
+
return;
|
|
453
|
+
}
|
|
454
|
+
const errorMessage = !selectedOrganisation && !selectedEvent ? "Either organisation context or event context is required for page permission checking" : "Insufficient context for permission checking. Please ensure you are properly authenticated and have selected an organisation or event.";
|
|
416
455
|
console.error("[PagePermissionGuard] Context resolution failed:", {
|
|
417
|
-
|
|
418
|
-
|
|
456
|
+
selectedOrganisation: selectedOrganisation ? selectedOrganisation.id : null,
|
|
457
|
+
selectedEvent: selectedEvent ? selectedEvent.event_id : null,
|
|
419
458
|
appId,
|
|
420
459
|
error: errorMessage
|
|
421
460
|
});
|
|
422
|
-
|
|
423
|
-
|
|
461
|
+
safeSetCheckError(new Error(errorMessage));
|
|
462
|
+
safeSetResolvedScope(null);
|
|
424
463
|
};
|
|
425
464
|
resolveScope();
|
|
426
|
-
|
|
465
|
+
return () => {
|
|
466
|
+
abortController.abort();
|
|
467
|
+
if (scopeResolutionAbortRef.current === abortController) {
|
|
468
|
+
scopeResolutionAbortRef.current = null;
|
|
469
|
+
}
|
|
470
|
+
};
|
|
471
|
+
}, [scope, selectedOrganisation, selectedEvent]);
|
|
427
472
|
const effectivePageId = useMemo2(() => {
|
|
428
473
|
return pageId || pageName;
|
|
429
474
|
}, [pageId, pageName]);
|
|
@@ -533,18 +578,18 @@ function SecureDataProvider({
|
|
|
533
578
|
maxHistorySize = 1e3,
|
|
534
579
|
enforceRLS = true
|
|
535
580
|
}) {
|
|
536
|
-
const { user,
|
|
581
|
+
const { user, selectedOrganisation, selectedEvent } = useUnifiedAuth();
|
|
537
582
|
const { validateContext } = useSecureDataAccess();
|
|
538
583
|
const [dataAccessHistory, setDataAccessHistory] = useState3([]);
|
|
539
584
|
const [isEnabled, setIsEnabled] = useState3(true);
|
|
540
585
|
const currentScope = useMemo3(() => {
|
|
541
|
-
if (!
|
|
586
|
+
if (!selectedOrganisation) return null;
|
|
542
587
|
return {
|
|
543
|
-
organisationId:
|
|
544
|
-
eventId:
|
|
588
|
+
organisationId: selectedOrganisation.id,
|
|
589
|
+
eventId: selectedEvent?.event_id || void 0,
|
|
545
590
|
appId: void 0
|
|
546
591
|
};
|
|
547
|
-
}, [
|
|
592
|
+
}, [selectedOrganisation, selectedEvent]);
|
|
548
593
|
const isDataAccessAllowed = useCallback3((table, operation, scope) => {
|
|
549
594
|
if (!isEnabled) return true;
|
|
550
595
|
if (!user?.id) return false;
|
|
@@ -654,7 +699,7 @@ function PermissionEnforcer({
|
|
|
654
699
|
loading = /* @__PURE__ */ jsx4(DefaultLoading2, {}),
|
|
655
700
|
requireAll = true
|
|
656
701
|
}) {
|
|
657
|
-
const { user,
|
|
702
|
+
const { user, selectedOrganisation, selectedEvent, supabase } = useUnifiedAuth();
|
|
658
703
|
const [hasChecked, setHasChecked] = useState4(false);
|
|
659
704
|
const [checkError, setCheckError] = useState4(null);
|
|
660
705
|
const [permissionResults, setPermissionResults] = useState4({});
|
|
@@ -665,25 +710,25 @@ function PermissionEnforcer({
|
|
|
665
710
|
setResolvedScope(scope);
|
|
666
711
|
return;
|
|
667
712
|
}
|
|
668
|
-
if (
|
|
713
|
+
if (selectedOrganisation && selectedEvent) {
|
|
669
714
|
setResolvedScope({
|
|
670
|
-
organisationId:
|
|
671
|
-
eventId:
|
|
715
|
+
organisationId: selectedOrganisation.id,
|
|
716
|
+
eventId: selectedEvent.event_id,
|
|
672
717
|
appId: void 0
|
|
673
718
|
});
|
|
674
719
|
return;
|
|
675
720
|
}
|
|
676
|
-
if (
|
|
721
|
+
if (selectedOrganisation) {
|
|
677
722
|
setResolvedScope({
|
|
678
|
-
organisationId:
|
|
679
|
-
eventId:
|
|
723
|
+
organisationId: selectedOrganisation.id,
|
|
724
|
+
eventId: selectedEvent?.event_id || void 0,
|
|
680
725
|
appId: void 0
|
|
681
726
|
});
|
|
682
727
|
return;
|
|
683
728
|
}
|
|
684
|
-
if (
|
|
729
|
+
if (selectedEvent && supabase) {
|
|
685
730
|
try {
|
|
686
|
-
const eventScope = await createScopeFromEvent(supabase,
|
|
731
|
+
const eventScope = await createScopeFromEvent(supabase, selectedEvent.event_id);
|
|
687
732
|
if (!eventScope) {
|
|
688
733
|
setCheckError(new Error("Could not resolve organization from event context"));
|
|
689
734
|
return;
|
|
@@ -697,11 +742,11 @@ function PermissionEnforcer({
|
|
|
697
742
|
setCheckError(new Error("Either organisation context or event context is required for permission checking"));
|
|
698
743
|
};
|
|
699
744
|
resolveScope();
|
|
700
|
-
}, [scope,
|
|
745
|
+
}, [scope, selectedOrganisation, selectedEvent, supabase]);
|
|
701
746
|
const representativePermission = permissions[0];
|
|
702
747
|
const { can, isLoading, error } = useCan(
|
|
703
748
|
user?.id || "",
|
|
704
|
-
resolvedScope || { eventId:
|
|
749
|
+
resolvedScope || { eventId: selectedEvent?.event_id || void 0 },
|
|
705
750
|
representativePermission,
|
|
706
751
|
void 0,
|
|
707
752
|
true
|
|
@@ -799,19 +844,19 @@ function RoleBasedRouter({
|
|
|
799
844
|
maxHistorySize = 1e3,
|
|
800
845
|
unauthorizedComponent: UnauthorizedComponent = DefaultUnauthorizedComponent
|
|
801
846
|
}) {
|
|
802
|
-
const { user,
|
|
847
|
+
const { user, selectedOrganisation, selectedEvent } = useUnifiedAuth();
|
|
803
848
|
const location = useLocation();
|
|
804
849
|
const navigate = useNavigate();
|
|
805
850
|
const [routeAccessHistory, setRouteAccessHistory] = useState5([]);
|
|
806
851
|
const [currentRoute, setCurrentRoute] = useState5("");
|
|
807
852
|
const currentScope = useMemo5(() => {
|
|
808
|
-
if (!
|
|
853
|
+
if (!selectedOrganisation) return null;
|
|
809
854
|
return {
|
|
810
|
-
organisationId:
|
|
811
|
-
eventId:
|
|
855
|
+
organisationId: selectedOrganisation.id,
|
|
856
|
+
eventId: selectedEvent?.event_id || void 0,
|
|
812
857
|
appId: void 0
|
|
813
858
|
};
|
|
814
|
-
}, [
|
|
859
|
+
}, [selectedOrganisation, selectedEvent]);
|
|
815
860
|
const currentRouteConfig = useMemo5(() => {
|
|
816
861
|
const currentPath = location.pathname;
|
|
817
862
|
return routes.find((route) => route.path === currentPath) || null;
|
|
@@ -977,22 +1022,39 @@ function NavigationProvider({
|
|
|
977
1022
|
onStrictModeViolation,
|
|
978
1023
|
maxHistorySize = 1e3
|
|
979
1024
|
}) {
|
|
980
|
-
const { user,
|
|
1025
|
+
const { user, selectedOrganisation, selectedEvent } = useUnifiedAuth();
|
|
981
1026
|
const [navigationAccessHistory, setNavigationAccessHistory] = useState6([]);
|
|
982
1027
|
const [isEnabled, setIsEnabled] = useState6(true);
|
|
983
1028
|
const currentScope = useMemo6(() => {
|
|
984
|
-
if (!
|
|
1029
|
+
if (!selectedOrganisation) return null;
|
|
985
1030
|
return {
|
|
986
|
-
organisationId:
|
|
987
|
-
eventId:
|
|
1031
|
+
organisationId: selectedOrganisation.id,
|
|
1032
|
+
eventId: selectedEvent?.event_id || void 0,
|
|
988
1033
|
appId: void 0
|
|
989
1034
|
};
|
|
990
|
-
}, [
|
|
1035
|
+
}, [selectedOrganisation, selectedEvent]);
|
|
991
1036
|
const hasNavigationPermission = useCallback6((item) => {
|
|
992
1037
|
if (!isEnabled) return true;
|
|
993
1038
|
if (!user?.id) return false;
|
|
994
1039
|
if (!currentScope) return false;
|
|
995
|
-
|
|
1040
|
+
if (!item.permissions || item.permissions.length === 0) {
|
|
1041
|
+
console.warn(`[NavigationProvider] Navigation item "${item.id}" has no permissions defined - denying access`);
|
|
1042
|
+
return false;
|
|
1043
|
+
}
|
|
1044
|
+
const permission = item.permissions[0];
|
|
1045
|
+
const { can, error } = useCan(
|
|
1046
|
+
user.id,
|
|
1047
|
+
currentScope,
|
|
1048
|
+
permission,
|
|
1049
|
+
item.pageId,
|
|
1050
|
+
true
|
|
1051
|
+
// useCache
|
|
1052
|
+
);
|
|
1053
|
+
if (error) {
|
|
1054
|
+
console.warn(`[NavigationProvider] Permission check error for "${item.id}": ${error.message} - allowing access for graceful degradation`);
|
|
1055
|
+
return true;
|
|
1056
|
+
}
|
|
1057
|
+
return can;
|
|
996
1058
|
}, [isEnabled, user?.id, currentScope]);
|
|
997
1059
|
const getNavigationPermissions = useCallback6(() => {
|
|
998
1060
|
if (!isEnabled || !user?.id) return {};
|
|
@@ -1081,7 +1143,7 @@ function NavigationGuard({
|
|
|
1081
1143
|
loading = /* @__PURE__ */ jsx7(DefaultLoading3, {}),
|
|
1082
1144
|
requireAll = true
|
|
1083
1145
|
}) {
|
|
1084
|
-
const { user,
|
|
1146
|
+
const { user, selectedOrganisation, selectedEvent, supabase } = useUnifiedAuth();
|
|
1085
1147
|
const [hasChecked, setHasChecked] = useState7(false);
|
|
1086
1148
|
const [checkError, setCheckError] = useState7(null);
|
|
1087
1149
|
const [resolvedScope, setResolvedScope] = useState7(null);
|
|
@@ -1091,25 +1153,25 @@ function NavigationGuard({
|
|
|
1091
1153
|
setResolvedScope(scope);
|
|
1092
1154
|
return;
|
|
1093
1155
|
}
|
|
1094
|
-
if (
|
|
1156
|
+
if (selectedOrganisation && selectedEvent) {
|
|
1095
1157
|
setResolvedScope({
|
|
1096
|
-
organisationId:
|
|
1097
|
-
eventId:
|
|
1158
|
+
organisationId: selectedOrganisation.id,
|
|
1159
|
+
eventId: selectedEvent.event_id,
|
|
1098
1160
|
appId: void 0
|
|
1099
1161
|
});
|
|
1100
1162
|
return;
|
|
1101
1163
|
}
|
|
1102
|
-
if (
|
|
1164
|
+
if (selectedOrganisation) {
|
|
1103
1165
|
setResolvedScope({
|
|
1104
|
-
organisationId:
|
|
1105
|
-
eventId:
|
|
1166
|
+
organisationId: selectedOrganisation.id,
|
|
1167
|
+
eventId: selectedEvent?.event_id || void 0,
|
|
1106
1168
|
appId: void 0
|
|
1107
1169
|
});
|
|
1108
1170
|
return;
|
|
1109
1171
|
}
|
|
1110
|
-
if (
|
|
1172
|
+
if (selectedEvent && supabase) {
|
|
1111
1173
|
try {
|
|
1112
|
-
const eventScope = await createScopeFromEvent(supabase,
|
|
1174
|
+
const eventScope = await createScopeFromEvent(supabase, selectedEvent.event_id);
|
|
1113
1175
|
if (!eventScope) {
|
|
1114
1176
|
setCheckError(new Error("Could not resolve organization from event context"));
|
|
1115
1177
|
return;
|
|
@@ -1123,11 +1185,11 @@ function NavigationGuard({
|
|
|
1123
1185
|
setCheckError(new Error("Either organisation context or event context is required for navigation permission checking"));
|
|
1124
1186
|
};
|
|
1125
1187
|
resolveScope();
|
|
1126
|
-
}, [scope,
|
|
1188
|
+
}, [scope, selectedOrganisation, selectedEvent, supabase]);
|
|
1127
1189
|
const representativePermission = navigationItem.permissions[0];
|
|
1128
1190
|
const { can, isLoading, error } = useCan(
|
|
1129
1191
|
user?.id || "",
|
|
1130
|
-
resolvedScope || { eventId:
|
|
1192
|
+
resolvedScope || { eventId: selectedEvent?.event_id || void 0 },
|
|
1131
1193
|
representativePermission,
|
|
1132
1194
|
navigationItem.pageId,
|
|
1133
1195
|
true
|
|
@@ -1341,467 +1403,9 @@ function EnhancedNavigationMenu({
|
|
|
1341
1403
|
}) });
|
|
1342
1404
|
}
|
|
1343
1405
|
|
|
1344
|
-
// src/rbac/providers/RBACProvider.tsx
|
|
1345
|
-
init_unified();
|
|
1346
|
-
init_debugLogger();
|
|
1347
|
-
import { createContext as createContext5, useContext as useContext5, useState as useState9, useEffect as useEffect9, useCallback as useCallback9, useMemo as useMemo9 } from "react";
|
|
1348
|
-
import { jsx as jsx9 } from "react/jsx-runtime";
|
|
1349
|
-
var RBACContext = createContext5(void 0);
|
|
1350
|
-
var useRBAC = () => {
|
|
1351
|
-
const context = useContext5(RBACContext);
|
|
1352
|
-
if (!context) {
|
|
1353
|
-
throw new Error("useRBAC must be used within an RBACProvider");
|
|
1354
|
-
}
|
|
1355
|
-
return context;
|
|
1356
|
-
};
|
|
1357
|
-
var STORAGE_KEYS = {
|
|
1358
|
-
SELECTED_EVENT: "pace-core-selected-event"
|
|
1359
|
-
};
|
|
1360
|
-
var transformRBACPermissions = (rbacData, _appName) => {
|
|
1361
|
-
const permissions = {};
|
|
1362
|
-
let roles = [];
|
|
1363
|
-
let access_level = "viewer" /* VIEWER */;
|
|
1364
|
-
if (!rbacData || !Array.isArray(rbacData)) {
|
|
1365
|
-
return { permissions: {}, roles: ["viewer"], access_level: "viewer" /* VIEWER */ };
|
|
1366
|
-
}
|
|
1367
|
-
const superAdminPerm = rbacData.find((p) => p.permission_type === "all_permissions");
|
|
1368
|
-
if (superAdminPerm) {
|
|
1369
|
-
return {
|
|
1370
|
-
permissions: { "all:all": true },
|
|
1371
|
-
roles: ["super"],
|
|
1372
|
-
access_level: "super" /* SUPER */
|
|
1373
|
-
};
|
|
1374
|
-
}
|
|
1375
|
-
const eventAppPerms = rbacData.filter((p) => p.permission_type === "event_app_access");
|
|
1376
|
-
if (eventAppPerms.length > 0) {
|
|
1377
|
-
const role = eventAppPerms[0].role_name;
|
|
1378
|
-
switch (role) {
|
|
1379
|
-
case "event_admin":
|
|
1380
|
-
access_level = "admin" /* ADMIN */;
|
|
1381
|
-
roles = ["admin"];
|
|
1382
|
-
break;
|
|
1383
|
-
case "planner":
|
|
1384
|
-
access_level = "planner" /* PLANNER */;
|
|
1385
|
-
roles = ["planner"];
|
|
1386
|
-
break;
|
|
1387
|
-
case "participant":
|
|
1388
|
-
access_level = "participant" /* PARTICIPANT */;
|
|
1389
|
-
roles = ["participant"];
|
|
1390
|
-
break;
|
|
1391
|
-
case "editor":
|
|
1392
|
-
access_level = "editor" /* EDITOR */;
|
|
1393
|
-
roles = ["editor"];
|
|
1394
|
-
break;
|
|
1395
|
-
case "viewer":
|
|
1396
|
-
default:
|
|
1397
|
-
access_level = "viewer" /* VIEWER */;
|
|
1398
|
-
roles = ["viewer"];
|
|
1399
|
-
break;
|
|
1400
|
-
}
|
|
1401
|
-
const basePermissions = ["read"];
|
|
1402
|
-
if (["event_admin", "planner"].includes(role)) {
|
|
1403
|
-
basePermissions.push("create", "update");
|
|
1404
|
-
}
|
|
1405
|
-
if (role === "event_admin") {
|
|
1406
|
-
basePermissions.push("delete");
|
|
1407
|
-
}
|
|
1408
|
-
basePermissions.forEach((operation) => {
|
|
1409
|
-
permissions[`default:${operation}`] = true;
|
|
1410
|
-
});
|
|
1411
|
-
}
|
|
1412
|
-
const orgPerms = rbacData.filter((p) => p.permission_type === "organisation_access");
|
|
1413
|
-
if (orgPerms.length > 0) {
|
|
1414
|
-
const role = orgPerms[0].role_name;
|
|
1415
|
-
if (role === "org_admin") {
|
|
1416
|
-
access_level = "admin" /* ADMIN */;
|
|
1417
|
-
roles = ["admin"];
|
|
1418
|
-
["create", "read", "update", "delete"].forEach((operation) => {
|
|
1419
|
-
permissions[`default:${operation}`] = true;
|
|
1420
|
-
});
|
|
1421
|
-
}
|
|
1422
|
-
}
|
|
1423
|
-
return { permissions, roles, access_level };
|
|
1424
|
-
};
|
|
1425
|
-
function RBACProvider({
|
|
1426
|
-
children,
|
|
1427
|
-
supabaseClient,
|
|
1428
|
-
user,
|
|
1429
|
-
session,
|
|
1430
|
-
appName,
|
|
1431
|
-
enableRBAC = false,
|
|
1432
|
-
persistState = true,
|
|
1433
|
-
enablePersistence,
|
|
1434
|
-
requireOrganisationContext: _requireOrganisationContext = true
|
|
1435
|
-
}) {
|
|
1436
|
-
const shouldPersist = enablePersistence !== void 0 ? enablePersistence : persistState;
|
|
1437
|
-
const [permissions, setPermissions] = useState9({});
|
|
1438
|
-
const [roles, setRoles] = useState9([]);
|
|
1439
|
-
const [accessLevel, setAccessLevel] = useState9("viewer" /* VIEWER */);
|
|
1440
|
-
const [rbacLoading, setRbacLoading] = useState9(false);
|
|
1441
|
-
const [rbacError, setRbacError] = useState9(null);
|
|
1442
|
-
const [selectedEventId, setSelectedEventId] = useState9(null);
|
|
1443
|
-
const [appConfig, setAppConfig] = useState9(null);
|
|
1444
|
-
const [userEventAccess, setUserEventAccess] = useState9([]);
|
|
1445
|
-
const [eventAccessLoading, setEventAccessLoading] = useState9(false);
|
|
1446
|
-
const [selectedOrganisationId, _setSelectedOrganisationId] = useState9(null);
|
|
1447
|
-
useEffect9(() => {
|
|
1448
|
-
if (!supabaseClient) return;
|
|
1449
|
-
const loadAppConfig = async () => {
|
|
1450
|
-
try {
|
|
1451
|
-
const { getCurrentAppName: getCurrentAppName2 } = await import("./appNameResolver-UURKN7NF.js");
|
|
1452
|
-
const resolvedAppName = getCurrentAppName2() || appName;
|
|
1453
|
-
const { data: appData, error: appError } = await supabaseClient.from("rbac_apps").select("id").eq("name", resolvedAppName).eq("is_active", true).single();
|
|
1454
|
-
if (appError || !appData) {
|
|
1455
|
-
console.warn("App not found or inactive:", resolvedAppName);
|
|
1456
|
-
setAppConfig({
|
|
1457
|
-
supports_direct_access: false,
|
|
1458
|
-
// Field removed from rbac_apps table
|
|
1459
|
-
requires_event: true
|
|
1460
|
-
});
|
|
1461
|
-
return;
|
|
1462
|
-
}
|
|
1463
|
-
const response = await supabaseClient.rpc("get_app_config", {
|
|
1464
|
-
app_id: appData.id
|
|
1465
|
-
});
|
|
1466
|
-
const { data } = response || {};
|
|
1467
|
-
if (data && data.length > 0) {
|
|
1468
|
-
setAppConfig({
|
|
1469
|
-
supports_direct_access: false,
|
|
1470
|
-
// Field removed from rbac_apps table
|
|
1471
|
-
requires_event: data[0].requires_event
|
|
1472
|
-
});
|
|
1473
|
-
} else {
|
|
1474
|
-
setAppConfig({
|
|
1475
|
-
supports_direct_access: false,
|
|
1476
|
-
requires_event: true
|
|
1477
|
-
});
|
|
1478
|
-
}
|
|
1479
|
-
} catch (error) {
|
|
1480
|
-
console.warn("Clearing corrupted localStorage data");
|
|
1481
|
-
if (typeof localStorage !== "undefined") {
|
|
1482
|
-
localStorage.removeItem(STORAGE_KEYS.SELECTED_EVENT);
|
|
1483
|
-
}
|
|
1484
|
-
console.warn("Failed to load app configuration:", error);
|
|
1485
|
-
setAppConfig({
|
|
1486
|
-
supports_direct_access: false,
|
|
1487
|
-
// Field removed from rbac_apps table
|
|
1488
|
-
requires_event: true
|
|
1489
|
-
});
|
|
1490
|
-
}
|
|
1491
|
-
};
|
|
1492
|
-
loadAppConfig();
|
|
1493
|
-
}, [supabaseClient, appName]);
|
|
1494
|
-
useEffect9(() => {
|
|
1495
|
-
const isSuperAdmin = user?.user_metadata?.globalRole === "super_admin";
|
|
1496
|
-
if (isSuperAdmin) {
|
|
1497
|
-
setRoles(["super_admin"]);
|
|
1498
|
-
} else {
|
|
1499
|
-
setRoles([]);
|
|
1500
|
-
}
|
|
1501
|
-
}, [user]);
|
|
1502
|
-
useEffect9(() => {
|
|
1503
|
-
if (!shouldPersist) return;
|
|
1504
|
-
try {
|
|
1505
|
-
const persistedEvent = localStorage.getItem(STORAGE_KEYS.SELECTED_EVENT);
|
|
1506
|
-
if (persistedEvent) {
|
|
1507
|
-
setSelectedEventId(JSON.parse(persistedEvent));
|
|
1508
|
-
}
|
|
1509
|
-
} catch (error) {
|
|
1510
|
-
console.warn("Clearing corrupted localStorage data");
|
|
1511
|
-
localStorage.removeItem(STORAGE_KEYS.SELECTED_EVENT);
|
|
1512
|
-
}
|
|
1513
|
-
}, [shouldPersist]);
|
|
1514
|
-
useEffect9(() => {
|
|
1515
|
-
if (!shouldPersist) return;
|
|
1516
|
-
try {
|
|
1517
|
-
if (selectedEventId) {
|
|
1518
|
-
localStorage.setItem(
|
|
1519
|
-
STORAGE_KEYS.SELECTED_EVENT,
|
|
1520
|
-
JSON.stringify(selectedEventId)
|
|
1521
|
-
);
|
|
1522
|
-
} else {
|
|
1523
|
-
localStorage.removeItem(STORAGE_KEYS.SELECTED_EVENT);
|
|
1524
|
-
}
|
|
1525
|
-
} catch (error) {
|
|
1526
|
-
console.warn("Clearing corrupted localStorage data");
|
|
1527
|
-
localStorage.removeItem(STORAGE_KEYS.SELECTED_EVENT);
|
|
1528
|
-
console.warn("Failed to persist auth state:", error);
|
|
1529
|
-
}
|
|
1530
|
-
}, [selectedEventId, shouldPersist]);
|
|
1531
|
-
const refreshPermissions = useCallback9(async (eventId) => {
|
|
1532
|
-
if (!supabaseClient || !user || !appConfig || !session) {
|
|
1533
|
-
DebugLogger.log("RBACProvider", "refreshPermissions: Missing required dependencies, clearing permissions");
|
|
1534
|
-
setPermissions({});
|
|
1535
|
-
setRoles([]);
|
|
1536
|
-
setAccessLevel("viewer" /* VIEWER */);
|
|
1537
|
-
return;
|
|
1538
|
-
}
|
|
1539
|
-
const { data: globalRoles } = await supabaseClient.from("rbac_global_roles").select("role").eq("user_id", user.id).eq("role", "super_admin").lte("valid_from", (/* @__PURE__ */ new Date()).toISOString()).or(`valid_to.is.null,valid_to.gte.${(/* @__PURE__ */ new Date()).toISOString()}`).limit(1);
|
|
1540
|
-
const isSuperAdmin = globalRoles && globalRoles.length > 0;
|
|
1541
|
-
if (isSuperAdmin) {
|
|
1542
|
-
setPermissions({
|
|
1543
|
-
"admin:create": true,
|
|
1544
|
-
"admin:read": true,
|
|
1545
|
-
"admin:update": true,
|
|
1546
|
-
"admin:delete": true,
|
|
1547
|
-
"users:create": true,
|
|
1548
|
-
"users:read": true,
|
|
1549
|
-
"users:update": true,
|
|
1550
|
-
"users:delete": true,
|
|
1551
|
-
"events:create": true,
|
|
1552
|
-
"events:read": true,
|
|
1553
|
-
"events:update": true,
|
|
1554
|
-
"events:delete": true
|
|
1555
|
-
});
|
|
1556
|
-
setRoles(["super_admin"]);
|
|
1557
|
-
setAccessLevel("super" /* SUPER */);
|
|
1558
|
-
return;
|
|
1559
|
-
}
|
|
1560
|
-
const shouldLoadDirectPermissions = !eventId && !appConfig.requires_event;
|
|
1561
|
-
const shouldLoadEventPermissions = eventId;
|
|
1562
|
-
const shouldClearPermissions = !eventId && appConfig.requires_event;
|
|
1563
|
-
if (shouldClearPermissions) {
|
|
1564
|
-
setPermissions({});
|
|
1565
|
-
setRoles([]);
|
|
1566
|
-
setAccessLevel("viewer" /* VIEWER */);
|
|
1567
|
-
return;
|
|
1568
|
-
}
|
|
1569
|
-
if (!shouldLoadDirectPermissions && !shouldLoadEventPermissions) {
|
|
1570
|
-
return;
|
|
1571
|
-
}
|
|
1572
|
-
setRbacLoading(true);
|
|
1573
|
-
setRbacError(null);
|
|
1574
|
-
try {
|
|
1575
|
-
const { getCurrentAppName: getCurrentAppName2 } = await import("./appNameResolver-UURKN7NF.js");
|
|
1576
|
-
const resolvedAppName = getCurrentAppName2() || appName;
|
|
1577
|
-
const { data: appData, error: appError } = await supabaseClient.from("rbac_apps").select("id").eq("name", resolvedAppName).eq("is_active", true).single();
|
|
1578
|
-
if (appError || !appData) {
|
|
1579
|
-
console.warn("App not found or inactive:", resolvedAppName);
|
|
1580
|
-
setRbacLoading(false);
|
|
1581
|
-
return;
|
|
1582
|
-
}
|
|
1583
|
-
const { data, error } = await supabaseClient.rpc("rbac_permissions_get", {
|
|
1584
|
-
p_user_id: user.id,
|
|
1585
|
-
p_app_id: appData.id,
|
|
1586
|
-
p_event_id: eventId || null,
|
|
1587
|
-
p_organisation_id: selectedOrganisationId || null
|
|
1588
|
-
});
|
|
1589
|
-
if (error) {
|
|
1590
|
-
throw error;
|
|
1591
|
-
}
|
|
1592
|
-
const { permissions: permissions2, roles: roles2, access_level } = transformRBACPermissions(data, appName);
|
|
1593
|
-
setPermissions(permissions2);
|
|
1594
|
-
setRoles(roles2);
|
|
1595
|
-
setAccessLevel(access_level);
|
|
1596
|
-
} catch (err) {
|
|
1597
|
-
setRbacError(err);
|
|
1598
|
-
} finally {
|
|
1599
|
-
setRbacLoading(false);
|
|
1600
|
-
}
|
|
1601
|
-
}, [supabaseClient, user, session, appName, appConfig, selectedOrganisationId]);
|
|
1602
|
-
const loadUserEventAccess = useCallback9(async () => {
|
|
1603
|
-
if (!supabaseClient || !user || !session) {
|
|
1604
|
-
DebugLogger.log("RBACProvider", "loadUserEventAccess: Missing required dependencies, clearing event access");
|
|
1605
|
-
setUserEventAccess([]);
|
|
1606
|
-
return;
|
|
1607
|
-
}
|
|
1608
|
-
setEventAccessLoading(true);
|
|
1609
|
-
try {
|
|
1610
|
-
const { getCurrentAppName: getCurrentAppName2 } = await import("./appNameResolver-UURKN7NF.js");
|
|
1611
|
-
const resolvedAppName = getCurrentAppName2() || appName;
|
|
1612
|
-
const { data: appData, error: appError } = await supabaseClient.from("rbac_apps").select("id").eq("name", resolvedAppName).eq("is_active", true).single();
|
|
1613
|
-
if (appError || !appData) {
|
|
1614
|
-
console.warn("App not found or inactive:", resolvedAppName);
|
|
1615
|
-
setEventAccessLoading(false);
|
|
1616
|
-
return;
|
|
1617
|
-
}
|
|
1618
|
-
const { data, error } = await supabaseClient.from("rbac_event_app_roles").select(`
|
|
1619
|
-
event_id,
|
|
1620
|
-
role,
|
|
1621
|
-
granted_at
|
|
1622
|
-
`).eq("user_id", user.id).eq("app_id", appData.id);
|
|
1623
|
-
if (error) {
|
|
1624
|
-
console.error("Failed to load user event access:", error);
|
|
1625
|
-
setUserEventAccess([]);
|
|
1626
|
-
return;
|
|
1627
|
-
}
|
|
1628
|
-
const eventAccess = data?.map((item) => ({
|
|
1629
|
-
event_id: item.event_id,
|
|
1630
|
-
event_name: "Unknown Event",
|
|
1631
|
-
// Event details not available in this query
|
|
1632
|
-
event_description: null,
|
|
1633
|
-
// Not available in this schema
|
|
1634
|
-
start_date: "",
|
|
1635
|
-
// Event date not available in this query
|
|
1636
|
-
end_date: "",
|
|
1637
|
-
// Event date not available in this query
|
|
1638
|
-
event_status: "unknown",
|
|
1639
|
-
// Not available in this schema
|
|
1640
|
-
app_id: appData.id,
|
|
1641
|
-
access_level: item.role,
|
|
1642
|
-
// Map role to access_level
|
|
1643
|
-
granted_at: item.granted_at,
|
|
1644
|
-
organisation_id: ""
|
|
1645
|
-
// Will be populated from event's organisation_id if needed
|
|
1646
|
-
})) || [];
|
|
1647
|
-
setUserEventAccess(eventAccess);
|
|
1648
|
-
} catch (error) {
|
|
1649
|
-
console.warn("Clearing corrupted localStorage data");
|
|
1650
|
-
localStorage.removeItem(STORAGE_KEYS.SELECTED_EVENT);
|
|
1651
|
-
console.error("Error loading user event access:", error);
|
|
1652
|
-
setUserEventAccess([]);
|
|
1653
|
-
} finally {
|
|
1654
|
-
setEventAccessLoading(false);
|
|
1655
|
-
}
|
|
1656
|
-
}, [supabaseClient, user, session, appName]);
|
|
1657
|
-
const getUserEventAccess = useCallback9((eventId) => {
|
|
1658
|
-
return userEventAccess.find((access) => access.event_id === eventId);
|
|
1659
|
-
}, [userEventAccess]);
|
|
1660
|
-
useEffect9(() => {
|
|
1661
|
-
if (!user || !appConfig || !session) {
|
|
1662
|
-
DebugLogger.log("RBACProvider", "Skipping permission refresh - no user, session, or app config");
|
|
1663
|
-
return;
|
|
1664
|
-
}
|
|
1665
|
-
const isSuperAdmin = user?.user_metadata?.globalRole === "super_admin";
|
|
1666
|
-
if (isSuperAdmin) {
|
|
1667
|
-
setPermissions({
|
|
1668
|
-
"admin:create": true,
|
|
1669
|
-
"admin:read": true,
|
|
1670
|
-
"admin:update": true,
|
|
1671
|
-
"admin:delete": true,
|
|
1672
|
-
"users:create": true,
|
|
1673
|
-
"users:read": true,
|
|
1674
|
-
"users:update": true,
|
|
1675
|
-
"users:delete": true,
|
|
1676
|
-
"events:create": true,
|
|
1677
|
-
"events:read": true,
|
|
1678
|
-
"events:update": true,
|
|
1679
|
-
"events:delete": true
|
|
1680
|
-
});
|
|
1681
|
-
setRoles(["super_admin"]);
|
|
1682
|
-
setAccessLevel("admin" /* ADMIN */);
|
|
1683
|
-
return;
|
|
1684
|
-
}
|
|
1685
|
-
if (selectedEventId) {
|
|
1686
|
-
refreshPermissions(selectedEventId);
|
|
1687
|
-
} else if (!appConfig.requires_event) {
|
|
1688
|
-
refreshPermissions();
|
|
1689
|
-
} else {
|
|
1690
|
-
setPermissions({});
|
|
1691
|
-
setRoles([]);
|
|
1692
|
-
setAccessLevel("viewer" /* VIEWER */);
|
|
1693
|
-
}
|
|
1694
|
-
}, [selectedEventId, user, session, appConfig, refreshPermissions]);
|
|
1695
|
-
useEffect9(() => {
|
|
1696
|
-
let isMounted = true;
|
|
1697
|
-
if (user && session) {
|
|
1698
|
-
DebugLogger.log("RBACProvider", "Loading user event access for authenticated user");
|
|
1699
|
-
loadUserEventAccess().catch((error) => {
|
|
1700
|
-
if (isMounted) {
|
|
1701
|
-
console.error("Error loading user event access:", error);
|
|
1702
|
-
}
|
|
1703
|
-
});
|
|
1704
|
-
} else {
|
|
1705
|
-
DebugLogger.log("RBACProvider", "Clearing user event access - no user or session");
|
|
1706
|
-
if (isMounted) {
|
|
1707
|
-
setUserEventAccess([]);
|
|
1708
|
-
}
|
|
1709
|
-
}
|
|
1710
|
-
return () => {
|
|
1711
|
-
isMounted = false;
|
|
1712
|
-
};
|
|
1713
|
-
}, [user, session, loadUserEventAccess]);
|
|
1714
|
-
const hasPermission2 = useCallback9((permission) => {
|
|
1715
|
-
const hasPerm = !!permissions[permission];
|
|
1716
|
-
return hasPerm;
|
|
1717
|
-
}, [permissions]);
|
|
1718
|
-
const hasAnyPermission2 = useCallback9((perms) => perms.some((p) => !!permissions[p]), [permissions]);
|
|
1719
|
-
const hasAllPermissions2 = useCallback9((perms) => perms.every((p) => !!permissions[p]), [permissions]);
|
|
1720
|
-
const hasRole = useCallback9((role) => {
|
|
1721
|
-
const isSuperAdmin = user?.user_metadata?.globalRole === "super_admin";
|
|
1722
|
-
if (role.toLowerCase() === "super_admin") {
|
|
1723
|
-
return isSuperAdmin;
|
|
1724
|
-
}
|
|
1725
|
-
return roles.includes(role);
|
|
1726
|
-
}, [roles, user]);
|
|
1727
|
-
const hasAccessLevel = useCallback9((level) => {
|
|
1728
|
-
const levels = Object.values(AccessLevel);
|
|
1729
|
-
return levels.indexOf(accessLevel) >= levels.indexOf(level);
|
|
1730
|
-
}, [accessLevel]);
|
|
1731
|
-
const canAccess = useCallback9((resource, action) => {
|
|
1732
|
-
const permission = `${resource}:${action}`;
|
|
1733
|
-
const hasAccess = hasPermission2(permission);
|
|
1734
|
-
return hasAccess;
|
|
1735
|
-
}, [hasPermission2]);
|
|
1736
|
-
const validatePermission = useCallback9(async (permission) => hasPermission2(permission), [hasPermission2]);
|
|
1737
|
-
const validateAccess = useCallback9(async (resource, action) => {
|
|
1738
|
-
return Promise.resolve(canAccess(resource, action));
|
|
1739
|
-
}, [canAccess]);
|
|
1740
|
-
const contextValue = useMemo9(() => ({
|
|
1741
|
-
permissions,
|
|
1742
|
-
roles,
|
|
1743
|
-
accessLevel,
|
|
1744
|
-
rbacLoading,
|
|
1745
|
-
rbacError,
|
|
1746
|
-
selectedEventId,
|
|
1747
|
-
appConfig,
|
|
1748
|
-
userEventAccess,
|
|
1749
|
-
eventAccessLoading,
|
|
1750
|
-
// Organisation context
|
|
1751
|
-
selectedOrganisationId,
|
|
1752
|
-
requireOrganisationContext: () => {
|
|
1753
|
-
if (!selectedOrganisationId) {
|
|
1754
|
-
throw new Error("Organisation context is required but not available");
|
|
1755
|
-
}
|
|
1756
|
-
return selectedOrganisationId;
|
|
1757
|
-
},
|
|
1758
|
-
hasPermission: hasPermission2,
|
|
1759
|
-
hasAnyPermission: hasAnyPermission2,
|
|
1760
|
-
hasAllPermissions: hasAllPermissions2,
|
|
1761
|
-
hasRole,
|
|
1762
|
-
hasAccessLevel,
|
|
1763
|
-
canAccess,
|
|
1764
|
-
validatePermission,
|
|
1765
|
-
validateAccess,
|
|
1766
|
-
refreshPermissions,
|
|
1767
|
-
setSelectedEventId,
|
|
1768
|
-
// New RBAC system support
|
|
1769
|
-
rbacEnabled: enableRBAC,
|
|
1770
|
-
rbacContext: void 0,
|
|
1771
|
-
// Will be populated by useRBAC hook when enabled
|
|
1772
|
-
loadUserEventAccess,
|
|
1773
|
-
getUserEventAccess
|
|
1774
|
-
}), [
|
|
1775
|
-
permissions,
|
|
1776
|
-
roles,
|
|
1777
|
-
accessLevel,
|
|
1778
|
-
rbacLoading,
|
|
1779
|
-
rbacError,
|
|
1780
|
-
selectedEventId,
|
|
1781
|
-
appConfig,
|
|
1782
|
-
userEventAccess,
|
|
1783
|
-
eventAccessLoading,
|
|
1784
|
-
selectedOrganisationId,
|
|
1785
|
-
hasPermission2,
|
|
1786
|
-
hasAnyPermission2,
|
|
1787
|
-
hasAllPermissions2,
|
|
1788
|
-
hasRole,
|
|
1789
|
-
hasAccessLevel,
|
|
1790
|
-
canAccess,
|
|
1791
|
-
validatePermission,
|
|
1792
|
-
validateAccess,
|
|
1793
|
-
refreshPermissions,
|
|
1794
|
-
setSelectedEventId,
|
|
1795
|
-
enableRBAC,
|
|
1796
|
-
loadUserEventAccess,
|
|
1797
|
-
getUserEventAccess
|
|
1798
|
-
]);
|
|
1799
|
-
return /* @__PURE__ */ jsx9(RBACContext.Provider, { value: contextValue, children });
|
|
1800
|
-
}
|
|
1801
|
-
|
|
1802
1406
|
// src/rbac/adapters.tsx
|
|
1803
|
-
|
|
1804
|
-
import { Fragment as Fragment4, jsx as
|
|
1407
|
+
init_UnifiedAuthProvider();
|
|
1408
|
+
import { Fragment as Fragment4, jsx as jsx9 } from "react/jsx-runtime";
|
|
1805
1409
|
function PermissionGuard({
|
|
1806
1410
|
userId,
|
|
1807
1411
|
scope,
|
|
@@ -1817,40 +1421,24 @@ function PermissionGuard({
|
|
|
1817
1421
|
enforceAudit = true
|
|
1818
1422
|
}) {
|
|
1819
1423
|
const logger = getRBACLogger();
|
|
1820
|
-
|
|
1821
|
-
|
|
1822
|
-
|
|
1823
|
-
|
|
1824
|
-
|
|
1825
|
-
|
|
1826
|
-
|
|
1827
|
-
|
|
1828
|
-
if (globalUser?.id) {
|
|
1829
|
-
effectiveUserId = globalUser.id;
|
|
1830
|
-
}
|
|
1831
|
-
}
|
|
1832
|
-
} catch (error2) {
|
|
1833
|
-
logger.debug("Could not infer userId from context:", error2);
|
|
1424
|
+
let authContext = null;
|
|
1425
|
+
try {
|
|
1426
|
+
authContext = useUnifiedAuth();
|
|
1427
|
+
} catch (error2) {
|
|
1428
|
+
if (error2 instanceof Error && error2.message.includes("must be used within")) {
|
|
1429
|
+
authContext = null;
|
|
1430
|
+
} else {
|
|
1431
|
+
throw error2;
|
|
1834
1432
|
}
|
|
1835
1433
|
}
|
|
1434
|
+
const effectiveUserId = userId ?? authContext?.user?.id ?? null;
|
|
1836
1435
|
const { can, isLoading, error } = useCan(effectiveUserId || "", scope, permission, pageId);
|
|
1837
1436
|
if (!effectiveUserId) {
|
|
1838
1437
|
logger.error("PermissionGuard: No userId provided and could not infer from context");
|
|
1839
|
-
return
|
|
1840
|
-
/* @__PURE__ */ jsx10("p", { children: "Permission check failed: User context not available" }),
|
|
1841
|
-
/* @__PURE__ */ jsxs6("details", { children: [
|
|
1842
|
-
/* @__PURE__ */ jsx10("summary", { children: "Debug info" }),
|
|
1843
|
-
/* @__PURE__ */ jsx10("p", { children: "Make sure to either:" }),
|
|
1844
|
-
/* @__PURE__ */ jsxs6("ul", { children: [
|
|
1845
|
-
/* @__PURE__ */ jsx10("li", { children: "Pass userId prop explicitly" }),
|
|
1846
|
-
/* @__PURE__ */ jsx10("li", { children: "Wrap your app with an auth provider" }),
|
|
1847
|
-
/* @__PURE__ */ jsx10("li", { children: "Set window.__PACE_USER__ with user data" })
|
|
1848
|
-
] })
|
|
1849
|
-
] })
|
|
1850
|
-
] });
|
|
1438
|
+
return fallback ?? null;
|
|
1851
1439
|
}
|
|
1852
1440
|
if (isLoading) {
|
|
1853
|
-
return loading || /* @__PURE__ */
|
|
1441
|
+
return loading || /* @__PURE__ */ jsx9("div", { className: "rbac-loading", role: "status", "aria-live": "polite", children: /* @__PURE__ */ jsx9("span", { className: "sr-only", children: "Checking permissions..." }) });
|
|
1854
1442
|
}
|
|
1855
1443
|
if (error) {
|
|
1856
1444
|
logger.error("Permission check failed:", error);
|
|
@@ -1888,7 +1476,7 @@ function PermissionGuard({
|
|
|
1888
1476
|
if (onDenied) {
|
|
1889
1477
|
onDenied();
|
|
1890
1478
|
}
|
|
1891
|
-
return /* @__PURE__ */
|
|
1479
|
+
return /* @__PURE__ */ jsx9(Fragment4, { children: fallback });
|
|
1892
1480
|
}
|
|
1893
1481
|
if (auditLog) {
|
|
1894
1482
|
logger.info(`[PermissionGuard] Permission granted:`, {
|
|
@@ -1899,7 +1487,7 @@ function PermissionGuard({
|
|
|
1899
1487
|
timestamp: (/* @__PURE__ */ new Date()).toISOString()
|
|
1900
1488
|
});
|
|
1901
1489
|
}
|
|
1902
|
-
return /* @__PURE__ */
|
|
1490
|
+
return /* @__PURE__ */ jsx9(Fragment4, { children });
|
|
1903
1491
|
}
|
|
1904
1492
|
function AccessLevelGuard({
|
|
1905
1493
|
userId,
|
|
@@ -1910,40 +1498,24 @@ function AccessLevelGuard({
|
|
|
1910
1498
|
loading = null
|
|
1911
1499
|
}) {
|
|
1912
1500
|
const logger = getRBACLogger();
|
|
1913
|
-
|
|
1914
|
-
|
|
1915
|
-
|
|
1916
|
-
|
|
1917
|
-
|
|
1918
|
-
|
|
1919
|
-
|
|
1920
|
-
|
|
1921
|
-
if (globalUser?.id) {
|
|
1922
|
-
effectiveUserId = globalUser.id;
|
|
1923
|
-
}
|
|
1924
|
-
}
|
|
1925
|
-
} catch (error2) {
|
|
1926
|
-
logger.debug("Could not infer userId from context:", error2);
|
|
1501
|
+
let authContext = null;
|
|
1502
|
+
try {
|
|
1503
|
+
authContext = useUnifiedAuth();
|
|
1504
|
+
} catch (error2) {
|
|
1505
|
+
if (error2 instanceof Error && error2.message.includes("must be used within")) {
|
|
1506
|
+
authContext = null;
|
|
1507
|
+
} else {
|
|
1508
|
+
throw error2;
|
|
1927
1509
|
}
|
|
1928
1510
|
}
|
|
1511
|
+
const effectiveUserId = userId ?? authContext?.user?.id ?? null;
|
|
1929
1512
|
const { accessLevel, isLoading, error } = useAccessLevel(effectiveUserId || "", scope);
|
|
1930
1513
|
if (!effectiveUserId) {
|
|
1931
1514
|
logger.error("AccessLevelGuard: No userId provided and could not infer from context");
|
|
1932
|
-
return
|
|
1933
|
-
/* @__PURE__ */ jsx10("p", { children: "Access level check failed: User context not available" }),
|
|
1934
|
-
/* @__PURE__ */ jsxs6("details", { children: [
|
|
1935
|
-
/* @__PURE__ */ jsx10("summary", { children: "Debug info" }),
|
|
1936
|
-
/* @__PURE__ */ jsx10("p", { children: "Make sure to either:" }),
|
|
1937
|
-
/* @__PURE__ */ jsxs6("ul", { children: [
|
|
1938
|
-
/* @__PURE__ */ jsx10("li", { children: "Pass userId prop explicitly" }),
|
|
1939
|
-
/* @__PURE__ */ jsx10("li", { children: "Wrap your app with an auth provider" }),
|
|
1940
|
-
/* @__PURE__ */ jsx10("li", { children: "Set window.__PACE_USER__ with user data" })
|
|
1941
|
-
] })
|
|
1942
|
-
] })
|
|
1943
|
-
] });
|
|
1515
|
+
return fallback ?? null;
|
|
1944
1516
|
}
|
|
1945
1517
|
if (isLoading) {
|
|
1946
|
-
return loading || /* @__PURE__ */
|
|
1518
|
+
return loading || /* @__PURE__ */ jsx9("div", { className: "rbac-loading", role: "status", "aria-live": "polite", children: /* @__PURE__ */ jsx9("span", { className: "sr-only", children: "Checking access level..." }) });
|
|
1947
1519
|
}
|
|
1948
1520
|
if (error) {
|
|
1949
1521
|
logger.error("Access level check failed:", error);
|
|
@@ -1953,9 +1525,9 @@ function AccessLevelGuard({
|
|
|
1953
1525
|
const userLevelIndex = accessLevel ? levelHierarchy.indexOf(accessLevel) : -1;
|
|
1954
1526
|
const requiredLevelIndex = levelHierarchy.indexOf(minLevel);
|
|
1955
1527
|
if (userLevelIndex < requiredLevelIndex) {
|
|
1956
|
-
return /* @__PURE__ */
|
|
1528
|
+
return /* @__PURE__ */ jsx9(Fragment4, { children: fallback });
|
|
1957
1529
|
}
|
|
1958
|
-
return /* @__PURE__ */
|
|
1530
|
+
return /* @__PURE__ */ jsx9(Fragment4, { children });
|
|
1959
1531
|
}
|
|
1960
1532
|
function withPermissionGuard(config, handler) {
|
|
1961
1533
|
return async (...args) => {
|
|
@@ -1967,7 +1539,7 @@ function withPermissionGuard(config, handler) {
|
|
|
1967
1539
|
if (!userId || !organisationId) {
|
|
1968
1540
|
throw new Error("User context required for permission check");
|
|
1969
1541
|
}
|
|
1970
|
-
const { isPermitted: isPermitted2 } = await import("./api-
|
|
1542
|
+
const { isPermitted: isPermitted2 } = await import("./api-KG4A2X7P.js");
|
|
1971
1543
|
const hasPermission2 = await isPermitted2({
|
|
1972
1544
|
userId,
|
|
1973
1545
|
scope: { organisationId, eventId, appId },
|
|
@@ -1990,7 +1562,7 @@ function withAccessLevelGuard(minLevel, handler) {
|
|
|
1990
1562
|
if (!userId || !organisationId) {
|
|
1991
1563
|
throw new Error("User context required for access level check");
|
|
1992
1564
|
}
|
|
1993
|
-
const { getAccessLevel: getAccessLevel2 } = await import("./api-
|
|
1565
|
+
const { getAccessLevel: getAccessLevel2 } = await import("./api-KG4A2X7P.js");
|
|
1994
1566
|
const accessLevel = await getAccessLevel2({
|
|
1995
1567
|
userId,
|
|
1996
1568
|
scope: { organisationId, eventId, appId }
|
|
@@ -2015,11 +1587,11 @@ function withRoleGuard(config, handler) {
|
|
|
2015
1587
|
throw new Error("User context required for role check");
|
|
2016
1588
|
}
|
|
2017
1589
|
if (config.globalRoles && config.globalRoles.length > 0) {
|
|
2018
|
-
const { isSuperAdmin } = await import("./api-
|
|
1590
|
+
const { isSuperAdmin } = await import("./api-KG4A2X7P.js");
|
|
2019
1591
|
const isSuper = await isSuperAdmin(userId);
|
|
2020
1592
|
if (isSuper) {
|
|
2021
1593
|
if (organisationId) {
|
|
2022
|
-
const { emitAuditEvent: emitAuditEvent2 } = await import("./audit-
|
|
1594
|
+
const { emitAuditEvent: emitAuditEvent2 } = await import("./audit-65VNHEV2.js");
|
|
2023
1595
|
await emitAuditEvent2({
|
|
2024
1596
|
type: "permission_check",
|
|
2025
1597
|
userId,
|
|
@@ -2041,21 +1613,21 @@ function withRoleGuard(config, handler) {
|
|
|
2041
1613
|
}
|
|
2042
1614
|
}
|
|
2043
1615
|
if (config.organisationRoles && config.organisationRoles.length > 0) {
|
|
2044
|
-
const { isOrganisationAdmin } = await import("./api-
|
|
1616
|
+
const { isOrganisationAdmin } = await import("./api-KG4A2X7P.js");
|
|
2045
1617
|
const isOrgAdmin = await isOrganisationAdmin(userId, organisationId);
|
|
2046
1618
|
if (!isOrgAdmin && config.requireAll !== false) {
|
|
2047
1619
|
throw new Error(`Organisation admin role required`);
|
|
2048
1620
|
}
|
|
2049
1621
|
}
|
|
2050
1622
|
if (config.eventAppRoles && config.eventAppRoles.length > 0 && eventId && appId) {
|
|
2051
|
-
const { isEventAdmin } = await import("./api-
|
|
1623
|
+
const { isEventAdmin } = await import("./api-KG4A2X7P.js");
|
|
2052
1624
|
const isEventAdminUser = await isEventAdmin(userId, { organisationId, eventId, appId });
|
|
2053
1625
|
if (!isEventAdminUser && config.requireAll !== false) {
|
|
2054
1626
|
throw new Error(`Event admin role required`);
|
|
2055
1627
|
}
|
|
2056
1628
|
}
|
|
2057
1629
|
if (organisationId) {
|
|
2058
|
-
const { emitAuditEvent: emitAuditEvent2 } = await import("./audit-
|
|
1630
|
+
const { emitAuditEvent: emitAuditEvent2 } = await import("./audit-65VNHEV2.js");
|
|
2059
1631
|
await emitAuditEvent2({
|
|
2060
1632
|
type: "permission_check",
|
|
2061
1633
|
userId,
|
|
@@ -2088,7 +1660,7 @@ function createRBACMiddleware(config) {
|
|
|
2088
1660
|
);
|
|
2089
1661
|
if (protectedRoute) {
|
|
2090
1662
|
try {
|
|
2091
|
-
const { isPermitted: isPermitted2 } = await import("./api-
|
|
1663
|
+
const { isPermitted: isPermitted2 } = await import("./api-KG4A2X7P.js");
|
|
2092
1664
|
const hasPermission2 = await isPermitted2({
|
|
2093
1665
|
userId,
|
|
2094
1666
|
scope: { organisationId },
|
|
@@ -2115,7 +1687,7 @@ function createRBACExpressMiddleware(config) {
|
|
|
2115
1687
|
return res.status(401).json({ error: "User context required" });
|
|
2116
1688
|
}
|
|
2117
1689
|
try {
|
|
2118
|
-
const { isPermitted: isPermitted2 } = await import("./api-
|
|
1690
|
+
const { isPermitted: isPermitted2 } = await import("./api-KG4A2X7P.js");
|
|
2119
1691
|
const hasPermission2 = await isPermitted2({
|
|
2120
1692
|
userId,
|
|
2121
1693
|
scope: { organisationId, eventId, appId },
|
|
@@ -2271,8 +1843,6 @@ export {
|
|
|
2271
1843
|
useNavigationPermissions,
|
|
2272
1844
|
NavigationGuard,
|
|
2273
1845
|
EnhancedNavigationMenu,
|
|
2274
|
-
useRBAC,
|
|
2275
|
-
RBACProvider,
|
|
2276
1846
|
PermissionGuard,
|
|
2277
1847
|
AccessLevelGuard,
|
|
2278
1848
|
withPermissionGuard,
|
|
@@ -2290,4 +1860,4 @@ export {
|
|
|
2290
1860
|
getPermissionsForRole,
|
|
2291
1861
|
ALL_PERMISSIONS
|
|
2292
1862
|
};
|
|
2293
|
-
//# sourceMappingURL=chunk-
|
|
1863
|
+
//# sourceMappingURL=chunk-2OGV6IRV.js.map
|