@jmruthers/pace-core 0.5.121 → 0.5.124

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (255) hide show
  1. package/dist/{AuthService-D4646R4b.d.ts → AuthService-DYuQPJj6.d.ts} +0 -9
  2. package/dist/{DataTable-DGZDJUYM.js → DataTable-OKDYRW2S.js} +7 -8
  3. package/dist/{PublicLoadingSpinner-DgDWTFqn.d.ts → PublicLoadingSpinner-CaoRbHvJ.d.ts} +30 -4
  4. package/dist/{UnifiedAuthProvider-UACKFATV.js → UnifiedAuthProvider-6C47WIML.js} +3 -4
  5. package/dist/{chunk-D6BOFXYR.js → chunk-35ZDPMBM.js} +3 -3
  6. package/dist/{chunk-CGURJ27Z.js → chunk-4MXVZVNS.js} +2 -2
  7. package/dist/{chunk-ZYJ6O5CA.js → chunk-C43QIDN3.js} +2 -2
  8. package/dist/{chunk-VKOCWWVY.js → chunk-CX5M4ZAG.js} +1 -6
  9. package/dist/{chunk-VKOCWWVY.js 3.map → chunk-CX5M4ZAG.js.map} +1 -1
  10. package/dist/{chunk-RIEJGKD3.js → chunk-ESJTIADP.js} +15 -6
  11. package/dist/{chunk-RIEJGKD3.js.map → chunk-ESJTIADP.js.map} +1 -1
  12. package/dist/{chunk-HFBOFZ3Z.js → chunk-GBGYYMC6.js} +317 -251
  13. package/dist/chunk-GBGYYMC6.js.map +1 -0
  14. package/dist/{chunk-SMJZMKYN.js → chunk-GEVIB2UB.js} +43 -10
  15. package/dist/chunk-GEVIB2UB.js.map +1 -0
  16. package/dist/{chunk-TDNI6ZWL.js → chunk-IJOZZOGT.js} +7 -7
  17. package/dist/chunk-IJOZZOGT.js.map +1 -0
  18. package/dist/{chunk-GZRXOUBE.js → chunk-M6DDYFUD.js} +2 -2
  19. package/dist/chunk-M6DDYFUD.js.map +1 -0
  20. package/dist/{chunk-B4GZ2BXO.js → chunk-NZGLXZGP.js} +3 -3
  21. package/dist/{chunk-NZ32EONV.js → chunk-QWNJCQXZ.js} +2 -2
  22. package/dist/{chunk-QPI2CCBA.js → chunk-VPUCTHTY.js} +149 -96
  23. package/dist/chunk-VPUCTHTY.js.map +1 -0
  24. package/dist/{chunk-FKFHZUGF.js → chunk-XN6GWKMV.js} +43 -56
  25. package/dist/chunk-XN6GWKMV.js.map +1 -0
  26. package/dist/{chunk-BHWIUEYH.js → chunk-ZBLK676C.js} +1 -61
  27. package/dist/chunk-ZBLK676C.js.map +1 -0
  28. package/dist/components.d.ts +1 -1
  29. package/dist/components.js +11 -11
  30. package/dist/{formatting-B1jSqgl-.d.ts → formatting-DFcCxUEk.d.ts} +1 -1
  31. package/dist/hooks.d.ts +1 -1
  32. package/dist/hooks.js +9 -8
  33. package/dist/hooks.js.map +1 -1
  34. package/dist/index.d.ts +6 -6
  35. package/dist/index.js +19 -17
  36. package/dist/index.js.map +1 -1
  37. package/dist/providers.d.ts +2 -2
  38. package/dist/providers.js +2 -3
  39. package/dist/rbac/index.js +7 -8
  40. package/dist/styles/index.d.ts +1 -1
  41. package/dist/styles/index.js +5 -3
  42. package/dist/theming/runtime.d.ts +73 -1
  43. package/dist/theming/runtime.js +5 -5
  44. package/dist/{usePublicRouteParams-BdF8bZgs.d.ts → usePublicRouteParams-Dyt1tzI9.d.ts} +60 -8
  45. package/dist/utils.d.ts +1 -1
  46. package/dist/utils.js +5 -5
  47. package/docs/api/classes/ColumnFactory.md +1 -1
  48. package/docs/api/classes/ErrorBoundary.md +1 -1
  49. package/docs/api/classes/InvalidScopeError.md +1 -1
  50. package/docs/api/classes/MissingUserContextError.md +1 -1
  51. package/docs/api/classes/OrganisationContextRequiredError.md +1 -1
  52. package/docs/api/classes/PermissionDeniedError.md +1 -1
  53. package/docs/api/classes/PublicErrorBoundary.md +6 -6
  54. package/docs/api/classes/RBACAuditManager.md +1 -1
  55. package/docs/api/classes/RBACCache.md +1 -1
  56. package/docs/api/classes/RBACEngine.md +1 -1
  57. package/docs/api/classes/RBACError.md +1 -1
  58. package/docs/api/classes/RBACNotInitializedError.md +1 -1
  59. package/docs/api/classes/SecureSupabaseClient.md +6 -6
  60. package/docs/api/classes/StorageUtils.md +1 -1
  61. package/docs/api/enums/FileCategory.md +1 -1
  62. package/docs/api/interfaces/AggregateConfig.md +1 -1
  63. package/docs/api/interfaces/ButtonProps.md +1 -1
  64. package/docs/api/interfaces/CardProps.md +1 -1
  65. package/docs/api/interfaces/ColorPalette.md +1 -1
  66. package/docs/api/interfaces/ColorShade.md +1 -1
  67. package/docs/api/interfaces/DataAccessRecord.md +1 -1
  68. package/docs/api/interfaces/DataRecord.md +1 -1
  69. package/docs/api/interfaces/DataTableAction.md +1 -1
  70. package/docs/api/interfaces/DataTableColumn.md +1 -1
  71. package/docs/api/interfaces/DataTableProps.md +1 -1
  72. package/docs/api/interfaces/DataTableToolbarButton.md +1 -1
  73. package/docs/api/interfaces/EmptyStateConfig.md +1 -1
  74. package/docs/api/interfaces/EnhancedNavigationMenuProps.md +1 -1
  75. package/docs/api/interfaces/EventAppRoleData.md +1 -1
  76. package/docs/api/interfaces/FileDisplayProps.md +1 -1
  77. package/docs/api/interfaces/FileMetadata.md +1 -1
  78. package/docs/api/interfaces/FileReference.md +1 -1
  79. package/docs/api/interfaces/FileSizeLimits.md +1 -1
  80. package/docs/api/interfaces/FileUploadOptions.md +1 -1
  81. package/docs/api/interfaces/FileUploadProps.md +1 -1
  82. package/docs/api/interfaces/FooterProps.md +1 -1
  83. package/docs/api/interfaces/GrantEventAppRoleParams.md +1 -1
  84. package/docs/api/interfaces/InactivityWarningModalProps.md +1 -1
  85. package/docs/api/interfaces/InputProps.md +1 -1
  86. package/docs/api/interfaces/LabelProps.md +1 -1
  87. package/docs/api/interfaces/LoginFormProps.md +1 -1
  88. package/docs/api/interfaces/NavigationAccessRecord.md +1 -1
  89. package/docs/api/interfaces/NavigationContextType.md +1 -1
  90. package/docs/api/interfaces/NavigationGuardProps.md +1 -1
  91. package/docs/api/interfaces/NavigationItem.md +1 -1
  92. package/docs/api/interfaces/NavigationMenuProps.md +1 -1
  93. package/docs/api/interfaces/NavigationProviderProps.md +1 -1
  94. package/docs/api/interfaces/Organisation.md +1 -1
  95. package/docs/api/interfaces/OrganisationContextType.md +1 -1
  96. package/docs/api/interfaces/OrganisationMembership.md +1 -1
  97. package/docs/api/interfaces/OrganisationProviderProps.md +1 -1
  98. package/docs/api/interfaces/OrganisationSecurityError.md +1 -1
  99. package/docs/api/interfaces/PaceAppLayoutProps.md +1 -1
  100. package/docs/api/interfaces/PaceLoginPageProps.md +1 -1
  101. package/docs/api/interfaces/PageAccessRecord.md +1 -1
  102. package/docs/api/interfaces/PagePermissionContextType.md +1 -1
  103. package/docs/api/interfaces/PagePermissionGuardProps.md +1 -1
  104. package/docs/api/interfaces/PagePermissionProviderProps.md +1 -1
  105. package/docs/api/interfaces/PaletteData.md +1 -1
  106. package/docs/api/interfaces/PermissionEnforcerProps.md +1 -1
  107. package/docs/api/interfaces/ProtectedRouteProps.md +1 -1
  108. package/docs/api/interfaces/PublicErrorBoundaryProps.md +7 -7
  109. package/docs/api/interfaces/PublicErrorBoundaryState.md +5 -5
  110. package/docs/api/interfaces/PublicLoadingSpinnerProps.md +7 -7
  111. package/docs/api/interfaces/PublicPageFooterProps.md +1 -1
  112. package/docs/api/interfaces/PublicPageHeaderProps.md +51 -12
  113. package/docs/api/interfaces/PublicPageLayoutProps.md +72 -12
  114. package/docs/api/interfaces/RBACConfig.md +1 -1
  115. package/docs/api/interfaces/RBACLogger.md +1 -1
  116. package/docs/api/interfaces/RevokeEventAppRoleParams.md +1 -1
  117. package/docs/api/interfaces/RoleBasedRouterContextType.md +1 -1
  118. package/docs/api/interfaces/RoleBasedRouterProps.md +1 -1
  119. package/docs/api/interfaces/RoleManagementResult.md +1 -1
  120. package/docs/api/interfaces/RouteAccessRecord.md +1 -1
  121. package/docs/api/interfaces/RouteConfig.md +1 -1
  122. package/docs/api/interfaces/SecureDataContextType.md +1 -1
  123. package/docs/api/interfaces/SecureDataProviderProps.md +1 -1
  124. package/docs/api/interfaces/StorageConfig.md +1 -1
  125. package/docs/api/interfaces/StorageFileInfo.md +1 -1
  126. package/docs/api/interfaces/StorageFileMetadata.md +1 -1
  127. package/docs/api/interfaces/StorageListOptions.md +1 -1
  128. package/docs/api/interfaces/StorageListResult.md +1 -1
  129. package/docs/api/interfaces/StorageUploadOptions.md +1 -1
  130. package/docs/api/interfaces/StorageUploadResult.md +1 -1
  131. package/docs/api/interfaces/StorageUrlOptions.md +1 -1
  132. package/docs/api/interfaces/StyleImport.md +1 -1
  133. package/docs/api/interfaces/SwitchProps.md +1 -1
  134. package/docs/api/interfaces/ToastActionElement.md +1 -1
  135. package/docs/api/interfaces/ToastProps.md +1 -1
  136. package/docs/api/interfaces/UnifiedAuthContextType.md +1 -1
  137. package/docs/api/interfaces/UnifiedAuthProviderProps.md +1 -1
  138. package/docs/api/interfaces/UseInactivityTrackerOptions.md +1 -1
  139. package/docs/api/interfaces/UseInactivityTrackerReturn.md +1 -1
  140. package/docs/api/interfaces/UsePublicEventOptions.md +1 -1
  141. package/docs/api/interfaces/UsePublicEventReturn.md +1 -1
  142. package/docs/api/interfaces/UsePublicFileDisplayOptions.md +1 -1
  143. package/docs/api/interfaces/UsePublicFileDisplayReturn.md +1 -1
  144. package/docs/api/interfaces/UsePublicRouteParamsReturn.md +1 -1
  145. package/docs/api/interfaces/UseResolvedScopeOptions.md +1 -1
  146. package/docs/api/interfaces/UseResolvedScopeReturn.md +1 -1
  147. package/docs/api/interfaces/UserEventAccess.md +1 -1
  148. package/docs/api/interfaces/UserMenuProps.md +1 -1
  149. package/docs/api/interfaces/UserProfile.md +1 -1
  150. package/docs/api/modules.md +140 -30
  151. package/docs/best-practices/README.md +1 -1
  152. package/docs/implementation-guides/datatable-filtering.md +313 -0
  153. package/docs/implementation-guides/datatable-rbac-usage.md +317 -0
  154. package/docs/implementation-guides/hierarchical-datatable.md +850 -0
  155. package/docs/implementation-guides/large-datasets.md +281 -0
  156. package/docs/implementation-guides/performance.md +403 -0
  157. package/docs/implementation-guides/public-pages.md +4 -4
  158. package/docs/migration/quick-migration-guide.md +320 -0
  159. package/docs/rbac/quick-start.md +16 -16
  160. package/docs/troubleshooting/README.md +4 -4
  161. package/docs/troubleshooting/cake-page-permission-guard-issue-summary.md +1 -1
  162. package/docs/troubleshooting/debugging.md +1117 -0
  163. package/docs/troubleshooting/migration.md +918 -0
  164. package/examples/public-pages/CorrectPublicPageImplementation.tsx +30 -30
  165. package/examples/public-pages/PublicEventPage.tsx +41 -41
  166. package/examples/public-pages/PublicPageApp.tsx +33 -33
  167. package/examples/public-pages/PublicPageUsageExample.tsx +30 -30
  168. package/package.json +4 -4
  169. package/src/__tests__/hooks/usePermissions.test.ts +265 -0
  170. package/src/components/DataTable/DataTable.test.tsx +9 -38
  171. package/src/components/DataTable/DataTable.tsx +0 -7
  172. package/src/components/DataTable/components/DataTableCore.tsx +125 -144
  173. package/src/components/DataTable/components/DataTableModals.tsx +25 -22
  174. package/src/components/DataTable/components/DataTableToolbar.tsx +14 -1
  175. package/src/components/DataTable/components/EditableRow.tsx +118 -42
  176. package/src/components/DataTable/components/UnifiedTableBody.tsx +129 -76
  177. package/src/components/DataTable/components/__tests__/DataTableModals.test.tsx +33 -14
  178. package/src/components/DataTable/utils/__tests__/exportUtils.test.ts +17 -5
  179. package/src/components/DataTable/utils/exportUtils.ts +3 -2
  180. package/src/components/Dialog/Dialog.tsx +1 -1
  181. package/src/components/Dialog/README.md +24 -24
  182. package/src/components/Dialog/examples/BasicHtmlTest.tsx +2 -2
  183. package/src/components/Dialog/examples/DebugHtmlExample.tsx +6 -6
  184. package/src/components/Dialog/examples/HtmlDialogExample.tsx +2 -2
  185. package/src/components/Dialog/examples/SimpleHtmlTest.tsx +3 -3
  186. package/src/components/Dialog/examples/__tests__/SimpleHtmlTest.test.tsx +4 -4
  187. package/src/components/PaceAppLayout/PaceAppLayout.tsx +12 -1
  188. package/src/components/PublicLayout/EventLogo.tsx +175 -0
  189. package/src/components/PublicLayout/PublicErrorBoundary.tsx +22 -18
  190. package/src/components/PublicLayout/PublicLoadingSpinner.tsx +22 -14
  191. package/src/components/PublicLayout/PublicPageHeader.tsx +133 -40
  192. package/src/components/PublicLayout/PublicPageLayout.tsx +75 -72
  193. package/src/components/PublicLayout/__tests__/PublicErrorBoundary.test.tsx +1 -1
  194. package/src/components/PublicLayout/__tests__/PublicLoadingSpinner.test.tsx +8 -8
  195. package/src/components/PublicLayout/__tests__/PublicPageHeader.test.tsx +23 -16
  196. package/src/components/PublicLayout/__tests__/PublicPageLayout.test.tsx +86 -14
  197. package/src/examples/CorrectPublicPageImplementation.tsx +30 -30
  198. package/src/examples/PublicEventPage.tsx +41 -41
  199. package/src/examples/PublicPageApp.tsx +33 -33
  200. package/src/examples/PublicPageUsageExample.tsx +30 -30
  201. package/src/hooks/__tests__/usePublicEvent.unit.test.ts +583 -0
  202. package/src/hooks/__tests__/usePublicRouteParams.unit.test.ts +10 -3
  203. package/src/hooks/index.ts +1 -1
  204. package/src/hooks/public/usePublicEventLogo.ts +285 -0
  205. package/src/hooks/public/usePublicRouteParams.ts +21 -4
  206. package/src/hooks/useEventTheme.test.ts +119 -43
  207. package/src/hooks/useEventTheme.ts +84 -55
  208. package/src/index.ts +3 -1
  209. package/src/rbac/components/__tests__/EnhancedNavigationMenu.test.tsx +630 -0
  210. package/src/rbac/components/__tests__/NavigationProvider.test.tsx +667 -0
  211. package/src/rbac/components/__tests__/PagePermissionProvider.test.tsx +647 -0
  212. package/src/rbac/components/__tests__/SecureDataProvider.fixed.test.tsx +496 -0
  213. package/src/rbac/components/__tests__/SecureDataProvider.test.tsx +496 -0
  214. package/src/rbac/secureClient.ts +4 -2
  215. package/src/services/EventService.ts +0 -66
  216. package/src/services/__tests__/EventService.eventColours.test.ts +44 -40
  217. package/src/styles/index.ts +1 -1
  218. package/src/theming/__tests__/parseEventColours.test.ts +209 -0
  219. package/src/theming/parseEventColours.ts +123 -0
  220. package/src/theming/runtime.ts +3 -0
  221. package/src/types/__tests__/file-reference.test.ts +447 -0
  222. package/src/utils/formatDate.test.ts +11 -11
  223. package/src/utils/formatting.ts +3 -2
  224. package/dist/chunk-BDZUMRBD.js 3.map +0 -1
  225. package/dist/chunk-BHWIUEYH.js.map +0 -1
  226. package/dist/chunk-CGURJ27Z.js.map +0 -1
  227. package/dist/chunk-FKFHZUGF.js.map +0 -1
  228. package/dist/chunk-GKHF54DI 2.js +0 -619
  229. package/dist/chunk-GKHF54DI.js 2.map +0 -1
  230. package/dist/chunk-GZRXOUBE.js.map +0 -1
  231. package/dist/chunk-HFBOFZ3Z.js.map +0 -1
  232. package/dist/chunk-NZ32EONV.js.map +0 -1
  233. package/dist/chunk-O3NWNXDY 2.js +0 -76
  234. package/dist/chunk-QPI2CCBA.js.map +0 -1
  235. package/dist/chunk-SMJZMKYN.js.map +0 -1
  236. package/dist/chunk-TDNI6ZWL.js 2.map +0 -1
  237. package/dist/chunk-TDNI6ZWL.js.map +0 -1
  238. package/dist/chunk-VKOCWWVY.js.map +0 -1
  239. package/dist/chunk-WP5I5GLN 2.js +0 -1564
  240. package/dist/index 3.js +0 -856
  241. package/dist/providers 3.js +0 -38
  242. package/dist/providers.js 3.map +0 -1
  243. package/dist/types 3.js +0 -128
  244. package/dist/types.js 3.map +0 -1
  245. package/dist/useInactivityTracker-MRUU55XI.js 3.map +0 -1
  246. package/dist/utils.js 3.map +0 -1
  247. package/dist/validation 3.js +0 -479
  248. package/src/styles/semantic.css +0 -24
  249. /package/dist/{DataTable-DGZDJUYM.js.map → DataTable-OKDYRW2S.js.map} +0 -0
  250. /package/dist/{UnifiedAuthProvider-UACKFATV.js.map → UnifiedAuthProvider-6C47WIML.js.map} +0 -0
  251. /package/dist/{chunk-D6BOFXYR.js.map → chunk-35ZDPMBM.js.map} +0 -0
  252. /package/dist/{chunk-CGURJ27Z.js 2.map → chunk-4MXVZVNS.js.map} +0 -0
  253. /package/dist/{chunk-ZYJ6O5CA.js.map → chunk-C43QIDN3.js.map} +0 -0
  254. /package/dist/{chunk-B4GZ2BXO.js.map → chunk-NZGLXZGP.js.map} +0 -0
  255. /package/dist/{chunk-NZ32EONV.js 2.map → chunk-QWNJCQXZ.js.map} +0 -0
package/dist/hooks.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"sources":["../src/hooks/useFocusManagement.ts","../src/hooks/useFocusTrap.ts","../src/hooks/useKeyboardShortcuts.ts","../src/hooks/useIsMobile.ts","../src/hooks/useDebounce.ts","../src/hooks/useDataTableState.ts","../src/hooks/useZodForm.ts","../src/hooks/usePerformanceMonitor.ts"],"sourcesContent":["\nimport { useRef, useCallback, useEffect } from 'react';\n\nexport interface FocusManagementOptions {\n trapFocus?: boolean;\n autoFocus?: boolean;\n restoreFocus?: boolean;\n onEscape?: () => void;\n onFocusFirst?: () => void;\n onFocusLast?: () => void;\n}\n\nexport interface FocusManagementReturn {\n containerRef: React.RefObject<HTMLDivElement>;\n focusRef: React.RefObject<HTMLElement>;\n setFocus: (element: HTMLElement | null) => void;\n focusFirst: () => void;\n focusLast: () => void;\n trapFocus: () => void;\n releaseFocus: () => void;\n getFocusableElements: () => HTMLElement[];\n handleEscape: (callback: () => void) => () => void;\n}\n\nexport function useFocusManagement(options: FocusManagementOptions = {}): FocusManagementReturn {\n const { \n trapFocus = false, \n autoFocus = false, \n restoreFocus = false,\n onEscape,\n onFocusFirst,\n onFocusLast \n } = options;\n\n const containerRef = useRef<HTMLDivElement>(null);\n const focusRef = useRef<HTMLElement | null>(null);\n const previousFocusRef = useRef<HTMLElement | null>(null);\n const trapFocusActiveRef = useRef<boolean>(false);\n\n const setFocus = useCallback((element: HTMLElement | null) => {\n focusRef.current = element;\n element?.focus();\n }, []);\n\n const getFocusableElements = useCallback((): HTMLElement[] => {\n if (!containerRef.current) return [];\n\n return Array.from(\n containerRef.current.querySelectorAll<HTMLElement>(\n 'button, [href], input, select, textarea, [tabindex]:not([tabindex=\"-1\"])'\n )\n ).filter((el) => !el.hasAttribute('disabled') && !el.hasAttribute('hidden'));\n }, []);\n\n const focusFirst = useCallback(() => {\n const elements = getFocusableElements();\n if (elements.length > 0) {\n setFocus(elements[0]);\n onFocusFirst?.();\n }\n }, [getFocusableElements, setFocus, onFocusFirst]);\n\n const focusLast = useCallback(() => {\n const elements = getFocusableElements();\n if (elements.length > 0) {\n setFocus(elements[elements.length - 1]);\n onFocusLast?.();\n }\n }, [getFocusableElements, setFocus, onFocusLast]);\n\n const trapFocusMethod = useCallback(() => {\n trapFocusActiveRef.current = true;\n }, []);\n\n const releaseFocus = useCallback(() => {\n trapFocusActiveRef.current = false;\n }, []);\n\n const handleEscape = useCallback((callback: () => void) => {\n return () => {\n const handleKeyDown = (event: KeyboardEvent) => {\n if (event.key === 'Escape') {\n callback();\n }\n };\n\n document.addEventListener('keydown', handleKeyDown);\n return () => document.removeEventListener('keydown', handleKeyDown);\n };\n }, []);\n\n // Handle focus trap\n useEffect(() => {\n if (!trapFocus || !containerRef.current) return;\n\n const handleKeyDown = (event: KeyboardEvent) => {\n if (event.key === 'Escape' && onEscape) {\n onEscape();\n return;\n }\n\n if (event.key !== 'Tab') return;\n\n const elements = getFocusableElements();\n if (elements.length === 0) return;\n\n const firstElement = elements[0];\n const lastElement = elements[elements.length - 1];\n\n if (event.shiftKey) {\n if (document.activeElement === firstElement) {\n event.preventDefault();\n lastElement.focus();\n }\n } else {\n if (document.activeElement === lastElement) {\n event.preventDefault();\n firstElement.focus();\n }\n }\n };\n\n const current = containerRef.current;\n current.addEventListener('keydown', handleKeyDown);\n return () => {\n current?.removeEventListener('keydown', handleKeyDown);\n };\n }, [trapFocus, onEscape, getFocusableElements]);\n\n // Handle auto focus\n useEffect(() => {\n if (autoFocus) {\n focusFirst();\n }\n }, [autoFocus, focusFirst]);\n\n // Handle focus restoration\n useEffect(() => {\n if (!restoreFocus) return;\n\n previousFocusRef.current = document.activeElement as HTMLElement;\n\n return () => {\n if (previousFocusRef.current) {\n previousFocusRef.current.focus();\n }\n };\n }, [restoreFocus]);\n\n return {\n containerRef,\n focusRef,\n setFocus,\n focusFirst,\n focusLast,\n trapFocus: trapFocusMethod,\n releaseFocus,\n getFocusableElements,\n handleEscape,\n };\n}\n","\nimport { useRef, useEffect, useCallback } from 'react';\n\nexport interface FocusTrapOptions {\n /** Whether the focus trap is active */\n isActive?: boolean;\n /** Whether to auto-focus the first element when activated */\n autoFocus?: boolean;\n /** Whether to restore focus to the previously focused element when deactivated */\n restoreFocus?: boolean;\n /** Callback when Escape key is pressed */\n onEscape?: () => void;\n /** Selector for focusable elements (optional override) */\n focusableSelector?: string;\n}\n\nexport interface FocusTrapReturn {\n /** Ref to attach to the container element */\n containerRef: React.RefObject<HTMLElement>;\n /** Focus the first focusable element */\n focusFirst: () => void;\n /** Focus the last focusable element */\n focusLast: () => void;\n /** Get all focusable elements in the container */\n getFocusableElements: () => HTMLElement[];\n}\n\nconst DEFAULT_FOCUSABLE_SELECTOR = [\n 'button:not([disabled])',\n '[href]',\n 'input:not([disabled])',\n 'select:not([disabled])',\n 'textarea:not([disabled])',\n '[tabindex]:not([tabindex=\"-1\"])',\n '[contenteditable=\"true\"]'\n].join(', ');\n\n/**\n * Hook for creating accessible focus traps\n * Useful for modals, dropdowns, and other overlay components\n */\nexport function useFocusTrap(options: FocusTrapOptions = {}): FocusTrapReturn {\n const {\n isActive = false,\n autoFocus = false,\n restoreFocus = false,\n onEscape,\n focusableSelector = DEFAULT_FOCUSABLE_SELECTOR\n } = options;\n\n const containerRef = useRef<HTMLElement>(null);\n const previouslyFocusedElement = useRef<HTMLElement | null>(null);\n\n const getFocusableElements = useCallback((): HTMLElement[] => {\n if (!containerRef.current) return [];\n\n return Array.from(\n containerRef.current.querySelectorAll<HTMLElement>(focusableSelector)\n ).filter((element) => {\n return (\n !element.hasAttribute('disabled') &&\n !element.hasAttribute('hidden') &&\n element.offsetParent !== null // visible check\n );\n });\n }, [focusableSelector]);\n\n const focusFirst = useCallback(() => {\n const elements = getFocusableElements();\n if (elements.length > 0) {\n elements[0].focus();\n }\n }, [getFocusableElements]);\n\n const focusLast = useCallback(() => {\n const elements = getFocusableElements();\n if (elements.length > 0) {\n elements[elements.length - 1].focus();\n }\n }, [getFocusableElements]);\n\n // Handle keyboard events\n useEffect(() => {\n if (!isActive || !containerRef.current) return;\n\n const handleKeyDown = (event: KeyboardEvent) => {\n // Handle Escape key\n if (event.key === 'Escape' && onEscape) {\n onEscape();\n return;\n }\n\n // Handle Tab key for focus trapping\n if (event.key === 'Tab') {\n const focusableElements = getFocusableElements();\n if (focusableElements.length === 0) return;\n\n const firstElement = focusableElements[0];\n const lastElement = focusableElements[focusableElements.length - 1];\n\n if (event.shiftKey) {\n // Shift + Tab: moving backwards\n if (document.activeElement === firstElement) {\n event.preventDefault();\n lastElement.focus();\n }\n } else {\n // Tab: moving forwards\n if (document.activeElement === lastElement) {\n event.preventDefault();\n firstElement.focus();\n }\n }\n }\n };\n\n const container = containerRef.current;\n container.addEventListener('keydown', handleKeyDown);\n\n return () => {\n container.removeEventListener('keydown', handleKeyDown);\n };\n }, [isActive, onEscape, getFocusableElements]);\n\n // Handle focus restoration\n useEffect(() => {\n if (!isActive) return;\n\n // Store the previously focused element\n if (restoreFocus) {\n previouslyFocusedElement.current = document.activeElement as HTMLElement;\n }\n\n // Auto-focus first element if requested\n if (autoFocus) {\n const timer = setTimeout(focusFirst, 0);\n return () => clearTimeout(timer);\n }\n\n return () => {\n // Restore focus when trap is deactivated\n if (restoreFocus && previouslyFocusedElement.current) {\n previouslyFocusedElement.current.focus();\n previouslyFocusedElement.current = null;\n }\n };\n }, [isActive, autoFocus, restoreFocus, focusFirst]);\n\n return {\n containerRef,\n focusFirst,\n focusLast,\n getFocusableElements\n };\n}\n","import { useEffect, useCallback } from 'react';\n\nexport interface KeyboardShortcut {\n /** Key combination (e.g., 'Escape', 'Enter', 'ArrowDown', 'ctrl+s') */\n key: string;\n /** Callback function to execute */\n handler: (event: KeyboardEvent) => void;\n /** Description for documentation/help */\n description?: string;\n /** Whether the shortcut is enabled */\n enabled?: boolean;\n /** Prevent default browser behavior */\n preventDefault?: boolean;\n /** Stop event propagation */\n stopPropagation?: boolean;\n}\n\nexport interface KeyboardShortcutsOptions {\n /** Element to attach listeners to (defaults to document) */\n element?: HTMLElement | Document;\n /** Whether shortcuts are globally enabled */\n enabled?: boolean;\n}\n\n/**\n * Parse key combination string into modifier and key parts\n */\nfunction parseKeyCombo(combo: string) {\n const parts = combo.toLowerCase().split('+');\n const key = parts.pop()!;\n const modifiers = {\n ctrl: parts.includes('ctrl') || parts.includes('control'),\n alt: parts.includes('alt'),\n shift: parts.includes('shift'),\n meta: parts.includes('meta') || parts.includes('cmd')\n };\n return { key, modifiers };\n}\n\n/**\n * Check if event matches the key combination\n */\nfunction matchesKeyCombo(event: KeyboardEvent, combo: string): boolean {\n const { key, modifiers } = parseKeyCombo(combo);\n \n // Check if the main key matches\n const eventKey = event.key.toLowerCase();\n const targetKey = key.toLowerCase();\n \n if (eventKey !== targetKey) {\n return false;\n }\n \n // Check modifiers\n return (\n event.ctrlKey === modifiers.ctrl &&\n event.altKey === modifiers.alt &&\n event.shiftKey === modifiers.shift &&\n event.metaKey === modifiers.meta\n );\n}\n\n/**\n * Hook for managing keyboard shortcuts\n * \n * @example\n * ```tsx\n * function MyComponent() {\n * const shortcuts = [\n * {\n * key: 'Escape',\n * handler: () => setIsOpen(false),\n * description: 'Close modal'\n * },\n * {\n * key: 'ctrl+s',\n * handler: (e) => handleSave(),\n * description: 'Save document',\n * preventDefault: true\n * }\n * ];\n * \n * useKeyboardShortcuts(shortcuts);\n * \n * return <div>Content</div>;\n * }\n * ```\n */\nexport function useKeyboardShortcuts(\n shortcuts: KeyboardShortcut[],\n options: KeyboardShortcutsOptions = {}\n): void {\n const { element = document, enabled = true } = options;\n\n const handleKeyDown = useCallback((event: KeyboardEvent) => {\n if (!enabled) return;\n\n for (const shortcut of shortcuts) {\n if (shortcut.enabled === false) continue;\n\n if (matchesKeyCombo(event, shortcut.key)) {\n if (shortcut.preventDefault) {\n event.preventDefault();\n }\n if (shortcut.stopPropagation) {\n event.stopPropagation();\n }\n \n shortcut.handler(event);\n break; // Only handle first matching shortcut\n }\n }\n }, [shortcuts, enabled]);\n\n useEffect(() => {\n if (!enabled) return;\n\n element.addEventListener('keydown', handleKeyDown as EventListener);\n return () => element.removeEventListener('keydown', handleKeyDown as EventListener);\n }, [element, enabled, handleKeyDown]);\n}\n\n/**\n * Hook for common accessibility keyboard shortcuts\n */\nexport function useAccessibilityShortcuts(handlers: {\n onEscape?: () => void;\n onEnter?: () => void;\n onSpace?: () => void;\n onArrowUp?: () => void;\n onArrowDown?: () => void;\n onArrowLeft?: () => void;\n onArrowRight?: () => void;\n onHome?: () => void;\n onEnd?: () => void;\n onTab?: () => void;\n onShiftTab?: () => void;\n}) {\n const shortcuts: KeyboardShortcut[] = [];\n\n if (handlers.onEscape) {\n shortcuts.push({\n key: 'Escape',\n handler: handlers.onEscape,\n description: 'Escape/Cancel'\n });\n }\n\n if (handlers.onEnter) {\n shortcuts.push({\n key: 'Enter',\n handler: handlers.onEnter,\n description: 'Activate/Submit'\n });\n }\n\n if (handlers.onSpace) {\n shortcuts.push({\n key: ' ',\n handler: handlers.onSpace,\n description: 'Activate',\n preventDefault: true\n });\n }\n\n if (handlers.onArrowUp) {\n shortcuts.push({\n key: 'ArrowUp',\n handler: handlers.onArrowUp,\n description: 'Navigate up',\n preventDefault: true\n });\n }\n\n if (handlers.onArrowDown) {\n shortcuts.push({\n key: 'ArrowDown',\n handler: handlers.onArrowDown,\n description: 'Navigate down',\n preventDefault: true\n });\n }\n\n if (handlers.onArrowLeft) {\n shortcuts.push({\n key: 'ArrowLeft',\n handler: handlers.onArrowLeft,\n description: 'Navigate left',\n preventDefault: true\n });\n }\n\n if (handlers.onArrowRight) {\n shortcuts.push({\n key: 'ArrowRight',\n handler: handlers.onArrowRight,\n description: 'Navigate right',\n preventDefault: true\n });\n }\n\n if (handlers.onHome) {\n shortcuts.push({\n key: 'Home',\n handler: handlers.onHome,\n description: 'Go to first item',\n preventDefault: true\n });\n }\n\n if (handlers.onEnd) {\n shortcuts.push({\n key: 'End',\n handler: handlers.onEnd,\n description: 'Go to last item',\n preventDefault: true\n });\n }\n\n if (handlers.onTab) {\n shortcuts.push({\n key: 'Tab',\n handler: handlers.onTab,\n description: 'Navigate forward'\n });\n }\n\n if (handlers.onShiftTab) {\n shortcuts.push({\n key: 'shift+Tab',\n handler: handlers.onShiftTab,\n description: 'Navigate backward'\n });\n }\n\n useKeyboardShortcuts(shortcuts);\n}\n","/**\n * @file useIsMobile Hook\n * @description Hook for detecting mobile viewport using modern matchMedia API\n */\n\nimport { useState, useEffect } from 'react';\n\nconst MOBILE_BREAKPOINT = 768;\n\n/**\n * Hook to detect if the viewport is mobile-sized using matchMedia API.\n * More performant than window resize events.\n * @returns {boolean} True if mobile, false otherwise.\n */\nexport function useIsMobile(): boolean {\n const [isMobile, setIsMobile] = useState<boolean | undefined>(undefined);\n\n useEffect(() => {\n // Handle SSR case\n if (typeof window === 'undefined') {\n setIsMobile(false);\n return;\n }\n\n const mql = window.matchMedia(`(max-width: ${MOBILE_BREAKPOINT - 1}px)`);\n \n const onChange = () => {\n setIsMobile(window.innerWidth < MOBILE_BREAKPOINT);\n };\n\n // Set initial value\n setIsMobile(window.innerWidth < MOBILE_BREAKPOINT);\n\n // Add event listener\n mql.addEventListener('change', onChange);\n\n // Cleanup\n return () => mql.removeEventListener('change', onChange);\n }, []);\n\n return !!isMobile;\n}\n","\nimport { useState, useEffect } from 'react';\n\nexport function useDebounce<T>(value: T, delay: number): T {\n const [debouncedValue, setDebouncedValue] = useState<T>(value);\n\n useEffect(() => {\n const handler = setTimeout(() => {\n setDebouncedValue(value);\n }, delay);\n\n return () => {\n clearTimeout(handler);\n };\n }, [value, delay]);\n\n return debouncedValue;\n}\n","/**\n * @file useDataTableState Hook\n * @description Hook for managing DataTable state\n */\n\nimport { useState, useCallback, useMemo } from 'react';\nimport type { SortingState, ColumnFiltersState, ExpandedState } from '@tanstack/react-table';\n\nexport interface DataTableState {\n sorting: SortingState;\n columnFilters: ColumnFiltersState;\n expanded: ExpandedState;\n pageSize: number;\n pageIndex: number;\n selectedRows: string[];\n}\n\nexport interface DataTableActions {\n setSorting: (sorting: SortingState) => void;\n setColumnFilters: (filters: ColumnFiltersState) => void;\n setExpanded: (expanded: ExpandedState) => void;\n setPageSize: (size: number) => void;\n setPageIndex: (index: number) => void;\n setSelectedRows: (rows: string[]) => void;\n resetState: () => void;\n}\n\nexport interface DataTableComputed {\n paginatedData: any[];\n totalPages: number;\n hasNextPage: boolean;\n hasPreviousPage: boolean;\n}\n\nexport interface UseDataTableStateOptions {\n initialPageSize?: number;\n data: any[];\n}\n\n/**\n * Hook for managing DataTable state\n * @param options Configuration options\n * @returns Object containing state, actions, and computed values\n */\nexport function useDataTableState(options: UseDataTableStateOptions) {\n const { initialPageSize = 10, data } = options;\n\n // State\n const [sorting, setSorting] = useState<SortingState>([]);\n const [columnFilters, setColumnFilters] = useState<ColumnFiltersState>([]);\n const [expanded, setExpanded] = useState<ExpandedState>({});\n const [pageSize, setPageSize] = useState(initialPageSize);\n const [pageIndex, setPageIndex] = useState(0);\n const [selectedRows, setSelectedRows] = useState<string[]>([]);\n\n // Actions\n const resetState = useCallback(() => {\n setSorting([]);\n setColumnFilters([]);\n setExpanded({});\n setPageSize(initialPageSize);\n setPageIndex(0);\n setSelectedRows([]);\n }, [initialPageSize]);\n\n // Computed values\n const paginatedData = useMemo(() => {\n const start = pageIndex * pageSize;\n const end = start + pageSize;\n return data.slice(start, end);\n }, [data, pageIndex, pageSize]);\n\n const totalPages = useMemo(() => {\n return Math.ceil(data.length / pageSize);\n }, [data.length, pageSize]);\n\n const hasNextPage = useMemo(() => {\n return pageIndex < totalPages - 1;\n }, [pageIndex, totalPages]);\n\n const hasPreviousPage = useMemo(() => {\n return pageIndex > 0;\n }, [pageIndex]);\n\n return {\n state: {\n sorting,\n columnFilters,\n expanded,\n pageSize,\n pageIndex,\n selectedRows\n },\n actions: {\n setSorting,\n setColumnFilters,\n setExpanded,\n setPageSize,\n setPageIndex,\n setSelectedRows,\n resetState\n },\n computed: {\n paginatedData,\n totalPages,\n hasNextPage,\n hasPreviousPage\n }\n };\n}\n","\n/**\n * Zod Form Hook\n * \n * Enhanced form hook with Zod validation\n */\n\nimport { useForm } from 'react-hook-form';\nimport { zodResolver } from '@hookform/resolvers/zod';\nimport { z } from 'zod';\n\ninterface UseZodFormProps<T extends z.ZodTypeAny> {\n schema: T;\n defaultValues?: Partial<z.infer<T>>;\n mode?: 'onSubmit' | 'onBlur' | 'onChange' | 'onTouched' | 'all';\n}\n\nexport function useZodForm<T extends z.ZodTypeAny>({\n schema,\n defaultValues,\n mode = 'onSubmit'\n}: UseZodFormProps<T>) {\n return useForm<z.infer<T>>({\n resolver: zodResolver(schema),\n defaultValues: defaultValues as any,\n mode\n });\n}\n","\nimport { useEffect, useRef, useCallback } from 'react';\nimport { performanceBudgetMonitor, PERFORMANCE_BUDGETS } from '../utils/performanceBudgets';\n\nexport interface PerformanceMetrics {\n renderTime: number;\n componentName: string;\n timestamp: number;\n}\n\n/**\n * Hook for monitoring component performance with budget validation\n * @param componentName - Name of the component being monitored\n * @param enabled - Whether performance monitoring is enabled\n * @param budgetName - Performance budget to validate against\n */\nexport function usePerformanceMonitor(\n componentName: string, \n enabled = import.meta.env.MODE === 'development',\n budgetName: string = 'COMPONENT_RENDER'\n) {\n const renderStartTime = useRef<number>(0);\n const metrics = useRef<PerformanceMetrics[]>([]);\n\n // Start performance measurement\n const startMeasurement = useCallback(() => {\n if (!enabled) return;\n renderStartTime.current = performance.now();\n }, [enabled]);\n\n // End performance measurement with budget validation\n const endMeasurement = useCallback(() => {\n if (!enabled || renderStartTime.current === 0) return;\n \n const renderTime = performance.now() - renderStartTime.current;\n const metric: PerformanceMetrics = {\n renderTime,\n componentName,\n timestamp: Date.now()\n };\n \n metrics.current.push(metric);\n \n // Keep only last 10 measurements\n if (metrics.current.length > 10) {\n metrics.current = metrics.current.slice(-10);\n }\n \n // Validate against performance budget\n const measurement = performanceBudgetMonitor.measure(budgetName, renderTime, {\n componentName,\n renderCount: metrics.current.length\n });\n \n // Log slow renders in development\n if (!measurement.passed) {\n console.warn(\n `🐌 Performance budget exceeded in ${componentName}: ${renderTime.toFixed(2)}ms ` +\n `(budget: ${PERFORMANCE_BUDGETS[budgetName]?.threshold}ms)`\n );\n }\n \n renderStartTime.current = 0;\n }, [enabled, componentName, budgetName]);\n\n // Get performance metrics\n const getMetrics = useCallback(() => {\n return metrics.current.slice();\n }, []);\n\n // Get average render time\n const getAverageRenderTime = useCallback(() => {\n if (metrics.current.length === 0) return 0;\n \n const total = metrics.current.reduce((sum, metric) => sum + metric.renderTime, 0);\n return total / metrics.current.length;\n }, []);\n\n // Get performance budget status\n const getBudgetStatus = useCallback(() => {\n const budget = PERFORMANCE_BUDGETS[budgetName];\n if (!budget) return null;\n\n const averageTime = getAverageRenderTime();\n return {\n budget: budget.threshold,\n average: averageTime,\n passed: averageTime <= budget.threshold,\n efficiency: budget.threshold > 0 ? (budget.threshold - averageTime) / budget.threshold : 0\n };\n }, [budgetName, getAverageRenderTime]);\n\n // Start measurement on every render\n useEffect(() => {\n startMeasurement();\n return endMeasurement;\n });\n\n return {\n getMetrics,\n getAverageRenderTime,\n getBudgetStatus,\n startMeasurement,\n endMeasurement\n };\n}\n\n// Hook for measuring specific operations\nexport function useOperationPerformance(operationName: string, budgetName?: string) {\n const measureOperation = useCallback(async <T>(\n operation: () => Promise<T> | T,\n context?: Record<string, any>\n ): Promise<T> => {\n const start = performance.now();\n const result = await operation();\n const duration = performance.now() - start;\n \n const budget = budgetName || 'COMPONENT_RENDER';\n performanceBudgetMonitor.measure(budget, duration, {\n operation: operationName,\n ...context\n });\n \n return result;\n }, [operationName, budgetName]);\n\n return { measureOperation };\n}\n"],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;AACA,SAAS,QAAQ,aAAa,iBAAiB;AAuBxC,SAAS,mBAAmB,UAAkC,CAAC,GAA0B;AAC9F,QAAM;AAAA,IACJ,YAAY;AAAA,IACZ,YAAY;AAAA,IACZ,eAAe;AAAA,IACf;AAAA,IACA;AAAA,IACA;AAAA,EACF,IAAI;AAEJ,QAAM,eAAe,OAAuB,IAAI;AAChD,QAAM,WAAW,OAA2B,IAAI;AAChD,QAAM,mBAAmB,OAA2B,IAAI;AACxD,QAAM,qBAAqB,OAAgB,KAAK;AAEhD,QAAM,WAAW,YAAY,CAAC,YAAgC;AAC5D,aAAS,UAAU;AACnB,aAAS,MAAM;AAAA,EACjB,GAAG,CAAC,CAAC;AAEL,QAAM,uBAAuB,YAAY,MAAqB;AAC5D,QAAI,CAAC,aAAa,QAAS,QAAO,CAAC;AAEnC,WAAO,MAAM;AAAA,MACX,aAAa,QAAQ;AAAA,QACnB;AAAA,MACF;AAAA,IACF,EAAE,OAAO,CAAC,OAAO,CAAC,GAAG,aAAa,UAAU,KAAK,CAAC,GAAG,aAAa,QAAQ,CAAC;AAAA,EAC7E,GAAG,CAAC,CAAC;AAEL,QAAM,aAAa,YAAY,MAAM;AACnC,UAAM,WAAW,qBAAqB;AACtC,QAAI,SAAS,SAAS,GAAG;AACvB,eAAS,SAAS,CAAC,CAAC;AACpB,qBAAe;AAAA,IACjB;AAAA,EACF,GAAG,CAAC,sBAAsB,UAAU,YAAY,CAAC;AAEjD,QAAM,YAAY,YAAY,MAAM;AAClC,UAAM,WAAW,qBAAqB;AACtC,QAAI,SAAS,SAAS,GAAG;AACvB,eAAS,SAAS,SAAS,SAAS,CAAC,CAAC;AACtC,oBAAc;AAAA,IAChB;AAAA,EACF,GAAG,CAAC,sBAAsB,UAAU,WAAW,CAAC;AAEhD,QAAM,kBAAkB,YAAY,MAAM;AACxC,uBAAmB,UAAU;AAAA,EAC/B,GAAG,CAAC,CAAC;AAEL,QAAM,eAAe,YAAY,MAAM;AACrC,uBAAmB,UAAU;AAAA,EAC/B,GAAG,CAAC,CAAC;AAEL,QAAM,eAAe,YAAY,CAAC,aAAyB;AACzD,WAAO,MAAM;AACX,YAAM,gBAAgB,CAAC,UAAyB;AAC9C,YAAI,MAAM,QAAQ,UAAU;AAC1B,mBAAS;AAAA,QACX;AAAA,MACF;AAEA,eAAS,iBAAiB,WAAW,aAAa;AAClD,aAAO,MAAM,SAAS,oBAAoB,WAAW,aAAa;AAAA,IACpE;AAAA,EACF,GAAG,CAAC,CAAC;AAGL,YAAU,MAAM;AACd,QAAI,CAAC,aAAa,CAAC,aAAa,QAAS;AAEzC,UAAM,gBAAgB,CAAC,UAAyB;AAC9C,UAAI,MAAM,QAAQ,YAAY,UAAU;AACtC,iBAAS;AACT;AAAA,MACF;AAEA,UAAI,MAAM,QAAQ,MAAO;AAEzB,YAAM,WAAW,qBAAqB;AACtC,UAAI,SAAS,WAAW,EAAG;AAE3B,YAAM,eAAe,SAAS,CAAC;AAC/B,YAAM,cAAc,SAAS,SAAS,SAAS,CAAC;AAEhD,UAAI,MAAM,UAAU;AAClB,YAAI,SAAS,kBAAkB,cAAc;AAC3C,gBAAM,eAAe;AACrB,sBAAY,MAAM;AAAA,QACpB;AAAA,MACF,OAAO;AACL,YAAI,SAAS,kBAAkB,aAAa;AAC1C,gBAAM,eAAe;AACrB,uBAAa,MAAM;AAAA,QACrB;AAAA,MACF;AAAA,IACF;AAEA,UAAM,UAAU,aAAa;AAC7B,YAAQ,iBAAiB,WAAW,aAAa;AACjD,WAAO,MAAM;AACX,eAAS,oBAAoB,WAAW,aAAa;AAAA,IACvD;AAAA,EACF,GAAG,CAAC,WAAW,UAAU,oBAAoB,CAAC;AAG9C,YAAU,MAAM;AACd,QAAI,WAAW;AACb,iBAAW;AAAA,IACb;AAAA,EACF,GAAG,CAAC,WAAW,UAAU,CAAC;AAG1B,YAAU,MAAM;AACd,QAAI,CAAC,aAAc;AAEnB,qBAAiB,UAAU,SAAS;AAEpC,WAAO,MAAM;AACX,UAAI,iBAAiB,SAAS;AAC5B,yBAAiB,QAAQ,MAAM;AAAA,MACjC;AAAA,IACF;AAAA,EACF,GAAG,CAAC,YAAY,CAAC;AAEjB,SAAO;AAAA,IACL;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA,WAAW;AAAA,IACX;AAAA,IACA;AAAA,IACA;AAAA,EACF;AACF;;;AC/JA,SAAS,UAAAA,SAAQ,aAAAC,YAAW,eAAAC,oBAAmB;AA0B/C,IAAM,6BAA6B;AAAA,EACjC;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AACF,EAAE,KAAK,IAAI;AAMJ,SAAS,aAAa,UAA4B,CAAC,GAAoB;AAC5E,QAAM;AAAA,IACJ,WAAW;AAAA,IACX,YAAY;AAAA,IACZ,eAAe;AAAA,IACf;AAAA,IACA,oBAAoB;AAAA,EACtB,IAAI;AAEJ,QAAM,eAAeF,QAAoB,IAAI;AAC7C,QAAM,2BAA2BA,QAA2B,IAAI;AAEhE,QAAM,uBAAuBE,aAAY,MAAqB;AAC5D,QAAI,CAAC,aAAa,QAAS,QAAO,CAAC;AAEnC,WAAO,MAAM;AAAA,MACX,aAAa,QAAQ,iBAA8B,iBAAiB;AAAA,IACtE,EAAE,OAAO,CAAC,YAAY;AACpB,aACE,CAAC,QAAQ,aAAa,UAAU,KAChC,CAAC,QAAQ,aAAa,QAAQ,KAC9B,QAAQ,iBAAiB;AAAA,IAE7B,CAAC;AAAA,EACH,GAAG,CAAC,iBAAiB,CAAC;AAEtB,QAAM,aAAaA,aAAY,MAAM;AACnC,UAAM,WAAW,qBAAqB;AACtC,QAAI,SAAS,SAAS,GAAG;AACvB,eAAS,CAAC,EAAE,MAAM;AAAA,IACpB;AAAA,EACF,GAAG,CAAC,oBAAoB,CAAC;AAEzB,QAAM,YAAYA,aAAY,MAAM;AAClC,UAAM,WAAW,qBAAqB;AACtC,QAAI,SAAS,SAAS,GAAG;AACvB,eAAS,SAAS,SAAS,CAAC,EAAE,MAAM;AAAA,IACtC;AAAA,EACF,GAAG,CAAC,oBAAoB,CAAC;AAGzB,EAAAD,WAAU,MAAM;AACd,QAAI,CAAC,YAAY,CAAC,aAAa,QAAS;AAExC,UAAM,gBAAgB,CAAC,UAAyB;AAE9C,UAAI,MAAM,QAAQ,YAAY,UAAU;AACtC,iBAAS;AACT;AAAA,MACF;AAGA,UAAI,MAAM,QAAQ,OAAO;AACvB,cAAM,oBAAoB,qBAAqB;AAC/C,YAAI,kBAAkB,WAAW,EAAG;AAEpC,cAAM,eAAe,kBAAkB,CAAC;AACxC,cAAM,cAAc,kBAAkB,kBAAkB,SAAS,CAAC;AAElE,YAAI,MAAM,UAAU;AAElB,cAAI,SAAS,kBAAkB,cAAc;AAC3C,kBAAM,eAAe;AACrB,wBAAY,MAAM;AAAA,UACpB;AAAA,QACF,OAAO;AAEL,cAAI,SAAS,kBAAkB,aAAa;AAC1C,kBAAM,eAAe;AACrB,yBAAa,MAAM;AAAA,UACrB;AAAA,QACF;AAAA,MACF;AAAA,IACF;AAEA,UAAM,YAAY,aAAa;AAC/B,cAAU,iBAAiB,WAAW,aAAa;AAEnD,WAAO,MAAM;AACX,gBAAU,oBAAoB,WAAW,aAAa;AAAA,IACxD;AAAA,EACF,GAAG,CAAC,UAAU,UAAU,oBAAoB,CAAC;AAG7C,EAAAA,WAAU,MAAM;AACd,QAAI,CAAC,SAAU;AAGf,QAAI,cAAc;AAChB,+BAAyB,UAAU,SAAS;AAAA,IAC9C;AAGA,QAAI,WAAW;AACb,YAAM,QAAQ,WAAW,YAAY,CAAC;AACtC,aAAO,MAAM,aAAa,KAAK;AAAA,IACjC;AAEA,WAAO,MAAM;AAEX,UAAI,gBAAgB,yBAAyB,SAAS;AACpD,iCAAyB,QAAQ,MAAM;AACvC,iCAAyB,UAAU;AAAA,MACrC;AAAA,IACF;AAAA,EACF,GAAG,CAAC,UAAU,WAAW,cAAc,UAAU,CAAC;AAElD,SAAO;AAAA,IACL;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,EACF;AACF;;;AC1JA,SAAS,aAAAE,YAAW,eAAAC,oBAAmB;AA2BvC,SAAS,cAAc,OAAe;AACpC,QAAM,QAAQ,MAAM,YAAY,EAAE,MAAM,GAAG;AAC3C,QAAM,MAAM,MAAM,IAAI;AACtB,QAAM,YAAY;AAAA,IAChB,MAAM,MAAM,SAAS,MAAM,KAAK,MAAM,SAAS,SAAS;AAAA,IACxD,KAAK,MAAM,SAAS,KAAK;AAAA,IACzB,OAAO,MAAM,SAAS,OAAO;AAAA,IAC7B,MAAM,MAAM,SAAS,MAAM,KAAK,MAAM,SAAS,KAAK;AAAA,EACtD;AACA,SAAO,EAAE,KAAK,UAAU;AAC1B;AAKA,SAAS,gBAAgB,OAAsB,OAAwB;AACrE,QAAM,EAAE,KAAK,UAAU,IAAI,cAAc,KAAK;AAG9C,QAAM,WAAW,MAAM,IAAI,YAAY;AACvC,QAAM,YAAY,IAAI,YAAY;AAElC,MAAI,aAAa,WAAW;AAC1B,WAAO;AAAA,EACT;AAGA,SACE,MAAM,YAAY,UAAU,QAC5B,MAAM,WAAW,UAAU,OAC3B,MAAM,aAAa,UAAU,SAC7B,MAAM,YAAY,UAAU;AAEhC;AA4BO,SAAS,qBACd,WACA,UAAoC,CAAC,GAC/B;AACN,QAAM,EAAE,UAAU,UAAU,UAAU,KAAK,IAAI;AAE/C,QAAM,gBAAgBA,aAAY,CAAC,UAAyB;AAC1D,QAAI,CAAC,QAAS;AAEd,eAAW,YAAY,WAAW;AAChC,UAAI,SAAS,YAAY,MAAO;AAEhC,UAAI,gBAAgB,OAAO,SAAS,GAAG,GAAG;AACxC,YAAI,SAAS,gBAAgB;AAC3B,gBAAM,eAAe;AAAA,QACvB;AACA,YAAI,SAAS,iBAAiB;AAC5B,gBAAM,gBAAgB;AAAA,QACxB;AAEA,iBAAS,QAAQ,KAAK;AACtB;AAAA,MACF;AAAA,IACF;AAAA,EACF,GAAG,CAAC,WAAW,OAAO,CAAC;AAEvB,EAAAD,WAAU,MAAM;AACd,QAAI,CAAC,QAAS;AAEd,YAAQ,iBAAiB,WAAW,aAA8B;AAClE,WAAO,MAAM,QAAQ,oBAAoB,WAAW,aAA8B;AAAA,EACpF,GAAG,CAAC,SAAS,SAAS,aAAa,CAAC;AACtC;;;ACnHA,SAAS,UAAU,aAAAE,kBAAiB;AAEpC,IAAM,oBAAoB;AAOnB,SAAS,cAAuB;AACrC,QAAM,CAAC,UAAU,WAAW,IAAI,SAA8B,MAAS;AAEvE,EAAAA,WAAU,MAAM;AAEd,QAAI,OAAO,WAAW,aAAa;AACjC,kBAAY,KAAK;AACjB;AAAA,IACF;AAEA,UAAM,MAAM,OAAO,WAAW,eAAe,oBAAoB,CAAC,KAAK;AAEvE,UAAM,WAAW,MAAM;AACrB,kBAAY,OAAO,aAAa,iBAAiB;AAAA,IACnD;AAGA,gBAAY,OAAO,aAAa,iBAAiB;AAGjD,QAAI,iBAAiB,UAAU,QAAQ;AAGvC,WAAO,MAAM,IAAI,oBAAoB,UAAU,QAAQ;AAAA,EACzD,GAAG,CAAC,CAAC;AAEL,SAAO,CAAC,CAAC;AACX;;;ACxCA,SAAS,YAAAC,WAAU,aAAAC,kBAAiB;AAE7B,SAAS,YAAe,OAAU,OAAkB;AACzD,QAAM,CAAC,gBAAgB,iBAAiB,IAAID,UAAY,KAAK;AAE7D,EAAAC,WAAU,MAAM;AACd,UAAM,UAAU,WAAW,MAAM;AAC/B,wBAAkB,KAAK;AAAA,IACzB,GAAG,KAAK;AAER,WAAO,MAAM;AACX,mBAAa,OAAO;AAAA,IACtB;AAAA,EACF,GAAG,CAAC,OAAO,KAAK,CAAC;AAEjB,SAAO;AACT;;;ACZA,SAAS,YAAAC,WAAU,eAAAC,cAAa,eAAe;AAuCxC,SAAS,kBAAkB,SAAmC;AACnE,QAAM,EAAE,kBAAkB,IAAI,KAAK,IAAI;AAGvC,QAAM,CAAC,SAAS,UAAU,IAAID,UAAuB,CAAC,CAAC;AACvD,QAAM,CAAC,eAAe,gBAAgB,IAAIA,UAA6B,CAAC,CAAC;AACzE,QAAM,CAAC,UAAU,WAAW,IAAIA,UAAwB,CAAC,CAAC;AAC1D,QAAM,CAAC,UAAU,WAAW,IAAIA,UAAS,eAAe;AACxD,QAAM,CAAC,WAAW,YAAY,IAAIA,UAAS,CAAC;AAC5C,QAAM,CAAC,cAAc,eAAe,IAAIA,UAAmB,CAAC,CAAC;AAG7D,QAAM,aAAaC,aAAY,MAAM;AACnC,eAAW,CAAC,CAAC;AACb,qBAAiB,CAAC,CAAC;AACnB,gBAAY,CAAC,CAAC;AACd,gBAAY,eAAe;AAC3B,iBAAa,CAAC;AACd,oBAAgB,CAAC,CAAC;AAAA,EACpB,GAAG,CAAC,eAAe,CAAC;AAGpB,QAAM,gBAAgB,QAAQ,MAAM;AAClC,UAAM,QAAQ,YAAY;AAC1B,UAAM,MAAM,QAAQ;AACpB,WAAO,KAAK,MAAM,OAAO,GAAG;AAAA,EAC9B,GAAG,CAAC,MAAM,WAAW,QAAQ,CAAC;AAE9B,QAAM,aAAa,QAAQ,MAAM;AAC/B,WAAO,KAAK,KAAK,KAAK,SAAS,QAAQ;AAAA,EACzC,GAAG,CAAC,KAAK,QAAQ,QAAQ,CAAC;AAE1B,QAAM,cAAc,QAAQ,MAAM;AAChC,WAAO,YAAY,aAAa;AAAA,EAClC,GAAG,CAAC,WAAW,UAAU,CAAC;AAE1B,QAAM,kBAAkB,QAAQ,MAAM;AACpC,WAAO,YAAY;AAAA,EACrB,GAAG,CAAC,SAAS,CAAC;AAEd,SAAO;AAAA,IACL,OAAO;AAAA,MACL;AAAA,MACA;AAAA,MACA;AAAA,MACA;AAAA,MACA;AAAA,MACA;AAAA,IACF;AAAA,IACA,SAAS;AAAA,MACP;AAAA,MACA;AAAA,MACA;AAAA,MACA;AAAA,MACA;AAAA,MACA;AAAA,MACA;AAAA,IACF;AAAA,IACA,UAAU;AAAA,MACR;AAAA,MACA;AAAA,MACA;AAAA,MACA;AAAA,IACF;AAAA,EACF;AACF;;;ACtGA,SAAS,eAAe;AACxB,SAAS,mBAAmB;AASrB,SAAS,WAAmC;AAAA,EACjD;AAAA,EACA;AAAA,EACA,OAAO;AACT,GAAuB;AACrB,SAAO,QAAoB;AAAA,IACzB,UAAU,YAAY,MAAM;AAAA,IAC5B;AAAA,IACA;AAAA,EACF,CAAC;AACH;;;AC1BA,SAAS,aAAAC,YAAW,UAAAC,SAAQ,eAAAC,oBAAmB;AAexC,SAAS,sBACd,eACA,UAAU,YAAY,IAAI,SAAS,eACnC,aAAqB,oBACrB;AACA,QAAM,kBAAkBC,QAAe,CAAC;AACxC,QAAM,UAAUA,QAA6B,CAAC,CAAC;AAG/C,QAAM,mBAAmBC,aAAY,MAAM;AACzC,QAAI,CAAC,QAAS;AACd,oBAAgB,UAAU,YAAY,IAAI;AAAA,EAC5C,GAAG,CAAC,OAAO,CAAC;AAGZ,QAAM,iBAAiBA,aAAY,MAAM;AACvC,QAAI,CAAC,WAAW,gBAAgB,YAAY,EAAG;AAE/C,UAAM,aAAa,YAAY,IAAI,IAAI,gBAAgB;AACvD,UAAM,SAA6B;AAAA,MACjC;AAAA,MACA;AAAA,MACA,WAAW,KAAK,IAAI;AAAA,IACtB;AAEA,YAAQ,QAAQ,KAAK,MAAM;AAG3B,QAAI,QAAQ,QAAQ,SAAS,IAAI;AAC/B,cAAQ,UAAU,QAAQ,QAAQ,MAAM,GAAG;AAAA,IAC7C;AAGA,UAAM,cAAc,yBAAyB,QAAQ,YAAY,YAAY;AAAA,MAC3E;AAAA,MACA,aAAa,QAAQ,QAAQ;AAAA,IAC/B,CAAC;AAGD,QAAI,CAAC,YAAY,QAAQ;AACvB,cAAQ;AAAA,QACN,4CAAqC,aAAa,KAAK,WAAW,QAAQ,CAAC,CAAC,eAChE,oBAAoB,UAAU,GAAG,SAAS;AAAA,MACxD;AAAA,IACF;AAEA,oBAAgB,UAAU;AAAA,EAC5B,GAAG,CAAC,SAAS,eAAe,UAAU,CAAC;AAGvC,QAAM,aAAaA,aAAY,MAAM;AACnC,WAAO,QAAQ,QAAQ,MAAM;AAAA,EAC/B,GAAG,CAAC,CAAC;AAGL,QAAM,uBAAuBA,aAAY,MAAM;AAC7C,QAAI,QAAQ,QAAQ,WAAW,EAAG,QAAO;AAEzC,UAAM,QAAQ,QAAQ,QAAQ,OAAO,CAAC,KAAK,WAAW,MAAM,OAAO,YAAY,CAAC;AAChF,WAAO,QAAQ,QAAQ,QAAQ;AAAA,EACjC,GAAG,CAAC,CAAC;AAGL,QAAM,kBAAkBA,aAAY,MAAM;AACxC,UAAM,SAAS,oBAAoB,UAAU;AAC7C,QAAI,CAAC,OAAQ,QAAO;AAEpB,UAAM,cAAc,qBAAqB;AACzC,WAAO;AAAA,MACL,QAAQ,OAAO;AAAA,MACf,SAAS;AAAA,MACT,QAAQ,eAAe,OAAO;AAAA,MAC9B,YAAY,OAAO,YAAY,KAAK,OAAO,YAAY,eAAe,OAAO,YAAY;AAAA,IAC3F;AAAA,EACF,GAAG,CAAC,YAAY,oBAAoB,CAAC;AAGrC,EAAAC,WAAU,MAAM;AACd,qBAAiB;AACjB,WAAO;AAAA,EACT,CAAC;AAED,SAAO;AAAA,IACL;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,IACA;AAAA,EACF;AACF;","names":["useRef","useEffect","useCallback","useEffect","useCallback","useEffect","useState","useEffect","useState","useCallback","useEffect","useRef","useCallback","useRef","useCallback","useEffect"]}
1
+ {"version":3,"sources":["../src/hooks/useFocusManagement.ts","../src/hooks/useFocusTrap.ts","../src/hooks/useKeyboardShortcuts.ts","../src/hooks/useIsMobile.ts","../src/hooks/useDebounce.ts","../src/hooks/useDataTableState.ts","../src/hooks/useZodForm.ts","../src/hooks/usePerformanceMonitor.ts"],"sourcesContent":["\nimport { useRef, useCallback, useEffect } from 'react';\n\nexport interface FocusManagementOptions {\n trapFocus?: boolean;\n autoFocus?: boolean;\n restoreFocus?: boolean;\n onEscape?: () => void;\n onFocusFirst?: () => void;\n onFocusLast?: () => void;\n}\n\nexport interface FocusManagementReturn {\n containerRef: React.RefObject<HTMLDivElement>;\n focusRef: React.RefObject<HTMLElement>;\n setFocus: (element: HTMLElement | null) => void;\n focusFirst: () => void;\n focusLast: () => void;\n trapFocus: () => void;\n releaseFocus: () => void;\n getFocusableElements: () => HTMLElement[];\n handleEscape: (callback: () => void) => () => void;\n}\n\nexport function useFocusManagement(options: FocusManagementOptions = {}): FocusManagementReturn {\n const { \n trapFocus = false, \n autoFocus = false, \n restoreFocus = false,\n onEscape,\n onFocusFirst,\n onFocusLast \n } = options;\n\n const containerRef = useRef<HTMLDivElement>(null);\n const focusRef = useRef<HTMLElement | null>(null);\n const previousFocusRef = useRef<HTMLElement | null>(null);\n const trapFocusActiveRef = useRef<boolean>(false);\n\n const setFocus = useCallback((element: HTMLElement | null) => {\n focusRef.current = element;\n element?.focus();\n }, []);\n\n const getFocusableElements = useCallback((): HTMLElement[] => {\n if (!containerRef.current) return [];\n\n return Array.from(\n containerRef.current.querySelectorAll<HTMLElement>(\n 'button, [href], input, select, textarea, [tabindex]:not([tabindex=\"-1\"])'\n )\n ).filter((el) => !el.hasAttribute('disabled') && !el.hasAttribute('hidden'));\n }, []);\n\n const focusFirst = useCallback(() => {\n const elements = getFocusableElements();\n if (elements.length > 0) {\n setFocus(elements[0]);\n onFocusFirst?.();\n }\n }, [getFocusableElements, setFocus, onFocusFirst]);\n\n const focusLast = useCallback(() => {\n const elements = getFocusableElements();\n if (elements.length > 0) {\n setFocus(elements[elements.length - 1]);\n onFocusLast?.();\n }\n }, [getFocusableElements, setFocus, onFocusLast]);\n\n const trapFocusMethod = useCallback(() => {\n trapFocusActiveRef.current = true;\n }, []);\n\n const releaseFocus = useCallback(() => {\n trapFocusActiveRef.current = false;\n }, []);\n\n const handleEscape = useCallback((callback: () => void) => {\n return () => {\n const handleKeyDown = (event: KeyboardEvent) => {\n if (event.key === 'Escape') {\n callback();\n }\n };\n\n document.addEventListener('keydown', handleKeyDown);\n return () => document.removeEventListener('keydown', handleKeyDown);\n };\n }, []);\n\n // Handle focus trap\n useEffect(() => {\n if (!trapFocus || !containerRef.current) return;\n\n const handleKeyDown = (event: KeyboardEvent) => {\n if (event.key === 'Escape' && onEscape) {\n onEscape();\n return;\n }\n\n if (event.key !== 'Tab') return;\n\n const elements = getFocusableElements();\n if (elements.length === 0) return;\n\n const firstElement = elements[0];\n const lastElement = elements[elements.length - 1];\n\n if (event.shiftKey) {\n if (document.activeElement === firstElement) {\n event.preventDefault();\n lastElement.focus();\n }\n } else {\n if (document.activeElement === lastElement) {\n event.preventDefault();\n firstElement.focus();\n }\n }\n };\n\n const current = containerRef.current;\n current.addEventListener('keydown', handleKeyDown);\n return () => {\n current?.removeEventListener('keydown', handleKeyDown);\n };\n }, [trapFocus, onEscape, getFocusableElements]);\n\n // Handle auto focus\n useEffect(() => {\n if (autoFocus) {\n focusFirst();\n }\n }, [autoFocus, focusFirst]);\n\n // Handle focus restoration\n useEffect(() => {\n if (!restoreFocus) return;\n\n previousFocusRef.current = document.activeElement as HTMLElement;\n\n return () => {\n if (previousFocusRef.current) {\n previousFocusRef.current.focus();\n }\n };\n }, [restoreFocus]);\n\n return {\n containerRef,\n focusRef,\n setFocus,\n focusFirst,\n focusLast,\n trapFocus: trapFocusMethod,\n releaseFocus,\n getFocusableElements,\n handleEscape,\n };\n}\n","\nimport { useRef, useEffect, useCallback } from 'react';\n\nexport interface FocusTrapOptions {\n /** Whether the focus trap is active */\n isActive?: boolean;\n /** Whether to auto-focus the first element when activated */\n autoFocus?: boolean;\n /** Whether to restore focus to the previously focused element when deactivated */\n restoreFocus?: boolean;\n /** Callback when Escape key is pressed */\n onEscape?: () => void;\n /** Selector for focusable elements (optional override) */\n focusableSelector?: string;\n}\n\nexport interface FocusTrapReturn {\n /** Ref to attach to the container element */\n containerRef: React.RefObject<HTMLElement>;\n /** Focus the first focusable element */\n focusFirst: () => void;\n /** Focus the last focusable element */\n focusLast: () => void;\n /** Get all focusable elements in the container */\n getFocusableElements: () => HTMLElement[];\n}\n\nconst DEFAULT_FOCUSABLE_SELECTOR = [\n 'button:not([disabled])',\n '[href]',\n 'input:not([disabled])',\n 'select:not([disabled])',\n 'textarea:not([disabled])',\n '[tabindex]:not([tabindex=\"-1\"])',\n '[contenteditable=\"true\"]'\n].join(', ');\n\n/**\n * Hook for creating accessible focus traps\n * Useful for modals, dropdowns, and other overlay components\n */\nexport function useFocusTrap(options: FocusTrapOptions = {}): FocusTrapReturn {\n const {\n isActive = false,\n autoFocus = false,\n restoreFocus = false,\n onEscape,\n focusableSelector = DEFAULT_FOCUSABLE_SELECTOR\n } = options;\n\n const containerRef = useRef<HTMLElement>(null);\n const previouslyFocusedElement = useRef<HTMLElement | null>(null);\n\n const getFocusableElements = useCallback((): HTMLElement[] => {\n if (!containerRef.current) return [];\n\n return Array.from(\n containerRef.current.querySelectorAll<HTMLElement>(focusableSelector)\n ).filter((element) => {\n return (\n !element.hasAttribute('disabled') &&\n !element.hasAttribute('hidden') &&\n element.offsetParent !== null // visible check\n );\n });\n }, [focusableSelector]);\n\n const focusFirst = useCallback(() => {\n const elements = getFocusableElements();\n if (elements.length > 0) {\n elements[0].focus();\n }\n }, [getFocusableElements]);\n\n const focusLast = useCallback(() => {\n const elements = getFocusableElements();\n if (elements.length > 0) {\n elements[elements.length - 1].focus();\n }\n }, [getFocusableElements]);\n\n // Handle keyboard events\n useEffect(() => {\n if (!isActive || !containerRef.current) return;\n\n const handleKeyDown = (event: KeyboardEvent) => {\n // Handle Escape key\n if (event.key === 'Escape' && onEscape) {\n onEscape();\n return;\n }\n\n // Handle Tab key for focus trapping\n if (event.key === 'Tab') {\n const focusableElements = getFocusableElements();\n if (focusableElements.length === 0) return;\n\n const firstElement = focusableElements[0];\n const lastElement = focusableElements[focusableElements.length - 1];\n\n if (event.shiftKey) {\n // Shift + Tab: moving backwards\n if (document.activeElement === firstElement) {\n event.preventDefault();\n lastElement.focus();\n }\n } else {\n // Tab: moving forwards\n if (document.activeElement === lastElement) {\n event.preventDefault();\n firstElement.focus();\n }\n }\n }\n };\n\n const container = containerRef.current;\n container.addEventListener('keydown', handleKeyDown);\n\n return () => {\n container.removeEventListener('keydown', handleKeyDown);\n };\n }, [isActive, onEscape, getFocusableElements]);\n\n // Handle focus restoration\n useEffect(() => {\n if (!isActive) return;\n\n // Store the previously focused element\n if (restoreFocus) {\n previouslyFocusedElement.current = document.activeElement as HTMLElement;\n }\n\n // Auto-focus first element if requested\n if (autoFocus) {\n const timer = setTimeout(focusFirst, 0);\n return () => clearTimeout(timer);\n }\n\n return () => {\n // Restore focus when trap is deactivated\n if (restoreFocus && previouslyFocusedElement.current) {\n previouslyFocusedElement.current.focus();\n previouslyFocusedElement.current = null;\n }\n };\n }, [isActive, autoFocus, restoreFocus, focusFirst]);\n\n return {\n containerRef,\n focusFirst,\n focusLast,\n getFocusableElements\n };\n}\n","import { useEffect, useCallback } from 'react';\n\nexport interface KeyboardShortcut {\n /** Key combination (e.g., 'Escape', 'Enter', 'ArrowDown', 'ctrl+s') */\n key: string;\n /** Callback function to execute */\n handler: (event: KeyboardEvent) => void;\n /** Description for documentation/help */\n description?: string;\n /** Whether the shortcut is enabled */\n enabled?: boolean;\n /** Prevent default browser behavior */\n preventDefault?: boolean;\n /** Stop event propagation */\n stopPropagation?: boolean;\n}\n\nexport interface KeyboardShortcutsOptions {\n /** Element to attach listeners to (defaults to document) */\n element?: HTMLElement | Document;\n /** Whether shortcuts are globally enabled */\n enabled?: boolean;\n}\n\n/**\n * Parse key combination string into modifier and key parts\n */\nfunction parseKeyCombo(combo: string) {\n const parts = combo.toLowerCase().split('+');\n const key = parts.pop()!;\n const modifiers = {\n ctrl: parts.includes('ctrl') || parts.includes('control'),\n alt: parts.includes('alt'),\n shift: parts.includes('shift'),\n meta: parts.includes('meta') || parts.includes('cmd')\n };\n return { key, modifiers };\n}\n\n/**\n * Check if event matches the key combination\n */\nfunction matchesKeyCombo(event: KeyboardEvent, combo: string): boolean {\n const { key, modifiers } = parseKeyCombo(combo);\n \n // Check if the main key matches\n const eventKey = event.key.toLowerCase();\n const targetKey = key.toLowerCase();\n \n if (eventKey !== targetKey) {\n return false;\n }\n \n // Check modifiers\n return (\n event.ctrlKey === modifiers.ctrl &&\n event.altKey === modifiers.alt &&\n event.shiftKey === modifiers.shift &&\n event.metaKey === modifiers.meta\n );\n}\n\n/**\n * Hook for managing keyboard shortcuts\n * \n * @example\n * ```tsx\n * function MyComponent() {\n * const shortcuts = [\n * {\n * key: 'Escape',\n * handler: () => setIsOpen(false),\n * description: 'Close modal'\n * },\n * {\n * key: 'ctrl+s',\n * handler: (e) => handleSave(),\n * description: 'Save document',\n * preventDefault: true\n * }\n * ];\n * \n * useKeyboardShortcuts(shortcuts);\n * \n * return <div>Content</div>;\n * }\n * ```\n */\nexport function useKeyboardShortcuts(\n shortcuts: KeyboardShortcut[],\n options: KeyboardShortcutsOptions = {}\n): void {\n const { element = document, enabled = true } = options;\n\n const handleKeyDown = useCallback((event: KeyboardEvent) => {\n if (!enabled) return;\n\n for (const shortcut of shortcuts) {\n if (shortcut.enabled === false) continue;\n\n if (matchesKeyCombo(event, shortcut.key)) {\n if (shortcut.preventDefault) {\n event.preventDefault();\n }\n if (shortcut.stopPropagation) {\n event.stopPropagation();\n }\n \n shortcut.handler(event);\n break; // Only handle first matching shortcut\n }\n }\n }, [shortcuts, enabled]);\n\n useEffect(() => {\n if (!enabled) return;\n\n element.addEventListener('keydown', handleKeyDown as EventListener);\n return () => element.removeEventListener('keydown', handleKeyDown as EventListener);\n }, [element, enabled, handleKeyDown]);\n}\n\n/**\n * Hook for common accessibility keyboard shortcuts\n */\nexport function useAccessibilityShortcuts(handlers: {\n onEscape?: () => void;\n onEnter?: () => void;\n onSpace?: () => void;\n onArrowUp?: () => void;\n onArrowDown?: () => void;\n onArrowLeft?: () => void;\n onArrowRight?: () => void;\n onHome?: () => void;\n onEnd?: () => void;\n onTab?: () => void;\n onShiftTab?: () => void;\n}) {\n const shortcuts: KeyboardShortcut[] = [];\n\n if (handlers.onEscape) {\n shortcuts.push({\n key: 'Escape',\n handler: handlers.onEscape,\n description: 'Escape/Cancel'\n });\n }\n\n if (handlers.onEnter) {\n shortcuts.push({\n key: 'Enter',\n handler: handlers.onEnter,\n description: 'Activate/Submit'\n });\n }\n\n if (handlers.onSpace) {\n shortcuts.push({\n key: ' ',\n handler: handlers.onSpace,\n description: 'Activate',\n preventDefault: true\n });\n }\n\n if (handlers.onArrowUp) {\n shortcuts.push({\n key: 'ArrowUp',\n handler: handlers.onArrowUp,\n description: 'Navigate up',\n preventDefault: true\n });\n }\n\n if (handlers.onArrowDown) {\n shortcuts.push({\n key: 'ArrowDown',\n handler: handlers.onArrowDown,\n description: 'Navigate down',\n preventDefault: true\n });\n }\n\n if (handlers.onArrowLeft) {\n shortcuts.push({\n key: 'ArrowLeft',\n handler: handlers.onArrowLeft,\n description: 'Navigate left',\n preventDefault: true\n });\n }\n\n if (handlers.onArrowRight) {\n shortcuts.push({\n key: 'ArrowRight',\n handler: handlers.onArrowRight,\n description: 'Navigate right',\n preventDefault: true\n });\n }\n\n if (handlers.onHome) {\n shortcuts.push({\n key: 'Home',\n handler: handlers.onHome,\n description: 'Go to first item',\n preventDefault: true\n });\n }\n\n if (handlers.onEnd) {\n shortcuts.push({\n key: 'End',\n handler: handlers.onEnd,\n description: 'Go to last item',\n preventDefault: true\n });\n }\n\n if (handlers.onTab) {\n shortcuts.push({\n key: 'Tab',\n handler: handlers.onTab,\n description: 'Navigate forward'\n });\n }\n\n if (handlers.onShiftTab) {\n shortcuts.push({\n key: 'shift+Tab',\n handler: handlers.onShiftTab,\n description: 'Navigate backward'\n });\n }\n\n useKeyboardShortcuts(shortcuts);\n}\n","/**\n * @file useIsMobile Hook\n * @description Hook for detecting mobile viewport using modern matchMedia API\n */\n\nimport { useState, useEffect } from 'react';\n\nconst MOBILE_BREAKPOINT = 768;\n\n/**\n * Hook to detect if the viewport is mobile-sized using matchMedia API.\n * More performant than window resize events.\n * @returns {boolean} True if mobile, false otherwise.\n */\nexport function useIsMobile(): boolean {\n const [isMobile, setIsMobile] = useState<boolean | undefined>(undefined);\n\n useEffect(() => {\n // Handle SSR case\n if (typeof window === 'undefined') {\n setIsMobile(false);\n return;\n }\n\n const mql = window.matchMedia(`(max-width: ${MOBILE_BREAKPOINT - 1}px)`);\n \n const onChange = () => {\n setIsMobile(window.innerWidth < MOBILE_BREAKPOINT);\n };\n\n // Set initial value\n setIsMobile(window.innerWidth < MOBILE_BREAKPOINT);\n\n // Add event listener\n mql.addEventListener('change', onChange);\n\n // Cleanup\n return () => mql.removeEventListener('change', onChange);\n }, []);\n\n return !!isMobile;\n}\n","\nimport { useState, useEffect } from 'react';\n\nexport function useDebounce<T>(value: T, delay: number): T {\n const [debouncedValue, setDebouncedValue] = useState<T>(value);\n\n useEffect(() => {\n const handler = setTimeout(() => {\n setDebouncedValue(value);\n }, delay);\n\n return () => {\n clearTimeout(handler);\n };\n }, [value, delay]);\n\n return debouncedValue;\n}\n","/**\n * @file useDataTableState Hook\n * @description Hook for managing DataTable state\n */\n\nimport { useState, useCallback, useMemo } from 'react';\nimport type { SortingState, ColumnFiltersState, ExpandedState } from '@tanstack/react-table';\n\nexport interface DataTableState {\n sorting: SortingState;\n columnFilters: ColumnFiltersState;\n expanded: ExpandedState;\n pageSize: number;\n pageIndex: number;\n selectedRows: string[];\n}\n\nexport interface DataTableActions {\n setSorting: (sorting: SortingState) => void;\n setColumnFilters: (filters: ColumnFiltersState) => void;\n setExpanded: (expanded: ExpandedState) => void;\n setPageSize: (size: number) => void;\n setPageIndex: (index: number) => void;\n setSelectedRows: (rows: string[]) => void;\n resetState: () => void;\n}\n\nexport interface DataTableComputed {\n paginatedData: any[];\n totalPages: number;\n hasNextPage: boolean;\n hasPreviousPage: boolean;\n}\n\nexport interface UseDataTableStateOptions {\n initialPageSize?: number;\n data: any[];\n}\n\n/**\n * Hook for managing DataTable state\n * @param options Configuration options\n * @returns Object containing state, actions, and computed values\n */\nexport function useDataTableState(options: UseDataTableStateOptions) {\n const { initialPageSize = 10, data } = options;\n\n // State\n const [sorting, setSorting] = useState<SortingState>([]);\n const [columnFilters, setColumnFilters] = useState<ColumnFiltersState>([]);\n const [expanded, setExpanded] = useState<ExpandedState>({});\n const [pageSize, setPageSize] = useState(initialPageSize);\n const [pageIndex, setPageIndex] = useState(0);\n const [selectedRows, setSelectedRows] = useState<string[]>([]);\n\n // Actions\n const resetState = useCallback(() => {\n setSorting([]);\n setColumnFilters([]);\n setExpanded({});\n setPageSize(initialPageSize);\n setPageIndex(0);\n setSelectedRows([]);\n }, [initialPageSize]);\n\n // Computed values\n const paginatedData = useMemo(() => {\n const start = pageIndex * pageSize;\n const end = start + pageSize;\n return data.slice(start, end);\n }, [data, pageIndex, pageSize]);\n\n const totalPages = useMemo(() => {\n return Math.ceil(data.length / pageSize);\n }, [data.length, pageSize]);\n\n const hasNextPage = useMemo(() => {\n return pageIndex < totalPages - 1;\n }, [pageIndex, totalPages]);\n\n const hasPreviousPage = useMemo(() => {\n return pageIndex > 0;\n }, [pageIndex]);\n\n return {\n state: {\n sorting,\n columnFilters,\n expanded,\n pageSize,\n pageIndex,\n selectedRows\n },\n actions: {\n setSorting,\n setColumnFilters,\n setExpanded,\n setPageSize,\n setPageIndex,\n setSelectedRows,\n resetState\n },\n computed: {\n paginatedData,\n totalPages,\n hasNextPage,\n hasPreviousPage\n }\n };\n}\n","\n/**\n * Zod Form Hook\n * \n * Enhanced form hook with Zod validation\n */\n\nimport { useForm } from 'react-hook-form';\nimport { zodResolver } from '@hookform/resolvers/zod';\nimport { z } from 'zod';\n\ninterface UseZodFormProps<T extends z.ZodTypeAny> {\n schema: T;\n defaultValues?: Partial<z.infer<T>>;\n mode?: 'onSubmit' | 'onBlur' | 'onChange' | 'onTouched' | 'all';\n}\n\nexport function useZodForm<T extends z.ZodTypeAny>({\n schema,\n defaultValues,\n mode = 'onSubmit'\n}: UseZodFormProps<T>) {\n return useForm<z.infer<T>>({\n resolver: zodResolver(schema),\n defaultValues: defaultValues as any,\n mode\n });\n}\n","\nimport { useEffect, useRef, useCallback } from 'react';\nimport { performanceBudgetMonitor, PERFORMANCE_BUDGETS } from '../utils/performanceBudgets';\n\nexport interface PerformanceMetrics {\n renderTime: number;\n componentName: string;\n timestamp: number;\n}\n\n/**\n * Hook for monitoring component performance with budget validation\n * @param componentName - Name of the component being monitored\n * @param enabled - Whether performance monitoring is enabled\n * @param budgetName - Performance budget to validate against\n */\nexport function usePerformanceMonitor(\n componentName: string, \n enabled = import.meta.env.MODE === 'development',\n budgetName: string = 'COMPONENT_RENDER'\n) {\n const renderStartTime = useRef<number>(0);\n const metrics = useRef<PerformanceMetrics[]>([]);\n\n // Start performance measurement\n const startMeasurement = useCallback(() => {\n if (!enabled) return;\n renderStartTime.current = performance.now();\n }, [enabled]);\n\n // End performance measurement with budget validation\n const endMeasurement = useCallback(() => {\n if (!enabled || renderStartTime.current === 0) return;\n \n const renderTime = performance.now() - renderStartTime.current;\n const metric: PerformanceMetrics = {\n renderTime,\n componentName,\n timestamp: Date.now()\n };\n \n metrics.current.push(metric);\n \n // Keep only last 10 measurements\n if (metrics.current.length > 10) {\n metrics.current = metrics.current.slice(-10);\n }\n \n // Validate against performance budget\n const measurement = performanceBudgetMonitor.measure(budgetName, renderTime, {\n componentName,\n renderCount: metrics.current.length\n });\n \n // Log slow renders in development\n if (!measurement.passed) {\n console.warn(\n `🐌 Performance budget exceeded in ${componentName}: ${renderTime.toFixed(2)}ms ` +\n `(budget: ${PERFORMANCE_BUDGETS[budgetName]?.threshold}ms)`\n );\n }\n \n renderStartTime.current = 0;\n }, [enabled, componentName, budgetName]);\n\n // Get performance metrics\n const getMetrics = useCallback(() => {\n return metrics.current.slice();\n }, []);\n\n // Get average render time\n const getAverageRenderTime = useCallback(() => {\n if (metrics.current.length === 0) return 0;\n \n const total = metrics.current.reduce((sum, metric) => sum + metric.renderTime, 0);\n return total / metrics.current.length;\n }, []);\n\n // Get performance budget status\n const getBudgetStatus = useCallback(() => {\n const budget = PERFORMANCE_BUDGETS[budgetName];\n if (!budget) return null;\n\n const averageTime = getAverageRenderTime();\n return {\n budget: budget.threshold,\n average: averageTime,\n passed: averageTime <= budget.threshold,\n efficiency: budget.threshold > 0 ? (budget.threshold - averageTime) / budget.threshold : 0\n };\n }, [budgetName, getAverageRenderTime]);\n\n // Start measurement on every render\n useEffect(() => {\n startMeasurement();\n return endMeasurement;\n });\n\n return {\n getMetrics,\n getAverageRenderTime,\n getBudgetStatus,\n startMeasurement,\n endMeasurement\n };\n}\n\n// Hook for measuring specific operations\nexport function useOperationPerformance(operationName: string, budgetName?: string) {\n const measureOperation = useCallback(async <T>(\n operation: () => Promise<T> | T,\n context?: Record<string, any>\n ): Promise<T> => {\n const start = performance.now();\n const result = await operation();\n const duration = performance.now() - start;\n \n const budget = budgetName || 'COMPONENT_RENDER';\n performanceBudgetMonitor.measure(budget, duration, {\n operation: operationName,\n ...context\n });\n \n return result;\n }, [operationName, budgetName]);\n\n return { measureOperation };\n}\n"],"mappings":"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","names":["useRef","useEffect","useCallback","useEffect","useCallback","useEffect","useState","useEffect","useState","useCallback","useEffect","useRef","useCallback","useRef","useCallback","useEffect"]}
package/dist/index.d.ts CHANGED
@@ -1,24 +1,24 @@
1
1
  export { a as UnifiedAuthContextType, c as UnifiedAuthProvider, b as UnifiedAuthProviderProps, U as UserEventAccess, u as useUnifiedAuth } from './UnifiedAuthProvider-BVKmQd9u.js';
2
- export { a as cn, c as createSecureDataAccess, j as formatCompactNumber, e as formatCurrency, f as formatDate, k as formatFileSize, h as formatNumber, i as formatPercent, g as getAppConfig, d as getCurrentAppId, b as getCurrentAppName, s as setAppConfig, u as useSessionTracking } from './formatting-B1jSqgl-.js';
3
- import { m as InactivityService, n as EventService, o as OrganisationService, A as AuthService } from './AuthService-D4646R4b.js';
4
- export { d as EventProvider, k as InactivityProvider, g as OrganisationProvider } from './AuthService-D4646R4b.js';
2
+ export { a as cn, c as createSecureDataAccess, j as formatCompactNumber, e as formatCurrency, f as formatDate, k as formatFileSize, h as formatNumber, i as formatPercent, g as getAppConfig, d as getCurrentAppId, b as getCurrentAppName, s as setAppConfig, u as useSessionTracking } from './formatting-DFcCxUEk.js';
3
+ import { m as InactivityService, n as EventService, o as OrganisationService, A as AuthService } from './AuthService-DYuQPJj6.js';
4
+ export { d as EventProvider, k as InactivityProvider, g as OrganisationProvider } from './AuthService-DYuQPJj6.js';
5
5
  import { e as OrganisationContextType } from './organisation-D6qRDtbF.js';
6
6
  export { O as Organisation, a as OrganisationMembership, f as OrganisationProviderProps, g as OrganisationSecurityError, U as UserProfile } from './organisation-D6qRDtbF.js';
7
7
  import { E as Event } from './unified-DQ4VcT7H.js';
8
8
  import { S as SessionRestorationState } from './auth-DReDSLq9.js';
9
9
  import * as react_jsx_runtime from 'react/jsx-runtime';
10
10
  export { ALL_PERMISSIONS, AccessLevel, AccessLevelGuard, AllPermissions, CACHE_PATTERNS, DataAccessRecord, EVENT_APP_PERMISSIONS, EnhancedNavigationMenu, EnhancedNavigationMenuProps, EventAppRole, EventAppRoleData, GLOBAL_PERMISSIONS, GlobalRole, GrantEventAppRoleParams, InvalidScopeError, LogLevel, MissingUserContextError, NavigationAccessRecord, NavigationContextType, NavigationGuard, NavigationGuardProps, NavigationProvider, NavigationProviderProps, ORGANISATION_PERMISSIONS, Operation, OrganisationContextRequiredError, OrganisationRole, PAGE_PERMISSIONS, PageAccessRecord, PagePermissionContextType, PagePermissionGuard, PagePermissionGuardProps, PagePermissionProvider, PagePermissionProviderProps, Permission, PermissionCheck, PermissionDeniedError, PermissionEnforcer, PermissionEnforcerProps, PermissionGuard, PermissionMap, RBACAuditManager, RBACCache, RBACConfig, RBACEngine, RBACError, RBACLogger, RBACNotInitializedError, RevokeEventAppRoleParams, RoleBasedRouter, RoleBasedRouterContextType, RoleBasedRouterProps, RoleManagementResult, RouteAccessRecord, RouteConfig, Scope, SecureDataContextType, SecureDataProvider, SecureDataProviderProps, SecureSupabaseClient, UUID, UseResolvedScopeOptions, UseResolvedScopeReturn, createAuditManager, createRBACConfig, createRBACEngine, createRBACExpressMiddleware, createRBACMiddleware, createSecureClient, emitAuditEvent, fromSupabaseClient, getAccessLevel, getGlobalAuditManager, getPermissionMap, getPermissionsForRole, getRBACConfig, getRBACLogger, getRoleContext, hasAllPermissions, hasAnyPermission, hasAnyPermissionCached, hasPermission, hasPermissionCached, isDebugMode, isDevelopmentMode, isPermitted, isPermittedCached, isValidPermission, rbacCache, resolveAppContext, setGlobalAuditManager, setupRBAC, useAccessLevel, useCachedPermissions, useCan, useHasAllPermissions, useHasAnyPermission, useMultiplePermissions, useNavigationPermissions, usePagePermissions, usePermissions, useRBAC, useResolvedScope, useRoleBasedRouter, useRoleManagement, useSecureData, withAccessLevelGuard, withPermissionGuard, withRoleGuard } from './rbac/index.js';
11
- export { A as Alert, m as AlertDescription, l as AlertTitle, n as Avatar, p as AvatarFallback, o as AvatarImage, B as Button, a as ButtonProps, C as Card, g as CardActions, f as CardContent, e as CardDescription, c as CardFooter, b as CardHeader, h as CardProps, d as CardTitle, q as Checkbox, b3 as DefaultPublicErrorFallback, D as Dialog, K as DialogBody, G as DialogClose, H as DialogContent, O as DialogDescription, M as DialogFooter, J as DialogHeader, E as DialogOverlay, z as DialogPortal, N as DialogTitle, F as DialogTrigger, aB as ErrorBoundary, aG as EventSelector, aK as FileDisplay, aL as FileDisplayProps, aI as FileUpload, aJ as FileUploadProps, ar as Footer, as as FooterProps, am as Form, aq as Header, I as Input, j as InputProps, L as Label, k as LabelProps, aE as LoadingSpinner, ao as LoginForm, ap as LoginFormProps, ax as NavigationItem, av as NavigationMenu, aw as NavigationMenuProps, ay as OrganisationSelector, be as PaceAppLayout, bd as PaceAppLayoutProps, bg as PaceLoginPage, bf as PaceLoginPageProps, aH as PasswordResetForm, P as Progress, at as ProtectedRoute, au as ProtectedRouteProps, b1 as PublicErrorBoundary, ba as PublicErrorBoundaryProps, bb as PublicErrorBoundaryState, b6 as PublicLoadingSkeleton, b4 as PublicLoadingSpinner, b5 as PublicLoadingSpinnerFullPage, bc as PublicLoadingSpinnerProps, b0 as PublicPageContextChecker, a_ as PublicPageDebugger, a$ as PublicPageDiagnostic, aZ as PublicPageFooter, b9 as PublicPageFooterProps, aV as PublicPageHeader, b8 as PublicPageHeaderProps, aT as PublicPageLayout, b7 as PublicPageLayoutProps, aW as PublicPageProvider, $ as Select, a3 as SelectContent, a0 as SelectGroup, a5 as SelectItem, a4 as SelectLabel, a6 as SelectSeparator, a2 as SelectTrigger, a1 as SelectValue, aF as SessionRestorationLoader, S as Switch, r as SwitchProps, T as Table, t as TableBody, u as TableCaption, v as TableCell, w as TableFooter, x as TableHead, s as TableHeader, y as TableRow, a7 as Toast, a9 as ToastAction, af as ToastActionElement, ae as ToastClose, ad as ToastDescription, ag as ToastProps, aa as ToastProvider, ac as ToastTitle, ab as ToastViewport, a8 as Toaster, ah as Tooltip, aj as TooltipContent, ak as TooltipProvider, al as TooltipRoot, ai as TooltipTrigger, aS as UseFileReferenceForRecordReturn, aQ as UseFileReferenceOptions, aR as UseFileReferenceReturn, aA as UserMenu, bh as UserMenuProps, b2 as useErrorBoundary, aM as useFileReference, aO as useFileReferenceById, aN as useFileReferenceForRecord, aP as useFilesByCategory, aY as useIsPublicPage, aU as usePublicPageContext, aX as usePublicPageProviderContext } from './PublicLoadingSpinner-DgDWTFqn.js';
11
+ export { A as Alert, m as AlertDescription, l as AlertTitle, n as Avatar, p as AvatarFallback, o as AvatarImage, B as Button, a as ButtonProps, C as Card, g as CardActions, f as CardContent, e as CardDescription, c as CardFooter, b as CardHeader, h as CardProps, d as CardTitle, q as Checkbox, b3 as DefaultPublicErrorFallback, D as Dialog, K as DialogBody, G as DialogClose, H as DialogContent, O as DialogDescription, M as DialogFooter, J as DialogHeader, E as DialogOverlay, z as DialogPortal, N as DialogTitle, F as DialogTrigger, aB as ErrorBoundary, aG as EventSelector, aK as FileDisplay, aL as FileDisplayProps, aI as FileUpload, aJ as FileUploadProps, ar as Footer, as as FooterProps, am as Form, aq as Header, I as Input, j as InputProps, L as Label, k as LabelProps, aE as LoadingSpinner, ao as LoginForm, ap as LoginFormProps, ax as NavigationItem, av as NavigationMenu, aw as NavigationMenuProps, ay as OrganisationSelector, be as PaceAppLayout, bd as PaceAppLayoutProps, bg as PaceLoginPage, bf as PaceLoginPageProps, aH as PasswordResetForm, P as Progress, at as ProtectedRoute, au as ProtectedRouteProps, b1 as PublicErrorBoundary, ba as PublicErrorBoundaryProps, bb as PublicErrorBoundaryState, b6 as PublicLoadingSkeleton, b4 as PublicLoadingSpinner, b5 as PublicLoadingSpinnerFullPage, bc as PublicLoadingSpinnerProps, b0 as PublicPageContextChecker, a_ as PublicPageDebugger, a$ as PublicPageDiagnostic, aZ as PublicPageFooter, b9 as PublicPageFooterProps, aV as PublicPageHeader, b8 as PublicPageHeaderProps, aT as PublicPageLayout, b7 as PublicPageLayoutProps, aW as PublicPageProvider, $ as Select, a3 as SelectContent, a0 as SelectGroup, a5 as SelectItem, a4 as SelectLabel, a6 as SelectSeparator, a2 as SelectTrigger, a1 as SelectValue, aF as SessionRestorationLoader, S as Switch, r as SwitchProps, T as Table, t as TableBody, u as TableCaption, v as TableCell, w as TableFooter, x as TableHead, s as TableHeader, y as TableRow, a7 as Toast, a9 as ToastAction, af as ToastActionElement, ae as ToastClose, ad as ToastDescription, ag as ToastProps, aa as ToastProvider, ac as ToastTitle, ab as ToastViewport, a8 as Toaster, ah as Tooltip, aj as TooltipContent, ak as TooltipProvider, al as TooltipRoot, ai as TooltipTrigger, aS as UseFileReferenceForRecordReturn, aQ as UseFileReferenceOptions, aR as UseFileReferenceReturn, aA as UserMenu, bh as UserMenuProps, b2 as useErrorBoundary, aM as useFileReference, aO as useFileReferenceById, aN as useFileReferenceForRecord, aP as useFilesByCategory, aY as useIsPublicPage, aU as usePublicPageContext, aX as usePublicPageProviderContext } from './PublicLoadingSpinner-CaoRbHvJ.js';
12
12
  export { u as useToast } from './useToast-C8gR5ir4.js';
13
13
  export { D as DataTable, a as DataTableProps } from './DataTable-D5cBRca8.js';
14
14
  import { D as DataRecord, f as DataTableAction } from './types-D4TVpDa1.js';
15
15
  export { A as AggregateConfig, a as DataTableColumn, g as DataTableToolbarButton, E as EmptyStateConfig, G as GetRowId } from './types-D4TVpDa1.js';
16
16
  import { ColumnDef } from '@tanstack/react-table';
17
- export { p as UsePublicEventOptions, o as UsePublicEventReturn, r as UsePublicFileDisplayOptions, q as UsePublicFileDisplayReturn, s as UsePublicRouteParamsReturn, f as clearPublicEventCache, i as clearPublicFileDisplayCache, n as extractEventCodeFromPath, m as generatePublicRoutePath, g as getPublicEventCacheStats, j as getPublicFileDisplayCacheStats, c as useAppConfig, u as useEventTheme, a as useOrganisationPermissions, b as useOrganisationSecurity, e as usePublicEvent, l as usePublicEventCode, h as usePublicFileDisplay, k as usePublicRouteParams } from './usePublicRouteParams-BdF8bZgs.js';
17
+ export { p as UsePublicEventOptions, o as UsePublicEventReturn, r as UsePublicFileDisplayOptions, q as UsePublicFileDisplayReturn, s as UsePublicRouteParamsReturn, f as clearPublicEventCache, i as clearPublicFileDisplayCache, n as extractEventCodeFromPath, m as generatePublicRoutePath, g as getPublicEventCacheStats, j as getPublicFileDisplayCacheStats, c as useAppConfig, u as useEventTheme, a as useOrganisationPermissions, b as useOrganisationSecurity, e as usePublicEvent, l as usePublicEventCode, h as usePublicFileDisplay, k as usePublicRouteParams } from './usePublicRouteParams-Dyt1tzI9.js';
18
18
  export { b as FileCategory, a as FileMetadata, F as FileReference, c as FileUploadOptions } from './file-reference-C9isKNPn.js';
19
19
  import { SupabaseClient } from '@supabase/supabase-js';
20
20
  export { StyleImport, getAllStylePaths, getStylePath, styleConfig } from './styles/index.js';
21
- export { ColorPalette, ColorShade, PaletteData, applyPalette, clearPalette, generateSSRThemeCSS, getCurrentThemeData, isDynamicThemingActive } from './theming/runtime.js';
21
+ export { ColorPalette, ColorShade, PaletteData, applyPalette, clearPalette, generateSSRThemeCSS, getCurrentThemeData, isDynamicThemingActive, parseAndNormalizeEventColours } from './theming/runtime.js';
22
22
  import 'react';
23
23
  import 'clsx';
24
24
  import './database-C6jy7EOu.js';
package/dist/index.js CHANGED
@@ -30,7 +30,7 @@ import {
30
30
  withAccessLevelGuard,
31
31
  withPermissionGuard,
32
32
  withRoleGuard
33
- } from "./chunk-TDNI6ZWL.js";
33
+ } from "./chunk-IJOZZOGT.js";
34
34
  import {
35
35
  init_useInactivityTracker,
36
36
  useInactivityTracker
@@ -90,7 +90,7 @@ import {
90
90
  useFileReferenceForRecord,
91
91
  useFilesByCategory,
92
92
  usePublicPageContext as usePublicPageContext2
93
- } from "./chunk-QPI2CCBA.js";
93
+ } from "./chunk-VPUCTHTY.js";
94
94
  import {
95
95
  Alert,
96
96
  AlertDescription,
@@ -131,7 +131,7 @@ import {
131
131
  TooltipProvider,
132
132
  TooltipRoot,
133
133
  TooltipTrigger
134
- } from "./chunk-HFBOFZ3Z.js";
134
+ } from "./chunk-GBGYYMC6.js";
135
135
  import {
136
136
  useAccessLevel,
137
137
  useCachedPermissions,
@@ -143,7 +143,7 @@ import {
143
143
  useRBAC,
144
144
  useResolvedScope,
145
145
  useRoleManagement
146
- } from "./chunk-D6BOFXYR.js";
146
+ } from "./chunk-35ZDPMBM.js";
147
147
  import {
148
148
  CACHE_PATTERNS,
149
149
  RBACCache,
@@ -183,8 +183,8 @@ import {
183
183
  usePublicEvent,
184
184
  usePublicEventCode,
185
185
  usePublicRouteParams
186
- } from "./chunk-RIEJGKD3.js";
187
- import "./chunk-B4GZ2BXO.js";
186
+ } from "./chunk-ESJTIADP.js";
187
+ import "./chunk-NZGLXZGP.js";
188
188
  import {
189
189
  APP_PATH_MAPPING,
190
190
  DEFAULT_FILE_SIZE_LIMIT,
@@ -215,7 +215,7 @@ import {
215
215
  usePublicFileDisplay,
216
216
  usePublicPageContext,
217
217
  validateFileSize
218
- } from "./chunk-FKFHZUGF.js";
218
+ } from "./chunk-XN6GWKMV.js";
219
219
  import {
220
220
  useToast
221
221
  } from "./chunk-GKHF54DI.js";
@@ -223,11 +223,11 @@ import {
223
223
  init_useOrganisations,
224
224
  useEvents,
225
225
  useOrganisations
226
- } from "./chunk-CGURJ27Z.js";
226
+ } from "./chunk-4MXVZVNS.js";
227
227
  import {
228
228
  init_UnifiedAuthProvider
229
- } from "./chunk-ZYJ6O5CA.js";
230
- import "./chunk-NZ32EONV.js";
229
+ } from "./chunk-C43QIDN3.js";
230
+ import "./chunk-QWNJCQXZ.js";
231
231
  import {
232
232
  EventServiceProvider,
233
233
  InactivityServiceProvider,
@@ -245,7 +245,7 @@ import {
245
245
  useOrganisationService2 as useOrganisationService,
246
246
  useSessionRestoration,
247
247
  useUnifiedAuth
248
- } from "./chunk-BHWIUEYH.js";
248
+ } from "./chunk-ZBLK676C.js";
249
249
  import {
250
250
  FileCategory
251
251
  } from "./chunk-XJ2HZOBU.js";
@@ -261,29 +261,30 @@ import {
261
261
  getCurrentAppName,
262
262
  setAppConfig,
263
263
  useSessionTracking
264
- } from "./chunk-GZRXOUBE.js";
264
+ } from "./chunk-M6DDYFUD.js";
265
265
  import {
266
266
  LoadingSpinner
267
267
  } from "./chunk-CDQ3PX7L.js";
268
+ import "./chunk-JCQZ6LA7.js";
269
+ import "./chunk-O3NWNXDY.js";
268
270
  import {
269
271
  cn
270
272
  } from "./chunk-PYUXFQJ3.js";
271
- import "./chunk-JCQZ6LA7.js";
272
- import "./chunk-O3NWNXDY.js";
273
273
  import "./chunk-BDZUMRBD.js";
274
274
  import "./chunk-UJI6WSMD.js";
275
275
  import {
276
276
  getAllStylePaths,
277
277
  getStylePath,
278
278
  styleConfig
279
- } from "./chunk-VKOCWWVY.js";
279
+ } from "./chunk-CX5M4ZAG.js";
280
280
  import {
281
281
  applyPalette,
282
282
  clearPalette,
283
283
  generateSSRThemeCSS,
284
284
  getCurrentThemeData,
285
- isDynamicThemingActive
286
- } from "./chunk-SMJZMKYN.js";
285
+ isDynamicThemingActive,
286
+ parseAndNormalizeEventColours
287
+ } from "./chunk-GEVIB2UB.js";
287
288
  import "./chunk-PLDDJCW6.js";
288
289
 
289
290
  // src/index.ts
@@ -800,6 +801,7 @@ export {
800
801
  isPermittedCached,
801
802
  isValidPermission,
802
803
  listFiles,
804
+ parseAndNormalizeEventColours,
803
805
  rbacCache,
804
806
  resolveAppContext,
805
807
  setAppConfig,
package/dist/index.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"sources":["../src/index.ts","../src/providers/InactivityProvider.tsx","../src/components/InactivityWarningModal/InactivityWarningModal.tsx","../src/utils/secureDataAccess.ts","../src/utils/storage/index.ts"],"sourcesContent":["/**\n * @file Complete Component Library Export\n * @package @jmruthers/pace-core\n * @module Core\n * @since 0.1.0\n * \n * This file exports the primary components, hooks, and utilities from the PACE Core library.\n * It is the main entry point for developers using the library.\n * \n * @example\n * // Import common components\n * import { Button, Card, useUnifiedAuth } from '@jmruthers/pace-core';\n * \n * // For specialized components, use the complete library import:\n * import { Dialog, NavigationMenu } from '@jmruthers/pace-core/components';\n */\n\n// AUTHENTICATION & AUTHORIZATION\n// Note: Providers are now service-based architecture for better testability and maintainability\nexport { UnifiedAuthProvider, useUnifiedAuth } from './providers/UnifiedAuthProvider';\nexport type { UnifiedAuthProviderProps, UnifiedAuthContextType, UserEventAccess } from './providers/UnifiedAuthProvider';\n\n// Session tracking utility (for manual use if needed)\nexport { useSessionTracking } from './utils/sessionTracking';\n\n// Provider components (using service architecture)\nexport { EventProvider } from './providers/EventProvider';\nexport { OrganisationProvider } from './providers/OrganisationProvider';\nexport { InactivityProvider } from './providers/InactivityProvider';\n\n// Convenience hooks for backward compatibility\nexport { useEvents } from './hooks/useEvents';\nexport { useOrganisations } from './hooks/useOrganisations';\n\n// Service hooks for advanced usage (better performance)\nexport { useEventService } from './hooks/services/useEventService';\nexport { useOrganisationService } from './hooks/services/useOrganisationService';\nexport { useAuthService } from './hooks/services/useAuthService';\nexport { useInactivityService } from './hooks/services/useInactivityService';\nexport { useSessionRestoration } from './hooks/useSessionRestoration';\n\nexport type { \n Organisation, \n OrganisationMembership, \n OrganisationContextType, \n OrganisationProviderProps,\n OrganisationSecurityError \n} from './types/organisation';\n\n// INACTIVITY TRACKING\nexport { InactivityWarningModal } from './components/InactivityWarningModal/InactivityWarningModal';\nexport type { InactivityWarningModalProps } from './components/InactivityWarningModal/InactivityWarningModal';\nexport { useInactivityTracker } from './hooks/useInactivityTracker';\nexport type { UseInactivityTrackerOptions, UseInactivityTrackerReturn } from './hooks/useInactivityTracker';\n\n// RBAC SYSTEM - Consolidated RBAC module\nexport * from './rbac';\n\n// BASIC UI COMPONENTS\nexport { Button } from './components/Button/Button';\nexport type { ButtonProps } from './components/Button/Button';\n\nexport { \n Card, \n CardHeader, \n CardFooter, \n CardTitle, \n CardDescription, \n CardContent,\n CardActions\n} from './components/Card/Card';\nexport type { CardProps } from './components/Card/Card';\n\nexport { Input } from './components/Input/Input';\nexport type { InputProps } from './components/Input/Input';\nexport { Label } from './components/Label/Label';\nexport type { LabelProps } from './components/Label/Label';\n\nexport { Alert, AlertTitle, AlertDescription } from './components/Alert/Alert';\nexport { Avatar, AvatarImage, AvatarFallback } from './components/Avatar/Avatar';\n\nexport { Checkbox } from './components/Checkbox/Checkbox';\nexport { Switch } from './components/Switch/Switch';\nexport type { SwitchProps } from './components/Switch/Switch';\nexport { Progress } from './components/Progress/Progress';\n\n// ADVANCED UI COMPONENTS\nexport {\n Dialog,\n DialogPortal,\n DialogOverlay,\n DialogTrigger,\n DialogClose,\n DialogContent,\n DialogHeader,\n DialogBody,\n DialogFooter,\n DialogTitle,\n DialogDescription,\n} from './components/Dialog/Dialog';\n\n// Dropdown Menu exports\n// DropdownMenu components have been merged into Select components\n\n// Select exports\nexport {\n Select,\n SelectGroup,\n SelectValue,\n SelectTrigger,\n SelectContent,\n SelectLabel,\n SelectItem,\n SelectSeparator,\n} from './components/Select';\n\n// Modal functionality is provided by Dialog components\n\nexport {\n Toast,\n Toaster,\n ToastAction,\n ToastProvider,\n ToastViewport,\n ToastTitle,\n ToastDescription,\n ToastClose,\n} from './components/Toast/Toast';\nexport { useToast } from './hooks/useToast';\nexport type { ToastActionElement, ToastProps } from './components/Toast/Toast';\n\nexport { Tooltip, TooltipTrigger, TooltipContent, TooltipProvider, TooltipRoot } from './components/Tooltip/Tooltip';\n\n// DATA DISPLAY COMPONENTS\nexport {\n DataTable,\n type DataTableProps,\n type DataTableColumn,\n type DataTableAction,\n type DataTableToolbarButton,\n type AggregateConfig,\n type EmptyStateConfig,\n type GetRowId,\n ColumnFactory\n} from './components/DataTable';\n\n// Re-export types from DataTable types\nexport type { DataRecord } from './components/DataTable/types';\n\n// FORM COMPONENTS\nexport { Form } from './components/Form/Form';\nexport { LoginForm } from './components/LoginForm/LoginForm';\nexport type { LoginFormProps } from './components/LoginForm/LoginForm';\n\n// LAYOUT COMPONENTS\nexport { Header } from './components/Header/Header';\nexport { Footer } from './components/Footer/Footer';\nexport type { FooterProps } from './components/Footer/Footer';\n\n// NAVIGATION COMPONENTS\nexport { NavigationMenu } from './components/NavigationMenu/NavigationMenu';\nexport type { NavigationMenuProps, NavigationItem } from './components/NavigationMenu/types';\nexport { UserMenu } from './components/UserMenu/UserMenu';\nexport type { UserMenuProps } from './components/UserMenu/UserMenu';\n\n// Reusable Page/Layout Components\nexport { PaceAppLayout } from './components/PaceAppLayout/PaceAppLayout';\nexport type { PaceAppLayoutProps } from './components/PaceAppLayout/PaceAppLayout';\nexport { PaceLoginPage } from './components/PaceLoginPage/PaceLoginPage';\nexport type { PaceLoginPageProps } from './components/PaceLoginPage/PaceLoginPage';\n\nexport { ProtectedRoute } from './components/ProtectedRoute/ProtectedRoute';\nexport type { ProtectedRouteProps } from './components/ProtectedRoute/ProtectedRoute';\n\n// UTILITY COMPONENTS\nexport { ErrorBoundary } from './components/ErrorBoundary/ErrorBoundary';\nexport { LoadingSpinner } from './components/LoadingSpinner/LoadingSpinner';\nexport { SessionRestorationLoader } from './components/SessionRestorationLoader';\n\n// EVENT MANAGEMENT\nexport { EventSelector } from './components/EventSelector/EventSelector';\n\n// ORGANISATION MANAGEMENT\nexport { OrganisationSelector } from './components/OrganisationSelector/OrganisationSelector';\nexport { useOrganisationPermissions } from './hooks/useOrganisationPermissions';\nexport { useOrganisationSecurity } from './hooks/useOrganisationSecurity';\nexport { createSecureDataAccess } from './utils/secureDataAccess';\n\n// TYPES\nexport type { UserProfile } from './types/organisation';\n\n// AUTHENTICATION FORMS\nexport { PasswordResetForm } from './components/PasswordReset/PasswordResetForm';\nexport { PasswordChangeForm } from './components/PasswordReset/PasswordChangeForm';\n\n// UTILS & HOOKS\nexport { useAppConfig } from './hooks/useAppConfig';\nexport { useEventTheme } from './hooks/useEventTheme';\nexport { cn } from './utils/cn';\nexport { setAppConfig, getAppConfig, getCurrentAppName, getCurrentAppId } from './utils/appConfig';\n\n// FORMATTING UTILITIES\nexport { \n formatDate, \n formatCurrency, \n formatNumber,\n formatPercent,\n formatCompactNumber,\n formatFileSize\n} from './utils/formatting';\n\n// STORAGE UTILITIES\nexport { FileUpload } from './components/FileUpload';\nexport type { FileUploadProps } from './components/FileUpload';\nexport { FileDisplay } from './components/FileDisplay';\nexport type { FileDisplayProps } from './components/FileDisplay';\nexport { FileCategory } from './types/file-reference';\nexport type { FileReference, FileMetadata, FileUploadOptions } from './types/file-reference';\nexport { \n useFileReference, \n useFileReferenceForRecord,\n useFileReferenceById,\n useFilesByCategory\n} from './hooks/useFileReference';\nexport type { \n UseFileReferenceOptions, \n UseFileReferenceReturn, \n UseFileReferenceForRecordReturn \n} from './hooks/useFileReference';\nexport * from './utils/storage';\n\n// Table components\nexport {\n Table,\n TableHeader,\n TableBody,\n TableCaption,\n TableCell,\n TableFooter,\n TableHead,\n TableRow,\n} from './components/Table/Table';\n\n// STYLES\nexport * from './styles';\n\n// PUBLIC PAGES\nexport * from './hooks/public';\nexport * from './components/PublicLayout';\n","/**\n * @file Re-export for InactivityProvider\n * @package @jmruthers/pace-core\n * @module Providers\n * @since 0.1.0\n * \n * Re-exports the service-based InactivityProvider for backward compatibility.\n */\n\nexport { InactivityServiceProvider as InactivityProvider } from './services/InactivityServiceProvider';\nexport type { InactivityServiceProviderProps as InactivityProviderProps, InactivityServiceContextType as InactivityContextType } from './services/InactivityServiceProvider';\n\n// Re-export hook\nexport { useInactivityService as useInactivity } from '../hooks/services/useInactivityService';\n\n","/**\n * @file Inactivity Warning Modal\n * @package @jmruthers/pace-core\n * @module Components/InactivityWarningModal\n * @since 0.1.0\n *\n * A modal dialog that warns users about impending auto-logout due to inactivity.\n * Provides a countdown timer and action buttons to either stay signed in or sign out immediately.\n *\n * Features:\n * - Accessible modal dialog with focus management\n * - Live countdown timer with 1-second updates\n * - Clear action buttons (Stay Signed In / Sign Out Now)\n * - Keyboard navigation support (Escape to stay signed in)\n * - Cross-tab awareness and synchronization\n * - Tailwind v4 styling with pace-core theme tokens\n * - Production-safe with no arbitrary bracket classes\n *\n * @example\n * ```tsx\n * <InactivityWarningModal\n * isOpen={showWarning}\n * timeRemaining={45}\n * onStaySignedIn={() => setShowWarning(false)}\n * onSignOutNow={() => signOut()}\n * />\n * ```\n *\n * @accessibility\n * - WCAG 2.1 AA compliant\n * - Focus trap within modal content\n * - Screen reader announcements for countdown changes\n * - Keyboard navigation support\n * - Clear visual hierarchy and contrast\n * - Escape key to stay signed in (safe default)\n *\n * @performance\n * - Efficient countdown updates (1-second intervals)\n * - Minimal re-renders with stable references\n * - Memory leak prevention with cleanup\n * - Optimized timer management\n *\n * @dependencies\n * - React 18+ - Hooks and effects\n * - Dialog components - Modal functionality\n * - Tailwind CSS v4 - Styling\n */\n\nimport React, { useEffect, useState, useCallback } from 'react';\nimport { Dialog, DialogContent, DialogHeader, DialogTitle, DialogDescription } from '../Dialog/Dialog';\nimport { Button } from '../Button/Button';\nimport { Clock, AlertTriangle } from 'lucide-react';\n\nexport interface InactivityWarningModalProps {\n /** Whether the modal is open */\n isOpen: boolean;\n /** Time remaining in seconds before auto-logout */\n timeRemaining: number;\n /** Callback when user chooses to stay signed in */\n onStaySignedIn: () => void;\n /** Callback when user chooses to sign out immediately */\n onSignOutNow: () => void;\n /** Optional custom title */\n title?: string;\n /** Optional custom description */\n description?: string;\n /** Optional custom className */\n className?: string;\n}\n\nexport function InactivityWarningModal({\n isOpen,\n timeRemaining,\n onStaySignedIn,\n onSignOutNow,\n title = \"Session Timeout Warning\",\n description = \"You've been inactive for a while. Your session will expire soon for security reasons.\",\n className\n}: InactivityWarningModalProps) {\n const [displayTime, setDisplayTime] = useState(timeRemaining);\n\n // Update display time when timeRemaining prop changes\n useEffect(() => {\n setDisplayTime(timeRemaining);\n }, [timeRemaining]);\n\n // Format time for display (MM:SS)\n const formatTime = useCallback((seconds: number) => {\n const mins = Math.floor(seconds / 60);\n const secs = seconds % 60;\n return `${mins.toString().padStart(2, '0')}:${secs.toString().padStart(2, '0')}`;\n }, []);\n\n\n\n\n return (\n <Dialog open={isOpen} onOpenChange={(open) => !open && onStaySignedIn()}>\n <DialogContent \n className={`sm:max-w-md ${className || ''}`}\n preventCloseOnEscape={false}\n preventCloseOnOutsideClick={true}\n data-testid=\"inactivity-warning-modal\"\n >\n <DialogHeader>\n <div className=\"flex items-center gap-3\">\n <div className=\"flex-shrink-0\">\n <AlertTriangle className=\"h-6 w-6 text-acc-600\" />\n </div>\n <div>\n <DialogTitle className=\"text-lg font-semibold text-main-900\">\n {title}\n </DialogTitle>\n </div>\n </div>\n <DialogDescription className=\"text-main-700 mt-2\">\n {description}\n </DialogDescription>\n </DialogHeader>\n\n <div className=\"space-y-6\">\n {/* Countdown Timer */}\n <div className=\"text-center\">\n <div className=\"inline-flex items-center gap-2 px-4 py-3 bg-acc-50 border border-acc-200 rounded-lg\">\n <Clock className=\"h-5 w-5 text-acc-600\" />\n <span className=\"text-2xl font-mono font-bold text-acc-700\">\n {formatTime(displayTime)}\n </span>\n </div>\n <p className=\"text-sm text-main-600 mt-2\">\n Time remaining before automatic logout\n </p>\n </div>\n\n {/* Action Buttons */}\n <div className=\"flex flex-col sm:flex-row gap-3\">\n <Button\n onClick={onStaySignedIn}\n className=\"flex-1 bg-main-600 hover:bg-main-700 text-main-50\"\n size=\"lg\"\n >\n Stay Signed In\n </Button>\n <Button\n onClick={onSignOutNow}\n variant=\"outline\"\n className=\"flex-1 border-acc-300 text-acc-700 hover:bg-acc-50\"\n size=\"lg\"\n >\n Sign Out Now\n </Button>\n </div>\n\n {/* Additional Info */}\n <div className=\"text-xs text-main-500 text-center\">\n <p>\n For security reasons, you'll be automatically signed out after 30 minutes of inactivity.\n </p>\n </div>\n </div>\n </DialogContent>\n </Dialog>\n );\n}\n","/**\n * @file Secure Data Access Utility\n * @package @jmruthers/pace-core\n * @module Utils/SecureDataAccess\n * @since 0.4.0\n *\n * Secure data access utilities that enforce organisation context for all database operations.\n * Prevents data leakage between organisations and ensures proper access validation.\n */\n\nimport type { SupabaseClient } from '@supabase/supabase-js';\n\n// Generic database record type\nexport interface DatabaseRecord {\n id: string;\n organisation_id: string;\n [key: string]: unknown;\n}\n\n// Generic data for insert/update operations\nexport interface DatabaseData {\n [key: string]: unknown;\n}\n\n// Generic filters for queries\nexport interface DatabaseFilters {\n [key: string]: unknown;\n}\n\n// Secure query options\nexport interface SecureQueryOptions {\n table: string;\n select: string;\n organisationId: string;\n filters?: DatabaseFilters;\n orderBy?: string;\n limit?: number;\n offset?: number;\n}\n\nexport interface SecureDataAccess {\n // Secure query methods\n secureQuery: <T extends DatabaseRecord = DatabaseRecord>(options: SecureQueryOptions) => Promise<T[]>;\n secureSingleQuery: <T extends DatabaseRecord = DatabaseRecord>(options: SecureQueryOptions) => Promise<T | null>;\n \n // Secure mutation methods\n secureInsert: <T extends DatabaseRecord = DatabaseRecord>(table: string, data: DatabaseData, organisationId: string) => Promise<T | null>;\n secureUpdate: <T extends DatabaseRecord = DatabaseRecord>(table: string, data: DatabaseData, filters: DatabaseFilters, organisationId: string) => Promise<T | null>;\n secureDelete: (table: string, filters: DatabaseFilters, organisationId: string) => Promise<boolean>;\n \n // Organisation-scoped queries\n queryByOrganisation: <T extends DatabaseRecord = DatabaseRecord>(table: string, select: string, organisationId: string, filters?: DatabaseFilters) => Promise<T[]>;\n \n // Validation helpers\n validateOrganisationContext: (organisationId: string) => void;\n ensureOrganisationColumn: (table: string) => boolean;\n}\n\nexport interface SecureQueryBuilder {\n table: string;\n select: string;\n organisationId: string;\n filters?: DatabaseFilters;\n orderBy?: string;\n limit?: number;\n offset?: number;\n}\n\n/**\n * Create a secure data access instance\n * @param supabase - Supabase client instance\n * @param organisationId - Current organisation context\n * @param isSuperAdmin - Whether user has super admin privileges\n * @returns Secure data access utilities\n */\nexport const createSecureDataAccess = (\n supabase: SupabaseClient,\n organisationId: string,\n isSuperAdmin: boolean = false\n): SecureDataAccess => {\n \n // Validate organisation context\n const validateOrganisationContext = (orgId: string): void => {\n if (!orgId) {\n throw new Error('Organisation context is required for secure data access');\n }\n \n if (!isSuperAdmin && !orgId) {\n throw new Error('Organisation context is mandatory for non-super admin users');\n }\n };\n\n // Check if table has organisation_id column\n const ensureOrganisationColumn = (table: string): boolean => {\n // This is a simplified check - in production you might want to cache this\n const tablesWithOrganisation = [\n 'event', 'organisation_settings',\n 'rbac_event_app_roles', 'rbac_organisation_roles',\n // SECURITY: Phase 2 additions - complete organisation table mapping\n 'organisation_audit_log', 'organisation_invitations', 'organisation_app_access',\n // SECURITY: Emergency additions for Phase 1 fixes\n 'cake_meal', 'cake_mealtype', 'pace_person', 'pace_member',\n // SECURITY: Phase 3A additions - medical and personal data\n 'medi_profile', 'medi_condition', 'medi_diet', 'medi_action_plan', 'medi_profile_versions',\n 'pace_consent', 'pace_contact', 'pace_id_documents', 'pace_qualifications',\n 'form_responses', 'form_response_values', 'forms',\n // SECURITY: Phase 3B additions - remaining critical tables\n 'invoice', 'line_item', 'credit_balance', 'payment_method',\n 'form_contexts', 'form_field_config', 'form_fields',\n 'cake_delivery', 'cake_diettype', 'cake_diner', 'cake_dish', 'cake_item', \n 'cake_logistics', 'cake_mealplan', 'cake_package', 'cake_recipe', 'cake_supplier', \n 'cake_supply', 'cake_unit', 'event_app_access', 'base_application', 'base_questions'\n ];\n \n return tablesWithOrganisation.includes(table);\n };\n\n // Build secure query with organisation context\n const buildSecureQuery = (options: SecureQueryBuilder) => {\n const { table, select, organisationId: orgId, filters, orderBy, limit, offset } = options;\n \n validateOrganisationContext(orgId);\n \n let query = supabase\n .from(table)\n .select(select);\n \n // Add organisation filter (unless super admin)\n if (!isSuperAdmin && ensureOrganisationColumn(table)) {\n query = query.eq('organisation_id', orgId);\n }\n \n // Add additional filters\n if (filters) {\n Object.entries(filters).forEach(([key, value]) => {\n if (value !== undefined && value !== null) {\n // Handle qualified column names (e.g., 'users.role')\n const columnName = key.includes('.') ? key.split('.').pop()! : key;\n query = query.eq(columnName, value);\n }\n });\n }\n \n // Add ordering\n if (orderBy) {\n // Only use the column name, not a qualified name\n const orderByColumn = orderBy.split('.').pop();\n if (orderByColumn) {\n query = query.order(orderByColumn);\n }\n }\n \n // Add pagination\n if (limit) {\n query = query.limit(limit);\n }\n \n if (offset) {\n query = query.range(offset, offset + (limit || 10) - 1);\n }\n \n return query;\n };\n\n // Secure query for multiple results\n const secureQuery = async <T extends DatabaseRecord = DatabaseRecord>(options: SecureQueryOptions): Promise<T[]> => {\n const { table, select, organisationId: orgId, filters, orderBy, limit, offset } = options;\n \n try {\n const query = buildSecureQuery({\n table,\n select,\n organisationId: orgId,\n filters,\n orderBy,\n limit,\n offset\n });\n \n const { data, error } = await query;\n \n if (error) {\n throw error;\n }\n \n // Ensure data is an array and not an error type\n if (Array.isArray(data)) {\n return data as unknown as T[];\n }\n \n return [];\n } catch (error) {\n throw error;\n }\n };\n\n // Secure query for single result\n const secureSingleQuery = async <T extends DatabaseRecord = DatabaseRecord>(options: SecureQueryOptions): Promise<T | null> => {\n const { table, select, organisationId: orgId, filters, orderBy, limit, offset } = options;\n \n try {\n const query = buildSecureQuery({\n table,\n select,\n organisationId: orgId,\n filters,\n orderBy,\n limit,\n offset\n });\n \n const { data, error } = await query.single();\n \n if (error) {\n if (error.code === 'PGRST116') {\n // No rows returned\n return null;\n }\n throw error;\n }\n \n // Ensure data is not an error type\n if (data && typeof data === 'object' && !('code' in data)) {\n return data as unknown as T;\n }\n \n return null;\n } catch (error) {\n throw error;\n }\n };\n\n // Secure insert with organisation context\n const secureInsert = async <T extends DatabaseRecord = DatabaseRecord>(\n table: string, \n data: DatabaseData, \n organisationId: string\n ): Promise<T | null> => {\n validateOrganisationContext(organisationId);\n \n try {\n const insertData = {\n ...data,\n organisation_id: organisationId\n };\n \n const { data: result, error } = await supabase\n .from(table)\n .insert(insertData)\n .select()\n .single();\n \n if (error) {\n throw error;\n }\n \n return result;\n } catch (error) {\n throw error;\n }\n };\n\n // Secure update with organisation context\n const secureUpdate = async <T extends DatabaseRecord = DatabaseRecord>(\n table: string, \n data: DatabaseData, \n filters: DatabaseFilters, \n organisationId: string\n ): Promise<T | null> => {\n validateOrganisationContext(organisationId);\n \n try {\n let query = supabase\n .from(table)\n .update(data);\n \n // Add organisation filter (unless super admin)\n if (!isSuperAdmin && ensureOrganisationColumn(table)) {\n query = query.eq('organisation_id', organisationId);\n }\n \n // Add additional filters\n if (filters) {\n Object.entries(filters).forEach(([key, value]) => {\n if (value !== undefined && value !== null) {\n query = query.eq(key, value);\n }\n });\n }\n \n const { data: result, error } = await query.select().single();\n \n if (error) {\n throw error;\n }\n \n return result;\n } catch (error) {\n throw error;\n }\n };\n\n // Secure delete with organisation context\n const secureDelete = async (\n table: string, \n filters: DatabaseFilters, \n organisationId: string\n ): Promise<boolean> => {\n validateOrganisationContext(organisationId);\n \n try {\n let query = supabase\n .from(table)\n .delete();\n \n // Add organisation filter (unless super admin)\n if (!isSuperAdmin && ensureOrganisationColumn(table)) {\n query = query.eq('organisation_id', organisationId);\n }\n \n // Add additional filters\n if (filters) {\n Object.entries(filters).forEach(([key, value]) => {\n if (value !== undefined && value !== null) {\n query = query.eq(key, value);\n }\n });\n }\n \n const { error } = await query;\n \n if (error) {\n throw error;\n }\n \n return true;\n } catch (error) {\n throw error;\n }\n };\n\n // Organisation-scoped query helper\n const queryByOrganisation = async <T extends DatabaseRecord = DatabaseRecord>(\n table: string, \n select: string, \n organisationId: string, \n filters?: DatabaseFilters\n ): Promise<T[]> => {\n return secureQuery<T>({\n table,\n select,\n organisationId,\n filters\n });\n };\n\n return {\n secureQuery,\n secureSingleQuery,\n secureInsert,\n secureUpdate,\n secureDelete,\n queryByOrganisation,\n validateOrganisationContext,\n ensureOrganisationColumn\n };\n};\n\n/**\n * Hook for secure data access\n * @returns Secure data access utilities\n */\nexport const useSecureDataAccess = (): SecureDataAccess => {\n // This would typically get the context from providers\n // For now, we'll create a placeholder that can be used with explicit parameters\n throw new Error('useSecureDataAccess must be used with explicit parameters. Use createSecureDataAccess instead.');\n}; ","/**\n * Storage utilities for pace-core\n * \n * Provides app-segregated file storage with organisation-scoped access\n */\n\nexport * from './types';\nexport * from './config';\nexport * from './helpers';\n\n// Import functions for StorageUtils class\nimport {\n uploadFile,\n getPublicUrl,\n getSignedUrl,\n deleteFile,\n downloadFile,\n listFiles,\n archiveFile,\n generateFilePath,\n generateUniqueFileName,\n extractFileMetadata\n} from './helpers';\n\n// Re-export commonly used functions for convenience\nexport {\n uploadFile,\n getPublicUrl,\n getSignedUrl,\n deleteFile,\n downloadFile,\n listFiles,\n archiveFile,\n generateFilePath,\n generateUniqueFileName,\n extractFileMetadata\n};\n\nexport {\n validateFileSize,\n getFileSizeLimit,\n formatFileSize\n} from './config';\n\n\nexport {\n FILE_SIZE_LIMITS,\n DEFAULT_FILE_SIZE_LIMIT,\n STORAGE_CONFIG,\n APP_PATH_MAPPING\n} from './config';\n\n/**\n * StorageUtils class for convenient access to storage functions\n */\nexport class StorageUtils {\n static generateFilePath = generateFilePath;\n static generateUniqueFileName = generateUniqueFileName;\n static extractFileMetadata = extractFileMetadata;\n static uploadFile = uploadFile;\n static getPublicUrl = getPublicUrl;\n static getSignedUrl = getSignedUrl;\n static deleteFile = deleteFile;\n static downloadFile = downloadFile;\n static listFiles = listFiles;\n static archiveFile = archiveFile;\n}\n"],"mappings":"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","names":["organisationId"]}
1
+ {"version":3,"sources":["../src/index.ts","../src/providers/InactivityProvider.tsx","../src/components/InactivityWarningModal/InactivityWarningModal.tsx","../src/utils/secureDataAccess.ts","../src/utils/storage/index.ts"],"sourcesContent":["/**\n * @file Complete Component Library Export\n * @package @jmruthers/pace-core\n * @module Core\n * @since 0.1.0\n * \n * This file exports the primary components, hooks, and utilities from the PACE Core library.\n * It is the main entry point for developers using the library.\n * \n * @example\n * // Import common components\n * import { Button, Card, useUnifiedAuth } from '@jmruthers/pace-core';\n * \n * // For specialized components, use the complete library import:\n * import { Dialog, NavigationMenu } from '@jmruthers/pace-core/components';\n */\n\n// AUTHENTICATION & AUTHORIZATION\n// Note: Providers are now service-based architecture for better testability and maintainability\nexport { UnifiedAuthProvider, useUnifiedAuth } from './providers/UnifiedAuthProvider';\nexport type { UnifiedAuthProviderProps, UnifiedAuthContextType, UserEventAccess } from './providers/UnifiedAuthProvider';\n\n// Session tracking utility (for manual use if needed)\nexport { useSessionTracking } from './utils/sessionTracking';\n\n// Provider components (using service architecture)\nexport { EventProvider } from './providers/EventProvider';\nexport { OrganisationProvider } from './providers/OrganisationProvider';\nexport { InactivityProvider } from './providers/InactivityProvider';\n\n// Convenience hooks for backward compatibility\nexport { useEvents } from './hooks/useEvents';\nexport { useOrganisations } from './hooks/useOrganisations';\n\n// Service hooks for advanced usage (better performance)\nexport { useEventService } from './hooks/services/useEventService';\nexport { useOrganisationService } from './hooks/services/useOrganisationService';\nexport { useAuthService } from './hooks/services/useAuthService';\nexport { useInactivityService } from './hooks/services/useInactivityService';\nexport { useSessionRestoration } from './hooks/useSessionRestoration';\n\nexport type { \n Organisation, \n OrganisationMembership, \n OrganisationContextType, \n OrganisationProviderProps,\n OrganisationSecurityError \n} from './types/organisation';\n\n// INACTIVITY TRACKING\nexport { InactivityWarningModal } from './components/InactivityWarningModal/InactivityWarningModal';\nexport type { InactivityWarningModalProps } from './components/InactivityWarningModal/InactivityWarningModal';\nexport { useInactivityTracker } from './hooks/useInactivityTracker';\nexport type { UseInactivityTrackerOptions, UseInactivityTrackerReturn } from './hooks/useInactivityTracker';\n\n// RBAC SYSTEM - Consolidated RBAC module\nexport * from './rbac';\n\n// BASIC UI COMPONENTS\nexport { Button } from './components/Button/Button';\nexport type { ButtonProps } from './components/Button/Button';\n\nexport { \n Card, \n CardHeader, \n CardFooter, \n CardTitle, \n CardDescription, \n CardContent,\n CardActions\n} from './components/Card/Card';\nexport type { CardProps } from './components/Card/Card';\n\nexport { Input } from './components/Input/Input';\nexport type { InputProps } from './components/Input/Input';\nexport { Label } from './components/Label/Label';\nexport type { LabelProps } from './components/Label/Label';\n\nexport { Alert, AlertTitle, AlertDescription } from './components/Alert/Alert';\nexport { Avatar, AvatarImage, AvatarFallback } from './components/Avatar/Avatar';\n\nexport { Checkbox } from './components/Checkbox/Checkbox';\nexport { Switch } from './components/Switch/Switch';\nexport type { SwitchProps } from './components/Switch/Switch';\nexport { Progress } from './components/Progress/Progress';\n\n// ADVANCED UI COMPONENTS\nexport {\n Dialog,\n DialogPortal,\n DialogOverlay,\n DialogTrigger,\n DialogClose,\n DialogContent,\n DialogHeader,\n DialogBody,\n DialogFooter,\n DialogTitle,\n DialogDescription,\n} from './components/Dialog/Dialog';\n\n// Dropdown Menu exports\n// DropdownMenu components have been merged into Select components\n\n// Select exports\nexport {\n Select,\n SelectGroup,\n SelectValue,\n SelectTrigger,\n SelectContent,\n SelectLabel,\n SelectItem,\n SelectSeparator,\n} from './components/Select';\n\n// Modal functionality is provided by Dialog components\n\nexport {\n Toast,\n Toaster,\n ToastAction,\n ToastProvider,\n ToastViewport,\n ToastTitle,\n ToastDescription,\n ToastClose,\n} from './components/Toast/Toast';\nexport { useToast } from './hooks/useToast';\nexport type { ToastActionElement, ToastProps } from './components/Toast/Toast';\n\nexport { Tooltip, TooltipTrigger, TooltipContent, TooltipProvider, TooltipRoot } from './components/Tooltip/Tooltip';\n\n// DATA DISPLAY COMPONENTS\nexport {\n DataTable,\n type DataTableProps,\n type DataTableColumn,\n type DataTableAction,\n type DataTableToolbarButton,\n type AggregateConfig,\n type EmptyStateConfig,\n type GetRowId,\n ColumnFactory\n} from './components/DataTable';\n\n// Re-export types from DataTable types\nexport type { DataRecord } from './components/DataTable/types';\n\n// FORM COMPONENTS\nexport { Form } from './components/Form/Form';\nexport { LoginForm } from './components/LoginForm/LoginForm';\nexport type { LoginFormProps } from './components/LoginForm/LoginForm';\n\n// LAYOUT COMPONENTS\nexport { Header } from './components/Header/Header';\nexport { Footer } from './components/Footer/Footer';\nexport type { FooterProps } from './components/Footer/Footer';\n\n// NAVIGATION COMPONENTS\nexport { NavigationMenu } from './components/NavigationMenu/NavigationMenu';\nexport type { NavigationMenuProps, NavigationItem } from './components/NavigationMenu/types';\nexport { UserMenu } from './components/UserMenu/UserMenu';\nexport type { UserMenuProps } from './components/UserMenu/UserMenu';\n\n// Reusable Page/Layout Components\nexport { PaceAppLayout } from './components/PaceAppLayout/PaceAppLayout';\nexport type { PaceAppLayoutProps } from './components/PaceAppLayout/PaceAppLayout';\nexport { PaceLoginPage } from './components/PaceLoginPage/PaceLoginPage';\nexport type { PaceLoginPageProps } from './components/PaceLoginPage/PaceLoginPage';\n\nexport { ProtectedRoute } from './components/ProtectedRoute/ProtectedRoute';\nexport type { ProtectedRouteProps } from './components/ProtectedRoute/ProtectedRoute';\n\n// UTILITY COMPONENTS\nexport { ErrorBoundary } from './components/ErrorBoundary/ErrorBoundary';\nexport { LoadingSpinner } from './components/LoadingSpinner/LoadingSpinner';\nexport { SessionRestorationLoader } from './components/SessionRestorationLoader';\n\n// EVENT MANAGEMENT\nexport { EventSelector } from './components/EventSelector/EventSelector';\n\n// ORGANISATION MANAGEMENT\nexport { OrganisationSelector } from './components/OrganisationSelector/OrganisationSelector';\nexport { useOrganisationPermissions } from './hooks/useOrganisationPermissions';\nexport { useOrganisationSecurity } from './hooks/useOrganisationSecurity';\nexport { createSecureDataAccess } from './utils/secureDataAccess';\n\n// TYPES\nexport type { UserProfile } from './types/organisation';\n\n// AUTHENTICATION FORMS\nexport { PasswordResetForm } from './components/PasswordReset/PasswordResetForm';\nexport { PasswordChangeForm } from './components/PasswordReset/PasswordChangeForm';\n\n// UTILS & HOOKS\nexport { useAppConfig } from './hooks/useAppConfig';\nexport { useEventTheme } from './hooks/useEventTheme';\nexport { cn } from './utils/cn';\nexport { setAppConfig, getAppConfig, getCurrentAppName, getCurrentAppId } from './utils/appConfig';\n\n// FORMATTING UTILITIES\nexport { \n formatDate, \n formatCurrency, \n formatNumber,\n formatPercent,\n formatCompactNumber,\n formatFileSize\n} from './utils/formatting';\n\n// STORAGE UTILITIES\nexport { FileUpload } from './components/FileUpload';\nexport type { FileUploadProps } from './components/FileUpload';\nexport { FileDisplay } from './components/FileDisplay';\nexport type { FileDisplayProps } from './components/FileDisplay';\nexport { FileCategory } from './types/file-reference';\nexport type { FileReference, FileMetadata, FileUploadOptions } from './types/file-reference';\nexport { \n useFileReference, \n useFileReferenceForRecord,\n useFileReferenceById,\n useFilesByCategory\n} from './hooks/useFileReference';\nexport type { \n UseFileReferenceOptions, \n UseFileReferenceReturn, \n UseFileReferenceForRecordReturn \n} from './hooks/useFileReference';\nexport * from './utils/storage';\n\n// Table components\nexport {\n Table,\n TableHeader,\n TableBody,\n TableCaption,\n TableCell,\n TableFooter,\n TableHead,\n TableRow,\n} from './components/Table/Table';\n\n// STYLES & THEMING\nexport * from './styles';\n// Direct export of theming utilities for convenience\nexport { parseAndNormalizeEventColours } from './theming/parseEventColours';\n\n// PUBLIC PAGES\nexport * from './hooks/public';\nexport * from './components/PublicLayout';\n","/**\n * @file Re-export for InactivityProvider\n * @package @jmruthers/pace-core\n * @module Providers\n * @since 0.1.0\n * \n * Re-exports the service-based InactivityProvider for backward compatibility.\n */\n\nexport { InactivityServiceProvider as InactivityProvider } from './services/InactivityServiceProvider';\nexport type { InactivityServiceProviderProps as InactivityProviderProps, InactivityServiceContextType as InactivityContextType } from './services/InactivityServiceProvider';\n\n// Re-export hook\nexport { useInactivityService as useInactivity } from '../hooks/services/useInactivityService';\n\n","/**\n * @file Inactivity Warning Modal\n * @package @jmruthers/pace-core\n * @module Components/InactivityWarningModal\n * @since 0.1.0\n *\n * A modal dialog that warns users about impending auto-logout due to inactivity.\n * Provides a countdown timer and action buttons to either stay signed in or sign out immediately.\n *\n * Features:\n * - Accessible modal dialog with focus management\n * - Live countdown timer with 1-second updates\n * - Clear action buttons (Stay Signed In / Sign Out Now)\n * - Keyboard navigation support (Escape to stay signed in)\n * - Cross-tab awareness and synchronization\n * - Tailwind v4 styling with pace-core theme tokens\n * - Production-safe with no arbitrary bracket classes\n *\n * @example\n * ```tsx\n * <InactivityWarningModal\n * isOpen={showWarning}\n * timeRemaining={45}\n * onStaySignedIn={() => setShowWarning(false)}\n * onSignOutNow={() => signOut()}\n * />\n * ```\n *\n * @accessibility\n * - WCAG 2.1 AA compliant\n * - Focus trap within modal content\n * - Screen reader announcements for countdown changes\n * - Keyboard navigation support\n * - Clear visual hierarchy and contrast\n * - Escape key to stay signed in (safe default)\n *\n * @performance\n * - Efficient countdown updates (1-second intervals)\n * - Minimal re-renders with stable references\n * - Memory leak prevention with cleanup\n * - Optimized timer management\n *\n * @dependencies\n * - React 18+ - Hooks and effects\n * - Dialog components - Modal functionality\n * - Tailwind CSS v4 - Styling\n */\n\nimport React, { useEffect, useState, useCallback } from 'react';\nimport { Dialog, DialogContent, DialogHeader, DialogTitle, DialogDescription } from '../Dialog/Dialog';\nimport { Button } from '../Button/Button';\nimport { Clock, AlertTriangle } from 'lucide-react';\n\nexport interface InactivityWarningModalProps {\n /** Whether the modal is open */\n isOpen: boolean;\n /** Time remaining in seconds before auto-logout */\n timeRemaining: number;\n /** Callback when user chooses to stay signed in */\n onStaySignedIn: () => void;\n /** Callback when user chooses to sign out immediately */\n onSignOutNow: () => void;\n /** Optional custom title */\n title?: string;\n /** Optional custom description */\n description?: string;\n /** Optional custom className */\n className?: string;\n}\n\nexport function InactivityWarningModal({\n isOpen,\n timeRemaining,\n onStaySignedIn,\n onSignOutNow,\n title = \"Session Timeout Warning\",\n description = \"You've been inactive for a while. Your session will expire soon for security reasons.\",\n className\n}: InactivityWarningModalProps) {\n const [displayTime, setDisplayTime] = useState(timeRemaining);\n\n // Update display time when timeRemaining prop changes\n useEffect(() => {\n setDisplayTime(timeRemaining);\n }, [timeRemaining]);\n\n // Format time for display (MM:SS)\n const formatTime = useCallback((seconds: number) => {\n const mins = Math.floor(seconds / 60);\n const secs = seconds % 60;\n return `${mins.toString().padStart(2, '0')}:${secs.toString().padStart(2, '0')}`;\n }, []);\n\n\n\n\n return (\n <Dialog open={isOpen} onOpenChange={(open) => !open && onStaySignedIn()}>\n <DialogContent \n className={`sm:max-w-md ${className || ''}`}\n preventCloseOnEscape={false}\n preventCloseOnOutsideClick={true}\n data-testid=\"inactivity-warning-modal\"\n >\n <DialogHeader>\n <div className=\"flex items-center gap-3\">\n <div className=\"flex-shrink-0\">\n <AlertTriangle className=\"h-6 w-6 text-acc-600\" />\n </div>\n <div>\n <DialogTitle className=\"text-lg font-semibold text-main-900\">\n {title}\n </DialogTitle>\n </div>\n </div>\n <DialogDescription className=\"text-main-700 mt-2\">\n {description}\n </DialogDescription>\n </DialogHeader>\n\n <div className=\"space-y-6\">\n {/* Countdown Timer */}\n <div className=\"text-center\">\n <div className=\"inline-flex items-center gap-2 px-4 py-3 bg-acc-50 border border-acc-200 rounded-lg\">\n <Clock className=\"h-5 w-5 text-acc-600\" />\n <span className=\"text-2xl font-mono font-bold text-acc-700\">\n {formatTime(displayTime)}\n </span>\n </div>\n <p className=\"text-sm text-main-600 mt-2\">\n Time remaining before automatic logout\n </p>\n </div>\n\n {/* Action Buttons */}\n <div className=\"flex flex-col sm:flex-row gap-3\">\n <Button\n onClick={onStaySignedIn}\n className=\"flex-1 bg-main-600 hover:bg-main-700 text-main-50\"\n size=\"lg\"\n >\n Stay Signed In\n </Button>\n <Button\n onClick={onSignOutNow}\n variant=\"outline\"\n className=\"flex-1 border-acc-300 text-acc-700 hover:bg-acc-50\"\n size=\"lg\"\n >\n Sign Out Now\n </Button>\n </div>\n\n {/* Additional Info */}\n <div className=\"text-xs text-main-500 text-center\">\n <p>\n For security reasons, you'll be automatically signed out after 30 minutes of inactivity.\n </p>\n </div>\n </div>\n </DialogContent>\n </Dialog>\n );\n}\n","/**\n * @file Secure Data Access Utility\n * @package @jmruthers/pace-core\n * @module Utils/SecureDataAccess\n * @since 0.4.0\n *\n * Secure data access utilities that enforce organisation context for all database operations.\n * Prevents data leakage between organisations and ensures proper access validation.\n */\n\nimport type { SupabaseClient } from '@supabase/supabase-js';\n\n// Generic database record type\nexport interface DatabaseRecord {\n id: string;\n organisation_id: string;\n [key: string]: unknown;\n}\n\n// Generic data for insert/update operations\nexport interface DatabaseData {\n [key: string]: unknown;\n}\n\n// Generic filters for queries\nexport interface DatabaseFilters {\n [key: string]: unknown;\n}\n\n// Secure query options\nexport interface SecureQueryOptions {\n table: string;\n select: string;\n organisationId: string;\n filters?: DatabaseFilters;\n orderBy?: string;\n limit?: number;\n offset?: number;\n}\n\nexport interface SecureDataAccess {\n // Secure query methods\n secureQuery: <T extends DatabaseRecord = DatabaseRecord>(options: SecureQueryOptions) => Promise<T[]>;\n secureSingleQuery: <T extends DatabaseRecord = DatabaseRecord>(options: SecureQueryOptions) => Promise<T | null>;\n \n // Secure mutation methods\n secureInsert: <T extends DatabaseRecord = DatabaseRecord>(table: string, data: DatabaseData, organisationId: string) => Promise<T | null>;\n secureUpdate: <T extends DatabaseRecord = DatabaseRecord>(table: string, data: DatabaseData, filters: DatabaseFilters, organisationId: string) => Promise<T | null>;\n secureDelete: (table: string, filters: DatabaseFilters, organisationId: string) => Promise<boolean>;\n \n // Organisation-scoped queries\n queryByOrganisation: <T extends DatabaseRecord = DatabaseRecord>(table: string, select: string, organisationId: string, filters?: DatabaseFilters) => Promise<T[]>;\n \n // Validation helpers\n validateOrganisationContext: (organisationId: string) => void;\n ensureOrganisationColumn: (table: string) => boolean;\n}\n\nexport interface SecureQueryBuilder {\n table: string;\n select: string;\n organisationId: string;\n filters?: DatabaseFilters;\n orderBy?: string;\n limit?: number;\n offset?: number;\n}\n\n/**\n * Create a secure data access instance\n * @param supabase - Supabase client instance\n * @param organisationId - Current organisation context\n * @param isSuperAdmin - Whether user has super admin privileges\n * @returns Secure data access utilities\n */\nexport const createSecureDataAccess = (\n supabase: SupabaseClient,\n organisationId: string,\n isSuperAdmin: boolean = false\n): SecureDataAccess => {\n \n // Validate organisation context\n const validateOrganisationContext = (orgId: string): void => {\n if (!orgId) {\n throw new Error('Organisation context is required for secure data access');\n }\n \n if (!isSuperAdmin && !orgId) {\n throw new Error('Organisation context is mandatory for non-super admin users');\n }\n };\n\n // Check if table has organisation_id column\n const ensureOrganisationColumn = (table: string): boolean => {\n // This is a simplified check - in production you might want to cache this\n const tablesWithOrganisation = [\n 'event', 'organisation_settings',\n 'rbac_event_app_roles', 'rbac_organisation_roles',\n // SECURITY: Phase 2 additions - complete organisation table mapping\n 'organisation_audit_log', 'organisation_invitations', 'organisation_app_access',\n // SECURITY: Emergency additions for Phase 1 fixes\n 'cake_meal', 'cake_mealtype', 'pace_person', 'pace_member',\n // SECURITY: Phase 3A additions - medical and personal data\n 'medi_profile', 'medi_condition', 'medi_diet', 'medi_action_plan', 'medi_profile_versions',\n 'pace_consent', 'pace_contact', 'pace_id_documents', 'pace_qualifications',\n 'form_responses', 'form_response_values', 'forms',\n // SECURITY: Phase 3B additions - remaining critical tables\n 'invoice', 'line_item', 'credit_balance', 'payment_method',\n 'form_contexts', 'form_field_config', 'form_fields',\n 'cake_delivery', 'cake_diettype', 'cake_diner', 'cake_dish', 'cake_item', \n 'cake_logistics', 'cake_mealplan', 'cake_package', 'cake_recipe', 'cake_supplier', \n 'cake_supply', 'cake_unit', 'event_app_access', 'base_application', 'base_questions'\n ];\n \n return tablesWithOrganisation.includes(table);\n };\n\n // Build secure query with organisation context\n const buildSecureQuery = (options: SecureQueryBuilder) => {\n const { table, select, organisationId: orgId, filters, orderBy, limit, offset } = options;\n \n validateOrganisationContext(orgId);\n \n let query = supabase\n .from(table)\n .select(select);\n \n // Add organisation filter (unless super admin)\n if (!isSuperAdmin && ensureOrganisationColumn(table)) {\n query = query.eq('organisation_id', orgId);\n }\n \n // Add additional filters\n if (filters) {\n Object.entries(filters).forEach(([key, value]) => {\n if (value !== undefined && value !== null) {\n // Handle qualified column names (e.g., 'users.role')\n const columnName = key.includes('.') ? key.split('.').pop()! : key;\n query = query.eq(columnName, value);\n }\n });\n }\n \n // Add ordering\n if (orderBy) {\n // Only use the column name, not a qualified name\n const orderByColumn = orderBy.split('.').pop();\n if (orderByColumn) {\n query = query.order(orderByColumn);\n }\n }\n \n // Add pagination\n if (limit) {\n query = query.limit(limit);\n }\n \n if (offset) {\n query = query.range(offset, offset + (limit || 10) - 1);\n }\n \n return query;\n };\n\n // Secure query for multiple results\n const secureQuery = async <T extends DatabaseRecord = DatabaseRecord>(options: SecureQueryOptions): Promise<T[]> => {\n const { table, select, organisationId: orgId, filters, orderBy, limit, offset } = options;\n \n try {\n const query = buildSecureQuery({\n table,\n select,\n organisationId: orgId,\n filters,\n orderBy,\n limit,\n offset\n });\n \n const { data, error } = await query;\n \n if (error) {\n throw error;\n }\n \n // Ensure data is an array and not an error type\n if (Array.isArray(data)) {\n return data as unknown as T[];\n }\n \n return [];\n } catch (error) {\n throw error;\n }\n };\n\n // Secure query for single result\n const secureSingleQuery = async <T extends DatabaseRecord = DatabaseRecord>(options: SecureQueryOptions): Promise<T | null> => {\n const { table, select, organisationId: orgId, filters, orderBy, limit, offset } = options;\n \n try {\n const query = buildSecureQuery({\n table,\n select,\n organisationId: orgId,\n filters,\n orderBy,\n limit,\n offset\n });\n \n const { data, error } = await query.single();\n \n if (error) {\n if (error.code === 'PGRST116') {\n // No rows returned\n return null;\n }\n throw error;\n }\n \n // Ensure data is not an error type\n if (data && typeof data === 'object' && !('code' in data)) {\n return data as unknown as T;\n }\n \n return null;\n } catch (error) {\n throw error;\n }\n };\n\n // Secure insert with organisation context\n const secureInsert = async <T extends DatabaseRecord = DatabaseRecord>(\n table: string, \n data: DatabaseData, \n organisationId: string\n ): Promise<T | null> => {\n validateOrganisationContext(organisationId);\n \n try {\n const insertData = {\n ...data,\n organisation_id: organisationId\n };\n \n const { data: result, error } = await supabase\n .from(table)\n .insert(insertData)\n .select()\n .single();\n \n if (error) {\n throw error;\n }\n \n return result;\n } catch (error) {\n throw error;\n }\n };\n\n // Secure update with organisation context\n const secureUpdate = async <T extends DatabaseRecord = DatabaseRecord>(\n table: string, \n data: DatabaseData, \n filters: DatabaseFilters, \n organisationId: string\n ): Promise<T | null> => {\n validateOrganisationContext(organisationId);\n \n try {\n let query = supabase\n .from(table)\n .update(data);\n \n // Add organisation filter (unless super admin)\n if (!isSuperAdmin && ensureOrganisationColumn(table)) {\n query = query.eq('organisation_id', organisationId);\n }\n \n // Add additional filters\n if (filters) {\n Object.entries(filters).forEach(([key, value]) => {\n if (value !== undefined && value !== null) {\n query = query.eq(key, value);\n }\n });\n }\n \n const { data: result, error } = await query.select().single();\n \n if (error) {\n throw error;\n }\n \n return result;\n } catch (error) {\n throw error;\n }\n };\n\n // Secure delete with organisation context\n const secureDelete = async (\n table: string, \n filters: DatabaseFilters, \n organisationId: string\n ): Promise<boolean> => {\n validateOrganisationContext(organisationId);\n \n try {\n let query = supabase\n .from(table)\n .delete();\n \n // Add organisation filter (unless super admin)\n if (!isSuperAdmin && ensureOrganisationColumn(table)) {\n query = query.eq('organisation_id', organisationId);\n }\n \n // Add additional filters\n if (filters) {\n Object.entries(filters).forEach(([key, value]) => {\n if (value !== undefined && value !== null) {\n query = query.eq(key, value);\n }\n });\n }\n \n const { error } = await query;\n \n if (error) {\n throw error;\n }\n \n return true;\n } catch (error) {\n throw error;\n }\n };\n\n // Organisation-scoped query helper\n const queryByOrganisation = async <T extends DatabaseRecord = DatabaseRecord>(\n table: string, \n select: string, \n organisationId: string, \n filters?: DatabaseFilters\n ): Promise<T[]> => {\n return secureQuery<T>({\n table,\n select,\n organisationId,\n filters\n });\n };\n\n return {\n secureQuery,\n secureSingleQuery,\n secureInsert,\n secureUpdate,\n secureDelete,\n queryByOrganisation,\n validateOrganisationContext,\n ensureOrganisationColumn\n };\n};\n\n/**\n * Hook for secure data access\n * @returns Secure data access utilities\n */\nexport const useSecureDataAccess = (): SecureDataAccess => {\n // This would typically get the context from providers\n // For now, we'll create a placeholder that can be used with explicit parameters\n throw new Error('useSecureDataAccess must be used with explicit parameters. Use createSecureDataAccess instead.');\n}; ","/**\n * Storage utilities for pace-core\n * \n * Provides app-segregated file storage with organisation-scoped access\n */\n\nexport * from './types';\nexport * from './config';\nexport * from './helpers';\n\n// Import functions for StorageUtils class\nimport {\n uploadFile,\n getPublicUrl,\n getSignedUrl,\n deleteFile,\n downloadFile,\n listFiles,\n archiveFile,\n generateFilePath,\n generateUniqueFileName,\n extractFileMetadata\n} from './helpers';\n\n// Re-export commonly used functions for convenience\nexport {\n uploadFile,\n getPublicUrl,\n getSignedUrl,\n deleteFile,\n downloadFile,\n listFiles,\n archiveFile,\n generateFilePath,\n generateUniqueFileName,\n extractFileMetadata\n};\n\nexport {\n validateFileSize,\n getFileSizeLimit,\n formatFileSize\n} from './config';\n\n\nexport {\n FILE_SIZE_LIMITS,\n DEFAULT_FILE_SIZE_LIMIT,\n STORAGE_CONFIG,\n APP_PATH_MAPPING\n} from './config';\n\n/**\n * StorageUtils class for convenient access to storage functions\n */\nexport class StorageUtils {\n static generateFilePath = generateFilePath;\n static generateUniqueFileName = generateUniqueFileName;\n static extractFileMetadata = extractFileMetadata;\n static uploadFile = uploadFile;\n static getPublicUrl = getPublicUrl;\n static getSignedUrl = getSignedUrl;\n static deleteFile = deleteFile;\n static downloadFile = downloadFile;\n static listFiles = listFiles;\n static archiveFile = archiveFile;\n}\n"],"mappings":"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","names":["organisationId"]}
@@ -1,6 +1,6 @@
1
1
  export { a as UnifiedAuthContextType, c as UnifiedAuthProvider, b as UnifiedAuthProviderProps, U as UserEventAccess, u as useUnifiedAuth } from './UnifiedAuthProvider-BVKmQd9u.js';
2
- import { A as AuthService } from './AuthService-D4646R4b.js';
3
- export { a as EventContextType, b as EventServiceContext, E as EventServiceContextType, d as EventServiceProvider, c as EventServiceProviderProps, i as InactivityServiceContext, I as InactivityServiceContextType, k as InactivityServiceProvider, j as InactivityServiceProviderProps, e as OrganisationServiceContext, O as OrganisationServiceContextType, g as OrganisationServiceProvider, f as OrganisationServiceProviderProps, u as useEventService, l as useInactivityService, h as useOrganisationService } from './AuthService-D4646R4b.js';
2
+ import { A as AuthService } from './AuthService-DYuQPJj6.js';
3
+ export { a as EventContextType, b as EventServiceContext, E as EventServiceContextType, d as EventServiceProvider, c as EventServiceProviderProps, i as InactivityServiceContext, I as InactivityServiceContextType, k as InactivityServiceProvider, j as InactivityServiceProviderProps, e as OrganisationServiceContext, O as OrganisationServiceContextType, g as OrganisationServiceProvider, f as OrganisationServiceProviderProps, u as useEventService, l as useInactivityService, h as useOrganisationService } from './AuthService-DYuQPJj6.js';
4
4
  import * as react_jsx_runtime from 'react/jsx-runtime';
5
5
  import React__default from 'react';
6
6
  import { SupabaseClient } from '@supabase/supabase-js';
package/dist/providers.js CHANGED
@@ -1,4 +1,4 @@
1
- import "./chunk-NZ32EONV.js";
1
+ import "./chunk-QWNJCQXZ.js";
2
2
  import {
3
3
  AuthServiceContext,
4
4
  AuthServiceProvider,
@@ -14,10 +14,9 @@ import {
14
14
  useInactivityService,
15
15
  useOrganisationService,
16
16
  useUnifiedAuth
17
- } from "./chunk-BHWIUEYH.js";
17
+ } from "./chunk-ZBLK676C.js";
18
18
  import "./chunk-BDZUMRBD.js";
19
19
  import "./chunk-UJI6WSMD.js";
20
- import "./chunk-SMJZMKYN.js";
21
20
  import "./chunk-PLDDJCW6.js";
22
21
  export {
23
22
  AuthServiceContext,
@@ -30,7 +30,7 @@ import {
30
30
  withAccessLevelGuard,
31
31
  withPermissionGuard,
32
32
  withRoleGuard
33
- } from "../chunk-TDNI6ZWL.js";
33
+ } from "../chunk-IJOZZOGT.js";
34
34
  import {
35
35
  useAccessLevel,
36
36
  useCachedPermissions,
@@ -42,7 +42,7 @@ import {
42
42
  useRBAC,
43
43
  useResolvedScope,
44
44
  useRoleManagement
45
- } from "../chunk-D6BOFXYR.js";
45
+ } from "../chunk-35ZDPMBM.js";
46
46
  import {
47
47
  CACHE_PATTERNS,
48
48
  RBACCache,
@@ -72,15 +72,14 @@ import {
72
72
  getGlobalAuditManager,
73
73
  setGlobalAuditManager
74
74
  } from "../chunk-3DBFLLLU.js";
75
- import "../chunk-B4GZ2BXO.js";
76
- import "../chunk-CGURJ27Z.js";
77
- import "../chunk-ZYJ6O5CA.js";
78
- import "../chunk-NZ32EONV.js";
79
- import "../chunk-BHWIUEYH.js";
75
+ import "../chunk-NZGLXZGP.js";
76
+ import "../chunk-4MXVZVNS.js";
77
+ import "../chunk-C43QIDN3.js";
78
+ import "../chunk-QWNJCQXZ.js";
79
+ import "../chunk-ZBLK676C.js";
80
80
  import "../chunk-JCQZ6LA7.js";
81
81
  import "../chunk-BDZUMRBD.js";
82
82
  import "../chunk-UJI6WSMD.js";
83
- import "../chunk-SMJZMKYN.js";
84
83
  import "../chunk-PLDDJCW6.js";
85
84
  export {
86
85
  ALL_PERMISSIONS,
@@ -1,4 +1,4 @@
1
- export { ColorPalette, ColorShade, PaletteData, applyPalette, clearPalette, generateSSRThemeCSS, getCurrentThemeData, isDynamicThemingActive } from '../theming/runtime.js';
1
+ export { ColorPalette, ColorShade, PaletteData, applyPalette, clearPalette, generateSSRThemeCSS, getCurrentThemeData, isDynamicThemingActive, parseAndNormalizeEventColours } from '../theming/runtime.js';
2
2
 
3
3
  /**
4
4
  * @file Styles Index