@taskforcehq/taskforce 0.3.327 → 0.3.329
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/Taskforce.module.css +257 -87
- package/dist/TaskforceCore.js +237 -230
- package/dist/annotatedAttachments/AnnotatedAttachmentSessionStore.js +1 -1
- package/dist/cli.js +34 -0
- package/dist/cliCloudTargetGuard.d.ts +5 -0
- package/dist/cliCloudTargetGuard.js +11 -0
- package/dist/components/activity/EntityActivityTimeline.js +15 -5
- package/dist/components/context/AttachmentPreviewHost.js +1 -1
- package/dist/components/context/ContextAttachmentManager.d.ts +3 -0
- package/dist/components/context/ContextAttachmentManager.js +116 -20
- package/dist/components/features/AnnotatedAttachmentWorkspace.js +24 -8
- package/dist/components/features/TaskSettings.d.ts +12 -1
- package/dist/components/features/TaskSettings.js +147 -40
- package/dist/components/features/agentCapabilities/AgentCapabilitiesPrototype.d.ts +1 -1
- package/dist/components/features/planning/PlanningEntitySummary.d.ts +3 -1
- package/dist/components/features/planning/PlanningEntitySummary.js +3 -2
- package/dist/components/features/planning/PlanningLinkPicker.d.ts +3 -1
- package/dist/components/features/planning/PlanningLinkPicker.js +5 -3
- package/dist/components/features/planning/PlanningModule.js +28 -14
- package/dist/components/features/planning/PlanningTaskOrderList.d.ts +1 -1
- package/dist/components/features/planning/PlanningTaskOrderList.js +17 -6
- package/dist/components/features/planning/PlanningVisualIdentity.d.ts +14 -0
- package/dist/components/features/planning/PlanningVisualIdentity.js +106 -0
- package/dist/components/features/planning/planningTaskArrangement.d.ts +1 -0
- package/dist/components/features/planning/planningTaskArrangement.js +5 -5
- package/dist/components/features/planning/planningWorkspaceModel.d.ts +11 -0
- package/dist/components/features/taskforceAgentEditorModel.js +3 -1
- package/dist/components/task/TaskActionHeader.d.ts +2 -1
- package/dist/components/task/TaskActionHeader.js +2 -2
- package/dist/components/task/TaskCard.d.ts +5 -0
- package/dist/components/task/TaskCard.js +101 -13
- package/dist/components/task/TaskContextUpload.d.ts +3 -0
- package/dist/components/task/TaskContextUpload.js +2 -2
- package/dist/components/task/TaskForm.d.ts +4 -0
- package/dist/components/task/TaskForm.js +32 -7
- package/dist/components/task/TaskImageReviews.js +28 -19
- package/dist/components/task/TaskKanban.d.ts +6 -1
- package/dist/components/task/TaskKanban.js +152 -6
- package/dist/components/task/TaskList.d.ts +5 -0
- package/dist/components/task/TaskList.js +3 -3
- package/dist/components/task/TaskStatusActions.js +11 -2
- package/dist/components/task/TaskWorkstreamPicker.js +2 -1
- package/dist/components/ui/DocumentTypeIcon.d.ts +7 -0
- package/dist/components/ui/DocumentTypeIcon.js +8 -0
- package/dist/components/ui/PasswordInput.d.ts +6 -0
- package/dist/components/ui/PasswordInput.js +11 -0
- package/dist/components/ui/TaxonomyDropdown.d.ts +9 -1
- package/dist/components/ui/TaxonomyDropdown.js +30 -3
- package/dist/components/ui/TopNoticeLayer.js +1 -1
- package/dist/components/views/AppShellHeader.js +32 -11
- package/dist/components/views/PlanComparisonPage.js +12 -0
- package/dist/components/views/StandaloneLayout.js +68 -39
- package/dist/components/views/WidgetView.js +10 -7
- package/dist/components/views/panels/PlanningDrawer.d.ts +7 -1
- package/dist/components/views/panels/PlanningDrawer.js +51 -54
- package/dist/components/views/standalone/modals/AccountSettingsModal.js +26 -17
- package/dist/config/envSchema.js +13 -0
- package/dist/config/localServiceCloudTarget.d.ts +10 -0
- package/dist/config/localServiceCloudTarget.js +76 -0
- package/dist/config/localServiceRuntimeContract.d.ts +13 -0
- package/dist/config/localServiceRuntimeContract.js +135 -0
- package/dist/core/AiProfileService.d.ts +1 -0
- package/dist/core/AiProfileService.js +48 -9
- package/dist/core/AttachmentLinkService.js +7 -4
- package/dist/core/DeletedTaskLifecycleService.d.ts +5 -0
- package/dist/core/DeletedTaskLifecycleService.js +55 -3
- package/dist/core/McpTokenService.d.ts +4 -0
- package/dist/core/McpTokenService.js +52 -0
- package/dist/core/TaskAttachmentLinksDurableMutationService.d.ts +8 -2
- package/dist/core/TaskAttachmentLinksDurableMutationService.js +51 -18
- package/dist/core/Taskforce.d.ts +124 -2
- package/dist/core/Taskforce.js +1175 -87
- package/dist/core/types.d.ts +8 -1
- package/dist/documentReviews/DocumentReviewCommentStore.d.ts +11 -0
- package/dist/documentReviews/DocumentReviewCommentStore.js +35 -2
- package/dist/documentReviews/service.d.ts +4 -0
- package/dist/documentReviews/service.js +141 -46
- package/dist/hooks/sync/useDurableLocalOutboxDrain.d.ts +1 -1
- package/dist/hooks/sync/useDurableTaskCreateMutation.js +1 -1
- package/dist/hooks/sync/useDurableTaskMetadataMutation.d.ts +1 -0
- package/dist/hooks/sync/useDurableTaskMetadataMutation.js +1 -0
- package/dist/hooks/sync/useDurableTaskStatusMutation.d.ts +1 -0
- package/dist/hooks/tasks/taskHttpMutation.js +1 -0
- package/dist/hooks/tasks/useCloudTaskSearch.d.ts +12 -0
- package/dist/hooks/tasks/useCloudTaskSearch.js +71 -0
- package/dist/hooks/tasks/useTaskDescriptionImageDraftRecovery.d.ts +16 -0
- package/dist/hooks/tasks/useTaskDescriptionImageDraftRecovery.js +197 -0
- package/dist/hooks/tasks/useTaskEditorNavigation.d.ts +16 -3
- package/dist/hooks/tasks/useTaskEditorNavigation.js +72 -13
- package/dist/hooks/tasks/useTaskFormActions.d.ts +9 -0
- package/dist/hooks/tasks/useTaskFormActions.js +96 -17
- package/dist/hooks/ui/useSettingsModel.d.ts +24 -2
- package/dist/hooks/ui/useSettingsModel.js +13 -2
- package/dist/hooks/ui/useSettingsPersistence.d.ts +12 -1
- package/dist/hooks/ui/useSettingsPersistence.js +74 -47
- package/dist/hooks/useFilterSort.d.ts +7 -3
- package/dist/hooks/useFilterSort.js +15 -5
- package/dist/hooks/useTaskData.d.ts +10 -1
- package/dist/hooks/useTaskData.js +216 -7
- package/dist/hooks/useTaskMutations.d.ts +10 -2
- package/dist/hooks/useTaskMutations.js +223 -43
- package/dist/hooks/useTaskforce.d.ts +94 -57
- package/dist/hooks/useTaskforce.js +428 -16
- package/dist/hooks/useUiNotice.d.ts +4 -0
- package/dist/hooks/useUiNotice.js +4 -0
- package/dist/mcp/adminWorkspaceRegistrar.js +3 -3
- package/dist/mcp/canonicalAssetHelpers.d.ts +13 -0
- package/dist/mcp/canonicalAssetHelpers.js +39 -5
- package/dist/mcp/collaborationRegistrar.js +15 -13
- package/dist/mcp/documentAssetRegistrar.js +60 -44
- package/dist/mcp/documentHelpers.d.ts +1 -0
- package/dist/mcp/documentHelpers.js +7 -3
- package/dist/mcp/localServiceProxy.js +4 -1
- package/dist/mcp/runtime.d.ts +16 -0
- package/dist/mcp/runtime.js +735 -210
- package/dist/mcp/taskAttachmentCommandAdapter.d.ts +2 -0
- package/dist/mcp/taskAttachmentCommandAdapter.js +14 -8
- package/dist/mcp/taskPlanningRegistrar.js +78 -67
- package/dist/mcp/toolCallCompatibility.js +38 -1
- package/dist/mcp/toolCatalog.d.ts +1 -0
- package/dist/mcp/toolRegistry.js +2 -2
- package/dist/migrations/taskSchemaMigrations.js +47 -0
- package/dist/runtime/appGateDefinitions.d.ts +30 -6
- package/dist/runtime/appGateDefinitions.js +6 -6
- package/dist/runtime/appGates.d.ts +12 -13
- package/dist/runtime/appGates.js +29 -13
- package/dist/runtime/nodeAppGates.d.ts +8 -0
- package/dist/runtime/nodeAppGates.js +27 -0
- package/dist/server/appAccess.d.ts +12 -0
- package/dist/server/appAccess.js +21 -0
- package/dist/server/authorizedWorkspaceAccess.d.ts +12 -0
- package/dist/server/authorizedWorkspaceAccess.js +40 -0
- package/dist/server/cloudCollectionRead.d.ts +25 -0
- package/dist/server/cloudCollectionRead.js +120 -0
- package/dist/server/cloudCollectionReadPool.d.ts +52 -0
- package/dist/server/cloudCollectionReadPool.js +140 -0
- package/dist/server/cloudCollectionReadWorker.d.ts +1 -0
- package/dist/server/cloudCollectionReadWorker.js +36 -0
- package/dist/server/index.d.ts +6 -11
- package/dist/server/index.js +67 -42
- package/dist/server/localServiceLease.d.ts +6 -0
- package/dist/server/localServiceLease.js +17 -1
- package/dist/server/localWorkspaceSyncServerRuntime.js +10 -3
- package/dist/server/rateLimit.d.ts +1 -0
- package/dist/server/rateLimit.js +4 -0
- package/dist/server/realtimeSyncWs.js +36 -12
- package/dist/server/routes/admin.js +1 -0
- package/dist/server/routes/agentRoles.js +3 -2
- package/dist/server/routes/agentSkills.js +3 -2
- package/dist/server/routes/agents.js +118 -16
- package/dist/server/routes/annotatedAttachments.js +3 -2
- package/dist/server/routes/auth.js +3 -1
- package/dist/server/routes/documents.d.ts +5 -2
- package/dist/server/routes/documents.js +160 -13
- package/dist/server/routes/durableTaskHttpRouters.d.ts +11 -2
- package/dist/server/routes/durableTaskHttpRouters.js +2 -2
- package/dist/server/routes/localService.js +4 -0
- package/dist/server/routes/primitives.d.ts +4 -0
- package/dist/server/routes/shared.d.ts +24 -0
- package/dist/server/routes/shared.js +114 -18
- package/dist/server/routes/sync.js +22 -0
- package/dist/server/routes/syncAuxRoutes.js +5 -2
- package/dist/server/routes/syncPullApplyRoutes.js +23 -4
- package/dist/server/routes/syncV3FeedRoutes.js +22 -18
- package/dist/server/routes/syncV3LocalCaptureRoutes.js +48 -4
- package/dist/server/routes/syncV3LocalFeedApplyRoutes.d.ts +1 -0
- package/dist/server/routes/syncV3LocalFeedApplyRoutes.js +26 -0
- package/dist/server/routes/syncV3OperationRoutes.js +27 -2
- package/dist/server/routes/tasks.js +299 -97
- package/dist/server/routes/workspaces.js +43 -1
- package/dist/server/routes.js +35 -7
- package/dist/server/workspaceDeletionAdmission.d.ts +23 -0
- package/dist/server/workspaceDeletionAdmission.js +50 -0
- package/dist/service/localServiceCli.js +52 -25
- package/dist/service/localServiceClientLifecycle.js +93 -6
- package/dist/services/codexAppServerModelGateway.d.ts +112 -0
- package/dist/services/codexAppServerModelGateway.js +438 -0
- package/dist/services/taskforceAgentMcpBridge.d.ts +7 -1
- package/dist/services/taskforceAgentMcpBridge.js +23 -3
- package/dist/shared/planningIdentity.d.ts +20 -0
- package/dist/shared/planningIdentity.js +79 -0
- package/dist/shared/taskforceAgentDefinition.js +7 -1
- package/dist/shared/taskforceAgentModels.d.ts +1 -0
- package/dist/shared/taskforceAgentModels.js +30 -1
- package/dist/storage/postgresAdapter.d.ts +20 -3
- package/dist/storage/postgresAdapter.js +110 -14
- package/dist/storage/postgresRequestDiagnostics.d.ts +8 -0
- package/dist/storage/postgresRequestDiagnostics.js +24 -0
- package/dist/storage/postgresWorker.js +13 -4
- package/dist/storage/postgresWorkerProtocol.d.ts +29 -0
- package/dist/storage/postgresWorkerProtocol.js +30 -0
- package/dist/storage/workspaceAssetStore.d.ts +32 -0
- package/dist/storage/workspaceAssetStore.js +70 -0
- package/dist/sync/cloudSyncApi.d.ts +4 -1
- package/dist/sync/cloudSyncApi.js +7 -2
- package/dist/sync/contentSyncState.d.ts +1 -1
- package/dist/sync/coordinator/localSyncExecutionPermitStore.d.ts +17 -0
- package/dist/sync/coordinator/localSyncExecutionPermitStore.js +77 -23
- package/dist/sync/coordinator/localWorkspaceSyncRunner.js +6 -2
- package/dist/sync/coordinator/workspaceSyncTransportGateway.js +4 -2
- package/dist/sync/engine/workspaceSyncEngineBrowserGatewayRemoteServices.js +20 -2
- package/dist/sync/engine/workspaceSyncEngineLocalServices.d.ts +4 -0
- package/dist/sync/engine/workspaceSyncEngineLocalServices.js +11 -0
- package/dist/sync/engine/workspaceSyncEngineRemoteServices.d.ts +16 -0
- package/dist/sync/engine/workspaceSyncEngineRemoteServices.js +2 -1
- package/dist/sync/engine/workspaceSyncEngineServerRemoteServices.d.ts +1 -1
- package/dist/sync/engine/workspaceSyncEngineServerRemoteServices.js +46 -4
- package/dist/sync/engine/workspaceSyncEngineServerRunnerOperations.d.ts +3 -1
- package/dist/sync/engine/workspaceSyncEngineServerRunnerOperations.js +51 -11
- package/dist/sync/engine/workspaceSyncEngineTransfers.d.ts +1 -1
- package/dist/sync/engine/workspaceSyncEngineTransfers.js +8 -3
- package/dist/sync/engine/workspaceSyncV2ChangeDispatcher.js +2 -0
- package/dist/sync/syncApplyHandlers.d.ts +3 -1
- package/dist/sync/syncApplyHandlers.js +29 -0
- package/dist/sync/syncService.d.ts +2 -0
- package/dist/sync/syncService.js +13 -1
- package/dist/sync/taskSyncPayload.d.ts +1 -0
- package/dist/sync/taskSyncPayload.js +6 -0
- package/dist/sync/v3/combinedFeedCapability.js +4 -0
- package/dist/sync/v3/durableTaskAttachmentLinksMutationRouter.d.ts +3 -0
- package/dist/sync/v3/durableTaskAttachmentLinksMutationRouter.js +31 -3
- package/dist/sync/v3/durableTaskChecklistMutationRouter.d.ts +2 -0
- package/dist/sync/v3/durableTaskChecklistMutationRouter.js +4 -0
- package/dist/sync/v3/durableTaskHttpBulkMutationRouter.d.ts +1 -0
- package/dist/sync/v3/durableTaskHttpBulkMutationRouter.js +47 -12
- package/dist/sync/v3/durableTaskHttpRootMutationRouter.d.ts +5 -3
- package/dist/sync/v3/durableTaskHttpRootMutationRouter.js +27 -2
- package/dist/sync/v3/localInitiativeOutboxService.js +4 -2
- package/dist/sync/v3/localOutboxDispatcher.js +5 -1
- package/dist/sync/v3/localTaskAttachmentLinksOutboxHandler.js +12 -2
- package/dist/sync/v3/localTaskAttachmentLinksOutboxService.d.ts +3 -0
- package/dist/sync/v3/localTaskAttachmentLinksOutboxService.js +62 -10
- package/dist/sync/v3/localTaskCreateOutboxService.js +15 -6
- package/dist/sync/v3/localTaskMetadataClient.d.ts +1 -0
- package/dist/sync/v3/localTaskMetadataClient.js +1 -0
- package/dist/sync/v3/localTaskMetadataOutboxHandler.js +5 -1
- package/dist/sync/v3/localTaskMetadataOutboxService.d.ts +2 -0
- package/dist/sync/v3/localTaskMetadataOutboxService.js +7 -0
- package/dist/sync/v3/localTaskRestoreOutboxService.js +14 -6
- package/dist/sync/v3/localTaskStatusClient.d.ts +1 -0
- package/dist/sync/v3/localTaskStatusClient.js +6 -1
- package/dist/sync/v3/localTaskStatusOutboxService.d.ts +2 -0
- package/dist/sync/v3/localTaskStatusOutboxService.js +54 -13
- package/dist/sync/v3/localWorkstreamOutboxService.js +4 -2
- package/dist/sync/v3/syncDurabilityStore.d.ts +15 -0
- package/dist/sync/v3/syncDurabilityStore.js +201 -43
- package/dist/sync/v3/taskAttachmentLinksMutationService.d.ts +7 -4
- package/dist/sync/v3/taskAttachmentLinksMutationService.js +37 -12
- package/dist/sync/v3/taskChecklistMutationService.d.ts +4 -2
- package/dist/sync/v3/taskChecklistMutationService.js +4 -0
- package/dist/sync/v3/taskCreateMutationService.d.ts +2 -2
- package/dist/sync/v3/taskCreateMutationService.js +7 -4
- package/dist/sync/v3/taskMetadataCoexistence.js +4 -0
- package/dist/sync/v3/taskMetadataMutationService.d.ts +3 -0
- package/dist/sync/v3/taskMetadataMutationService.js +4 -0
- package/dist/sync/v3/taskRestoreMutationService.d.ts +2 -2
- package/dist/sync/v3/taskRestoreMutationService.js +7 -4
- package/dist/sync/v3/taskStatusMutationService.d.ts +2 -0
- package/dist/sync/v3/taskStatusMutationService.js +4 -0
- package/dist/sync/v3/workflowAssignmentSync.d.ts +1 -0
- package/dist/sync/v3/workflowAssignmentSync.js +3 -0
- package/dist/sync/v3/workspaceSyncV2ProjectionExclusions.d.ts +1 -1
- package/dist/sync/v3/workspaceSyncV2ProjectionExclusions.js +14 -12
- package/dist/sync/v3/workspaceSyncV3AttachmentApplyObligationStore.d.ts +11 -0
- package/dist/sync/v3/workspaceSyncV3AttachmentApplyObligationStore.js +27 -10
- package/dist/sync/v3/workspaceSyncV3AttachmentAssetHydration.d.ts +2 -1
- package/dist/sync/v3/workspaceSyncV3AttachmentAssetHydration.js +52 -10
- package/dist/sync/v3/workspaceSyncV3CloudOperationHandler.js +10 -1
- package/dist/sync/v3/workspaceSyncV3CombinedFeedOrchestrator.js +15 -4
- package/dist/sync/v3/workspaceSyncV3CombinedLocalApply.js +66 -13
- package/dist/sync/v3/workspaceSyncV3CombinedRepairBaseline.d.ts +11 -0
- package/dist/sync/v3/workspaceSyncV3CombinedRepairBaseline.js +57 -22
- package/dist/sync/v3/workspaceSyncV3CombinedRepairMaterialization.d.ts +10 -4
- package/dist/sync/v3/workspaceSyncV3CombinedRepairMaterialization.js +124 -51
- package/dist/sync/v3/workspaceSyncV3CombinedRepairSnapshot.d.ts +10 -0
- package/dist/sync/v3/workspaceSyncV3CombinedRepairSnapshot.js +120 -28
- package/dist/sync/v3/workspaceSyncV3CombinedWireContract.d.ts +3 -1
- package/dist/sync/v3/workspaceSyncV3CombinedWireContract.js +18 -0
- package/dist/sync/v3/workspaceSyncV3CoverageRegistry.js +6 -0
- package/dist/sync/v3/workspaceSyncV3FeedProfile.d.ts +1 -1
- package/dist/sync/v3/workspaceSyncV3LegacyBoundaryAttestation.d.ts +1 -0
- package/dist/sync/v3/workspaceSyncV3LegacyBoundaryAttestation.js +23 -10
- package/dist/sync/v3/workspaceSyncV3NestedTaskApply.d.ts +3 -0
- package/dist/sync/v3/workspaceSyncV3NestedTaskApply.js +64 -13
- package/dist/sync/v3/workspaceSyncV3NestedTaskCodecs.d.ts +9 -0
- package/dist/sync/v3/workspaceSyncV3NestedTaskCodecs.js +26 -0
- package/dist/sync/v3/workspaceSyncV3NestedTaskProjection.d.ts +15 -5
- package/dist/sync/v3/workspaceSyncV3NestedTaskProjection.js +50 -14
- package/dist/sync/v3/workspaceSyncV3NestedTaskRepairSnapshot.d.ts +2 -1
- package/dist/sync/v3/workspaceSyncV3NestedTaskRepairSnapshot.js +11 -3
- package/dist/sync/v3/workspaceSyncV3OperationProtocol.d.ts +3 -0
- package/dist/sync/v3/workspaceSyncV3OperatorDiagnostics.d.ts +2 -0
- package/dist/sync/v3/workspaceSyncV3OperatorDiagnostics.js +19 -7
- package/dist/sync/v3/workspaceSyncV3RepairSqlBatching.d.ts +2 -0
- package/dist/sync/v3/workspaceSyncV3RepairSqlBatching.js +10 -0
- package/dist/sync/v3/workspaceSyncV3TaskCommentAudit.js +9 -2
- package/dist/sync/v3/workspaceSyncV3TaskCoverCoverage.d.ts +7 -0
- package/dist/sync/v3/workspaceSyncV3TaskCoverCoverage.js +37 -0
- package/dist/sync/v3/workspaceSyncV3TaskCoverWireContract.d.ts +6 -0
- package/dist/sync/v3/workspaceSyncV3TaskCoverWireContract.js +9 -0
- package/dist/sync/v3/workspaceSyncV3TaskRootProjection.d.ts +1 -1
- package/dist/sync/v3/workspaceSyncV3TaskRootProjection.js +1 -1
- package/dist/sync/workspacePullFeed.d.ts +6 -1
- package/dist/sync/workspacePullFeed.js +174 -162
- package/dist/sync/workspaceRepair.d.ts +3 -0
- package/dist/sync/workspaceRepair.js +67 -6
- package/dist/sync/workspaceSyncModel.d.ts +11 -0
- package/dist/sync/workspaceSyncModel.js +27 -2
- package/dist/types.d.ts +55 -1
- package/dist/types.js +6 -0
- package/dist/ui/assets/{AiIdentityRosterCard-DB1BLO_j.js → AiIdentityRosterCard-BZM4aQnM.js} +1 -1
- package/dist/ui/assets/AiProfilesModule-BbAEWtHH.js +1 -0
- package/dist/ui/assets/AnnotatedAttachmentWorkspace-B68Wg-RV.js +3 -0
- package/dist/ui/assets/AnnotatedAttachmentWorkspace-TzYu7pkG.css +1 -0
- package/dist/ui/assets/AssetTraySortControl-C8Rztyal.js +1 -0
- package/dist/ui/assets/ContextAttachmentManager-Cj3c7X9y.js +3 -0
- package/dist/ui/assets/{DocumentWorkspace-BC7sy5TG.js → DocumentWorkspace-B5uvzems.js} +4 -4
- package/dist/ui/assets/EntityActivityTimeline-BVFvCB5R.js +1 -0
- package/dist/ui/assets/PlanningModule-B5DWQOGz.js +1 -0
- package/dist/ui/assets/PlanningModule-CoIR9hbV.css +1 -0
- package/dist/ui/assets/PlansPage-AY4cGWco.js +1 -0
- package/dist/ui/assets/TaskContextUpload-DZxTVesW.js +1 -0
- package/dist/ui/assets/TaskContextUpload-qmBeUw3u.css +1 -0
- package/dist/ui/assets/TaskSettings-BeWAuyZj.js +12 -0
- package/dist/ui/assets/{TaskforceAgentsModule-CkAxW19K.js → TaskforceAgentsModule-BifCYtjR.js} +6 -6
- package/dist/ui/assets/WorkflowManagerModule-DEr5di_r.js +1 -0
- package/dist/ui/assets/index-I5zhdtgt.js +7 -0
- package/dist/ui/assets/index-VRFsx3wz.css +1 -0
- package/dist/ui/assets/{vendor-icons-B8ZNsH1g.js → vendor-icons-D9Lpw-j4.js} +1 -1
- package/dist/ui/index.html +3 -3
- package/dist/utils/constants.d.ts +2 -2
- package/dist/utils/constants.js +1 -1
- package/dist/utils/contextAttachmentUpload.d.ts +2 -0
- package/dist/utils/contextAttachmentUpload.js +7 -0
- package/dist/utils/contextFiles.d.ts +1 -1
- package/dist/utils/contextFiles.js +4 -4
- package/dist/utils/taskActivity.d.ts +3 -2
- package/dist/utils/taskActivity.js +19 -2
- package/dist/utils/taskEditorReconciliation.d.ts +40 -0
- package/dist/utils/taskEditorReconciliation.js +217 -0
- package/dist/utils/taskNormalization.d.ts +1 -0
- package/dist/utils/taskNormalization.js +39 -0
- package/dist/utils/taskSearch.js +2 -2
- package/dist/utils/uiNotice.d.ts +4 -0
- package/package.json +21 -4
- package/dist/ui/assets/AiProfilesModule-DPxQeF9N.js +0 -1
- package/dist/ui/assets/AnnotatedAttachmentWorkspace-CBRZ8rca.css +0 -1
- package/dist/ui/assets/AnnotatedAttachmentWorkspace-DHNYaNg6.js +0 -3
- package/dist/ui/assets/AssetTraySortControl-DphbyHVc.js +0 -1
- package/dist/ui/assets/ContextAttachmentManager-CMxSzHqc.js +0 -3
- package/dist/ui/assets/EntityActivityTimeline-pJ2ZjZ-k.js +0 -1
- package/dist/ui/assets/PlanningModule-CeTqXMMz.css +0 -1
- package/dist/ui/assets/PlanningModule-t5GbvVR9.js +0 -1
- package/dist/ui/assets/PlansPage-BVH_NfgT.js +0 -1
- package/dist/ui/assets/TaskContextUpload-Ds4LnDzV.css +0 -1
- package/dist/ui/assets/TaskContextUpload-bl4fOOUz.js +0 -1
- package/dist/ui/assets/TaskSettings-xVsxSa0g.js +0 -12
- package/dist/ui/assets/WorkflowManagerModule-BKqIGVnF.js +0 -1
- package/dist/ui/assets/index-BzJlVnNS.css +0 -1
- package/dist/ui/assets/index-Cx7vZJHL.js +0 -7
|
@@ -1160,6 +1160,22 @@ export function ensureWorkspaceAssetsSchema(db) {
|
|
|
1160
1160
|
ON workspace_asset_links(tenant_id, workspace_id, asset_id, deleted_at, updated_at);
|
|
1161
1161
|
CREATE INDEX IF NOT EXISTS idx_workspace_asset_links_workspace_updated
|
|
1162
1162
|
ON workspace_asset_links(tenant_id, workspace_id, updated_at, asset_id);
|
|
1163
|
+
|
|
1164
|
+
CREATE TABLE IF NOT EXISTS workspace_asset_upload_drafts (
|
|
1165
|
+
tenant_id TEXT NOT NULL DEFAULT 'default',
|
|
1166
|
+
workspace_id TEXT NOT NULL,
|
|
1167
|
+
draft_id TEXT NOT NULL,
|
|
1168
|
+
asset_id TEXT NOT NULL,
|
|
1169
|
+
storage_key TEXT NOT NULL,
|
|
1170
|
+
purpose TEXT NOT NULL,
|
|
1171
|
+
created_by_user_id TEXT NOT NULL,
|
|
1172
|
+
created_at TEXT NOT NULL,
|
|
1173
|
+
retired_at TEXT,
|
|
1174
|
+
PRIMARY KEY (tenant_id, workspace_id, draft_id, asset_id)
|
|
1175
|
+
);
|
|
1176
|
+
|
|
1177
|
+
CREATE INDEX IF NOT EXISTS idx_workspace_asset_upload_drafts_expiry
|
|
1178
|
+
ON workspace_asset_upload_drafts(tenant_id, workspace_id, retired_at, created_at);
|
|
1163
1179
|
`);
|
|
1164
1180
|
const linkColumns = db.prepare(`PRAGMA table_info(workspace_asset_links)`).all();
|
|
1165
1181
|
const hasDisplayNameColumn = linkColumns.some((c) => c.name === 'display_name');
|
|
@@ -1407,6 +1423,7 @@ export function buildWorkspaceSyncDurabilitySchemaSql(provider) {
|
|
|
1407
1423
|
base_lifecycle_revision ${revisionType} NOT NULL DEFAULT 0,
|
|
1408
1424
|
payload_json TEXT NOT NULL,
|
|
1409
1425
|
payload_fingerprint TEXT NOT NULL,
|
|
1426
|
+
canonical_intent_json TEXT,
|
|
1410
1427
|
status TEXT NOT NULL DEFAULT 'pending',
|
|
1411
1428
|
attempt_count INTEGER NOT NULL DEFAULT 0,
|
|
1412
1429
|
initial_not_found_attempt_count INTEGER NOT NULL DEFAULT 0,
|
|
@@ -1811,6 +1828,9 @@ export function ensureWorkspaceSyncDurabilitySchema(db) {
|
|
|
1811
1828
|
if (!outboxColumns.some((column) => column.name === 'initial_not_found_attempt_count')) {
|
|
1812
1829
|
db.exec(`ALTER TABLE workspace_sync_outbox ADD COLUMN initial_not_found_attempt_count INTEGER NOT NULL DEFAULT 0`);
|
|
1813
1830
|
}
|
|
1831
|
+
if (!outboxColumns.some((column) => column.name === 'canonical_intent_json')) {
|
|
1832
|
+
db.exec(`ALTER TABLE workspace_sync_outbox ADD COLUMN canonical_intent_json TEXT`);
|
|
1833
|
+
}
|
|
1814
1834
|
if (!outboxColumns.some((column) => column.name === 'owns_task_metadata')) {
|
|
1815
1835
|
db.exec(`ALTER TABLE workspace_sync_outbox ADD COLUMN owns_task_metadata INTEGER NOT NULL DEFAULT 0`);
|
|
1816
1836
|
}
|
|
@@ -2113,6 +2133,8 @@ export function ensureLocalSyncCoordinatorSchema(db) {
|
|
|
2113
2133
|
created_at TEXT NOT NULL,
|
|
2114
2134
|
updated_at TEXT NOT NULL,
|
|
2115
2135
|
next_attempt_at TEXT NOT NULL,
|
|
2136
|
+
terminal_at TEXT,
|
|
2137
|
+
terminal_reason TEXT,
|
|
2116
2138
|
resolved_at TEXT,
|
|
2117
2139
|
PRIMARY KEY (tenant_id, workspace_id, task_id)
|
|
2118
2140
|
);
|
|
@@ -2156,6 +2178,12 @@ export function ensureLocalSyncCoordinatorSchema(db) {
|
|
|
2156
2178
|
if (!attachmentApplyColumns.has('revision_fingerprint')) {
|
|
2157
2179
|
db.exec(`ALTER TABLE workspace_sync_v3_attachment_apply_obligations ADD COLUMN revision_fingerprint TEXT`);
|
|
2158
2180
|
}
|
|
2181
|
+
if (!attachmentApplyColumns.has('terminal_at')) {
|
|
2182
|
+
db.exec(`ALTER TABLE workspace_sync_v3_attachment_apply_obligations ADD COLUMN terminal_at TEXT`);
|
|
2183
|
+
}
|
|
2184
|
+
if (!attachmentApplyColumns.has('terminal_reason')) {
|
|
2185
|
+
db.exec(`ALTER TABLE workspace_sync_v3_attachment_apply_obligations ADD COLUMN terminal_reason TEXT`);
|
|
2186
|
+
}
|
|
2159
2187
|
const coordinatorStateColumns = db.provider === 'postgres'
|
|
2160
2188
|
? new Set(db.prepare(`
|
|
2161
2189
|
SELECT column_name AS name
|
|
@@ -2801,6 +2829,9 @@ export function ensureDocumentReviewSessionsSchema(db) {
|
|
|
2801
2829
|
thread_status_updated_at TEXT,
|
|
2802
2830
|
resolved_at TEXT,
|
|
2803
2831
|
resolved_by_actor_id TEXT,
|
|
2832
|
+
idempotency_key TEXT,
|
|
2833
|
+
idempotency_fingerprint TEXT,
|
|
2834
|
+
idempotency_actor_scope TEXT NOT NULL DEFAULT '',
|
|
2804
2835
|
order_index INTEGER NOT NULL DEFAULT 0,
|
|
2805
2836
|
created_at TEXT NOT NULL,
|
|
2806
2837
|
updated_at TEXT NOT NULL,
|
|
@@ -2830,6 +2861,22 @@ export function ensureDocumentReviewSessionsSchema(db) {
|
|
|
2830
2861
|
if (!commentColumnNames.has('deleted_by_actor_id')) {
|
|
2831
2862
|
addCommentColumn('deleted_by_actor_id');
|
|
2832
2863
|
}
|
|
2864
|
+
if (!commentColumnNames.has('idempotency_key')) {
|
|
2865
|
+
addCommentColumn('idempotency_key');
|
|
2866
|
+
}
|
|
2867
|
+
if (!commentColumnNames.has('idempotency_fingerprint')) {
|
|
2868
|
+
addCommentColumn('idempotency_fingerprint');
|
|
2869
|
+
}
|
|
2870
|
+
if (!commentColumnNames.has('idempotency_actor_scope')) {
|
|
2871
|
+
const ifNotExists = db.provider === 'postgres' ? ' IF NOT EXISTS' : '';
|
|
2872
|
+
db.exec(`ALTER TABLE document_review_comments ADD COLUMN${ifNotExists} idempotency_actor_scope TEXT NOT NULL DEFAULT ''`);
|
|
2873
|
+
}
|
|
2874
|
+
db.exec(`
|
|
2875
|
+
CREATE UNIQUE INDEX IF NOT EXISTS idx_document_review_comments_idempotency
|
|
2876
|
+
ON document_review_comments (
|
|
2877
|
+
tenant_id, workspace_id, idempotency_actor_scope, idempotency_key
|
|
2878
|
+
)
|
|
2879
|
+
`);
|
|
2833
2880
|
if (!commentColumnNames.has('parent_comment_id')) {
|
|
2834
2881
|
addCommentColumn('parent_comment_id');
|
|
2835
2882
|
}
|
|
@@ -1,36 +1,60 @@
|
|
|
1
1
|
export declare const APP_GATE_DEFINITIONS: {
|
|
2
2
|
readonly 'annotated_attachments.workspace_access': {
|
|
3
|
-
readonly
|
|
3
|
+
readonly enabledByEnvironment: {
|
|
4
|
+
readonly performance: true;
|
|
5
|
+
readonly staging: true;
|
|
6
|
+
readonly production: true;
|
|
7
|
+
};
|
|
4
8
|
readonly description: "Annotated Attachment workspace readiness gate.";
|
|
5
9
|
readonly owner: "taskforce";
|
|
6
10
|
readonly removalMilestone: "Annotated Attachment GA";
|
|
7
11
|
};
|
|
8
12
|
readonly 'documents.workspace_access': {
|
|
9
|
-
readonly
|
|
13
|
+
readonly enabledByEnvironment: {
|
|
14
|
+
readonly performance: true;
|
|
15
|
+
readonly staging: true;
|
|
16
|
+
readonly production: true;
|
|
17
|
+
};
|
|
10
18
|
readonly description: "Document Manager/editor workspace readiness gate.";
|
|
11
19
|
readonly owner: "taskforce";
|
|
12
20
|
readonly removalMilestone: "Document Manager GA";
|
|
13
21
|
};
|
|
14
22
|
readonly 'workflow_manager.workspace_access': {
|
|
15
|
-
readonly
|
|
23
|
+
readonly enabledByEnvironment: {
|
|
24
|
+
readonly performance: true;
|
|
25
|
+
readonly staging: true;
|
|
26
|
+
readonly production: false;
|
|
27
|
+
};
|
|
16
28
|
readonly description: "Workflow Manager workspace readiness gate.";
|
|
17
29
|
readonly owner: "taskforce";
|
|
18
30
|
readonly removalMilestone: "Workflow Manager GA";
|
|
19
31
|
};
|
|
20
32
|
readonly 'taskforce_agents.workspace_access': {
|
|
21
|
-
readonly
|
|
33
|
+
readonly enabledByEnvironment: {
|
|
34
|
+
readonly performance: true;
|
|
35
|
+
readonly staging: true;
|
|
36
|
+
readonly production: false;
|
|
37
|
+
};
|
|
22
38
|
readonly description: "Taskforce Agents workspace readiness gate.";
|
|
23
39
|
readonly owner: "taskforce";
|
|
24
40
|
readonly removalMilestone: "Taskforce Agents workspace GA";
|
|
25
41
|
};
|
|
26
42
|
readonly 'ai_profiles.workspace_access': {
|
|
27
|
-
readonly
|
|
43
|
+
readonly enabledByEnvironment: {
|
|
44
|
+
readonly performance: true;
|
|
45
|
+
readonly staging: true;
|
|
46
|
+
readonly production: true;
|
|
47
|
+
};
|
|
28
48
|
readonly description: "AI Profiles workspace readiness gate.";
|
|
29
49
|
readonly owner: "taskforce";
|
|
30
50
|
readonly removalMilestone: "AI Profiles workspace GA";
|
|
31
51
|
};
|
|
32
52
|
readonly 'planning.workspace_access': {
|
|
33
|
-
readonly
|
|
53
|
+
readonly enabledByEnvironment: {
|
|
54
|
+
readonly performance: false;
|
|
55
|
+
readonly staging: false;
|
|
56
|
+
readonly production: false;
|
|
57
|
+
};
|
|
34
58
|
readonly description: "Planning workspace readiness gate.";
|
|
35
59
|
readonly owner: "taskforce";
|
|
36
60
|
readonly removalMilestone: "Planning workspace GA";
|
|
@@ -1,36 +1,36 @@
|
|
|
1
1
|
export const APP_GATE_DEFINITIONS = {
|
|
2
2
|
'annotated_attachments.workspace_access': {
|
|
3
|
-
|
|
3
|
+
enabledByEnvironment: { performance: true, staging: true, production: true },
|
|
4
4
|
description: 'Annotated Attachment workspace readiness gate.',
|
|
5
5
|
owner: 'taskforce',
|
|
6
6
|
removalMilestone: 'Annotated Attachment GA'
|
|
7
7
|
},
|
|
8
8
|
'documents.workspace_access': {
|
|
9
|
-
|
|
9
|
+
enabledByEnvironment: { performance: true, staging: true, production: true },
|
|
10
10
|
description: 'Document Manager/editor workspace readiness gate.',
|
|
11
11
|
owner: 'taskforce',
|
|
12
12
|
removalMilestone: 'Document Manager GA'
|
|
13
13
|
},
|
|
14
14
|
'workflow_manager.workspace_access': {
|
|
15
|
-
|
|
15
|
+
enabledByEnvironment: { performance: true, staging: true, production: false },
|
|
16
16
|
description: 'Workflow Manager workspace readiness gate.',
|
|
17
17
|
owner: 'taskforce',
|
|
18
18
|
removalMilestone: 'Workflow Manager GA'
|
|
19
19
|
},
|
|
20
20
|
'taskforce_agents.workspace_access': {
|
|
21
|
-
|
|
21
|
+
enabledByEnvironment: { performance: true, staging: true, production: false },
|
|
22
22
|
description: 'Taskforce Agents workspace readiness gate.',
|
|
23
23
|
owner: 'taskforce',
|
|
24
24
|
removalMilestone: 'Taskforce Agents workspace GA'
|
|
25
25
|
},
|
|
26
26
|
'ai_profiles.workspace_access': {
|
|
27
|
-
|
|
27
|
+
enabledByEnvironment: { performance: true, staging: true, production: true },
|
|
28
28
|
description: 'AI Profiles workspace readiness gate.',
|
|
29
29
|
owner: 'taskforce',
|
|
30
30
|
removalMilestone: 'AI Profiles workspace GA'
|
|
31
31
|
},
|
|
32
32
|
'planning.workspace_access': {
|
|
33
|
-
|
|
33
|
+
enabledByEnvironment: { performance: false, staging: false, production: false },
|
|
34
34
|
description: 'Planning workspace readiness gate.',
|
|
35
35
|
owner: 'taskforce',
|
|
36
36
|
removalMilestone: 'Planning workspace GA'
|
|
@@ -1,17 +1,18 @@
|
|
|
1
|
-
|
|
1
|
+
import type { TaskforceCloudEnvironment } from '../config/cloudEnvironment.js';
|
|
2
|
+
import { APP_GATE_DEFINITIONS as APP_GATE_CONFIG } from './appGateDefinitions.js';
|
|
2
3
|
export declare const ANNOTATED_ATTACHMENTS_WORKSPACE_FEATURE_KEY: "annotated_attachments.workspace_access";
|
|
3
4
|
export declare const DOCUMENT_WORKSPACE_FEATURE_KEY: "documents.workspace_access";
|
|
4
5
|
export declare const WORKFLOW_MANAGER_WORKSPACE_FEATURE_KEY: "workflow_manager.workspace_access";
|
|
5
6
|
export declare const TASKFORCE_AGENTS_WORKSPACE_FEATURE_KEY: "taskforce_agents.workspace_access";
|
|
6
7
|
export declare const AI_PROFILES_WORKSPACE_FEATURE_KEY: "ai_profiles.workspace_access";
|
|
7
8
|
export declare const PLANNING_WORKSPACE_FEATURE_KEY: "planning.workspace_access";
|
|
8
|
-
export type AppGateKey =
|
|
9
|
+
export type AppGateKey = keyof typeof APP_GATE_CONFIG;
|
|
9
10
|
export interface AppGateDefinition {
|
|
10
|
-
key: AppGateKey;
|
|
11
|
-
|
|
12
|
-
description: string;
|
|
13
|
-
owner: string;
|
|
14
|
-
removalMilestone: string;
|
|
11
|
+
readonly key: AppGateKey;
|
|
12
|
+
readonly enabledByEnvironment: Readonly<Record<TaskforceCloudEnvironment, boolean>>;
|
|
13
|
+
readonly description: string;
|
|
14
|
+
readonly owner: string;
|
|
15
|
+
readonly removalMilestone: string;
|
|
15
16
|
}
|
|
16
17
|
export interface ResolvedFeatureAccess {
|
|
17
18
|
featureKey: string;
|
|
@@ -20,11 +21,9 @@ export interface ResolvedFeatureAccess {
|
|
|
20
21
|
code: string;
|
|
21
22
|
}
|
|
22
23
|
export type ResolvedFeatureAccessMap = Record<string, ResolvedFeatureAccess>;
|
|
23
|
-
export declare const APP_GATE_DEFINITIONS: Record<AppGateKey, AppGateDefinition
|
|
24
|
+
export declare const APP_GATE_DEFINITIONS: Readonly<Record<AppGateKey, AppGateDefinition>>;
|
|
24
25
|
export declare function listAppGateDefinitions(): AppGateDefinition[];
|
|
25
26
|
export declare function getAppGateDefinition(featureKey: string): AppGateDefinition | null;
|
|
26
|
-
export declare function resolveAppGateAccess(featureKey: string): ResolvedFeatureAccess;
|
|
27
|
-
export declare function
|
|
28
|
-
|
|
29
|
-
runtimeMode: RuntimeMode;
|
|
30
|
-
}): ResolvedFeatureAccess;
|
|
27
|
+
export declare function resolveAppGateAccess(featureKey: string, environment: TaskforceCloudEnvironment): ResolvedFeatureAccess;
|
|
28
|
+
export declare function resolveAppGateAccessMap(environment: TaskforceCloudEnvironment): ResolvedFeatureAccessMap;
|
|
29
|
+
export declare function isResolvedFeatureAccessMap(value: unknown): value is ResolvedFeatureAccessMap;
|
package/dist/runtime/appGates.js
CHANGED
|
@@ -5,16 +5,17 @@ export const WORKFLOW_MANAGER_WORKSPACE_FEATURE_KEY = 'workflow_manager.workspac
|
|
|
5
5
|
export const TASKFORCE_AGENTS_WORKSPACE_FEATURE_KEY = 'taskforce_agents.workspace_access';
|
|
6
6
|
export const AI_PROFILES_WORKSPACE_FEATURE_KEY = 'ai_profiles.workspace_access';
|
|
7
7
|
export const PLANNING_WORKSPACE_FEATURE_KEY = 'planning.workspace_access';
|
|
8
|
-
|
|
9
|
-
|
|
8
|
+
const appGateDefinitions = Object.fromEntries(Object.entries(APP_GATE_CONFIG).map(([key, definition]) => [
|
|
9
|
+
key,
|
|
10
|
+
Object.freeze({
|
|
10
11
|
key: key,
|
|
11
|
-
|
|
12
|
-
description:
|
|
13
|
-
owner:
|
|
14
|
-
removalMilestone:
|
|
15
|
-
}
|
|
16
|
-
|
|
17
|
-
|
|
12
|
+
enabledByEnvironment: Object.freeze({ ...definition.enabledByEnvironment }),
|
|
13
|
+
description: definition.description,
|
|
14
|
+
owner: definition.owner,
|
|
15
|
+
removalMilestone: definition.removalMilestone,
|
|
16
|
+
}),
|
|
17
|
+
]));
|
|
18
|
+
export const APP_GATE_DEFINITIONS = Object.freeze(appGateDefinitions);
|
|
18
19
|
export function listAppGateDefinitions() {
|
|
19
20
|
return Object.values(APP_GATE_DEFINITIONS);
|
|
20
21
|
}
|
|
@@ -24,7 +25,7 @@ export function getAppGateDefinition(featureKey) {
|
|
|
24
25
|
return null;
|
|
25
26
|
return APP_GATE_DEFINITIONS[normalizedKey] || null;
|
|
26
27
|
}
|
|
27
|
-
export function resolveAppGateAccess(featureKey) {
|
|
28
|
+
export function resolveAppGateAccess(featureKey, environment) {
|
|
28
29
|
const gate = getAppGateDefinition(featureKey);
|
|
29
30
|
if (!gate) {
|
|
30
31
|
return {
|
|
@@ -34,7 +35,7 @@ export function resolveAppGateAccess(featureKey) {
|
|
|
34
35
|
code: 'OK'
|
|
35
36
|
};
|
|
36
37
|
}
|
|
37
|
-
if (!gate.
|
|
38
|
+
if (!gate.enabledByEnvironment[environment]) {
|
|
38
39
|
return {
|
|
39
40
|
featureKey,
|
|
40
41
|
allowed: false,
|
|
@@ -49,6 +50,21 @@ export function resolveAppGateAccess(featureKey) {
|
|
|
49
50
|
code: 'OK'
|
|
50
51
|
};
|
|
51
52
|
}
|
|
52
|
-
export function
|
|
53
|
-
return
|
|
53
|
+
export function resolveAppGateAccessMap(environment) {
|
|
54
|
+
return Object.fromEntries(listAppGateDefinitions().map(({ key }) => [key, resolveAppGateAccess(key, environment)]));
|
|
55
|
+
}
|
|
56
|
+
export function isResolvedFeatureAccessMap(value) {
|
|
57
|
+
if (!value || typeof value !== 'object' || Array.isArray(value))
|
|
58
|
+
return false;
|
|
59
|
+
const candidate = value;
|
|
60
|
+
return listAppGateDefinitions().every(({ key }) => {
|
|
61
|
+
const access = candidate[key];
|
|
62
|
+
if (!access || typeof access !== 'object' || Array.isArray(access))
|
|
63
|
+
return false;
|
|
64
|
+
const resolved = access;
|
|
65
|
+
return resolved.featureKey === key
|
|
66
|
+
&& typeof resolved.allowed === 'boolean'
|
|
67
|
+
&& (resolved.source === 'app_gate' || resolved.source === 'cloud_entitlement' || resolved.source === 'none')
|
|
68
|
+
&& typeof resolved.code === 'string';
|
|
69
|
+
});
|
|
54
70
|
}
|
|
@@ -0,0 +1,8 @@
|
|
|
1
|
+
import type { TaskforceCloudEnvironment } from '../config/cloudEnvironment.js';
|
|
2
|
+
import { type ResolvedFeatureAccess, type ResolvedFeatureAccessMap } from './appGates.js';
|
|
3
|
+
export interface NodeAppGateResolutionOptions {
|
|
4
|
+
onWarning?: (message: string) => void;
|
|
5
|
+
}
|
|
6
|
+
export declare function resolveNodeAppGateEnvironment(env?: NodeJS.ProcessEnv, options?: NodeAppGateResolutionOptions): TaskforceCloudEnvironment;
|
|
7
|
+
export declare function resolveNodeAppGateAccess(featureKey: string, env?: NodeJS.ProcessEnv, options?: NodeAppGateResolutionOptions): ResolvedFeatureAccess;
|
|
8
|
+
export declare function resolveNodeAppGateAccessMap(env?: NodeJS.ProcessEnv, options?: NodeAppGateResolutionOptions): ResolvedFeatureAccessMap;
|
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
import { resolveDeploymentConfig } from '../config/deployment.js';
|
|
2
|
+
import { resolveAppGateAccess, resolveAppGateAccessMap, } from './appGates.js';
|
|
3
|
+
const warnedEnvironmentSignatures = new WeakMap();
|
|
4
|
+
export function resolveNodeAppGateEnvironment(env = process.env, options = {}) {
|
|
5
|
+
const deployment = resolveDeploymentConfig(env);
|
|
6
|
+
const warnings = [...deployment.warnings];
|
|
7
|
+
if (!deployment.cloudEnvironment) {
|
|
8
|
+
warnings.push('TASKFORCE_CLOUD_ENVIRONMENT could not be resolved; using the production App Gate profile.');
|
|
9
|
+
}
|
|
10
|
+
const warningSignature = warnings.join('\n');
|
|
11
|
+
if (warnings.length === 0) {
|
|
12
|
+
warnedEnvironmentSignatures.delete(env);
|
|
13
|
+
}
|
|
14
|
+
else if (warnedEnvironmentSignatures.get(env) !== warningSignature) {
|
|
15
|
+
const onWarning = options.onWarning || ((message) => console.warn(`[Taskforce App Gates] ${message}`));
|
|
16
|
+
for (const warning of warnings)
|
|
17
|
+
onWarning(warning);
|
|
18
|
+
warnedEnvironmentSignatures.set(env, warningSignature);
|
|
19
|
+
}
|
|
20
|
+
return deployment.cloudEnvironment || 'production';
|
|
21
|
+
}
|
|
22
|
+
export function resolveNodeAppGateAccess(featureKey, env = process.env, options = {}) {
|
|
23
|
+
return resolveAppGateAccess(featureKey, resolveNodeAppGateEnvironment(env, options));
|
|
24
|
+
}
|
|
25
|
+
export function resolveNodeAppGateAccessMap(env = process.env, options = {}) {
|
|
26
|
+
return resolveAppGateAccessMap(resolveNodeAppGateEnvironment(env, options));
|
|
27
|
+
}
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
import type { AccountAccessStatus } from '../core/types.js';
|
|
2
|
+
export interface AppAccessDeniedResponse {
|
|
3
|
+
statusCode: 403;
|
|
4
|
+
body: {
|
|
5
|
+
error: string;
|
|
6
|
+
code: string;
|
|
7
|
+
gate: AccountAccessStatus['gate'];
|
|
8
|
+
canAccessPlans: boolean;
|
|
9
|
+
planSelectionRequired: boolean;
|
|
10
|
+
};
|
|
11
|
+
}
|
|
12
|
+
export declare function resolveAppAccessDeniedResponse(accountAccess: AccountAccessStatus): AppAccessDeniedResponse | null;
|
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
export function resolveAppAccessDeniedResponse(accountAccess) {
|
|
2
|
+
if (accountAccess.canAccessApp)
|
|
3
|
+
return null;
|
|
4
|
+
const code = accountAccess.gate === 'plan_selection_required'
|
|
5
|
+
? 'PLAN_SELECTION_REQUIRED'
|
|
6
|
+
: accountAccess.gate === 'checkout_pending'
|
|
7
|
+
? 'CHECKOUT_PENDING'
|
|
8
|
+
: accountAccess.gate === 'misconfigured'
|
|
9
|
+
? 'ACCOUNT_ACCESS_MISCONFIGURED'
|
|
10
|
+
: 'ACCOUNT_ENTITLEMENT_REQUIRED';
|
|
11
|
+
return {
|
|
12
|
+
statusCode: 403,
|
|
13
|
+
body: {
|
|
14
|
+
error: accountAccess.message || 'This account cannot access the app.',
|
|
15
|
+
code,
|
|
16
|
+
gate: accountAccess.gate,
|
|
17
|
+
canAccessPlans: accountAccess.canAccessPlans,
|
|
18
|
+
planSelectionRequired: accountAccess.planSelectionRequired
|
|
19
|
+
}
|
|
20
|
+
};
|
|
21
|
+
}
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
import type { TaskforceCore } from '../core/Taskforce.js';
|
|
2
|
+
import type { RequestAccessContext } from './auth.js';
|
|
3
|
+
export interface AuthorizedRequestAccess extends RequestAccessContext {
|
|
4
|
+
disabled?: boolean;
|
|
5
|
+
accountDisabled?: boolean;
|
|
6
|
+
workspaceDisabled?: boolean;
|
|
7
|
+
}
|
|
8
|
+
type WorkspaceAccessCore = Pick<TaskforceCore, 'resolveUserAccess' | 'getSystemRole'>;
|
|
9
|
+
export declare function resolveAuthorizedWorkspaceAccess(core: WorkspaceAccessCore, access: AuthorizedRequestAccess, requestedWorkspaceId: string): AuthorizedRequestAccess;
|
|
10
|
+
export declare function isWorkspaceAccessRecoveryRoute(pathname: string): boolean;
|
|
11
|
+
export declare function resolveDisabledAccessError(access: Pick<AuthorizedRequestAccess, 'disabled' | 'accountDisabled' | 'workspaceDisabled'>, pathname: string): string | null;
|
|
12
|
+
export {};
|
|
@@ -0,0 +1,40 @@
|
|
|
1
|
+
export function resolveAuthorizedWorkspaceAccess(core, access, requestedWorkspaceId) {
|
|
2
|
+
if (!access.authenticated || !access.userId || access.userId === 'anonymous')
|
|
3
|
+
return access;
|
|
4
|
+
const trimmedRequestedWorkspaceId = String(requestedWorkspaceId || '').trim();
|
|
5
|
+
const candidateWorkspaceIds = [
|
|
6
|
+
trimmedRequestedWorkspaceId,
|
|
7
|
+
String(access.workspaceId || '').trim()
|
|
8
|
+
].filter((workspaceId, index, values) => Boolean(workspaceId) && values.indexOf(workspaceId) === index);
|
|
9
|
+
for (const workspaceId of candidateWorkspaceIds) {
|
|
10
|
+
const resolved = core.resolveUserAccess(access.userId, workspaceId, access.role);
|
|
11
|
+
if (!resolved)
|
|
12
|
+
continue;
|
|
13
|
+
return {
|
|
14
|
+
...access,
|
|
15
|
+
role: resolved.role,
|
|
16
|
+
workspaceId: resolved.workspaceId,
|
|
17
|
+
userId: resolved.userId,
|
|
18
|
+
systemRole: core.getSystemRole(resolved.userId),
|
|
19
|
+
disabled: resolved.disabled,
|
|
20
|
+
accountDisabled: resolved.accountDisabled ?? resolved.disabled,
|
|
21
|
+
workspaceDisabled: resolved.workspaceDisabled ?? false
|
|
22
|
+
};
|
|
23
|
+
}
|
|
24
|
+
return access;
|
|
25
|
+
}
|
|
26
|
+
export function isWorkspaceAccessRecoveryRoute(pathname) {
|
|
27
|
+
return pathname === '/api/taskforce/workspaces'
|
|
28
|
+
|| pathname === '/api/taskforce/session/workspace';
|
|
29
|
+
}
|
|
30
|
+
export function resolveDisabledAccessError(access, pathname) {
|
|
31
|
+
if (pathname.startsWith('/api/taskforce/auth/'))
|
|
32
|
+
return null;
|
|
33
|
+
if (access.accountDisabled ?? access.disabled) {
|
|
34
|
+
return 'Forbidden: user account is disabled.';
|
|
35
|
+
}
|
|
36
|
+
if (access.workspaceDisabled && !isWorkspaceAccessRecoveryRoute(pathname)) {
|
|
37
|
+
return 'Forbidden: workspace access is not active for this user.';
|
|
38
|
+
}
|
|
39
|
+
return null;
|
|
40
|
+
}
|
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
import type { TaskforceCore } from '../core/Taskforce.js';
|
|
2
|
+
import { type AuthorizedRequestAccess } from './authorizedWorkspaceAccess.js';
|
|
3
|
+
export type CloudCollectionReadOperation = 'tasks' | 'archive' | 'deleted' | 'planning-bootstrap';
|
|
4
|
+
export interface CloudCollectionReadRequest {
|
|
5
|
+
operation: CloudCollectionReadOperation;
|
|
6
|
+
pathname: string;
|
|
7
|
+
requestedWorkspaceId: string;
|
|
8
|
+
access: AuthorizedRequestAccess;
|
|
9
|
+
performanceTrace: boolean;
|
|
10
|
+
}
|
|
11
|
+
export interface CloudCollectionReadResponse {
|
|
12
|
+
statusCode: number;
|
|
13
|
+
headers: Record<string, string>;
|
|
14
|
+
body: string;
|
|
15
|
+
workspaceId: string;
|
|
16
|
+
performance?: {
|
|
17
|
+
durationMs: number;
|
|
18
|
+
details: Record<string, number>;
|
|
19
|
+
};
|
|
20
|
+
}
|
|
21
|
+
type CloudCollectionReadCore = Pick<TaskforceCore, 'resolveUserAccess' | 'getSystemRole' | 'getAccountAccessStatus' | 'listActiveTaskSummaries' | 'listArchiveSummaries' | 'listDeletedTasksReadOnly' | 'listPlanningBootstrap'>;
|
|
22
|
+
export declare function resolveCloudCollectionReadOperation(method: string | undefined, pathname: string): CloudCollectionReadOperation | null;
|
|
23
|
+
export declare function executeCloudCollectionRead(core: CloudCollectionReadCore, request: CloudCollectionReadRequest): CloudCollectionReadResponse;
|
|
24
|
+
export declare function cloudCollectionReadRoute(operation: CloudCollectionReadOperation): string;
|
|
25
|
+
export {};
|
|
@@ -0,0 +1,120 @@
|
|
|
1
|
+
import { getRequestPerformanceDiagnostics, runWithRequestPerformanceDiagnostics, } from '../storage/postgresRequestDiagnostics.js';
|
|
2
|
+
import { resolveAppAccessDeniedResponse } from './appAccess.js';
|
|
3
|
+
import { resolveAuthorizedWorkspaceAccess, resolveDisabledAccessError, } from './authorizedWorkspaceAccess.js';
|
|
4
|
+
const ROUTE_BY_OPERATION = {
|
|
5
|
+
tasks: '/api/taskforce/tasks',
|
|
6
|
+
archive: '/api/taskforce/archive',
|
|
7
|
+
deleted: '/api/taskforce/deleted',
|
|
8
|
+
'planning-bootstrap': '/api/taskforce/planning/bootstrap',
|
|
9
|
+
};
|
|
10
|
+
export function resolveCloudCollectionReadOperation(method, pathname) {
|
|
11
|
+
if (String(method || 'GET').toUpperCase() !== 'GET')
|
|
12
|
+
return null;
|
|
13
|
+
if (pathname === '/api/taskforce/tasks')
|
|
14
|
+
return 'tasks';
|
|
15
|
+
if (pathname === '/api/taskforce/archive')
|
|
16
|
+
return 'archive';
|
|
17
|
+
if (pathname === '/api/taskforce/deleted' || pathname === '/api/taskforce/trash')
|
|
18
|
+
return 'deleted';
|
|
19
|
+
if (pathname === '/api/taskforce/planning/bootstrap')
|
|
20
|
+
return 'planning-bootstrap';
|
|
21
|
+
return null;
|
|
22
|
+
}
|
|
23
|
+
function serverTimingMetric(name, durationMs) {
|
|
24
|
+
return `${name};dur=${Math.max(0, Math.round(durationMs))}`;
|
|
25
|
+
}
|
|
26
|
+
function performanceHeaders(diagnostics, responseBytes, metrics) {
|
|
27
|
+
const headers = {
|
|
28
|
+
'Content-Type': 'application/json',
|
|
29
|
+
'Server-Timing': metrics.map((metric) => serverTimingMetric(metric.name, metric.durationMs)).join(', '),
|
|
30
|
+
};
|
|
31
|
+
if (diagnostics) {
|
|
32
|
+
headers['X-Taskforce-Postgres-Query-Count'] = String(diagnostics.postgresQueryCount);
|
|
33
|
+
headers['X-Taskforce-Postgres-Worker-Call-Count'] = String(diagnostics.postgresWorkerCallCount);
|
|
34
|
+
headers['X-Taskforce-Response-Bytes'] = String(responseBytes);
|
|
35
|
+
}
|
|
36
|
+
return headers;
|
|
37
|
+
}
|
|
38
|
+
export function executeCloudCollectionRead(core, request) {
|
|
39
|
+
return runWithRequestPerformanceDiagnostics(request.performanceTrace, () => {
|
|
40
|
+
const access = resolveAuthorizedWorkspaceAccess(core, request.access, request.requestedWorkspaceId);
|
|
41
|
+
const workspaceId = String(access.workspaceId || '').trim();
|
|
42
|
+
const disabledAccessError = resolveDisabledAccessError(access, request.pathname);
|
|
43
|
+
if (disabledAccessError) {
|
|
44
|
+
return {
|
|
45
|
+
statusCode: 403,
|
|
46
|
+
headers: { 'Content-Type': 'application/json' },
|
|
47
|
+
body: JSON.stringify({ error: disabledAccessError }),
|
|
48
|
+
workspaceId,
|
|
49
|
+
};
|
|
50
|
+
}
|
|
51
|
+
if (access.authenticated && access.userId && access.userId !== 'anonymous') {
|
|
52
|
+
const denied = resolveAppAccessDeniedResponse(core.getAccountAccessStatus(access.userId));
|
|
53
|
+
if (denied) {
|
|
54
|
+
return {
|
|
55
|
+
statusCode: denied.statusCode,
|
|
56
|
+
headers: { 'Content-Type': 'application/json' },
|
|
57
|
+
body: JSON.stringify(denied.body),
|
|
58
|
+
workspaceId,
|
|
59
|
+
};
|
|
60
|
+
}
|
|
61
|
+
}
|
|
62
|
+
const startedAt = performance.now();
|
|
63
|
+
let data;
|
|
64
|
+
const planningDiagnostics = {};
|
|
65
|
+
if (request.operation === 'tasks')
|
|
66
|
+
data = core.listActiveTaskSummaries(workspaceId);
|
|
67
|
+
else if (request.operation === 'archive')
|
|
68
|
+
data = core.listArchiveSummaries(workspaceId);
|
|
69
|
+
else if (request.operation === 'deleted')
|
|
70
|
+
data = core.listDeletedTasksReadOnly(workspaceId);
|
|
71
|
+
else
|
|
72
|
+
data = core.listPlanningBootstrap(workspaceId, planningDiagnostics);
|
|
73
|
+
const loadCompletedAt = performance.now();
|
|
74
|
+
const serializeStartedAt = performance.now();
|
|
75
|
+
const body = JSON.stringify(data);
|
|
76
|
+
const serializeDurationMs = performance.now() - serializeStartedAt;
|
|
77
|
+
const totalDurationMs = performance.now() - startedAt;
|
|
78
|
+
const responseBytes = Buffer.byteLength(body, 'utf8');
|
|
79
|
+
const diagnostics = getRequestPerformanceDiagnostics();
|
|
80
|
+
const metrics = request.operation === 'planning-bootstrap'
|
|
81
|
+
? [
|
|
82
|
+
{ name: 'planning-bootstrap', durationMs: totalDurationMs },
|
|
83
|
+
{ name: 'planning-bootstrap-initiatives', durationMs: planningDiagnostics.initiativeLoadMs || 0 },
|
|
84
|
+
{ name: 'planning-bootstrap-workstreams', durationMs: planningDiagnostics.workstreamLoadMs || 0 },
|
|
85
|
+
{ name: 'planning-bootstrap-tasks', durationMs: planningDiagnostics.taskSummaryQueryMs || 0 },
|
|
86
|
+
{ name: 'planning-bootstrap-build', durationMs: planningDiagnostics.taskSummaryBuildMs || 0 },
|
|
87
|
+
{ name: 'planning-bootstrap-json', durationMs: serializeDurationMs },
|
|
88
|
+
]
|
|
89
|
+
: [
|
|
90
|
+
{ name: 'route-total', durationMs: totalDurationMs },
|
|
91
|
+
{ name: 'route-load', durationMs: loadCompletedAt - startedAt },
|
|
92
|
+
{ name: 'route-json', durationMs: serializeDurationMs },
|
|
93
|
+
];
|
|
94
|
+
if (diagnostics) {
|
|
95
|
+
metrics.push({ name: 'postgres-worker-wait', durationMs: diagnostics.postgresWorkerWaitMs });
|
|
96
|
+
}
|
|
97
|
+
return {
|
|
98
|
+
statusCode: 200,
|
|
99
|
+
headers: performanceHeaders(diagnostics, responseBytes, metrics),
|
|
100
|
+
body,
|
|
101
|
+
workspaceId,
|
|
102
|
+
performance: {
|
|
103
|
+
durationMs: totalDurationMs,
|
|
104
|
+
details: {
|
|
105
|
+
responseBytes,
|
|
106
|
+
jsonSerializeMs: serializeDurationMs,
|
|
107
|
+
...(diagnostics ? {
|
|
108
|
+
postgresQueryCount: diagnostics.postgresQueryCount,
|
|
109
|
+
postgresWorkerCallCount: diagnostics.postgresWorkerCallCount,
|
|
110
|
+
postgresWorkerWaitMs: Math.round(diagnostics.postgresWorkerWaitMs),
|
|
111
|
+
} : {}),
|
|
112
|
+
...(request.operation === 'planning-bootstrap' ? planningDiagnostics : {}),
|
|
113
|
+
},
|
|
114
|
+
},
|
|
115
|
+
};
|
|
116
|
+
});
|
|
117
|
+
}
|
|
118
|
+
export function cloudCollectionReadRoute(operation) {
|
|
119
|
+
return ROUTE_BY_OPERATION[operation];
|
|
120
|
+
}
|
|
@@ -0,0 +1,52 @@
|
|
|
1
|
+
import type { CloudCollectionReadRequest, CloudCollectionReadResponse } from './cloudCollectionRead.js';
|
|
2
|
+
export interface CloudCollectionReadPoolOptions {
|
|
3
|
+
projectRoot: string;
|
|
4
|
+
tenantId: string;
|
|
5
|
+
connectionString: string;
|
|
6
|
+
size?: number;
|
|
7
|
+
requestTimeoutMs?: number;
|
|
8
|
+
workerFactory?: () => CloudCollectionReadWorker;
|
|
9
|
+
}
|
|
10
|
+
export interface CloudCollectionReadWorker {
|
|
11
|
+
postMessage(message: unknown): void;
|
|
12
|
+
terminate(): Promise<number>;
|
|
13
|
+
on(event: 'message', listener: (message: CloudCollectionReadWorkerResponse) => void): this;
|
|
14
|
+
on(event: 'error', listener: (error: unknown) => void): this;
|
|
15
|
+
on(event: 'exit', listener: (code: number) => void): this;
|
|
16
|
+
}
|
|
17
|
+
export type CloudCollectionReadWorkerResponse = {
|
|
18
|
+
type: 'ready';
|
|
19
|
+
} | {
|
|
20
|
+
type: 'result';
|
|
21
|
+
requestId: number;
|
|
22
|
+
response: CloudCollectionReadResponse;
|
|
23
|
+
} | {
|
|
24
|
+
type: 'error';
|
|
25
|
+
requestId: number;
|
|
26
|
+
error: string;
|
|
27
|
+
};
|
|
28
|
+
export declare class CloudCollectionReadPool {
|
|
29
|
+
private readonly slots;
|
|
30
|
+
private readonly queue;
|
|
31
|
+
private readonly requestTimeoutMs;
|
|
32
|
+
private readonly desiredSize;
|
|
33
|
+
private readonly workerData;
|
|
34
|
+
private readonly workerFactory;
|
|
35
|
+
private nextRequestId;
|
|
36
|
+
private closing;
|
|
37
|
+
constructor(options: CloudCollectionReadPoolOptions);
|
|
38
|
+
execute(request: CloudCollectionReadRequest): Promise<CloudCollectionReadResponse>;
|
|
39
|
+
close(): Promise<void>;
|
|
40
|
+
private spawnSlot;
|
|
41
|
+
private handleMessage;
|
|
42
|
+
private handleWorkerFailure;
|
|
43
|
+
private ensureSlots;
|
|
44
|
+
private pump;
|
|
45
|
+
}
|
|
46
|
+
export declare function resolveCloudCollectionReadPoolSize(env?: NodeJS.ProcessEnv): number;
|
|
47
|
+
export declare function shouldUseCloudCollectionReadPool(input: {
|
|
48
|
+
runtimeMode: 'local' | 'cloud';
|
|
49
|
+
databaseProvider: 'sqlite' | 'postgres';
|
|
50
|
+
connectionString?: string;
|
|
51
|
+
workerCount: number;
|
|
52
|
+
}): boolean;
|