@jmruthers/pace-core 0.5.193 → 0.6.2
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 +62 -0
- package/README.md +7 -1
- package/cursor-rules/00-pace-core-compliance.mdc +299 -0
- package/cursor-rules/01-standards-compliance.mdc +244 -0
- package/cursor-rules/02-project-structure.mdc +200 -0
- package/cursor-rules/03-solid-principles.mdc +222 -0
- package/cursor-rules/04-testing-standards.mdc +268 -0
- package/cursor-rules/05-bug-reports-and-features.mdc +246 -0
- package/cursor-rules/06-code-quality.mdc +309 -0
- package/cursor-rules/07-tech-stack-compliance.mdc +214 -0
- package/cursor-rules/08-markup-quality.mdc +452 -0
- package/cursor-rules/CHANGELOG.md +119 -0
- package/cursor-rules/README.md +192 -0
- package/dist/{AuthService-DjnJHDtC.d.ts → AuthService-BPvc3Ka0.d.ts} +54 -0
- package/dist/{DataTable-Be6dH_dR.d.ts → DataTable-BMRU8a1j.d.ts} +34 -2
- package/dist/{DataTable-5FU7IESH.js → DataTable-TPTKCX4D.js} +10 -9
- package/dist/{PublicPageProvider-C0Sm_e5k.d.ts → PublicPageProvider-DC6kCaqf.d.ts} +385 -261
- package/dist/{UnifiedAuthProvider-RGJTDE2C.js → UnifiedAuthProvider-CH6Z342H.js} +3 -3
- package/dist/{UnifiedAuthProvider-185Ih4dj.d.ts → UnifiedAuthProvider-CVcTjx-d.d.ts} +29 -0
- package/dist/{api-N774RPUA.js → api-MVVQZLJI.js} +2 -2
- package/dist/{chunk-KNC55RTG.js → chunk-24UVZUZG.js} +90 -54
- package/dist/chunk-24UVZUZG.js.map +1 -0
- package/dist/{chunk-HWIIPPNI.js → chunk-2UOI2FG5.js} +20 -20
- package/dist/chunk-2UOI2FG5.js.map +1 -0
- package/dist/{chunk-E3SPN4VZ 5.js → chunk-3XC4CPTD.js} +4345 -3986
- package/dist/chunk-3XC4CPTD.js.map +1 -0
- package/dist/{chunk-7EQTDTTJ.js → chunk-6J4GEEJR.js} +172 -45
- package/dist/chunk-6J4GEEJR.js.map +1 -0
- package/dist/{chunk-6C4YBBJM 5.js → chunk-6SOIHG6Z.js} +1 -1
- package/dist/chunk-6SOIHG6Z.js.map +1 -0
- package/dist/{chunk-7FLMSG37.js → chunk-EHMR7VYL.js} +25 -25
- package/dist/chunk-EHMR7VYL.js.map +1 -0
- package/dist/{chunk-I7PSE6JW.js → chunk-F2IMUDXZ.js} +2 -75
- package/dist/chunk-F2IMUDXZ.js.map +1 -0
- package/dist/{chunk-QWWZ5CAQ.js → chunk-FFQEQTNW.js} +7 -9
- package/dist/chunk-FFQEQTNW.js.map +1 -0
- package/dist/chunk-FMUCXFII.js +76 -0
- package/dist/chunk-FMUCXFII.js.map +1 -0
- package/dist/{chunk-HW3OVDUF.js → chunk-J36DSWQK.js} +1 -1
- package/dist/{chunk-HW3OVDUF.js.map → chunk-J36DSWQK.js.map} +1 -1
- package/dist/{chunk-SQGMNID3.js → chunk-L4OXEN46.js} +4 -5
- package/dist/chunk-L4OXEN46.js.map +1 -0
- package/dist/{chunk-R77UEZ4E 3.js → chunk-M43Y4SSO.js} +1 -1
- package/dist/chunk-M43Y4SSO.js.map +1 -0
- package/dist/{chunk-IIELH4DL.js → chunk-MMZ7JXPU.js} +60 -223
- package/dist/chunk-MMZ7JXPU.js.map +1 -0
- package/dist/{chunk-NOAYCWCX 5.js → chunk-NECFR5MM.js} +394 -312
- package/dist/chunk-NECFR5MM.js.map +1 -0
- package/dist/{chunk-BC4IJKSL.js → chunk-SFZUDBL5.js} +40 -4
- package/dist/chunk-SFZUDBL5.js.map +1 -0
- package/dist/{chunk-XNXXZ43G.js → chunk-XWQCNGTQ.js} +748 -364
- package/dist/chunk-XWQCNGTQ.js.map +1 -0
- package/dist/components.d.ts +6 -6
- package/dist/components.js +15 -12
- package/dist/components.js.map +1 -1
- package/dist/{functions-D_kgHktt.d.ts → functions-DHebl8-F.d.ts} +1 -1
- package/dist/hooks.d.ts +59 -126
- package/dist/hooks.js +19 -28
- package/dist/hooks.js.map +1 -1
- package/dist/index.d.ts +63 -16
- package/dist/index.js +23 -24
- package/dist/index.js.map +1 -1
- package/dist/providers.d.ts +21 -3
- package/dist/providers.js +2 -2
- package/dist/rbac/index.d.ts +146 -115
- package/dist/rbac/index.js +8 -11
- package/dist/theming/runtime.d.ts +1 -13
- package/dist/theming/runtime.js +1 -1
- package/dist/{timezone-_pgH8qrY.d.ts → timezone-CHhWg6b4.d.ts} +3 -10
- package/dist/{types-UU913iLA.d.ts → types-BeoeWV5I.d.ts} +8 -0
- package/dist/{types-CEpcvwwF.d.ts → types-CkbwOr4Y.d.ts} +6 -0
- package/dist/types.d.ts +2 -2
- package/dist/{usePublicRouteParams-TZe0gy-4.d.ts → usePublicRouteParams-1oMokgLF.d.ts} +34 -4
- package/dist/{useToast-C8gR5ir4.d.ts → useToast-AyaT-x7p.d.ts} +2 -2
- package/dist/utils.d.ts +4 -5
- package/dist/utils.js +15 -15
- package/dist/utils.js.map +1 -1
- package/docs/api/README.md +7 -1
- package/docs/api/classes/ColumnFactory.md +8 -8
- package/docs/api/classes/InvalidScopeError.md +4 -4
- package/docs/api/classes/Logger.md +1 -1
- package/docs/api/classes/MissingUserContextError.md +4 -4
- package/docs/api/classes/OrganisationContextRequiredError.md +4 -4
- package/docs/api/classes/PermissionDeniedError.md +4 -4
- package/docs/api/classes/RBACAuditManager.md +1 -1
- package/docs/api/classes/RBACCache.md +1 -1
- package/docs/api/classes/RBACEngine.md +1 -1
- package/docs/api/classes/RBACError.md +4 -4
- package/docs/api/classes/RBACNotInitializedError.md +4 -4
- package/docs/api/classes/SecureSupabaseClient.md +18 -15
- package/docs/api/classes/StorageUtils.md +1 -1
- package/docs/api/enums/FileCategory.md +1 -1
- package/docs/api/enums/LogLevel.md +1 -1
- package/docs/api/enums/RBACErrorCode.md +1 -1
- package/docs/api/enums/RPCFunction.md +1 -1
- package/docs/api/interfaces/AddressFieldProps.md +1 -1
- package/docs/api/interfaces/AddressFieldRef.md +1 -1
- package/docs/api/interfaces/AggregateConfig.md +4 -4
- package/docs/api/interfaces/AutocompleteOptions.md +1 -1
- package/docs/api/interfaces/AvatarProps.md +1 -1
- package/docs/api/interfaces/BadgeProps.md +9 -2
- package/docs/api/interfaces/ButtonProps.md +7 -4
- package/docs/api/interfaces/CalendarProps.md +8 -5
- package/docs/api/interfaces/CardProps.md +8 -5
- package/docs/api/interfaces/ColorPalette.md +1 -1
- package/docs/api/interfaces/ColorShade.md +1 -1
- package/docs/api/interfaces/ComplianceResult.md +1 -1
- package/docs/api/interfaces/DataAccessRecord.md +9 -9
- package/docs/api/interfaces/DataRecord.md +1 -1
- package/docs/api/interfaces/DataTableAction.md +24 -21
- package/docs/api/interfaces/DataTableColumn.md +31 -31
- package/docs/api/interfaces/DataTableProps.md +1 -1
- package/docs/api/interfaces/DataTableToolbarButton.md +7 -7
- package/docs/api/interfaces/DatabaseComplianceResult.md +1 -1
- package/docs/api/interfaces/DatabaseIssue.md +1 -1
- package/docs/api/interfaces/EmptyStateConfig.md +5 -5
- package/docs/api/interfaces/EnhancedNavigationMenuProps.md +1 -1
- package/docs/api/interfaces/ErrorBoundaryProps.md +147 -0
- package/docs/api/interfaces/ErrorBoundaryProviderProps.md +36 -0
- package/docs/api/interfaces/ErrorBoundaryState.md +75 -0
- package/docs/api/interfaces/EventAppRoleData.md +1 -1
- package/docs/api/interfaces/ExportColumn.md +1 -1
- package/docs/api/interfaces/ExportOptions.md +8 -8
- 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 +26 -23
- package/docs/api/interfaces/FooterProps.md +10 -8
- package/docs/api/interfaces/FormFieldProps.md +10 -10
- package/docs/api/interfaces/FormProps.md +1 -1
- package/docs/api/interfaces/GrantEventAppRoleParams.md +1 -1
- package/docs/api/interfaces/InactivityWarningModalProps.md +1 -1
- package/docs/api/interfaces/InputProps.md +7 -4
- package/docs/api/interfaces/LabelProps.md +1 -1
- package/docs/api/interfaces/LoggerConfig.md +1 -1
- package/docs/api/interfaces/LoginFormProps.md +14 -11
- package/docs/api/interfaces/NavigationAccessRecord.md +1 -1
- package/docs/api/interfaces/NavigationContextType.md +1 -1
- package/docs/api/interfaces/NavigationGuardProps.md +1 -1
- package/docs/api/interfaces/NavigationItem.md +11 -11
- package/docs/api/interfaces/NavigationMenuProps.md +15 -15
- package/docs/api/interfaces/NavigationProviderProps.md +1 -1
- 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 +30 -27
- package/docs/api/interfaces/PaceLoginPageProps.md +6 -4
- package/docs/api/interfaces/PageAccessRecord.md +1 -1
- package/docs/api/interfaces/PagePermissionContextType.md +1 -1
- package/docs/api/interfaces/PagePermissionGuardProps.md +1 -1
- package/docs/api/interfaces/PagePermissionProviderProps.md +1 -1
- package/docs/api/interfaces/PaletteData.md +1 -1
- package/docs/api/interfaces/ParsedAddress.md +1 -1
- package/docs/api/interfaces/PermissionEnforcerProps.md +1 -1
- package/docs/api/interfaces/ProgressProps.md +1 -1
- package/docs/api/interfaces/ProtectedRouteProps.md +7 -26
- package/docs/api/interfaces/PublicPageFooterProps.md +9 -9
- package/docs/api/interfaces/PublicPageHeaderProps.md +10 -10
- package/docs/api/interfaces/PublicPageLayoutProps.md +7 -20
- package/docs/api/interfaces/QuickFix.md +1 -1
- package/docs/api/interfaces/RBACAccessValidateParams.md +1 -1
- package/docs/api/interfaces/RBACAccessValidateResult.md +1 -1
- package/docs/api/interfaces/RBACAuditLogParams.md +1 -1
- package/docs/api/interfaces/RBACAuditLogResult.md +1 -1
- package/docs/api/interfaces/RBACConfig.md +1 -1
- package/docs/api/interfaces/RBACContext.md +1 -1
- package/docs/api/interfaces/RBACLogger.md +1 -1
- package/docs/api/interfaces/RBACPageAccessCheckParams.md +1 -1
- package/docs/api/interfaces/RBACPerformanceMetrics.md +1 -1
- package/docs/api/interfaces/RBACPermissionCheckParams.md +1 -1
- package/docs/api/interfaces/RBACPermissionCheckResult.md +1 -1
- package/docs/api/interfaces/RBACPermissionsGetParams.md +1 -1
- package/docs/api/interfaces/RBACPermissionsGetResult.md +1 -1
- package/docs/api/interfaces/RBACResult.md +1 -1
- package/docs/api/interfaces/RBACRoleGrantParams.md +1 -1
- package/docs/api/interfaces/RBACRoleGrantResult.md +1 -1
- package/docs/api/interfaces/RBACRoleRevokeParams.md +1 -1
- package/docs/api/interfaces/RBACRoleRevokeResult.md +1 -1
- package/docs/api/interfaces/RBACRoleValidateParams.md +1 -1
- package/docs/api/interfaces/RBACRoleValidateResult.md +1 -1
- package/docs/api/interfaces/RBACRolesListParams.md +1 -1
- package/docs/api/interfaces/RBACRolesListResult.md +1 -1
- package/docs/api/interfaces/RBACSessionTrackParams.md +1 -1
- package/docs/api/interfaces/RBACSessionTrackResult.md +1 -1
- package/docs/api/interfaces/ResourcePermissions.md +1 -1
- package/docs/api/interfaces/RevokeEventAppRoleParams.md +1 -1
- package/docs/api/interfaces/RoleBasedRouterContextType.md +1 -1
- package/docs/api/interfaces/RoleBasedRouterProps.md +1 -1
- package/docs/api/interfaces/RoleManagementResult.md +1 -1
- package/docs/api/interfaces/RouteAccessRecord.md +1 -1
- package/docs/api/interfaces/RouteConfig.md +1 -1
- package/docs/api/interfaces/RuntimeComplianceResult.md +1 -1
- package/docs/api/interfaces/SecureDataContextType.md +9 -9
- package/docs/api/interfaces/SecureDataProviderProps.md +8 -8
- package/docs/api/interfaces/SessionRestorationLoaderProps.md +3 -3
- package/docs/api/interfaces/SetupIssue.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/TabsContentProps.md +1 -1
- package/docs/api/interfaces/TabsListProps.md +1 -1
- package/docs/api/interfaces/TabsProps.md +1 -1
- package/docs/api/interfaces/TabsTriggerProps.md +3 -3
- package/docs/api/interfaces/TextareaProps.md +1 -1
- package/docs/api/interfaces/ToastActionElement.md +4 -1
- package/docs/api/interfaces/ToastProps.md +1 -1
- package/docs/api/interfaces/UnifiedAuthContextType.md +58 -55
- package/docs/api/interfaces/UnifiedAuthProviderProps.md +15 -13
- package/docs/api/interfaces/UseFormDialogOptions.md +1 -1
- package/docs/api/interfaces/UseFormDialogReturn.md +1 -1
- package/docs/api/interfaces/UseInactivityTrackerOptions.md +11 -9
- package/docs/api/interfaces/UseInactivityTrackerReturn.md +8 -8
- package/docs/api/interfaces/UsePublicEventLogoOptions.md +6 -6
- package/docs/api/interfaces/UsePublicEventLogoReturn.md +9 -6
- package/docs/api/interfaces/UsePublicEventOptions.md +3 -3
- package/docs/api/interfaces/UsePublicEventReturn.md +8 -5
- package/docs/api/interfaces/UsePublicFileDisplayOptions.md +4 -4
- package/docs/api/interfaces/UsePublicFileDisplayReturn.md +12 -9
- package/docs/api/interfaces/UsePublicRouteParamsReturn.md +10 -7
- package/docs/api/interfaces/UseResolvedScopeOptions.md +1 -1
- package/docs/api/interfaces/UseResolvedScopeReturn.md +1 -1
- package/docs/api/interfaces/UseResourcePermissionsOptions.md +1 -1
- package/docs/api/interfaces/UserEventAccess.md +14 -11
- package/docs/api/interfaces/UserMenuProps.md +8 -6
- package/docs/api/interfaces/UserProfile.md +1 -1
- package/docs/api/modules.md +575 -634
- package/docs/architecture/database-schema-requirements.md +161 -0
- package/docs/core-concepts/rbac-system.md +3 -3
- package/docs/documentation-index.md +2 -4
- package/docs/getting-started/cursor-rules.md +263 -0
- package/docs/getting-started/installation-guide.md +6 -1
- package/docs/getting-started/quick-start.md +6 -1
- package/docs/migration/DOCUMENTATION_STRUCTURE.md +441 -0
- package/docs/migration/MIGRATION_GUIDE.md +6 -28
- package/docs/migration/README.md +52 -6
- package/docs/migration/V0.5.190_TO_V0.6.1_MIGRATION.md +1153 -0
- package/docs/migration/V0.6.0_REACT_19_MIGRATION.md +227 -0
- package/docs/migration/database-changes-december-2025.md +3 -3
- package/docs/rbac/event-based-apps.md +1 -1
- package/docs/rbac/getting-started.md +1 -1
- package/docs/rbac/quick-start.md +1 -1
- package/docs/standards/README.md +40 -0
- package/docs/troubleshooting/migration.md +4 -4
- package/examples/PublicPages/PublicEventPage.tsx +1 -1
- package/package.json +12 -6
- package/scripts/audit/core/checks/accessibility.cjs +197 -0
- package/scripts/audit/core/checks/api-usage.cjs +191 -0
- package/scripts/audit/core/checks/bundle.cjs +142 -0
- package/scripts/{check-pace-core-compliance.cjs → audit/core/checks/compliance.cjs} +737 -691
- package/scripts/audit/core/checks/config.cjs +54 -0
- package/scripts/audit/core/checks/coverage.cjs +84 -0
- package/scripts/audit/core/checks/dependencies.cjs +454 -0
- package/scripts/audit/core/checks/documentation.cjs +203 -0
- package/scripts/audit/core/checks/environment.cjs +128 -0
- package/scripts/audit/core/checks/error-handling.cjs +299 -0
- package/scripts/audit/core/checks/forms.cjs +172 -0
- package/scripts/audit/core/checks/heuristics.cjs +68 -0
- package/scripts/audit/core/checks/hooks.cjs +334 -0
- package/scripts/audit/core/checks/imports.cjs +244 -0
- package/scripts/audit/core/checks/performance.cjs +325 -0
- package/scripts/audit/core/checks/routes.cjs +117 -0
- package/scripts/audit/core/checks/state.cjs +130 -0
- package/scripts/audit/core/checks/structure.cjs +65 -0
- package/scripts/audit/core/checks/style.cjs +584 -0
- package/scripts/audit/core/checks/testing.cjs +122 -0
- package/scripts/audit/core/checks/typescript.cjs +61 -0
- package/scripts/audit/core/scanner.cjs +199 -0
- package/scripts/audit/core/utils.cjs +137 -0
- package/scripts/audit/index.cjs +223 -0
- package/scripts/audit/reporters/console.cjs +151 -0
- package/scripts/audit/reporters/json.cjs +54 -0
- package/scripts/audit/reporters/markdown.cjs +124 -0
- package/scripts/audit-consuming-app.cjs +86 -0
- package/scripts/build-docs/build-decision.js +240 -0
- package/scripts/build-docs/cache-utils.js +105 -0
- package/scripts/build-docs/content-normalization.js +150 -0
- package/scripts/build-docs/file-utils.js +105 -0
- package/scripts/build-docs/git-utils.js +86 -0
- package/scripts/build-docs/hash-utils.js +116 -0
- package/scripts/build-docs/typedoc-runner.js +220 -0
- package/scripts/build-docs-incremental.js +77 -913
- package/scripts/install-cursor-rules.cjs +236 -0
- package/scripts/utils/command-runner.js +16 -11
- package/scripts/validate-formats.js +61 -56
- package/scripts/validate-master.js +74 -69
- package/scripts/validate-pre-publish.js +70 -65
- package/src/__tests__/helpers/test-providers.tsx +1 -1
- package/src/__tests__/helpers/test-utils.tsx +1 -1
- package/src/__tests__/hooks/usePermissions.test.ts +2 -2
- package/src/components/Alert/Alert.test.tsx +12 -18
- package/src/components/Alert/Alert.tsx +5 -7
- package/src/components/Avatar/Avatar.test.tsx +4 -4
- package/src/components/Badge/Badge.tsx +16 -4
- package/src/components/Button/Button.tsx +27 -4
- package/src/components/Calendar/Calendar.tsx +9 -3
- package/src/components/Card/Card.tsx +4 -0
- package/src/components/Checkbox/Checkbox.test.tsx +12 -12
- package/src/components/Checkbox/Checkbox.tsx +2 -2
- package/src/components/DataTable/DataTable.test.tsx +57 -93
- package/src/components/DataTable/DataTable.tsx +40 -6
- package/src/components/DataTable/__tests__/DataTableCore.test-setup.ts +5 -6
- package/src/components/DataTable/__tests__/pagination.modes.test.tsx +29 -7
- package/src/components/DataTable/__tests__/ssr.strict-mode.test.tsx +12 -12
- package/src/components/DataTable/__tests__/test-utils/sharedTestUtils.tsx +2 -3
- package/src/components/DataTable/components/AccessDeniedPage.tsx +17 -26
- package/src/components/DataTable/components/ActionButtons.tsx +10 -7
- package/src/components/DataTable/components/BulkOperationsDropdown.tsx +2 -2
- package/src/components/DataTable/components/ColumnFilter.tsx +10 -0
- package/src/components/DataTable/components/ColumnVisibilityDropdown.tsx +12 -0
- package/src/components/DataTable/components/DataTableBody.tsx +8 -0
- package/src/components/DataTable/components/DataTableCore.tsx +200 -561
- package/src/components/DataTable/components/DataTableErrorBoundary.tsx +11 -0
- package/src/components/DataTable/components/DataTableLayout.tsx +559 -0
- package/src/components/DataTable/components/DataTableModals.tsx +9 -1
- package/src/components/DataTable/components/DataTableToolbar.tsx +8 -0
- package/src/components/DataTable/components/DraggableColumnHeader.tsx +12 -0
- package/src/components/DataTable/components/EditFields.tsx +307 -0
- package/src/components/DataTable/components/EditableRow.tsx +9 -1
- package/src/components/DataTable/components/EmptyState.tsx +10 -0
- package/src/components/DataTable/components/FilterRow.tsx +12 -0
- package/src/components/DataTable/components/GroupHeader.tsx +12 -0
- package/src/components/DataTable/components/GroupingDropdown.tsx +12 -0
- package/src/components/DataTable/components/ImportModal.tsx +7 -0
- package/src/components/DataTable/components/LoadingState.tsx +6 -0
- package/src/components/DataTable/components/PaginationControls.tsx +16 -1
- package/src/components/DataTable/components/RowComponent.tsx +391 -0
- package/src/components/DataTable/components/UnifiedTableBody.tsx +62 -852
- package/src/components/DataTable/components/VirtualizedDataTable.tsx +16 -4
- package/src/components/DataTable/components/__tests__/AccessDeniedPage.test.tsx +4 -2
- package/src/components/DataTable/components/__tests__/DataTableModals.test.tsx +23 -23
- package/src/components/DataTable/components/__tests__/EditableRow.test.tsx +11 -11
- package/src/components/DataTable/components/__tests__/ExpandButton.test.tsx +36 -36
- package/src/components/DataTable/components/__tests__/GroupHeader.test.tsx +27 -27
- package/src/components/DataTable/components/__tests__/ImportModal.test.tsx +39 -39
- package/src/components/DataTable/components/__tests__/UnifiedTableBody.test.tsx +33 -33
- package/src/components/DataTable/components/__tests__/ViewRowModal.test.tsx +29 -29
- package/src/components/DataTable/components/cellValueUtils.ts +40 -0
- package/src/components/DataTable/components/hooks/useImportModalFocus.ts +53 -0
- package/src/components/DataTable/components/hooks/usePermissionTracking.ts +126 -0
- package/src/components/DataTable/context/DataTableContext.tsx +50 -0
- package/src/components/DataTable/core/ColumnFactory.ts +31 -0
- package/src/components/DataTable/core/DataTableContext.tsx +32 -1
- package/src/components/DataTable/hooks/useColumnOrderPersistence.ts +10 -0
- package/src/components/DataTable/hooks/useColumnReordering.ts +14 -2
- package/src/components/DataTable/hooks/useColumnVisibilityPersistence.ts +10 -0
- package/src/components/DataTable/hooks/useDataTableDataPipeline.ts +16 -0
- package/src/components/DataTable/hooks/useDataTablePermissions.ts +124 -32
- package/src/components/DataTable/hooks/useDataTableState.ts +35 -1
- package/src/components/DataTable/hooks/useEffectiveColumnOrder.ts +12 -0
- package/src/components/DataTable/hooks/useKeyboardNavigation.ts +2 -2
- package/src/components/DataTable/hooks/useServerSideDataEffect.ts +11 -0
- package/src/components/DataTable/hooks/useTableColumns.ts +8 -0
- package/src/components/DataTable/hooks/useTableHandlers.ts +14 -0
- package/src/components/DataTable/styles.ts +6 -6
- package/src/components/DataTable/types.ts +6 -10
- package/src/components/DataTable/utils/a11yUtils.ts +7 -0
- package/src/components/DataTable/utils/debugTools.ts +18 -113
- package/src/components/DataTable/utils/errorHandling.ts +12 -0
- package/src/components/DataTable/utils/exportUtils.ts +9 -0
- package/src/components/DataTable/utils/flexibleImport.ts +12 -48
- package/src/components/DataTable/utils/paginationUtils.ts +8 -0
- package/src/components/DataTable/utils/performanceUtils.ts +5 -1
- package/src/components/DatePickerWithTimezone/DatePickerWithTimezone.test.tsx +8 -14
- package/src/components/Dialog/Dialog.tsx +8 -7
- package/src/components/ErrorBoundary/ErrorBoundary.test.tsx +180 -1
- package/src/components/ErrorBoundary/ErrorBoundary.tsx +46 -6
- package/src/components/ErrorBoundary/ErrorBoundaryContext.tsx +129 -0
- package/src/components/ErrorBoundary/index.ts +27 -2
- package/src/components/EventSelector/EventSelector.tsx +4 -1
- package/src/components/FileDisplay/FileDisplay.test.tsx +2 -2
- package/src/components/FileDisplay/FileDisplay.tsx +32 -18
- package/src/components/FileUpload/FileUpload.tsx +22 -2
- package/src/components/Footer/Footer.test.tsx +16 -16
- package/src/components/Footer/Footer.tsx +15 -12
- package/src/components/Form/Form.test.tsx +36 -15
- package/src/components/Form/Form.tsx +31 -26
- package/src/components/Header/Header.tsx +22 -11
- package/src/components/InactivityWarningModal/InactivityWarningModal.test.tsx +40 -40
- package/src/components/InactivityWarningModal/InactivityWarningModal.tsx +1 -1
- package/src/components/Input/Input.test.tsx +2 -2
- package/src/components/Input/Input.tsx +36 -34
- package/src/components/Label/Label.tsx +1 -1
- package/src/components/LoadingSpinner/LoadingSpinner.test.tsx +4 -4
- package/src/components/LoadingSpinner/LoadingSpinner.tsx +1 -1
- package/src/components/LoginForm/LoginForm.test.tsx +42 -42
- package/src/components/LoginForm/LoginForm.tsx +12 -8
- package/src/components/NavigationMenu/NavigationMenu.tsx +15 -514
- package/src/components/NavigationMenu/types.ts +56 -0
- package/src/components/NavigationMenu/useNavigationFiltering.ts +390 -0
- package/src/components/OrganisationSelector/OrganisationSelector.tsx +3 -0
- package/src/components/PaceAppLayout/PaceAppLayout.performance.test.tsx +1 -1
- package/src/components/PaceAppLayout/PaceAppLayout.test.tsx +54 -52
- package/src/components/PaceAppLayout/PaceAppLayout.tsx +33 -12
- package/src/components/PaceAppLayout/README.md +1 -1
- package/src/components/PaceAppLayout/test-setup.tsx +1 -2
- package/src/components/PaceLoginPage/PaceLoginPage.tsx +4 -1
- package/src/components/PasswordChange/PasswordChangeForm.test.tsx +33 -33
- package/src/components/PasswordChange/PasswordChangeForm.tsx +10 -1
- package/src/components/Progress/Progress.tsx +1 -1
- package/src/components/ProtectedRoute/ProtectedRoute.tsx +3 -9
- package/src/components/PublicLayout/PublicPageLayout.tsx +3 -6
- package/src/components/PublicLayout/PublicPageProvider.tsx +4 -0
- package/src/components/Select/Select.tsx +95 -438
- package/src/components/Select/context.ts +23 -0
- package/src/components/Select/hooks/useSelectEvents.ts +87 -0
- package/src/components/Select/hooks/useSelectSearch.ts +91 -0
- package/src/components/Select/hooks/useSelectState.ts +104 -0
- package/src/components/Select/index.ts +9 -1
- package/src/components/Select/types.ts +123 -0
- package/src/components/Select/utils/text.ts +26 -0
- package/src/components/SessionRestorationLoader/SessionRestorationLoader.tsx +5 -6
- package/src/components/Switch/Switch.tsx +4 -4
- package/src/components/Table/Table.tsx +1 -1
- package/src/components/Tabs/Tabs.tsx +1 -1
- package/src/components/Textarea/Textarea.tsx +27 -29
- package/src/components/Toast/Toast.tsx +5 -1
- package/src/components/Tooltip/Tooltip.tsx +3 -3
- package/src/components/UserMenu/UserMenu.test.tsx +24 -11
- package/src/components/UserMenu/UserMenu.tsx +22 -19
- package/src/components/index.ts +2 -2
- package/src/hooks/__tests__/hooks.integration.test.tsx +80 -55
- package/src/hooks/__tests__/index.unit.test.ts +2 -5
- package/src/hooks/__tests__/useStorage.unit.test.ts +36 -36
- package/src/hooks/index.ts +1 -2
- package/src/hooks/public/usePublicEvent.ts +5 -1
- package/src/hooks/public/usePublicEventLogo.ts +5 -1
- package/src/hooks/public/usePublicFileDisplay.ts +4 -0
- package/src/hooks/public/usePublicRouteParams.ts +5 -1
- package/src/hooks/services/useAuth.ts +32 -0
- package/src/hooks/services/useCurrentEvent.ts +6 -0
- package/src/hooks/services/useCurrentOrganisation.ts +6 -0
- package/src/hooks/useDataTableState.ts +8 -18
- package/src/hooks/useDebounce.ts +9 -0
- package/src/hooks/useEventTheme.ts +6 -0
- package/src/hooks/useFileDisplay.ts +4 -0
- package/src/hooks/useFileReference.ts +25 -7
- package/src/hooks/useFileUrl.ts +11 -1
- package/src/hooks/useFocusManagement.ts +16 -2
- package/src/hooks/useFocusTrap.ts +7 -4
- package/src/hooks/useFormDialog.ts +8 -7
- package/src/hooks/useInactivityTracker.ts +4 -1
- package/src/hooks/useKeyboardShortcuts.ts +4 -0
- package/src/hooks/useOrganisationPermissions.ts +4 -0
- package/src/hooks/useOrganisationSecurity.ts +4 -0
- package/src/hooks/usePerformanceMonitor.ts +4 -0
- package/src/hooks/usePermissionCache.ts +8 -1
- package/src/hooks/useQueryCache.ts +12 -1
- package/src/hooks/useSessionRestoration.ts +4 -0
- package/src/hooks/useStorage.ts +4 -0
- package/src/hooks/useToast.ts +3 -3
- package/src/index.ts +2 -1
- package/src/providers/__tests__/OrganisationProvider.test.tsx +115 -49
- package/src/providers/__tests__/ProviderLifecycle.test.tsx +21 -6
- package/src/providers/__tests__/UnifiedAuthProvider.test.tsx +10 -10
- package/src/providers/services/AuthServiceProvider.tsx +18 -0
- package/src/providers/services/EventServiceProvider.tsx +18 -0
- package/src/providers/services/InactivityServiceProvider.tsx +18 -0
- package/src/providers/services/OrganisationServiceProvider.tsx +18 -0
- package/src/providers/services/UnifiedAuthProvider.tsx +58 -22
- package/src/providers/services/__tests__/AuthServiceProvider.integration.test.tsx +33 -7
- package/src/rbac/README.md +1 -1
- package/src/rbac/__tests__/adapters.comprehensive.test.tsx +26 -26
- package/src/rbac/__tests__/scenarios.user-role.test.tsx +4 -5
- package/src/rbac/adapters.tsx +14 -5
- package/src/rbac/api.ts +100 -67
- package/src/rbac/components/EnhancedNavigationMenu.tsx +1 -1
- package/src/rbac/components/NavigationGuard.tsx +1 -1
- package/src/rbac/components/NavigationProvider.tsx +5 -2
- package/src/rbac/components/PagePermissionGuard.tsx +158 -18
- package/src/rbac/components/PagePermissionProvider.tsx +1 -1
- package/src/rbac/components/PermissionEnforcer.tsx +1 -1
- package/src/rbac/components/RoleBasedRouter.tsx +6 -2
- package/src/rbac/components/SecureDataProvider.test.tsx +84 -49
- package/src/rbac/components/SecureDataProvider.tsx +21 -6
- package/src/rbac/components/__tests__/PagePermissionGuard.race-condition.test.tsx +24 -14
- package/src/rbac/components/__tests__/PagePermissionGuard.test.tsx +7 -0
- package/src/rbac/components/__tests__/PagePermissionGuard.verification.test.tsx +14 -6
- package/src/rbac/components/__tests__/RoleBasedRouter.test.tsx +15 -4
- package/src/rbac/components/__tests__/SecureDataProvider.fixed.test.tsx +148 -24
- package/src/rbac/components/__tests__/SecureDataProvider.test.tsx +81 -15
- package/src/rbac/engine.ts +38 -14
- package/src/rbac/hooks/permissions/index.ts +7 -0
- package/src/rbac/hooks/permissions/useAccessLevel.ts +105 -0
- package/src/rbac/hooks/permissions/useCachedPermissions.ts +79 -0
- package/src/rbac/hooks/permissions/useCan.ts +347 -0
- package/src/rbac/hooks/permissions/useHasAllPermissions.ts +90 -0
- package/src/rbac/hooks/permissions/useHasAnyPermission.ts +90 -0
- package/src/rbac/hooks/permissions/useMultiplePermissions.ts +93 -0
- package/src/rbac/hooks/permissions/usePermissions.ts +253 -0
- package/src/rbac/hooks/useCan.test.ts +71 -64
- package/src/rbac/hooks/usePermissions.ts +14 -995
- package/src/rbac/hooks/useResourcePermissions.test.ts +54 -18
- package/src/rbac/hooks/useResourcePermissions.ts +14 -4
- package/src/rbac/hooks/useSecureSupabase.ts +33 -13
- package/src/rbac/permissions.ts +0 -30
- package/src/rbac/secureClient.ts +212 -61
- package/src/rbac/types.ts +8 -0
- package/src/theming/__tests__/parseEventColours.test.ts +6 -9
- package/src/theming/parseEventColours.ts +5 -19
- package/src/types/vitest-globals.d.ts +51 -26
- package/src/utils/__mocks__/supabaseMock.ts +1 -3
- package/src/utils/__tests__/formatting.unit.test.ts +4 -4
- package/src/utils/__tests__/index.unit.test.ts +2 -2
- package/src/utils/audit/audit.ts +0 -3
- package/src/utils/core/cn.ts +1 -1
- package/src/utils/file-reference/index.ts +53 -1
- package/src/utils/formatting/formatting.ts +8 -18
- package/src/utils/index.ts +0 -1
- package/src/utils/security/secureDataAccess.test.ts +31 -20
- package/src/utils/security/secureDataAccess.ts +4 -3
- package/dist/chunk-6C4YBBJM.js +0 -628
- package/dist/chunk-6C4YBBJM.js.map +0 -1
- package/dist/chunk-7D4SUZUM.js 2.map +0 -1
- package/dist/chunk-7EQTDTTJ.js 2.map +0 -1
- package/dist/chunk-7EQTDTTJ.js.map +0 -1
- package/dist/chunk-7FLMSG37.js 2.map +0 -1
- package/dist/chunk-7FLMSG37.js.map +0 -1
- package/dist/chunk-BC4IJKSL.js.map +0 -1
- package/dist/chunk-E3SPN4VZ.js +0 -12917
- package/dist/chunk-E3SPN4VZ.js.map +0 -1
- package/dist/chunk-E66EQZE6 5.js +0 -37
- package/dist/chunk-E66EQZE6.js 2.map +0 -1
- package/dist/chunk-HWIIPPNI.js.map +0 -1
- package/dist/chunk-I7PSE6JW 5.js +0 -191
- package/dist/chunk-I7PSE6JW.js 2.map +0 -1
- package/dist/chunk-I7PSE6JW.js.map +0 -1
- package/dist/chunk-IIELH4DL.js.map +0 -1
- package/dist/chunk-KNC55RTG.js 5.map +0 -1
- package/dist/chunk-KNC55RTG.js.map +0 -1
- package/dist/chunk-KQCRWDSA.js 5.map +0 -1
- package/dist/chunk-LFNCN2SP.js +0 -412
- package/dist/chunk-LFNCN2SP.js 2.map +0 -1
- package/dist/chunk-LFNCN2SP.js.map +0 -1
- package/dist/chunk-LMC26NLJ 2.js +0 -84
- package/dist/chunk-NOAYCWCX.js +0 -4993
- package/dist/chunk-NOAYCWCX.js.map +0 -1
- package/dist/chunk-QWWZ5CAQ.js 3.map +0 -1
- package/dist/chunk-QWWZ5CAQ.js.map +0 -1
- package/dist/chunk-QXHPKYJV 3.js +0 -113
- package/dist/chunk-R77UEZ4E.js +0 -68
- package/dist/chunk-R77UEZ4E.js.map +0 -1
- package/dist/chunk-SQGMNID3.js.map +0 -1
- package/dist/chunk-VBXEHIUJ.js 6.map +0 -1
- package/dist/chunk-XNXXZ43G.js.map +0 -1
- package/dist/chunk-ZSAAAMVR 6.js +0 -25
- package/dist/components.js 5.map +0 -1
- package/dist/styles/index 2.js +0 -12
- package/dist/styles/index.js 5.map +0 -1
- package/dist/theming/runtime 5.js +0 -19
- package/dist/theming/runtime.js 5.map +0 -1
- package/docs/api/classes/ErrorBoundary.md +0 -144
- package/docs/migration/quick-migration-guide.md +0 -356
- package/docs/migration/service-architecture.md +0 -281
- package/src/hooks/__tests__/useSecureDataAccess.unit.test.tsx +0 -680
- package/src/hooks/useSecureDataAccess.test.ts +0 -559
- package/src/hooks/useSecureDataAccess.ts +0 -666
- /package/dist/{DataTable-5FU7IESH.js.map → DataTable-TPTKCX4D.js.map} +0 -0
- /package/dist/{UnifiedAuthProvider-RGJTDE2C.js.map → UnifiedAuthProvider-CH6Z342H.js.map} +0 -0
- /package/dist/{api-N774RPUA.js.map → api-MVVQZLJI.js.map} +0 -0
- /package/docs/migration/{organisation-context-timing-fix.md → V0.3.44_organisation-context-timing-fix.md} +0 -0
- /package/docs/migration/{rbac-migration.md → V0.4.0_rbac-migration.md} +0 -0
- /package/docs/migration/{person-scoped-profiles-migration-guide.md → V0.5.190_person-scoped-profiles-migration-guide.md} +0 -0
- /package/examples/{rbac → RBAC}/CompleteRBACExample.tsx +0 -0
- /package/examples/{rbac → RBAC}/EventBasedApp.tsx +0 -0
- /package/examples/{rbac → RBAC}/PermissionExample.tsx +0 -0
- /package/examples/{rbac → RBAC}/index.ts +0 -0
|
@@ -14,9 +14,9 @@ import type {
|
|
|
14
14
|
import { createLogger } from '../../../utils/core/logger';
|
|
15
15
|
|
|
16
16
|
/**
|
|
17
|
-
* Debug levels for controlling verbosity
|
|
17
|
+
* Debug levels for controlling verbosity (internal use only)
|
|
18
18
|
*/
|
|
19
|
-
|
|
19
|
+
enum DebugLevel {
|
|
20
20
|
NONE = 0,
|
|
21
21
|
ERROR = 1,
|
|
22
22
|
WARN = 2,
|
|
@@ -26,9 +26,9 @@ export enum DebugLevel {
|
|
|
26
26
|
}
|
|
27
27
|
|
|
28
28
|
/**
|
|
29
|
-
* Performance debug configuration
|
|
29
|
+
* Performance debug configuration (internal use only)
|
|
30
30
|
*/
|
|
31
|
-
|
|
31
|
+
interface DebugConfig {
|
|
32
32
|
enabled: boolean;
|
|
33
33
|
level: DebugLevel;
|
|
34
34
|
logToConsole: boolean;
|
|
@@ -41,9 +41,9 @@ export interface DebugConfig {
|
|
|
41
41
|
}
|
|
42
42
|
|
|
43
43
|
/**
|
|
44
|
-
* Default debug configuration
|
|
44
|
+
* Default debug configuration (internal use only)
|
|
45
45
|
*/
|
|
46
|
-
|
|
46
|
+
const DEFAULT_DEBUG_CONFIG: DebugConfig = {
|
|
47
47
|
enabled: import.meta.env.MODE === 'development',
|
|
48
48
|
level: DebugLevel.INFO,
|
|
49
49
|
logToConsole: true,
|
|
@@ -56,9 +56,9 @@ export const DEFAULT_DEBUG_CONFIG: DebugConfig = {
|
|
|
56
56
|
};
|
|
57
57
|
|
|
58
58
|
/**
|
|
59
|
-
* Debug log entry interface
|
|
59
|
+
* Debug log entry interface (internal use only)
|
|
60
60
|
*/
|
|
61
|
-
|
|
61
|
+
interface DebugLogEntry {
|
|
62
62
|
timestamp: number;
|
|
63
63
|
level: DebugLevel;
|
|
64
64
|
category: string;
|
|
@@ -70,9 +70,9 @@ export interface DebugLogEntry {
|
|
|
70
70
|
}
|
|
71
71
|
|
|
72
72
|
/**
|
|
73
|
-
* Performance timeline entry
|
|
73
|
+
* Performance timeline entry (internal use only)
|
|
74
74
|
*/
|
|
75
|
-
|
|
75
|
+
interface PerformanceTimelineEntry {
|
|
76
76
|
id: string;
|
|
77
77
|
operation: string;
|
|
78
78
|
startTime: number;
|
|
@@ -83,9 +83,9 @@ export interface PerformanceTimelineEntry {
|
|
|
83
83
|
}
|
|
84
84
|
|
|
85
85
|
/**
|
|
86
|
-
* Memory snapshot
|
|
86
|
+
* Memory snapshot (internal use only)
|
|
87
87
|
*/
|
|
88
|
-
|
|
88
|
+
interface MemorySnapshot {
|
|
89
89
|
timestamp: number;
|
|
90
90
|
heapUsed: number;
|
|
91
91
|
heapTotal: number;
|
|
@@ -94,9 +94,9 @@ export interface MemorySnapshot {
|
|
|
94
94
|
}
|
|
95
95
|
|
|
96
96
|
/**
|
|
97
|
-
* Render performance data
|
|
97
|
+
* Render performance data (internal use only)
|
|
98
98
|
*/
|
|
99
|
-
|
|
99
|
+
interface RenderPerformanceData {
|
|
100
100
|
componentName: string;
|
|
101
101
|
renderCount: number;
|
|
102
102
|
totalRenderTime: number;
|
|
@@ -106,9 +106,9 @@ export interface RenderPerformanceData {
|
|
|
106
106
|
}
|
|
107
107
|
|
|
108
108
|
/**
|
|
109
|
-
* Advanced DataTable debugger
|
|
109
|
+
* Advanced DataTable debugger (internal use only)
|
|
110
110
|
*/
|
|
111
|
-
|
|
111
|
+
class DataTableDebugger {
|
|
112
112
|
private config: DebugConfig
|
|
113
113
|
private logger = createLogger('DataTableDebugger');
|
|
114
114
|
private logEntries: DebugLogEntry[] = [];
|
|
@@ -469,104 +469,9 @@ export class DataTableDebugger {
|
|
|
469
469
|
}
|
|
470
470
|
|
|
471
471
|
/**
|
|
472
|
-
* Global debugger instance
|
|
472
|
+
* Global debugger instance (internal use only)
|
|
473
473
|
*/
|
|
474
|
-
|
|
475
|
-
|
|
476
|
-
/**
|
|
477
|
-
* Performance profiler decorator
|
|
478
|
-
*/
|
|
479
|
-
export function profile(operation: string) {
|
|
480
|
-
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
481
|
-
return function (target: any, propertyKey: string, descriptor: PropertyDescriptor) {
|
|
482
|
-
const originalMethod = descriptor.value;
|
|
483
|
-
|
|
484
|
-
descriptor.value = async function (this: unknown, ...args: unknown[]) {
|
|
485
|
-
const operationId = `${target.constructor.name}.${propertyKey}_${Date.now()}`;
|
|
486
|
-
|
|
487
|
-
dataTableDebugger.startOperation(operationId, operation, {
|
|
488
|
-
className: target.constructor.name,
|
|
489
|
-
methodName: propertyKey,
|
|
490
|
-
args: args.length,
|
|
491
|
-
});
|
|
492
|
-
|
|
493
|
-
try {
|
|
494
|
-
const result = await originalMethod.apply(this, args);
|
|
495
|
-
dataTableDebugger.endOperation(operationId, { success: true });
|
|
496
|
-
return result;
|
|
497
|
-
} catch (error) {
|
|
498
|
-
dataTableDebugger.endOperation(operationId, { success: false, error: error instanceof Error ? error.message : String(error) });
|
|
499
|
-
dataTableDebugger.log(DebugLevel.ERROR, 'Performance', `Operation failed: ${operation}`, error);
|
|
500
|
-
throw error;
|
|
501
|
-
}
|
|
502
|
-
};
|
|
503
|
-
|
|
504
|
-
return descriptor;
|
|
505
|
-
};
|
|
506
|
-
}
|
|
507
|
-
|
|
508
|
-
/**
|
|
509
|
-
* Memory monitoring utility
|
|
510
|
-
*/
|
|
511
|
-
export class MemoryMonitor {
|
|
512
|
-
private debuggerInstance: DataTableDebugger;
|
|
513
|
-
private intervalId: NodeJS.Timeout | null = null;
|
|
514
|
-
|
|
515
|
-
constructor(debuggerInstance: DataTableDebugger = dataTableDebugger) {
|
|
516
|
-
this.debuggerInstance = debuggerInstance;
|
|
517
|
-
}
|
|
518
|
-
|
|
519
|
-
start(interval: number = 5000): void {
|
|
520
|
-
this.stop(); // Stop any existing monitoring
|
|
521
|
-
|
|
522
|
-
this.intervalId = setInterval(() => {
|
|
523
|
-
this.debuggerInstance.takeMemorySnapshot('periodic');
|
|
524
|
-
}, interval);
|
|
525
|
-
}
|
|
526
|
-
|
|
527
|
-
stop(): void {
|
|
528
|
-
if (this.intervalId) {
|
|
529
|
-
clearInterval(this.intervalId);
|
|
530
|
-
this.intervalId = null;
|
|
531
|
-
}
|
|
532
|
-
}
|
|
533
|
-
}
|
|
534
|
-
|
|
535
|
-
/**
|
|
536
|
-
* Performance monitoring React hook
|
|
537
|
-
*/
|
|
538
|
-
export function usePerformanceDebugger(componentName: string) {
|
|
539
|
-
const startTime = React.useRef<number>(0);
|
|
540
|
-
|
|
541
|
-
React.useEffect(() => {
|
|
542
|
-
startTime.current = performance.now();
|
|
543
|
-
|
|
544
|
-
return () => {
|
|
545
|
-
const renderTime = performance.now() - startTime.current;
|
|
546
|
-
dataTableDebugger.trackRender(componentName, renderTime);
|
|
547
|
-
};
|
|
548
|
-
});
|
|
549
|
-
|
|
550
|
-
const trackOperation = React.useCallback((operation: string, fn: () => unknown) => {
|
|
551
|
-
const operationId = `${componentName}_${operation}_${Date.now()}`;
|
|
552
|
-
dataTableDebugger.startOperation(operationId, operation);
|
|
553
|
-
|
|
554
|
-
try {
|
|
555
|
-
const result = fn();
|
|
556
|
-
dataTableDebugger.endOperation(operationId);
|
|
557
|
-
return result;
|
|
558
|
-
} catch (error) {
|
|
559
|
-
dataTableDebugger.endOperation(operationId, { error: error instanceof Error ? error.message : String(error) });
|
|
560
|
-
throw error;
|
|
561
|
-
}
|
|
562
|
-
}, [componentName]);
|
|
563
|
-
|
|
564
|
-
return {
|
|
565
|
-
trackOperation,
|
|
566
|
-
log: (level: DebugLevel, message: string, data?: unknown) =>
|
|
567
|
-
dataTableDebugger.log(level, componentName, message, data),
|
|
568
|
-
};
|
|
569
|
-
}
|
|
474
|
+
const dataTableDebugger = new DataTableDebugger();
|
|
570
475
|
|
|
571
476
|
/**
|
|
572
477
|
* Development tools integration
|
|
@@ -23,6 +23,10 @@ export enum DataTableErrorType {
|
|
|
23
23
|
MEMORY = 'memory'
|
|
24
24
|
}
|
|
25
25
|
|
|
26
|
+
/**
|
|
27
|
+
* Custom error class for DataTable operations.
|
|
28
|
+
* Provides error type and recoverability information.
|
|
29
|
+
*/
|
|
26
30
|
export class DataTableError extends Error {
|
|
27
31
|
constructor(
|
|
28
32
|
message: string,
|
|
@@ -34,6 +38,10 @@ export class DataTableError extends Error {
|
|
|
34
38
|
}
|
|
35
39
|
}
|
|
36
40
|
|
|
41
|
+
/**
|
|
42
|
+
* Error recovery manager for DataTable.
|
|
43
|
+
* Handles error recovery strategies and error logging.
|
|
44
|
+
*/
|
|
37
45
|
export class ErrorRecoveryManager {
|
|
38
46
|
constructor(private config: FallbackConfig) {}
|
|
39
47
|
|
|
@@ -46,6 +54,10 @@ export class ErrorRecoveryManager {
|
|
|
46
54
|
}
|
|
47
55
|
}
|
|
48
56
|
|
|
57
|
+
/**
|
|
58
|
+
* Memory monitor for DataTable.
|
|
59
|
+
* Tracks memory usage and provides warnings when thresholds are exceeded.
|
|
60
|
+
*/
|
|
49
61
|
export class MemoryMonitor {
|
|
50
62
|
constructor(private threshold: number = 100) {}
|
|
51
63
|
|
|
@@ -333,6 +333,15 @@ export async function exportToCSVWithTableRows(
|
|
|
333
333
|
* - Triggers browser download
|
|
334
334
|
* - Throws error if export fails
|
|
335
335
|
*/
|
|
336
|
+
/**
|
|
337
|
+
* Exports DataTable data to CSV format.
|
|
338
|
+
* Handles column mapping, data formatting, and browser download.
|
|
339
|
+
*
|
|
340
|
+
* @template TData - The type of data records in the table
|
|
341
|
+
* @param data - Array of data records to export
|
|
342
|
+
* @param columns - Column definitions for export
|
|
343
|
+
* @param filename - Name of the CSV file to download
|
|
344
|
+
*/
|
|
336
345
|
export function exportToCSV<TData extends DataRecord>(
|
|
337
346
|
data: TData[],
|
|
338
347
|
columns: ExportColumn[],
|
|
@@ -11,10 +11,18 @@
|
|
|
11
11
|
import { createLogger } from '../../../utils/core/logger';
|
|
12
12
|
import type { CellValue } from '../types';
|
|
13
13
|
|
|
14
|
+
/**
|
|
15
|
+
* Column mapping interface for CSV import.
|
|
16
|
+
* Maps target field names to possible CSV column names.
|
|
17
|
+
*/
|
|
14
18
|
export interface ColumnMapping {
|
|
15
19
|
[targetField: string]: string[];
|
|
16
20
|
}
|
|
17
21
|
|
|
22
|
+
/**
|
|
23
|
+
* Options for flexible CSV import.
|
|
24
|
+
* Configures column mapping, date parsing, validation, and other import settings.
|
|
25
|
+
*/
|
|
18
26
|
export interface ImportOptions {
|
|
19
27
|
columnMappings?: ColumnMapping;
|
|
20
28
|
dateFormats?: readonly string[];
|
|
@@ -160,6 +168,10 @@ export interface ImportError {
|
|
|
160
168
|
message: string;
|
|
161
169
|
}
|
|
162
170
|
|
|
171
|
+
/**
|
|
172
|
+
* Import warning interface.
|
|
173
|
+
* Represents warnings encountered during CSV import.
|
|
174
|
+
*/
|
|
163
175
|
export interface ImportWarning {
|
|
164
176
|
row: number;
|
|
165
177
|
field: string;
|
|
@@ -609,54 +621,6 @@ export const commonMappings = {
|
|
|
609
621
|
}
|
|
610
622
|
};
|
|
611
623
|
|
|
612
|
-
/**
|
|
613
|
-
* Helper function to create import options with predefined date format sets
|
|
614
|
-
*/
|
|
615
|
-
export function createImportOptions(options: Partial<ImportOptions> = {}): ImportOptions {
|
|
616
|
-
return {
|
|
617
|
-
dateFormats: DATE_FORMAT_SETS.ALL,
|
|
618
|
-
strictDateParsing: false,
|
|
619
|
-
...options,
|
|
620
|
-
};
|
|
621
|
-
}
|
|
622
|
-
|
|
623
|
-
/**
|
|
624
|
-
* Helper function to create import options for specific regions
|
|
625
|
-
*/
|
|
626
|
-
export function createRegionalImportOptions(region: 'US' | 'EUROPEAN' | 'ISO' | 'NATURAL' | 'ALL', options: Partial<ImportOptions> = {}): ImportOptions {
|
|
627
|
-
return {
|
|
628
|
-
dateFormats: DATE_FORMAT_SETS[region],
|
|
629
|
-
strictDateParsing: false,
|
|
630
|
-
...options,
|
|
631
|
-
};
|
|
632
|
-
}
|
|
633
|
-
|
|
634
|
-
/**
|
|
635
|
-
* Helper function to test if a string can be parsed as a date
|
|
636
|
-
*/
|
|
637
|
-
export function testDateParsing(dateStr: string, formats?: string[]): { success: boolean; parsedDate?: Date; matchedFormat?: string } {
|
|
638
|
-
if (!dateStr || typeof dateStr !== 'string') {
|
|
639
|
-
return { success: false };
|
|
640
|
-
}
|
|
641
|
-
|
|
642
|
-
const testFormats = formats || DATE_FORMAT_SETS.ALL;
|
|
643
|
-
|
|
644
|
-
for (const format of testFormats) {
|
|
645
|
-
// This is a simplified version of the parseDateWithFormat function
|
|
646
|
-
// In a real implementation, you'd want to reuse the actual parsing logic
|
|
647
|
-
try {
|
|
648
|
-
const date = new Date(dateStr);
|
|
649
|
-
if (!isNaN(date.getTime())) {
|
|
650
|
-
return { success: true, parsedDate: date, matchedFormat: 'native' };
|
|
651
|
-
}
|
|
652
|
-
} catch (error) {
|
|
653
|
-
// Continue to next format
|
|
654
|
-
}
|
|
655
|
-
}
|
|
656
|
-
|
|
657
|
-
return { success: false };
|
|
658
|
-
}
|
|
659
|
-
|
|
660
624
|
/**
|
|
661
625
|
* Helper function to get suggested date formats based on sample data
|
|
662
626
|
*/
|
|
@@ -121,6 +121,14 @@ export interface PaginationBinding {
|
|
|
121
121
|
* });
|
|
122
122
|
* ```
|
|
123
123
|
*/
|
|
124
|
+
/**
|
|
125
|
+
* Creates a unified pagination binding that works across all pagination modes.
|
|
126
|
+
* Provides consistent pagination state and actions regardless of client/server/hybrid mode.
|
|
127
|
+
*
|
|
128
|
+
* @template TData - The type of data records in the table
|
|
129
|
+
* @param config - Pagination binding configuration
|
|
130
|
+
* @returns Unified pagination state and actions
|
|
131
|
+
*/
|
|
124
132
|
export function getPaginationBinding<TData extends DataRecord>(
|
|
125
133
|
config: PaginationBindingConfig<TData>
|
|
126
134
|
): PaginationBinding {
|
|
@@ -17,7 +17,7 @@ import type {
|
|
|
17
17
|
// ============================================================================
|
|
18
18
|
|
|
19
19
|
/**
|
|
20
|
-
* Determines the optimal pagination mode based on dataset size
|
|
20
|
+
* Determines the optimal pagination mode based on dataset size.
|
|
21
21
|
*
|
|
22
22
|
* IMPORTANT: This function NEVER returns 'server' mode - it only returns 'client' or 'hybrid'.
|
|
23
23
|
* Server mode should ONLY be used when serverSide config is explicitly provided.
|
|
@@ -26,6 +26,10 @@ import type {
|
|
|
26
26
|
*
|
|
27
27
|
* For large datasets (>10k rows), returns 'hybrid' which still uses client-side pagination
|
|
28
28
|
* but with optimizations. If true server-side pagination is needed, serverSide config must be provided.
|
|
29
|
+
*
|
|
30
|
+
* @param dataLength - Number of rows in the dataset
|
|
31
|
+
* @param serverSideThreshold - Threshold for switching to hybrid mode (default: 10000)
|
|
32
|
+
* @returns Optimal pagination mode ('client' or 'hybrid')
|
|
29
33
|
*/
|
|
30
34
|
export function determinePaginationMode(
|
|
31
35
|
dataLength: number,
|
|
@@ -295,24 +295,18 @@ describe('DatePickerWithTimezone Component', () => {
|
|
|
295
295
|
|
|
296
296
|
render(<DatePickerWithTimezone selected={selected} onSelect={onSelect} />);
|
|
297
297
|
|
|
298
|
-
expect(MockedCalendar).
|
|
299
|
-
expect.objectContaining({
|
|
300
|
-
mode: 'single',
|
|
301
|
-
selected: selected,
|
|
302
|
-
onSelect: onSelect,
|
|
303
|
-
initialFocus: true,
|
|
304
|
-
captionLayout: 'dropdown',
|
|
305
|
-
startMonth: expect.any(Date),
|
|
306
|
-
endMonth: expect.any(Date),
|
|
307
|
-
className: 'p-0'
|
|
308
|
-
}),
|
|
309
|
-
expect.anything()
|
|
310
|
-
);
|
|
298
|
+
expect(MockedCalendar).toHaveBeenCalled();
|
|
311
299
|
|
|
312
|
-
// Verify the
|
|
300
|
+
// Verify the props are correct
|
|
313
301
|
const callArgs = MockedCalendar.mock.calls[0][0];
|
|
302
|
+
expect(callArgs.mode).toBe('single');
|
|
303
|
+
expect(callArgs.selected).toEqual(selected);
|
|
304
|
+
expect(callArgs.onSelect).toBe(onSelect);
|
|
305
|
+
expect(callArgs.initialFocus).toBe(true);
|
|
306
|
+
expect(callArgs.captionLayout).toBe('dropdown');
|
|
314
307
|
expect(callArgs.startMonth).toEqual(new Date(1900, 0));
|
|
315
308
|
expect(callArgs.endMonth).toEqual(new Date(2100, 11));
|
|
309
|
+
expect(callArgs.className).toBe('p-0');
|
|
316
310
|
});
|
|
317
311
|
});
|
|
318
312
|
});
|
|
@@ -43,10 +43,10 @@
|
|
|
43
43
|
* </DialogHeader>
|
|
44
44
|
* <DialogBody>
|
|
45
45
|
* <section className="space-y-4">
|
|
46
|
-
* <
|
|
46
|
+
* <fieldset className="grid grid-cols-4 items-center gap-4">
|
|
47
47
|
* <Label htmlFor="name" className="text-right">Name</Label>
|
|
48
48
|
* <Input id="name" defaultValue="John Doe" className="col-span-3" />
|
|
49
|
-
* </
|
|
49
|
+
* </fieldset>
|
|
50
50
|
* </section>
|
|
51
51
|
* </DialogBody>
|
|
52
52
|
* <DialogFooter>
|
|
@@ -149,7 +149,7 @@
|
|
|
149
149
|
* @dependencies
|
|
150
150
|
* - @radix-ui/react-dialog - Core dialog functionality
|
|
151
151
|
* - lucide-react - Icons
|
|
152
|
-
* - React
|
|
152
|
+
* - React 19+ - Hooks and refs
|
|
153
153
|
* - Tailwind CSS - Styling and animations
|
|
154
154
|
*/
|
|
155
155
|
|
|
@@ -465,17 +465,18 @@ const DialogContent = React.forwardRef<
|
|
|
465
465
|
enableScrolling
|
|
466
466
|
});
|
|
467
467
|
|
|
468
|
-
|
|
468
|
+
// React Compiler handles memoization automatically
|
|
469
|
+
const handleEscapeKeyDown = (event: KeyboardEvent) => {
|
|
469
470
|
if (preventCloseOnEscape) {
|
|
470
471
|
event.preventDefault();
|
|
471
472
|
}
|
|
472
|
-
}
|
|
473
|
+
};
|
|
473
474
|
|
|
474
|
-
const handlePointerDownOutside =
|
|
475
|
+
const handlePointerDownOutside = (event: Event) => {
|
|
475
476
|
if (preventCloseOnOutsideClick) {
|
|
476
477
|
event.preventDefault();
|
|
477
478
|
}
|
|
478
|
-
}
|
|
479
|
+
};
|
|
479
480
|
|
|
480
481
|
// Merge smart dimensions with provided style
|
|
481
482
|
const mergedStyle = React.useMemo(() => {
|
|
@@ -8,7 +8,8 @@ import React from 'react';
|
|
|
8
8
|
import { screen, waitFor } from '@testing-library/react';
|
|
9
9
|
import userEvent from '@testing-library/user-event';
|
|
10
10
|
import { describe, it, expect, vi, beforeEach, afterEach } from 'vitest';
|
|
11
|
-
import { ErrorBoundary } from './
|
|
11
|
+
import { ErrorBoundary } from './index';
|
|
12
|
+
import { ErrorBoundaryProvider } from './ErrorBoundaryContext';
|
|
12
13
|
import { renderWithProviders } from '../../__tests__/helpers/test-utils';
|
|
13
14
|
|
|
14
15
|
// Mock the performance budget monitor
|
|
@@ -778,4 +779,182 @@ describe('ErrorBoundary Component', () => {
|
|
|
778
779
|
}
|
|
779
780
|
vi.clearAllMocks();
|
|
780
781
|
});
|
|
782
|
+
|
|
783
|
+
describe('Global Error Handler', () => {
|
|
784
|
+
it('uses global error handler when no onError prop is provided', async () => {
|
|
785
|
+
const consoleSpy = vi.spyOn(console, 'error').mockImplementation(() => {});
|
|
786
|
+
const globalErrorHandler = vi.fn();
|
|
787
|
+
|
|
788
|
+
renderWithProviders(
|
|
789
|
+
<ErrorBoundaryProvider defaultErrorHandler={globalErrorHandler}>
|
|
790
|
+
<ErrorBoundary componentName="TestComponent">
|
|
791
|
+
<ThrowingComponent />
|
|
792
|
+
</ErrorBoundary>
|
|
793
|
+
</ErrorBoundaryProvider>
|
|
794
|
+
);
|
|
795
|
+
|
|
796
|
+
await waitFor(() => {
|
|
797
|
+
expect(globalErrorHandler).toHaveBeenCalledTimes(1);
|
|
798
|
+
expect(globalErrorHandler).toHaveBeenCalledWith(
|
|
799
|
+
expect.any(Error),
|
|
800
|
+
expect.any(Object), // errorInfo
|
|
801
|
+
expect.any(String), // errorId
|
|
802
|
+
'TestComponent' // componentName
|
|
803
|
+
);
|
|
804
|
+
}, { interval: 10 });
|
|
805
|
+
|
|
806
|
+
consoleSpy.mockRestore();
|
|
807
|
+
});
|
|
808
|
+
|
|
809
|
+
it('uses global error handler with default component name when componentName not provided', async () => {
|
|
810
|
+
const consoleSpy = vi.spyOn(console, 'error').mockImplementation(() => {});
|
|
811
|
+
const globalErrorHandler = vi.fn();
|
|
812
|
+
|
|
813
|
+
renderWithProviders(
|
|
814
|
+
<ErrorBoundaryProvider defaultErrorHandler={globalErrorHandler}>
|
|
815
|
+
<ErrorBoundary>
|
|
816
|
+
<ThrowingComponent />
|
|
817
|
+
</ErrorBoundary>
|
|
818
|
+
</ErrorBoundaryProvider>
|
|
819
|
+
);
|
|
820
|
+
|
|
821
|
+
await waitFor(() => {
|
|
822
|
+
expect(globalErrorHandler).toHaveBeenCalledTimes(1);
|
|
823
|
+
expect(globalErrorHandler).toHaveBeenCalledWith(
|
|
824
|
+
expect.any(Error),
|
|
825
|
+
expect.any(Object), // errorInfo
|
|
826
|
+
expect.any(String), // errorId
|
|
827
|
+
'Unknown Component' // componentName (default)
|
|
828
|
+
);
|
|
829
|
+
}, { interval: 10 });
|
|
830
|
+
|
|
831
|
+
consoleSpy.mockRestore();
|
|
832
|
+
});
|
|
833
|
+
|
|
834
|
+
it('prefers onError prop over global error handler', async () => {
|
|
835
|
+
const consoleSpy = vi.spyOn(console, 'error').mockImplementation(() => {});
|
|
836
|
+
const globalErrorHandler = vi.fn();
|
|
837
|
+
const localErrorHandler = vi.fn();
|
|
838
|
+
|
|
839
|
+
renderWithProviders(
|
|
840
|
+
<ErrorBoundaryProvider defaultErrorHandler={globalErrorHandler}>
|
|
841
|
+
<ErrorBoundary
|
|
842
|
+
componentName="TestComponent"
|
|
843
|
+
onError={localErrorHandler}
|
|
844
|
+
>
|
|
845
|
+
<ThrowingComponent />
|
|
846
|
+
</ErrorBoundary>
|
|
847
|
+
</ErrorBoundaryProvider>
|
|
848
|
+
);
|
|
849
|
+
|
|
850
|
+
await waitFor(() => {
|
|
851
|
+
expect(localErrorHandler).toHaveBeenCalledTimes(1);
|
|
852
|
+
expect(globalErrorHandler).not.toHaveBeenCalled();
|
|
853
|
+
}, { interval: 10 });
|
|
854
|
+
|
|
855
|
+
consoleSpy.mockRestore();
|
|
856
|
+
});
|
|
857
|
+
|
|
858
|
+
it('does not call global handler when ErrorBoundary is not wrapped in provider', async () => {
|
|
859
|
+
const consoleSpy = vi.spyOn(console, 'error').mockImplementation(() => {});
|
|
860
|
+
const globalErrorHandler = vi.fn();
|
|
861
|
+
|
|
862
|
+
// Render without provider
|
|
863
|
+
renderWithProviders(
|
|
864
|
+
<ErrorBoundary componentName="TestComponent">
|
|
865
|
+
<ThrowingComponent />
|
|
866
|
+
</ErrorBoundary>
|
|
867
|
+
);
|
|
868
|
+
|
|
869
|
+
await waitFor(() => {
|
|
870
|
+
expect(screen.getByText('Error in TestComponent')).toBeInTheDocument();
|
|
871
|
+
}, { interval: 10 });
|
|
872
|
+
|
|
873
|
+
// Global handler should not be called since there's no provider
|
|
874
|
+
expect(globalErrorHandler).not.toHaveBeenCalled();
|
|
875
|
+
|
|
876
|
+
consoleSpy.mockRestore();
|
|
877
|
+
});
|
|
878
|
+
|
|
879
|
+
it('works with nested ErrorBoundary providers (inner provider overrides outer)', async () => {
|
|
880
|
+
const consoleSpy = vi.spyOn(console, 'error').mockImplementation(() => {});
|
|
881
|
+
const outerErrorHandler = vi.fn();
|
|
882
|
+
const innerErrorHandler = vi.fn();
|
|
883
|
+
|
|
884
|
+
renderWithProviders(
|
|
885
|
+
<ErrorBoundaryProvider defaultErrorHandler={outerErrorHandler}>
|
|
886
|
+
<ErrorBoundary componentName="Outer">
|
|
887
|
+
<ErrorBoundaryProvider defaultErrorHandler={innerErrorHandler}>
|
|
888
|
+
<ErrorBoundary componentName="Inner">
|
|
889
|
+
<ThrowingComponent />
|
|
890
|
+
</ErrorBoundary>
|
|
891
|
+
</ErrorBoundaryProvider>
|
|
892
|
+
</ErrorBoundary>
|
|
893
|
+
</ErrorBoundaryProvider>
|
|
894
|
+
);
|
|
895
|
+
|
|
896
|
+
await waitFor(() => {
|
|
897
|
+
expect(innerErrorHandler).toHaveBeenCalledTimes(1);
|
|
898
|
+
expect(innerErrorHandler).toHaveBeenCalledWith(
|
|
899
|
+
expect.any(Error),
|
|
900
|
+
expect.any(Object),
|
|
901
|
+
expect.any(String),
|
|
902
|
+
'Inner'
|
|
903
|
+
);
|
|
904
|
+
// Outer handler should not be called for inner boundary
|
|
905
|
+
expect(outerErrorHandler).not.toHaveBeenCalled();
|
|
906
|
+
}, { interval: 10 });
|
|
907
|
+
|
|
908
|
+
consoleSpy.mockRestore();
|
|
909
|
+
});
|
|
910
|
+
|
|
911
|
+
it('allows ErrorBoundaryProvider without defaultErrorHandler (no-op)', async () => {
|
|
912
|
+
const consoleSpy = vi.spyOn(console, 'error').mockImplementation(() => {});
|
|
913
|
+
|
|
914
|
+
renderWithProviders(
|
|
915
|
+
<ErrorBoundaryProvider>
|
|
916
|
+
<ErrorBoundary componentName="TestComponent">
|
|
917
|
+
<ThrowingComponent />
|
|
918
|
+
</ErrorBoundary>
|
|
919
|
+
</ErrorBoundaryProvider>
|
|
920
|
+
);
|
|
921
|
+
|
|
922
|
+
await waitFor(() => {
|
|
923
|
+
expect(screen.getByText('Error in TestComponent')).toBeInTheDocument();
|
|
924
|
+
}, { interval: 10 });
|
|
925
|
+
|
|
926
|
+
// Should render error UI without calling any handler
|
|
927
|
+
expect(screen.getByText('Error in TestComponent')).toBeInTheDocument();
|
|
928
|
+
|
|
929
|
+
consoleSpy.mockRestore();
|
|
930
|
+
});
|
|
931
|
+
|
|
932
|
+
it('passes correct error information to global handler', async () => {
|
|
933
|
+
const consoleSpy = vi.spyOn(console, 'error').mockImplementation(() => {});
|
|
934
|
+
const globalErrorHandler = vi.fn();
|
|
935
|
+
const testError = new Error('Custom test error');
|
|
936
|
+
|
|
937
|
+
renderWithProviders(
|
|
938
|
+
<ErrorBoundaryProvider defaultErrorHandler={globalErrorHandler}>
|
|
939
|
+
<ErrorBoundary componentName="TestComponent">
|
|
940
|
+
<ThrowingComponent errorMessage="Custom test error" />
|
|
941
|
+
</ErrorBoundary>
|
|
942
|
+
</ErrorBoundaryProvider>
|
|
943
|
+
);
|
|
944
|
+
|
|
945
|
+
await waitFor(() => {
|
|
946
|
+
expect(globalErrorHandler).toHaveBeenCalledTimes(1);
|
|
947
|
+
const callArgs = globalErrorHandler.mock.calls[0];
|
|
948
|
+
expect(callArgs[0]).toBeInstanceOf(Error);
|
|
949
|
+
expect(callArgs[0].message).toBe('Custom test error');
|
|
950
|
+
expect(callArgs[1]).toBeDefined(); // errorInfo
|
|
951
|
+
expect(callArgs[1].componentStack).toBeDefined();
|
|
952
|
+
expect(typeof callArgs[2]).toBe('string'); // errorId
|
|
953
|
+
expect(callArgs[2]).toMatch(/^error_/); // errorId format
|
|
954
|
+
expect(callArgs[3]).toBe('TestComponent'); // componentName
|
|
955
|
+
}, { interval: 10 });
|
|
956
|
+
|
|
957
|
+
consoleSpy.mockRestore();
|
|
958
|
+
});
|
|
959
|
+
});
|
|
781
960
|
});
|