@stackcraftmx/calcita 0.0.0-stage → 0.23.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/LICENSE +110 -0
- package/README.md +611 -2
- package/cli/askQuestions.js +63 -0
- package/cli/calcita.js +150 -0
- package/cli/makeComponent.js +50 -0
- package/cli/makeForm.js +68 -0
- package/cli/makeModule.js +78 -0
- package/cli/makePage.js +62 -0
- package/cli/names.js +64 -0
- package/cli/newProject.js +103 -0
- package/cli/packageVersions.js +38 -0
- package/cli/projectAnswers.js +145 -0
- package/cli/projectConfig.js +38 -0
- package/cli/projectFiles.js +126 -0
- package/cli/screenLabels.js +41 -0
- package/cli/templateFiles.js +186 -0
- package/cli/templates/component/core/__ComponentName__.jsx.tpl +23 -0
- package/cli/templates/component/module/__ComponentName__.jsx.tpl +21 -0
- package/cli/templates/form/formik/__FormName__.jsx.tpl +50 -0
- package/cli/templates/form/hookForm/__FormName__.jsx.tpl +53 -0
- package/cli/templates/form/shared/__formName__Schema.js.tpl +20 -0
- package/cli/templates/form/shared/__formName__Texts.js.tpl +6 -0
- package/cli/templates/module/__Name__Page.jsx.tpl +75 -0
- package/cli/templates/module/__name__Api.js.tpl +39 -0
- package/cli/templates/module/__name__Texts.js.tpl +27 -0
- package/cli/templates/module/menu.js.tpl +21 -0
- package/cli/templates/module/routes.js.tpl +7 -0
- package/cli/templates/moduleServer/__name__Server.js.tpl +68 -0
- package/cli/templates/page/__PageName__Page.jsx.tpl +22 -0
- package/cli/templates/page/__pageName__PageTexts.js.tpl +23 -0
- package/cli/templates/project/README.md.tpl +55 -0
- package/cli/templates/project/dot-gitignore.tpl +11 -0
- package/cli/templates/project/index.html.tpl +20 -0
- package/cli/templates/project/jsconfig.json.tpl +16 -0
- package/cli/templates/project/pnpm-workspace.yaml.tpl +5 -0
- package/cli/templates/project/public/favicon.svg +1 -0
- package/cli/templates/project/public/icons/apple-touch-icon.png +0 -0
- package/cli/templates/project/public/icons/icon-192.png +0 -0
- package/cli/templates/project/public/icons/icon-512-maskable.png +0 -0
- package/cli/templates/project/public/icons/icon-512.png +0 -0
- package/cli/templates/project/public/manifest.webmanifest.tpl +17 -0
- package/cli/templates/project/src/app/AppProviders.jsx.tpl +102 -0
- package/cli/templates/project/src/app/AppShell.jsx.tpl +87 -0
- package/cli/templates/project/src/app/appRouter.jsx.tpl +49 -0
- package/cli/templates/project/src/app/appSettings.js.tpl +13 -0
- package/cli/templates/project/src/app/appTexts.js.tpl +15 -0
- package/cli/templates/project/src/app/combineTexts.js.tpl +31 -0
- package/cli/templates/project/src/app/i18n.js.tpl +19 -0
- package/cli/templates/project/src/app/shellTexts.js.tpl +16 -0
- package/cli/templates/project/src/core/AppLogo.jsx.tpl +12 -0
- package/cli/templates/project/src/core/accountConnector.js.tpl +36 -0
- package/cli/templates/project/src/core/apiClient.js.tpl +15 -0
- package/cli/templates/project/src/core/appPaths.js.tpl +11 -0
- package/cli/templates/project/src/core/index.js.tpl +8 -0
- package/cli/templates/project/src/fakeServer/networkDelay.js.tpl +40 -0
- package/cli/templates/project/src/fakeServer/serverText.js.tpl +20 -0
- package/cli/templates/project/src/main.jsx.tpl +24 -0
- package/cli/templates/project/src/modules/auth/ForgotPasswordPage.jsx.tpl +14 -0
- package/cli/templates/project/src/modules/auth/ResetPasswordPage.jsx.tpl +15 -0
- package/cli/templates/project/src/modules/auth/SignInPage.jsx.tpl +29 -0
- package/cli/templates/project/src/modules/auth/authTexts.js.tpl +6 -0
- package/cli/templates/project/src/modules/auth/routes.js.tpl +11 -0
- package/cli/templates/project/src/modules/home/HomePage.jsx.tpl +38 -0
- package/cli/templates/project/src/modules/home/homeTexts.js.tpl +29 -0
- package/cli/templates/project/src/modules/home/menu.js.tpl +17 -0
- package/cli/templates/project/src/modules/home/routes.js.tpl +4 -0
- package/cli/templates/project/src/modules/profile/ProfilePage.jsx.tpl +13 -0
- package/cli/templates/project/src/modules/profile/routes.js.tpl +6 -0
- package/cli/templates/project/vite.config.js.tpl +27 -0
- package/dist/DataTable/AuditTrailDialog.js +40 -0
- package/dist/DataTable/AuditTrailDialog.js.map +1 -0
- package/dist/DataTable/AuditTrailTable.js +87 -0
- package/dist/DataTable/AuditTrailTable.js.map +1 -0
- package/dist/DataTable/ColumnFilters/HeaderFilterPopover.js +71 -0
- package/dist/DataTable/ColumnFilters/HeaderFilterPopover.js.map +1 -0
- package/dist/DataTable/ColumnFilters/MultiSelectColumnFilter.js +50 -0
- package/dist/DataTable/ColumnFilters/MultiSelectColumnFilter.js.map +1 -0
- package/dist/DataTable/ColumnFilters/SortableFilterHeader.js +54 -0
- package/dist/DataTable/ColumnFilters/SortableFilterHeader.js.map +1 -0
- package/dist/DataTable/ColumnFilters/TextColumnFilter.js +24 -0
- package/dist/DataTable/ColumnFilters/TextColumnFilter.js.map +1 -0
- package/dist/DataTable/EmptyState.js +22 -0
- package/dist/DataTable/EmptyState.js.map +1 -0
- package/dist/DataTable/FilterChips.js +39 -0
- package/dist/DataTable/FilterChips.js.map +1 -0
- package/dist/DataTable/GoToPage.js +62 -0
- package/dist/DataTable/GoToPage.js.map +1 -0
- package/dist/DataTable/ServerTable.js +407 -0
- package/dist/DataTable/ServerTable.js.map +1 -0
- package/dist/DataTable/buildChipConfig.js +27 -0
- package/dist/DataTable/buildChipConfig.js.map +1 -0
- package/dist/DataTable/columns.js +122 -0
- package/dist/DataTable/columns.js.map +1 -0
- package/dist/DataTable/filterContext.js +15 -0
- package/dist/DataTable/filterContext.js.map +1 -0
- package/dist/DataTable/serverTableParams.js +19 -0
- package/dist/DataTable/serverTableParams.js.map +1 -0
- package/dist/DataTable/tableMachine.js +87 -0
- package/dist/DataTable/tableMachine.js.map +1 -0
- package/dist/DataTable/useDebouncedFilter.js +29 -0
- package/dist/DataTable/useDebouncedFilter.js.map +1 -0
- package/dist/DataTable/useTableState.js +132 -0
- package/dist/DataTable/useTableState.js.map +1 -0
- package/dist/access/Can.js +9 -0
- package/dist/access/Can.js.map +1 -0
- package/dist/access/PermissionMatrix.js +83 -0
- package/dist/access/PermissionMatrix.js.map +1 -0
- package/dist/access/RequireAccess.js +14 -0
- package/dist/access/RequireAccess.js.map +1 -0
- package/dist/access/accessRules.js +49 -0
- package/dist/access/accessRules.js.map +1 -0
- package/dist/access/permissionGroups.js +43 -0
- package/dist/access/permissionGroups.js.map +1 -0
- package/dist/access/useCan.js +12 -0
- package/dist/access/useCan.js.map +1 -0
- package/dist/account/AccountProvider.js +58 -0
- package/dist/account/AccountProvider.js.map +1 -0
- package/dist/account/AccountSecuritySection.js +81 -0
- package/dist/account/AccountSecuritySection.js.map +1 -0
- package/dist/account/DemoTotpCodeButton.js +26 -0
- package/dist/account/DemoTotpCodeButton.js.map +1 -0
- package/dist/account/ForgotPasswordScreen.js +26 -0
- package/dist/account/ForgotPasswordScreen.js.map +1 -0
- package/dist/account/ProfileScreen.js +108 -0
- package/dist/account/ProfileScreen.js.map +1 -0
- package/dist/account/ResetPasswordScreen.js +57 -0
- package/dist/account/ResetPasswordScreen.js.map +1 -0
- package/dist/account/SignInScreen.js +101 -0
- package/dist/account/SignInScreen.js.map +1 -0
- package/dist/account/accountConnector.js +31 -0
- package/dist/account/accountConnector.js.map +1 -0
- package/dist/account/demo/createDemoAccountConnector.js +368 -0
- package/dist/account/demo/createDemoAccountConnector.js.map +1 -0
- package/dist/account/demo/totp.js +61 -0
- package/dist/account/demo/totp.js.map +1 -0
- package/dist/account/restAccountConnector.js +117 -0
- package/dist/account/restAccountConnector.js.map +1 -0
- package/dist/account-demo.js +12 -0
- package/dist/account-demo.js.map +1 -0
- package/dist/account.js +25 -0
- package/dist/account.js.map +1 -0
- package/dist/adapters/i18next.js +7 -0
- package/dist/adapters/i18next.js.map +1 -0
- package/dist/adapters/nextNavigation.js +36 -0
- package/dist/adapters/nextNavigation.js.map +1 -0
- package/dist/adapters/reactRouter.js +7 -0
- package/dist/adapters/reactRouter.js.map +1 -0
- package/dist/adapters/reactRouterRoutes.js +48 -0
- package/dist/adapters/reactRouterRoutes.js.map +1 -0
- package/dist/api/ApiError.js +58 -0
- package/dist/api/ApiError.js.map +1 -0
- package/dist/api/createApiClient.js +226 -0
- package/dist/api/createApiClient.js.map +1 -0
- package/dist/api/staleChunks.js +47 -0
- package/dist/api/staleChunks.js.map +1 -0
- package/dist/appShell/AccountMenu.js +86 -0
- package/dist/appShell/AccountMenu.js.map +1 -0
- package/dist/appShell/AppLayout.js +493 -0
- package/dist/appShell/AppLayout.js.map +1 -0
- package/dist/appShell/AppearanceSettings.js +93 -0
- package/dist/appShell/AppearanceSettings.js.map +1 -0
- package/dist/appShell/AuthLayout.js +44 -0
- package/dist/appShell/AuthLayout.js.map +1 -0
- package/dist/appShell/BarActionButton.js +31 -0
- package/dist/appShell/BarActionButton.js.map +1 -0
- package/dist/appShell/BarActions.js +94 -0
- package/dist/appShell/BarActions.js.map +1 -0
- package/dist/appShell/BarCapsule.js +35 -0
- package/dist/appShell/BarCapsule.js.map +1 -0
- package/dist/appShell/HeaderTools.js +53 -0
- package/dist/appShell/HeaderTools.js.map +1 -0
- package/dist/appShell/MobileTabBar.js +346 -0
- package/dist/appShell/MobileTabBar.js.map +1 -0
- package/dist/appShell/SettingsMenu.js +41 -0
- package/dist/appShell/SettingsMenu.js.map +1 -0
- package/dist/appShell/SideMenu.js +217 -0
- package/dist/appShell/SideMenu.js.map +1 -0
- package/dist/appShell/SideMenuEntry.js +140 -0
- package/dist/appShell/SideMenuEntry.js.map +1 -0
- package/dist/appShell/SubmenuActionsMenu.js +71 -0
- package/dist/appShell/SubmenuActionsMenu.js.map +1 -0
- package/dist/appShell/TabBarEditor.js +55 -0
- package/dist/appShell/TabBarEditor.js.map +1 -0
- package/dist/appShell/TopMenu.js +80 -0
- package/dist/appShell/TopMenu.js.map +1 -0
- package/dist/appShell/appMenuContext.js +11 -0
- package/dist/appShell/appMenuContext.js.map +1 -0
- package/dist/appShell/barActionsSlot.js +26 -0
- package/dist/appShell/barActionsSlot.js.map +1 -0
- package/dist/appShell/barMenuPlacement.js +33 -0
- package/dist/appShell/barMenuPlacement.js.map +1 -0
- package/dist/appShell/menuItemText.js +33 -0
- package/dist/appShell/menuItemText.js.map +1 -0
- package/dist/appShell/pageTitle.js +45 -0
- package/dist/appShell/pageTitle.js.map +1 -0
- package/dist/appShell/shellSizes.js +38 -0
- package/dist/appShell/shellSizes.js.map +1 -0
- package/dist/appShell/tabBarRule.js +12 -0
- package/dist/appShell/tabBarRule.js.map +1 -0
- package/dist/appShell/tabBarScroll.js +23 -0
- package/dist/appShell/tabBarScroll.js.map +1 -0
- package/dist/appShell/useDrawerCollapsed.js +29 -0
- package/dist/appShell/useDrawerCollapsed.js.map +1 -0
- package/dist/appShell/useFittingActionCount.js +45 -0
- package/dist/appShell/useFittingActionCount.js.map +1 -0
- package/dist/appShell/usePinnedMobileTabs.js +32 -0
- package/dist/appShell/usePinnedMobileTabs.js.map +1 -0
- package/dist/appShell/useTabBarMinimized.js +33 -0
- package/dist/appShell/useTabBarMinimized.js.map +1 -0
- package/dist/auth/PasswordChecklist.js +44 -0
- package/dist/auth/PasswordChecklist.js.map +1 -0
- package/dist/auth/passwordRules.js +43 -0
- package/dist/auth/passwordRules.js.map +1 -0
- package/dist/calendar/EventCalendar.js +138 -0
- package/dist/calendar/EventCalendar.js.map +1 -0
- package/dist/calendar.js +6 -0
- package/dist/calendar.js.map +1 -0
- package/dist/charts.js +7 -0
- package/dist/charts.js.map +1 -0
- package/dist/date-pickers.js +8 -0
- package/dist/date-pickers.js.map +1 -0
- package/dist/datePickers/DateInput.js +75 -0
- package/dist/datePickers/DateInput.js.map +1 -0
- package/dist/datePickers/FormDateField.js +12 -0
- package/dist/datePickers/FormDateField.js.map +1 -0
- package/dist/dates.js +25 -0
- package/dist/dates.js.map +1 -0
- package/dist/dictionaries/dictionaries.js +48 -0
- package/dist/dictionaries/dictionaries.js.map +1 -0
- package/dist/downloads/DownloadManager.js +201 -0
- package/dist/downloads/DownloadManager.js.map +1 -0
- package/dist/downloads/downloadQueue.js +54 -0
- package/dist/downloads/downloadQueue.js.map +1 -0
- package/dist/downloads/downloadsMachine.js +77 -0
- package/dist/downloads/downloadsMachine.js.map +1 -0
- package/dist/excel/reportWorkbook.js +299 -0
- package/dist/excel/reportWorkbook.js.map +1 -0
- package/dist/excel.js +13 -0
- package/dist/excel.js.map +1 -0
- package/dist/feedback/ConfirmDialog.js +72 -0
- package/dist/feedback/ConfirmDialog.js.map +1 -0
- package/dist/feedback/ModalWaiting.js +23 -0
- package/dist/feedback/ModalWaiting.js.map +1 -0
- package/dist/feedback/NewBuildNotice.js +79 -0
- package/dist/feedback/NewBuildNotice.js.map +1 -0
- package/dist/feedback/StaleBuildBoundary.js +36 -0
- package/dist/feedback/StaleBuildBoundary.js.map +1 -0
- package/dist/feedback/Toaster.js +20 -0
- package/dist/feedback/Toaster.js.map +1 -0
- package/dist/feedback/confirmActionMachine.js +67 -0
- package/dist/feedback/confirmActionMachine.js.map +1 -0
- package/dist/feedback/toast.js +88 -0
- package/dist/feedback/toast.js.map +1 -0
- package/dist/feedback/useConfirmAction.js +40 -0
- package/dist/feedback/useConfirmAction.js.map +1 -0
- package/dist/filepond/FileDropzone.js +254 -0
- package/dist/filepond/FileDropzone.js.map +1 -0
- package/dist/filepond/pondServer.js +48 -0
- package/dist/filepond/pondServer.js.map +1 -0
- package/dist/filepond.js +10 -0
- package/dist/filepond.js.map +1 -0
- package/dist/files.js +43 -0
- package/dist/files.js.map +1 -0
- package/dist/formatting.js +177 -0
- package/dist/formatting.js.map +1 -0
- package/dist/forms/FormCatalogField.js +12 -0
- package/dist/forms/FormCatalogField.js.map +1 -0
- package/dist/forms/FormColorField.js +12 -0
- package/dist/forms/FormColorField.js.map +1 -0
- package/dist/forms/FormNumberField.js +12 -0
- package/dist/forms/FormNumberField.js.map +1 -0
- package/dist/forms/FormProblemAlert.js +15 -0
- package/dist/forms/FormProblemAlert.js.map +1 -0
- package/dist/forms/FormSelectField.js +12 -0
- package/dist/forms/FormSelectField.js.map +1 -0
- package/dist/forms/FormServerProblem.js +23 -0
- package/dist/forms/FormServerProblem.js.map +1 -0
- package/dist/forms/FormTextField.js +12 -0
- package/dist/forms/FormTextField.js.map +1 -0
- package/dist/forms/FormWizard.js +90 -0
- package/dist/forms/FormWizard.js.map +1 -0
- package/dist/forms/SubmitButton.js +14 -0
- package/dist/forms/SubmitButton.js.map +1 -0
- package/dist/forms/applyServerProblem.js +15 -0
- package/dist/forms/applyServerProblem.js.map +1 -0
- package/dist/forms/auth/ChangePasswordForm.js +46 -0
- package/dist/forms/auth/ChangePasswordForm.js.map +1 -0
- package/dist/forms/auth/ForgotPasswordForm.js +50 -0
- package/dist/forms/auth/ForgotPasswordForm.js.map +1 -0
- package/dist/forms/auth/SignInForm.js +48 -0
- package/dist/forms/auth/SignInForm.js.map +1 -0
- package/dist/forms/security/SecondStepForm.js +122 -0
- package/dist/forms/security/SecondStepForm.js.map +1 -0
- package/dist/forms/security/TwoStepVerificationCard.js +336 -0
- package/dist/forms/security/TwoStepVerificationCard.js.map +1 -0
- package/dist/forms/security/securityRules.js +28 -0
- package/dist/forms/security/securityRules.js.map +1 -0
- package/dist/forms/serverProblemFields.js +25 -0
- package/dist/forms/serverProblemFields.js.map +1 -0
- package/dist/forms/useFormikField.js +16 -0
- package/dist/forms/useFormikField.js.map +1 -0
- package/dist/forms/validation.js +55 -0
- package/dist/forms/validation.js.map +1 -0
- package/dist/forms/validationMessages.js +16 -0
- package/dist/forms/validationMessages.js.map +1 -0
- package/dist/forms.js +57 -0
- package/dist/forms.js.map +1 -0
- package/dist/hookForm/FormCatalogField.js +12 -0
- package/dist/hookForm/FormCatalogField.js.map +1 -0
- package/dist/hookForm/FormColorField.js +12 -0
- package/dist/hookForm/FormColorField.js.map +1 -0
- package/dist/hookForm/FormNumberField.js +12 -0
- package/dist/hookForm/FormNumberField.js.map +1 -0
- package/dist/hookForm/FormProblemAlert.js +17 -0
- package/dist/hookForm/FormProblemAlert.js.map +1 -0
- package/dist/hookForm/FormSelectField.js +12 -0
- package/dist/hookForm/FormSelectField.js.map +1 -0
- package/dist/hookForm/FormTextField.js +12 -0
- package/dist/hookForm/FormTextField.js.map +1 -0
- package/dist/hookForm/SubmitButton.js +15 -0
- package/dist/hookForm/SubmitButton.js.map +1 -0
- package/dist/hookForm/applyServerProblem.js +21 -0
- package/dist/hookForm/applyServerProblem.js.map +1 -0
- package/dist/hookForm/useHookFormField.js +19 -0
- package/dist/hookForm/useHookFormField.js.map +1 -0
- package/dist/i18next.js +5 -0
- package/dist/i18next.js.map +1 -0
- package/dist/identifiers.js +8 -0
- package/dist/identifiers.js.map +1 -0
- package/dist/inbox/InboxLayout.js +68 -0
- package/dist/inbox/InboxLayout.js.map +1 -0
- package/dist/inbox/MessageList.js +64 -0
- package/dist/inbox/MessageList.js.map +1 -0
- package/dist/inbox/MessageView.js +53 -0
- package/dist/inbox/MessageView.js.map +1 -0
- package/dist/inbox/inboxDates.js +8 -0
- package/dist/inbox/inboxDates.js.map +1 -0
- package/dist/index.js +383 -0
- package/dist/index.js.map +1 -0
- package/dist/inputs/CatalogInput.js +62 -0
- package/dist/inputs/CatalogInput.js.map +1 -0
- package/dist/inputs/ColorInput.js +108 -0
- package/dist/inputs/ColorInput.js.map +1 -0
- package/dist/inputs/FieldFrame.js +20 -0
- package/dist/inputs/FieldFrame.js.map +1 -0
- package/dist/inputs/FormSection.js +105 -0
- package/dist/inputs/FormSection.js.map +1 -0
- package/dist/inputs/NumberInput.js +69 -0
- package/dist/inputs/NumberInput.js.map +1 -0
- package/dist/inputs/SelectInput.js +66 -0
- package/dist/inputs/SelectInput.js.map +1 -0
- package/dist/inputs/TextInput.js +97 -0
- package/dist/inputs/TextInput.js.map +1 -0
- package/dist/inputs/colorContrast.js +46 -0
- package/dist/inputs/colorContrast.js.map +1 -0
- package/dist/inputs/formLayoutContext.js +9 -0
- package/dist/inputs/formLayoutContext.js.map +1 -0
- package/dist/inputs/numberText.js +48 -0
- package/dist/inputs/numberText.js.map +1 -0
- package/dist/kanban/KanbanBoard.js +113 -0
- package/dist/kanban/KanbanBoard.js.map +1 -0
- package/dist/kanban/kanbanMoves.js +29 -0
- package/dist/kanban/kanbanMoves.js.map +1 -0
- package/dist/kanban.js +9 -0
- package/dist/kanban.js.map +1 -0
- package/dist/laravel/csrfRetry.js +18 -0
- package/dist/laravel/csrfRetry.js.map +1 -0
- package/dist/laravel.js +6 -0
- package/dist/laravel.js.map +1 -0
- package/dist/lastListUrl.js +35 -0
- package/dist/lastListUrl.js.map +1 -0
- package/dist/locales/en.js +714 -0
- package/dist/locales/en.js.map +1 -0
- package/dist/locales/es.js +714 -0
- package/dist/locales/es.js.map +1 -0
- package/dist/maps/MapView.js +96 -0
- package/dist/maps/MapView.js.map +1 -0
- package/dist/maps/mapMarkers.js +19 -0
- package/dist/maps/mapMarkers.js.map +1 -0
- package/dist/maps.js +10 -0
- package/dist/maps.js.map +1 -0
- package/dist/money/money.js +380 -0
- package/dist/money/money.js.map +1 -0
- package/dist/money.js +6 -0
- package/dist/money.js.map +1 -0
- package/dist/navigation/appMenu.js +93 -0
- package/dist/navigation/appMenu.js.map +1 -0
- package/dist/navigation/useMenuBadges.js +45 -0
- package/dist/navigation/useMenuBadges.js.map +1 -0
- package/dist/navigation.js +30 -0
- package/dist/navigation.js.map +1 -0
- package/dist/navigationTrail.js +82 -0
- package/dist/navigationTrail.js.map +1 -0
- package/dist/next.js +5 -0
- package/dist/next.js.map +1 -0
- package/dist/observability/buildWatch.js +19 -0
- package/dist/observability/buildWatch.js.map +1 -0
- package/dist/observability/logger.js +43 -0
- package/dist/observability/logger.js.map +1 -0
- package/dist/observability/publishedBuild.js +39 -0
- package/dist/observability/publishedBuild.js.map +1 -0
- package/dist/observability/usePublishedBuildWatch.js +76 -0
- package/dist/observability/usePublishedBuildWatch.js.map +1 -0
- package/dist/passkeys.js +7 -0
- package/dist/passkeys.js.map +1 -0
- package/dist/periodRanges.js +33 -0
- package/dist/periodRanges.js.map +1 -0
- package/dist/problems.js +51 -0
- package/dist/problems.js.map +1 -0
- package/dist/pwa/InstallAppSetting.js +33 -0
- package/dist/pwa/InstallAppSetting.js.map +1 -0
- package/dist/pwa/InstallInstructionsDialog.js +35 -0
- package/dist/pwa/InstallInstructionsDialog.js.map +1 -0
- package/dist/pwa/InstallPromptBanner.js +64 -0
- package/dist/pwa/InstallPromptBanner.js.map +1 -0
- package/dist/pwa/installInstructions.js +60 -0
- package/dist/pwa/installInstructions.js.map +1 -0
- package/dist/pwa/useInstallPrompt.js +70 -0
- package/dist/pwa/useInstallPrompt.js.map +1 -0
- package/dist/react-hook-form.js +30 -0
- package/dist/react-hook-form.js.map +1 -0
- package/dist/react-router.js +10 -0
- package/dist/react-router.js.map +1 -0
- package/dist/security/ActivityLog.js +79 -0
- package/dist/security/ActivityLog.js.map +1 -0
- package/dist/security/RecoveryCodesDialog.js +84 -0
- package/dist/security/RecoveryCodesDialog.js.map +1 -0
- package/dist/security/SessionsCard.js +81 -0
- package/dist/security/SessionsCard.js.map +1 -0
- package/dist/security/passkeys.js +39 -0
- package/dist/security/passkeys.js.map +1 -0
- package/dist/table.js +35 -0
- package/dist/table.js.map +1 -0
- package/dist/theme/androidDevice.js +16 -0
- package/dist/theme/androidDevice.js.map +1 -0
- package/dist/theme/appleTracking.js +34 -0
- package/dist/theme/appleTracking.js.map +1 -0
- package/dist/theme/components/MuiAppBar.js +27 -0
- package/dist/theme/components/MuiAppBar.js.map +1 -0
- package/dist/theme/components/MuiBackdrop.js +13 -0
- package/dist/theme/components/MuiBackdrop.js.map +1 -0
- package/dist/theme/components/MuiButton.js +25 -0
- package/dist/theme/components/MuiButton.js.map +1 -0
- package/dist/theme/components/MuiButtonBase.js +16 -0
- package/dist/theme/components/MuiButtonBase.js.map +1 -0
- package/dist/theme/components/MuiChip.js +30 -0
- package/dist/theme/components/MuiChip.js.map +1 -0
- package/dist/theme/components/MuiDataGrid.js +30 -0
- package/dist/theme/components/MuiDataGrid.js.map +1 -0
- package/dist/theme/components/MuiDrawer.js +18 -0
- package/dist/theme/components/MuiDrawer.js.map +1 -0
- package/dist/theme/components/MuiMenuItem.js +17 -0
- package/dist/theme/components/MuiMenuItem.js.map +1 -0
- package/dist/theme/components/MuiTypography.js +22 -0
- package/dist/theme/components/MuiTypography.js.map +1 -0
- package/dist/theme/components/glassComponents.js +885 -0
- package/dist/theme/components/glassComponents.js.map +1 -0
- package/dist/theme/components/minimalComponents.js +146 -0
- package/dist/theme/components/minimalComponents.js.map +1 -0
- package/dist/theme/components/paletteOf.js +7 -0
- package/dist/theme/components/paletteOf.js.map +1 -0
- package/dist/theme/createToolkitTheme.js +100 -0
- package/dist/theme/createToolkitTheme.js.map +1 -0
- package/dist/theme/glassSurface.js +328 -0
- package/dist/theme/glassSurface.js.map +1 -0
- package/dist/theme/glassToasterStyles.js +50 -0
- package/dist/theme/glassToasterStyles.js.map +1 -0
- package/dist/theme/mergeComponents.js +42 -0
- package/dist/theme/mergeComponents.js.map +1 -0
- package/dist/theme/stackcraftPalette.js +59 -0
- package/dist/theme/stackcraftPalette.js.map +1 -0
- package/dist/theme/toolkitComponents.js +26 -0
- package/dist/theme/toolkitComponents.js.map +1 -0
- package/dist/timeline.js +8 -0
- package/dist/timeline.js.map +1 -0
- package/dist/toolkit/ToolkitProvider.js +49 -0
- package/dist/toolkit/ToolkitProvider.js.map +1 -0
- package/dist/toolkit/browserNavigation.js +34 -0
- package/dist/toolkit/browserNavigation.js.map +1 -0
- package/dist/toolkit/toolkitContext.js +19 -0
- package/dist/toolkit/toolkitContext.js.map +1 -0
- package/dist/toolkit/toolkitSettings.js +87 -0
- package/dist/toolkit/toolkitSettings.js.map +1 -0
- package/dist/toolkit/useToolkitTranslation.js +18 -0
- package/dist/toolkit/useToolkitTranslation.js.map +1 -0
- package/dist/types/DataTable/AuditTrailDialog.d.ts +32 -0
- package/dist/types/DataTable/AuditTrailTable.d.ts +28 -0
- package/dist/types/DataTable/ColumnFilters/HeaderFilterPopover.d.ts +8 -0
- package/dist/types/DataTable/ColumnFilters/MultiSelectColumnFilter.d.ts +16 -0
- package/dist/types/DataTable/ColumnFilters/SortableFilterHeader.d.ts +26 -0
- package/dist/types/DataTable/ColumnFilters/TextColumnFilter.d.ts +8 -0
- package/dist/types/DataTable/ColumnFilters/index.d.ts +4 -0
- package/dist/types/DataTable/EmptyState.d.ts +8 -0
- package/dist/types/DataTable/FilterChips.d.ts +15 -0
- package/dist/types/DataTable/GoToPage.d.ts +8 -0
- package/dist/types/DataTable/ServerTable.d.ts +110 -0
- package/dist/types/DataTable/buildChipConfig.d.ts +22 -0
- package/dist/types/DataTable/columns.d.ts +93 -0
- package/dist/types/DataTable/filterContext.d.ts +13 -0
- package/dist/types/DataTable/index.d.ts +13 -0
- package/dist/types/DataTable/serverTableParams.d.ts +16 -0
- package/dist/types/DataTable/tableMachine.d.ts +41 -0
- package/dist/types/DataTable/useDebouncedFilter.d.ts +8 -0
- package/dist/types/DataTable/useTableState.d.ts +93 -0
- package/dist/types/access/Can.d.ts +11 -0
- package/dist/types/access/PermissionMatrix.d.ts +21 -0
- package/dist/types/access/RequireAccess.d.ts +11 -0
- package/dist/types/access/accessRules.d.ts +24 -0
- package/dist/types/access/permissionGroups.d.ts +56 -0
- package/dist/types/access/useCan.d.ts +11 -0
- package/dist/types/account/AccountProvider.d.ts +27 -0
- package/dist/types/account/AccountSecuritySection.d.ts +7 -0
- package/dist/types/account/DemoTotpCodeButton.d.ts +6 -0
- package/dist/types/account/ForgotPasswordScreen.d.ts +15 -0
- package/dist/types/account/ProfileScreen.d.ts +13 -0
- package/dist/types/account/ResetPasswordScreen.d.ts +19 -0
- package/dist/types/account/SignInScreen.d.ts +25 -0
- package/dist/types/account/accountConnector.d.ts +263 -0
- package/dist/types/account/demo/createDemoAccountConnector.d.ts +30 -0
- package/dist/types/account/demo/totp.d.ts +45 -0
- package/dist/types/account/restAccountConnector.d.ts +49 -0
- package/dist/types/account-demo.d.ts +2 -0
- package/dist/types/account.d.ts +16 -0
- package/dist/types/adapters/i18next.d.ts +11 -0
- package/dist/types/adapters/nextNavigation.d.ts +33 -0
- package/dist/types/adapters/reactRouter.d.ts +6 -0
- package/dist/types/adapters/reactRouterRoutes.d.ts +30 -0
- package/dist/types/api/ApiError.d.ts +42 -0
- package/dist/types/api/createApiClient.d.ts +146 -0
- package/dist/types/api/staleChunks.d.ts +15 -0
- package/dist/types/appShell/AccountMenu.d.ts +28 -0
- package/dist/types/appShell/AppLayout.d.ts +66 -0
- package/dist/types/appShell/AppearanceSettings.d.ts +34 -0
- package/dist/types/appShell/AuthLayout.d.ts +21 -0
- package/dist/types/appShell/BarActionButton.d.ts +15 -0
- package/dist/types/appShell/BarActions.d.ts +18 -0
- package/dist/types/appShell/BarCapsule.d.ts +12 -0
- package/dist/types/appShell/HeaderTools.d.ts +27 -0
- package/dist/types/appShell/MobileTabBar.d.ts +17 -0
- package/dist/types/appShell/SettingsMenu.d.ts +13 -0
- package/dist/types/appShell/SideMenu.d.ts +31 -0
- package/dist/types/appShell/SideMenuEntry.d.ts +17 -0
- package/dist/types/appShell/SubmenuActionsMenu.d.ts +24 -0
- package/dist/types/appShell/TabBarEditor.d.ts +13 -0
- package/dist/types/appShell/TopMenu.d.ts +7 -0
- package/dist/types/appShell/appMenuContext.d.ts +9 -0
- package/dist/types/appShell/barActionsSlot.d.ts +35 -0
- package/dist/types/appShell/barMenuPlacement.d.ts +9 -0
- package/dist/types/appShell/menuItemText.d.ts +55 -0
- package/dist/types/appShell/pageTitle.d.ts +26 -0
- package/dist/types/appShell/shellSizes.d.ts +45 -0
- package/dist/types/appShell/tabBarRule.d.ts +5 -0
- package/dist/types/appShell/tabBarScroll.d.ts +26 -0
- package/dist/types/appShell/useDrawerCollapsed.d.ts +8 -0
- package/dist/types/appShell/useFittingActionCount.d.ts +7 -0
- package/dist/types/appShell/usePinnedMobileTabs.d.ts +7 -0
- package/dist/types/appShell/useTabBarMinimized.d.ts +8 -0
- package/dist/types/auth/PasswordChecklist.d.ts +11 -0
- package/dist/types/auth/passwordRules.d.ts +34 -0
- package/dist/types/calendar/EventCalendar.d.ts +46 -0
- package/dist/types/calendar.d.ts +1 -0
- package/dist/types/charts.d.ts +2 -0
- package/dist/types/date-pickers.d.ts +2 -0
- package/dist/types/datePickers/DateInput.d.ts +39 -0
- package/dist/types/datePickers/FormDateField.d.ts +7 -0
- package/dist/types/dates.d.ts +18 -0
- package/dist/types/dictionaries/dictionaries.d.ts +54 -0
- package/dist/types/downloads/DownloadManager.d.ts +1 -0
- package/dist/types/downloads/downloadQueue.d.ts +45 -0
- package/dist/types/downloads/downloadsMachine.d.ts +10 -0
- package/dist/types/downloads/index.d.ts +3 -0
- package/dist/types/excel/reportWorkbook.d.ts +157 -0
- package/dist/types/excel.d.ts +1 -0
- package/dist/types/feedback/ConfirmDialog.d.ts +29 -0
- package/dist/types/feedback/ModalWaiting.d.ts +8 -0
- package/dist/types/feedback/NewBuildNotice.d.ts +18 -0
- package/dist/types/feedback/StaleBuildBoundary.d.ts +21 -0
- package/dist/types/feedback/Toaster.d.ts +1 -0
- package/dist/types/feedback/confirmActionMachine.d.ts +19 -0
- package/dist/types/feedback/index.d.ts +8 -0
- package/dist/types/feedback/toast.d.ts +100 -0
- package/dist/types/feedback/useConfirmAction.d.ts +33 -0
- package/dist/types/filepond/FileDropzone.d.ts +59 -0
- package/dist/types/filepond/pondServer.d.ts +17 -0
- package/dist/types/filepond.d.ts +3 -0
- package/dist/types/files.d.ts +29 -0
- package/dist/types/formatting.d.ts +106 -0
- package/dist/types/forms/FormCatalogField.d.ts +6 -0
- package/dist/types/forms/FormColorField.d.ts +6 -0
- package/dist/types/forms/FormNumberField.d.ts +6 -0
- package/dist/types/forms/FormProblemAlert.d.ts +6 -0
- package/dist/types/forms/FormSelectField.d.ts +6 -0
- package/dist/types/forms/FormServerProblem.d.ts +8 -0
- package/dist/types/forms/FormTextField.d.ts +6 -0
- package/dist/types/forms/FormWizard.d.ts +20 -0
- package/dist/types/forms/SubmitButton.d.ts +9 -0
- package/dist/types/forms/applyServerProblem.d.ts +9 -0
- package/dist/types/forms/auth/ChangePasswordForm.d.ts +15 -0
- package/dist/types/forms/auth/ForgotPasswordForm.d.ts +12 -0
- package/dist/types/forms/auth/SignInForm.d.ts +18 -0
- package/dist/types/forms/index.d.ts +19 -0
- package/dist/types/forms/security/SecondStepForm.d.ts +28 -0
- package/dist/types/forms/security/TwoStepVerificationCard.d.ts +81 -0
- package/dist/types/forms/security/securityRules.d.ts +24 -0
- package/dist/types/forms/serverProblemFields.d.ts +19 -0
- package/dist/types/forms/useFormikField.d.ts +11 -0
- package/dist/types/forms/validation.d.ts +251 -0
- package/dist/types/forms/validationMessages.d.ts +12 -0
- package/dist/types/forms.d.ts +2 -0
- package/dist/types/hookForm/FormCatalogField.d.ts +8 -0
- package/dist/types/hookForm/FormColorField.d.ts +8 -0
- package/dist/types/hookForm/FormNumberField.d.ts +8 -0
- package/dist/types/hookForm/FormProblemAlert.d.ts +7 -0
- package/dist/types/hookForm/FormSelectField.d.ts +8 -0
- package/dist/types/hookForm/FormTextField.d.ts +8 -0
- package/dist/types/hookForm/SubmitButton.d.ts +21 -0
- package/dist/types/hookForm/applyServerProblem.d.ts +10 -0
- package/dist/types/hookForm/useHookFormField.d.ts +13 -0
- package/dist/types/i18next.d.ts +1 -0
- package/dist/types/identifiers.d.ts +2 -0
- package/dist/types/inbox/InboxLayout.d.ts +26 -0
- package/dist/types/inbox/MessageList.d.ts +27 -0
- package/dist/types/inbox/MessageView.d.ts +23 -0
- package/dist/types/inbox/inboxDates.d.ts +6 -0
- package/dist/types/index.d.ts +84 -0
- package/dist/types/inputs/CatalogInput.d.ts +41 -0
- package/dist/types/inputs/ColorInput.d.ts +28 -0
- package/dist/types/inputs/FieldFrame.d.ts +14 -0
- package/dist/types/inputs/FormSection.d.ts +29 -0
- package/dist/types/inputs/NumberInput.d.ts +36 -0
- package/dist/types/inputs/SelectInput.d.ts +34 -0
- package/dist/types/inputs/TextInput.d.ts +60 -0
- package/dist/types/inputs/colorContrast.d.ts +18 -0
- package/dist/types/inputs/formLayoutContext.d.ts +3 -0
- package/dist/types/inputs/numberText.d.ts +25 -0
- package/dist/types/kanban/KanbanBoard.d.ts +33 -0
- package/dist/types/kanban/kanbanMoves.d.ts +38 -0
- package/dist/types/kanban.d.ts +2 -0
- package/dist/types/laravel/csrfRetry.d.ts +21 -0
- package/dist/types/laravel.d.ts +1 -0
- package/dist/types/lastListUrl.d.ts +20 -0
- package/dist/types/locales/en.d.ts +711 -0
- package/dist/types/locales/es.d.ts +711 -0
- package/dist/types/maps/MapView.d.ts +32 -0
- package/dist/types/maps/mapMarkers.d.ts +23 -0
- package/dist/types/maps.d.ts +2 -0
- package/dist/types/money/money.d.ts +203 -0
- package/dist/types/money.d.ts +1 -0
- package/dist/types/navigation/appMenu.d.ts +92 -0
- package/dist/types/navigation/useMenuBadges.d.ts +16 -0
- package/dist/types/navigation.d.ts +22 -0
- package/dist/types/navigationTrail.d.ts +49 -0
- package/dist/types/next.d.ts +1 -0
- package/dist/types/observability/buildWatch.d.ts +28 -0
- package/dist/types/observability/logger.d.ts +19 -0
- package/dist/types/observability/publishedBuild.d.ts +35 -0
- package/dist/types/observability/usePublishedBuildWatch.d.ts +16 -0
- package/dist/types/passkeys.d.ts +1 -0
- package/dist/types/periodRanges.d.ts +32 -0
- package/dist/types/problems.d.ts +31 -0
- package/dist/types/pwa/InstallAppSetting.d.ts +1 -0
- package/dist/types/pwa/InstallInstructionsDialog.d.ts +18 -0
- package/dist/types/pwa/InstallPromptBanner.d.ts +7 -0
- package/dist/types/pwa/installInstructions.d.ts +52 -0
- package/dist/types/pwa/useInstallPrompt.d.ts +12 -0
- package/dist/types/react-hook-form.d.ts +11 -0
- package/dist/types/react-router.d.ts +2 -0
- package/dist/types/security/ActivityLog.d.ts +31 -0
- package/dist/types/security/RecoveryCodesDialog.d.ts +11 -0
- package/dist/types/security/SessionsCard.d.ts +22 -0
- package/dist/types/security/passkeys.d.ts +18 -0
- package/dist/types/table.d.ts +1 -0
- package/dist/types/theme/androidDevice.d.ts +11 -0
- package/dist/types/theme/appleTracking.d.ts +17 -0
- package/dist/types/theme/components/MuiAppBar.d.ts +13 -0
- package/dist/types/theme/components/MuiBackdrop.d.ts +11 -0
- package/dist/types/theme/components/MuiButton.d.ts +27 -0
- package/dist/types/theme/components/MuiButtonBase.d.ts +14 -0
- package/dist/types/theme/components/MuiChip.d.ts +29 -0
- package/dist/types/theme/components/MuiDataGrid.d.ts +45 -0
- package/dist/types/theme/components/MuiDrawer.d.ts +13 -0
- package/dist/types/theme/components/MuiMenuItem.d.ts +17 -0
- package/dist/types/theme/components/MuiTypography.d.ts +20 -0
- package/dist/types/theme/components/glassComponents.d.ts +8 -0
- package/dist/types/theme/components/minimalComponents.d.ts +22 -0
- package/dist/types/theme/components/paletteOf.d.ts +5 -0
- package/dist/types/theme/createToolkitTheme.d.ts +48 -0
- package/dist/types/theme/glassSurface.d.ts +247 -0
- package/dist/types/theme/glassToasterStyles.d.ts +7 -0
- package/dist/types/theme/mergeComponents.d.ts +15 -0
- package/dist/types/theme/stackcraftPalette.d.ts +142 -0
- package/dist/types/theme/toolkitComponents.d.ts +4 -0
- package/dist/types/timeline.d.ts +2 -0
- package/dist/types/toolkit/ToolkitProvider.d.ts +31 -0
- package/dist/types/toolkit/browserNavigation.d.ts +32 -0
- package/dist/types/toolkit/toolkitContext.d.ts +28 -0
- package/dist/types/toolkit/toolkitSettings.d.ts +68 -0
- package/dist/types/toolkit/useToolkitTranslation.d.ts +10 -0
- package/dist/types/ui/actions/CopyButton.d.ts +13 -0
- package/dist/types/ui/actions/DownloadMenu.d.ts +50 -0
- package/dist/types/ui/actions/SecretField.d.ts +13 -0
- package/dist/types/ui/filters/DateRangeFilter.d.ts +16 -0
- package/dist/types/ui/filters/PeriodRangeSelector.d.ts +28 -0
- package/dist/types/ui/filters/QuickFilters.d.ts +21 -0
- package/dist/types/ui/filters/SegmentedControl.d.ts +44 -0
- package/dist/types/ui/index.d.ts +33 -0
- package/dist/types/ui/labels/DictionaryText.d.ts +7 -0
- package/dist/types/ui/labels/StatusChip.d.ts +21 -0
- package/dist/types/ui/labels/Tag.d.ts +19 -0
- package/dist/types/ui/layout/CollapsibleSection.d.ts +15 -0
- package/dist/types/ui/layout/ContentDialog.d.ts +13 -0
- package/dist/types/ui/layout/DefinitionList.d.ts +15 -0
- package/dist/types/ui/layout/DetailHeader.d.ts +15 -0
- package/dist/types/ui/layout/ErrorPage.d.ts +22 -0
- package/dist/types/ui/layout/FullPageLoader.d.ts +1 -0
- package/dist/types/ui/layout/GlassLensFilter.d.ts +1 -0
- package/dist/types/ui/layout/GlassPanel.d.ts +11 -0
- package/dist/types/ui/layout/PageHeader.d.ts +15 -0
- package/dist/types/ui/layout/PageHeading.d.ts +18 -0
- package/dist/types/ui/layout/ProfileHeader.d.ts +17 -0
- package/dist/types/ui/layout/ScrollableRow.d.ts +33 -0
- package/dist/types/ui/layout/SectionCard.d.ts +11 -0
- package/dist/types/ui/layout/appBarHeight.d.ts +13 -0
- package/dist/types/ui/metrics/BarList.d.ts +19 -0
- package/dist/types/ui/metrics/CalendarHeatmap.d.ts +28 -0
- package/dist/types/ui/metrics/ChartTooltip.d.ts +5 -0
- package/dist/types/ui/metrics/ColumnChart.d.ts +35 -0
- package/dist/types/ui/metrics/MetricCard.d.ts +31 -0
- package/dist/types/ui/metrics/TableToggle.d.ts +7 -0
- package/dist/types/ui/metrics/barListLabels.d.ts +17 -0
- package/dist/types/ui/metrics/heatmapScale.d.ts +45 -0
- package/dist/types/ui/navigation/BackButton.d.ts +11 -0
- package/dist/types/ui/navigation/ColorSchemeToggle.d.ts +7 -0
- package/dist/types/ui/navigation/DocumentTitle.d.ts +6 -0
- package/dist/types/ui/navigation/FontSizeToggle.d.ts +6 -0
- package/dist/types/ui/navigation/LanguageToggle.d.ts +8 -0
- package/dist/types/ui/navigation/PageBreadcrumbs.d.ts +9 -0
- package/dist/types/ui/navigation/colorMode.d.ts +18 -0
- package/dist/types/ui/navigation/fontSizeLevels.d.ts +25 -0
- package/dist/types/ui/navigation/useFontSize.d.ts +10 -0
- package/dist/types/ui/timeline/GroupedTimeline.d.ts +38 -0
- package/dist/types/ui/timeline/timelineDot.d.ts +19 -0
- package/dist/types/upload/FileDropzone.d.ts +34 -0
- package/dist/types/upload/fileRules.d.ts +51 -0
- package/dist/types/upload/uploadMachine.d.ts +23 -0
- package/dist/types/upload/uploadWithProgress.d.ts +16 -0
- package/dist/ui/actions/CopyButton.js +28 -0
- package/dist/ui/actions/CopyButton.js.map +1 -0
- package/dist/ui/actions/DownloadMenu.js +163 -0
- package/dist/ui/actions/DownloadMenu.js.map +1 -0
- package/dist/ui/actions/SecretField.js +57 -0
- package/dist/ui/actions/SecretField.js.map +1 -0
- package/dist/ui/filters/DateRangeFilter.js +86 -0
- package/dist/ui/filters/DateRangeFilter.js.map +1 -0
- package/dist/ui/filters/PeriodRangeSelector.js +56 -0
- package/dist/ui/filters/PeriodRangeSelector.js.map +1 -0
- package/dist/ui/filters/QuickFilters.js +91 -0
- package/dist/ui/filters/QuickFilters.js.map +1 -0
- package/dist/ui/filters/SegmentedControl.js +80 -0
- package/dist/ui/filters/SegmentedControl.js.map +1 -0
- package/dist/ui/labels/DictionaryText.js +11 -0
- package/dist/ui/labels/DictionaryText.js.map +1 -0
- package/dist/ui/labels/StatusChip.js +52 -0
- package/dist/ui/labels/StatusChip.js.map +1 -0
- package/dist/ui/labels/Tag.js +26 -0
- package/dist/ui/labels/Tag.js.map +1 -0
- package/dist/ui/layout/CollapsibleSection.js +48 -0
- package/dist/ui/layout/CollapsibleSection.js.map +1 -0
- package/dist/ui/layout/ContentDialog.js +97 -0
- package/dist/ui/layout/ContentDialog.js.map +1 -0
- package/dist/ui/layout/DefinitionList.js +30 -0
- package/dist/ui/layout/DefinitionList.js.map +1 -0
- package/dist/ui/layout/DetailHeader.js +27 -0
- package/dist/ui/layout/DetailHeader.js.map +1 -0
- package/dist/ui/layout/ErrorPage.js +40 -0
- package/dist/ui/layout/ErrorPage.js.map +1 -0
- package/dist/ui/layout/FullPageLoader.js +13 -0
- package/dist/ui/layout/FullPageLoader.js.map +1 -0
- package/dist/ui/layout/GlassLensFilter.js +53 -0
- package/dist/ui/layout/GlassLensFilter.js.map +1 -0
- package/dist/ui/layout/GlassPanel.js +18 -0
- package/dist/ui/layout/GlassPanel.js.map +1 -0
- package/dist/ui/layout/PageHeader.js +23 -0
- package/dist/ui/layout/PageHeader.js.map +1 -0
- package/dist/ui/layout/PageHeading.js +51 -0
- package/dist/ui/layout/PageHeading.js.map +1 -0
- package/dist/ui/layout/ProfileHeader.js +64 -0
- package/dist/ui/layout/ProfileHeader.js.map +1 -0
- package/dist/ui/layout/ScrollableRow.js +156 -0
- package/dist/ui/layout/ScrollableRow.js.map +1 -0
- package/dist/ui/layout/SectionCard.js +18 -0
- package/dist/ui/layout/SectionCard.js.map +1 -0
- package/dist/ui/layout/appBarHeight.js +42 -0
- package/dist/ui/layout/appBarHeight.js.map +1 -0
- package/dist/ui/metrics/BarList.js +89 -0
- package/dist/ui/metrics/BarList.js.map +1 -0
- package/dist/ui/metrics/CalendarHeatmap.js +131 -0
- package/dist/ui/metrics/CalendarHeatmap.js.map +1 -0
- package/dist/ui/metrics/ChartTooltip.js +16 -0
- package/dist/ui/metrics/ChartTooltip.js.map +1 -0
- package/dist/ui/metrics/ColumnChart.js +110 -0
- package/dist/ui/metrics/ColumnChart.js.map +1 -0
- package/dist/ui/metrics/MetricCard.js +64 -0
- package/dist/ui/metrics/MetricCard.js.map +1 -0
- package/dist/ui/metrics/TableToggle.js +13 -0
- package/dist/ui/metrics/TableToggle.js.map +1 -0
- package/dist/ui/metrics/barListLabels.js +9 -0
- package/dist/ui/metrics/barListLabels.js.map +1 -0
- package/dist/ui/metrics/heatmapScale.js +67 -0
- package/dist/ui/metrics/heatmapScale.js.map +1 -0
- package/dist/ui/navigation/BackButton.js +28 -0
- package/dist/ui/navigation/BackButton.js.map +1 -0
- package/dist/ui/navigation/ColorSchemeToggle.js +37 -0
- package/dist/ui/navigation/ColorSchemeToggle.js.map +1 -0
- package/dist/ui/navigation/DocumentTitle.js +11 -0
- package/dist/ui/navigation/DocumentTitle.js.map +1 -0
- package/dist/ui/navigation/FontSizeToggle.js +40 -0
- package/dist/ui/navigation/FontSizeToggle.js.map +1 -0
- package/dist/ui/navigation/LanguageToggle.js +27 -0
- package/dist/ui/navigation/LanguageToggle.js.map +1 -0
- package/dist/ui/navigation/PageBreadcrumbs.js +51 -0
- package/dist/ui/navigation/PageBreadcrumbs.js.map +1 -0
- package/dist/ui/navigation/colorMode.js +13 -0
- package/dist/ui/navigation/colorMode.js.map +1 -0
- package/dist/ui/navigation/fontSizeLevels.js +24 -0
- package/dist/ui/navigation/fontSizeLevels.js.map +1 -0
- package/dist/ui/navigation/useFontSize.js +44 -0
- package/dist/ui/navigation/useFontSize.js.map +1 -0
- package/dist/ui/timeline/GroupedTimeline.js +104 -0
- package/dist/ui/timeline/GroupedTimeline.js.map +1 -0
- package/dist/ui/timeline/timelineDot.js +20 -0
- package/dist/ui/timeline/timelineDot.js.map +1 -0
- package/dist/upload/FileDropzone.js +143 -0
- package/dist/upload/FileDropzone.js.map +1 -0
- package/dist/upload/fileRules.js +62 -0
- package/dist/upload/fileRules.js.map +1 -0
- package/dist/upload/uploadMachine.js +73 -0
- package/dist/upload/uploadMachine.js.map +1 -0
- package/dist/upload/uploadWithProgress.js +45 -0
- package/dist/upload/uploadWithProgress.js.map +1 -0
- package/package.json +303 -5
|
@@ -0,0 +1,201 @@
|
|
|
1
|
+
"use client";
|
|
2
|
+
import { jsx, jsxs } from "react/jsx-runtime";
|
|
3
|
+
import { useState, useRef, useEffect, Fragment } from "react";
|
|
4
|
+
import { useToolkitTranslation } from "../toolkit/useToolkitTranslation.js";
|
|
5
|
+
import { useSelector } from "@xstate/react";
|
|
6
|
+
import Box from "@mui/material/Box";
|
|
7
|
+
import CircularProgress from "@mui/material/CircularProgress";
|
|
8
|
+
import Collapse from "@mui/material/Collapse";
|
|
9
|
+
import Divider from "@mui/material/Divider";
|
|
10
|
+
import IconButton from "@mui/material/IconButton";
|
|
11
|
+
import List from "@mui/material/List";
|
|
12
|
+
import ListItem from "@mui/material/ListItem";
|
|
13
|
+
import Paper from "@mui/material/Paper";
|
|
14
|
+
import Slide from "@mui/material/Slide";
|
|
15
|
+
import Stack from "@mui/material/Stack";
|
|
16
|
+
import Tooltip from "@mui/material/Tooltip";
|
|
17
|
+
import Typography from "@mui/material/Typography";
|
|
18
|
+
import BlockOutlinedIcon from "@mui/icons-material/BlockOutlined";
|
|
19
|
+
import CheckCircleIcon from "@mui/icons-material/CheckCircle";
|
|
20
|
+
import CloseIcon from "@mui/icons-material/Close";
|
|
21
|
+
import ErrorOutlineIcon from "@mui/icons-material/ErrorOutline";
|
|
22
|
+
import ExpandLessIcon from "@mui/icons-material/ExpandLess";
|
|
23
|
+
import ExpandMoreIcon from "@mui/icons-material/ExpandMore";
|
|
24
|
+
import InsertDriveFileOutlinedIcon from "@mui/icons-material/InsertDriveFileOutlined";
|
|
25
|
+
import PictureAsPdfOutlinedIcon from "@mui/icons-material/PictureAsPdfOutlined";
|
|
26
|
+
import TableViewOutlinedIcon from "@mui/icons-material/TableViewOutlined";
|
|
27
|
+
import TextSnippetOutlinedIcon from "@mui/icons-material/TextSnippetOutlined";
|
|
28
|
+
import { downloadsActor, countActiveDownloads, clearFinishedDownloads, cancelDownload } from "./downloadQueue.js";
|
|
29
|
+
import { DOWNLOAD_STATUS } from "./downloadsMachine.js";
|
|
30
|
+
import { formatFileSize } from "../formatting.js";
|
|
31
|
+
import { isGlassTheme, glassStylesOf } from "../theme/glassSurface.js";
|
|
32
|
+
const FILE_TYPE_APPEARANCE = {
|
|
33
|
+
xlsx: { Icon: TableViewOutlinedIcon, color: "success.main" },
|
|
34
|
+
csv: { Icon: TextSnippetOutlinedIcon, color: "info.main" },
|
|
35
|
+
pdf: { Icon: PictureAsPdfOutlinedIcon, color: "error.main" }
|
|
36
|
+
};
|
|
37
|
+
const DEFAULT_FILE_TYPE_APPEARANCE = { Icon: InsertDriveFileOutlinedIcon, color: "text.secondary" };
|
|
38
|
+
const AUTO_DISMISS_MILLISECONDS = 5e3;
|
|
39
|
+
const SCREEN_EDGE_SPACING = 3;
|
|
40
|
+
const PANEL_WIDTH_PIXELS = 360;
|
|
41
|
+
const LIST_MAX_HEIGHT = "40vh";
|
|
42
|
+
const PROGRESS_RING_PIXELS = 22;
|
|
43
|
+
function fileTypeAppearanceOf(download) {
|
|
44
|
+
const extension = download.fileName?.split(".").pop()?.toLowerCase();
|
|
45
|
+
return FILE_TYPE_APPEARANCE[download.format ?? extension] ?? DEFAULT_FILE_TYPE_APPEARANCE;
|
|
46
|
+
}
|
|
47
|
+
function detailTextOf(download, t) {
|
|
48
|
+
if (download.status === DOWNLOAD_STATUS.completed) {
|
|
49
|
+
return formatFileSize(download.loadedBytes);
|
|
50
|
+
}
|
|
51
|
+
if (download.status === DOWNLOAD_STATUS.failed) {
|
|
52
|
+
return download.errorMessage ?? t("downloads.failed");
|
|
53
|
+
}
|
|
54
|
+
if (download.status === DOWNLOAD_STATUS.canceled) {
|
|
55
|
+
return t("downloads.canceled");
|
|
56
|
+
}
|
|
57
|
+
if (download.loadedBytes === 0) {
|
|
58
|
+
return t("downloads.preparing");
|
|
59
|
+
}
|
|
60
|
+
return download.totalBytes ? t("downloads.progressOf", { loaded: formatFileSize(download.loadedBytes), total: formatFileSize(download.totalBytes) }) : t("downloads.progressLoaded", { loaded: formatFileSize(download.loadedBytes) });
|
|
61
|
+
}
|
|
62
|
+
function summaryTextOf(downloads, t) {
|
|
63
|
+
const activeCount = countActiveDownloads(downloads);
|
|
64
|
+
if (activeCount > 0) {
|
|
65
|
+
return t("downloads.summaryDownloading", { count: activeCount });
|
|
66
|
+
}
|
|
67
|
+
const failedCount = downloads.filter((download) => download.status === DOWNLOAD_STATUS.failed).length;
|
|
68
|
+
if (failedCount > 0) {
|
|
69
|
+
return t("downloads.summaryFailed", { count: failedCount });
|
|
70
|
+
}
|
|
71
|
+
const completedCount = downloads.filter((download) => download.status === DOWNLOAD_STATUS.completed).length;
|
|
72
|
+
return t("downloads.summaryCompleted", { count: completedCount });
|
|
73
|
+
}
|
|
74
|
+
function DownloadStatusIndicator({ download, displayName }) {
|
|
75
|
+
const { t } = useToolkitTranslation("common");
|
|
76
|
+
if (download.status === DOWNLOAD_STATUS.completed) {
|
|
77
|
+
return /* @__PURE__ */ jsx(CheckCircleIcon, { sx: { color: "success.main" }, "aria-label": t("downloads.completedOf", { name: displayName }) });
|
|
78
|
+
}
|
|
79
|
+
if (download.status === DOWNLOAD_STATUS.failed) {
|
|
80
|
+
return /* @__PURE__ */ jsx(ErrorOutlineIcon, { sx: { color: "error.main" }, "aria-label": t("downloads.failedOf", { name: displayName }) });
|
|
81
|
+
}
|
|
82
|
+
if (download.status === DOWNLOAD_STATUS.canceled) {
|
|
83
|
+
return /* @__PURE__ */ jsx(BlockOutlinedIcon, { sx: { color: "text.disabled" }, "aria-label": t("downloads.canceledOf", { name: displayName }) });
|
|
84
|
+
}
|
|
85
|
+
const hasKnownSize = Boolean(download.totalBytes);
|
|
86
|
+
return /* @__PURE__ */ jsx(Tooltip, { title: t("downloads.cancel"), children: /* @__PURE__ */ jsxs(
|
|
87
|
+
IconButton,
|
|
88
|
+
{
|
|
89
|
+
size: "small",
|
|
90
|
+
"aria-label": t("downloads.cancelOf", { name: displayName }),
|
|
91
|
+
onClick: () => cancelDownload(download.id),
|
|
92
|
+
sx: { position: "relative", width: PROGRESS_RING_PIXELS + 10, height: PROGRESS_RING_PIXELS + 10 },
|
|
93
|
+
children: [
|
|
94
|
+
/* @__PURE__ */ jsx(
|
|
95
|
+
CircularProgress,
|
|
96
|
+
{
|
|
97
|
+
size: PROGRESS_RING_PIXELS,
|
|
98
|
+
thickness: 4,
|
|
99
|
+
variant: hasKnownSize ? "determinate" : "indeterminate",
|
|
100
|
+
value: hasKnownSize ? Math.min(100, download.loadedBytes * 100 / download.totalBytes) : void 0,
|
|
101
|
+
sx: { position: "absolute" }
|
|
102
|
+
}
|
|
103
|
+
),
|
|
104
|
+
/* @__PURE__ */ jsx(CloseIcon, { sx: { fontSize: 12 } })
|
|
105
|
+
]
|
|
106
|
+
}
|
|
107
|
+
) });
|
|
108
|
+
}
|
|
109
|
+
function DownloadRow({ download }) {
|
|
110
|
+
const { t } = useToolkitTranslation("common");
|
|
111
|
+
const { Icon, color } = fileTypeAppearanceOf(download);
|
|
112
|
+
const displayName = download.fileName ?? download.label;
|
|
113
|
+
const isFailed = download.status === DOWNLOAD_STATUS.failed;
|
|
114
|
+
return (
|
|
115
|
+
// minWidth 0: sin él un nombre largo empuja el renglón y la lista enseña una barra horizontal
|
|
116
|
+
/* @__PURE__ */ jsxs(ListItem, { disableGutters: true, sx: { gap: 1.5, px: 2, py: 1, minWidth: 0 }, children: [
|
|
117
|
+
/* @__PURE__ */ jsx(Icon, { fontSize: "small", sx: { color, flexShrink: 0 } }),
|
|
118
|
+
/* @__PURE__ */ jsxs(Box, { sx: { minWidth: 0, flex: 1 }, children: [
|
|
119
|
+
/* @__PURE__ */ jsx(Tooltip, { title: displayName, children: /* @__PURE__ */ jsx(Typography, { variant: "body2", noWrap: true, children: displayName }) }),
|
|
120
|
+
/* @__PURE__ */ jsx(
|
|
121
|
+
Typography,
|
|
122
|
+
{
|
|
123
|
+
variant: "caption",
|
|
124
|
+
component: "p",
|
|
125
|
+
noWrap: !isFailed,
|
|
126
|
+
sx: { color: isFailed ? "error.main" : "text.secondary" },
|
|
127
|
+
children: detailTextOf(download, t)
|
|
128
|
+
}
|
|
129
|
+
)
|
|
130
|
+
] }),
|
|
131
|
+
/* @__PURE__ */ jsx(Box, { sx: { flexShrink: 0, display: "flex", alignItems: "center" }, children: /* @__PURE__ */ jsx(DownloadStatusIndicator, { download, displayName }) })
|
|
132
|
+
] })
|
|
133
|
+
);
|
|
134
|
+
}
|
|
135
|
+
function DownloadManager() {
|
|
136
|
+
const { t } = useToolkitTranslation("common");
|
|
137
|
+
const downloads = useSelector(downloadsActor, (snapshot) => snapshot.context.downloads);
|
|
138
|
+
const [isExpanded, setIsExpanded] = useState(true);
|
|
139
|
+
const previousCountRef = useRef(downloads.length);
|
|
140
|
+
const activeCount = countActiveDownloads(downloads);
|
|
141
|
+
const allSucceeded = downloads.length > 0 && downloads.every((download) => download.status === DOWNLOAD_STATUS.completed);
|
|
142
|
+
useEffect(() => {
|
|
143
|
+
if (downloads.length > previousCountRef.current) {
|
|
144
|
+
setIsExpanded(true);
|
|
145
|
+
}
|
|
146
|
+
previousCountRef.current = downloads.length;
|
|
147
|
+
}, [downloads.length]);
|
|
148
|
+
useEffect(() => {
|
|
149
|
+
if (!allSucceeded) {
|
|
150
|
+
return void 0;
|
|
151
|
+
}
|
|
152
|
+
const dismissTimer = setTimeout(clearFinishedDownloads, AUTO_DISMISS_MILLISECONDS);
|
|
153
|
+
return () => clearTimeout(dismissTimer);
|
|
154
|
+
}, [allSucceeded, downloads.length]);
|
|
155
|
+
return /* @__PURE__ */ jsx(Slide, { direction: "up", in: downloads.length > 0, mountOnEnter: true, unmountOnExit: true, children: /* @__PURE__ */ jsxs(
|
|
156
|
+
Paper,
|
|
157
|
+
{
|
|
158
|
+
elevation: 8,
|
|
159
|
+
role: "region",
|
|
160
|
+
"aria-label": t("downloads.title"),
|
|
161
|
+
sx: [{
|
|
162
|
+
position: "fixed",
|
|
163
|
+
right: (theme) => theme.spacing(SCREEN_EDGE_SPACING),
|
|
164
|
+
bottom: 0,
|
|
165
|
+
width: (theme) => `min(${PANEL_WIDTH_PIXELS}px, calc(100vw - ${theme.spacing(SCREEN_EDGE_SPACING * 2)}))`,
|
|
166
|
+
// pegado al borde de abajo como en Drive: solo se redondean las esquinas de arriba
|
|
167
|
+
borderBottomLeftRadius: 0,
|
|
168
|
+
borderBottomRightRadius: 0,
|
|
169
|
+
overflow: "hidden",
|
|
170
|
+
zIndex: (theme) => theme.zIndex.snackbar
|
|
171
|
+
}, (theme) => isGlassTheme(theme) ? glassStylesOf(theme) : {}],
|
|
172
|
+
children: [
|
|
173
|
+
/* @__PURE__ */ jsxs(Stack, { direction: "row", sx: { alignItems: "center", gap: 0.5, pl: 2, pr: 1, py: 1, bgcolor: "action.hover" }, children: [
|
|
174
|
+
/* @__PURE__ */ jsx(Typography, { variant: "subtitle2", component: "h2", noWrap: true, sx: { flex: 1 }, "aria-live": "polite", children: summaryTextOf(downloads, t) }),
|
|
175
|
+
/* @__PURE__ */ jsx(Tooltip, { title: isExpanded ? t("downloads.collapse") : t("downloads.expand"), children: /* @__PURE__ */ jsx(
|
|
176
|
+
IconButton,
|
|
177
|
+
{
|
|
178
|
+
size: "small",
|
|
179
|
+
"aria-expanded": isExpanded,
|
|
180
|
+
"aria-label": isExpanded ? t("downloads.collapse") : t("downloads.expand"),
|
|
181
|
+
onClick: () => setIsExpanded((wasExpanded) => !wasExpanded),
|
|
182
|
+
children: isExpanded ? /* @__PURE__ */ jsx(ExpandMoreIcon, { fontSize: "small" }) : /* @__PURE__ */ jsx(ExpandLessIcon, { fontSize: "small" })
|
|
183
|
+
}
|
|
184
|
+
) }),
|
|
185
|
+
activeCount === 0 && /* @__PURE__ */ jsx(Tooltip, { title: t("downloads.close"), children: /* @__PURE__ */ jsx(IconButton, { size: "small", "aria-label": t("downloads.close"), onClick: clearFinishedDownloads, children: /* @__PURE__ */ jsx(CloseIcon, { fontSize: "small" }) }) })
|
|
186
|
+
] }),
|
|
187
|
+
/* @__PURE__ */ jsxs(Collapse, { in: isExpanded, children: [
|
|
188
|
+
/* @__PURE__ */ jsx(Divider, {}),
|
|
189
|
+
/* @__PURE__ */ jsx(List, { dense: true, disablePadding: true, sx: { maxHeight: LIST_MAX_HEIGHT, overflowY: "auto", overflowX: "hidden" }, children: downloads.map((download, index) => /* @__PURE__ */ jsxs(Fragment, { children: [
|
|
190
|
+
index > 0 && /* @__PURE__ */ jsx(Divider, { component: "li" }),
|
|
191
|
+
/* @__PURE__ */ jsx(DownloadRow, { download })
|
|
192
|
+
] }, download.id)) })
|
|
193
|
+
] })
|
|
194
|
+
]
|
|
195
|
+
}
|
|
196
|
+
) });
|
|
197
|
+
}
|
|
198
|
+
export {
|
|
199
|
+
DownloadManager as default
|
|
200
|
+
};
|
|
201
|
+
//# sourceMappingURL=DownloadManager.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"DownloadManager.js","sources":["../../src/downloads/DownloadManager.jsx"],"sourcesContent":["// Panel de descargas al estilo de Google Drive: se pega abajo a la derecha SOLO mientras hay descargas, con una barra que\n// resume («Descargando 2 archivos…», «3 descargas listas») y la lista con el ícono del tipo de archivo y un anillo de\n// avance que termina en ✓. Con MUI y XState, sin Redux.\n//\n// Qué hace para no hacer ruido:\n// - no hay botón fijo: sin descargas no se pinta nada;\n// - se pliega a la barra con la flecha y se vuelve a abrir cuando entra otra descarga;\n// - cuando todo terminó bien se va solo a los AUTO_DISMISS_MILLISECONDS; si algo falló o se canceló se queda hasta que\n// la persona lo cierra, para que vea el motivo;\n// - la X solo aparece cuando ya nada descarga (cerrar a media descarga dejaría el archivo sin aviso de que terminó).\n//\n// Se monta UNA sola vez en la raíz de la aplicación. Lee la lista de downloadsActor; las descargas las arranca startDownload desde cada\n// pantalla. Los avisos (sonner) salen abajo a la izquierda, así que el panel va a la derecha.\n// Con el vidrio del tema (createToolkitTheme({glass: true})) el panel es de vidrio: flota sobre la pantalla.\n//\n// Genérico del paquete: function (regla de la casa).\nimport {Fragment, useEffect, useRef, useState} from 'react';\nimport {useToolkitTranslation} from '@/toolkit/useToolkitTranslation.js';\nimport {useSelector} from '@xstate/react';\nimport Box from '@mui/material/Box';\nimport CircularProgress from '@mui/material/CircularProgress';\nimport Collapse from '@mui/material/Collapse';\nimport Divider from '@mui/material/Divider';\nimport IconButton from '@mui/material/IconButton';\nimport List from '@mui/material/List';\nimport ListItem from '@mui/material/ListItem';\nimport Paper from '@mui/material/Paper';\nimport Slide from '@mui/material/Slide';\nimport Stack from '@mui/material/Stack';\nimport Tooltip from '@mui/material/Tooltip';\nimport Typography from '@mui/material/Typography';\nimport BlockOutlinedIcon from '@mui/icons-material/BlockOutlined';\nimport CheckCircleIcon from '@mui/icons-material/CheckCircle';\nimport CloseIcon from '@mui/icons-material/Close';\nimport ErrorOutlineIcon from '@mui/icons-material/ErrorOutline';\nimport ExpandLessIcon from '@mui/icons-material/ExpandLess';\nimport ExpandMoreIcon from '@mui/icons-material/ExpandMore';\nimport InsertDriveFileOutlinedIcon from '@mui/icons-material/InsertDriveFileOutlined';\nimport PictureAsPdfOutlinedIcon from '@mui/icons-material/PictureAsPdfOutlined';\nimport TableViewOutlinedIcon from '@mui/icons-material/TableViewOutlined';\nimport TextSnippetOutlinedIcon from '@mui/icons-material/TextSnippetOutlined';\n\nimport {cancelDownload, clearFinishedDownloads, countActiveDownloads, downloadsActor} from '@/downloads/downloadQueue.js';\nimport {DOWNLOAD_STATUS} from '@/downloads/downloadsMachine.js';\nimport {formatFileSize} from '@/formatting.js';\nimport {glassStylesOf, isGlassTheme} from '@/theme/glassSurface.js';\n\n// ícono y color del tipo de archivo (el color sale de la paleta del tema, claro y oscuro)\nconst FILE_TYPE_APPEARANCE = {\n xlsx: {Icon: TableViewOutlinedIcon, color: 'success.main'},\n csv: {Icon: TextSnippetOutlinedIcon, color: 'info.main'},\n pdf: {Icon: PictureAsPdfOutlinedIcon, color: 'error.main'},\n};\nconst DEFAULT_FILE_TYPE_APPEARANCE = {Icon: InsertDriveFileOutlinedIcon, color: 'text.secondary'};\n\n// cuánto se queda el panel después de que TODAS las descargas terminaron bien\nconst AUTO_DISMISS_MILLISECONDS = 5000;\n\n// separación del borde derecho y ancho del panel (en el teléfono ocupa el ancho menos los márgenes)\nconst SCREEN_EDGE_SPACING = 3;\nconst PANEL_WIDTH_PIXELS = 360;\nconst LIST_MAX_HEIGHT = '40vh';\nconst PROGRESS_RING_PIXELS = 22;\n\n/**\n * Tipo de archivo de una descarga: el que dijo quien la arrancó o, al terminar, la extensión del nombre.\n *\n * @param {object} download renglón de la lista (downloadsMachine)\n * @returns {{Icon: import('react').ElementType, color: string}}\n */\nfunction fileTypeAppearanceOf(download) {\n const extension = download.fileName?.split('.').pop()?.toLowerCase();\n return FILE_TYPE_APPEARANCE[download.format ?? extension] ?? DEFAULT_FILE_TYPE_APPEARANCE;\n}\n\n/**\n * Segunda línea del renglón: cuánto lleva, cuánto pesó o por qué no se pudo.\n *\n * @param {object} download\n * @param {Function} t traductor de common\n * @returns {string}\n */\nfunction detailTextOf(download, t) {\n if (download.status === DOWNLOAD_STATUS.completed) {\n return formatFileSize(download.loadedBytes);\n }\n if (download.status === DOWNLOAD_STATUS.failed) {\n return download.errorMessage ?? t('downloads.failed');\n }\n if (download.status === DOWNLOAD_STATUS.canceled) {\n return t('downloads.canceled');\n }\n if (download.loadedBytes === 0) {\n return t('downloads.preparing');\n }\n // un archivo que se arma al vuelo (el log) no dice su tamaño: se enseña lo que ya bajó\n return download.totalBytes\n ? t('downloads.progressOf', {loaded: formatFileSize(download.loadedBytes), total: formatFileSize(download.totalBytes)})\n : t('downloads.progressLoaded', {loaded: formatFileSize(download.loadedBytes)});\n}\n\n/**\n * Resumen de la barra, como en Drive: lo que está pasando ahora o cómo terminó.\n *\n * @param {Array<object>} downloads\n * @param {Function} t traductor de common\n * @returns {string}\n */\nfunction summaryTextOf(downloads, t) {\n const activeCount = countActiveDownloads(downloads);\n if (activeCount > 0) {\n return t('downloads.summaryDownloading', {count: activeCount});\n }\n const failedCount = downloads.filter((download) => download.status === DOWNLOAD_STATUS.failed).length;\n if (failedCount > 0) {\n return t('downloads.summaryFailed', {count: failedCount});\n }\n const completedCount = downloads.filter((download) => download.status === DOWNLOAD_STATUS.completed).length;\n return t('downloads.summaryCompleted', {count: completedCount});\n}\n\n/**\n * Lo que va a la derecha del renglón: el anillo de avance con su botón para cancelar, o cómo terminó.\n *\n * @param {{download: object, displayName: string}} props\n */\nfunction DownloadStatusIndicator({download, displayName}) {\n const {t} = useToolkitTranslation('common');\n\n if (download.status === DOWNLOAD_STATUS.completed) {\n return <CheckCircleIcon sx={{color: 'success.main'}} aria-label={t('downloads.completedOf', {name: displayName})} />;\n }\n if (download.status === DOWNLOAD_STATUS.failed) {\n return <ErrorOutlineIcon sx={{color: 'error.main'}} aria-label={t('downloads.failedOf', {name: displayName})} />;\n }\n if (download.status === DOWNLOAD_STATUS.canceled) {\n return <BlockOutlinedIcon sx={{color: 'text.disabled'}} aria-label={t('downloads.canceledOf', {name: displayName})} />;\n }\n\n const hasKnownSize = Boolean(download.totalBytes);\n // el anillo y, encima, la X para cancelar: como en Drive, un solo lugar para ver y detener\n return (\n <Tooltip title={t('downloads.cancel')}>\n <IconButton size=\"small\" aria-label={t('downloads.cancelOf', {name: displayName})} onClick={() => cancelDownload(download.id)}\n sx={{position: 'relative', width: PROGRESS_RING_PIXELS + 10, height: PROGRESS_RING_PIXELS + 10}}>\n <CircularProgress\n size={PROGRESS_RING_PIXELS}\n thickness={4}\n variant={hasKnownSize ? 'determinate' : 'indeterminate'}\n value={hasKnownSize ? Math.min(100, (download.loadedBytes * 100) / download.totalBytes) : undefined}\n sx={{position: 'absolute'}}\n />\n <CloseIcon sx={{fontSize: 12}} />\n </IconButton>\n </Tooltip>\n );\n}\n\n/**\n * Un renglón: ícono del tipo de archivo, nombre, detalle y estatus.\n *\n * @param {{download: object}} props\n */\nfunction DownloadRow({download}) {\n const {t} = useToolkitTranslation('common');\n const {Icon, color} = fileTypeAppearanceOf(download);\n const displayName = download.fileName ?? download.label;\n const isFailed = download.status === DOWNLOAD_STATUS.failed;\n\n return (\n // minWidth 0: sin él un nombre largo empuja el renglón y la lista enseña una barra horizontal\n <ListItem disableGutters sx={{gap: 1.5, px: 2, py: 1, minWidth: 0}}>\n <Icon fontSize=\"small\" sx={{color, flexShrink: 0}} />\n <Box sx={{minWidth: 0, flex: 1}}>\n <Tooltip title={displayName}>\n <Typography variant=\"body2\" noWrap>{displayName}</Typography>\n </Tooltip>\n <Typography variant=\"caption\" component=\"p\" noWrap={!isFailed}\n sx={{color: isFailed ? 'error.main' : 'text.secondary'}}>\n {detailTextOf(download, t)}\n </Typography>\n </Box>\n <Box sx={{flexShrink: 0, display: 'flex', alignItems: 'center'}}>\n <DownloadStatusIndicator download={download} displayName={displayName} />\n </Box>\n </ListItem>\n );\n}\n\nexport default function DownloadManager() {\n const {t} = useToolkitTranslation('common');\n const downloads = useSelector(downloadsActor, (snapshot) => snapshot.context.downloads);\n const [isExpanded, setIsExpanded] = useState(true);\n const previousCountRef = useRef(downloads.length);\n\n const activeCount = countActiveDownloads(downloads);\n const allSucceeded = downloads.length > 0 && downloads.every((download) => download.status === DOWNLOAD_STATUS.completed);\n\n // una descarga nueva vuelve a desplegar el panel aunque se haya plegado\n useEffect(() => {\n if (downloads.length > previousCountRef.current) {\n setIsExpanded(true);\n }\n previousCountRef.current = downloads.length;\n }, [downloads.length]);\n\n // todo terminó bien: el panel se va solo (con un error o una cancelada se queda para que se lea)\n useEffect(() => {\n if (!allSucceeded) {\n return undefined;\n }\n const dismissTimer = setTimeout(clearFinishedDownloads, AUTO_DISMISS_MILLISECONDS);\n return () => clearTimeout(dismissTimer);\n }, [allSucceeded, downloads.length]);\n\n return (\n <Slide direction=\"up\" in={downloads.length > 0} mountOnEnter unmountOnExit>\n <Paper\n elevation={8}\n role=\"region\"\n aria-label={t('downloads.title')}\n sx={[{\n position: 'fixed',\n right: (theme) => theme.spacing(SCREEN_EDGE_SPACING),\n bottom: 0,\n width: (theme) => `min(${PANEL_WIDTH_PIXELS}px, calc(100vw - ${theme.spacing(SCREEN_EDGE_SPACING * 2)}))`,\n // pegado al borde de abajo como en Drive: solo se redondean las esquinas de arriba\n borderBottomLeftRadius: 0,\n borderBottomRightRadius: 0,\n overflow: 'hidden',\n zIndex: (theme) => theme.zIndex.snackbar,\n }, (theme) => (isGlassTheme(theme) ? glassStylesOf(theme) : {})]}\n >\n <Stack direction=\"row\" sx={{alignItems: 'center', gap: 0.5, pl: 2, pr: 1, py: 1, bgcolor: 'action.hover'}}>\n <Typography variant=\"subtitle2\" component=\"h2\" noWrap sx={{flex: 1}} aria-live=\"polite\">\n {summaryTextOf(downloads, t)}\n </Typography>\n <Tooltip title={isExpanded ? t('downloads.collapse') : t('downloads.expand')}>\n <IconButton size=\"small\" aria-expanded={isExpanded}\n aria-label={isExpanded ? t('downloads.collapse') : t('downloads.expand')}\n onClick={() => setIsExpanded((wasExpanded) => !wasExpanded)}>\n {isExpanded ? <ExpandMoreIcon fontSize=\"small\" /> : <ExpandLessIcon fontSize=\"small\" />}\n </IconButton>\n </Tooltip>\n {/* cerrar a media descarga dejaría el archivo sin aviso de que terminó: la X sale cuando ya nada baja */}\n {activeCount === 0 && (\n <Tooltip title={t('downloads.close')}>\n <IconButton size=\"small\" aria-label={t('downloads.close')} onClick={clearFinishedDownloads}>\n <CloseIcon fontSize=\"small\" />\n </IconButton>\n </Tooltip>\n )}\n </Stack>\n <Collapse in={isExpanded}>\n <Divider />\n {/* OJO: overflowY auto también prende el scroll horizontal ante 1 px de más; se apaga explícito */}\n <List dense disablePadding sx={{maxHeight: LIST_MAX_HEIGHT, overflowY: 'auto', overflowX: 'hidden'}}>\n {downloads.map((download, index) => (\n <Fragment key={download.id}>\n {index > 0 && <Divider component=\"li\" />}\n <DownloadRow download={download} />\n </Fragment>\n ))}\n </List>\n </Collapse>\n </Paper>\n </Slide>\n );\n}\n"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,54 @@
|
|
|
1
|
+
import { createActor } from "xstate";
|
|
2
|
+
import { downloadsMachine, DOWNLOAD_STATUS } from "./downloadsMachine.js";
|
|
3
|
+
import { saveBlob } from "../files.js";
|
|
4
|
+
import { newIdentifier } from "../identifiers.js";
|
|
5
|
+
const downloadsActor = createActor(downloadsMachine).start();
|
|
6
|
+
const abortControllerByDownloadId = /* @__PURE__ */ new Map();
|
|
7
|
+
async function startDownload({ label, format, request, onCompleted }) {
|
|
8
|
+
const downloadId = newIdentifier();
|
|
9
|
+
const abortController = new AbortController();
|
|
10
|
+
abortControllerByDownloadId.set(downloadId, abortController);
|
|
11
|
+
downloadsActor.send({ type: "STARTED", id: downloadId, label, format });
|
|
12
|
+
try {
|
|
13
|
+
const { blob, fileName } = await request({
|
|
14
|
+
signal: abortController.signal,
|
|
15
|
+
// la petición avisa cada pedazo que llega; total viene en null cuando el servidor arma el archivo al vuelo (sin
|
|
16
|
+
// Content-Length) y el panel enseña lo que lleva en vez del porcentaje
|
|
17
|
+
onDownloadProgress: (progressEvent) => downloadsActor.send({
|
|
18
|
+
type: "PROGRESSED",
|
|
19
|
+
id: downloadId,
|
|
20
|
+
loadedBytes: progressEvent.loaded,
|
|
21
|
+
totalBytes: progressEvent.total
|
|
22
|
+
})
|
|
23
|
+
});
|
|
24
|
+
saveBlob(blob, fileName);
|
|
25
|
+
downloadsActor.send({ type: "COMPLETED", id: downloadId, fileName });
|
|
26
|
+
onCompleted?.(fileName);
|
|
27
|
+
} catch (error) {
|
|
28
|
+
if (abortController.signal.aborted) {
|
|
29
|
+
downloadsActor.send({ type: "CANCELED", id: downloadId });
|
|
30
|
+
} else {
|
|
31
|
+
downloadsActor.send({ type: "FAILED", id: downloadId, errorMessage: error?.message ?? null });
|
|
32
|
+
}
|
|
33
|
+
} finally {
|
|
34
|
+
abortControllerByDownloadId.delete(downloadId);
|
|
35
|
+
}
|
|
36
|
+
return downloadId;
|
|
37
|
+
}
|
|
38
|
+
function cancelDownload(downloadId) {
|
|
39
|
+
abortControllerByDownloadId.get(downloadId)?.abort();
|
|
40
|
+
}
|
|
41
|
+
function clearFinishedDownloads() {
|
|
42
|
+
downloadsActor.send({ type: "CLEAR_FINISHED" });
|
|
43
|
+
}
|
|
44
|
+
function countActiveDownloads(downloads) {
|
|
45
|
+
return downloads.filter((download) => download.status === DOWNLOAD_STATUS.downloading).length;
|
|
46
|
+
}
|
|
47
|
+
export {
|
|
48
|
+
cancelDownload,
|
|
49
|
+
clearFinishedDownloads,
|
|
50
|
+
countActiveDownloads,
|
|
51
|
+
downloadsActor,
|
|
52
|
+
startDownload
|
|
53
|
+
};
|
|
54
|
+
//# sourceMappingURL=downloadQueue.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"downloadQueue.js","sources":["../../src/downloads/downloadQueue.js"],"sourcesContent":["// Arranca descargas y las anota en la lista que pinta DownloadManager (el administrador de descargas).\n//\n// Uso (desde un módulo, que es quien conoce el API):\n// startDownload({\n// label: t('detail.downloadLog'),\n// request: (transferOptions) => ingestionApi.downloadProcessingLog(batchId, transferOptions),\n// onCompleted: () => refreshPeriods(),\n// });\n//\n// startDownload no espera a que termine quien la llama: el diálogo de confirmación se cierra en cuanto la descarga entra\n// a la lista y la persona sigue trabajando mientras baja (el log más grande tarda ~30 s). El panel (tipo Google Drive) es\n// el ÚNICO lugar que avisa: avance, lista y error con su texto del API (RFC 9457). Sin aviso aparte, para no avisar dos\n// veces lo mismo.\n//\n// Una sola lista para toda la app (un actor de módulo, como el cliente de createApiClient): la llenan varias pantallas y\n// la lee un solo panel montado en la raíz de la aplicación.\n//\n// Funciones puras del paquete, no renderizan: function (regla de la casa). No conoce el API: el archivo lo pide la\n// `request` que le pasan.\nimport {createActor} from 'xstate';\n\nimport {DOWNLOAD_STATUS, downloadsMachine} from '@/downloads/downloadsMachine.js';\nimport {saveBlob} from '@/files.js';\nimport {newIdentifier} from '@/identifiers.js';\n\nexport const downloadsActor = createActor(downloadsMachine).start();\n\n// cómo cancelar cada descarga en curso; vive fuera del contexto de la máquina porque un AbortController no es un dato\nconst abortControllerByDownloadId = new Map();\n\n/**\n * Descarga un archivo con avance en el panel, lo guarda en disco y avisa al terminar.\n *\n * @param {object} options\n * @param {string} options.label ya traducido; lo que se ve en el panel mientras todavía no se sabe el nombre del\n * archivo\n * @param {'xlsx'|'csv'|'pdf'} [options.format] para el ícono del tipo de archivo en el panel\n * @param {(transferOptions: {signal: AbortSignal, onDownloadProgress: (progress: {loaded: number, total?: number|null}) => void}) => Promise<{blob: Blob, fileName: string}>} options.request\n * @param {(fileName: string) => void} [options.onCompleted] p. ej. volver a pedir la tabla (si la descarga cambia algo\n * en el servidor)\n * @returns {Promise<string>} id de la descarga; la promesa se cumple cuando termina (bien, mal o cancelada), nunca falla\n */\nexport async function startDownload({label, format, request, onCompleted}) {\n const downloadId = newIdentifier();\n const abortController = new AbortController();\n abortControllerByDownloadId.set(downloadId, abortController);\n downloadsActor.send({type: 'STARTED', id: downloadId, label, format});\n\n try {\n const {blob, fileName} = await request({\n signal: abortController.signal,\n // la petición avisa cada pedazo que llega; total viene en null cuando el servidor arma el archivo al vuelo (sin\n // Content-Length) y el panel enseña lo que lleva en vez del porcentaje\n onDownloadProgress: (progressEvent) => downloadsActor.send({\n type: 'PROGRESSED', id: downloadId, loadedBytes: progressEvent.loaded, totalBytes: progressEvent.total,\n }),\n });\n saveBlob(blob, fileName);\n downloadsActor.send({type: 'COMPLETED', id: downloadId, fileName});\n onCompleted?.(fileName);\n } catch (error) {\n // OJO: cancelar también llega aquí como error (el AbortError del navegador); se distingue por la señal, no por el\n // tipo de error, porque cada `request` del proyecto puede tronar con el suyo\n if (abortController.signal.aborted) {\n downloadsActor.send({type: 'CANCELED', id: downloadId});\n } else {\n // el mensaje ya viene traducido del API (ApiError con el detail de RFC 9457)\n downloadsActor.send({type: 'FAILED', id: downloadId, errorMessage: error?.message ?? null});\n }\n } finally {\n abortControllerByDownloadId.delete(downloadId);\n }\n\n return downloadId;\n}\n\n/**\n * Cancela una descarga en curso (el panel la marca como cancelada).\n *\n * @param {string} downloadId\n */\nexport function cancelDownload(downloadId) {\n abortControllerByDownloadId.get(downloadId)?.abort();\n}\n\n/** Quita del panel todas las descargas terminadas (completadas, fallidas o canceladas). */\nexport function clearFinishedDownloads() {\n downloadsActor.send({type: 'CLEAR_FINISHED'});\n}\n\n/**\n * ¿Cuántas siguen descargando? Decide el resumen del panel y si se puede cerrar.\n *\n * @param {Array<object>} downloads\n * @returns {number}\n */\nexport function countActiveDownloads(downloads) {\n return downloads.filter((download) => download.status === DOWNLOAD_STATUS.downloading).length;\n}\n"],"names":[],"mappings":";;;;AAyBY,MAAC,iBAAiB,YAAY,gBAAgB,EAAE,MAAK;AAGjE,MAAM,8BAA8B,oBAAI,IAAG;AAcpC,eAAe,cAAc,EAAC,OAAO,QAAQ,SAAS,YAAW,GAAG;AACvE,QAAM,aAAa,cAAa;AAChC,QAAM,kBAAkB,IAAI,gBAAe;AAC3C,8BAA4B,IAAI,YAAY,eAAe;AAC3D,iBAAe,KAAK,EAAC,MAAM,WAAW,IAAI,YAAY,OAAO,OAAM,CAAC;AAEpE,MAAI;AACA,UAAM,EAAC,MAAM,SAAQ,IAAI,MAAM,QAAQ;AAAA,MACnC,QAAQ,gBAAgB;AAAA;AAAA;AAAA,MAGxB,oBAAoB,CAAC,kBAAkB,eAAe,KAAK;AAAA,QACvD,MAAM;AAAA,QAAc,IAAI;AAAA,QAAY,aAAa,cAAc;AAAA,QAAQ,YAAY,cAAc;AAAA,MACjH,CAAa;AAAA,IACb,CAAS;AACD,aAAS,MAAM,QAAQ;AACvB,mBAAe,KAAK,EAAC,MAAM,aAAa,IAAI,YAAY,SAAQ,CAAC;AACjE,kBAAc,QAAQ;AAAA,EAC1B,SAAS,OAAO;AAGZ,QAAI,gBAAgB,OAAO,SAAS;AAChC,qBAAe,KAAK,EAAC,MAAM,YAAY,IAAI,WAAU,CAAC;AAAA,IAC1D,OAAO;AAEH,qBAAe,KAAK,EAAC,MAAM,UAAU,IAAI,YAAY,cAAc,OAAO,WAAW,KAAI,CAAC;AAAA,IAC9F;AAAA,EACJ,UAAC;AACG,gCAA4B,OAAO,UAAU;AAAA,EACjD;AAEA,SAAO;AACX;AAOO,SAAS,eAAe,YAAY;AACvC,8BAA4B,IAAI,UAAU,GAAG,MAAK;AACtD;AAGO,SAAS,yBAAyB;AACrC,iBAAe,KAAK,EAAC,MAAM,iBAAgB,CAAC;AAChD;AAQO,SAAS,qBAAqB,WAAW;AAC5C,SAAO,UAAU,OAAO,CAAC,aAAa,SAAS,WAAW,gBAAgB,WAAW,EAAE;AAC3F;"}
|
|
@@ -0,0 +1,77 @@
|
|
|
1
|
+
import { setup, assign } from "xstate";
|
|
2
|
+
const DOWNLOAD_STATUS = Object.freeze({
|
|
3
|
+
downloading: "downloading",
|
|
4
|
+
completed: "completed",
|
|
5
|
+
failed: "failed",
|
|
6
|
+
canceled: "canceled"
|
|
7
|
+
});
|
|
8
|
+
function updateActiveDownload(downloads, downloadId, changes) {
|
|
9
|
+
return downloads.map((download) => download.id === downloadId && download.status === DOWNLOAD_STATUS.downloading ? { ...download, ...changes } : download);
|
|
10
|
+
}
|
|
11
|
+
const downloadsMachine = setup({}).createMachine({
|
|
12
|
+
id: "downloads",
|
|
13
|
+
context: {
|
|
14
|
+
// la más nueva primero
|
|
15
|
+
downloads: []
|
|
16
|
+
},
|
|
17
|
+
on: {
|
|
18
|
+
STARTED: {
|
|
19
|
+
actions: assign({
|
|
20
|
+
downloads: ({ context, event }) => [
|
|
21
|
+
{
|
|
22
|
+
id: event.id,
|
|
23
|
+
label: event.label,
|
|
24
|
+
// xlsx, csv o pdf: el panel pinta el ícono del tipo de archivo (null si quien descarga no lo dice)
|
|
25
|
+
format: event.format ?? null,
|
|
26
|
+
fileName: null,
|
|
27
|
+
status: DOWNLOAD_STATUS.downloading,
|
|
28
|
+
loadedBytes: 0,
|
|
29
|
+
totalBytes: null,
|
|
30
|
+
errorMessage: null
|
|
31
|
+
},
|
|
32
|
+
...context.downloads
|
|
33
|
+
]
|
|
34
|
+
})
|
|
35
|
+
},
|
|
36
|
+
PROGRESSED: {
|
|
37
|
+
actions: assign({
|
|
38
|
+
downloads: ({ context, event }) => updateActiveDownload(context.downloads, event.id, {
|
|
39
|
+
loadedBytes: event.loadedBytes,
|
|
40
|
+
// un archivo que se arma al vuelo (el log) no dice su tamaño: se queda en null y la barra no tiene fin
|
|
41
|
+
totalBytes: event.totalBytes ?? null
|
|
42
|
+
})
|
|
43
|
+
})
|
|
44
|
+
},
|
|
45
|
+
COMPLETED: {
|
|
46
|
+
actions: assign({
|
|
47
|
+
downloads: ({ context, event }) => updateActiveDownload(context.downloads, event.id, {
|
|
48
|
+
status: DOWNLOAD_STATUS.completed,
|
|
49
|
+
fileName: event.fileName
|
|
50
|
+
})
|
|
51
|
+
})
|
|
52
|
+
},
|
|
53
|
+
FAILED: {
|
|
54
|
+
actions: assign({
|
|
55
|
+
downloads: ({ context, event }) => updateActiveDownload(context.downloads, event.id, {
|
|
56
|
+
status: DOWNLOAD_STATUS.failed,
|
|
57
|
+
errorMessage: event.errorMessage ?? null
|
|
58
|
+
})
|
|
59
|
+
})
|
|
60
|
+
},
|
|
61
|
+
CANCELED: {
|
|
62
|
+
actions: assign({
|
|
63
|
+
downloads: ({ context, event }) => updateActiveDownload(context.downloads, event.id, { status: DOWNLOAD_STATUS.canceled })
|
|
64
|
+
})
|
|
65
|
+
},
|
|
66
|
+
CLEAR_FINISHED: {
|
|
67
|
+
actions: assign({
|
|
68
|
+
downloads: ({ context }) => context.downloads.filter((download) => download.status === DOWNLOAD_STATUS.downloading)
|
|
69
|
+
})
|
|
70
|
+
}
|
|
71
|
+
}
|
|
72
|
+
});
|
|
73
|
+
export {
|
|
74
|
+
DOWNLOAD_STATUS,
|
|
75
|
+
downloadsMachine
|
|
76
|
+
};
|
|
77
|
+
//# sourceMappingURL=downloadsMachine.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"downloadsMachine.js","sources":["../../src/downloads/downloadsMachine.js"],"sourcesContent":["// Lista de descargas de la sesión (el «administrador de descargas», sin Redux).\n//\n// Cada descarga vive así:\n//\n// STARTED ──▶ downloading ──PROGRESSED──▶ downloading\n// │\n// ├── COMPLETED ──▶ completed ─┐\n// ├── FAILED ─────▶ failed ────┼── CLEAR_FINISHED ──▶ (sale de la lista)\n// └── CANCELED ───▶ canceled ──┘\n//\n// Por qué una máquina y no un useState: la lista la alimentan varias pantallas a la vez (quien descarga) y la lee un\n// solo panel (DownloadManager); una descarga que ya terminó no puede volver a «descargando» por un aviso de progreso\n// que llegó tarde. Lo prueba downloadsMachine.test.js.\n//\n// Pura: solo importa xstate. Quien descarga de verdad es startDownload (downloadQueue.js); el paquete no conoce el API.\nimport {assign, setup} from 'xstate';\n\n/** Estatus de una descarga; son los que pinta el panel (con su texto en common:downloads.statuses). */\nexport const DOWNLOAD_STATUS = Object.freeze({\n downloading: 'downloading',\n completed: 'completed',\n failed: 'failed',\n canceled: 'canceled',\n});\n\n/**\n * Cambia una sola descarga de la lista, y solo si sigue descargando (las terminadas ya no cambian).\n *\n * @param {Array<object>} downloads\n * @param {string} downloadId\n * @param {object} changes\n * @returns {Array<object>}\n */\nfunction updateActiveDownload(downloads, downloadId, changes) {\n return downloads.map((download) => (\n download.id === downloadId && download.status === DOWNLOAD_STATUS.downloading ? {...download, ...changes} : download\n ));\n}\n\nexport const downloadsMachine = setup({}).createMachine({\n id: 'downloads',\n context: {\n // la más nueva primero\n downloads: [],\n },\n on: {\n STARTED: {\n actions: assign({\n downloads: ({context, event}) => [\n {\n id: event.id,\n label: event.label,\n // xlsx, csv o pdf: el panel pinta el ícono del tipo de archivo (null si quien descarga no lo dice)\n format: event.format ?? null,\n fileName: null,\n status: DOWNLOAD_STATUS.downloading,\n loadedBytes: 0,\n totalBytes: null,\n errorMessage: null,\n },\n ...context.downloads,\n ],\n }),\n },\n PROGRESSED: {\n actions: assign({\n downloads: ({context, event}) => updateActiveDownload(context.downloads, event.id, {\n loadedBytes: event.loadedBytes,\n // un archivo que se arma al vuelo (el log) no dice su tamaño: se queda en null y la barra no tiene fin\n totalBytes: event.totalBytes ?? null,\n }),\n }),\n },\n COMPLETED: {\n actions: assign({\n downloads: ({context, event}) => updateActiveDownload(context.downloads, event.id, {\n status: DOWNLOAD_STATUS.completed,\n fileName: event.fileName,\n }),\n }),\n },\n FAILED: {\n actions: assign({\n downloads: ({context, event}) => updateActiveDownload(context.downloads, event.id, {\n status: DOWNLOAD_STATUS.failed,\n errorMessage: event.errorMessage ?? null,\n }),\n }),\n },\n CANCELED: {\n actions: assign({\n downloads: ({context, event}) => updateActiveDownload(context.downloads, event.id, {status: DOWNLOAD_STATUS.canceled}),\n }),\n },\n CLEAR_FINISHED: {\n actions: assign({\n downloads: ({context}) => context.downloads.filter((download) => download.status === DOWNLOAD_STATUS.downloading),\n }),\n },\n },\n});\n"],"names":[],"mappings":";AAkBY,MAAC,kBAAkB,OAAO,OAAO;AAAA,EACzC,aAAa;AAAA,EACb,WAAW;AAAA,EACX,QAAQ;AAAA,EACR,UAAU;AACd,CAAC;AAUD,SAAS,qBAAqB,WAAW,YAAY,SAAS;AAC1D,SAAO,UAAU,IAAI,CAAC,aAClB,SAAS,OAAO,cAAc,SAAS,WAAW,gBAAgB,cAAc,EAAC,GAAG,UAAU,GAAG,QAAO,IAAI,QAC/G;AACL;AAEY,MAAC,mBAAmB,MAAM,EAAE,EAAE,cAAc;AAAA,EACpD,IAAI;AAAA,EACJ,SAAS;AAAA;AAAA,IAEL,WAAW,CAAA;AAAA,EACnB;AAAA,EACI,IAAI;AAAA,IACA,SAAS;AAAA,MACL,SAAS,OAAO;AAAA,QACZ,WAAW,CAAC,EAAC,SAAS,MAAK,MAAM;AAAA,UAC7B;AAAA,YACI,IAAI,MAAM;AAAA,YACV,OAAO,MAAM;AAAA;AAAA,YAEb,QAAQ,MAAM,UAAU;AAAA,YACxB,UAAU;AAAA,YACV,QAAQ,gBAAgB;AAAA,YACxB,aAAa;AAAA,YACb,YAAY;AAAA,YACZ,cAAc;AAAA,UACtC;AAAA,UACoB,GAAG,QAAQ;AAAA,QAC/B;AAAA,MACA,CAAa;AAAA,IACb;AAAA,IACQ,YAAY;AAAA,MACR,SAAS,OAAO;AAAA,QACZ,WAAW,CAAC,EAAC,SAAS,MAAK,MAAM,qBAAqB,QAAQ,WAAW,MAAM,IAAI;AAAA,UAC/E,aAAa,MAAM;AAAA;AAAA,UAEnB,YAAY,MAAM,cAAc;AAAA,QACpD,CAAiB;AAAA,MACjB,CAAa;AAAA,IACb;AAAA,IACQ,WAAW;AAAA,MACP,SAAS,OAAO;AAAA,QACZ,WAAW,CAAC,EAAC,SAAS,MAAK,MAAM,qBAAqB,QAAQ,WAAW,MAAM,IAAI;AAAA,UAC/E,QAAQ,gBAAgB;AAAA,UACxB,UAAU,MAAM;AAAA,QACpC,CAAiB;AAAA,MACjB,CAAa;AAAA,IACb;AAAA,IACQ,QAAQ;AAAA,MACJ,SAAS,OAAO;AAAA,QACZ,WAAW,CAAC,EAAC,SAAS,MAAK,MAAM,qBAAqB,QAAQ,WAAW,MAAM,IAAI;AAAA,UAC/E,QAAQ,gBAAgB;AAAA,UACxB,cAAc,MAAM,gBAAgB;AAAA,QACxD,CAAiB;AAAA,MACjB,CAAa;AAAA,IACb;AAAA,IACQ,UAAU;AAAA,MACN,SAAS,OAAO;AAAA,QACZ,WAAW,CAAC,EAAC,SAAS,MAAK,MAAM,qBAAqB,QAAQ,WAAW,MAAM,IAAI,EAAC,QAAQ,gBAAgB,SAAQ,CAAC;AAAA,MACrI,CAAa;AAAA,IACb;AAAA,IACQ,gBAAgB;AAAA,MACZ,SAAS,OAAO;AAAA,QACZ,WAAW,CAAC,EAAC,QAAO,MAAM,QAAQ,UAAU,OAAO,CAAC,aAAa,SAAS,WAAW,gBAAgB,WAAW;AAAA,MAChI,CAAa;AAAA,IACb;AAAA,EACA;AACA,CAAC;"}
|