@open-mercato/core 0.4.2-canary-ed15f2e753 → 0.4.2-canary-e2aeb1a7bf
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/dist/generated/entities/notification/index.js +57 -0
- package/dist/generated/entities/notification/index.js.map +7 -0
- package/dist/generated/entities.ids.generated.js +5 -2
- package/dist/generated/entities.ids.generated.js.map +2 -2
- package/dist/generated/entity-fields-registry.js +2 -2
- package/dist/generated/entity-fields-registry.js.map +2 -2
- package/dist/modules/api_docs/frontend/docs/api/page.js +3 -2
- package/dist/modules/api_docs/frontend/docs/api/page.js.map +2 -2
- package/dist/modules/api_keys/backend/api-keys/page.js +1 -1
- package/dist/modules/api_keys/backend/api-keys/page.js.map +2 -2
- package/dist/modules/api_keys/setup.js +11 -0
- package/dist/modules/api_keys/setup.js.map +7 -0
- package/dist/modules/attachments/components/AttachmentLibrary.js +5 -1
- package/dist/modules/attachments/components/AttachmentLibrary.js.map +2 -2
- package/dist/modules/attachments/components/AttachmentPartitionSettings.js +2 -0
- package/dist/modules/attachments/components/AttachmentPartitionSettings.js.map +2 -2
- package/dist/modules/attachments/lib/assignmentDetails.js +31 -17
- package/dist/modules/attachments/lib/assignmentDetails.js.map +2 -2
- package/dist/modules/attachments/lib/partitions.js +3 -3
- package/dist/modules/attachments/lib/partitions.js.map +2 -2
- package/dist/modules/attachments/setup.js +11 -0
- package/dist/modules/attachments/setup.js.map +7 -0
- package/dist/modules/audit_logs/setup.js +12 -0
- package/dist/modules/audit_logs/setup.js.map +7 -0
- package/dist/modules/auth/api/admin/nav.js +4 -3
- package/dist/modules/auth/api/admin/nav.js.map +2 -2
- package/dist/modules/auth/api/login.js +25 -6
- package/dist/modules/auth/api/login.js.map +2 -2
- package/dist/modules/auth/api/profile/route.js +157 -0
- package/dist/modules/auth/api/profile/route.js.map +7 -0
- package/dist/modules/auth/api/reset/confirm.js +25 -2
- package/dist/modules/auth/api/reset/confirm.js.map +2 -2
- package/dist/modules/auth/api/reset.js +23 -0
- package/dist/modules/auth/api/reset.js.map +2 -2
- package/dist/modules/auth/api/sidebar/preferences/route.js +14 -9
- package/dist/modules/auth/api/sidebar/preferences/route.js.map +2 -2
- package/dist/modules/auth/api/users/route.js +4 -2
- package/dist/modules/auth/api/users/route.js.map +2 -2
- package/dist/modules/auth/backend/auth/profile/page.js +141 -0
- package/dist/modules/auth/backend/auth/profile/page.js.map +7 -0
- package/dist/modules/auth/backend/auth/profile/page.meta.js +13 -0
- package/dist/modules/auth/backend/auth/profile/page.meta.js.map +7 -0
- package/dist/modules/auth/backend/roles/[id]/edit/page.js +4 -1
- package/dist/modules/auth/backend/roles/[id]/edit/page.js.map +2 -2
- package/dist/modules/auth/backend/roles/page.js +3 -3
- package/dist/modules/auth/backend/roles/page.js.map +2 -2
- package/dist/modules/auth/backend/users/[id]/edit/page.js +18 -3
- package/dist/modules/auth/backend/users/[id]/edit/page.js.map +2 -2
- package/dist/modules/auth/backend/users/create/page.js +15 -2
- package/dist/modules/auth/backend/users/create/page.js.map +2 -2
- package/dist/modules/auth/backend/users/page.js +3 -3
- package/dist/modules/auth/backend/users/page.js.map +2 -2
- package/dist/modules/auth/cli.js +25 -11
- package/dist/modules/auth/cli.js.map +2 -2
- package/dist/modules/auth/commands/users.js +59 -2
- package/dist/modules/auth/commands/users.js.map +2 -2
- package/dist/modules/auth/data/validators.js +6 -3
- package/dist/modules/auth/data/validators.js.map +2 -2
- package/dist/modules/auth/frontend/login.js +112 -3
- package/dist/modules/auth/frontend/login.js.map +2 -2
- package/dist/modules/auth/frontend/reset/[token]/page.js +20 -10
- package/dist/modules/auth/frontend/reset/[token]/page.js.map +2 -2
- package/dist/modules/auth/lib/setup-app.js +70 -167
- package/dist/modules/auth/lib/setup-app.js.map +2 -2
- package/dist/modules/auth/notifications.js +112 -0
- package/dist/modules/auth/notifications.js.map +7 -0
- package/dist/modules/auth/services/authService.js +24 -3
- package/dist/modules/auth/services/authService.js.map +2 -2
- package/dist/modules/auth/setup.js +11 -0
- package/dist/modules/auth/setup.js.map +7 -0
- package/dist/modules/business_rules/api/execute/route.js +7 -1
- package/dist/modules/business_rules/api/execute/route.js.map +2 -2
- package/dist/modules/business_rules/backend/rules/page.js +4 -0
- package/dist/modules/business_rules/backend/rules/page.js.map +2 -2
- package/dist/modules/business_rules/backend/sets/page.js +3 -0
- package/dist/modules/business_rules/backend/sets/page.js.map +2 -2
- package/dist/modules/business_rules/cli.js +2 -1
- package/dist/modules/business_rules/cli.js.map +2 -2
- package/dist/modules/business_rules/data/validators.js +0 -34
- package/dist/modules/business_rules/data/validators.js.map +2 -2
- package/dist/modules/business_rules/index.js +1 -21
- package/dist/modules/business_rules/index.js.map +2 -2
- package/dist/modules/business_rules/lib/rule-engine.js +34 -185
- package/dist/modules/business_rules/lib/rule-engine.js.map +2 -2
- package/dist/modules/business_rules/notifications.js +28 -0
- package/dist/modules/business_rules/notifications.js.map +7 -0
- package/dist/modules/business_rules/setup.js +11 -0
- package/dist/modules/business_rules/setup.js.map +7 -0
- package/dist/modules/business_rules/subscribers/rule-execution-failed-notification.js +37 -0
- package/dist/modules/business_rules/subscribers/rule-execution-failed-notification.js.map +7 -0
- package/dist/modules/catalog/components/PriceKindSettings.js +2 -0
- package/dist/modules/catalog/components/PriceKindSettings.js.map +2 -2
- package/dist/modules/catalog/components/categories/CategoriesDataTable.js +2 -2
- package/dist/modules/catalog/components/categories/CategoriesDataTable.js.map +2 -2
- package/dist/modules/catalog/components/products/ProductsDataTable.js +2 -0
- package/dist/modules/catalog/components/products/ProductsDataTable.js.map +2 -2
- package/dist/modules/catalog/notifications.js +28 -0
- package/dist/modules/catalog/notifications.js.map +7 -0
- package/dist/modules/catalog/setup.js +22 -0
- package/dist/modules/catalog/setup.js.map +7 -0
- package/dist/modules/catalog/subscribers/low-stock-notification.js +38 -0
- package/dist/modules/catalog/subscribers/low-stock-notification.js.map +7 -0
- package/dist/modules/configs/cli.js +6 -0
- package/dist/modules/configs/cli.js.map +2 -2
- package/dist/modules/configs/components/CachePanel.js +4 -4
- package/dist/modules/configs/components/CachePanel.js.map +2 -2
- package/dist/modules/configs/lib/system-status.js +48 -1
- package/dist/modules/configs/lib/system-status.js.map +2 -2
- package/dist/modules/configs/lib/upgrade-actions.js +1 -302
- package/dist/modules/configs/lib/upgrade-actions.js.map +2 -2
- package/dist/modules/configs/setup.js +16 -0
- package/dist/modules/configs/setup.js.map +7 -0
- package/dist/modules/currencies/backend/currencies/page.js +3 -0
- package/dist/modules/currencies/backend/currencies/page.js.map +2 -2
- package/dist/modules/currencies/backend/exchange-rates/page.js +2 -0
- package/dist/modules/currencies/backend/exchange-rates/page.js.map +2 -2
- package/dist/modules/currencies/setup.js +16 -0
- package/dist/modules/currencies/setup.js.map +7 -0
- package/dist/modules/customers/backend/customers/companies/page.js +3 -0
- package/dist/modules/customers/backend/customers/companies/page.js.map +2 -2
- package/dist/modules/customers/backend/customers/deals/page.js +3 -0
- package/dist/modules/customers/backend/customers/deals/page.js.map +2 -2
- package/dist/modules/customers/backend/customers/people/page.js +3 -0
- package/dist/modules/customers/backend/customers/people/page.js.map +2 -2
- package/dist/modules/customers/commands/deals.js +31 -0
- package/dist/modules/customers/commands/deals.js.map +2 -2
- package/dist/modules/customers/components/CustomerTodosTable.js +1 -0
- package/dist/modules/customers/components/CustomerTodosTable.js.map +2 -2
- package/dist/modules/customers/notifications.js +48 -0
- package/dist/modules/customers/notifications.js.map +7 -0
- package/dist/modules/customers/setup.js +36 -0
- package/dist/modules/customers/setup.js.map +7 -0
- package/dist/modules/customers/widgets/dashboard/customer-todos/widget.js +2 -1
- package/dist/modules/customers/widgets/dashboard/customer-todos/widget.js.map +2 -2
- package/dist/modules/customers/widgets/dashboard/new-customers/widget.js +2 -1
- package/dist/modules/customers/widgets/dashboard/new-customers/widget.js.map +2 -2
- package/dist/modules/customers/widgets/dashboard/new-deals/widget.js +2 -1
- package/dist/modules/customers/widgets/dashboard/new-deals/widget.js.map +2 -2
- package/dist/modules/customers/widgets/dashboard/next-interactions/widget.js +2 -1
- package/dist/modules/customers/widgets/dashboard/next-interactions/widget.js.map +2 -2
- package/dist/modules/dashboards/cli.js +44 -5
- package/dist/modules/dashboards/cli.js.map +2 -2
- package/dist/modules/dashboards/components/WidgetVisibilityEditor.js +16 -11
- package/dist/modules/dashboards/components/WidgetVisibilityEditor.js.map +3 -3
- package/dist/modules/dashboards/lib/role-widgets.js +58 -0
- package/dist/modules/dashboards/lib/role-widgets.js.map +7 -0
- package/dist/modules/dashboards/services/widgetDataService.js +139 -3
- package/dist/modules/dashboards/services/widgetDataService.js.map +2 -2
- package/dist/modules/dashboards/setup.js +27 -0
- package/dist/modules/dashboards/setup.js.map +7 -0
- package/dist/modules/dashboards/widgets/dashboard/aov-kpi/widget.js +2 -1
- package/dist/modules/dashboards/widgets/dashboard/aov-kpi/widget.js.map +2 -2
- package/dist/modules/dashboards/widgets/dashboard/new-customers-kpi/widget.js +2 -1
- package/dist/modules/dashboards/widgets/dashboard/new-customers-kpi/widget.js.map +2 -2
- package/dist/modules/dashboards/widgets/dashboard/orders-by-status/widget.js +2 -1
- package/dist/modules/dashboards/widgets/dashboard/orders-by-status/widget.js.map +2 -2
- package/dist/modules/dashboards/widgets/dashboard/orders-kpi/widget.js +2 -1
- package/dist/modules/dashboards/widgets/dashboard/orders-kpi/widget.js.map +2 -2
- package/dist/modules/dashboards/widgets/dashboard/pipeline-summary/widget.js +2 -1
- package/dist/modules/dashboards/widgets/dashboard/pipeline-summary/widget.js.map +2 -2
- package/dist/modules/dashboards/widgets/dashboard/revenue-kpi/widget.js +2 -1
- package/dist/modules/dashboards/widgets/dashboard/revenue-kpi/widget.js.map +2 -2
- package/dist/modules/dashboards/widgets/dashboard/revenue-trend/widget.js +2 -1
- package/dist/modules/dashboards/widgets/dashboard/revenue-trend/widget.js.map +2 -2
- package/dist/modules/dashboards/widgets/dashboard/sales-by-region/widget.js +2 -1
- package/dist/modules/dashboards/widgets/dashboard/sales-by-region/widget.js.map +2 -2
- package/dist/modules/dashboards/widgets/dashboard/top-customers/widget.js +2 -1
- package/dist/modules/dashboards/widgets/dashboard/top-customers/widget.js.map +2 -2
- package/dist/modules/dashboards/widgets/dashboard/top-products/widget.js +2 -1
- package/dist/modules/dashboards/widgets/dashboard/top-products/widget.js.map +2 -2
- package/dist/modules/dictionaries/components/DictionaryTable.js +2 -0
- package/dist/modules/dictionaries/components/DictionaryTable.js.map +2 -2
- package/dist/modules/dictionaries/setup.js +12 -0
- package/dist/modules/dictionaries/setup.js.map +7 -0
- package/dist/modules/directory/api/get/tenants/lookup.js +70 -0
- package/dist/modules/directory/api/get/tenants/lookup.js.map +7 -0
- package/dist/modules/directory/backend/directory/organizations/page.js +2 -2
- package/dist/modules/directory/backend/directory/organizations/page.js.map +2 -2
- package/dist/modules/directory/backend/directory/tenants/page.js +2 -2
- package/dist/modules/directory/backend/directory/tenants/page.js.map +2 -2
- package/dist/modules/directory/setup.js +12 -0
- package/dist/modules/directory/setup.js.map +7 -0
- package/dist/modules/entities/backend/entities/user/[entityId]/records/page.js +2 -2
- package/dist/modules/entities/backend/entities/user/[entityId]/records/page.js.map +2 -2
- package/dist/modules/entities/components/SystemEntitiesTable.js +1 -1
- package/dist/modules/entities/components/SystemEntitiesTable.js.map +2 -2
- package/dist/modules/entities/components/UserEntitiesTable.js +2 -2
- package/dist/modules/entities/components/UserEntitiesTable.js.map +2 -2
- package/dist/modules/entities/setup.js +11 -0
- package/dist/modules/entities/setup.js.map +7 -0
- package/dist/modules/feature_toggles/components/FeatureTogglesTable.js +3 -3
- package/dist/modules/feature_toggles/components/FeatureTogglesTable.js.map +2 -2
- package/dist/modules/feature_toggles/components/OverridesTable.js +1 -1
- package/dist/modules/feature_toggles/components/OverridesTable.js.map +2 -2
- package/dist/modules/feature_toggles/setup.js +11 -0
- package/dist/modules/feature_toggles/setup.js.map +7 -0
- package/dist/modules/notifications/acl.js +11 -0
- package/dist/modules/notifications/acl.js.map +7 -0
- package/dist/modules/notifications/api/[id]/action/route.js +74 -0
- package/dist/modules/notifications/api/[id]/action/route.js.map +7 -0
- package/dist/modules/notifications/api/[id]/dismiss/route.js +15 -0
- package/dist/modules/notifications/api/[id]/dismiss/route.js.map +7 -0
- package/dist/modules/notifications/api/[id]/read/route.js +15 -0
- package/dist/modules/notifications/api/[id]/read/route.js.map +7 -0
- package/dist/modules/notifications/api/[id]/restore/route.js +53 -0
- package/dist/modules/notifications/api/[id]/restore/route.js.map +7 -0
- package/dist/modules/notifications/api/batch/route.js +17 -0
- package/dist/modules/notifications/api/batch/route.js.map +7 -0
- package/dist/modules/notifications/api/feature/route.js +17 -0
- package/dist/modules/notifications/api/feature/route.js.map +7 -0
- package/dist/modules/notifications/api/mark-all-read/route.js +35 -0
- package/dist/modules/notifications/api/mark-all-read/route.js.map +7 -0
- package/dist/modules/notifications/api/openapi.js +76 -0
- package/dist/modules/notifications/api/openapi.js.map +7 -0
- package/dist/modules/notifications/api/role/route.js +17 -0
- package/dist/modules/notifications/api/role/route.js.map +7 -0
- package/dist/modules/notifications/api/route.js +85 -0
- package/dist/modules/notifications/api/route.js.map +7 -0
- package/dist/modules/notifications/api/settings/route.js +155 -0
- package/dist/modules/notifications/api/settings/route.js.map +7 -0
- package/dist/modules/notifications/api/unread-count/route.js +38 -0
- package/dist/modules/notifications/api/unread-count/route.js.map +7 -0
- package/dist/modules/notifications/backend/config/notifications/page.js +10 -0
- package/dist/modules/notifications/backend/config/notifications/page.js.map +7 -0
- package/dist/modules/notifications/backend/config/notifications/page.meta.js +24 -0
- package/dist/modules/notifications/backend/config/notifications/page.meta.js.map +7 -0
- package/dist/modules/notifications/cli.js +16 -0
- package/dist/modules/notifications/cli.js.map +7 -0
- package/dist/modules/notifications/data/entities.js +112 -0
- package/dist/modules/notifications/data/entities.js.map +7 -0
- package/dist/modules/notifications/data/validators.js +98 -0
- package/dist/modules/notifications/data/validators.js.map +7 -0
- package/dist/modules/notifications/di.js +13 -0
- package/dist/modules/notifications/di.js.map +7 -0
- package/dist/modules/notifications/emails/NotificationEmail.js +58 -0
- package/dist/modules/notifications/emails/NotificationEmail.js.map +7 -0
- package/dist/modules/notifications/frontend/NotificationInboxPageClient.js +44 -0
- package/dist/modules/notifications/frontend/NotificationInboxPageClient.js.map +7 -0
- package/dist/modules/notifications/frontend/NotificationSettingsPageClient.js +220 -0
- package/dist/modules/notifications/frontend/NotificationSettingsPageClient.js.map +7 -0
- package/dist/modules/notifications/index.js +14 -0
- package/dist/modules/notifications/index.js.map +7 -0
- package/dist/modules/notifications/lib/deliveryConfig.js +107 -0
- package/dist/modules/notifications/lib/deliveryConfig.js.map +7 -0
- package/dist/modules/notifications/lib/deliveryStrategies.js +14 -0
- package/dist/modules/notifications/lib/deliveryStrategies.js.map +7 -0
- package/dist/modules/notifications/lib/events.js +12 -0
- package/dist/modules/notifications/lib/events.js.map +7 -0
- package/dist/modules/notifications/lib/notificationBuilder.js +66 -0
- package/dist/modules/notifications/lib/notificationBuilder.js.map +7 -0
- package/dist/modules/notifications/lib/notificationFactory.js +54 -0
- package/dist/modules/notifications/lib/notificationFactory.js.map +7 -0
- package/dist/modules/notifications/lib/notificationMapper.js +34 -0
- package/dist/modules/notifications/lib/notificationMapper.js.map +7 -0
- package/dist/modules/notifications/lib/notificationRecipients.js +35 -0
- package/dist/modules/notifications/lib/notificationRecipients.js.map +7 -0
- package/dist/modules/notifications/lib/notificationService.js +279 -0
- package/dist/modules/notifications/lib/notificationService.js.map +7 -0
- package/dist/modules/notifications/lib/routeHelpers.js +101 -0
- package/dist/modules/notifications/lib/routeHelpers.js.map +7 -0
- package/dist/modules/notifications/lib/safeHref.js +24 -0
- package/dist/modules/notifications/lib/safeHref.js.map +7 -0
- package/dist/modules/notifications/migrations/Migration20260123000001.js +70 -0
- package/dist/modules/notifications/migrations/Migration20260123000001.js.map +7 -0
- package/dist/modules/notifications/migrations/Migration20260126150000.js +37 -0
- package/dist/modules/notifications/migrations/Migration20260126150000.js.map +7 -0
- package/dist/modules/notifications/migrations/Migration20260129082610.js +13 -0
- package/dist/modules/notifications/migrations/Migration20260129082610.js.map +7 -0
- package/dist/modules/notifications/subscribers/deliver-notification.js +165 -0
- package/dist/modules/notifications/subscribers/deliver-notification.js.map +7 -0
- package/dist/modules/notifications/workers/create-notification.worker.js +70 -0
- package/dist/modules/notifications/workers/create-notification.worker.js.map +7 -0
- package/dist/modules/perspectives/setup.js +12 -0
- package/dist/modules/perspectives/setup.js.map +7 -0
- package/dist/modules/planner/backend/planner/availability-rulesets/page.js +2 -2
- package/dist/modules/planner/backend/planner/availability-rulesets/page.js.map +2 -2
- package/dist/modules/planner/setup.js +21 -0
- package/dist/modules/planner/setup.js.map +7 -0
- package/dist/modules/query_index/cli.js +63 -7
- package/dist/modules/query_index/cli.js.map +2 -2
- package/dist/modules/query_index/components/QueryIndexesTable.js +7 -1
- package/dist/modules/query_index/components/QueryIndexesTable.js.map +2 -2
- package/dist/modules/query_index/setup.js +11 -0
- package/dist/modules/query_index/setup.js.map +7 -0
- package/dist/modules/resources/backend/resources/resource-types/page.js +2 -2
- package/dist/modules/resources/backend/resources/resource-types/page.js.map +2 -2
- package/dist/modules/resources/backend/resources/resources/page.js +2 -2
- package/dist/modules/resources/backend/resources/resources/page.js.map +2 -2
- package/dist/modules/resources/setup.js +21 -0
- package/dist/modules/resources/setup.js.map +7 -0
- package/dist/modules/sales/acl.js +0 -1
- package/dist/modules/sales/acl.js.map +2 -2
- package/dist/modules/sales/backend/sales/channels/offers/page.js +2 -0
- package/dist/modules/sales/backend/sales/channels/offers/page.js.map +2 -2
- package/dist/modules/sales/backend/sales/channels/page.js +2 -0
- package/dist/modules/sales/backend/sales/channels/page.js.map +2 -2
- package/dist/modules/sales/backend/sales/documents/[id]/page.js +0 -12
- package/dist/modules/sales/backend/sales/documents/[id]/page.js.map +2 -2
- package/dist/modules/sales/cli.js +2 -42
- package/dist/modules/sales/cli.js.map +2 -2
- package/dist/modules/sales/commands/documents.js +53 -62
- package/dist/modules/sales/commands/documents.js.map +2 -2
- package/dist/modules/sales/commands/payments.js +26 -0
- package/dist/modules/sales/commands/payments.js.map +2 -2
- package/dist/modules/sales/components/AdjustmentKindSettings.js +2 -2
- package/dist/modules/sales/components/AdjustmentKindSettings.js.map +2 -2
- package/dist/modules/sales/components/PaymentMethodsSettings.js +2 -2
- package/dist/modules/sales/components/PaymentMethodsSettings.js.map +2 -2
- package/dist/modules/sales/components/ShippingMethodsSettings.js +2 -2
- package/dist/modules/sales/components/ShippingMethodsSettings.js.map +2 -2
- package/dist/modules/sales/components/TaxRatesSettings.js +2 -2
- package/dist/modules/sales/components/TaxRatesSettings.js.map +2 -2
- package/dist/modules/sales/components/channels/SalesChannelOffersPanel.js +2 -0
- package/dist/modules/sales/components/channels/SalesChannelOffersPanel.js.map +2 -2
- package/dist/modules/sales/components/documents/AdjustmentsSection.js +2 -0
- package/dist/modules/sales/components/documents/AdjustmentsSection.js.map +2 -2
- package/dist/modules/sales/components/documents/PaymentsSection.js +2 -1
- package/dist/modules/sales/components/documents/PaymentsSection.js.map +2 -2
- package/dist/modules/sales/components/documents/SalesDocumentsTable.js +2 -0
- package/dist/modules/sales/components/documents/SalesDocumentsTable.js.map +2 -2
- package/dist/modules/sales/lib/dictionaries.js +0 -3
- package/dist/modules/sales/lib/dictionaries.js.map +2 -2
- package/dist/modules/sales/lib/seeds.js +48 -0
- package/dist/modules/sales/lib/seeds.js.map +7 -0
- package/dist/modules/sales/notifications.client.js +51 -0
- package/dist/modules/sales/notifications.client.js.map +7 -0
- package/dist/modules/sales/notifications.js +88 -0
- package/dist/modules/sales/notifications.js.map +7 -0
- package/dist/modules/sales/setup.js +99 -0
- package/dist/modules/sales/setup.js.map +7 -0
- package/dist/modules/sales/subscribers/quote-expiring-notification.js +38 -0
- package/dist/modules/sales/subscribers/quote-expiring-notification.js.map +7 -0
- package/dist/modules/sales/widgets/notifications/SalesOrderCreatedRenderer.js +137 -0
- package/dist/modules/sales/widgets/notifications/SalesOrderCreatedRenderer.js.map +7 -0
- package/dist/modules/sales/widgets/notifications/SalesQuoteCreatedRenderer.js +137 -0
- package/dist/modules/sales/widgets/notifications/SalesQuoteCreatedRenderer.js.map +7 -0
- package/dist/modules/sales/widgets/notifications/index.js +7 -0
- package/dist/modules/sales/widgets/notifications/index.js.map +7 -0
- package/dist/modules/sales/widgets/notifications/useSalesDocumentTotals.js +60 -0
- package/dist/modules/sales/widgets/notifications/useSalesDocumentTotals.js.map +7 -0
- package/dist/modules/staff/backend/staff/team-members/page.js +1 -1
- package/dist/modules/staff/backend/staff/team-members/page.js.map +2 -2
- package/dist/modules/staff/backend/staff/team-roles/page.js +2 -2
- package/dist/modules/staff/backend/staff/team-roles/page.js.map +2 -2
- package/dist/modules/staff/backend/staff/teams/[id]/edit/page.js +2 -2
- package/dist/modules/staff/backend/staff/teams/[id]/edit/page.js.map +2 -2
- package/dist/modules/staff/backend/staff/teams/page.js +2 -2
- package/dist/modules/staff/backend/staff/teams/page.js.map +2 -2
- package/dist/modules/staff/commands/leave-requests.js +79 -0
- package/dist/modules/staff/commands/leave-requests.js.map +2 -2
- package/dist/modules/staff/notifications.js +75 -0
- package/dist/modules/staff/notifications.js.map +7 -0
- package/dist/modules/staff/setup.js +27 -0
- package/dist/modules/staff/setup.js.map +7 -0
- package/dist/modules/workflows/acl.js +0 -2
- package/dist/modules/workflows/acl.js.map +2 -2
- package/dist/modules/workflows/api/instances/route.js +6 -18
- package/dist/modules/workflows/api/instances/route.js.map +2 -2
- package/dist/modules/workflows/api/tasks/route.js +1 -6
- package/dist/modules/workflows/api/tasks/route.js.map +2 -2
- package/dist/modules/workflows/backend/definitions/[id]/page.js +1 -9
- package/dist/modules/workflows/backend/definitions/[id]/page.js.map +2 -2
- package/dist/modules/workflows/backend/definitions/[id]/page.meta.js +1 -1
- package/dist/modules/workflows/backend/definitions/[id]/page.meta.js.map +2 -2
- package/dist/modules/workflows/backend/definitions/create/page.js +15 -24
- package/dist/modules/workflows/backend/definitions/create/page.js.map +2 -2
- package/dist/modules/workflows/backend/definitions/create/page.meta.js +1 -1
- package/dist/modules/workflows/backend/definitions/create/page.meta.js.map +2 -2
- package/dist/modules/workflows/backend/definitions/page.js +5 -0
- package/dist/modules/workflows/backend/definitions/page.js.map +2 -2
- package/dist/modules/workflows/backend/definitions/visual-editor/page.js +132 -150
- package/dist/modules/workflows/backend/definitions/visual-editor/page.js.map +2 -2
- package/dist/modules/workflows/backend/definitions/visual-editor/page.meta.js +1 -1
- package/dist/modules/workflows/backend/definitions/visual-editor/page.meta.js.map +2 -2
- package/dist/modules/workflows/backend/events/[id]/page.js +1 -1
- package/dist/modules/workflows/backend/events/[id]/page.js.map +2 -2
- package/dist/modules/workflows/backend/events/[id]/page.meta.js +2 -2
- package/dist/modules/workflows/backend/events/[id]/page.meta.js.map +2 -2
- package/dist/modules/workflows/backend/instances/[id]/page.meta.js +2 -2
- package/dist/modules/workflows/backend/instances/[id]/page.meta.js.map +2 -2
- package/dist/modules/workflows/backend/instances/page.js +3 -0
- package/dist/modules/workflows/backend/instances/page.js.map +2 -2
- package/dist/modules/workflows/backend/tasks/[id]/page.js +1 -1
- package/dist/modules/workflows/backend/tasks/[id]/page.js.map +2 -2
- package/dist/modules/workflows/backend/tasks/[id]/page.meta.js +2 -2
- package/dist/modules/workflows/backend/tasks/[id]/page.meta.js.map +2 -2
- package/dist/modules/workflows/backend/tasks/page.js +9 -5
- package/dist/modules/workflows/backend/tasks/page.js.map +2 -2
- package/dist/modules/workflows/cli.js +15 -93
- package/dist/modules/workflows/cli.js.map +3 -3
- package/dist/modules/workflows/data/entities.js +1 -64
- package/dist/modules/workflows/data/entities.js.map +2 -2
- package/dist/modules/workflows/data/validators.js +0 -115
- package/dist/modules/workflows/data/validators.js.map +2 -2
- package/dist/modules/workflows/examples/checkout-demo-definition.json +5 -1
- package/dist/modules/workflows/lib/activity-executor.js +13 -75
- package/dist/modules/workflows/lib/activity-executor.js.map +2 -2
- package/dist/modules/workflows/lib/graph-utils.js +2 -71
- package/dist/modules/workflows/lib/graph-utils.js.map +2 -2
- package/dist/modules/workflows/lib/seeds.js +7 -36
- package/dist/modules/workflows/lib/seeds.js.map +2 -2
- package/dist/modules/workflows/lib/start-validator.js +23 -33
- package/dist/modules/workflows/lib/start-validator.js.map +2 -2
- package/dist/modules/workflows/lib/transition-handler.js +57 -161
- package/dist/modules/workflows/lib/transition-handler.js.map +3 -3
- package/dist/modules/workflows/migrations/Migration20251207131955.js +76 -72
- package/dist/modules/workflows/migrations/Migration20251207131955.js.map +2 -2
- package/dist/modules/workflows/notifications.js +28 -0
- package/dist/modules/workflows/notifications.js.map +7 -0
- package/dist/modules/workflows/setup.js +16 -0
- package/dist/modules/workflows/setup.js.map +7 -0
- package/dist/modules/workflows/subscribers/task-assigned-notification.js +38 -0
- package/dist/modules/workflows/subscribers/task-assigned-notification.js.map +7 -0
- package/generated/entities/notification/index.ts +27 -0
- package/generated/entities.ids.generated.ts +5 -2
- package/generated/entity-fields-registry.ts +2 -2
- package/package.json +2 -2
- package/src/__tests__/module-decoupling.test.ts +356 -0
- package/src/modules/api_docs/frontend/docs/api/page.tsx +3 -2
- package/src/modules/api_keys/backend/api-keys/page.tsx +1 -1
- package/src/modules/api_keys/setup.ts +9 -0
- package/src/modules/attachments/components/AttachmentLibrary.tsx +6 -2
- package/src/modules/attachments/components/AttachmentPartitionSettings.tsx +2 -0
- package/src/modules/attachments/lib/assignmentDetails.ts +32 -16
- package/src/modules/attachments/lib/partitions.ts +3 -3
- package/src/modules/attachments/setup.ts +9 -0
- package/src/modules/audit_logs/setup.ts +10 -0
- package/src/modules/auth/README.md +1 -1
- package/src/modules/auth/__tests__/cli-setup-acl.test.ts +31 -1
- package/src/modules/auth/api/__tests__/login.test.ts +2 -0
- package/src/modules/auth/api/admin/nav.ts +10 -6
- package/src/modules/auth/api/login.ts +26 -7
- package/src/modules/auth/api/profile/route.ts +163 -0
- package/src/modules/auth/api/reset/confirm.ts +25 -2
- package/src/modules/auth/api/reset.ts +23 -0
- package/src/modules/auth/api/sidebar/preferences/route.ts +21 -12
- package/src/modules/auth/api/users/route.ts +5 -2
- package/src/modules/auth/backend/auth/profile/page.meta.ts +9 -0
- package/src/modules/auth/backend/auth/profile/page.tsx +174 -0
- package/src/modules/auth/backend/roles/[id]/edit/page.tsx +4 -1
- package/src/modules/auth/backend/roles/page.tsx +3 -3
- package/src/modules/auth/backend/users/[id]/edit/page.tsx +22 -3
- package/src/modules/auth/backend/users/create/page.tsx +19 -2
- package/src/modules/auth/backend/users/page.tsx +3 -3
- package/src/modules/auth/cli.ts +38 -11
- package/src/modules/auth/commands/users.ts +73 -2
- package/src/modules/auth/data/validators.ts +6 -2
- package/src/modules/auth/frontend/login.tsx +134 -5
- package/src/modules/auth/frontend/reset/[token]/page.tsx +24 -11
- package/src/modules/auth/i18n/de.json +48 -1
- package/src/modules/auth/i18n/en.json +48 -1
- package/src/modules/auth/i18n/es.json +48 -1
- package/src/modules/auth/i18n/pl.json +48 -1
- package/src/modules/auth/lib/setup-app.ts +97 -186
- package/src/modules/auth/notifications.ts +109 -0
- package/src/modules/auth/services/authService.ts +27 -4
- package/src/modules/auth/setup.ts +9 -0
- package/src/modules/business_rules/api/execute/route.ts +8 -1
- package/src/modules/business_rules/backend/rules/page.tsx +4 -0
- package/src/modules/business_rules/backend/sets/page.tsx +3 -0
- package/src/modules/business_rules/cli.ts +2 -1
- package/src/modules/business_rules/data/validators.ts +0 -40
- package/src/modules/business_rules/i18n/en.json +3 -1
- package/src/modules/business_rules/index.ts +0 -25
- package/src/modules/business_rules/lib/__tests__/rule-engine.test.ts +51 -0
- package/src/modules/business_rules/lib/rule-engine.ts +51 -277
- package/src/modules/business_rules/notifications.ts +25 -0
- package/src/modules/business_rules/setup.ts +9 -0
- package/src/modules/business_rules/subscribers/rule-execution-failed-notification.ts +50 -0
- package/src/modules/catalog/components/PriceKindSettings.tsx +2 -0
- package/src/modules/catalog/components/categories/CategoriesDataTable.tsx +2 -2
- package/src/modules/catalog/components/products/ProductsDataTable.tsx +2 -0
- package/src/modules/catalog/i18n/en.json +3 -1
- package/src/modules/catalog/notifications.ts +25 -0
- package/src/modules/catalog/setup.ts +22 -0
- package/src/modules/catalog/subscribers/low-stock-notification.ts +52 -0
- package/src/modules/configs/cli.ts +6 -0
- package/src/modules/configs/components/CachePanel.tsx +4 -4
- package/src/modules/configs/i18n/en.json +12 -2
- package/src/modules/configs/i18n/pl.json +12 -2
- package/src/modules/configs/lib/system-status.ts +48 -1
- package/src/modules/configs/lib/system-status.types.ts +1 -0
- package/src/modules/configs/lib/upgrade-actions.ts +5 -338
- package/src/modules/configs/setup.ts +14 -0
- package/src/modules/currencies/backend/currencies/page.tsx +3 -0
- package/src/modules/currencies/backend/exchange-rates/page.tsx +2 -0
- package/src/modules/currencies/setup.ts +15 -0
- package/src/modules/customers/backend/customers/companies/page.tsx +3 -0
- package/src/modules/customers/backend/customers/deals/page.tsx +3 -0
- package/src/modules/customers/backend/customers/people/page.tsx +3 -0
- package/src/modules/customers/commands/deals.ts +39 -0
- package/src/modules/customers/components/CustomerTodosTable.tsx +1 -0
- package/src/modules/customers/i18n/en.json +5 -1
- package/src/modules/customers/notifications.ts +44 -0
- package/src/modules/customers/setup.ts +36 -0
- package/src/modules/customers/widgets/dashboard/customer-todos/widget.ts +2 -2
- package/src/modules/customers/widgets/dashboard/new-customers/widget.ts +2 -2
- package/src/modules/customers/widgets/dashboard/new-deals/widget.ts +2 -2
- package/src/modules/customers/widgets/dashboard/next-interactions/widget.ts +2 -2
- package/src/modules/dashboards/cli.ts +55 -5
- package/src/modules/dashboards/components/WidgetVisibilityEditor.tsx +22 -11
- package/src/modules/dashboards/lib/role-widgets.ts +80 -0
- package/src/modules/dashboards/services/widgetDataService.ts +164 -4
- package/src/modules/dashboards/setup.ts +26 -0
- package/src/modules/dashboards/widgets/dashboard/aov-kpi/widget.ts +2 -2
- package/src/modules/dashboards/widgets/dashboard/new-customers-kpi/widget.ts +2 -2
- package/src/modules/dashboards/widgets/dashboard/orders-by-status/widget.ts +2 -2
- package/src/modules/dashboards/widgets/dashboard/orders-kpi/widget.ts +2 -2
- package/src/modules/dashboards/widgets/dashboard/pipeline-summary/widget.ts +2 -2
- package/src/modules/dashboards/widgets/dashboard/revenue-kpi/widget.ts +2 -2
- package/src/modules/dashboards/widgets/dashboard/revenue-trend/widget.ts +2 -2
- package/src/modules/dashboards/widgets/dashboard/sales-by-region/widget.ts +2 -2
- package/src/modules/dashboards/widgets/dashboard/top-customers/widget.ts +2 -2
- package/src/modules/dashboards/widgets/dashboard/top-products/widget.ts +2 -2
- package/src/modules/dictionaries/components/DictionaryTable.tsx +2 -0
- package/src/modules/dictionaries/setup.ts +10 -0
- package/src/modules/directory/api/get/tenants/lookup.ts +75 -0
- package/src/modules/directory/backend/directory/organizations/page.tsx +2 -2
- package/src/modules/directory/backend/directory/tenants/page.tsx +2 -2
- package/src/modules/directory/setup.ts +10 -0
- package/src/modules/entities/backend/entities/user/[entityId]/records/page.tsx +2 -2
- package/src/modules/entities/components/SystemEntitiesTable.tsx +1 -1
- package/src/modules/entities/components/UserEntitiesTable.tsx +2 -2
- package/src/modules/entities/setup.ts +9 -0
- package/src/modules/feature_toggles/components/FeatureTogglesTable.tsx +3 -4
- package/src/modules/feature_toggles/components/OverridesTable.tsx +1 -1
- package/src/modules/feature_toggles/setup.ts +9 -0
- package/src/modules/notifications/__tests__/deliver-notification.test.ts +195 -0
- package/src/modules/notifications/__tests__/deliveryStrategies.test.ts +19 -0
- package/src/modules/notifications/__tests__/notificationService.test.ts +208 -0
- package/src/modules/notifications/acl.ts +7 -0
- package/src/modules/notifications/api/[id]/action/route.ts +75 -0
- package/src/modules/notifications/api/[id]/dismiss/route.ts +12 -0
- package/src/modules/notifications/api/[id]/read/route.ts +12 -0
- package/src/modules/notifications/api/[id]/restore/route.ts +53 -0
- package/src/modules/notifications/api/batch/route.ts +14 -0
- package/src/modules/notifications/api/feature/route.ts +14 -0
- package/src/modules/notifications/api/mark-all-read/route.ts +34 -0
- package/src/modules/notifications/api/openapi.ts +76 -0
- package/src/modules/notifications/api/role/route.ts +14 -0
- package/src/modules/notifications/api/route.ts +92 -0
- package/src/modules/notifications/api/settings/route.ts +157 -0
- package/src/modules/notifications/api/unread-count/route.ts +38 -0
- package/src/modules/notifications/backend/config/notifications/page.meta.ts +22 -0
- package/src/modules/notifications/backend/config/notifications/page.tsx +12 -0
- package/src/modules/notifications/cli.ts +18 -0
- package/src/modules/notifications/data/entities.ts +99 -0
- package/src/modules/notifications/data/validators.ts +115 -0
- package/src/modules/notifications/di.ts +11 -0
- package/src/modules/notifications/emails/NotificationEmail.tsx +98 -0
- package/src/modules/notifications/frontend/NotificationInboxPageClient.tsx +42 -0
- package/src/modules/notifications/frontend/NotificationSettingsPageClient.tsx +233 -0
- package/src/modules/notifications/i18n/de.json +50 -0
- package/src/modules/notifications/i18n/en.json +50 -0
- package/src/modules/notifications/i18n/es.json +50 -0
- package/src/modules/notifications/i18n/pl.json +50 -0
- package/src/modules/notifications/index.ts +12 -0
- package/src/modules/notifications/lib/deliveryConfig.ts +153 -0
- package/src/modules/notifications/lib/deliveryStrategies.ts +50 -0
- package/src/modules/notifications/lib/events.ts +48 -0
- package/src/modules/notifications/lib/notificationBuilder.ts +121 -0
- package/src/modules/notifications/lib/notificationFactory.ts +76 -0
- package/src/modules/notifications/lib/notificationMapper.ts +33 -0
- package/src/modules/notifications/lib/notificationRecipients.ts +83 -0
- package/src/modules/notifications/lib/notificationService.ts +414 -0
- package/src/modules/notifications/lib/routeHelpers.ts +151 -0
- package/src/modules/notifications/lib/safeHref.ts +29 -0
- package/src/modules/notifications/migrations/.snapshot-open-mercato.json +336 -0
- package/src/modules/notifications/migrations/Migration20260123000001.ts +73 -0
- package/src/modules/notifications/migrations/Migration20260126150000.ts +39 -0
- package/src/modules/notifications/migrations/Migration20260129082610.ts +13 -0
- package/src/modules/notifications/subscribers/deliver-notification.ts +204 -0
- package/src/modules/notifications/workers/create-notification.worker.ts +122 -0
- package/src/modules/perspectives/setup.ts +10 -0
- package/src/modules/planner/backend/planner/availability-rulesets/page.tsx +2 -2
- package/src/modules/planner/setup.ts +21 -0
- package/src/modules/query_index/cli.ts +82 -13
- package/src/modules/query_index/components/QueryIndexesTable.tsx +8 -2
- package/src/modules/query_index/setup.ts +9 -0
- package/src/modules/resources/backend/resources/resource-types/page.tsx +2 -2
- package/src/modules/resources/backend/resources/resources/page.tsx +2 -2
- package/src/modules/resources/setup.ts +21 -0
- package/src/modules/sales/acl.ts +0 -1
- package/src/modules/sales/backend/sales/channels/offers/page.tsx +2 -0
- package/src/modules/sales/backend/sales/channels/page.tsx +2 -0
- package/src/modules/sales/backend/sales/documents/[id]/page.tsx +0 -16
- package/src/modules/sales/cli.ts +2 -43
- package/src/modules/sales/commands/documents.ts +62 -70
- package/src/modules/sales/commands/payments.ts +33 -0
- package/src/modules/sales/components/AdjustmentKindSettings.tsx +2 -2
- package/src/modules/sales/components/PaymentMethodsSettings.tsx +2 -2
- package/src/modules/sales/components/ShippingMethodsSettings.tsx +2 -2
- package/src/modules/sales/components/TaxRatesSettings.tsx +2 -2
- package/src/modules/sales/components/channels/SalesChannelOffersPanel.tsx +2 -0
- package/src/modules/sales/components/documents/AdjustmentsSection.tsx +2 -0
- package/src/modules/sales/components/documents/PaymentsSection.tsx +2 -1
- package/src/modules/sales/components/documents/SalesDocumentsTable.tsx +2 -0
- package/src/modules/sales/i18n/de.json +20 -0
- package/src/modules/sales/i18n/en.json +25 -1
- package/src/modules/sales/i18n/es.json +20 -0
- package/src/modules/sales/i18n/pl.json +20 -0
- package/src/modules/sales/lib/dictionaries.ts +0 -3
- package/src/modules/sales/lib/seeds.ts +53 -0
- package/src/modules/sales/notifications.client.ts +65 -0
- package/src/modules/sales/notifications.ts +82 -0
- package/src/modules/sales/setup.ts +108 -0
- package/src/modules/sales/subscribers/quote-expiring-notification.ts +53 -0
- package/src/modules/sales/widgets/notifications/SalesOrderCreatedRenderer.tsx +156 -0
- package/src/modules/sales/widgets/notifications/SalesQuoteCreatedRenderer.tsx +156 -0
- package/src/modules/sales/widgets/notifications/index.ts +2 -0
- package/src/modules/sales/widgets/notifications/useSalesDocumentTotals.ts +81 -0
- package/src/modules/staff/backend/staff/team-members/page.tsx +1 -1
- package/src/modules/staff/backend/staff/team-roles/page.tsx +2 -2
- package/src/modules/staff/backend/staff/teams/[id]/edit/page.tsx +2 -2
- package/src/modules/staff/backend/staff/teams/page.tsx +2 -2
- package/src/modules/staff/commands/leave-requests.ts +94 -0
- package/src/modules/staff/i18n/de.json +4 -0
- package/src/modules/staff/i18n/en.json +9 -1
- package/src/modules/staff/i18n/es.json +4 -0
- package/src/modules/staff/i18n/pl.json +4 -0
- package/src/modules/staff/notifications.ts +71 -0
- package/src/modules/staff/setup.ts +27 -0
- package/src/modules/workflows/acl.ts +0 -2
- package/src/modules/workflows/api/__tests__/instances.route.test.ts +2 -5
- package/src/modules/workflows/api/instances/route.ts +7 -21
- package/src/modules/workflows/api/tasks/route.ts +1 -7
- package/src/modules/workflows/backend/definitions/[id]/page.meta.ts +1 -1
- package/src/modules/workflows/backend/definitions/[id]/page.tsx +0 -9
- package/src/modules/workflows/backend/definitions/create/page.meta.ts +1 -1
- package/src/modules/workflows/backend/definitions/create/page.tsx +0 -9
- package/src/modules/workflows/backend/definitions/page.tsx +5 -0
- package/src/modules/workflows/backend/definitions/visual-editor/page.meta.ts +1 -1
- package/src/modules/workflows/backend/definitions/visual-editor/page.tsx +3 -21
- package/src/modules/workflows/backend/events/[id]/page.meta.ts +2 -2
- package/src/modules/workflows/backend/events/[id]/page.tsx +1 -1
- package/src/modules/workflows/backend/instances/[id]/page.meta.ts +2 -2
- package/src/modules/workflows/backend/instances/page.tsx +4 -1
- package/src/modules/workflows/backend/tasks/[id]/page.meta.ts +2 -2
- package/src/modules/workflows/backend/tasks/[id]/page.tsx +1 -1
- package/src/modules/workflows/backend/tasks/page.tsx +10 -6
- package/src/modules/workflows/cli.ts +12 -123
- package/src/modules/workflows/data/entities.ts +0 -124
- package/src/modules/workflows/data/validators.ts +0 -138
- package/src/modules/workflows/examples/checkout-demo-definition.json +5 -1
- package/src/modules/workflows/i18n/en.json +3 -72
- package/src/modules/workflows/lib/__tests__/activity-executor.test.ts +36 -43
- package/src/modules/workflows/lib/__tests__/transition-handler.test.ts +90 -170
- package/src/modules/workflows/lib/activity-executor.ts +16 -129
- package/src/modules/workflows/lib/graph-utils.ts +2 -117
- package/src/modules/workflows/lib/seeds.ts +12 -50
- package/src/modules/workflows/lib/start-validator.ts +28 -38
- package/src/modules/workflows/lib/transition-handler.ts +71 -212
- package/src/modules/workflows/migrations/Migration20251207131955.ts +77 -143
- package/src/modules/workflows/notifications.ts +25 -0
- package/src/modules/workflows/setup.ts +15 -0
- package/src/modules/workflows/subscribers/task-assigned-notification.ts +53 -0
- package/dist/generated/entities/workflow_event_trigger/index.js +0 -33
- package/dist/generated/entities/workflow_event_trigger/index.js.map +0 -7
- package/dist/modules/auth/events.js +0 -30
- package/dist/modules/auth/events.js.map +0 -7
- package/dist/modules/business_rules/api/execute/[ruleId]/route.js +0 -145
- package/dist/modules/business_rules/api/execute/[ruleId]/route.js.map +0 -7
- package/dist/modules/catalog/events.js +0 -34
- package/dist/modules/catalog/events.js.map +0 -7
- package/dist/modules/customers/events.js +0 -49
- package/dist/modules/customers/events.js.map +0 -7
- package/dist/modules/directory/events.js +0 -23
- package/dist/modules/directory/events.js.map +0 -7
- package/dist/modules/sales/events.js +0 -63
- package/dist/modules/sales/events.js.map +0 -7
- package/dist/modules/sales/lib/frontend/documentDataEvents.js +0 -25
- package/dist/modules/sales/lib/frontend/documentDataEvents.js.map +0 -7
- package/dist/modules/workflows/components/DefinitionTriggersEditor.js +0 -481
- package/dist/modules/workflows/components/DefinitionTriggersEditor.js.map +0 -7
- package/dist/modules/workflows/components/EventTriggersEditor.js +0 -553
- package/dist/modules/workflows/components/EventTriggersEditor.js.map +0 -7
- package/dist/modules/workflows/events.js +0 -38
- package/dist/modules/workflows/events.js.map +0 -7
- package/dist/modules/workflows/examples/order-approval-definition.json +0 -257
- package/dist/modules/workflows/examples/order-approval-guard-rules.json +0 -32
- package/dist/modules/workflows/lib/event-trigger-service.js +0 -308
- package/dist/modules/workflows/lib/event-trigger-service.js.map +0 -7
- package/dist/modules/workflows/migrations/Migration20260123143500.js +0 -36
- package/dist/modules/workflows/migrations/Migration20260123143500.js.map +0 -7
- package/dist/modules/workflows/subscribers/event-trigger.js +0 -78
- package/dist/modules/workflows/subscribers/event-trigger.js.map +0 -7
- package/dist/modules/workflows/widgets/injection/order-approval/widget.client.js +0 -323
- package/dist/modules/workflows/widgets/injection/order-approval/widget.client.js.map +0 -7
- package/dist/modules/workflows/widgets/injection/order-approval/widget.js +0 -17
- package/dist/modules/workflows/widgets/injection/order-approval/widget.js.map +0 -7
- package/dist/modules/workflows/widgets/injection-table.js +0 -19
- package/dist/modules/workflows/widgets/injection-table.js.map +0 -7
- package/generated/entities/workflow_event_trigger/index.ts +0 -15
- package/src/modules/auth/events.ts +0 -39
- package/src/modules/business_rules/api/execute/[ruleId]/route.ts +0 -163
- package/src/modules/catalog/events.ts +0 -45
- package/src/modules/customers/events.ts +0 -63
- package/src/modules/directory/events.ts +0 -31
- package/src/modules/sales/events.ts +0 -82
- package/src/modules/sales/lib/frontend/documentDataEvents.ts +0 -28
- package/src/modules/workflows/components/DefinitionTriggersEditor.tsx +0 -581
- package/src/modules/workflows/components/EventTriggersEditor.tsx +0 -664
- package/src/modules/workflows/events.ts +0 -49
- package/src/modules/workflows/examples/order-approval-definition.json +0 -257
- package/src/modules/workflows/examples/order-approval-guard-rules.json +0 -32
- package/src/modules/workflows/lib/event-trigger-service.ts +0 -557
- package/src/modules/workflows/migrations/Migration20260123143500.ts +0 -38
- package/src/modules/workflows/subscribers/event-trigger.ts +0 -109
- package/src/modules/workflows/widgets/injection/order-approval/widget.client.tsx +0 -446
- package/src/modules/workflows/widgets/injection/order-approval/widget.ts +0 -16
- package/src/modules/workflows/widgets/injection-table.ts +0 -21
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"version": 3,
|
|
3
3
|
"sources": ["../../../../../src/modules/workflows/backend/instances/page.tsx"],
|
|
4
|
-
"sourcesContent": ["\"use client\"\n\nimport * as React from 'react'\nimport Link from 'next/link'\nimport { useRouter } from 'next/navigation'\nimport { Page, PageBody } from '@open-mercato/ui/backend/Page'\nimport { DataTable } from '@open-mercato/ui/backend/DataTable'\nimport type { ColumnDef } from '@tanstack/react-table'\nimport { Button } from '@open-mercato/ui/primitives/button'\nimport { RowActions } from '@open-mercato/ui/backend/RowActions'\nimport { apiCall } from '@open-mercato/ui/backend/utils/apiCall'\nimport { flash } from '@open-mercato/ui/backend/FlashMessages'\nimport { useQuery, useQueryClient } from '@tanstack/react-query'\nimport { useT } from '@open-mercato/shared/lib/i18n/context'\nimport type { FilterDef, FilterValues } from '@open-mercato/ui/backend/FilterBar'\n\ntype WorkflowInstance = {\n id: string\n definitionId: string\n workflowId: string\n version: number\n status: 'RUNNING' | 'PAUSED' | 'COMPLETED' | 'FAILED' | 'CANCELLED' | 'COMPENSATING' | 'COMPENSATED'\n currentStepId: string\n correlationKey: string | null\n startedAt: string\n completedAt: string | null\n cancelledAt: string | null\n errorMessage: string | null\n retryCount: number\n tenantId: string\n organizationId: string\n createdAt: string\n updatedAt: string\n}\n\ntype InstancesResponse = {\n data: WorkflowInstance[]\n pagination: {\n total: number\n limit: number\n offset: number\n hasMore: boolean\n }\n}\n\nexport default function WorkflowInstancesListPage() {\n const [page, setPage] = React.useState(1)\n const [pageSize] = React.useState(50)\n const [total, setTotal] = React.useState(0)\n const [totalPages, setTotalPages] = React.useState(1)\n const t = useT()\n const router = useRouter()\n const queryClient = useQueryClient()\n const [filterValues, setFilterValues] = React.useState<FilterValues>({})\n\n const { data, isLoading, error } = useQuery({\n queryKey: ['workflow-instances', 'list', filterValues, page],\n queryFn: async () => {\n const params = new URLSearchParams()\n const offset = (page - 1) * pageSize\n params.set('limit', pageSize.toString())\n params.set('offset', offset.toString())\n\n if (filterValues.status) params.set('status', filterValues.status as string)\n if (filterValues.workflowId) params.set('workflowId', filterValues.workflowId as string)\n if (filterValues.correlationKey) params.set('correlationKey', filterValues.correlationKey as string)\n if (filterValues.entityType) params.set('entityType', filterValues.entityType as string)\n if (filterValues.entityId) params.set('entityId', filterValues.entityId as string)\n\n const result = await apiCall<InstancesResponse>(\n `/api/workflows/instances?${params.toString()}`\n )\n\n if (!result.ok) {\n throw new Error('Failed to fetch workflow instances')\n }\n\n const response = result.result\n if (response?.pagination) {\n setTotal(response.pagination.total || 0)\n const calculatedPages = Math.ceil((response.pagination.total || 0) / pageSize)\n setTotalPages(calculatedPages || 1)\n }\n\n return response?.data || []\n },\n })\n\n const handleCancel = async (id: string, workflowId: string) => {\n if (!confirm(t('workflows.instances.confirm.cancel', { id: workflowId }))) {\n return\n }\n\n const result = await apiCall(`/api/workflows/instances/${id}/cancel`, {\n method: 'POST',\n })\n\n if (result.ok) {\n flash(t('workflows.instances.messages.cancelled'), 'success')\n queryClient.invalidateQueries({ queryKey: ['workflow-instances'] })\n } else {\n flash(t('workflows.instances.messages.cancelFailed'), 'error')\n }\n }\n\n const handleRetry = async (id: string, workflowId: string) => {\n if (!confirm(t('workflows.instances.confirm.retry', { id: workflowId }))) {\n return\n }\n\n const result = await apiCall(`/api/workflows/instances/${id}/retry`, {\n method: 'POST',\n })\n\n if (result.ok) {\n flash(t('workflows.instances.messages.retried'), 'success')\n queryClient.invalidateQueries({ queryKey: ['workflow-instances'] })\n } else {\n flash(t('workflows.instances.messages.retryFailed'), 'error')\n }\n }\n\n const handleFiltersApply = React.useCallback((values: FilterValues) => {\n const next: FilterValues = {}\n Object.entries(values).forEach(([key, value]) => {\n if (value !== undefined && value !== '') next[key] = value\n })\n setFilterValues(next)\n setPage(1)\n }, [])\n\n const handleFiltersClear = React.useCallback(() => {\n setFilterValues({})\n setPage(1)\n }, [])\n\n const getStatusBadgeClass = (status: WorkflowInstance['status']) => {\n switch (status) {\n case 'RUNNING':\n return 'bg-blue-100 text-blue-800'\n case 'PAUSED':\n return 'bg-yellow-100 text-yellow-800'\n case 'COMPLETED':\n return 'bg-green-100 text-green-800'\n case 'FAILED':\n return 'bg-red-100 text-red-800'\n case 'CANCELLED':\n return 'bg-muted text-foreground'\n case 'COMPENSATING':\n return 'bg-orange-100 text-orange-800'\n case 'COMPENSATED':\n return 'bg-purple-100 text-purple-800'\n default:\n return 'bg-muted text-muted-foreground'\n }\n }\n\n const filters: FilterDef[] = [\n {\n id: 'status',\n type: 'select',\n label: t('workflows.instances.filters.status'),\n options: [\n { label: t('common.all'), value: '' },\n { label: t('workflows.instances.status.RUNNING'), value: 'RUNNING' },\n { label: t('workflows.instances.status.PAUSED'), value: 'PAUSED' },\n { label: t('workflows.instances.status.COMPLETED'), value: 'COMPLETED' },\n { label: t('workflows.instances.status.FAILED'), value: 'FAILED' },\n { label: t('workflows.instances.status.CANCELLED'), value: 'CANCELLED' },\n { label: t('workflows.instances.status.COMPENSATING'), value: 'COMPENSATING' },\n { label: t('workflows.instances.status.COMPENSATED'), value: 'COMPENSATED' },\n ],\n },\n {\n id: 'workflowId',\n type: 'text',\n label: t('workflows.instances.filters.workflowId'),\n placeholder: t('workflows.instances.filters.workflowIdPlaceholder'),\n },\n {\n id: 'correlationKey',\n type: 'text',\n label: t('workflows.instances.filters.correlationKey'),\n placeholder: t('workflows.instances.filters.correlationKeyPlaceholder'),\n },\n {\n id: 'entityType',\n type: 'text',\n label: t('workflows.instances.filters.entityType'),\n placeholder: t('workflows.instances.filters.entityTypePlaceholder'),\n },\n {\n id: 'entityId',\n type: 'text',\n label: t('workflows.instances.filters.entityId'),\n placeholder: t('workflows.instances.filters.entityIdPlaceholder'),\n },\n ]\n\n const columns: ColumnDef<WorkflowInstance>[] = [\n {\n id: 'workflowId',\n header: t('workflows.instances.fields.workflowId'),\n accessorKey: 'workflowId',\n cell: ({ row }) => (\n <div>\n <div className=\"font-mono text-sm font-medium\">{row.original.workflowId}</div>\n {row.original.correlationKey && (\n <div className=\"text-xs text-muted-foreground\">\n {t('workflows.instances.fields.correlationKey')}: {row.original.correlationKey}\n </div>\n )}\n </div>\n ),\n },\n {\n id: 'status',\n header: t('workflows.instances.fields.status'),\n accessorKey: 'status',\n cell: ({ row }) => (\n <span className={`inline-flex items-center px-2 py-1 rounded text-xs font-medium ${getStatusBadgeClass(row.original.status)}`}>\n {t(`workflows.instances.status.${row.original.status}`)}\n </span>\n ),\n },\n {\n id: 'currentStep',\n header: t('workflows.instances.fields.currentStep'),\n accessorKey: 'currentStepId',\n cell: ({ row }) => (\n <span className=\"text-sm text-muted-foreground\">{row.original.currentStepId}</span>\n ),\n },\n {\n id: 'timing',\n header: t('workflows.instances.fields.timing'),\n cell: ({ row }) => {\n const started = new Date(row.original.startedAt)\n const completed = row.original.completedAt ? new Date(row.original.completedAt) : null\n const duration = completed ? completed.getTime() - started.getTime() : Date.now() - started.getTime()\n const durationText = duration < 60000\n ? `${Math.floor(duration / 1000)}s`\n : `${Math.floor(duration / 60000)}m`\n\n return (\n <div className=\"text-sm\">\n <div className=\"text-foreground\">{started.toLocaleString()}</div>\n <div className=\"text-xs text-muted-foreground\">\n {completed ? t('workflows.instances.duration') : t('workflows.instances.elapsed')}: {durationText}\n </div>\n </div>\n )\n },\n },\n {\n id: 'retryCount',\n header: t('workflows.instances.fields.retryCount'),\n accessorKey: 'retryCount',\n cell: ({ row }) => (\n <span className={`text-sm ${row.original.retryCount > 0 ? 'text-orange-600 font-medium' : 'text-muted-foreground'}`}>\n {row.original.retryCount}\n </span>\n ),\n },\n {\n id: 'actions',\n header: '',\n cell: ({ row }) => {\n const items: Array<{label: string; href?: string; onSelect?: () => void}> = [\n {\n label: t('workflows.instances.actions.viewDetails'),\n href: `/backend/instances/${row.original.id}`,\n },\n ]\n\n if (row.original.status === 'RUNNING' || row.original.status === 'PAUSED') {\n items.push({\n label: t('workflows.instances.actions.cancel'),\n onSelect: () => handleCancel(row.original.id, row.original.workflowId),\n })\n }\n\n if (row.original.status === 'FAILED') {\n items.push({\n label: t('workflows.instances.actions.retry'),\n onSelect: () => handleRetry(row.original.id, row.original.workflowId),\n })\n }\n\n return <RowActions items={items} />\n },\n },\n ]\n\n if (error) {\n return (\n <Page>\n <PageBody>\n <div className=\"p-8 text-center\">\n <p className=\"text-red-600\">{t('workflows.instances.messages.loadFailed')}</p>\n <Button onClick={() => queryClient.invalidateQueries({ queryKey: ['workflow-instances'] })} className=\"mt-4\">\n {t('common.retry')}\n </Button>\n </div>\n </PageBody>\n </Page>\n )\n }\n\n return (\n <Page>\n <PageBody>\n <DataTable\n title={t('workflows.instances.list.title')}\n columns={columns}\n data={data || []}\n filters={filters}\n filterValues={filterValues}\n onFiltersApply={handleFiltersApply}\n onFiltersClear={handleFiltersClear}\n perspective={{\n tableId: 'workflows.instances.list',\n }}\n pagination={{ page, pageSize, total, totalPages, onPageChange: setPage }}\n />\n </PageBody>\n </Page>\n )\n}\n"],
|
|
5
|
-
"mappings": "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
|
|
4
|
+
"sourcesContent": ["\"use client\"\n\nimport * as React from 'react'\nimport Link from 'next/link'\nimport { useRouter } from 'next/navigation'\nimport { Page, PageBody } from '@open-mercato/ui/backend/Page'\nimport { DataTable } from '@open-mercato/ui/backend/DataTable'\nimport type { ColumnDef } from '@tanstack/react-table'\nimport { Button } from '@open-mercato/ui/primitives/button'\nimport { RowActions } from '@open-mercato/ui/backend/RowActions'\nimport { apiCall } from '@open-mercato/ui/backend/utils/apiCall'\nimport { flash } from '@open-mercato/ui/backend/FlashMessages'\nimport { useQuery, useQueryClient } from '@tanstack/react-query'\nimport { useT } from '@open-mercato/shared/lib/i18n/context'\nimport type { FilterDef, FilterValues } from '@open-mercato/ui/backend/FilterBar'\n\ntype WorkflowInstance = {\n id: string\n definitionId: string\n workflowId: string\n version: number\n status: 'RUNNING' | 'PAUSED' | 'COMPLETED' | 'FAILED' | 'CANCELLED' | 'COMPENSATING' | 'COMPENSATED'\n currentStepId: string\n correlationKey: string | null\n startedAt: string\n completedAt: string | null\n cancelledAt: string | null\n errorMessage: string | null\n retryCount: number\n tenantId: string\n organizationId: string\n createdAt: string\n updatedAt: string\n}\n\ntype InstancesResponse = {\n data: WorkflowInstance[]\n pagination: {\n total: number\n limit: number\n offset: number\n hasMore: boolean\n }\n}\n\nexport default function WorkflowInstancesListPage() {\n const [page, setPage] = React.useState(1)\n const [pageSize] = React.useState(50)\n const [total, setTotal] = React.useState(0)\n const [totalPages, setTotalPages] = React.useState(1)\n const t = useT()\n const router = useRouter()\n const queryClient = useQueryClient()\n const [filterValues, setFilterValues] = React.useState<FilterValues>({})\n\n const { data, isLoading, error } = useQuery({\n queryKey: ['workflow-instances', 'list', filterValues, page],\n queryFn: async () => {\n const params = new URLSearchParams()\n const offset = (page - 1) * pageSize\n params.set('limit', pageSize.toString())\n params.set('offset', offset.toString())\n\n if (filterValues.status) params.set('status', filterValues.status as string)\n if (filterValues.workflowId) params.set('workflowId', filterValues.workflowId as string)\n if (filterValues.correlationKey) params.set('correlationKey', filterValues.correlationKey as string)\n if (filterValues.entityType) params.set('entityType', filterValues.entityType as string)\n if (filterValues.entityId) params.set('entityId', filterValues.entityId as string)\n\n const result = await apiCall<InstancesResponse>(\n `/api/workflows/instances?${params.toString()}`\n )\n\n if (!result.ok) {\n throw new Error('Failed to fetch workflow instances')\n }\n\n const response = result.result\n if (response?.pagination) {\n setTotal(response.pagination.total || 0)\n const calculatedPages = Math.ceil((response.pagination.total || 0) / pageSize)\n setTotalPages(calculatedPages || 1)\n }\n\n return response?.data || []\n },\n })\n\n const handleCancel = async (id: string, workflowId: string) => {\n if (!confirm(t('workflows.instances.confirm.cancel', { id: workflowId }))) {\n return\n }\n\n const result = await apiCall(`/api/workflows/instances/${id}/cancel`, {\n method: 'POST',\n })\n\n if (result.ok) {\n flash(t('workflows.instances.messages.cancelled'), 'success')\n queryClient.invalidateQueries({ queryKey: ['workflow-instances'] })\n } else {\n flash(t('workflows.instances.messages.cancelFailed'), 'error')\n }\n }\n\n const handleRetry = async (id: string, workflowId: string) => {\n if (!confirm(t('workflows.instances.confirm.retry', { id: workflowId }))) {\n return\n }\n\n const result = await apiCall(`/api/workflows/instances/${id}/retry`, {\n method: 'POST',\n })\n\n if (result.ok) {\n flash(t('workflows.instances.messages.retried'), 'success')\n queryClient.invalidateQueries({ queryKey: ['workflow-instances'] })\n } else {\n flash(t('workflows.instances.messages.retryFailed'), 'error')\n }\n }\n\n const handleFiltersApply = React.useCallback((values: FilterValues) => {\n const next: FilterValues = {}\n Object.entries(values).forEach(([key, value]) => {\n if (value !== undefined && value !== '') next[key] = value\n })\n setFilterValues(next)\n setPage(1)\n }, [])\n\n const handleFiltersClear = React.useCallback(() => {\n setFilterValues({})\n setPage(1)\n }, [])\n\n const getStatusBadgeClass = (status: WorkflowInstance['status']) => {\n switch (status) {\n case 'RUNNING':\n return 'bg-blue-100 text-blue-800'\n case 'PAUSED':\n return 'bg-yellow-100 text-yellow-800'\n case 'COMPLETED':\n return 'bg-green-100 text-green-800'\n case 'FAILED':\n return 'bg-red-100 text-red-800'\n case 'CANCELLED':\n return 'bg-muted text-foreground'\n case 'COMPENSATING':\n return 'bg-orange-100 text-orange-800'\n case 'COMPENSATED':\n return 'bg-purple-100 text-purple-800'\n default:\n return 'bg-muted text-muted-foreground'\n }\n }\n\n const filters: FilterDef[] = [\n {\n id: 'status',\n type: 'select',\n label: t('workflows.instances.filters.status'),\n options: [\n { label: t('common.all'), value: '' },\n { label: t('workflows.instances.status.RUNNING'), value: 'RUNNING' },\n { label: t('workflows.instances.status.PAUSED'), value: 'PAUSED' },\n { label: t('workflows.instances.status.COMPLETED'), value: 'COMPLETED' },\n { label: t('workflows.instances.status.FAILED'), value: 'FAILED' },\n { label: t('workflows.instances.status.CANCELLED'), value: 'CANCELLED' },\n { label: t('workflows.instances.status.COMPENSATING'), value: 'COMPENSATING' },\n { label: t('workflows.instances.status.COMPENSATED'), value: 'COMPENSATED' },\n ],\n },\n {\n id: 'workflowId',\n type: 'text',\n label: t('workflows.instances.filters.workflowId'),\n placeholder: t('workflows.instances.filters.workflowIdPlaceholder'),\n },\n {\n id: 'correlationKey',\n type: 'text',\n label: t('workflows.instances.filters.correlationKey'),\n placeholder: t('workflows.instances.filters.correlationKeyPlaceholder'),\n },\n {\n id: 'entityType',\n type: 'text',\n label: t('workflows.instances.filters.entityType'),\n placeholder: t('workflows.instances.filters.entityTypePlaceholder'),\n },\n {\n id: 'entityId',\n type: 'text',\n label: t('workflows.instances.filters.entityId'),\n placeholder: t('workflows.instances.filters.entityIdPlaceholder'),\n },\n ]\n\n const columns: ColumnDef<WorkflowInstance>[] = [\n {\n id: 'workflowId',\n header: t('workflows.instances.fields.workflowId'),\n accessorKey: 'workflowId',\n cell: ({ row }) => (\n <div>\n <div className=\"font-mono text-sm font-medium\">{row.original.workflowId}</div>\n {row.original.correlationKey && (\n <div className=\"text-xs text-muted-foreground\">\n {t('workflows.instances.fields.correlationKey')}: {row.original.correlationKey}\n </div>\n )}\n </div>\n ),\n },\n {\n id: 'status',\n header: t('workflows.instances.fields.status'),\n accessorKey: 'status',\n cell: ({ row }) => (\n <span className={`inline-flex items-center px-2 py-1 rounded text-xs font-medium ${getStatusBadgeClass(row.original.status)}`}>\n {t(`workflows.instances.status.${row.original.status}`)}\n </span>\n ),\n },\n {\n id: 'currentStep',\n header: t('workflows.instances.fields.currentStep'),\n accessorKey: 'currentStepId',\n cell: ({ row }) => (\n <span className=\"text-sm text-muted-foreground\">{row.original.currentStepId}</span>\n ),\n },\n {\n id: 'timing',\n header: t('workflows.instances.fields.timing'),\n cell: ({ row }) => {\n const started = new Date(row.original.startedAt)\n const completed = row.original.completedAt ? new Date(row.original.completedAt) : null\n const duration = completed ? completed.getTime() - started.getTime() : Date.now() - started.getTime()\n const durationText = duration < 60000\n ? `${Math.floor(duration / 1000)}s`\n : `${Math.floor(duration / 60000)}m`\n\n return (\n <div className=\"text-sm\">\n <div className=\"text-foreground\">{started.toLocaleString()}</div>\n <div className=\"text-xs text-muted-foreground\">\n {completed ? t('workflows.instances.duration') : t('workflows.instances.elapsed')}: {durationText}\n </div>\n </div>\n )\n },\n },\n {\n id: 'retryCount',\n header: t('workflows.instances.fields.retryCount'),\n accessorKey: 'retryCount',\n cell: ({ row }) => (\n <span className={`text-sm ${row.original.retryCount > 0 ? 'text-orange-600 font-medium' : 'text-muted-foreground'}`}>\n {row.original.retryCount}\n </span>\n ),\n },\n {\n id: 'actions',\n header: '',\n cell: ({ row }) => {\n const items: Array<{ id: string; label: string; href?: string; onSelect?: () => void }> = [\n {\n id: 'view',\n label: t('workflows.instances.actions.viewDetails'),\n href: `/backend/instances/${row.original.id}`,\n },\n ]\n\n if (row.original.status === 'RUNNING' || row.original.status === 'PAUSED') {\n items.push({\n id: 'cancel',\n label: t('workflows.instances.actions.cancel'),\n onSelect: () => handleCancel(row.original.id, row.original.workflowId),\n })\n }\n\n if (row.original.status === 'FAILED') {\n items.push({\n id: 'retry',\n label: t('workflows.instances.actions.retry'),\n onSelect: () => handleRetry(row.original.id, row.original.workflowId),\n })\n }\n\n return <RowActions items={items} />\n },\n },\n ]\n\n if (error) {\n return (\n <Page>\n <PageBody>\n <div className=\"p-8 text-center\">\n <p className=\"text-red-600\">{t('workflows.instances.messages.loadFailed')}</p>\n <Button onClick={() => queryClient.invalidateQueries({ queryKey: ['workflow-instances'] })} className=\"mt-4\">\n {t('common.retry')}\n </Button>\n </div>\n </PageBody>\n </Page>\n )\n }\n\n return (\n <Page>\n <PageBody>\n <DataTable\n title={t('workflows.instances.list.title')}\n columns={columns}\n data={data || []}\n filters={filters}\n filterValues={filterValues}\n onFiltersApply={handleFiltersApply}\n onFiltersClear={handleFiltersClear}\n perspective={{\n tableId: 'workflows.instances.list',\n }}\n pagination={{ page, pageSize, total, totalPages, onPageChange: setPage }}\n />\n </PageBody>\n </Page>\n )\n}\n"],
|
|
5
|
+
"mappings": "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",
|
|
6
6
|
"names": []
|
|
7
7
|
}
|
|
@@ -300,7 +300,7 @@ function UserTaskDetailPage({ params }) {
|
|
|
300
300
|
className: `inline-flex items-center px-3 py-1 rounded text-sm font-medium ${getStatusBadgeClass(
|
|
301
301
|
task.status
|
|
302
302
|
)}`,
|
|
303
|
-
children: t(`workflows.tasks.
|
|
303
|
+
children: t(`workflows.tasks.status.${task.status}`)
|
|
304
304
|
}
|
|
305
305
|
)
|
|
306
306
|
] }),
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"version": 3,
|
|
3
3
|
"sources": ["../../../../../../src/modules/workflows/backend/tasks/%5Bid%5D/page.tsx"],
|
|
4
|
-
"sourcesContent": ["\"use client\"\n\nimport * as React from 'react'\nimport Link from 'next/link'\nimport { useRouter } from 'next/navigation'\nimport { Page, PageBody } from '@open-mercato/ui/backend/Page'\nimport { Button } from '@open-mercato/ui/primitives/button'\nimport { Spinner } from '@open-mercato/ui/primitives/spinner'\nimport { Separator } from '@open-mercato/ui/primitives/separator'\nimport { JsonDisplay } from '@open-mercato/ui/backend/JsonDisplay'\nimport { apiCall } from '@open-mercato/ui/backend/utils/apiCall'\nimport { flash } from '@open-mercato/ui/backend/FlashMessages'\nimport { useQuery } from '@tanstack/react-query'\nimport { useT } from '@open-mercato/shared/lib/i18n/context'\n\ntype UserTaskStatus = 'PENDING' | 'IN_PROGRESS' | 'COMPLETED' | 'CANCELLED'\n\ntype UserTask = {\n id: string\n workflowInstanceId: string\n stepInstanceId: string\n taskName: string\n description: string | null\n status: UserTaskStatus\n formSchema: any | null\n formData: any | null\n assignedTo: string | null\n assignedToRoles: string[] | null\n claimedBy: string | null\n claimedAt: string | null\n dueDate: string | null\n completedBy: string | null\n completedAt: string | null\n comments: string | null\n tenantId: string\n organizationId: string\n createdAt: string\n updatedAt: string\n}\n\nexport default function UserTaskDetailPage({ params }: { params: { id: string } }) {\n const router = useRouter()\n const t = useT()\n const [formData, setFormData] = React.useState<Record<string, any>>({})\n const [comments, setComments] = React.useState('')\n const [submitting, setSubmitting] = React.useState(false)\n\n const { data: task, isLoading, error } = useQuery({\n queryKey: ['workflow-task', params.id],\n queryFn: async () => {\n const result = await apiCall<{ data: UserTask }>(\n `/api/workflows/tasks/${params.id}`\n )\n\n if (!result.ok) {\n throw new Error('Failed to fetch task')\n }\n\n return result.result?.data || null\n },\n })\n\n const handleFieldChange = (fieldName: string, value: any) => {\n setFormData(prev => ({\n ...prev,\n [fieldName]: value,\n }))\n }\n\n const handleSubmit = async (e: React.FormEvent) => {\n e.preventDefault()\n\n if (!task) return\n\n // Validate required fields\n if (task.formSchema?.required) {\n for (const requiredField of task.formSchema.required) {\n if (!formData[requiredField] || formData[requiredField] === '') {\n flash(t('workflows.tasks.detail.validation.requiredField', { field: requiredField }), 'error')\n return\n }\n }\n }\n\n setSubmitting(true)\n\n try {\n const result = await apiCall(`/api/workflows/tasks/${params.id}/complete`, {\n method: 'POST',\n headers: {\n 'Content-Type': 'application/json',\n },\n body: JSON.stringify({\n formData,\n comments: comments || undefined,\n }),\n })\n\n if (result.ok) {\n flash(t('workflows.tasks.messages.completed'), 'success')\n router.push('/backend/tasks')\n } else {\n const error = result.result as any\n flash(error?.error || t('workflows.tasks.messages.completeFailed'), 'error')\n }\n } catch (err) {\n console.error('Error completing task:', err)\n flash(t('workflows.tasks.messages.completeFailed'), 'error')\n } finally {\n setSubmitting(false)\n }\n }\n\n const renderFormField = (fieldName: string, fieldSchema: any) => {\n const fieldType = fieldSchema.type || 'string'\n const fieldTitle = fieldSchema.title || fieldName\n const fieldDescription = fieldSchema.description\n const required = task?.formSchema?.required?.includes(fieldName) || false\n const enumValues = fieldSchema.enum\n\n const inputClasses = \"w-full px-3 py-2 border border-border rounded-md focus:outline-none focus:ring-2 focus:ring-primary\"\n const labelClasses = \"block text-sm font-medium text-foreground mb-1\"\n\n // Handle enum (select dropdown)\n if (enumValues && Array.isArray(enumValues)) {\n return (\n <div key={fieldName} className=\"space-y-2\">\n <label htmlFor={fieldName} className={labelClasses}>\n {fieldTitle}\n {required && <span className=\"text-red-600 ml-1\">*</span>}\n </label>\n {fieldDescription && (\n <p className=\"text-xs text-muted-foreground\">{fieldDescription}</p>\n )}\n <select\n id={fieldName}\n value={formData[fieldName] || ''}\n onChange={(e) => handleFieldChange(fieldName, e.target.value)}\n required={required}\n className={inputClasses}\n >\n <option value=\"\">{t('workflows.tasks.detail.form.selectOption')}</option>\n {enumValues.map((value: any) => (\n <option key={value} value={value}>\n {value}\n </option>\n ))}\n </select>\n </div>\n )\n }\n\n // Handle different field types\n switch (fieldType) {\n case 'string':\n if (fieldSchema.format === 'email') {\n return (\n <div key={fieldName} className=\"space-y-2\">\n <label htmlFor={fieldName} className={labelClasses}>\n {fieldTitle}\n {required && <span className=\"text-red-600 ml-1\">*</span>}\n </label>\n {fieldDescription && (\n <p className=\"text-xs text-muted-foreground\">{fieldDescription}</p>\n )}\n <input\n type=\"email\"\n id={fieldName}\n value={formData[fieldName] || ''}\n onChange={(e) => handleFieldChange(fieldName, e.target.value)}\n required={required}\n className={inputClasses}\n />\n </div>\n )\n }\n if (fieldSchema.format === 'date') {\n return (\n <div key={fieldName} className=\"space-y-2\">\n <label htmlFor={fieldName} className={labelClasses}>\n {fieldTitle}\n {required && <span className=\"text-red-600 ml-1\">*</span>}\n </label>\n {fieldDescription && (\n <p className=\"text-xs text-muted-foreground\">{fieldDescription}</p>\n )}\n <input\n type=\"date\"\n id={fieldName}\n value={formData[fieldName] || ''}\n onChange={(e) => handleFieldChange(fieldName, e.target.value)}\n required={required}\n className={inputClasses}\n />\n </div>\n )\n }\n if (fieldSchema.maxLength && fieldSchema.maxLength > 200) {\n return (\n <div key={fieldName} className=\"space-y-2\">\n <label htmlFor={fieldName} className={labelClasses}>\n {fieldTitle}\n {required && <span className=\"text-red-600 ml-1\">*</span>}\n </label>\n {fieldDescription && (\n <p className=\"text-xs text-muted-foreground\">{fieldDescription}</p>\n )}\n <textarea\n id={fieldName}\n value={formData[fieldName] || ''}\n onChange={(e) => handleFieldChange(fieldName, e.target.value)}\n required={required}\n rows={4}\n className={inputClasses}\n />\n </div>\n )\n }\n return (\n <div key={fieldName} className=\"space-y-2\">\n <label htmlFor={fieldName} className={labelClasses}>\n {fieldTitle}\n {required && <span className=\"text-red-600 ml-1\">*</span>}\n </label>\n {fieldDescription && (\n <p className=\"text-xs text-muted-foreground\">{fieldDescription}</p>\n )}\n <input\n type=\"text\"\n id={fieldName}\n value={formData[fieldName] || ''}\n onChange={(e) => handleFieldChange(fieldName, e.target.value)}\n required={required}\n className={inputClasses}\n />\n </div>\n )\n\n case 'number':\n case 'integer':\n return (\n <div key={fieldName} className=\"space-y-2\">\n <label htmlFor={fieldName} className={labelClasses}>\n {fieldTitle}\n {required && <span className=\"text-red-600 ml-1\">*</span>}\n </label>\n {fieldDescription && (\n <p className=\"text-xs text-muted-foreground\">{fieldDescription}</p>\n )}\n <input\n type=\"number\"\n id={fieldName}\n value={formData[fieldName] || ''}\n onChange={(e) => handleFieldChange(fieldName, e.target.value ? Number(e.target.value) : '')}\n required={required}\n step={fieldType === 'integer' ? 1 : 'any'}\n className={inputClasses}\n />\n </div>\n )\n\n case 'boolean':\n return (\n <div key={fieldName} className=\"space-y-2\">\n <div className=\"flex items-center gap-2\">\n <input\n type=\"checkbox\"\n id={fieldName}\n checked={!!formData[fieldName]}\n onChange={(e) => handleFieldChange(fieldName, e.target.checked)}\n className=\"w-4 h-4 text-primary border-border rounded focus:ring-primary\"\n />\n <label htmlFor={fieldName} className=\"text-sm font-medium text-foreground\">\n {fieldTitle}\n {required && <span className=\"text-red-600 ml-1\">*</span>}\n </label>\n </div>\n {fieldDescription && (\n <p className=\"text-xs text-muted-foreground ml-6\">{fieldDescription}</p>\n )}\n </div>\n )\n\n default:\n return (\n <div key={fieldName} className=\"space-y-2\">\n <label htmlFor={fieldName} className={labelClasses}>\n {fieldTitle}\n {required && <span className=\"text-red-600 ml-1\">*</span>}\n </label>\n {fieldDescription && (\n <p className=\"text-xs text-muted-foreground\">{fieldDescription}</p>\n )}\n <input\n type=\"text\"\n id={fieldName}\n value={formData[fieldName] || ''}\n onChange={(e) => handleFieldChange(fieldName, e.target.value)}\n required={required}\n className={inputClasses}\n />\n </div>\n )\n }\n }\n\n const getStatusBadgeClass = (status: UserTaskStatus) => {\n switch (status) {\n case 'PENDING':\n return 'bg-yellow-100 text-yellow-800'\n case 'IN_PROGRESS':\n return 'bg-blue-100 text-blue-800 dark:text-blue-200'\n case 'COMPLETED':\n return 'bg-green-100 text-green-800'\n case 'CANCELLED':\n return 'bg-muted text-foreground dark:bg-muted dark:text-foreground'\n default:\n return 'bg-muted text-muted-foreground'\n }\n }\n\n if (isLoading) {\n return (\n <Page>\n <PageBody>\n <div className=\"flex items-center justify-center py-12\">\n <Spinner />\n <span className=\"ml-3 text-muted-foreground\">{t('workflows.tasks.detail.loading')}</span>\n </div>\n </PageBody>\n </Page>\n )\n }\n\n if (error || !task) {\n return (\n <Page>\n <PageBody>\n <div className=\"p-8 text-center\">\n <p className=\"text-red-600\">{t('workflows.tasks.detail.notFound')}</p>\n <Button onClick={() => router.push('/backend/tasks')} className=\"mt-4\">\n {t('workflows.tasks.detail.backToList')}\n </Button>\n </div>\n </PageBody>\n </Page>\n )\n }\n\n const isCompletable = task.status === 'PENDING' || task.status === 'IN_PROGRESS'\n const isOverdue = task.dueDate && new Date(task.dueDate) < new Date() && isCompletable\n\n return (\n <Page>\n <PageBody>\n <div className=\"max-w-4xl mx-auto space-y-6\">\n {/* Header */}\n <div className=\"flex flex-col gap-3 md:flex-row md:items-center md:justify-between\">\n <div className=\"flex flex-wrap items-center gap-3\">\n <Link\n href=\"/backend/tasks\"\n className=\"inline-flex items-center text-sm text-muted-foreground hover:text-foreground\"\n >\n <span aria-hidden className=\"mr-1 text-base\">\u2190</span>\n <span className=\"sr-only\">{t('workflows.tasks.backToList', 'Back to tasks')}</span>\n </Link>\n <div className=\"space-y-1\">\n <p className=\"text-xs uppercase text-muted-foreground\">\n {t('workflows.tasks.detail.type', 'User task')}\n </p>\n <div className=\"flex flex-wrap items-center gap-2\">\n <h1 className=\"text-2xl font-bold\">{task.taskName}</h1>\n </div>\n {task.description && (\n <p className=\"text-sm text-muted-foreground\">{task.description}</p>\n )}\n </div>\n </div>\n <span\n className={`inline-flex items-center px-3 py-1 rounded text-sm font-medium ${getStatusBadgeClass(\n task.status\n )}`}\n >\n {t(`workflows.tasks.statuses.${task.status}`)}\n </span>\n </div>\n\n <div className=\"space-y-3\">\n\n {isOverdue && (\n <div className=\"bg-red-50 border border-red-200 rounded-lg p-3\">\n <p className=\"text-sm text-red-800 font-medium\">\n {t('workflows.tasks.detail.overdueWarning')}\n </p>\n </div>\n )}\n </div>\n\n <Separator />\n\n {/* Task Information */}\n <div className=\"bg-muted/50 rounded-lg p-4 space-y-3\">\n <h2 className=\"text-sm font-semibold\">{t('workflows.tasks.detail.sections.taskInfo')}</h2>\n <div className=\"grid grid-cols-2 gap-4 text-sm\">\n <div>\n <span className=\"text-muted-foreground\">{t('workflows.tasks.fields.createdAt')}:</span>\n <span className=\"ml-2 text-foreground\">{new Date(task.createdAt).toLocaleString()}</span>\n </div>\n {task.dueDate && (\n <div>\n <span className=\"text-muted-foreground\">{t('workflows.tasks.fields.dueDate')}:</span>\n <span className={`ml-2 ${isOverdue ? 'text-red-600 font-medium' : 'text-foreground'}`}>\n {new Date(task.dueDate).toLocaleString()}\n </span>\n </div>\n )}\n {task.assignedTo && (\n <div>\n <span className=\"text-muted-foreground\">{t('workflows.tasks.detail.assignedTo')}:</span>\n <span className=\"ml-2 text-foreground\">{task.assignedTo}</span>\n </div>\n )}\n {task.claimedBy && (\n <div>\n <span className=\"text-muted-foreground\">{t('workflows.tasks.claimedBy')}:</span>\n <span className=\"ml-2 text-foreground\">{task.claimedBy}</span>\n </div>\n )}\n <div>\n <span className=\"text-muted-foreground\">{t('workflows.tasks.detail.workflowInstance')}:</span>\n <Link\n href={`/backend/instances/${task.workflowInstanceId}`}\n className=\"ml-2 text-primary hover:underline text-xs font-mono\"\n >\n {task.workflowInstanceId.slice(0, 8)}...\n </Link>\n </div>\n </div>\n </div>\n\n {!isCompletable && (\n <div className=\"bg-blue-50 dark:bg-blue-950/50 border border-blue-200 dark:border-blue-800 rounded-lg p-4\">\n <p className=\"text-sm text-blue-800 dark:text-blue-200\">\n {t('workflows.tasks.detail.cannotComplete')}\n </p>\n </div>\n )}\n\n {isCompletable && (\n <>\n <Separator />\n\n {/* Dynamic Form */}\n <form onSubmit={handleSubmit} className=\"space-y-6\">\n {task.formSchema?.properties && (\n <div className=\"space-y-4\">\n <h2 className=\"text-lg font-semibold\">{t('workflows.tasks.detail.sections.form')}</h2>\n {Object.keys(task.formSchema.properties).map((fieldName) =>\n renderFormField(fieldName, task.formSchema.properties[fieldName])\n )}\n </div>\n )}\n\n {!task.formSchema?.properties && (\n <div className=\"bg-blue-50 dark:bg-blue-950/50 border border-blue-200 dark:border-blue-800 rounded-lg p-4\">\n <p className=\"text-sm text-blue-800 dark:text-blue-200\">\n {t('workflows.tasks.detail.noFormSchema')}\n </p>\n </div>\n )}\n\n <Separator />\n\n {/* Comments */}\n <div className=\"space-y-2\">\n <label htmlFor=\"comments\" className=\"block text-sm font-medium text-foreground\">\n {t('workflows.tasks.detail.comments')} ({t('workflows.tasks.detail.optional')})\n </label>\n <textarea\n id=\"comments\"\n value={comments}\n onChange={(e) => setComments(e.target.value)}\n rows={3}\n className=\"w-full px-3 py-2 border border-border rounded-md focus:outline-none focus:ring-2 focus:ring-primary\"\n placeholder={t('workflows.tasks.detail.commentsPlaceholder')}\n />\n </div>\n\n {/* Actions */}\n <div className=\"flex items-center gap-3 pt-4\">\n <Button\n type=\"submit\"\n disabled={submitting}\n className=\"bg-primary text-primary-foreground hover:bg-primary/90\"\n >\n {submitting ? t('workflows.tasks.detail.submitting') : t('workflows.tasks.detail.completeTask')}\n </Button>\n <Button\n type=\"button\"\n variant=\"outline\"\n onClick={() => router.push('/backend/tasks')}\n disabled={submitting}\n >\n {t('common.cancel')}\n </Button>\n </div>\n </form>\n </>\n )}\n\n {task.status === 'COMPLETED' && task.formData && (\n <>\n <Separator />\n <JsonDisplay\n data={task.formData}\n title={t('workflows.tasks.detail.sections.submittedData')}\n maxInitialDepth={2}\n />\n {task.comments && (\n <div className=\"bg-muted/50 rounded-lg p-4\">\n <p className=\"text-sm font-medium text-foreground mb-2\">{t('workflows.tasks.detail.comments')}:</p>\n <p className=\"text-sm text-muted-foreground whitespace-pre-wrap\">{task.comments}</p>\n </div>\n )}\n </>\n )}\n </div>\n </PageBody>\n </Page>\n )\n}\n"],
|
|
5
|
-
"mappings": "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
|
|
4
|
+
"sourcesContent": ["\"use client\"\n\nimport * as React from 'react'\nimport Link from 'next/link'\nimport { useRouter } from 'next/navigation'\nimport { Page, PageBody } from '@open-mercato/ui/backend/Page'\nimport { Button } from '@open-mercato/ui/primitives/button'\nimport { Spinner } from '@open-mercato/ui/primitives/spinner'\nimport { Separator } from '@open-mercato/ui/primitives/separator'\nimport { JsonDisplay } from '@open-mercato/ui/backend/JsonDisplay'\nimport { apiCall } from '@open-mercato/ui/backend/utils/apiCall'\nimport { flash } from '@open-mercato/ui/backend/FlashMessages'\nimport { useQuery } from '@tanstack/react-query'\nimport { useT } from '@open-mercato/shared/lib/i18n/context'\n\ntype UserTaskStatus = 'PENDING' | 'IN_PROGRESS' | 'COMPLETED' | 'CANCELLED'\n\ntype UserTask = {\n id: string\n workflowInstanceId: string\n stepInstanceId: string\n taskName: string\n description: string | null\n status: UserTaskStatus\n formSchema: any | null\n formData: any | null\n assignedTo: string | null\n assignedToRoles: string[] | null\n claimedBy: string | null\n claimedAt: string | null\n dueDate: string | null\n completedBy: string | null\n completedAt: string | null\n comments: string | null\n tenantId: string\n organizationId: string\n createdAt: string\n updatedAt: string\n}\n\nexport default function UserTaskDetailPage({ params }: { params: { id: string } }) {\n const router = useRouter()\n const t = useT()\n const [formData, setFormData] = React.useState<Record<string, any>>({})\n const [comments, setComments] = React.useState('')\n const [submitting, setSubmitting] = React.useState(false)\n\n const { data: task, isLoading, error } = useQuery({\n queryKey: ['workflow-task', params.id],\n queryFn: async () => {\n const result = await apiCall<{ data: UserTask }>(\n `/api/workflows/tasks/${params.id}`\n )\n\n if (!result.ok) {\n throw new Error('Failed to fetch task')\n }\n\n return result.result?.data || null\n },\n })\n\n const handleFieldChange = (fieldName: string, value: any) => {\n setFormData(prev => ({\n ...prev,\n [fieldName]: value,\n }))\n }\n\n const handleSubmit = async (e: React.FormEvent) => {\n e.preventDefault()\n\n if (!task) return\n\n // Validate required fields\n if (task.formSchema?.required) {\n for (const requiredField of task.formSchema.required) {\n if (!formData[requiredField] || formData[requiredField] === '') {\n flash(t('workflows.tasks.detail.validation.requiredField', { field: requiredField }), 'error')\n return\n }\n }\n }\n\n setSubmitting(true)\n\n try {\n const result = await apiCall(`/api/workflows/tasks/${params.id}/complete`, {\n method: 'POST',\n headers: {\n 'Content-Type': 'application/json',\n },\n body: JSON.stringify({\n formData,\n comments: comments || undefined,\n }),\n })\n\n if (result.ok) {\n flash(t('workflows.tasks.messages.completed'), 'success')\n router.push('/backend/tasks')\n } else {\n const error = result.result as any\n flash(error?.error || t('workflows.tasks.messages.completeFailed'), 'error')\n }\n } catch (err) {\n console.error('Error completing task:', err)\n flash(t('workflows.tasks.messages.completeFailed'), 'error')\n } finally {\n setSubmitting(false)\n }\n }\n\n const renderFormField = (fieldName: string, fieldSchema: any) => {\n const fieldType = fieldSchema.type || 'string'\n const fieldTitle = fieldSchema.title || fieldName\n const fieldDescription = fieldSchema.description\n const required = task?.formSchema?.required?.includes(fieldName) || false\n const enumValues = fieldSchema.enum\n\n const inputClasses = \"w-full px-3 py-2 border border-border rounded-md focus:outline-none focus:ring-2 focus:ring-primary\"\n const labelClasses = \"block text-sm font-medium text-foreground mb-1\"\n\n // Handle enum (select dropdown)\n if (enumValues && Array.isArray(enumValues)) {\n return (\n <div key={fieldName} className=\"space-y-2\">\n <label htmlFor={fieldName} className={labelClasses}>\n {fieldTitle}\n {required && <span className=\"text-red-600 ml-1\">*</span>}\n </label>\n {fieldDescription && (\n <p className=\"text-xs text-muted-foreground\">{fieldDescription}</p>\n )}\n <select\n id={fieldName}\n value={formData[fieldName] || ''}\n onChange={(e) => handleFieldChange(fieldName, e.target.value)}\n required={required}\n className={inputClasses}\n >\n <option value=\"\">{t('workflows.tasks.detail.form.selectOption')}</option>\n {enumValues.map((value: any) => (\n <option key={value} value={value}>\n {value}\n </option>\n ))}\n </select>\n </div>\n )\n }\n\n // Handle different field types\n switch (fieldType) {\n case 'string':\n if (fieldSchema.format === 'email') {\n return (\n <div key={fieldName} className=\"space-y-2\">\n <label htmlFor={fieldName} className={labelClasses}>\n {fieldTitle}\n {required && <span className=\"text-red-600 ml-1\">*</span>}\n </label>\n {fieldDescription && (\n <p className=\"text-xs text-muted-foreground\">{fieldDescription}</p>\n )}\n <input\n type=\"email\"\n id={fieldName}\n value={formData[fieldName] || ''}\n onChange={(e) => handleFieldChange(fieldName, e.target.value)}\n required={required}\n className={inputClasses}\n />\n </div>\n )\n }\n if (fieldSchema.format === 'date') {\n return (\n <div key={fieldName} className=\"space-y-2\">\n <label htmlFor={fieldName} className={labelClasses}>\n {fieldTitle}\n {required && <span className=\"text-red-600 ml-1\">*</span>}\n </label>\n {fieldDescription && (\n <p className=\"text-xs text-muted-foreground\">{fieldDescription}</p>\n )}\n <input\n type=\"date\"\n id={fieldName}\n value={formData[fieldName] || ''}\n onChange={(e) => handleFieldChange(fieldName, e.target.value)}\n required={required}\n className={inputClasses}\n />\n </div>\n )\n }\n if (fieldSchema.maxLength && fieldSchema.maxLength > 200) {\n return (\n <div key={fieldName} className=\"space-y-2\">\n <label htmlFor={fieldName} className={labelClasses}>\n {fieldTitle}\n {required && <span className=\"text-red-600 ml-1\">*</span>}\n </label>\n {fieldDescription && (\n <p className=\"text-xs text-muted-foreground\">{fieldDescription}</p>\n )}\n <textarea\n id={fieldName}\n value={formData[fieldName] || ''}\n onChange={(e) => handleFieldChange(fieldName, e.target.value)}\n required={required}\n rows={4}\n className={inputClasses}\n />\n </div>\n )\n }\n return (\n <div key={fieldName} className=\"space-y-2\">\n <label htmlFor={fieldName} className={labelClasses}>\n {fieldTitle}\n {required && <span className=\"text-red-600 ml-1\">*</span>}\n </label>\n {fieldDescription && (\n <p className=\"text-xs text-muted-foreground\">{fieldDescription}</p>\n )}\n <input\n type=\"text\"\n id={fieldName}\n value={formData[fieldName] || ''}\n onChange={(e) => handleFieldChange(fieldName, e.target.value)}\n required={required}\n className={inputClasses}\n />\n </div>\n )\n\n case 'number':\n case 'integer':\n return (\n <div key={fieldName} className=\"space-y-2\">\n <label htmlFor={fieldName} className={labelClasses}>\n {fieldTitle}\n {required && <span className=\"text-red-600 ml-1\">*</span>}\n </label>\n {fieldDescription && (\n <p className=\"text-xs text-muted-foreground\">{fieldDescription}</p>\n )}\n <input\n type=\"number\"\n id={fieldName}\n value={formData[fieldName] || ''}\n onChange={(e) => handleFieldChange(fieldName, e.target.value ? Number(e.target.value) : '')}\n required={required}\n step={fieldType === 'integer' ? 1 : 'any'}\n className={inputClasses}\n />\n </div>\n )\n\n case 'boolean':\n return (\n <div key={fieldName} className=\"space-y-2\">\n <div className=\"flex items-center gap-2\">\n <input\n type=\"checkbox\"\n id={fieldName}\n checked={!!formData[fieldName]}\n onChange={(e) => handleFieldChange(fieldName, e.target.checked)}\n className=\"w-4 h-4 text-primary border-border rounded focus:ring-primary\"\n />\n <label htmlFor={fieldName} className=\"text-sm font-medium text-foreground\">\n {fieldTitle}\n {required && <span className=\"text-red-600 ml-1\">*</span>}\n </label>\n </div>\n {fieldDescription && (\n <p className=\"text-xs text-muted-foreground ml-6\">{fieldDescription}</p>\n )}\n </div>\n )\n\n default:\n return (\n <div key={fieldName} className=\"space-y-2\">\n <label htmlFor={fieldName} className={labelClasses}>\n {fieldTitle}\n {required && <span className=\"text-red-600 ml-1\">*</span>}\n </label>\n {fieldDescription && (\n <p className=\"text-xs text-muted-foreground\">{fieldDescription}</p>\n )}\n <input\n type=\"text\"\n id={fieldName}\n value={formData[fieldName] || ''}\n onChange={(e) => handleFieldChange(fieldName, e.target.value)}\n required={required}\n className={inputClasses}\n />\n </div>\n )\n }\n }\n\n const getStatusBadgeClass = (status: UserTaskStatus) => {\n switch (status) {\n case 'PENDING':\n return 'bg-yellow-100 text-yellow-800'\n case 'IN_PROGRESS':\n return 'bg-blue-100 text-blue-800 dark:text-blue-200'\n case 'COMPLETED':\n return 'bg-green-100 text-green-800'\n case 'CANCELLED':\n return 'bg-muted text-foreground dark:bg-muted dark:text-foreground'\n default:\n return 'bg-muted text-muted-foreground'\n }\n }\n\n if (isLoading) {\n return (\n <Page>\n <PageBody>\n <div className=\"flex items-center justify-center py-12\">\n <Spinner />\n <span className=\"ml-3 text-muted-foreground\">{t('workflows.tasks.detail.loading')}</span>\n </div>\n </PageBody>\n </Page>\n )\n }\n\n if (error || !task) {\n return (\n <Page>\n <PageBody>\n <div className=\"p-8 text-center\">\n <p className=\"text-red-600\">{t('workflows.tasks.detail.notFound')}</p>\n <Button onClick={() => router.push('/backend/tasks')} className=\"mt-4\">\n {t('workflows.tasks.detail.backToList')}\n </Button>\n </div>\n </PageBody>\n </Page>\n )\n }\n\n const isCompletable = task.status === 'PENDING' || task.status === 'IN_PROGRESS'\n const isOverdue = task.dueDate && new Date(task.dueDate) < new Date() && isCompletable\n\n return (\n <Page>\n <PageBody>\n <div className=\"max-w-4xl mx-auto space-y-6\">\n {/* Header */}\n <div className=\"flex flex-col gap-3 md:flex-row md:items-center md:justify-between\">\n <div className=\"flex flex-wrap items-center gap-3\">\n <Link\n href=\"/backend/tasks\"\n className=\"inline-flex items-center text-sm text-muted-foreground hover:text-foreground\"\n >\n <span aria-hidden className=\"mr-1 text-base\">\u2190</span>\n <span className=\"sr-only\">{t('workflows.tasks.backToList', 'Back to tasks')}</span>\n </Link>\n <div className=\"space-y-1\">\n <p className=\"text-xs uppercase text-muted-foreground\">\n {t('workflows.tasks.detail.type', 'User task')}\n </p>\n <div className=\"flex flex-wrap items-center gap-2\">\n <h1 className=\"text-2xl font-bold\">{task.taskName}</h1>\n </div>\n {task.description && (\n <p className=\"text-sm text-muted-foreground\">{task.description}</p>\n )}\n </div>\n </div>\n <span\n className={`inline-flex items-center px-3 py-1 rounded text-sm font-medium ${getStatusBadgeClass(\n task.status\n )}`}\n >\n {t(`workflows.tasks.status.${task.status}`)}\n </span>\n </div>\n\n <div className=\"space-y-3\">\n\n {isOverdue && (\n <div className=\"bg-red-50 border border-red-200 rounded-lg p-3\">\n <p className=\"text-sm text-red-800 font-medium\">\n {t('workflows.tasks.detail.overdueWarning')}\n </p>\n </div>\n )}\n </div>\n\n <Separator />\n\n {/* Task Information */}\n <div className=\"bg-muted/50 rounded-lg p-4 space-y-3\">\n <h2 className=\"text-sm font-semibold\">{t('workflows.tasks.detail.sections.taskInfo')}</h2>\n <div className=\"grid grid-cols-2 gap-4 text-sm\">\n <div>\n <span className=\"text-muted-foreground\">{t('workflows.tasks.fields.createdAt')}:</span>\n <span className=\"ml-2 text-foreground\">{new Date(task.createdAt).toLocaleString()}</span>\n </div>\n {task.dueDate && (\n <div>\n <span className=\"text-muted-foreground\">{t('workflows.tasks.fields.dueDate')}:</span>\n <span className={`ml-2 ${isOverdue ? 'text-red-600 font-medium' : 'text-foreground'}`}>\n {new Date(task.dueDate).toLocaleString()}\n </span>\n </div>\n )}\n {task.assignedTo && (\n <div>\n <span className=\"text-muted-foreground\">{t('workflows.tasks.detail.assignedTo')}:</span>\n <span className=\"ml-2 text-foreground\">{task.assignedTo}</span>\n </div>\n )}\n {task.claimedBy && (\n <div>\n <span className=\"text-muted-foreground\">{t('workflows.tasks.claimedBy')}:</span>\n <span className=\"ml-2 text-foreground\">{task.claimedBy}</span>\n </div>\n )}\n <div>\n <span className=\"text-muted-foreground\">{t('workflows.tasks.detail.workflowInstance')}:</span>\n <Link\n href={`/backend/instances/${task.workflowInstanceId}`}\n className=\"ml-2 text-primary hover:underline text-xs font-mono\"\n >\n {task.workflowInstanceId.slice(0, 8)}...\n </Link>\n </div>\n </div>\n </div>\n\n {!isCompletable && (\n <div className=\"bg-blue-50 dark:bg-blue-950/50 border border-blue-200 dark:border-blue-800 rounded-lg p-4\">\n <p className=\"text-sm text-blue-800 dark:text-blue-200\">\n {t('workflows.tasks.detail.cannotComplete')}\n </p>\n </div>\n )}\n\n {isCompletable && (\n <>\n <Separator />\n\n {/* Dynamic Form */}\n <form onSubmit={handleSubmit} className=\"space-y-6\">\n {task.formSchema?.properties && (\n <div className=\"space-y-4\">\n <h2 className=\"text-lg font-semibold\">{t('workflows.tasks.detail.sections.form')}</h2>\n {Object.keys(task.formSchema.properties).map((fieldName) =>\n renderFormField(fieldName, task.formSchema.properties[fieldName])\n )}\n </div>\n )}\n\n {!task.formSchema?.properties && (\n <div className=\"bg-blue-50 dark:bg-blue-950/50 border border-blue-200 dark:border-blue-800 rounded-lg p-4\">\n <p className=\"text-sm text-blue-800 dark:text-blue-200\">\n {t('workflows.tasks.detail.noFormSchema')}\n </p>\n </div>\n )}\n\n <Separator />\n\n {/* Comments */}\n <div className=\"space-y-2\">\n <label htmlFor=\"comments\" className=\"block text-sm font-medium text-foreground\">\n {t('workflows.tasks.detail.comments')} ({t('workflows.tasks.detail.optional')})\n </label>\n <textarea\n id=\"comments\"\n value={comments}\n onChange={(e) => setComments(e.target.value)}\n rows={3}\n className=\"w-full px-3 py-2 border border-border rounded-md focus:outline-none focus:ring-2 focus:ring-primary\"\n placeholder={t('workflows.tasks.detail.commentsPlaceholder')}\n />\n </div>\n\n {/* Actions */}\n <div className=\"flex items-center gap-3 pt-4\">\n <Button\n type=\"submit\"\n disabled={submitting}\n className=\"bg-primary text-primary-foreground hover:bg-primary/90\"\n >\n {submitting ? t('workflows.tasks.detail.submitting') : t('workflows.tasks.detail.completeTask')}\n </Button>\n <Button\n type=\"button\"\n variant=\"outline\"\n onClick={() => router.push('/backend/tasks')}\n disabled={submitting}\n >\n {t('common.cancel')}\n </Button>\n </div>\n </form>\n </>\n )}\n\n {task.status === 'COMPLETED' && task.formData && (\n <>\n <Separator />\n <JsonDisplay\n data={task.formData}\n title={t('workflows.tasks.detail.sections.submittedData')}\n maxInitialDepth={2}\n />\n {task.comments && (\n <div className=\"bg-muted/50 rounded-lg p-4\">\n <p className=\"text-sm font-medium text-foreground mb-2\">{t('workflows.tasks.detail.comments')}:</p>\n <p className=\"text-sm text-muted-foreground whitespace-pre-wrap\">{task.comments}</p>\n </div>\n )}\n </>\n )}\n </div>\n </PageBody>\n </Page>\n )\n}\n"],
|
|
5
|
+
"mappings": "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",
|
|
6
6
|
"names": ["error"]
|
|
7
7
|
}
|
|
@@ -4,8 +4,8 @@ const metadata = {
|
|
|
4
4
|
pageTitle: "Task Details",
|
|
5
5
|
pageTitleKey: "workflows.tasks.singular",
|
|
6
6
|
breadcrumb: [
|
|
7
|
-
{ label: "Workflows", labelKey: "workflows.module.name", href: "/backend/definitions" },
|
|
8
|
-
{ label: "Tasks", labelKey: "workflows.tasks.plural", href: "/backend/tasks" },
|
|
7
|
+
{ label: "Workflows", labelKey: "workflows.module.name", href: "/backend/workflows/definitions" },
|
|
8
|
+
{ label: "Tasks", labelKey: "workflows.tasks.plural", href: "/backend/workflows/tasks" },
|
|
9
9
|
{ label: "Details", labelKey: "common.details" }
|
|
10
10
|
]
|
|
11
11
|
};
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"version": 3,
|
|
3
3
|
"sources": ["../../../../../../src/modules/workflows/backend/tasks/%5Bid%5D/page.meta.ts"],
|
|
4
|
-
"sourcesContent": ["export const metadata = {\n requireAuth: true,\n requireFeatures: ['workflows.view_tasks'],\n pageTitle: 'Task Details',\n pageTitleKey: 'workflows.tasks.singular',\n breadcrumb: [\n { label: 'Workflows', labelKey: 'workflows.module.name', href: '/backend/definitions' },\n { label: 'Tasks', labelKey: 'workflows.tasks.plural', href: '/backend/tasks' },\n { label: 'Details', labelKey: 'common.details' },\n ],\n}\n"],
|
|
5
|
-
"mappings": "AAAO,MAAM,WAAW;AAAA,EACtB,aAAa;AAAA,EACb,iBAAiB,CAAC,sBAAsB;AAAA,EACxC,WAAW;AAAA,EACX,cAAc;AAAA,EACd,YAAY;AAAA,IACV,EAAE,OAAO,aAAa,UAAU,yBAAyB,MAAM,
|
|
4
|
+
"sourcesContent": ["export const metadata = {\n requireAuth: true,\n requireFeatures: ['workflows.view_tasks'],\n pageTitle: 'Task Details',\n pageTitleKey: 'workflows.tasks.singular',\n breadcrumb: [\n { label: 'Workflows', labelKey: 'workflows.module.name', href: '/backend/workflows/definitions' },\n { label: 'Tasks', labelKey: 'workflows.tasks.plural', href: '/backend/workflows/tasks' },\n { label: 'Details', labelKey: 'common.details' },\n ],\n}\n"],
|
|
5
|
+
"mappings": "AAAO,MAAM,WAAW;AAAA,EACtB,aAAa;AAAA,EACb,iBAAiB,CAAC,sBAAsB;AAAA,EACxC,WAAW;AAAA,EACX,cAAc;AAAA,EACd,YAAY;AAAA,IACV,EAAE,OAAO,aAAa,UAAU,yBAAyB,MAAM,iCAAiC;AAAA,IAChG,EAAE,OAAO,SAAS,UAAU,0BAA0B,MAAM,2BAA2B;AAAA,IACvF,EAAE,OAAO,WAAW,UAAU,iBAAiB;AAAA,EACjD;AACF;",
|
|
6
6
|
"names": []
|
|
7
7
|
}
|
|
@@ -30,6 +30,7 @@ function UserTasksListPage() {
|
|
|
30
30
|
params.set("limit", pageSize.toString());
|
|
31
31
|
params.set("offset", offset.toString());
|
|
32
32
|
if (filterValues.status) params.set("status", filterValues.status);
|
|
33
|
+
if (filterValues.myTasks === "true") params.set("myTasks", "true");
|
|
33
34
|
if (filterValues.overdue === "true") params.set("overdue", "true");
|
|
34
35
|
if (filterValues.workflowInstanceId) params.set("workflowInstanceId", filterValues.workflowInstanceId);
|
|
35
36
|
const result = await apiCall(
|
|
@@ -100,10 +101,10 @@ function UserTasksListPage() {
|
|
|
100
101
|
label: t("workflows.tasks.filters.status"),
|
|
101
102
|
options: [
|
|
102
103
|
{ label: t("common.all"), value: "" },
|
|
103
|
-
{ label: t("workflows.tasks.
|
|
104
|
-
{ label: t("workflows.tasks.
|
|
105
|
-
{ label: t("workflows.tasks.
|
|
106
|
-
{ label: t("workflows.tasks.
|
|
104
|
+
{ label: t("workflows.tasks.status.PENDING"), value: "PENDING" },
|
|
105
|
+
{ label: t("workflows.tasks.status.IN_PROGRESS"), value: "IN_PROGRESS" },
|
|
106
|
+
{ label: t("workflows.tasks.status.COMPLETED"), value: "COMPLETED" },
|
|
107
|
+
{ label: t("workflows.tasks.status.CANCELLED"), value: "CANCELLED" }
|
|
107
108
|
]
|
|
108
109
|
},
|
|
109
110
|
{
|
|
@@ -146,7 +147,7 @@ function UserTasksListPage() {
|
|
|
146
147
|
id: "status",
|
|
147
148
|
header: t("workflows.tasks.fields.status"),
|
|
148
149
|
accessorKey: "status",
|
|
149
|
-
cell: ({ row }) => /* @__PURE__ */ jsx("span", { className: `inline-flex items-center px-2 py-1 rounded text-xs font-medium ${getStatusBadgeClass(row.original.status)}`, children: t(`workflows.tasks.
|
|
150
|
+
cell: ({ row }) => /* @__PURE__ */ jsx("span", { className: `inline-flex items-center px-2 py-1 rounded text-xs font-medium ${getStatusBadgeClass(row.original.status)}`, children: t(`workflows.tasks.status.${row.original.status}`) })
|
|
150
151
|
},
|
|
151
152
|
{
|
|
152
153
|
id: "assignment",
|
|
@@ -197,18 +198,21 @@ function UserTasksListPage() {
|
|
|
197
198
|
cell: ({ row }) => {
|
|
198
199
|
const items = [
|
|
199
200
|
{
|
|
201
|
+
id: "view",
|
|
200
202
|
label: t("workflows.tasks.actions.viewDetails"),
|
|
201
203
|
href: `/backend/tasks/${row.original.id}`
|
|
202
204
|
}
|
|
203
205
|
];
|
|
204
206
|
if (row.original.status === "PENDING" && !row.original.assignedTo && row.original.assignedToRoles && row.original.assignedToRoles.length > 0) {
|
|
205
207
|
items.push({
|
|
208
|
+
id: "claim",
|
|
206
209
|
label: t("workflows.tasks.actions.claim"),
|
|
207
210
|
onSelect: () => handleClaim(row.original.id, row.original.taskName)
|
|
208
211
|
});
|
|
209
212
|
}
|
|
210
213
|
if (row.original.status === "PENDING" || row.original.status === "IN_PROGRESS") {
|
|
211
214
|
items.push({
|
|
215
|
+
id: "complete",
|
|
212
216
|
label: t("workflows.tasks.actions.complete"),
|
|
213
217
|
href: `/backend/tasks/${row.original.id}`
|
|
214
218
|
});
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"version": 3,
|
|
3
3
|
"sources": ["../../../../../src/modules/workflows/backend/tasks/page.tsx"],
|
|
4
|
-
"sourcesContent": ["\"use client\"\n\nimport * as React from 'react'\nimport Link from 'next/link'\nimport { useRouter } from 'next/navigation'\nimport { Page, PageBody } from '@open-mercato/ui/backend/Page'\nimport { DataTable } from '@open-mercato/ui/backend/DataTable'\nimport type { ColumnDef } from '@tanstack/react-table'\nimport { Button } from '@open-mercato/ui/primitives/button'\nimport { RowActions } from '@open-mercato/ui/backend/RowActions'\nimport { apiCall } from '@open-mercato/ui/backend/utils/apiCall'\nimport { flash } from '@open-mercato/ui/backend/FlashMessages'\nimport { useQuery, useQueryClient } from '@tanstack/react-query'\nimport { useT } from '@open-mercato/shared/lib/i18n/context'\nimport type { FilterDef, FilterValues } from '@open-mercato/ui/backend/FilterBar'\n\ntype UserTaskStatus = 'PENDING' | 'IN_PROGRESS' | 'COMPLETED' | 'CANCELLED'\n\ntype UserTask = {\n id: string\n workflowInstanceId: string\n stepInstanceId: string\n taskName: string\n description: string | null\n status: UserTaskStatus\n formSchema: any | null\n formData: any | null\n assignedTo: string | null\n assignedToRoles: string[] | null\n claimedBy: string | null\n claimedAt: string | null\n dueDate: string | null\n escalatedAt: string | null\n escalatedTo: string | null\n completedBy: string | null\n completedAt: string | null\n comments: string | null\n tenantId: string\n organizationId: string\n createdAt: string\n updatedAt: string\n}\n\ntype TasksResponse = {\n data: UserTask[]\n pagination: {\n total: number\n limit: number\n offset: number\n hasMore: boolean\n }\n}\n\nexport default function UserTasksListPage() {\n const [page, setPage] = React.useState(1)\n const [pageSize] = React.useState(50)\n const [total, setTotal] = React.useState(0)\n const [totalPages, setTotalPages] = React.useState(1)\n const t = useT()\n const router = useRouter()\n const queryClient = useQueryClient()\n const [filterValues, setFilterValues] = React.useState<FilterValues>({\n myTasks: 'true', // Default to \"My Tasks\" view\n })\n\n const { data, isLoading, error } = useQuery({\n queryKey: ['workflow-tasks', 'list', filterValues, page],\n queryFn: async () => {\n const params = new URLSearchParams()\n const offset = (page - 1) * pageSize\n params.set('limit', pageSize.toString())\n params.set('offset', offset.toString())\n\n if (filterValues.status) params.set('status', filterValues.status as string)\n if (filterValues.overdue === 'true') params.set('overdue', 'true')\n if (filterValues.workflowInstanceId) params.set('workflowInstanceId', filterValues.workflowInstanceId as string)\n\n const result = await apiCall<TasksResponse>(\n `/api/workflows/tasks?${params.toString()}`\n )\n\n if (!result.ok) {\n throw new Error('Failed to fetch user tasks')\n }\n\n const response = result.result\n if (response?.pagination) {\n setTotal(response.pagination.total || 0)\n const calculatedPages = Math.ceil((response.pagination.total || 0) / pageSize)\n setTotalPages(calculatedPages || 1)\n }\n\n return response?.data || []\n },\n })\n\n const handleClaim = async (id: string, taskName: string) => {\n if (!confirm(t('workflows.tasks.confirm.claim', { name: taskName }))) {\n return\n }\n\n const result = await apiCall(`/api/workflows/tasks/${id}/claim`, {\n method: 'POST',\n })\n\n if (result.ok) {\n flash(t('workflows.tasks.messages.claimed'), 'success')\n queryClient.invalidateQueries({ queryKey: ['workflow-tasks'] })\n } else {\n flash(t('workflows.tasks.messages.claimFailed'), 'error')\n }\n }\n\n const handleFiltersApply = React.useCallback((values: FilterValues) => {\n const next: FilterValues = {}\n Object.entries(values).forEach(([key, value]) => {\n if (value !== undefined && value !== '') next[key] = value\n })\n setFilterValues(next)\n setPage(1)\n }, [])\n\n const handleFiltersClear = React.useCallback(() => {\n setFilterValues({ myTasks: 'true' })\n setPage(1)\n }, [])\n\n const getStatusBadgeClass = (status: UserTaskStatus) => {\n switch (status) {\n case 'PENDING':\n return 'bg-yellow-100 text-yellow-800'\n case 'IN_PROGRESS':\n return 'bg-blue-100 text-blue-800'\n case 'COMPLETED':\n return 'bg-green-100 text-green-800'\n case 'CANCELLED':\n return 'bg-muted text-foreground'\n default:\n return 'bg-muted text-muted-foreground'\n }\n }\n\n const isOverdue = (task: UserTask) => {\n if (!task.dueDate || task.status === 'COMPLETED' || task.status === 'CANCELLED') {\n return false\n }\n return new Date(task.dueDate) < new Date()\n }\n\n const filters: FilterDef[] = [\n {\n id: 'status',\n type: 'select',\n label: t('workflows.tasks.filters.status'),\n options: [\n { label: t('common.all'), value: '' },\n { label: t('workflows.tasks.statuses.PENDING'), value: 'PENDING' },\n { label: t('workflows.tasks.statuses.IN_PROGRESS'), value: 'IN_PROGRESS' },\n { label: t('workflows.tasks.statuses.COMPLETED'), value: 'COMPLETED' },\n { label: t('workflows.tasks.statuses.CANCELLED'), value: 'CANCELLED' },\n ],\n },\n {\n id: 'myTasks',\n type: 'select',\n label: t('workflows.tasks.filters.view'),\n options: [\n { label: t('workflows.tasks.filters.myTasks'), value: 'true' },\n { label: t('workflows.tasks.filters.allTasks'), value: '' },\n ],\n },\n {\n id: 'overdue',\n type: 'select',\n label: t('workflows.tasks.filters.overdue'),\n options: [\n { label: t('common.all'), value: '' },\n { label: t('workflows.tasks.filters.overdueOnly'), value: 'true' },\n ],\n },\n {\n id: 'workflowInstanceId',\n type: 'text',\n label: t('workflows.tasks.filters.workflowInstanceId'),\n placeholder: t('workflows.tasks.filters.workflowInstanceIdPlaceholder'),\n },\n ]\n\n const columns: ColumnDef<UserTask>[] = [\n {\n id: 'taskName',\n header: t('workflows.tasks.fields.taskName'),\n accessorKey: 'taskName',\n cell: ({ row }) => (\n <div>\n <div className=\"font-medium text-sm\">{row.original.taskName}</div>\n {row.original.description && (\n <div className=\"text-xs text-muted-foreground line-clamp-1\">\n {row.original.description}\n </div>\n )}\n {isOverdue(row.original) && (\n <div className=\"text-xs text-red-600 font-medium mt-1\">\n {t('workflows.tasks.overdue')}\n </div>\n )}\n </div>\n ),\n },\n {\n id: 'status',\n header: t('workflows.tasks.fields.status'),\n accessorKey: 'status',\n cell: ({ row }) => (\n <span className={`inline-flex items-center px-2 py-1 rounded text-xs font-medium ${getStatusBadgeClass(row.original.status)}`}>\n {t(`workflows.tasks.statuses.${row.original.status}`)}\n </span>\n ),\n },\n {\n id: 'assignment',\n header: t('workflows.tasks.fields.assignment'),\n cell: ({ row }) => {\n if (row.original.claimedBy) {\n return (\n <div className=\"text-sm\">\n <div className=\"text-foreground\">{t('workflows.tasks.claimedBy')}: {row.original.claimedBy}</div>\n </div>\n )\n }\n if (row.original.assignedTo) {\n return <div className=\"text-sm text-foreground\">{row.original.assignedTo}</div>\n }\n if (row.original.assignedToRoles && row.original.assignedToRoles.length > 0) {\n return (\n <div className=\"text-sm text-muted-foreground\">\n {t('workflows.tasks.roles')}: {row.original.assignedToRoles.join(', ')}\n </div>\n )\n }\n return <span className=\"text-sm text-muted-foreground\">-</span>\n },\n },\n {\n id: 'dueDate',\n header: t('workflows.tasks.fields.dueDate'),\n accessorKey: 'dueDate',\n cell: ({ row }) => {\n if (!row.original.dueDate) {\n return <span className=\"text-sm text-muted-foreground\">-</span>\n }\n const dueDate = new Date(row.original.dueDate)\n const overdue = isOverdue(row.original)\n return (\n <div className={`text-sm ${overdue ? 'text-red-600 font-medium' : 'text-foreground'}`}>\n {dueDate.toLocaleString()}\n </div>\n )\n },\n },\n {\n id: 'createdAt',\n header: t('workflows.tasks.fields.createdAt'),\n accessorKey: 'createdAt',\n cell: ({ row }) => (\n <span className=\"text-sm text-muted-foreground\">\n {new Date(row.original.createdAt).toLocaleString()}\n </span>\n ),\n },\n {\n id: 'actions',\n header: '',\n cell: ({ row }) => {\n const items: Array<{label: string; href?: string; onSelect?: () => void}> = [\n {\n label: t('workflows.tasks.actions.viewDetails'),\n href: `/backend/tasks/${row.original.id}`,\n },\n ]\n\n // Allow claiming if task is PENDING and assigned to roles (not specific user)\n if (\n row.original.status === 'PENDING' &&\n !row.original.assignedTo &&\n row.original.assignedToRoles &&\n row.original.assignedToRoles.length > 0\n ) {\n items.push({\n label: t('workflows.tasks.actions.claim'),\n onSelect: () => handleClaim(row.original.id, row.original.taskName),\n })\n }\n\n // Allow completing if task is in progress or pending\n if (row.original.status === 'PENDING' || row.original.status === 'IN_PROGRESS') {\n items.push({\n label: t('workflows.tasks.actions.complete'),\n href: `/backend/tasks/${row.original.id}`,\n })\n }\n\n return <RowActions items={items} />\n },\n },\n ]\n\n if (error) {\n return (\n <Page>\n <PageBody>\n <div className=\"p-8 text-center\">\n <p className=\"text-red-600\">{t('workflows.tasks.messages.loadFailed')}</p>\n <Button onClick={() => queryClient.invalidateQueries({ queryKey: ['workflow-tasks'] })} className=\"mt-4\">\n {t('common.retry')}\n </Button>\n </div>\n </PageBody>\n </Page>\n )\n }\n\n return (\n <Page>\n <PageBody>\n <DataTable\n title={t('workflows.tasks.list.title')}\n columns={columns}\n data={data || []}\n filters={filters}\n filterValues={filterValues}\n onFiltersApply={handleFiltersApply}\n onFiltersClear={handleFiltersClear}\n perspective={{\n tableId: 'workflows.tasks.list',\n }}\n pagination={{ page, pageSize, total, totalPages, onPageChange: setPage }}\n />\n </PageBody>\n </Page>\n )\n}\n"],
|
|
5
|
-
"mappings": ";
|
|
4
|
+
"sourcesContent": ["\"use client\"\n\nimport * as React from 'react'\nimport Link from 'next/link'\nimport { useRouter } from 'next/navigation'\nimport { Page, PageBody } from '@open-mercato/ui/backend/Page'\nimport { DataTable } from '@open-mercato/ui/backend/DataTable'\nimport type { ColumnDef } from '@tanstack/react-table'\nimport { Button } from '@open-mercato/ui/primitives/button'\nimport { RowActions } from '@open-mercato/ui/backend/RowActions'\nimport { apiCall } from '@open-mercato/ui/backend/utils/apiCall'\nimport { flash } from '@open-mercato/ui/backend/FlashMessages'\nimport { useQuery, useQueryClient } from '@tanstack/react-query'\nimport { useT } from '@open-mercato/shared/lib/i18n/context'\nimport type { FilterDef, FilterValues } from '@open-mercato/ui/backend/FilterBar'\n\ntype UserTaskStatus = 'PENDING' | 'IN_PROGRESS' | 'COMPLETED' | 'CANCELLED'\n\ntype UserTask = {\n id: string\n workflowInstanceId: string\n stepInstanceId: string\n taskName: string\n description: string | null\n status: UserTaskStatus\n formSchema: any | null\n formData: any | null\n assignedTo: string | null\n assignedToRoles: string[] | null\n claimedBy: string | null\n claimedAt: string | null\n dueDate: string | null\n escalatedAt: string | null\n escalatedTo: string | null\n completedBy: string | null\n completedAt: string | null\n comments: string | null\n tenantId: string\n organizationId: string\n createdAt: string\n updatedAt: string\n}\n\ntype TasksResponse = {\n data: UserTask[]\n pagination: {\n total: number\n limit: number\n offset: number\n hasMore: boolean\n }\n}\n\nexport default function UserTasksListPage() {\n const [page, setPage] = React.useState(1)\n const [pageSize] = React.useState(50)\n const [total, setTotal] = React.useState(0)\n const [totalPages, setTotalPages] = React.useState(1)\n const t = useT()\n const router = useRouter()\n const queryClient = useQueryClient()\n const [filterValues, setFilterValues] = React.useState<FilterValues>({\n myTasks: 'true', // Default to \"My Tasks\" view\n })\n\n const { data, isLoading, error } = useQuery({\n queryKey: ['workflow-tasks', 'list', filterValues, page],\n queryFn: async () => {\n const params = new URLSearchParams()\n const offset = (page - 1) * pageSize\n params.set('limit', pageSize.toString())\n params.set('offset', offset.toString())\n\n if (filterValues.status) params.set('status', filterValues.status as string)\n if (filterValues.myTasks === 'true') params.set('myTasks', 'true')\n if (filterValues.overdue === 'true') params.set('overdue', 'true')\n if (filterValues.workflowInstanceId) params.set('workflowInstanceId', filterValues.workflowInstanceId as string)\n\n const result = await apiCall<TasksResponse>(\n `/api/workflows/tasks?${params.toString()}`\n )\n\n if (!result.ok) {\n throw new Error('Failed to fetch user tasks')\n }\n\n const response = result.result\n if (response?.pagination) {\n setTotal(response.pagination.total || 0)\n const calculatedPages = Math.ceil((response.pagination.total || 0) / pageSize)\n setTotalPages(calculatedPages || 1)\n }\n\n return response?.data || []\n },\n })\n\n const handleClaim = async (id: string, taskName: string) => {\n if (!confirm(t('workflows.tasks.confirm.claim', { name: taskName }))) {\n return\n }\n\n const result = await apiCall(`/api/workflows/tasks/${id}/claim`, {\n method: 'POST',\n })\n\n if (result.ok) {\n flash(t('workflows.tasks.messages.claimed'), 'success')\n queryClient.invalidateQueries({ queryKey: ['workflow-tasks'] })\n } else {\n flash(t('workflows.tasks.messages.claimFailed'), 'error')\n }\n }\n\n const handleFiltersApply = React.useCallback((values: FilterValues) => {\n const next: FilterValues = {}\n Object.entries(values).forEach(([key, value]) => {\n if (value !== undefined && value !== '') next[key] = value\n })\n setFilterValues(next)\n setPage(1)\n }, [])\n\n const handleFiltersClear = React.useCallback(() => {\n setFilterValues({ myTasks: 'true' })\n setPage(1)\n }, [])\n\n const getStatusBadgeClass = (status: UserTaskStatus) => {\n switch (status) {\n case 'PENDING':\n return 'bg-yellow-100 text-yellow-800'\n case 'IN_PROGRESS':\n return 'bg-blue-100 text-blue-800'\n case 'COMPLETED':\n return 'bg-green-100 text-green-800'\n case 'CANCELLED':\n return 'bg-muted text-foreground'\n default:\n return 'bg-muted text-muted-foreground'\n }\n }\n\n const isOverdue = (task: UserTask) => {\n if (!task.dueDate || task.status === 'COMPLETED' || task.status === 'CANCELLED') {\n return false\n }\n return new Date(task.dueDate) < new Date()\n }\n\n const filters: FilterDef[] = [\n {\n id: 'status',\n type: 'select',\n label: t('workflows.tasks.filters.status'),\n options: [\n { label: t('common.all'), value: '' },\n { label: t('workflows.tasks.status.PENDING'), value: 'PENDING' },\n { label: t('workflows.tasks.status.IN_PROGRESS'), value: 'IN_PROGRESS' },\n { label: t('workflows.tasks.status.COMPLETED'), value: 'COMPLETED' },\n { label: t('workflows.tasks.status.CANCELLED'), value: 'CANCELLED' },\n ],\n },\n {\n id: 'myTasks',\n type: 'select',\n label: t('workflows.tasks.filters.view'),\n options: [\n { label: t('workflows.tasks.filters.myTasks'), value: 'true' },\n { label: t('workflows.tasks.filters.allTasks'), value: '' },\n ],\n },\n {\n id: 'overdue',\n type: 'select',\n label: t('workflows.tasks.filters.overdue'),\n options: [\n { label: t('common.all'), value: '' },\n { label: t('workflows.tasks.filters.overdueOnly'), value: 'true' },\n ],\n },\n {\n id: 'workflowInstanceId',\n type: 'text',\n label: t('workflows.tasks.filters.workflowInstanceId'),\n placeholder: t('workflows.tasks.filters.workflowInstanceIdPlaceholder'),\n },\n ]\n\n const columns: ColumnDef<UserTask>[] = [\n {\n id: 'taskName',\n header: t('workflows.tasks.fields.taskName'),\n accessorKey: 'taskName',\n cell: ({ row }) => (\n <div>\n <div className=\"font-medium text-sm\">{row.original.taskName}</div>\n {row.original.description && (\n <div className=\"text-xs text-muted-foreground line-clamp-1\">\n {row.original.description}\n </div>\n )}\n {isOverdue(row.original) && (\n <div className=\"text-xs text-red-600 font-medium mt-1\">\n {t('workflows.tasks.overdue')}\n </div>\n )}\n </div>\n ),\n },\n {\n id: 'status',\n header: t('workflows.tasks.fields.status'),\n accessorKey: 'status',\n cell: ({ row }) => (\n <span className={`inline-flex items-center px-2 py-1 rounded text-xs font-medium ${getStatusBadgeClass(row.original.status)}`}>\n {t(`workflows.tasks.status.${row.original.status}`)}\n </span>\n ),\n },\n {\n id: 'assignment',\n header: t('workflows.tasks.fields.assignment'),\n cell: ({ row }) => {\n if (row.original.claimedBy) {\n return (\n <div className=\"text-sm\">\n <div className=\"text-foreground\">{t('workflows.tasks.claimedBy')}: {row.original.claimedBy}</div>\n </div>\n )\n }\n if (row.original.assignedTo) {\n return <div className=\"text-sm text-foreground\">{row.original.assignedTo}</div>\n }\n if (row.original.assignedToRoles && row.original.assignedToRoles.length > 0) {\n return (\n <div className=\"text-sm text-muted-foreground\">\n {t('workflows.tasks.roles')}: {row.original.assignedToRoles.join(', ')}\n </div>\n )\n }\n return <span className=\"text-sm text-muted-foreground\">-</span>\n },\n },\n {\n id: 'dueDate',\n header: t('workflows.tasks.fields.dueDate'),\n accessorKey: 'dueDate',\n cell: ({ row }) => {\n if (!row.original.dueDate) {\n return <span className=\"text-sm text-muted-foreground\">-</span>\n }\n const dueDate = new Date(row.original.dueDate)\n const overdue = isOverdue(row.original)\n return (\n <div className={`text-sm ${overdue ? 'text-red-600 font-medium' : 'text-foreground'}`}>\n {dueDate.toLocaleString()}\n </div>\n )\n },\n },\n {\n id: 'createdAt',\n header: t('workflows.tasks.fields.createdAt'),\n accessorKey: 'createdAt',\n cell: ({ row }) => (\n <span className=\"text-sm text-muted-foreground\">\n {new Date(row.original.createdAt).toLocaleString()}\n </span>\n ),\n },\n {\n id: 'actions',\n header: '',\n cell: ({ row }) => {\n const items: Array<{ id: string; label: string; href?: string; onSelect?: () => void }> = [\n {\n id: 'view',\n label: t('workflows.tasks.actions.viewDetails'),\n href: `/backend/tasks/${row.original.id}`,\n },\n ]\n\n // Allow claiming if task is PENDING and assigned to roles (not specific user)\n if (\n row.original.status === 'PENDING' &&\n !row.original.assignedTo &&\n row.original.assignedToRoles &&\n row.original.assignedToRoles.length > 0\n ) {\n items.push({\n id: 'claim',\n label: t('workflows.tasks.actions.claim'),\n onSelect: () => handleClaim(row.original.id, row.original.taskName),\n })\n }\n\n // Allow completing if task is in progress or pending\n if (row.original.status === 'PENDING' || row.original.status === 'IN_PROGRESS') {\n items.push({\n id: 'complete',\n label: t('workflows.tasks.actions.complete'),\n href: `/backend/tasks/${row.original.id}`,\n })\n }\n\n return <RowActions items={items} />\n },\n },\n ]\n\n if (error) {\n return (\n <Page>\n <PageBody>\n <div className=\"p-8 text-center\">\n <p className=\"text-red-600\">{t('workflows.tasks.messages.loadFailed')}</p>\n <Button onClick={() => queryClient.invalidateQueries({ queryKey: ['workflow-tasks'] })} className=\"mt-4\">\n {t('common.retry')}\n </Button>\n </div>\n </PageBody>\n </Page>\n )\n }\n\n return (\n <Page>\n <PageBody>\n <DataTable\n title={t('workflows.tasks.list.title')}\n columns={columns}\n data={data || []}\n filters={filters}\n filterValues={filterValues}\n onFiltersApply={handleFiltersApply}\n onFiltersClear={handleFiltersClear}\n perspective={{\n tableId: 'workflows.tasks.list',\n }}\n pagination={{ page, pageSize, total, totalPages, onPageChange: setPage }}\n />\n </PageBody>\n </Page>\n )\n}\n"],
|
|
5
|
+
"mappings": "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",
|
|
6
6
|
"names": []
|
|
7
7
|
}
|