From 9eea28bacd27b2ee6d5183e195c397bba8b515a0 Mon Sep 17 00:00:00 2001 From: Julius Marminge Date: Thu, 8 Oct 2026 14:18:16 -0700 Subject: [PATCH] refactor(provider-core): add provider-core and provider-testing packages (#17299) Co-authored-by: Claude Opus 5.5 --- apps/server/package.json | 2 + apps/server/scripts/evaluate-thread-titles.ts | 2 +- ...probe-claude-fork-local-rollback-replay.ts | 4 +- .../record-claude-agent-sdk-replay-fixture.ts | 4 +- .../record-cursor-agent-sdk-replay-fixture.ts | 2 +- .../scripts/record-grok-acp-replay-fixture.ts | 6 +- .../scripts/record-muse-msp-replay-fixture.ts | 6 +- .../scripts/record-pi-rpc-replay-fixture.ts | 4 +- .../scripts/threadTitleEvaluationCases.ts | 2 +- apps/server/src/assets/AssetAccess.ts | 2 +- apps/server/src/mcp/McpSessionRegistry.ts | 2 +- .../server/src/mcp/McpToolAccess.race.test.ts | 2 +- .../src/mcp/OrchestratorMcpService.test.ts | 2 +- ...OrchestratorMcpToolkit.integration.test.ts | 6 +- .../server/src/mcpApps/McpAppRequests.test.ts | 2 +- apps/server/src/mcpApps/McpAppRequests.ts | 2 +- .../Adapters/AcpAdapterV2.test.ts | 6 +- .../Adapters/AcpAdapterV2.testkit.ts | 2 +- .../orchestration-v2/Adapters/AcpAdapterV2.ts | 17 +- .../Adapters/AcpRegistryAdapterV2.test.ts | 4 +- .../Adapters/AcpRegistryAdapterV2.testkit.ts | 4 +- .../Adapters/AcpRegistryAdapterV2.ts | 8 +- .../Adapters/AntigravityAdapterV2.test.ts | 4 +- .../Adapters/AntigravityAdapterV2.ts | 2 +- .../Adapters/ClaudeAdapterV2.test.ts | 8 +- .../Adapters/ClaudeAdapterV2.testkit.ts | 8 +- .../Adapters/ClaudeAdapterV2.ts | 28 ++-- .../Adapters/CodexAdapterV2.test.ts | 8 +- .../Adapters/CodexAdapterV2.testkit.ts | 8 +- .../Adapters/CodexAdapterV2.ts | 18 +- .../Adapters/CursorAdapterV2.test.ts | 6 +- .../Adapters/CursorAdapterV2.testkit.ts | 6 +- .../Adapters/CursorAdapterV2.ts | 18 +- .../Adapters/GrokAdapterV2.test.ts | 6 +- .../Adapters/GrokAdapterV2.testkit.ts | 4 +- .../Adapters/GrokAdapterV2.ts | 10 +- .../Adapters/MuseAdapterV2.test.ts | 6 +- .../Adapters/MuseAdapterV2.testkit.ts | 2 +- .../Adapters/MuseAdapterV2.ts | 10 +- .../Adapters/OpenCode2AdapterV2.test.ts | 6 +- .../Adapters/OpenCode2AdapterV2.testkit.ts | 4 +- .../Adapters/OpenCode2AdapterV2.ts | 12 +- .../Adapters/OpenCodeAdapterV2.test.ts | 4 +- .../Adapters/OpenCodeAdapterV2.testkit.ts | 4 +- .../Adapters/OpenCodeAdapterV2.ts | 18 +- .../Adapters/PiAdapterV2.test.ts | 23 +-- .../Adapters/PiAdapterV2.testkit.ts | 23 ++- .../orchestration-v2/Adapters/PiAdapterV2.ts | 43 +++-- .../src/orchestration-v2/Adapters/PiRpc.ts | 2 +- .../Adapters/piT3McpExtensionSource.ts | 2 +- .../Adapters/piT3McpInjection.ts | 2 +- .../BackgroundWorkStop.integration.test.ts | 4 +- .../CheckpointCaptureService.test.ts | 2 +- .../CheckpointCaptureService.ts | 2 +- .../CheckpointRestoreSafety.test.ts | 2 +- .../CheckpointRollbackService.test.ts | 4 +- .../CheckpointRollbackService.ts | 4 +- .../CheckpointScopeOwnership.test.ts | 2 +- .../CheckpointService.test.ts | 2 +- .../src/orchestration-v2/CheckpointService.ts | 2 +- ...laudeAutomaticDelivery.integration.test.ts | 4 +- .../ContextHandoffBudget.test.ts | 2 +- .../ContextHandoffDelivery.ts | 11 +- .../ContextHandoffService.test.ts | 2 +- .../orchestration-v2/ContextHandoffService.ts | 2 +- .../DelegatedCompletionDelivery.test.ts | 4 +- .../DispatchModeLimit.test.ts | 2 +- .../FoundationPersistence.test.ts | 2 +- ...penCode2OrchestratorV2.integration.test.ts | 6 +- .../OpenCode2OrchestratorV2.live.test.ts | 2 +- .../Orchestrator.control-reads.test.ts | 2 +- .../src/orchestration-v2/Orchestrator.ts | 6 +- .../ProviderAdapterRegistry.test.ts | 9 +- .../ProviderAdapterRegistry.ts | 4 +- .../ProviderContinuationService.test.ts | 2 +- .../ProviderContinuationService.ts | 2 +- .../ProviderEventIngestor.test.ts | 4 +- .../orchestration-v2/ProviderEventIngestor.ts | 6 +- ...ProviderRuntimeRecoveryPerformance.test.ts | 2 +- ...rRuntimeRecoveryService.regression.test.ts | 2 +- .../ProviderRuntimeRecoveryService.test.ts | 2 +- .../ProviderRuntimeRecoveryService.ts | 2 +- .../ProviderSelectionTransition.test.ts | 2 +- .../ProviderSessionManager.test.ts | 6 +- .../ProviderSessionManager.ts | 6 +- .../ProviderSessionTransitionPolicy.ts | 4 +- .../ProviderSwitchService.test.ts | 4 +- .../ProviderTurnControlService.test.ts | 2 +- .../ProviderTurnStartService.test.ts | 4 +- .../ProviderTurnStartService.ts | 6 +- .../RestartContinuation.test.ts | 2 +- .../RunExecutionService.test.ts | 4 +- .../orchestration-v2/RunExecutionService.ts | 11 +- .../orchestration-v2/RuntimePolicy.test.ts | 2 +- .../src/orchestration-v2/RuntimePolicy.ts | 2 +- .../RuntimeRequestService.test.ts | 2 +- .../SelectionRestart.integration.test.ts | 4 +- .../SteeringCompletion.integration.test.ts | 4 +- .../orchestration-v2/ThreadDeletion.test.ts | 2 +- .../src/orchestration-v2/ThreadDeletion.ts | 2 +- .../ThreadFork.execution.test.ts | 2 +- .../ThreadLaunchService.test.ts | 4 +- .../orchestration-v2/ThreadLaunchService.ts | 6 +- .../src/orchestration-v2/ThreadStop.test.ts | 2 +- .../ThreadTitleRegenerationService.test.ts | 2 +- .../ThreadTitleRegenerationService.ts | 4 +- .../assistantStreaming.test.ts | 2 +- .../orchestration-v2/assistantStreaming.ts | 2 +- .../builtInProviderAdapterDrivers.ts | 2 +- .../LegacyV1Cutover.integration.test.ts | 4 +- .../legacy/LegacyV1ThreadImporter.ts | 2 +- .../src/orchestration-v2/runtimeLayer.test.ts | 7 +- .../src/orchestration-v2/runtimeLayer.ts | 2 +- .../ClaudeReplayFixtures.integration.test.ts | 6 +- .../CodexReplayFixtures.integration.test.ts | 2 +- ...rchestratorReplayFixtures.contract.test.ts | 4 +- ...estratorReplayFixtures.integration.test.ts | 8 +- ...estratorReplayRecovery.integration.test.ts | 8 +- ...yRestartBackgroundNote.integration.test.ts | 6 +- .../testkit/OrchestratorScenario.ts | 2 +- .../testkit/ProviderReplayHarness.ts | 7 +- .../ProviderSwitch.integration.test.ts | 6 +- .../ProviderTurnStartMemory.fixture.mjs | 4 +- .../testkit/ReplayRuntimeInstructions.ts | 70 ++++++++ .../testkit/ThreadFork.integration.test.ts | 4 +- .../ThreadMergeBack.integration.test.ts | 6 +- .../testkit/fixtures/shared.ts | 2 +- apps/server/src/processRunner.ts | 25 +-- .../src/project/AgentSessionImporter.test.ts | 2 +- .../src/project/AgentSessionImporter.ts | 2 +- .../server/src/project/AgentSessionScanner.ts | 2 +- .../project/ProjectService.deletion.test.ts | 2 +- .../server/src/project/ProjectService.test.ts | 2 +- apps/server/src/project/ProjectService.ts | 2 +- .../src/provider/AntigravityProvider.test.ts | 20 ++- .../src/provider/AntigravityProvider.ts | 4 +- .../provider/ClaudeCapabilitiesProbe.test.ts | 2 +- apps/server/src/provider/ClaudeProvider.ts | 6 +- .../provider/CodexDeveloperInstructions.ts | 2 +- apps/server/src/provider/CodexProvider.ts | 6 +- .../src/provider/CodexToolPresentation.ts | 2 +- apps/server/src/provider/CursorProvider.ts | 2 +- .../src/provider/Drivers/AcpRegistryDriver.ts | 20 +-- .../Drivers/AntigravityDriver.test.ts | 6 +- .../src/provider/Drivers/AntigravityDriver.ts | 18 +- .../src/provider/Drivers/ClaudeDriver.ts | 20 +-- .../server/src/provider/Drivers/ClaudeHome.ts | 2 +- .../src/provider/Drivers/ClaudeSkills.ts | 2 +- .../src/provider/Drivers/CodexDriver.test.ts | 10 +- .../src/provider/Drivers/CodexDriver.ts | 18 +- .../src/provider/Drivers/CodexHomeLayout.ts | 2 +- .../provider/Drivers/CodexManagedProvider.ts | 15 +- .../src/provider/Drivers/CursorDriver.test.ts | 8 +- .../src/provider/Drivers/CursorDriver.ts | 13 +- .../src/provider/Drivers/GrokDriver.test.ts | 6 +- .../server/src/provider/Drivers/GrokDriver.ts | 18 +- .../server/src/provider/Drivers/GrokSkills.ts | 2 +- .../server/src/provider/Drivers/MuseDriver.ts | 22 ++- .../provider/Drivers/OpenCodeDriver.test.ts | 11 +- .../src/provider/Drivers/OpenCodeDriver.ts | 20 +-- .../src/provider/Drivers/PiDriver.test.ts | 7 +- apps/server/src/provider/Drivers/PiDriver.ts | 24 ++- .../src/provider/Drivers/instanceIdentity.ts | 4 +- apps/server/src/provider/Errors.ts | 19 +-- apps/server/src/provider/GrokProvider.ts | 4 +- apps/server/src/provider/ModelManifest.ts | 2 +- apps/server/src/provider/MuseProvider.test.ts | 2 +- apps/server/src/provider/MuseProvider.ts | 2 +- apps/server/src/provider/OpenCodeProvider.ts | 2 +- .../src/provider/OpenCodeServerLedger.ts | 2 +- apps/server/src/provider/PiProvider.ts | 4 +- .../src/provider/ProviderAuthService.test.ts | 2 +- .../src/provider/ProviderAuthService.ts | 48 +----- apps/server/src/provider/ProviderHostLive.ts | 39 +++++ .../provider/ProviderInstanceRegistry.test.ts | 9 +- .../src/provider/ProviderInstanceRegistry.ts | 2 +- .../ProviderInstanceRegistryHydration.ts | 11 +- ...viderOrchestrationAdapterInfrastructure.ts | 2 +- .../src/provider/ProviderRegistry.test.ts | 9 +- apps/server/src/provider/ProviderRegistry.ts | 7 +- .../src/provider/acp/AcpRegistrySupport.ts | 2 +- .../src/provider/acp/AcpSessionRuntime.ts | 2 +- .../src/provider/antigravityAuthSupport.ts | 2 +- apps/server/src/provider/builtInDrivers.ts | 2 +- .../src/provider/builtInProviderCatalog.ts | 2 +- apps/server/src/provider/claudeUsageLimits.ts | 2 +- apps/server/src/provider/codexUsageLimits.ts | 2 +- apps/server/src/provider/cursorUsageLimits.ts | 2 +- apps/server/src/provider/grokUsageLimits.ts | 2 +- .../makeManagedServerProvider.test.ts | 29 +++- .../src/provider/makeManagedServerProvider.ts | 27 ++- .../src/provider/museMaintenance.test.ts | 2 +- apps/server/src/provider/museMaintenance.ts | 4 +- .../src/provider/openCodeUsageLimits.ts | 2 +- apps/server/src/provider/opencodeRuntime.ts | 4 +- .../src/provider/opencodeVersionProbe.ts | 2 +- .../provider/providerCompatibility.test.ts | 4 +- .../src/provider/providerInstallation.test.ts | 2 +- .../src/provider/providerInstallation.ts | 2 +- .../providerMaintenanceRunner.test.ts | 2 +- .../src/provider/providerMaintenanceRunner.ts | 6 +- .../src/provider/providerUpdateSettings.ts | 8 +- .../testUtils/providerRegistryMock.ts | 2 +- .../provider/unavailableProviderSnapshot.ts | 2 +- apps/server/src/sourceControl/BitbucketApi.ts | 2 +- apps/server/src/sourceControl/ForgejoCli.ts | 2 +- apps/server/src/sourceControl/GitHubApi.ts | 2 +- .../SourceControlRepositoryService.ts | 2 +- apps/server/src/terminal/Manager.ts | 4 +- .../AntigravityTextGeneration.ts | 2 +- .../ClaudeTextGeneration.test.ts | 2 +- .../textGeneration/ClaudeTextGeneration.ts | 7 +- .../src/textGeneration/CodexTextGeneration.ts | 9 +- .../textGeneration/CursorTextGeneration.ts | 2 +- .../src/textGeneration/GrokTextGeneration.ts | 2 +- .../src/textGeneration/MuseTextGeneration.ts | 4 +- .../textGeneration/OpenCode2TextGeneration.ts | 2 +- .../textGeneration/OpenCodeTextGeneration.ts | 2 +- .../src/textGeneration/PiTextGeneration.ts | 2 +- .../src/textGeneration/TextGeneration.test.ts | 4 +- .../src/textGeneration/TextGeneration.ts | 119 ++----------- .../TextGenerationOperations.ts | 153 ----------------- .../textGeneration/TextGenerationPresets.ts | 2 +- apps/server/src/usage/UsageService.ts | 4 +- apps/server/src/usage/cliproxyApi.ts | 2 +- apps/server/src/workspace/WorkspaceEntries.ts | 2 +- apps/server/src/workspace/WorkspacePaths.ts | 2 +- apps/server/src/worktreesDirectory.ts | 2 +- apps/server/src/ws.ts | 4 +- apps/web/package.json | 1 + .../components/chat/ComposerUsageLimits.tsx | 4 +- .../onboarding/WelcomeWizard.import.test.tsx | 4 +- .../WelcomeWizard.terminal.test.tsx | 2 +- .../components/onboarding/WelcomeWizard.tsx | 4 +- .../settings/AddProviderInstanceDialog.tsx | 20 +-- .../settings/ProviderInstanceCard.tsx | 19 ++- .../settings/ProviderSettingsForm.test.ts | 18 +- .../settings/ProviderSettingsForm.tsx | 8 +- .../settings/ProviderSettingsPanel.tsx | 8 +- .../components/settings/providerDriverMeta.ts | 80 ++------- .../components/usage/UsageLimitsPooled.tsx | 12 +- .../usage/UsagePage.refresh.test.tsx | 4 +- docs/internals/adding-a-provider.md | 2 +- docs/internals/providers.md | 2 +- package.json | 2 +- packages/provider-core/package.json | 138 +++++++++++++++ packages/provider-core/src/client.test.ts | 34 ++++ packages/provider-core/src/client.ts | 77 +++++++++ .../provider-core/src/server}/IdAllocator.ts | 4 +- .../src/server}/ProviderAdapter.ts | 4 +- .../provider-core/src/server/ProviderHost.ts | 54 ++++++ .../provider-core/src/server/adapterDriver.ts | 2 +- packages/provider-core/src/server/auth.ts | 57 +++++++ .../src/server/collectStreamText.test.ts | 2 +- .../src/server/collectStreamText.ts | 0 .../provider-core/src/server/driver.ts | 14 +- packages/provider-core/src/server/errors.ts | 21 +++ .../provider-core/src/server/failure.test.ts | 6 +- .../provider-core/src/server/failure.ts | 12 +- .../src/server/instanceEnvironment.test.ts | 2 +- .../src/server/instanceEnvironment.ts | 2 +- .../provider-core/src/server/maintenance.ts | 30 ++++ .../src/server/maintenanceResolver.test.ts | 2 +- .../src/server/maintenanceResolver.ts | 39 +---- .../src/server/mcpSession.test.ts | 2 +- .../provider-core/src/server/mcpSession.ts | 0 .../src/server/mcpToolPresentation.test.ts | 2 +- .../src/server/mcpToolPresentation.ts | 0 .../server/orchestrationInstructions.test.ts | 2 +- .../src/server/orchestrationInstructions.ts | 0 .../src/server}/pathExpansion.test.ts | 0 .../src/server}/pathExpansion.ts | 0 .../src/server}/processGroup.test.ts | 0 .../provider-core/src/server}/processGroup.ts | 0 .../provider-core/src/server/randomUuid.ts | 0 .../src/server/selectionTransition.ts | 0 .../provider-core/src/server/snapshot.ts | 2 +- .../src/server/snapshotProbe.test.ts | 2 +- .../provider-core/src/server/snapshotProbe.ts | 27 ++- .../src/server/textGeneration.ts | 104 ++++++++++++ .../src/server/textGenerationOperations.ts | 157 ++++++++++++++++++ .../src/server/textGenerationPolicy.ts | 0 .../src/server/textGenerationPrompts.test.ts | 4 +- .../src/server/textGenerationPrompts.ts | 6 +- .../src/server/textGenerationUtils.ts | 0 .../src/server/threadTitleContext.test.ts | 2 +- .../src/server/threadTitleContext.ts | 0 .../src/server/usageLimits.test.ts | 2 +- .../provider-core/src/server/usageLimits.ts | 0 packages/provider-core/tsconfig.json | 7 + packages/provider-testing/package.json | 38 +++++ packages/provider-testing/src/host.ts | 54 ++++++ .../provider-testing/src/replayGate.test.ts | 38 +++++ .../provider-testing/src/replayGate.ts | 0 .../src/replayTranscript.test.ts | 96 +++++++++++ .../provider-testing/src/replayTranscript.ts | 70 -------- .../provider-testing/src/replayWorkspace.ts | 0 packages/provider-testing/tsconfig.json | 7 + pnpm-lock.yaml | 59 +++++++ scripts/release-smoke.ts | 2 + 300 files changed, 1893 insertions(+), 1166 deletions(-) create mode 100644 apps/server/src/orchestration-v2/testkit/ReplayRuntimeInstructions.ts create mode 100644 apps/server/src/provider/ProviderHostLive.ts delete mode 100644 apps/server/src/textGeneration/TextGenerationOperations.ts create mode 100644 packages/provider-core/package.json create mode 100644 packages/provider-core/src/client.test.ts create mode 100644 packages/provider-core/src/client.ts rename {apps/server/src/orchestration-v2 => packages/provider-core/src/server}/IdAllocator.ts (99%) rename {apps/server/src/orchestration-v2 => packages/provider-core/src/server}/ProviderAdapter.ts (99%) create mode 100644 packages/provider-core/src/server/ProviderHost.ts rename apps/server/src/orchestration-v2/ProviderAdapterDriver.ts => packages/provider-core/src/server/adapterDriver.ts (94%) create mode 100644 packages/provider-core/src/server/auth.ts rename apps/server/src/stream/collectUint8StreamText.test.ts => packages/provider-core/src/server/collectStreamText.test.ts (96%) rename apps/server/src/stream/collectUint8StreamText.ts => packages/provider-core/src/server/collectStreamText.ts (100%) rename apps/server/src/provider/ProviderDriver.ts => packages/provider-core/src/server/driver.ts (95%) create mode 100644 packages/provider-core/src/server/errors.ts rename apps/server/src/orchestration-v2/ProviderFailure.test.ts => packages/provider-core/src/server/failure.test.ts (97%) rename apps/server/src/orchestration-v2/ProviderFailure.ts => packages/provider-core/src/server/failure.ts (94%) rename apps/server/src/provider/ProviderInstanceEnvironment.test.ts => packages/provider-core/src/server/instanceEnvironment.test.ts (96%) rename apps/server/src/provider/ProviderInstanceEnvironment.ts => packages/provider-core/src/server/instanceEnvironment.ts (92%) create mode 100644 packages/provider-core/src/server/maintenance.ts rename apps/server/src/provider/providerMaintenance.test.ts => packages/provider-core/src/server/maintenanceResolver.test.ts (99%) rename apps/server/src/provider/providerMaintenance.ts => packages/provider-core/src/server/maintenanceResolver.ts (96%) rename apps/server/src/mcp/McpProviderSession.test.ts => packages/provider-core/src/server/mcpSession.test.ts (94%) rename apps/server/src/mcp/McpProviderSession.ts => packages/provider-core/src/server/mcpSession.ts (100%) rename apps/server/src/provider/McpToolPresentation.test.ts => packages/provider-core/src/server/mcpToolPresentation.test.ts (98%) rename apps/server/src/provider/McpToolPresentation.ts => packages/provider-core/src/server/mcpToolPresentation.ts (100%) rename apps/server/src/provider/T3OrchestrationInstructions.test.ts => packages/provider-core/src/server/orchestrationInstructions.test.ts (98%) rename apps/server/src/provider/T3OrchestrationInstructions.ts => packages/provider-core/src/server/orchestrationInstructions.ts (100%) rename {apps/server/src => packages/provider-core/src/server}/pathExpansion.test.ts (100%) rename {apps/server/src => packages/provider-core/src/server}/pathExpansion.ts (100%) rename {apps/server/src/process => packages/provider-core/src/server}/processGroup.test.ts (100%) rename {apps/server/src/process => packages/provider-core/src/server}/processGroup.ts (100%) rename apps/server/src/orchestration-v2/RandomUuid.ts => packages/provider-core/src/server/randomUuid.ts (100%) rename apps/server/src/orchestration-v2/ProviderSelectionTransition.ts => packages/provider-core/src/server/selectionTransition.ts (100%) rename apps/server/src/provider/ServerProvider.ts => packages/provider-core/src/server/snapshot.ts (92%) rename apps/server/src/provider/providerSnapshot.test.ts => packages/provider-core/src/server/snapshotProbe.test.ts (99%) rename apps/server/src/provider/providerSnapshot.ts => packages/provider-core/src/server/snapshotProbe.ts (89%) create mode 100644 packages/provider-core/src/server/textGeneration.ts create mode 100644 packages/provider-core/src/server/textGenerationOperations.ts rename apps/server/src/textGeneration/TextGenerationPolicy.ts => packages/provider-core/src/server/textGenerationPolicy.ts (100%) rename apps/server/src/textGeneration/TextGenerationPrompts.test.ts => packages/provider-core/src/server/textGenerationPrompts.test.ts (99%) rename apps/server/src/textGeneration/TextGenerationPrompts.ts => packages/provider-core/src/server/textGenerationPrompts.ts (98%) rename apps/server/src/textGeneration/TextGenerationUtils.ts => packages/provider-core/src/server/textGenerationUtils.ts (100%) rename apps/server/src/textGeneration/ThreadTitleContext.test.ts => packages/provider-core/src/server/threadTitleContext.test.ts (97%) rename apps/server/src/textGeneration/ThreadTitleContext.ts => packages/provider-core/src/server/threadTitleContext.ts (100%) rename apps/server/src/provider/providerUsageLimits.test.ts => packages/provider-core/src/server/usageLimits.test.ts (98%) rename apps/server/src/provider/providerUsageLimits.ts => packages/provider-core/src/server/usageLimits.ts (100%) create mode 100644 packages/provider-core/tsconfig.json create mode 100644 packages/provider-testing/package.json create mode 100644 packages/provider-testing/src/host.ts create mode 100644 packages/provider-testing/src/replayGate.test.ts rename apps/server/src/orchestration-v2/testkit/ProviderReplayGate.testkit.ts => packages/provider-testing/src/replayGate.ts (100%) create mode 100644 packages/provider-testing/src/replayTranscript.test.ts rename apps/server/src/orchestration-v2/testkit/ReplayTranscriptNdjson.ts => packages/provider-testing/src/replayTranscript.ts (70%) rename apps/server/src/orchestration-v2/testkit/ReplayFixtureWorkspace.ts => packages/provider-testing/src/replayWorkspace.ts (100%) create mode 100644 packages/provider-testing/tsconfig.json diff --git a/apps/server/package.json b/apps/server/package.json index 5f81d57f588f9de0384abd9b5727f40e193855f6..74bb7cac0e94efad2dc1ab3113a3b9d4cb988190 100644 --- a/apps/server/package.json +++ b/apps/server/package.json @@ -41,6 +41,7 @@ "@opencode/client": "2.0.23", "@opencode/protocol": "2.0.23", "@opencode/schema": "2.0.23", + "@t3tools/provider-core": "workspace:*", "diff": "8.0.3", "effect": "catalog:", "jose": "catalog:", @@ -56,6 +57,7 @@ "@effect/vitest": "catalog:", "@modelcontextprotocol/sdk": "1.29.0", "@t3tools/contracts": "workspace:*", + "@t3tools/provider-testing": "workspace:*", "@t3tools/shared": "workspace:*", "@t3tools/ssh": "workspace:*", "@t3tools/tailscale": "workspace:*", diff --git a/apps/server/scripts/evaluate-thread-titles.ts b/apps/server/scripts/evaluate-thread-titles.ts index b91196f28f84c80432304dc114daa8cababd9334..0747825dcb5b33fc137b0d05ebc51e784a29f10f 100644 --- a/apps/server/scripts/evaluate-thread-titles.ts +++ b/apps/server/scripts/evaluate-thread-titles.ts @@ -20,7 +20,7 @@ import { threadTitleEvaluationCases } from "./threadTitleEvaluationCases.ts"; import { formatThreadTitleContext, type ThreadTitleMessage, -} from "../src/textGeneration/ThreadTitleContext.ts"; +} from "@t3tools/provider-core/server/threadTitleContext"; import * as ThreadTitleLinks from "../src/textGeneration/ThreadTitleLinks.ts"; import * as SourceControlProviderRegistry from "../src/sourceControl/SourceControlProviderRegistry.ts"; import * as GitHubApi from "../src/sourceControl/GitHubApi.ts"; diff --git a/apps/server/scripts/probe-claude-fork-local-rollback-replay.ts b/apps/server/scripts/probe-claude-fork-local-rollback-replay.ts index e5a233dcc5c8cec18580b44172db0bc12c009c68..3d856fb9672e68c7c230ce8052ab1d90ede0042e 100644 --- a/apps/server/scripts/probe-claude-fork-local-rollback-replay.ts +++ b/apps/server/scripts/probe-claude-fork-local-rollback-replay.ts @@ -15,8 +15,8 @@ import { makeClaudeUserMessage, type ClaudeAgentSdkQueryOptions, } from "../src/orchestration-v2/Adapters/ClaudeAdapterV2.ts"; -import { randomUuidV4 } from "../src/orchestration-v2/RandomUuid.ts"; -import { makeCheckpointWorkspace } from "../src/orchestration-v2/testkit/ReplayFixtureWorkspace.ts"; +import { randomUuidV4 } from "@t3tools/provider-core/server/randomUuid"; +import { makeCheckpointWorkspace } from "@t3tools/provider-testing/replayWorkspace"; const SCENARIO = "thread_fork_native_fork_local_rollback"; const DEFAULT_OUTPUT = new URL( diff --git a/apps/server/scripts/record-claude-agent-sdk-replay-fixture.ts b/apps/server/scripts/record-claude-agent-sdk-replay-fixture.ts index 22a6df8eefbe4c04dc2d49cb07c3cc690f1d50cc..970c1faf1e14d7e7092cacc3e1e733c55cb58115 100644 --- a/apps/server/scripts/record-claude-agent-sdk-replay-fixture.ts +++ b/apps/server/scripts/record-claude-agent-sdk-replay-fixture.ts @@ -13,9 +13,9 @@ import { claudeRuntimeQueryPolicyForRuntimePolicy } from "../src/orchestration-v import { ProviderAdapterV2RuntimePolicy, type ProviderAdapterV2RuntimePolicy as ProviderAdapterV2RuntimePolicyType, -} from "../src/orchestration-v2/ProviderAdapter.ts"; +} from "@t3tools/provider-core/server/ProviderAdapter"; import type { RuntimePolicyV2Override } from "../src/orchestration-v2/RuntimePolicy.ts"; -import { makeCheckpointWorkspace } from "../src/orchestration-v2/testkit/ReplayFixtureWorkspace.ts"; +import { makeCheckpointWorkspace } from "@t3tools/provider-testing/replayWorkspace"; import { CLAUDE_MODEL_SELECTION } from "../src/orchestration-v2/testkit/fixtures/shared.ts"; import { MESSAGE_STEERING_INITIAL_PROMPT, diff --git a/apps/server/scripts/record-cursor-agent-sdk-replay-fixture.ts b/apps/server/scripts/record-cursor-agent-sdk-replay-fixture.ts index 1ccfb13c1bc5b5103baba681dbee08c7ba58f8a2..0f50f11ba345b9ce46aba7be5971a9ea443e8f6d 100644 --- a/apps/server/scripts/record-cursor-agent-sdk-replay-fixture.ts +++ b/apps/server/scripts/record-cursor-agent-sdk-replay-fixture.ts @@ -15,7 +15,7 @@ import { recordCursorAgentSdkReplayTranscript, type CursorAgentSdkReplayTranscript, } from "../src/orchestration-v2/Adapters/CursorAdapterV2.testkit.ts"; -import { checkpointWorkspace } from "../src/orchestration-v2/testkit/ReplayFixtureWorkspace.ts"; +import { checkpointWorkspace } from "@t3tools/provider-testing/replayWorkspace"; import { CURSOR_MODEL_SELECTION, MESSAGE_STEERING_INITIAL_PROMPT, diff --git a/apps/server/scripts/record-grok-acp-replay-fixture.ts b/apps/server/scripts/record-grok-acp-replay-fixture.ts index cd384c0db7c090c8c24c6f85700e2a33499ccb21..5623b45eda8c0781c221c7171420e6323eb2b382 100644 --- a/apps/server/scripts/record-grok-acp-replay-fixture.ts +++ b/apps/server/scripts/record-grok-acp-replay-fixture.ts @@ -32,8 +32,8 @@ import { makeGrokAdapterV2, } from "../src/orchestration-v2/Adapters/GrokAdapterV2.ts"; import { ACP_PROTOCOL } from "../src/orchestration-v2/Adapters/AcpAdapterV2.ts"; -import * as IdAllocator from "../src/orchestration-v2/IdAllocator.ts"; -import type { ProviderAdapterV2SessionRuntime } from "../src/orchestration-v2/ProviderAdapter.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; +import type { ProviderAdapterV2SessionRuntime } from "@t3tools/provider-core/server/ProviderAdapter"; import * as ProviderContinuationRequests from "../src/orchestration-v2/ProviderContinuationRequests.ts"; import * as ProviderAdapterRegistry from "../src/orchestration-v2/ProviderAdapterRegistry.ts"; import { provideDeterministicTestRuntime } from "../src/orchestration-v2/testkit/DeterministicRuntime.ts"; @@ -42,7 +42,7 @@ import { materializeFixtureInput } from "../src/orchestration-v2/testkit/fixture import { runOrchestratorV2Scenario } from "../src/orchestration-v2/testkit/OrchestratorScenario.ts"; import { makeReplayServerConfig } from "../src/orchestration-v2/testkit/ProviderReplayHarness.ts"; import * as ProviderReplayHarness from "../src/orchestration-v2/testkit/ProviderReplayHarness.ts"; -import { checkpointWorkspace } from "../src/orchestration-v2/testkit/ReplayFixtureWorkspace.ts"; +import { checkpointWorkspace } from "@t3tools/provider-testing/replayWorkspace"; import { makeGrokAcpRuntime } from "../src/provider/acp/GrokAcpSupport.ts"; import { buildRuntimeInstructions } from "../src/provider/RuntimeInstructions.ts"; diff --git a/apps/server/scripts/record-muse-msp-replay-fixture.ts b/apps/server/scripts/record-muse-msp-replay-fixture.ts index 53572e50837da89bcc0a9cf1e1fca4b4fd9c3a30..dde469487be077407738b0de633fab8cfef08c71 100644 --- a/apps/server/scripts/record-muse-msp-replay-fixture.ts +++ b/apps/server/scripts/record-muse-msp-replay-fixture.ts @@ -32,18 +32,18 @@ import { museRecordLabel, MuseOrchestratorReplayHarness, } from "../src/orchestration-v2/Adapters/MuseAdapterV2.testkit.ts"; -import * as IdAllocator from "../src/orchestration-v2/IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import { parseMuseVersion } from "../src/provider/museMaintenance.ts"; import { makeMuseEnvironment, museServeArgs } from "../src/provider/museSdk.ts"; import { provideDeterministicTestRuntime } from "../src/orchestration-v2/testkit/DeterministicRuntime.ts"; import { ORCHESTRATOR_REPLAY_FIXTURES } from "../src/orchestration-v2/testkit/fixtures/index.ts"; import { materializeFixtureInput } from "../src/orchestration-v2/testkit/fixtures/shared.ts"; import { runOrchestratorV2ProviderReplayScenario } from "../src/orchestration-v2/testkit/ProviderReplayHarness.ts"; -import { materializeReplayTranscriptWorkspace } from "../src/orchestration-v2/testkit/ReplayTranscriptNdjson.ts"; +import { materializeReplayTranscriptWorkspace } from "@t3tools/provider-testing/replayTranscript"; import { checkpointWorkspace, makeCheckpointWorkspace, -} from "../src/orchestration-v2/testkit/ReplayFixtureWorkspace.ts"; +} from "@t3tools/provider-testing/replayWorkspace"; const CLOCK_TICK = Duration.millis(20); diff --git a/apps/server/scripts/record-pi-rpc-replay-fixture.ts b/apps/server/scripts/record-pi-rpc-replay-fixture.ts index 32d0dc7c7560cf74360972b2f50bf5ba3bfe8e8f..8ea04f8ada6229c4d2f4886716d5fce6c866856a 100644 --- a/apps/server/scripts/record-pi-rpc-replay-fixture.ts +++ b/apps/server/scripts/record-pi-rpc-replay-fixture.ts @@ -30,7 +30,7 @@ import { } from "../src/orchestration-v2/Adapters/PiAdapterV2.testkit.ts"; import * as PiAdapterV2Testkit from "../src/orchestration-v2/Adapters/PiAdapterV2.testkit.ts"; import { PI_PROVIDER } from "../src/orchestration-v2/Adapters/PiAdapterV2.ts"; -import * as IdAllocator from "../src/orchestration-v2/IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import { provideDeterministicTestRuntime } from "../src/orchestration-v2/testkit/DeterministicRuntime.ts"; import { ORCHESTRATOR_REPLAY_FIXTURES } from "../src/orchestration-v2/testkit/fixtures/index.ts"; import { materializeFixtureInput } from "../src/orchestration-v2/testkit/fixtures/shared.ts"; @@ -38,7 +38,7 @@ import { runOrchestratorV2ProviderReplayScenario } from "../src/orchestration-v2 import { checkpointWorkspace, makeCheckpointWorkspace, -} from "../src/orchestration-v2/testkit/ReplayFixtureWorkspace.ts"; +} from "@t3tools/provider-testing/replayWorkspace"; /** * Keeps the user's skills, templates and context files out of the recording. diff --git a/apps/server/scripts/threadTitleEvaluationCases.ts b/apps/server/scripts/threadTitleEvaluationCases.ts index 02d8fecbe4a07c99289cc54f1a26ccc3fd337a0c..c8c4322d5447143387b8cc2258b8080abfd2ac0a 100644 --- a/apps/server/scripts/threadTitleEvaluationCases.ts +++ b/apps/server/scripts/threadTitleEvaluationCases.ts @@ -1,4 +1,4 @@ -import type { ThreadTitleMessage } from "../src/textGeneration/ThreadTitleContext.ts"; +import type { ThreadTitleMessage } from "@t3tools/provider-core/server/threadTitleContext"; // Public PR subjects and existing title scenarios. Repeated text adds context pressure. export const threadTitleEvaluationCases = [ diff --git a/apps/server/src/assets/AssetAccess.ts b/apps/server/src/assets/AssetAccess.ts index 5c0596237b7ebeecc2dbefc00d37713d93c581b0..b9344451e64f4c0d044f43f268f6d843d9c32eca 100644 --- a/apps/server/src/assets/AssetAccess.ts +++ b/apps/server/src/assets/AssetAccess.ts @@ -53,7 +53,7 @@ import * as ServerSecretStore from "../auth/ServerSecretStore.ts"; import { parseAttachmentFileExtension, resolveAttachmentPathById } from "../attachmentStore.ts"; import * as ServerConfig from "../config.ts"; import * as Orchestrator from "../orchestration-v2/Orchestrator.ts"; -import { expandHomePathWith } from "../pathExpansion.ts"; +import { expandHomePathWith } from "@t3tools/provider-core/server/pathExpansion"; import * as ProjectFaviconResolver from "../project/ProjectFaviconResolver.ts"; import * as WorkspacePaths from "../workspace/WorkspacePaths.ts"; import * as NativeAppIconResolver from "./NativeAppIconResolver.ts"; diff --git a/apps/server/src/mcp/McpSessionRegistry.ts b/apps/server/src/mcp/McpSessionRegistry.ts index f90d344efaff2521c48f48211efa6175954bef90..f1e027f9eb85f51e8f7b40a15aeb90cb7f3b786d 100644 --- a/apps/server/src/mcp/McpSessionRegistry.ts +++ b/apps/server/src/mcp/McpSessionRegistry.ts @@ -10,7 +10,7 @@ import * as NetAddress from "effect/net/NetAddress"; import * as ServerEnvironment from "../environment/ServerEnvironment.ts"; import * as McpInvocationContext from "./McpInvocationContext.ts"; -import * as McpProviderSession from "./McpProviderSession.ts"; +import * as McpProviderSession from "@t3tools/provider-core/server/mcpSession"; export interface McpCredentialRequest { readonly threadId: ThreadId; diff --git a/apps/server/src/mcp/McpToolAccess.race.test.ts b/apps/server/src/mcp/McpToolAccess.race.test.ts index b29d81a4948eb121ae8a596c2947f7a657282cf8..52458c8401e89f697e0359113be559f259b52ab9 100644 --- a/apps/server/src/mcp/McpToolAccess.race.test.ts +++ b/apps/server/src/mcp/McpToolAccess.race.test.ts @@ -19,7 +19,7 @@ import { DispatchModeLimit } from "../orchestration-v2/DispatchModeLimit.ts"; import { CodexProviderCapabilitiesV2 } from "../orchestration-v2/Adapters/CodexAdapterV2.ts"; import * as Orchestrator from "../orchestration-v2/Orchestrator.ts"; import * as ProjectionStore from "../orchestration-v2/ProjectionStore.ts"; -import type { ProviderAdapterV2Shape } from "../orchestration-v2/ProviderAdapter.ts"; +import type { ProviderAdapterV2Shape } from "@t3tools/provider-core/server/ProviderAdapter"; import * as ProviderAdapterRegistry from "../orchestration-v2/ProviderAdapterRegistry.ts"; import * as ThreadManagement from "../orchestration-v2/ThreadManagementService.ts"; import * as ProviderReplayHarness from "../orchestration-v2/testkit/ProviderReplayHarness.ts"; diff --git a/apps/server/src/mcp/OrchestratorMcpService.test.ts b/apps/server/src/mcp/OrchestratorMcpService.test.ts index 18b444b851774c162575fe281cd69dce6010d802..eaa776173af33c462e2f4727852c4cdbe0d2fee2 100644 --- a/apps/server/src/mcp/OrchestratorMcpService.test.ts +++ b/apps/server/src/mcp/OrchestratorMcpService.test.ts @@ -28,7 +28,7 @@ import { OrchestratorProjectionError, OrchestratorThreadAboveModeLimitError, } from "../orchestration-v2/Orchestrator.ts"; -import type { ProviderAdapterV2Shape } from "../orchestration-v2/ProviderAdapter.ts"; +import type { ProviderAdapterV2Shape } from "@t3tools/provider-core/server/ProviderAdapter"; import * as ProviderAdapterRegistry from "../orchestration-v2/ProviderAdapterRegistry.ts"; import * as ThreadManagementService from "../orchestration-v2/ThreadManagementService.ts"; import * as ProviderRegistry from "../provider/ProviderRegistry.ts"; diff --git a/apps/server/src/mcp/OrchestratorMcpToolkit.integration.test.ts b/apps/server/src/mcp/OrchestratorMcpToolkit.integration.test.ts index cfca51b629c889c53fb3f76b9a97e7d6710e560b..496c6260d9b49dea4a70518209023065f364a4e1 100644 --- a/apps/server/src/mcp/OrchestratorMcpToolkit.integration.test.ts +++ b/apps/server/src/mcp/OrchestratorMcpToolkit.integration.test.ts @@ -62,15 +62,15 @@ import { ProviderAdapterProtocolError, type ProviderAdapterV2Shape, type ProviderAdapterV2TurnInput, -} from "../orchestration-v2/ProviderAdapter.ts"; +} from "@t3tools/provider-core/server/ProviderAdapter"; import * as ProviderAdapterRegistry from "../orchestration-v2/ProviderAdapterRegistry.ts"; import * as ProviderContinuationRequests from "../orchestration-v2/ProviderContinuationRequests.ts"; -import { checkpointWorkspace } from "../orchestration-v2/testkit/ReplayFixtureWorkspace.ts"; +import { checkpointWorkspace } from "@t3tools/provider-testing/replayWorkspace"; import * as ProviderReplayHarness from "../orchestration-v2/testkit/ProviderReplayHarness.ts"; import { decodeProviderReplayNdjson, materializeReplayTranscriptWorkspace, -} from "../orchestration-v2/testkit/ReplayTranscriptNdjson.ts"; +} from "@t3tools/provider-testing/replayTranscript"; import * as ProviderRegistryMock from "../provider/testUtils/providerRegistryMock.ts"; import * as ProjectService from "../project/ProjectService.ts"; import * as ScheduledTaskService from "../scheduledTasks/ScheduledTaskService.ts"; diff --git a/apps/server/src/mcpApps/McpAppRequests.test.ts b/apps/server/src/mcpApps/McpAppRequests.test.ts index 1fdc8e0c50cafe94f73035beff08b0cc16a49362..ce2d6428091c0e251e55ea8d16f81c4847246c73 100644 --- a/apps/server/src/mcpApps/McpAppRequests.test.ts +++ b/apps/server/src/mcpApps/McpAppRequests.test.ts @@ -17,7 +17,7 @@ import * as Orchestrator from "../orchestration-v2/Orchestrator.ts"; import type { ProviderAdapterV2McpApps, ProviderAdapterV2SessionRuntime, -} from "../orchestration-v2/ProviderAdapter.ts"; +} from "@t3tools/provider-core/server/ProviderAdapter"; import * as ProviderSessionManager from "../orchestration-v2/ProviderSessionManager.ts"; import * as ThreadManagementService from "../orchestration-v2/ThreadManagementService.ts"; import * as McpAppModelContext from "./McpAppModelContext.ts"; diff --git a/apps/server/src/mcpApps/McpAppRequests.ts b/apps/server/src/mcpApps/McpAppRequests.ts index c95606ccd2156f5df4dff858e02b79b1e4430b52..41902c528aebcac8a502ab30cf70353bcb401a21 100644 --- a/apps/server/src/mcpApps/McpAppRequests.ts +++ b/apps/server/src/mcpApps/McpAppRequests.ts @@ -24,7 +24,7 @@ import * as Orchestrator from "../orchestration-v2/Orchestrator.ts"; import type { ProviderAdapterV2McpApps, ProviderAdapterV2McpTool, -} from "../orchestration-v2/ProviderAdapter.ts"; +} from "@t3tools/provider-core/server/ProviderAdapter"; import * as ProviderSessionManager from "../orchestration-v2/ProviderSessionManager.ts"; import * as ThreadManagementService from "../orchestration-v2/ThreadManagementService.ts"; import * as McpAppModelContext from "./McpAppModelContext.ts"; diff --git a/apps/server/src/orchestration-v2/Adapters/AcpAdapterV2.test.ts b/apps/server/src/orchestration-v2/Adapters/AcpAdapterV2.test.ts index dfefe387a58a39bece9ea0a6e8b6d30386a6cbc1..c6ad1fe57e719b9c48926fd72a855713b64e38ac 100644 --- a/apps/server/src/orchestration-v2/Adapters/AcpAdapterV2.test.ts +++ b/apps/server/src/orchestration-v2/Adapters/AcpAdapterV2.test.ts @@ -55,7 +55,7 @@ import type * as EffectAcpProtocol from "effect-acp/protocol"; import type * as EffectAcpSchema from "effect-acp/compat"; import * as ServerConfig from "../../config.ts"; -import * as McpProviderSession from "../../mcp/McpProviderSession.ts"; +import * as McpProviderSession from "@t3tools/provider-core/server/mcpSession"; import * as AcpSessionRuntime from "../../provider/acp/AcpSessionRuntime.ts"; import { extractXAiAcpSubagentEndNotice, @@ -64,13 +64,13 @@ import { normalizeXAiAcpToolCallState, registerXAiBackgroundTaskTracking, } from "../../provider/acp/XAiAcpExtension.ts"; -import * as IdAllocator from "../IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import { ProviderAdapterProtocolError, ProviderAdapterV2RuntimePolicy, type ProviderAdapterV2Event, type ProviderAdapterV2TurnInput, -} from "../ProviderAdapter.ts"; +} from "@t3tools/provider-core/server/ProviderAdapter"; import type { ProviderContinuationRequest } from "../ProviderContinuationRequests.ts"; import { AcpProviderCapabilitiesV2, diff --git a/apps/server/src/orchestration-v2/Adapters/AcpAdapterV2.testkit.ts b/apps/server/src/orchestration-v2/Adapters/AcpAdapterV2.testkit.ts index cf9c20e2860ab8d6d1934fc64f37f07bb12d4e10..960ac6f57f011cd369d17f3110d1684e5a5b3d44 100644 --- a/apps/server/src/orchestration-v2/Adapters/AcpAdapterV2.testkit.ts +++ b/apps/server/src/orchestration-v2/Adapters/AcpAdapterV2.testkit.ts @@ -14,7 +14,7 @@ import { ChildProcessSpawner } from "effect/process"; import * as EffectAcpErrors from "effect-acp/errors"; import * as AcpSessionRuntime from "../../provider/acp/AcpSessionRuntime.ts"; -import type { ProviderReplayGate } from "../testkit/ProviderReplayGate.testkit.ts"; +import type { ProviderReplayGate } from "@t3tools/provider-testing/replayGate"; import { ACP_PROTOCOL, type AcpAdapterV2RuntimeInput } from "./AcpAdapterV2.ts"; export const AcpReplayTranscript = Schema.Struct({ diff --git a/apps/server/src/orchestration-v2/Adapters/AcpAdapterV2.ts b/apps/server/src/orchestration-v2/Adapters/AcpAdapterV2.ts index 7fa7b4874d8fe0fcd2ef3854887b5718a33c52bd..0c8332743b1522e5ddd5420ccc2477ea5ef9c0f2 100644 --- a/apps/server/src/orchestration-v2/Adapters/AcpAdapterV2.ts +++ b/apps/server/src/orchestration-v2/Adapters/AcpAdapterV2.ts @@ -63,8 +63,8 @@ import { makeAcpMcpOverAcpBridge, type AcpMcpOverAcpBridge, } from "../../mcp/AcpMcpOverAcpBridge.ts"; -import { mcpToolPresentation } from "../../provider/McpToolPresentation.ts"; -import * as McpProviderSession from "../../mcp/McpProviderSession.ts"; +import { mcpToolPresentation } from "@t3tools/provider-core/server/mcpToolPresentation"; +import * as McpProviderSession from "@t3tools/provider-core/server/mcpSession"; import { applyAcpAgentTerminalUpdate, acpContentBlockDisplayText, @@ -97,17 +97,20 @@ import * as AcpSessionRuntime from "../../provider/acp/AcpSessionRuntime.ts"; import { t3AcpPromptWithInstructions, type T3AcpInstructionState, -} from "../../provider/T3OrchestrationInstructions.ts"; +} from "@t3tools/provider-core/server/orchestrationInstructions"; import { buildRuntimeInstructions } from "../../provider/RuntimeInstructions.ts"; -import * as IdAllocator from "../IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import { type ProviderContinuationRequest } from "../ProviderContinuationRequests.ts"; import { type BackgroundWork, type BackgroundWorkReport, backgroundWorkNotification, } from "../Notification.ts"; -import { makeProviderFailure, makeProviderRetryTurnItem } from "../ProviderFailure.ts"; -import { acpSelectionTransition } from "../ProviderSelectionTransition.ts"; +import { + makeProviderFailure, + makeProviderRetryTurnItem, +} from "@t3tools/provider-core/server/failure"; +import { acpSelectionTransition } from "@t3tools/provider-core/server/selectionTransition"; import { isProviderNativeImageAttachment, providerMessageTextWithAttachmentPaths, @@ -117,7 +120,7 @@ import { makeSubagentConversationArtifacts, subagentThreadTitle, } from "../SubagentProjection.ts"; -import * as ProviderAdapter from "../ProviderAdapter.ts"; +import * as ProviderAdapter from "@t3tools/provider-core/server/ProviderAdapter"; export const ACP_PROTOCOL = "acp.ndjson-jsonrpc" as const; diff --git a/apps/server/src/orchestration-v2/Adapters/AcpRegistryAdapterV2.test.ts b/apps/server/src/orchestration-v2/Adapters/AcpRegistryAdapterV2.test.ts index 140476f4fa27cb0dcd06c6327bb134e2e0acbe89..85ae7368ee676e7a4cc50c08ceb20888ddcc6238 100644 --- a/apps/server/src/orchestration-v2/Adapters/AcpRegistryAdapterV2.test.ts +++ b/apps/server/src/orchestration-v2/Adapters/AcpRegistryAdapterV2.test.ts @@ -23,13 +23,13 @@ import type { import * as AcpRegistrySupport from "../../provider/acp/AcpRegistrySupport.ts"; import { ACP_SESSION_MODE_OPTION_ID } from "../../provider/acp/AcpSessionConfig.ts"; import * as AcpSessionRuntime from "../../provider/acp/AcpSessionRuntime.ts"; -import * as IdAllocator from "../IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import { decodeAcpReplayTranscript, makeAcpReplayCompletenessAssertion, makeAcpReplayRuntime, } from "./AcpAdapterV2.testkit.ts"; -import { ProviderAdapterV2RuntimePolicy } from "../ProviderAdapter.ts"; +import { ProviderAdapterV2RuntimePolicy } from "@t3tools/provider-core/server/ProviderAdapter"; import { BUILT_IN_PROVIDER_ADAPTER_DRIVER_KINDS_V2 } from "../builtInProviderAdapterDrivers.ts"; import { ACP_REGISTRY_PROVIDER, diff --git a/apps/server/src/orchestration-v2/Adapters/AcpRegistryAdapterV2.testkit.ts b/apps/server/src/orchestration-v2/Adapters/AcpRegistryAdapterV2.testkit.ts index 4289d0314b38a11d2eba694d98a098e84c39e229..7d829741862dbe9cae3d6546b4d608a1dda5a860 100644 --- a/apps/server/src/orchestration-v2/Adapters/AcpRegistryAdapterV2.testkit.ts +++ b/apps/server/src/orchestration-v2/Adapters/AcpRegistryAdapterV2.testkit.ts @@ -10,9 +10,9 @@ import * as Schema from "effect/Schema"; import { ChildProcessSpawner } from "effect/process"; import * as ServerConfig from "../../config.ts"; -import * as IdAllocator from "../IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import * as ProviderAdapterRegistry from "../ProviderAdapterRegistry.ts"; -import type { ProviderReplayGate } from "../testkit/ProviderReplayGate.testkit.ts"; +import type { ProviderReplayGate } from "@t3tools/provider-testing/replayGate"; import type { OrchestratorV2ProviderReplayHarness } from "../testkit/ProviderReplayHarness.ts"; import { makeReplayServerConfig } from "../testkit/ProviderReplayHarness.ts"; import { diff --git a/apps/server/src/orchestration-v2/Adapters/AcpRegistryAdapterV2.ts b/apps/server/src/orchestration-v2/Adapters/AcpRegistryAdapterV2.ts index be73eaec681928d3188a66ded3ac07d580a8e6e4..f1a1ef3a583f2795e942deb4b65456bd60c6a5ed 100644 --- a/apps/server/src/orchestration-v2/Adapters/AcpRegistryAdapterV2.ts +++ b/apps/server/src/orchestration-v2/Adapters/AcpRegistryAdapterV2.ts @@ -32,14 +32,14 @@ import * as AcpRegistryRuntimeCoordinator from "../../provider/acp/AcpRegistryRu import * as AcpSessionRuntime from "../../provider/acp/AcpSessionRuntime.ts"; import { makeAcpNativeLoggerFactory } from "../../provider/acp/AcpNativeLogging.ts"; import * as ProviderEventLoggers from "../../provider/ProviderEventLoggers.ts"; -import { mergeProviderInstanceEnvironment } from "../../provider/ProviderInstanceEnvironment.ts"; -import * as IdAllocator from "../IdAllocator.ts"; -import { makeProviderFailure } from "../ProviderFailure.ts"; +import { mergeProviderInstanceEnvironment } from "@t3tools/provider-core/server/instanceEnvironment"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; +import { makeProviderFailure } from "@t3tools/provider-core/server/failure"; import { ProviderAdapterDriverCreateError, type ProviderAdapterDriver, type ProviderAdapterDriverCreateInput, -} from "../ProviderAdapterDriver.ts"; +} from "@t3tools/provider-core/server/adapterDriver"; import { AcpProviderCapabilitiesV2, makeAcpAdapterV2, diff --git a/apps/server/src/orchestration-v2/Adapters/AntigravityAdapterV2.test.ts b/apps/server/src/orchestration-v2/Adapters/AntigravityAdapterV2.test.ts index 6905e72fafb56291836368db81571239728c5b52..ed00f33728b7c99dac368810cf834ce14be45d92 100644 --- a/apps/server/src/orchestration-v2/Adapters/AntigravityAdapterV2.test.ts +++ b/apps/server/src/orchestration-v2/Adapters/AntigravityAdapterV2.test.ts @@ -25,8 +25,8 @@ import type * as EffectAcpSchema from "effect-acp/compat"; import * as ServerConfig from "../../config.ts"; import type * as AcpSessionRuntime from "../../provider/acp/AcpSessionRuntime.ts"; import { makeAntigravityAcpRuntime } from "../../provider/acp/AntigravityAcpSupport.ts"; -import * as IdAllocator from "../IdAllocator.ts"; -import { ProviderAdapterV2RuntimePolicy } from "../ProviderAdapter.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; +import { ProviderAdapterV2RuntimePolicy } from "@t3tools/provider-core/server/ProviderAdapter"; import { makeAntigravityAcpAdapterFlavor, makeAntigravityAdapterV2, diff --git a/apps/server/src/orchestration-v2/Adapters/AntigravityAdapterV2.ts b/apps/server/src/orchestration-v2/Adapters/AntigravityAdapterV2.ts index 1ee304556cc1653070a5136cf4fc84ac7a130ea4..3d8f8f75091a7a62f500b06dc285ca956a434869 100644 --- a/apps/server/src/orchestration-v2/Adapters/AntigravityAdapterV2.ts +++ b/apps/server/src/orchestration-v2/Adapters/AntigravityAdapterV2.ts @@ -34,7 +34,7 @@ import { makeAntigravityUserInputResponse, normalizeAntigravityToolCall, } from "../../provider/acp/AntigravityProtocol.ts"; -import type { IdAllocatorV2 } from "../IdAllocator.ts"; +import type { IdAllocatorV2 } from "@t3tools/provider-core/server/IdAllocator"; import { AcpProviderCapabilitiesV2, makeAcpAdapterV2, diff --git a/apps/server/src/orchestration-v2/Adapters/ClaudeAdapterV2.test.ts b/apps/server/src/orchestration-v2/Adapters/ClaudeAdapterV2.test.ts index 595fe28b1b9e54141d00b9c3cff1f04d11e4d3da..5273c37d7d68bfb97010c3ace17562c63a6a1362 100644 --- a/apps/server/src/orchestration-v2/Adapters/ClaudeAdapterV2.test.ts +++ b/apps/server/src/orchestration-v2/Adapters/ClaudeAdapterV2.test.ts @@ -52,7 +52,7 @@ import { SpawnExecutableResolution } from "@t3tools/shared/shell"; import { attachmentRelativePath } from "../../attachmentStore.ts"; import * as ServerConfig from "../../config.ts"; -import * as McpProviderSession from "../../mcp/McpProviderSession.ts"; +import * as McpProviderSession from "@t3tools/provider-core/server/mcpSession"; import { PreviewControlsToolkit } from "../../mcp/toolkits/previewControls/tools.ts"; import { HtmlToolkit } from "../../mcp/toolkits/html/tools.ts"; import { EnvironmentToolkit } from "../../mcp/toolkits/environment/tools.ts"; @@ -66,11 +66,11 @@ import { ProviderAdapterV2RuntimePolicy, type ProviderAdapterV2Event, type ProviderAdapterV2TurnInput, -} from "../ProviderAdapter.ts"; +} from "@t3tools/provider-core/server/ProviderAdapter"; import type { ProviderContinuationRequest } from "../ProviderContinuationRequests.ts"; -import { makeProviderFailure } from "../ProviderFailure.ts"; +import { makeProviderFailure } from "@t3tools/provider-core/server/failure"; import * as ClaudeAdapterV2 from "./ClaudeAdapterV2.ts"; -import * as IdAllocator from "../IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; const DEFAULT_CLAUDE_SETTINGS = Schema.decodeSync(ClaudeSettings)({}); const AUTO_COMPACT_CLAUDE_SETTINGS = Schema.decodeSync(ClaudeSettings)({ diff --git a/apps/server/src/orchestration-v2/Adapters/ClaudeAdapterV2.testkit.ts b/apps/server/src/orchestration-v2/Adapters/ClaudeAdapterV2.testkit.ts index 3e70e3d9a8ff8ff5e485ce5f4bb8ec8142f0f2c8..cc8a5bef6f5a997167af72168fecac078129019a 100644 --- a/apps/server/src/orchestration-v2/Adapters/ClaudeAdapterV2.testkit.ts +++ b/apps/server/src/orchestration-v2/Adapters/ClaudeAdapterV2.testkit.ts @@ -31,15 +31,15 @@ import { resolveClaudeSdkExecutablePath, } from "../../provider/Drivers/ClaudeExecutable.ts"; import * as ClaudeAdapterV2 from "./ClaudeAdapterV2.ts"; -import * as IdAllocator from "../IdAllocator.ts"; -import { ProviderAdapterDriverCreateError } from "../ProviderAdapterDriver.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; +import { ProviderAdapterDriverCreateError } from "@t3tools/provider-core/server/adapterDriver"; import * as ProviderAdapterRegistry from "../ProviderAdapterRegistry.ts"; -import { randomUuidV4 } from "../RandomUuid.ts"; +import { randomUuidV4 } from "@t3tools/provider-core/server/randomUuid"; import { makeReplayServerConfig, type OrchestratorV2ProviderReplayHarness, } from "../testkit/ProviderReplayHarness.ts"; -import type { ProviderReplayGate } from "../testkit/ProviderReplayGate.testkit.ts"; +import type { ProviderReplayGate } from "@t3tools/provider-testing/replayGate"; export const CLAUDE_AGENT_SDK_REPLAY_PROTOCOL = "claude-agent-sdk.query" as const; /** diff --git a/apps/server/src/orchestration-v2/Adapters/ClaudeAdapterV2.ts b/apps/server/src/orchestration-v2/Adapters/ClaudeAdapterV2.ts index 1ad916ec2548baadf9d21ea1243aaeb18eba9308..17876e430879e23b22e4806d66b4c1fe9ea82d53 100644 --- a/apps/server/src/orchestration-v2/Adapters/ClaudeAdapterV2.ts +++ b/apps/server/src/orchestration-v2/Adapters/ClaudeAdapterV2.ts @@ -90,7 +90,7 @@ import { planClaudeSkillDispatch } from "../../provider/Drivers/ClaudeSkillDispa import { discoverClaudeSkills } from "../../provider/Drivers/ClaudeSkills.ts"; import { compileClaudeModelSelection } from "../../claudeModelOptions.ts"; import * as ServerConfig from "../../config.ts"; -import { expandHomePath } from "../../pathExpansion.ts"; +import { expandHomePath } from "@t3tools/provider-core/server/pathExpansion"; import { claudeSignedOutMessage, makeClaudeEnvironment, @@ -109,22 +109,28 @@ import { claudeRateLimitEventToUpdate, type ClaudeScopedLimitNames, } from "../../provider/claudeUsageLimits.ts"; -import type { ServerProviderShape } from "../../provider/ServerProvider.ts"; -import { mergeProviderInstanceEnvironment } from "../../provider/ProviderInstanceEnvironment.ts"; -import { T3_CODE_ORCHESTRATION_INSTRUCTIONS } from "../../provider/T3OrchestrationInstructions.ts"; +import type { ServerProviderShape } from "@t3tools/provider-core/server/snapshot"; +import { mergeProviderInstanceEnvironment } from "@t3tools/provider-core/server/instanceEnvironment"; +import { T3_CODE_ORCHESTRATION_INSTRUCTIONS } from "@t3tools/provider-core/server/orchestrationInstructions"; import { buildRuntimeInstructions } from "../../provider/RuntimeInstructions.ts"; -import { mcpToolPresentation, normalizeMcpText } from "../../provider/McpToolPresentation.ts"; -import * as McpProviderSession from "../../mcp/McpProviderSession.ts"; -import * as IdAllocator from "../IdAllocator.ts"; -import { makeProviderFailure, makeProviderRetryTurnItem } from "../ProviderFailure.ts"; -import { turnScopedSelectionTransition } from "../ProviderSelectionTransition.ts"; +import { + mcpToolPresentation, + normalizeMcpText, +} from "@t3tools/provider-core/server/mcpToolPresentation"; +import * as McpProviderSession from "@t3tools/provider-core/server/mcpSession"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; +import { + makeProviderFailure, + makeProviderRetryTurnItem, +} from "@t3tools/provider-core/server/failure"; +import { turnScopedSelectionTransition } from "@t3tools/provider-core/server/selectionTransition"; import { providerMessageTextWithAttachmentPaths } from "../AttachmentPrompt.ts"; -import * as ProviderAdapter from "../ProviderAdapter.ts"; +import * as ProviderAdapter from "@t3tools/provider-core/server/ProviderAdapter"; import { ProviderAdapterDriverCreateError, type ProviderAdapterDriver, type ProviderAdapterDriverCreateInput, -} from "../ProviderAdapterDriver.ts"; +} from "@t3tools/provider-core/server/adapterDriver"; import { type BackgroundWorkReport, backgroundWorkNotification } from "../Notification.ts"; import * as ProviderContinuationRequests from "../ProviderContinuationRequests.ts"; import { diff --git a/apps/server/src/orchestration-v2/Adapters/CodexAdapterV2.test.ts b/apps/server/src/orchestration-v2/Adapters/CodexAdapterV2.test.ts index 86281066231068811cc7e6d30aa5a6a911f0e3de..cadf666611434a1082035df473f076e04ef10e80 100644 --- a/apps/server/src/orchestration-v2/Adapters/CodexAdapterV2.test.ts +++ b/apps/server/src/orchestration-v2/Adapters/CodexAdapterV2.test.ts @@ -1,7 +1,7 @@ import * as NodeOS from "node:os"; import { historyResponseItems } from "../ContextHandoffBudget.ts"; -import type { ProviderAdapterV2HistoricalContext } from "../ProviderAdapter.ts"; +import type { ProviderAdapterV2HistoricalContext } from "@t3tools/provider-core/server/ProviderAdapter"; import { makeProviderTextDeltaCoalescer, type ProviderTextDeltaUpdate, @@ -55,10 +55,10 @@ import { ChildProcess, ChildProcessSpawner } from "effect/process"; import packageJson from "../../../package.json" with { type: "json" }; import * as ServerConfig from "../../config.ts"; -import * as McpProviderSession from "../../mcp/McpProviderSession.ts"; +import * as McpProviderSession from "@t3tools/provider-core/server/mcpSession"; import type { EventNdjsonLogger } from "../../provider/EventNdjsonLogger.ts"; import * as ProviderEventLoggers from "../../provider/ProviderEventLoggers.ts"; -import * as IdAllocator from "../IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import * as EffectWorker from "../EffectWorker.ts"; import * as Orchestrator from "../Orchestrator.ts"; import * as ProviderReplayHarness from "../testkit/ProviderReplayHarness.ts"; @@ -69,7 +69,7 @@ import { ProviderAdapterV2RuntimePolicy, type ProviderAdapterV2Event, type ProviderAdapterV2TurnInput, -} from "../ProviderAdapter.ts"; +} from "@t3tools/provider-core/server/ProviderAdapter"; import type { ProviderContinuationRequest } from "../ProviderContinuationRequests.ts"; import * as CodexAdapterV2 from "./CodexAdapterV2.ts"; import { makeReplayServerConfig, withCodexReplayChildMetadata } from "./CodexAdapterV2.testkit.ts"; diff --git a/apps/server/src/orchestration-v2/Adapters/CodexAdapterV2.testkit.ts b/apps/server/src/orchestration-v2/Adapters/CodexAdapterV2.testkit.ts index 403d85afae7da26485d315a653c88ffd95a6d003..0941a1f88e3adeaa88ff8447ef04aecc7f13f915 100644 --- a/apps/server/src/orchestration-v2/Adapters/CodexAdapterV2.testkit.ts +++ b/apps/server/src/orchestration-v2/Adapters/CodexAdapterV2.testkit.ts @@ -14,12 +14,12 @@ import * as Predicate from "effect/Predicate"; import * as Schema from "effect/Schema"; import * as ServerConfig from "../../config.ts"; -import * as IdAllocator from "../IdAllocator.ts"; -import { ProviderAdapterOpenSessionError } from "../ProviderAdapter.ts"; -import { ProviderAdapterDriverCreateError } from "../ProviderAdapterDriver.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; +import { ProviderAdapterOpenSessionError } from "@t3tools/provider-core/server/ProviderAdapter"; +import { ProviderAdapterDriverCreateError } from "@t3tools/provider-core/server/adapterDriver"; import * as ProviderAdapterRegistry from "../ProviderAdapterRegistry.ts"; import type { OrchestratorV2ProviderReplayHarness } from "../testkit/ProviderReplayHarness.ts"; -import type { ProviderReplayGate } from "../testkit/ProviderReplayGate.testkit.ts"; +import type { ProviderReplayGate } from "@t3tools/provider-testing/replayGate"; import * as CodexAdapterV2 from "./CodexAdapterV2.ts"; export class CodexReplayTranscriptDecodeError extends Schema.TaggedError()( diff --git a/apps/server/src/orchestration-v2/Adapters/CodexAdapterV2.ts b/apps/server/src/orchestration-v2/Adapters/CodexAdapterV2.ts index fefc1ece4fc9aabf3247a698f2f7341d543b3695..f87525e9c8f717eb232947da67035ca763c89723 100644 --- a/apps/server/src/orchestration-v2/Adapters/CodexAdapterV2.ts +++ b/apps/server/src/orchestration-v2/Adapters/CodexAdapterV2.ts @@ -12,7 +12,7 @@ import { completeCodexTurnTokenUsage, type CodexTurnTokenUsageState, } from "../../provider/CodexTurnTokenUsage.ts"; -import type { ServerProviderShape } from "../../provider/ServerProvider.ts"; +import type { ServerProviderShape } from "@t3tools/provider-core/server/snapshot"; import type { CodexEffectiveRuntime } from "../../provider/CodexManagedRuntime.ts"; import { buildCodexInitializeParams } from "../../provider/CodexProvider.ts"; import { @@ -87,7 +87,7 @@ import { ChildProcess, ChildProcessSpawner } from "effect/process"; import { resolveAttachmentPath, resolveAttachmentPathById } from "../../attachmentStore.ts"; import { getCodexServiceTierOptionValue } from "../../codexModelOptions.ts"; import { ServerConfig } from "../../config.ts"; -import { expandHomePath } from "../../pathExpansion.ts"; +import { expandHomePath } from "@t3tools/provider-core/server/pathExpansion"; import { buildCodexAdditionalContext, buildCodexDeveloperInstructions, @@ -107,8 +107,8 @@ import { } from "../../provider/EventNdjsonLogger.ts"; import { ProviderEventLoggers } from "../../provider/ProviderEventLoggers.ts"; import { codexAppServerArgs, resolveCodexLaunchArgs } from "../../provider/codexLaunchArgs.ts"; -import { mergeProviderInstanceEnvironment } from "../../provider/ProviderInstanceEnvironment.ts"; -import * as McpProviderSession from "../../mcp/McpProviderSession.ts"; +import { mergeProviderInstanceEnvironment } from "@t3tools/provider-core/server/instanceEnvironment"; +import * as McpProviderSession from "@t3tools/provider-core/server/mcpSession"; import { MCP_APP_EXTENSION_ID, MCP_APP_MIME_TYPE, @@ -120,8 +120,8 @@ import { ProviderAdapterDriverCreateError, type ProviderAdapterDriver, type ProviderAdapterDriverCreateInput, -} from "../ProviderAdapterDriver.ts"; -import { IdAllocatorV2, type IdAllocatorV2Shape } from "../IdAllocator.ts"; +} from "@t3tools/provider-core/server/adapterDriver"; +import { IdAllocatorV2, type IdAllocatorV2Shape } from "@t3tools/provider-core/server/IdAllocator"; import { type ProviderContinuationRequest, ProviderContinuationRequests, @@ -131,8 +131,8 @@ import { makeProviderFailure, makeProviderFailureTurnItem, makeProviderRetryTurnItem, -} from "../ProviderFailure.ts"; -import { turnScopedSelectionTransition } from "../ProviderSelectionTransition.ts"; +} from "@t3tools/provider-core/server/failure"; +import { turnScopedSelectionTransition } from "@t3tools/provider-core/server/selectionTransition"; import { isProviderNativeImageAttachment, providerMessageTextWithAttachmentPaths, @@ -160,7 +160,7 @@ import { type ProviderAdapterV2InterruptInput, type ProviderAdapterV2SteerInput, type ProviderAdapterV2TurnInput, -} from "../ProviderAdapter.ts"; +} from "@t3tools/provider-core/server/ProviderAdapter"; import { makeSubagentChildThread, makeSubagentConversationArtifacts, diff --git a/apps/server/src/orchestration-v2/Adapters/CursorAdapterV2.test.ts b/apps/server/src/orchestration-v2/Adapters/CursorAdapterV2.test.ts index 8b0bdfb98b97301f993261dddf2f7ed51822abeb..cf37340d0e181ae3dc9fcd3f839ba6eeccaaac74 100644 --- a/apps/server/src/orchestration-v2/Adapters/CursorAdapterV2.test.ts +++ b/apps/server/src/orchestration-v2/Adapters/CursorAdapterV2.test.ts @@ -23,9 +23,9 @@ import * as Schema from "effect/Schema"; import * as Stream from "effect/Stream"; import * as ServerConfig from "../../config.ts"; -import * as McpProviderSession from "../../mcp/McpProviderSession.ts"; -import * as IdAllocator from "../IdAllocator.ts"; -import { ProviderAdapterV2RuntimePolicy } from "../ProviderAdapter.ts"; +import * as McpProviderSession from "@t3tools/provider-core/server/mcpSession"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; +import { ProviderAdapterV2RuntimePolicy } from "@t3tools/provider-core/server/ProviderAdapter"; import { cursorMcpServers, cursorRuntimeAgentPolicy, diff --git a/apps/server/src/orchestration-v2/Adapters/CursorAdapterV2.testkit.ts b/apps/server/src/orchestration-v2/Adapters/CursorAdapterV2.testkit.ts index 42ec1f7a8ea4b6b39c7c4ad4aecbeb0618f5e995..a3a72f7411380e5a5d64eac4fe3c0b4af778d706 100644 --- a/apps/server/src/orchestration-v2/Adapters/CursorAdapterV2.testkit.ts +++ b/apps/server/src/orchestration-v2/Adapters/CursorAdapterV2.testkit.ts @@ -20,8 +20,8 @@ import * as PlatformError from "effect/PlatformError"; import * as Schema from "effect/Schema"; import * as ServerConfig from "../../config.ts"; -import * as IdAllocator from "../IdAllocator.ts"; -import { ProviderAdapterDriverCreateError } from "../ProviderAdapterDriver.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; +import { ProviderAdapterDriverCreateError } from "@t3tools/provider-core/server/adapterDriver"; import * as ProviderAdapterRegistry from "../ProviderAdapterRegistry.ts"; import type { OrchestratorV2ProviderReplayHarness } from "../testkit/ProviderReplayHarness.ts"; import * as CursorAgentSdk from "./CursorAgentSdk.ts"; @@ -32,7 +32,7 @@ import { cursorSdkModelSelection, makeCursorAgentOptions, } from "./CursorAdapterV2.ts"; -import type { ProviderAdapterV2RuntimePolicy } from "../ProviderAdapter.ts"; +import type { ProviderAdapterV2RuntimePolicy } from "@t3tools/provider-core/server/ProviderAdapter"; import type { RuntimePolicyV2Override } from "../RuntimePolicy.ts"; const CursorAgentSdkReplayTranscript = Schema.Struct({ diff --git a/apps/server/src/orchestration-v2/Adapters/CursorAdapterV2.ts b/apps/server/src/orchestration-v2/Adapters/CursorAdapterV2.ts index 5ade7c13911b0080e9207f97fe03255af95380a1..077cb6ead3373fe809a69c261339c27835eb5358 100644 --- a/apps/server/src/orchestration-v2/Adapters/CursorAdapterV2.ts +++ b/apps/server/src/orchestration-v2/Adapters/CursorAdapterV2.ts @@ -44,8 +44,8 @@ import * as Stream from "effect/Stream"; import { resolveAttachmentPath } from "../../attachmentStore.ts"; import * as ServerConfig from "../../config.ts"; -import { mcpToolPresentation } from "../../provider/McpToolPresentation.ts"; -import * as McpProviderSession from "../../mcp/McpProviderSession.ts"; +import { mcpToolPresentation } from "@t3tools/provider-core/server/mcpToolPresentation"; +import * as McpProviderSession from "@t3tools/provider-core/server/mcpSession"; import { CursorTransportFailure } from "../../provider/acp/CursorTransportFailure.ts"; import { cursorSdkModelSelection } from "../../provider/cursorSdkModel.ts"; import { @@ -53,22 +53,22 @@ import { hasCursorSkillMention, rewriteCursorSkillMentions, } from "../../provider/Drivers/CursorSkills.ts"; -import { mergeProviderInstanceEnvironment } from "../../provider/ProviderInstanceEnvironment.ts"; -import { t3OrchestrationPromptForFirstRun } from "../../provider/T3OrchestrationInstructions.ts"; +import { mergeProviderInstanceEnvironment } from "@t3tools/provider-core/server/instanceEnvironment"; +import { t3OrchestrationPromptForFirstRun } from "@t3tools/provider-core/server/orchestrationInstructions"; import { buildRuntimeInstructions } from "../../provider/RuntimeInstructions.ts"; -import * as IdAllocator from "../IdAllocator.ts"; -import { makeProviderFailure } from "../ProviderFailure.ts"; -import { turnScopedSelectionTransition } from "../ProviderSelectionTransition.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; +import { makeProviderFailure } from "@t3tools/provider-core/server/failure"; +import { turnScopedSelectionTransition } from "@t3tools/provider-core/server/selectionTransition"; import { isProviderNativeImageAttachment, providerMessageTextWithAttachmentPaths, } from "../AttachmentPrompt.ts"; -import * as ProviderAdapter from "../ProviderAdapter.ts"; +import * as ProviderAdapter from "@t3tools/provider-core/server/ProviderAdapter"; import { ProviderAdapterDriverCreateError, type ProviderAdapterDriver, type ProviderAdapterDriverCreateInput, -} from "../ProviderAdapterDriver.ts"; +} from "@t3tools/provider-core/server/adapterDriver"; import { makeSubagentChildThread, makeSubagentConversationArtifacts, diff --git a/apps/server/src/orchestration-v2/Adapters/GrokAdapterV2.test.ts b/apps/server/src/orchestration-v2/Adapters/GrokAdapterV2.test.ts index 59e09b2b44c06f683fff57e77adc98416198c207..4284de473a17d22bf8f40f395c92a7550af58e0f 100644 --- a/apps/server/src/orchestration-v2/Adapters/GrokAdapterV2.test.ts +++ b/apps/server/src/orchestration-v2/Adapters/GrokAdapterV2.test.ts @@ -25,10 +25,10 @@ import type * as EffectAcpSchema from "effect-acp/compat"; import * as ServerConfig from "../../config.ts"; import * as ProjectStore from "../ProjectStore.ts"; import { buildInitialGrokProviderSnapshot } from "../../provider/GrokProvider.ts"; -import type { ProviderInstance } from "../../provider/ProviderDriver.ts"; +import type { ProviderInstance } from "@t3tools/provider-core/server/driver"; import * as ProviderInstanceRegistry from "../../provider/ProviderInstanceRegistry.ts"; -import * as IdAllocator from "../IdAllocator.ts"; -import { ProviderAdapterV2RuntimePolicy } from "../ProviderAdapter.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; +import { ProviderAdapterV2RuntimePolicy } from "@t3tools/provider-core/server/ProviderAdapter"; import * as RuntimePolicy from "../RuntimePolicy.ts"; import { acpPermissionDisposition } from "../../provider/acp/AcpClientPolicy.ts"; import { diff --git a/apps/server/src/orchestration-v2/Adapters/GrokAdapterV2.testkit.ts b/apps/server/src/orchestration-v2/Adapters/GrokAdapterV2.testkit.ts index 96d0bedab89ace657ea3e0225c282abba8099eb8..30438a421408612394e249132bab6e3000f73ad4 100644 --- a/apps/server/src/orchestration-v2/Adapters/GrokAdapterV2.testkit.ts +++ b/apps/server/src/orchestration-v2/Adapters/GrokAdapterV2.testkit.ts @@ -16,10 +16,10 @@ import { GROK_ACP_INITIALIZE_META, } from "../../provider/acp/GrokAcpSupport.ts"; import { makeXAiPromptCompletionRuntime } from "../../provider/acp/XAiAcpExtension.ts"; -import * as IdAllocator from "../IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import * as ProviderContinuationRequests from "../ProviderContinuationRequests.ts"; import * as ProviderAdapterRegistry from "../ProviderAdapterRegistry.ts"; -import type { ProviderReplayGate } from "../testkit/ProviderReplayGate.testkit.ts"; +import type { ProviderReplayGate } from "@t3tools/provider-testing/replayGate"; import type { OrchestratorV2ProviderReplayHarness } from "../testkit/ProviderReplayHarness.ts"; import { makeReplayServerConfig } from "../testkit/ProviderReplayHarness.ts"; import { diff --git a/apps/server/src/orchestration-v2/Adapters/GrokAdapterV2.ts b/apps/server/src/orchestration-v2/Adapters/GrokAdapterV2.ts index b446e7ff02df64170a0e78997b7f48720131e0fa..5f28bd1b419f43d22f40cb611db1a6141f68475b 100644 --- a/apps/server/src/orchestration-v2/Adapters/GrokAdapterV2.ts +++ b/apps/server/src/orchestration-v2/Adapters/GrokAdapterV2.ts @@ -1,4 +1,4 @@ -import { makeProviderFailure } from "../ProviderFailure.ts"; +import { makeProviderFailure } from "@t3tools/provider-core/server/failure"; import { XAiPromptFailureText, isXAiTaskCompletedWakeNotification, @@ -53,18 +53,18 @@ import { XAiAskUserQuestionRequest, XAiExitPlanModeRequest, } from "../../provider/acp/XAiAcpExtension.ts"; -import { mergeProviderInstanceEnvironment } from "../../provider/ProviderInstanceEnvironment.ts"; +import { mergeProviderInstanceEnvironment } from "@t3tools/provider-core/server/instanceEnvironment"; import { acpPermissionDisposition } from "../../provider/acp/AcpClientPolicy.ts"; import * as AcpSessionRuntime from "../../provider/acp/AcpSessionRuntime.ts"; import * as ProviderEventLoggers from "../../provider/ProviderEventLoggers.ts"; -import * as IdAllocator from "../IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import * as ProviderContinuationRequests from "../ProviderContinuationRequests.ts"; -import * as ProviderAdapter from "../ProviderAdapter.ts"; +import * as ProviderAdapter from "@t3tools/provider-core/server/ProviderAdapter"; import { ProviderAdapterDriverCreateError, type ProviderAdapterDriver, type ProviderAdapterDriverCreateInput, -} from "../ProviderAdapterDriver.ts"; +} from "@t3tools/provider-core/server/adapterDriver"; import { AcpProviderCapabilitiesV2, makeAcpAdapterV2, diff --git a/apps/server/src/orchestration-v2/Adapters/MuseAdapterV2.test.ts b/apps/server/src/orchestration-v2/Adapters/MuseAdapterV2.test.ts index ffc520bed1c917057910d0f25a6046070c2a50f8..a896f876d1ad725abb88e16e56911e87f30d7a73 100644 --- a/apps/server/src/orchestration-v2/Adapters/MuseAdapterV2.test.ts +++ b/apps/server/src/orchestration-v2/Adapters/MuseAdapterV2.test.ts @@ -32,15 +32,15 @@ import * as Schema from "effect/Schema"; import * as Stream from "effect/Stream"; import * as ServerConfig from "../../config.ts"; -import * as McpProviderSession from "../../mcp/McpProviderSession.ts"; +import * as McpProviderSession from "@t3tools/provider-core/server/mcpSession"; import type { MuseItem } from "../../provider/museProtocol.ts"; import type { MuseSdkHost } from "../../provider/museSdk.ts"; -import * as IdAllocator from "../IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import { ProviderAdapterV2RuntimePolicy, type ProviderAdapterV2Event, type ProviderAdapterV2TurnInput, -} from "../ProviderAdapter.ts"; +} from "@t3tools/provider-core/server/ProviderAdapter"; import type { ProviderContinuationRequest } from "../ProviderContinuationRequests.ts"; import { makeMuseAdapterV2, type MuseAdapterV2Options } from "./MuseAdapterV2.ts"; diff --git a/apps/server/src/orchestration-v2/Adapters/MuseAdapterV2.testkit.ts b/apps/server/src/orchestration-v2/Adapters/MuseAdapterV2.testkit.ts index 826179c918286c1c5e09940a6f45b443990167da..182b67c20aad44c5d940db529ed9b0539a2bb9dd 100644 --- a/apps/server/src/orchestration-v2/Adapters/MuseAdapterV2.testkit.ts +++ b/apps/server/src/orchestration-v2/Adapters/MuseAdapterV2.testkit.ts @@ -35,7 +35,7 @@ import { type MuseSdkHost, type MuseSdkHostOptions, } from "../../provider/museSdk.ts"; -import * as IdAllocator from "../IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import * as ProviderAdapterRegistry from "../ProviderAdapterRegistry.ts"; import * as ProviderContinuationRequests from "../ProviderContinuationRequests.ts"; import { diff --git a/apps/server/src/orchestration-v2/Adapters/MuseAdapterV2.ts b/apps/server/src/orchestration-v2/Adapters/MuseAdapterV2.ts index 406ea9cd59ca35e1fb1a3530db7b6e6744f60794..7384afad822af160098e4be665686b454c31c6bd 100644 --- a/apps/server/src/orchestration-v2/Adapters/MuseAdapterV2.ts +++ b/apps/server/src/orchestration-v2/Adapters/MuseAdapterV2.ts @@ -36,7 +36,7 @@ import * as Stream from "effect/Stream"; import { resolveAttachmentPath } from "../../attachmentStore.ts"; import * as ServerConfig from "../../config.ts"; -import * as McpProviderSession from "../../mcp/McpProviderSession.ts"; +import * as McpProviderSession from "@t3tools/provider-core/server/mcpSession"; import { buildRuntimeInstructions } from "../../provider/RuntimeInstructions.ts"; import { museModelCapabilities, @@ -71,7 +71,7 @@ import { providerMessageTextWithAttachmentPaths, isProviderNativeImageAttachment, } from "../AttachmentPrompt.ts"; -import * as IdAllocator from "../IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import { ProviderAdapterEnsureThreadError, ProviderAdapterForkThreadError, @@ -94,11 +94,11 @@ import { type ProviderAdapterV2ThreadSnapshot, type ProviderAdapterV2TurnInput, type ProviderAdapterV2TurnMessage, -} from "../ProviderAdapter.ts"; +} from "@t3tools/provider-core/server/ProviderAdapter"; import { backgroundWorkNotification, type BackgroundWorkReport } from "../Notification.ts"; import type * as ProviderContinuationRequests from "../ProviderContinuationRequests.ts"; -import { makeProviderFailure } from "../ProviderFailure.ts"; -import { turnScopedSelectionTransition } from "../ProviderSelectionTransition.ts"; +import { makeProviderFailure } from "@t3tools/provider-core/server/failure"; +import { turnScopedSelectionTransition } from "@t3tools/provider-core/server/selectionTransition"; import { museItemStatus, museToolPresentation } from "./MuseItemPresentation.ts"; const MUSE_PROVIDER = ProviderDriverKind.make("muse"); diff --git a/apps/server/src/orchestration-v2/Adapters/OpenCode2AdapterV2.test.ts b/apps/server/src/orchestration-v2/Adapters/OpenCode2AdapterV2.test.ts index 7274de8c386f0615b6baad00f3b2adbc1f832e62..1be5940027911252be62b13fca0c56d1b09382c2 100644 --- a/apps/server/src/orchestration-v2/Adapters/OpenCode2AdapterV2.test.ts +++ b/apps/server/src/orchestration-v2/Adapters/OpenCode2AdapterV2.test.ts @@ -41,9 +41,9 @@ import { describe } from "vite-plus/test"; import type { ProviderAdapterV2Event, ProviderAdapterV2SessionRuntime, -} from "../ProviderAdapter.ts"; -import * as McpProviderSession from "../../mcp/McpProviderSession.ts"; -import * as IdAllocator from "../IdAllocator.ts"; +} from "@t3tools/provider-core/server/ProviderAdapter"; +import * as McpProviderSession from "@t3tools/provider-core/server/mcpSession"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import type { ProviderContinuationRequest } from "../ProviderContinuationRequests.ts"; import * as ProviderContinuationRequests from "../ProviderContinuationRequests.ts"; import { OPENCODE_PROVIDER } from "./OpenCodeAdapterV2.ts"; diff --git a/apps/server/src/orchestration-v2/Adapters/OpenCode2AdapterV2.testkit.ts b/apps/server/src/orchestration-v2/Adapters/OpenCode2AdapterV2.testkit.ts index e8fd1a0258f58b250ae2cdb8087dad63b65c24f3..466349cc37ff73e2ecdac5b882cd345b93132768 100644 --- a/apps/server/src/orchestration-v2/Adapters/OpenCode2AdapterV2.testkit.ts +++ b/apps/server/src/orchestration-v2/Adapters/OpenCode2AdapterV2.testkit.ts @@ -23,9 +23,9 @@ import * as UrlParams from "effect/http/UrlParams"; import * as ServerConfig from "../../config.ts"; import * as OpenCode2Client from "../../provider/opencode2/OpenCode2Client.ts"; import * as OpenCode2Server from "../../provider/opencode2/OpenCode2Server.ts"; -import * as IdAllocator from "../IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import * as ProviderAdapterRegistry from "../ProviderAdapterRegistry.ts"; -import type { ProviderReplayGate } from "../testkit/ProviderReplayGate.testkit.ts"; +import type { ProviderReplayGate } from "@t3tools/provider-testing/replayGate"; import { makeReplayServerConfig, type OrchestratorV2ProviderReplayHarness, diff --git a/apps/server/src/orchestration-v2/Adapters/OpenCode2AdapterV2.ts b/apps/server/src/orchestration-v2/Adapters/OpenCode2AdapterV2.ts index 102eb721bb1a67ce4a4bcc3e19a55ebe3f0602c1..ef05da600de1adb8303d921d87dcf3f4428d90e0 100644 --- a/apps/server/src/orchestration-v2/Adapters/OpenCode2AdapterV2.ts +++ b/apps/server/src/orchestration-v2/Adapters/OpenCode2AdapterV2.ts @@ -77,26 +77,26 @@ import { parseOpenCodeModelSlug, type OpenCodeRuntimeError, } from "../../provider/opencodeRuntime.ts"; -import * as McpProviderSession from "../../mcp/McpProviderSession.ts"; +import * as McpProviderSession from "@t3tools/provider-core/server/mcpSession"; import { buildRuntimeInstructions } from "../../provider/RuntimeInstructions.ts"; -import { t3OrchestrationSystemPrompt } from "../../provider/T3OrchestrationInstructions.ts"; +import { t3OrchestrationSystemPrompt } from "@t3tools/provider-core/server/orchestrationInstructions"; import { SKILL_MENTION_PATTERN } from "@t3tools/shared/composerInlineTokens"; import * as KeyedLock from "@t3tools/shared/KeyedLock"; import { getModelSelectionStringOptionValue, modelSelectionsEqual } from "@t3tools/shared/model"; import { causeErrorTag } from "@t3tools/shared/observability"; import { providerMessageTextWithAttachmentPaths } from "../AttachmentPrompt.ts"; -import * as IdAllocator from "../IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import { backgroundWorkNotification, type BackgroundWorkReport } from "../Notification.ts"; import * as ProviderContinuationRequests from "../ProviderContinuationRequests.ts"; -import { makeProviderFailure } from "../ProviderFailure.ts"; +import { makeProviderFailure } from "@t3tools/provider-core/server/failure"; import { makeSubagentChildThread, makeSubagentConversationArtifacts, subagentThreadTitle, } from "../SubagentProjection.ts"; -import * as ProviderAdapter from "../ProviderAdapter.ts"; -import { turnScopedSelectionTransition } from "../ProviderSelectionTransition.ts"; +import * as ProviderAdapter from "@t3tools/provider-core/server/ProviderAdapter"; +import { turnScopedSelectionTransition } from "@t3tools/provider-core/server/selectionTransition"; import { OPENCODE_PROVIDER, openCodePermissionRequestKind } from "./OpenCodeAdapterV2.ts"; import { openCodeToolTurnItem } from "./OpenCodeToolItems.ts"; diff --git a/apps/server/src/orchestration-v2/Adapters/OpenCodeAdapterV2.test.ts b/apps/server/src/orchestration-v2/Adapters/OpenCodeAdapterV2.test.ts index a8e28a377d1aeab338888899d072b0e8230c90a5..c52447fafaeb3a7400aed17f5d334eef3df961be 100644 --- a/apps/server/src/orchestration-v2/Adapters/OpenCodeAdapterV2.test.ts +++ b/apps/server/src/orchestration-v2/Adapters/OpenCodeAdapterV2.test.ts @@ -34,7 +34,7 @@ import * as TestClock from "effect/testing/TestClock"; import * as ServerConfig from "../../config.ts"; import type { EventNdjsonLogger } from "../../provider/EventNdjsonLogger.ts"; import type { OpenCodeRuntimeShape } from "../../provider/opencodeRuntime.ts"; -import * as IdAllocator from "../IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import { advanceOpenCodePromptAdmission, @@ -49,7 +49,7 @@ import { OPENCODE_PROVIDER, reconcileOpenCodePromptAdmissionStatus, } from "./OpenCodeAdapterV2.ts"; -import { ProviderAdapterV2RuntimePolicy } from "../ProviderAdapter.ts"; +import { ProviderAdapterV2RuntimePolicy } from "@t3tools/provider-core/server/ProviderAdapter"; const encodeUnknownJson = Schema.encodeUnknownSync(Schema.fromJsonString(Schema.Unknown)); const OPEN_CODE_TEST_SETTINGS = Schema.decodeSync(OpenCodeSettings)({ diff --git a/apps/server/src/orchestration-v2/Adapters/OpenCodeAdapterV2.testkit.ts b/apps/server/src/orchestration-v2/Adapters/OpenCodeAdapterV2.testkit.ts index ea7deb3846442860b3cd289af3c4b65e0e78efca..aaf50f24a6ac4f32aa2c669e19ca06f90ea56c11 100644 --- a/apps/server/src/orchestration-v2/Adapters/OpenCodeAdapterV2.testkit.ts +++ b/apps/server/src/orchestration-v2/Adapters/OpenCodeAdapterV2.testkit.ts @@ -9,8 +9,8 @@ import * as Schema from "effect/Schema"; import * as ServerConfig from "../../config.ts"; import * as OpenCodeRuntime from "../../provider/opencodeRuntime.ts"; import * as ProviderEventLoggers from "../../provider/ProviderEventLoggers.ts"; -import * as IdAllocator from "../IdAllocator.ts"; -import { ProviderAdapterDriverCreateError } from "../ProviderAdapterDriver.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; +import { ProviderAdapterDriverCreateError } from "@t3tools/provider-core/server/adapterDriver"; import * as ProviderAdapterRegistry from "../ProviderAdapterRegistry.ts"; import { makeReplayServerConfig, diff --git a/apps/server/src/orchestration-v2/Adapters/OpenCodeAdapterV2.ts b/apps/server/src/orchestration-v2/Adapters/OpenCodeAdapterV2.ts index 510a4c859d362e9f037fc3dbbe4bf9cdf15bfcd5..8b3216fbaaa7de419695ccdeaf10b08da51dd942 100644 --- a/apps/server/src/orchestration-v2/Adapters/OpenCodeAdapterV2.ts +++ b/apps/server/src/orchestration-v2/Adapters/OpenCodeAdapterV2.ts @@ -56,28 +56,28 @@ import * as Stream from "effect/Stream"; import { resolveAttachmentPath } from "../../attachmentStore.ts"; import * as ServerConfig from "../../config.ts"; -import { mcpToolPresentation } from "../../provider/McpToolPresentation.ts"; -import * as McpProviderSession from "../../mcp/McpProviderSession.ts"; +import { mcpToolPresentation } from "@t3tools/provider-core/server/mcpToolPresentation"; +import * as McpProviderSession from "@t3tools/provider-core/server/mcpSession"; import type { EventNdjsonLogger } from "../../provider/EventNdjsonLogger.ts"; import * as ProviderEventLoggers from "../../provider/ProviderEventLoggers.ts"; import { structuralProtocolMethod, summarizeNativeProtocolPayload, } from "../../provider/NativeProtocolLogging.ts"; -import { mergeProviderInstanceEnvironment } from "../../provider/ProviderInstanceEnvironment.ts"; -import { t3OrchestrationSystemPrompt } from "../../provider/T3OrchestrationInstructions.ts"; +import { mergeProviderInstanceEnvironment } from "@t3tools/provider-core/server/instanceEnvironment"; +import { t3OrchestrationSystemPrompt } from "@t3tools/provider-core/server/orchestrationInstructions"; import { buildRuntimeInstructions } from "../../provider/RuntimeInstructions.ts"; import * as OpenCodeRuntime from "../../provider/opencodeRuntime.ts"; -import * as IdAllocator from "../IdAllocator.ts"; -import { makeProviderFailure } from "../ProviderFailure.ts"; -import { turnScopedSelectionTransition } from "../ProviderSelectionTransition.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; +import { makeProviderFailure } from "@t3tools/provider-core/server/failure"; +import { turnScopedSelectionTransition } from "@t3tools/provider-core/server/selectionTransition"; import { providerMessageTextWithAttachmentPaths } from "../AttachmentPrompt.ts"; -import * as ProviderAdapter from "../ProviderAdapter.ts"; +import * as ProviderAdapter from "@t3tools/provider-core/server/ProviderAdapter"; import { ProviderAdapterDriverCreateError, type ProviderAdapterDriver, type ProviderAdapterDriverCreateInput, -} from "../ProviderAdapterDriver.ts"; +} from "@t3tools/provider-core/server/adapterDriver"; import { makeSubagentChildThread, subagentThreadTitle } from "../SubagentProjection.ts"; import { openCodeToolTurnItem } from "./OpenCodeToolItems.ts"; diff --git a/apps/server/src/orchestration-v2/Adapters/PiAdapterV2.test.ts b/apps/server/src/orchestration-v2/Adapters/PiAdapterV2.test.ts index 4db9305cd2e6f56b7009ddade32d3559b0ee0766..8789b5268498d8da10f07a722954178964a1f1c7 100644 --- a/apps/server/src/orchestration-v2/Adapters/PiAdapterV2.test.ts +++ b/apps/server/src/orchestration-v2/Adapters/PiAdapterV2.test.ts @@ -33,15 +33,16 @@ import * as TestClock from "effect/testing/TestClock"; import { ChildProcess, ChildProcessSpawner } from "effect/process"; import { HostProcessEnvironment } from "@t3tools/shared/hostProcess"; -import * as ServerConfig from "../../config.ts"; +import { ProviderHost } from "@t3tools/provider-core/server/ProviderHost"; +import { layerTestProviderHost } from "@t3tools/provider-testing/host"; import * as ProviderContinuationRequests from "../ProviderContinuationRequests.ts"; -import * as McpProviderSession from "../../mcp/McpProviderSession.ts"; -import * as IdAllocator from "../IdAllocator.ts"; +import * as McpProviderSession from "@t3tools/provider-core/server/mcpSession"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import { ProviderAdapterV2RuntimePolicy, type ProviderAdapterV2Event, type ProviderAdapterV2SessionRuntime, -} from "../ProviderAdapter.ts"; +} from "@t3tools/provider-core/server/ProviderAdapter"; import { handoffBudget } from "../ContextHandoffBudget.ts"; import { makePiAdapterV2, @@ -51,11 +52,11 @@ import { } from "./PiAdapterV2.ts"; import { makePiRpcConnection, type PiRpcRecord } from "./PiRpc.ts"; -const layerServerConfig = ServerConfig.layerTest(process.cwd(), { - prefix: "t3-pi-v2-adapter-", -}).pipe(Layer.provide(NodeServices.layer)); - -const layerTest = Layer.mergeAll(NodeServices.layer, IdAllocator.layer, layerServerConfig); +const layerTest = Layer.mergeAll( + NodeServices.layer, + IdAllocator.layer, + layerTestProviderHost().pipe(Layer.provide(NodeServices.layer)), +); const decodeJsonLine = Schema.decodeSync(Schema.fromJsonString(Schema.Unknown)); const encodeJsonLine = Schema.encodeSync(Schema.fromJsonString(Schema.Unknown)); @@ -330,7 +331,7 @@ const makeAdapter = Effect.fnUntraced(function* ( continuationRequests?: PiAdapterV2Options["continuationRequests"], ) { const idAllocator = yield* IdAllocator.IdAllocatorV2; - const serverConfig = yield* ServerConfig.ServerConfig; + const host = yield* ProviderHost; const fileSystem = yield* FileSystem.FileSystem; const spawner = forkFake === undefined @@ -363,7 +364,7 @@ const makeAdapter = Effect.fnUntraced(function* ( spawner, fileSystem, idAllocator, - serverConfig, + host, }); }); diff --git a/apps/server/src/orchestration-v2/Adapters/PiAdapterV2.testkit.ts b/apps/server/src/orchestration-v2/Adapters/PiAdapterV2.testkit.ts index c5c4ead2f3e3b3cf9692d781673c51f0f7dd532c..a66a6a2b1a5d35397b85244bf7bf0b28e5852d76 100644 --- a/apps/server/src/orchestration-v2/Adapters/PiAdapterV2.testkit.ts +++ b/apps/server/src/orchestration-v2/Adapters/PiAdapterV2.testkit.ts @@ -30,14 +30,11 @@ import * as Sink from "effect/Sink"; import * as Stream from "effect/Stream"; import { ChildProcess, ChildProcessSpawner } from "effect/process"; -import * as ServerConfig from "../../config.ts"; -import * as IdAllocator from "../IdAllocator.ts"; -import { ProviderAdapterDriverCreateError } from "../ProviderAdapterDriver.ts"; +import { layerTestProviderHost } from "@t3tools/provider-testing/host"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; +import { ProviderAdapterDriverCreateError } from "@t3tools/provider-core/server/adapterDriver"; import * as ProviderAdapterRegistry from "../ProviderAdapterRegistry.ts"; -import { - makeReplayServerConfig, - type OrchestratorV2ProviderReplayHarness, -} from "../testkit/ProviderReplayHarness.ts"; +import type { OrchestratorV2ProviderReplayHarness } from "../testkit/ProviderReplayHarness.ts"; import { PI_PROVIDER, PiAdapterV2Driver } from "./PiAdapterV2.ts"; export const PI_RPC_REPLAY_PROTOCOL = "pi.rpc-jsonl"; @@ -414,10 +411,6 @@ export function layer(input: { readonly launchArgs: string; readonly environment?: ProviderInstanceEnvironment; }) { - const layerServerConfig = Layer.effect( - ServerConfig.ServerConfig, - makeReplayServerConfig(`pi-${input.scenario}`).pipe(Effect.orDie), - ).pipe(Layer.provide(NodeServices.layer)); return ProviderAdapterRegistry.layerFromDrivers({ drivers: [PiAdapterV2Driver], configMap: { @@ -430,7 +423,13 @@ export function layer(input: { }, }).pipe( Layer.provide(input.spawner), - Layer.provide(Layer.mergeAll(layerServerConfig, NodeServices.layer, IdAllocator.layer)), + Layer.provide( + Layer.mergeAll( + layerTestProviderHost().pipe(Layer.provide(NodeServices.layer)), + NodeServices.layer, + IdAllocator.layer, + ), + ), ); } diff --git a/apps/server/src/orchestration-v2/Adapters/PiAdapterV2.ts b/apps/server/src/orchestration-v2/Adapters/PiAdapterV2.ts index b05454aefc126a8d2709d35adf30f32ca4ead05b..520992dbc4e40a65f39e215d4a79f20c8f2f77b8 100644 --- a/apps/server/src/orchestration-v2/Adapters/PiAdapterV2.ts +++ b/apps/server/src/orchestration-v2/Adapters/PiAdapterV2.ts @@ -60,27 +60,29 @@ import * as Semaphore from "effect/Semaphore"; import * as Stream from "effect/Stream"; import { ChildProcessSpawner } from "effect/process"; -import { resolveAttachmentPath } from "../../attachmentStore.ts"; -import * as ServerConfig from "../../config.ts"; -import { mcpToolPresentation } from "../../provider/McpToolPresentation.ts"; -import * as McpProviderSession from "../../mcp/McpProviderSession.ts"; +import { ProviderHost, type ProviderHostShape } from "@t3tools/provider-core/server/ProviderHost"; +import { mcpToolPresentation } from "@t3tools/provider-core/server/mcpToolPresentation"; +import * as McpProviderSession from "@t3tools/provider-core/server/mcpSession"; import { expandPiSkillReference, parsePiCompactCommand, parsePiDiscoveredCommands, type PiCompactCommand, } from "../../provider/PiCommands.ts"; -import { mergeProviderInstanceEnvironment } from "../../provider/ProviderInstanceEnvironment.ts"; -import * as IdAllocator from "../IdAllocator.ts"; -import * as ProviderAdapter from "../ProviderAdapter.ts"; +import { mergeProviderInstanceEnvironment } from "@t3tools/provider-core/server/instanceEnvironment"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; +import * as ProviderAdapter from "@t3tools/provider-core/server/ProviderAdapter"; import * as ProviderContinuationRequests from "../ProviderContinuationRequests.ts"; import { ProviderAdapterDriverCreateError, type ProviderAdapterDriver, type ProviderAdapterDriverCreateInput, -} from "../ProviderAdapterDriver.ts"; -import { makeProviderFailure, makeProviderRetryTurnItem } from "../ProviderFailure.ts"; -import { turnScopedSelectionTransition } from "../ProviderSelectionTransition.ts"; +} from "@t3tools/provider-core/server/adapterDriver"; +import { + makeProviderFailure, + makeProviderRetryTurnItem, +} from "@t3tools/provider-core/server/failure"; +import { turnScopedSelectionTransition } from "@t3tools/provider-core/server/selectionTransition"; import { makePiRpcConnection, parsePiModelSlug, @@ -229,7 +231,7 @@ export interface PiAdapterV2Options { readonly spawner: ChildProcessSpawner.ChildProcessSpawner["Service"]; readonly fileSystem: FileSystem.FileSystem; readonly idAllocator: IdAllocator.IdAllocatorV2["Service"]; - readonly serverConfig: ServerConfig.ServerConfig["Service"]; + readonly host: ProviderHostShape; readonly continuationRequests?: { readonly offer: ( request: ProviderContinuationRequests.ProviderContinuationRequest, @@ -405,7 +407,7 @@ export function makePiAdapterV2( input: ProviderAdapter.ProviderAdapterV2OpenSessionInput, ) { const scope = yield* Effect.scope; - const cwd = input.runtimePolicy.cwd ?? options.serverConfig.cwd; + const cwd = input.runtimePolicy.cwd ?? options.host.paths.cwd; const mcpSession = McpProviderSession.readMcpProviderSession(input.threadId); const provideCacheFs = (effect: Effect.Effect) => effect.pipe( @@ -423,7 +425,7 @@ export function makePiAdapterV2( // hook. Materialize it even when this session has no MCP credential so // Supervised never silently degrades to unrestricted tool execution. const extensionPath = yield* provideCacheFs( - materializePiT3McpExtension(options.serverConfig.providerStatusCacheDir), + materializePiT3McpExtension(options.host.paths.providerStatusCacheDir), ); const resolvedLaunchArgs = resolvePiLaunchArgs(options.settings.launchArgs); if (!resolvedLaunchArgs.ok) { @@ -2335,10 +2337,7 @@ export function makePiAdapterV2( const images: Array<{ type: "image"; data: string; mimeType: string }> = []; const extraLines: Array = []; for (const attachment of attachments) { - const path = resolveAttachmentPath({ - attachmentsDir: options.serverConfig.attachmentsDir, - attachment, - }); + const path = options.host.resolveAttachmentPath(attachment); if (path === null) continue; if (attachment.mimeType.startsWith("image/")) { const bytes = yield* options.fileSystem.readFile(path); @@ -3202,7 +3201,7 @@ export type PiAdapterV2DriverEnv = | ChildProcessSpawner.ChildProcessSpawner | FileSystem.FileSystem | IdAllocator.IdAllocatorV2 - | ServerConfig.ServerConfig; + | ProviderHost; export const PiAdapterV2Driver: ProviderAdapterDriver = { driverKind: PI_DRIVER_KIND, @@ -3214,7 +3213,7 @@ export const PiAdapterV2Driver: ProviderAdapterDriver()("PiRpcError", { operation: Schema.String, diff --git a/apps/server/src/orchestration-v2/Adapters/piT3McpExtensionSource.ts b/apps/server/src/orchestration-v2/Adapters/piT3McpExtensionSource.ts index d5c9f0669125096231bc46ada94ab2d83fba7b1d..e11e953f8433962cf3057f9025463f2ea4f09120 100644 --- a/apps/server/src/orchestration-v2/Adapters/piT3McpExtensionSource.ts +++ b/apps/server/src/orchestration-v2/Adapters/piT3McpExtensionSource.ts @@ -8,7 +8,7 @@ * Do not import t3code modules from the string body. The Pi process resolves * `@earendil-works/pi-coding-agent` and `typebox` from the user's pi install. */ -import { T3_CODE_ORCHESTRATION_INSTRUCTIONS } from "../../provider/T3OrchestrationInstructions.ts"; +import { T3_CODE_ORCHESTRATION_INSTRUCTIONS } from "@t3tools/provider-core/server/orchestrationInstructions"; export const PI_T3_MCP_EXTENSION_FILENAME = "pi-t3-mcp-extension.ts"; diff --git a/apps/server/src/orchestration-v2/Adapters/piT3McpInjection.ts b/apps/server/src/orchestration-v2/Adapters/piT3McpInjection.ts index 9de59156047893c6bdc85d36453d22001fd487d5..5f377782178007f54bf56992c026bef0fd5ab5cb 100644 --- a/apps/server/src/orchestration-v2/Adapters/piT3McpInjection.ts +++ b/apps/server/src/orchestration-v2/Adapters/piT3McpInjection.ts @@ -2,7 +2,7 @@ import { tokenizeCliArgs } from "@t3tools/shared/cliArgs"; import * as Effect from "effect/Effect"; import * as FileSystem from "effect/FileSystem"; -import type { McpProviderSessionConfig } from "../../mcp/McpProviderSession.ts"; +import type { McpProviderSessionConfig } from "@t3tools/provider-core/server/mcpSession"; import { PI_T3_MCP_EXTENSION_FILENAME, PI_T3_MCP_EXTENSION_SOURCE, diff --git a/apps/server/src/orchestration-v2/BackgroundWorkStop.integration.test.ts b/apps/server/src/orchestration-v2/BackgroundWorkStop.integration.test.ts index c1a72d05f6854440d46bab82a74ed5677babea9c..4d4950bcb4b7e6959e8375fff36674507c11cd88 100644 --- a/apps/server/src/orchestration-v2/BackgroundWorkStop.integration.test.ts +++ b/apps/server/src/orchestration-v2/BackgroundWorkStop.integration.test.ts @@ -29,11 +29,11 @@ import type { ProviderAdapterV2InterruptInput, ProviderAdapterV2Shape, ProviderAdapterV2TurnInput, -} from "./ProviderAdapter.ts"; +} from "@t3tools/provider-core/server/ProviderAdapter"; import * as ProviderAdapterRegistry from "./ProviderAdapterRegistry.ts"; import * as ProviderSessionManager from "./ProviderSessionManager.ts"; import * as ProviderReplayHarness from "./testkit/ProviderReplayHarness.ts"; -import { checkpointWorkspace } from "./testkit/ReplayFixtureWorkspace.ts"; +import { checkpointWorkspace } from "@t3tools/provider-testing/replayWorkspace"; const driver = ProviderDriverKind.make("codex"); const instanceId = ProviderInstanceId.make("codex"); diff --git a/apps/server/src/orchestration-v2/CheckpointCaptureService.test.ts b/apps/server/src/orchestration-v2/CheckpointCaptureService.test.ts index 91d197dc82dde0296ba184c306599e0041bae552..bb7619f6a8abd01a9082023ea734a216e8fc2c0c 100644 --- a/apps/server/src/orchestration-v2/CheckpointCaptureService.test.ts +++ b/apps/server/src/orchestration-v2/CheckpointCaptureService.test.ts @@ -28,7 +28,7 @@ import { VcsProcessTimeoutError } from "@t3tools/contracts"; import * as CheckpointService from "./CheckpointService.ts"; import * as CheckpointCaptureService from "./CheckpointCaptureService.ts"; import * as EventSink from "./EventSink.ts"; -import * as IdAllocator from "./IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import * as ProjectionStore from "./ProjectionStore.ts"; const layerProjectionStoreTest = Layer.mergeAll( diff --git a/apps/server/src/orchestration-v2/CheckpointCaptureService.ts b/apps/server/src/orchestration-v2/CheckpointCaptureService.ts index ab34b62367b5991ead2edff3b9aebb23c802344d..6be935c9c23bbbdaae8c23757c01cacb16662b0a 100644 --- a/apps/server/src/orchestration-v2/CheckpointCaptureService.ts +++ b/apps/server/src/orchestration-v2/CheckpointCaptureService.ts @@ -17,7 +17,7 @@ import * as Schema from "effect/Schema"; import * as CheckpointService from "./CheckpointService.ts"; import * as EventSink from "./EventSink.ts"; -import * as IdAllocator from "./IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import * as ProjectionStore from "./ProjectionStore.ts"; export class CheckpointCaptureExecutionError extends Schema.TaggedError()( diff --git a/apps/server/src/orchestration-v2/CheckpointRestoreSafety.test.ts b/apps/server/src/orchestration-v2/CheckpointRestoreSafety.test.ts index 34bf5cce6a5375b37a3d48f4285ee7fc4bc9d273..f86e1b7402d92f8b31a0e6435fd209de946a5ac0 100644 --- a/apps/server/src/orchestration-v2/CheckpointRestoreSafety.test.ts +++ b/apps/server/src/orchestration-v2/CheckpointRestoreSafety.test.ts @@ -20,7 +20,7 @@ import * as CheckpointRollbackService from "./CheckpointRollbackService.ts"; import * as ThreadCommandExecutor from "./ThreadCommandExecutor.ts"; import { CheckpointServiceV2 } from "./CheckpointService.ts"; import { EventSinkV2 } from "./EventSink.ts"; -import * as IdAllocator from "./IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import { ProjectionStoreV2 } from "./ProjectionStore.ts"; import * as ProjectStore from "./ProjectStore.ts"; import { ProviderSessionManagerV2 } from "./ProviderSessionManager.ts"; diff --git a/apps/server/src/orchestration-v2/CheckpointRollbackService.test.ts b/apps/server/src/orchestration-v2/CheckpointRollbackService.test.ts index bb37290363ac7f59690b61caf2f669f3905f9ffe..217a73697133e077d1f0d1ce27d9313412206153 100644 --- a/apps/server/src/orchestration-v2/CheckpointRollbackService.test.ts +++ b/apps/server/src/orchestration-v2/CheckpointRollbackService.test.ts @@ -23,10 +23,10 @@ import * as CheckpointRollbackService from "./CheckpointRollbackService.ts"; import * as ThreadCommandExecutor from "./ThreadCommandExecutor.ts"; import * as KeyedLock from "@t3tools/shared/KeyedLock"; import * as EventSink from "./EventSink.ts"; -import * as IdAllocator from "./IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import * as ProjectionStore from "./ProjectionStore.ts"; import * as ProjectStore from "./ProjectStore.ts"; -import type { ProviderAdapterV2RollbackThreadInput } from "./ProviderAdapter.ts"; +import type { ProviderAdapterV2RollbackThreadInput } from "@t3tools/provider-core/server/ProviderAdapter"; import * as ProviderSessionManager from "./ProviderSessionManager.ts"; import * as RuntimePolicy from "./RuntimePolicy.ts"; diff --git a/apps/server/src/orchestration-v2/CheckpointRollbackService.ts b/apps/server/src/orchestration-v2/CheckpointRollbackService.ts index b1532a74c6dc7d7e12cf7c8da1f1c1f3549568cf..f9747abe2093dc04d92da0985d23e2eb5717142b 100644 --- a/apps/server/src/orchestration-v2/CheckpointRollbackService.ts +++ b/apps/server/src/orchestration-v2/CheckpointRollbackService.ts @@ -20,10 +20,10 @@ import { } from "./CheckpointRestoreSafety.ts"; import { CheckpointServiceV2 } from "./CheckpointService.ts"; import { EventSinkV2 } from "./EventSink.ts"; -import { IdAllocatorV2 } from "./IdAllocator.ts"; +import { IdAllocatorV2 } from "@t3tools/provider-core/server/IdAllocator"; import { ProjectionStoreV2 } from "./ProjectionStore.ts"; import * as ProjectStore from "./ProjectStore.ts"; -import type { ProviderAdapterV2RollbackTarget } from "./ProviderAdapter.ts"; +import type { ProviderAdapterV2RollbackTarget } from "@t3tools/provider-core/server/ProviderAdapter"; import { ProviderSessionManagerV2 } from "./ProviderSessionManager.ts"; import { RuntimePolicyV2 } from "./RuntimePolicy.ts"; import * as ThreadCommandExecutor from "./ThreadCommandExecutor.ts"; diff --git a/apps/server/src/orchestration-v2/CheckpointScopeOwnership.test.ts b/apps/server/src/orchestration-v2/CheckpointScopeOwnership.test.ts index 4935ffb9fbd407d03f80465a6663fb1900f30d61..b29eb33b69a2f26a869b7e36ae55c828fd748c3f 100644 --- a/apps/server/src/orchestration-v2/CheckpointScopeOwnership.test.ts +++ b/apps/server/src/orchestration-v2/CheckpointScopeOwnership.test.ts @@ -16,7 +16,7 @@ import { } from "@t3tools/contracts"; import * as CheckpointDiffQuery from "../checkpointing/CheckpointDiffQuery.ts"; import * as CheckpointStore from "../checkpointing/CheckpointStore.ts"; -import * as IdAllocator from "./IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import { checkpointRefForScopeOrdinal } from "./CheckpointService.ts"; import * as ProjectionStore from "./ProjectionStore.ts"; import * as ThreadManagement from "./ThreadManagementService.ts"; diff --git a/apps/server/src/orchestration-v2/CheckpointService.test.ts b/apps/server/src/orchestration-v2/CheckpointService.test.ts index cef73dd1cbbc076db209678f431529c69539a49c..3bb6d0be84528c4c292f12e47f895e777ae15887 100644 --- a/apps/server/src/orchestration-v2/CheckpointService.test.ts +++ b/apps/server/src/orchestration-v2/CheckpointService.test.ts @@ -16,7 +16,7 @@ import * as Layer from "effect/Layer"; import * as CheckpointStore from "../checkpointing/CheckpointStore.ts"; import * as CheckpointService from "./CheckpointService.ts"; -import * as IdAllocator from "./IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; it.effect.each([false, true, "interrupt"] as const)( "materializes baseline, lookup fails=%s", diff --git a/apps/server/src/orchestration-v2/CheckpointService.ts b/apps/server/src/orchestration-v2/CheckpointService.ts index cb514529349bb288a66a22da68b284729d0f8162..c0bf30311a248a795c0cf1a6ae93004110b4fa74 100644 --- a/apps/server/src/orchestration-v2/CheckpointService.ts +++ b/apps/server/src/orchestration-v2/CheckpointService.ts @@ -21,7 +21,7 @@ import * as Schema from "effect/Schema"; import { parseTurnDiffFilesFromNumstat } from "../checkpointing/Diffs.ts"; import * as CheckpointStore from "../checkpointing/CheckpointStore.ts"; -import * as IdAllocator from "./IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; const CHECKPOINT_REFS_PREFIX = "refs/t3/orchestration-v2/checkpoints"; const ROOT_CHECKPOINT_SCOPE_NAME = "root"; diff --git a/apps/server/src/orchestration-v2/ClaudeAutomaticDelivery.integration.test.ts b/apps/server/src/orchestration-v2/ClaudeAutomaticDelivery.integration.test.ts index a6cac12037e21d3b3a56fb2bd3011486981c74b5..fe4340474bcb82b54b82352ac89d6142909f56bb 100644 --- a/apps/server/src/orchestration-v2/ClaudeAutomaticDelivery.integration.test.ts +++ b/apps/server/src/orchestration-v2/ClaudeAutomaticDelivery.integration.test.ts @@ -31,14 +31,14 @@ import * as SqlitePersistence from "../persistence/Sqlite.ts"; import * as ClaudeAdapterV2 from "./Adapters/ClaudeAdapterV2.ts"; import * as EffectWorker from "./EffectWorker.ts"; import * as EventSink from "./EventSink.ts"; -import * as IdAllocator from "./IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import * as LegacyV1ThreadImporter from "./legacy/LegacyV1ThreadImporter.ts"; import * as Orchestrator from "./Orchestrator.ts"; import * as ProviderAdapterRegistry from "./ProviderAdapterRegistry.ts"; import * as ThreadLaunchService from "./ThreadLaunchService.ts"; import * as ThreadManagementService from "./ThreadManagementService.ts"; import * as ProviderReplayHarness from "./testkit/ProviderReplayHarness.ts"; -import { checkpointWorkspace } from "./testkit/ReplayFixtureWorkspace.ts"; +import { checkpointWorkspace } from "@t3tools/provider-testing/replayWorkspace"; const sessionId = "automatic-delivery-session"; const settings = Schema.decodeSync(ClaudeSettings)({}); diff --git a/apps/server/src/orchestration-v2/ContextHandoffBudget.test.ts b/apps/server/src/orchestration-v2/ContextHandoffBudget.test.ts index 2c6c878b25e9fa78cdc2b30324d031882946bf31..6f385a128b39c7eca0868836bb1cbebe3cf6ee0e 100644 --- a/apps/server/src/orchestration-v2/ContextHandoffBudget.test.ts +++ b/apps/server/src/orchestration-v2/ContextHandoffBudget.test.ts @@ -1,4 +1,4 @@ -import type { ProviderAdapterV2HistoricalContext } from "./ProviderAdapter.ts"; +import type { ProviderAdapterV2HistoricalContext } from "@t3tools/provider-core/server/ProviderAdapter"; import { assert, describe, it } from "@effect/vitest"; import { ContextHandoffId, diff --git a/apps/server/src/orchestration-v2/ContextHandoffDelivery.ts b/apps/server/src/orchestration-v2/ContextHandoffDelivery.ts index 52a80448f8c37841a305b8325ed3d534844a4f96..f3c4a846b7e7e9f77bb99974d4e51eb4aa24f5b8 100644 --- a/apps/server/src/orchestration-v2/ContextHandoffDelivery.ts +++ b/apps/server/src/orchestration-v2/ContextHandoffDelivery.ts @@ -2,7 +2,8 @@ import type { OrchestrationV2ContextHandoff, OrchestrationV2ProviderThread, } from "@t3tools/contracts"; -import type { ProviderAdapterV2HistoricalContext } from "./ProviderAdapter.ts"; +import type { ProviderAdapterV2HistoricalContext } from "@t3tools/provider-core/server/ProviderAdapter"; +import { ContextHandoffBudgetError } from "@t3tools/provider-core/server/failure"; import * as Effect from "effect/Effect"; import * as Schema from "effect/Schema"; import { historyCost, renderHistory, selectHistory } from "./ContextHandoffBudget.ts"; @@ -146,14 +147,6 @@ export const deliverContextHandoffs = Effect.fn("orchestrationV2.deliverContextH }, ); -export class ContextHandoffBudgetError extends Schema.TaggedError()( - "ContextHandoffBudgetError", - {}, -) { - override get message() { - return "Insufficient context allowance for the provider handoff. Compact the target conversation or use a larger-context model; the current request has not been truncated."; - } -} export class ContextHandoffDeliveryUncertainError extends Schema.TaggedError()( "ContextHandoffDeliveryUncertainError", {}, diff --git a/apps/server/src/orchestration-v2/ContextHandoffService.test.ts b/apps/server/src/orchestration-v2/ContextHandoffService.test.ts index 18c7e982af7e9d3ae9910b2316c0200db5604379..9f24d165c55de5f956c640c95922c0aba31b9fde 100644 --- a/apps/server/src/orchestration-v2/ContextHandoffService.test.ts +++ b/apps/server/src/orchestration-v2/ContextHandoffService.test.ts @@ -13,7 +13,7 @@ import * as Effect from "effect/Effect"; import * as Layer from "effect/Layer"; import * as ContextHandoffService from "./ContextHandoffService.ts"; -import * as IdAllocator from "./IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; const layerTest = ContextHandoffService.layer.pipe(Layer.provide(IdAllocator.layer)); diff --git a/apps/server/src/orchestration-v2/ContextHandoffService.ts b/apps/server/src/orchestration-v2/ContextHandoffService.ts index 226c2119d3ea1f970b065bfd3f041f9465f90046..0d66db6deb3f0f46a679f3bb1057e6e7afb837e5 100644 --- a/apps/server/src/orchestration-v2/ContextHandoffService.ts +++ b/apps/server/src/orchestration-v2/ContextHandoffService.ts @@ -21,7 +21,7 @@ import { renderHistory, selectHistory, } from "./ContextHandoffBudget.ts"; -import * as IdAllocator from "./IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; export class ContextHandoffPrepareError extends Schema.TaggedError()( "ContextHandoffPrepareError", diff --git a/apps/server/src/orchestration-v2/DelegatedCompletionDelivery.test.ts b/apps/server/src/orchestration-v2/DelegatedCompletionDelivery.test.ts index 0344e3aed4cfe162bbc8741f302496c75be6c854..ed2ae984501e6fa5ab67ce385421ce2ecf7c2c1d 100644 --- a/apps/server/src/orchestration-v2/DelegatedCompletionDelivery.test.ts +++ b/apps/server/src/orchestration-v2/DelegatedCompletionDelivery.test.ts @@ -27,7 +27,7 @@ import * as McpSessionRegistryTestkit from "../mcp/McpSessionRegistry.testkit.ts import * as SqlitePersistence from "../persistence/Sqlite.ts"; import * as ProjectEnrichmentService from "../project/ProjectEnrichmentService.ts"; import * as ProjectService from "../project/ProjectService.ts"; -import type { ProviderInstance } from "../provider/ProviderDriver.ts"; +import type { ProviderInstance } from "@t3tools/provider-core/server/driver"; import * as ProviderInstanceRegistry from "../provider/ProviderInstanceRegistry.ts"; import * as ServerSettings from "../serverSettings.ts"; import * as VcsDriverRegistry from "../vcs/VcsDriverRegistry.ts"; @@ -36,7 +36,7 @@ import * as WorkspacePaths from "../workspace/WorkspacePaths.ts"; import { CodexProviderCapabilitiesV2 } from "./Adapters/CodexAdapterV2.ts"; import * as EventSink from "./EventSink.ts"; import * as Orchestrator from "./Orchestrator.ts"; -import type { ProviderAdapterV2Shape } from "./ProviderAdapter.ts"; +import type { ProviderAdapterV2Shape } from "@t3tools/provider-core/server/ProviderAdapter"; import { continueRestartedRun } from "./RestartContinuation.ts"; import * as RuntimeLayer from "./runtimeLayer.ts"; import * as ProviderTurnStartServiceTestkit from "./ProviderTurnStartService.testkit.ts"; diff --git a/apps/server/src/orchestration-v2/DispatchModeLimit.test.ts b/apps/server/src/orchestration-v2/DispatchModeLimit.test.ts index dca74400e82113351cfdccc54d57330396afb3be..044b1b66bcdc7c5491addaff86a4beb964291079 100644 --- a/apps/server/src/orchestration-v2/DispatchModeLimit.test.ts +++ b/apps/server/src/orchestration-v2/DispatchModeLimit.test.ts @@ -13,7 +13,7 @@ import { CodexProviderCapabilitiesV2 } from "./Adapters/CodexAdapterV2.ts"; import { DispatchModeLimit } from "./DispatchModeLimit.ts"; import * as Orchestrator from "./Orchestrator.ts"; import * as ProjectionStore from "./ProjectionStore.ts"; -import type { ProviderAdapterV2Shape } from "./ProviderAdapter.ts"; +import type { ProviderAdapterV2Shape } from "@t3tools/provider-core/server/ProviderAdapter"; import * as ProviderAdapterRegistry from "./ProviderAdapterRegistry.ts"; import * as ProviderReplayHarness from "./testkit/ProviderReplayHarness.ts"; diff --git a/apps/server/src/orchestration-v2/FoundationPersistence.test.ts b/apps/server/src/orchestration-v2/FoundationPersistence.test.ts index 5b70ae8b7fd5cf91b93e37e77f720bde572366b1..9f4549370377b17717544cfa7851d8898951ad23 100644 --- a/apps/server/src/orchestration-v2/FoundationPersistence.test.ts +++ b/apps/server/src/orchestration-v2/FoundationPersistence.test.ts @@ -50,7 +50,7 @@ import * as EffectOutbox from "./EffectOutbox.ts"; import * as EffectWorker from "./EffectWorker.ts"; import * as EventSink from "./EventSink.ts"; import * as EventStore from "./EventStore.ts"; -import * as IdAllocator from "./IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import * as ProjectionMaintenance from "./ProjectionMaintenance.ts"; import * as ProjectionStore from "./ProjectionStore.ts"; import * as ProjectStore from "./ProjectStore.ts"; diff --git a/apps/server/src/orchestration-v2/OpenCode2OrchestratorV2.integration.test.ts b/apps/server/src/orchestration-v2/OpenCode2OrchestratorV2.integration.test.ts index 024b94c242361884cb507d9994460af0d48949d0..873ca407a7012a9f1827759a782817875d04cb23 100644 --- a/apps/server/src/orchestration-v2/OpenCode2OrchestratorV2.integration.test.ts +++ b/apps/server/src/orchestration-v2/OpenCode2OrchestratorV2.integration.test.ts @@ -31,12 +31,12 @@ import { OPENCODE_PROVIDER } from "./Adapters/OpenCodeAdapterV2.ts"; import { provideDeterministicTestRuntime } from "./testkit/DeterministicRuntime.ts"; import type { OrchestratorV2ScenarioStep } from "./testkit/OrchestratorScenario.ts"; import { runOrchestratorV2ProviderReplayScenario } from "./testkit/ProviderReplayHarness.ts"; -import { checkpointWorkspace } from "./testkit/ReplayFixtureWorkspace.ts"; +import { checkpointWorkspace } from "@t3tools/provider-testing/replayWorkspace"; import { decodeProviderReplayNdjson, readProviderReplayTranscript, -} from "./testkit/ReplayTranscriptNdjson.ts"; -import * as IdAllocator from "./IdAllocator.ts"; +} from "@t3tools/provider-testing/replayTranscript"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; const SESSION = "ses_f148ca2deffeJcwCnRQtb0YFNX"; /** Held until the scenario releases it, so the turn is still running meanwhile. */ diff --git a/apps/server/src/orchestration-v2/OpenCode2OrchestratorV2.live.test.ts b/apps/server/src/orchestration-v2/OpenCode2OrchestratorV2.live.test.ts index ba442d99bfece4e0c9862e422e1ed7f211f97a4f..3e486a14f0de8620116b8d11a5b9ad4bb85ec5c6 100644 --- a/apps/server/src/orchestration-v2/OpenCode2OrchestratorV2.live.test.ts +++ b/apps/server/src/orchestration-v2/OpenCode2OrchestratorV2.live.test.ts @@ -66,7 +66,7 @@ import * as Orchestrator from "./Orchestrator.ts"; import * as ProviderInstanceRegistry from "../provider/ProviderInstanceRegistry.ts"; import * as ProviderTurnStartServiceTestkit from "./ProviderTurnStartService.testkit.ts"; import * as RuntimeLayer from "./runtimeLayer.ts"; -import * as IdAllocator from "./IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import * as ProviderContinuationRequests from "./ProviderContinuationRequests.ts"; import * as ProviderContinuationService from "./ProviderContinuationService.ts"; import * as ThreadManagementService from "./ThreadManagementService.ts"; diff --git a/apps/server/src/orchestration-v2/Orchestrator.control-reads.test.ts b/apps/server/src/orchestration-v2/Orchestrator.control-reads.test.ts index c68fc0ace5e93512b8c74679864aa4098812a396..76a4bd8c1beced3e59e10a62bb23027f9f2b8e68 100644 --- a/apps/server/src/orchestration-v2/Orchestrator.control-reads.test.ts +++ b/apps/server/src/orchestration-v2/Orchestrator.control-reads.test.ts @@ -25,7 +25,7 @@ import * as SqlitePersistence from "../persistence/Sqlite.ts"; import { CodexProviderCapabilitiesV2 } from "./Adapters/CodexAdapterV2.ts"; import * as Orchestrator from "./Orchestrator.ts"; import * as ProjectionStore from "./ProjectionStore.ts"; -import type { ProviderAdapterV2Shape } from "./ProviderAdapter.ts"; +import type { ProviderAdapterV2Shape } from "@t3tools/provider-core/server/ProviderAdapter"; import * as ProviderAdapterRegistry from "./ProviderAdapterRegistry.ts"; import * as ProviderReplayHarness from "./testkit/ProviderReplayHarness.ts"; diff --git a/apps/server/src/orchestration-v2/Orchestrator.ts b/apps/server/src/orchestration-v2/Orchestrator.ts index 1d7f907a519602766577ec5b33fb2e1388d40212..226108f6a50384e3a809b5230b8fffaebcb70420 100644 --- a/apps/server/src/orchestration-v2/Orchestrator.ts +++ b/apps/server/src/orchestration-v2/Orchestrator.ts @@ -91,7 +91,7 @@ import { isUndeliveredMailboxSteer } from "./NotificationMailbox.ts"; import { EventSinkV2 } from "./EventSink.ts"; import * as EffectOutbox from "./EffectOutbox.ts"; import type { OrchestrationEffectRequestV2, PendingOrchestrationEffectV2 } from "./EffectOutbox.ts"; -import { IdAllocatorV2 } from "./IdAllocator.ts"; +import { IdAllocatorV2 } from "@t3tools/provider-core/server/IdAllocator"; import * as ThreadCommandExecutor from "./ThreadCommandExecutor.ts"; import { DispatchModeLimit, exceededDispatchModeLimit } from "./DispatchModeLimit.ts"; import { @@ -107,10 +107,10 @@ import { type ProjectionCheckpointContext, type ShellSnapshotOptions, } from "./ProjectionStore.ts"; -import type { ProviderAdapterV2Shape } from "./ProviderAdapter.ts"; +import type { ProviderAdapterV2Shape } from "@t3tools/provider-core/server/ProviderAdapter"; import { ProviderAdapterRegistryV2 } from "./ProviderAdapterRegistry.ts"; import { ProviderContinuationRequests } from "./ProviderContinuationRequests.ts"; -import { makeProviderFailure } from "./ProviderFailure.ts"; +import { makeProviderFailure } from "@t3tools/provider-core/server/failure"; import * as RunExecutionService from "./RunExecutionService.ts"; import { ProviderSessionManagerV2 } from "./ProviderSessionManager.ts"; import { ProviderSwitchServiceV2 } from "./ProviderSwitchService.ts"; diff --git a/apps/server/src/orchestration-v2/ProviderAdapterRegistry.test.ts b/apps/server/src/orchestration-v2/ProviderAdapterRegistry.test.ts index f79c974902a4405c42d537c4ebfc1130f40835aa..3a11ab7c2722b6bb040b6ead6b585f6b22e92fbd 100644 --- a/apps/server/src/orchestration-v2/ProviderAdapterRegistry.test.ts +++ b/apps/server/src/orchestration-v2/ProviderAdapterRegistry.test.ts @@ -20,13 +20,16 @@ import * as Stream from "effect/Stream"; import * as ProviderAuthFlow from "../provider/ProviderAuthFlow.ts"; import type { ProviderAuthController } from "../provider/ProviderAuthService.ts"; -import type { ProviderInstance } from "../provider/ProviderDriver.ts"; +import type { ProviderInstance } from "@t3tools/provider-core/server/driver"; import * as ProviderInstanceRegistry from "../provider/ProviderInstanceRegistry.ts"; -import { ProviderAdapterOpenSessionError, type ProviderAdapterV2Shape } from "./ProviderAdapter.ts"; +import { + ProviderAdapterOpenSessionError, + type ProviderAdapterV2Shape, +} from "@t3tools/provider-core/server/ProviderAdapter"; import { ProviderAdapterDriverCreateError, type ProviderAdapterDriver, -} from "./ProviderAdapterDriver.ts"; +} from "@t3tools/provider-core/server/adapterDriver"; import * as ProviderAdapterRegistry from "./ProviderAdapterRegistry.ts"; const driver = ProviderDriverKind.make("codex"); diff --git a/apps/server/src/orchestration-v2/ProviderAdapterRegistry.ts b/apps/server/src/orchestration-v2/ProviderAdapterRegistry.ts index d487aa18c9be025024f9217bad5b2ceb8563612a..984fd586e5ea54d4da4c247f6f97059b2b46b9c2 100644 --- a/apps/server/src/orchestration-v2/ProviderAdapterRegistry.ts +++ b/apps/server/src/orchestration-v2/ProviderAdapterRegistry.ts @@ -17,8 +17,8 @@ import * as ProviderInstanceRegistry from "../provider/ProviderInstanceRegistry. import { ProviderAdapterDriverCreateError, type AnyProviderAdapterDriver, -} from "./ProviderAdapterDriver.ts"; -import * as ProviderAdapter from "./ProviderAdapter.ts"; +} from "@t3tools/provider-core/server/adapterDriver"; +import * as ProviderAdapter from "@t3tools/provider-core/server/ProviderAdapter"; const isProviderSetupError = Schema.is(ProviderSetupError); diff --git a/apps/server/src/orchestration-v2/ProviderContinuationService.test.ts b/apps/server/src/orchestration-v2/ProviderContinuationService.test.ts index 0c2df4e9cf44cd92858d6a3be7d833fe3af472d3..2ed8b465b2c3fc2d30361007a11cfaba59e94cb1 100644 --- a/apps/server/src/orchestration-v2/ProviderContinuationService.test.ts +++ b/apps/server/src/orchestration-v2/ProviderContinuationService.test.ts @@ -18,7 +18,7 @@ import * as Ref from "effect/Ref"; import * as Semaphore from "effect/Semaphore"; import * as TestClock from "effect/testing/TestClock"; -import * as IdAllocator from "./IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import * as ProviderContinuationRequests from "./ProviderContinuationRequests.ts"; import * as ProviderContinuationService from "./ProviderContinuationService.ts"; import * as ThreadManagementService from "./ThreadManagementService.ts"; diff --git a/apps/server/src/orchestration-v2/ProviderContinuationService.ts b/apps/server/src/orchestration-v2/ProviderContinuationService.ts index 2520847c77482fb73509e8b96c77041b54368d3c..ac254a0ae27c6c4b2a4fa8c75363310450cd636a 100644 --- a/apps/server/src/orchestration-v2/ProviderContinuationService.ts +++ b/apps/server/src/orchestration-v2/ProviderContinuationService.ts @@ -3,7 +3,7 @@ import * as Effect from "effect/Effect"; import * as Layer from "effect/Layer"; import * as Ref from "effect/Ref"; -import * as IdAllocator from "./IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import * as ProviderContinuationRequests from "./ProviderContinuationRequests.ts"; import * as ThreadManagementService from "./ThreadManagementService.ts"; import { isUndeliveredMailboxSteer } from "./NotificationMailbox.ts"; diff --git a/apps/server/src/orchestration-v2/ProviderEventIngestor.test.ts b/apps/server/src/orchestration-v2/ProviderEventIngestor.test.ts index c9740adfbf0c414cb963a2d8cbe66ae2e26e822e..1ccbdaf9597029204526cb1e21a0e8b6152dbfb7 100644 --- a/apps/server/src/orchestration-v2/ProviderEventIngestor.test.ts +++ b/apps/server/src/orchestration-v2/ProviderEventIngestor.test.ts @@ -31,11 +31,11 @@ import { toolOutputImages } from "@t3tools/shared/toolOutput"; import * as SqlitePersistence from "../persistence/Sqlite.ts"; import * as EventSink from "./EventSink.ts"; import * as EventStore from "./EventStore.ts"; -import * as IdAllocator from "./IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import * as ProjectionStore from "./ProjectionStore.ts"; import * as ProviderEventIngestor from "./ProviderEventIngestor.ts"; import * as ThreadCommandExecutor from "./ThreadCommandExecutor.ts"; -import { makeProviderFailure } from "./ProviderFailure.ts"; +import { makeProviderFailure } from "@t3tools/provider-core/server/failure"; import { makeProviderEventRoutingState, type ProviderEventRouteIdentity, diff --git a/apps/server/src/orchestration-v2/ProviderEventIngestor.ts b/apps/server/src/orchestration-v2/ProviderEventIngestor.ts index dcaa956d078955cb1e86c01a2ae09cd6da5aae28..b794883c092da6d22b2aed0b67685cbce487e5b4 100644 --- a/apps/server/src/orchestration-v2/ProviderEventIngestor.ts +++ b/apps/server/src/orchestration-v2/ProviderEventIngestor.ts @@ -29,9 +29,9 @@ import { getModelSelectionStringOptionValue } from "@t3tools/shared/model"; import * as AnalyticsService from "../telemetry/AnalyticsService.ts"; import * as EventSink from "./EventSink.ts"; import * as ProjectionStore from "./ProjectionStore.ts"; -import * as IdAllocator from "./IdAllocator.ts"; -import { ProviderAdapterV2Event } from "./ProviderAdapter.ts"; -import { makeProviderFailureTurnItem } from "./ProviderFailure.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; +import { ProviderAdapterV2Event } from "@t3tools/provider-core/server/ProviderAdapter"; +import { makeProviderFailureTurnItem } from "@t3tools/provider-core/server/failure"; import * as ThreadCommandExecutor from "./ThreadCommandExecutor.ts"; import { stripUnservedToolOutputImageBytes } from "./toolOutputImageBytes.ts"; diff --git a/apps/server/src/orchestration-v2/ProviderRuntimeRecoveryPerformance.test.ts b/apps/server/src/orchestration-v2/ProviderRuntimeRecoveryPerformance.test.ts index 6d92c82904ccb1519251996d5209eea336e9d544..dd2a05f539097cc04dc48340bdbe4e97974b5acd 100644 --- a/apps/server/src/orchestration-v2/ProviderRuntimeRecoveryPerformance.test.ts +++ b/apps/server/src/orchestration-v2/ProviderRuntimeRecoveryPerformance.test.ts @@ -31,7 +31,7 @@ import { CodexProviderCapabilitiesV2 } from "./Adapters/CodexAdapterV2.ts"; import * as EffectOutbox from "./EffectOutbox.ts"; import * as EventSink from "./EventSink.ts"; import * as EventStore from "./EventStore.ts"; -import * as IdAllocator from "./IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import * as ProjectionStore from "./ProjectionStore.ts"; import * as ProviderRuntimeRecovery from "./ProviderRuntimeRecoveryService.ts"; diff --git a/apps/server/src/orchestration-v2/ProviderRuntimeRecoveryService.regression.test.ts b/apps/server/src/orchestration-v2/ProviderRuntimeRecoveryService.regression.test.ts index 443584ce69fc4046ebdeb12e4ec18be298f33268..126746648f970007a23f0fd761fe392ce89fa314 100644 --- a/apps/server/src/orchestration-v2/ProviderRuntimeRecoveryService.regression.test.ts +++ b/apps/server/src/orchestration-v2/ProviderRuntimeRecoveryService.regression.test.ts @@ -12,7 +12,7 @@ import { expect, it } from "vite-plus/test"; import * as EffectWorker from "./EffectWorker.ts"; import * as EffectOutbox from "./EffectOutbox.ts"; import * as EventSink from "./EventSink.ts"; -import * as IdAllocator from "./IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import * as ProjectionStore from "./ProjectionStore.ts"; import * as ProviderRuntimeRecovery from "./ProviderRuntimeRecoveryService.ts"; import * as ServerSettings from "../serverSettings.ts"; diff --git a/apps/server/src/orchestration-v2/ProviderRuntimeRecoveryService.test.ts b/apps/server/src/orchestration-v2/ProviderRuntimeRecoveryService.test.ts index cb06238395a683f7d43ab4eba08faebda13bea29..da764d41d73011cd93e853327a9753348e5bc215 100644 --- a/apps/server/src/orchestration-v2/ProviderRuntimeRecoveryService.test.ts +++ b/apps/server/src/orchestration-v2/ProviderRuntimeRecoveryService.test.ts @@ -21,7 +21,7 @@ import * as Ref from "effect/Ref"; import * as EffectWorker from "./EffectWorker.ts"; import * as EffectOutbox from "./EffectOutbox.ts"; import * as EventSink from "./EventSink.ts"; -import * as IdAllocator from "./IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import * as ProjectionStore from "./ProjectionStore.ts"; import * as ProviderRuntimeRecovery from "./ProviderRuntimeRecoveryService.ts"; import * as ServerSettings from "../serverSettings.ts"; diff --git a/apps/server/src/orchestration-v2/ProviderRuntimeRecoveryService.ts b/apps/server/src/orchestration-v2/ProviderRuntimeRecoveryService.ts index 27a79b9fa7571451e664724e5343759eb50bdaff..7a063bec065bc60e11cbb6023526b4c9c5265842 100644 --- a/apps/server/src/orchestration-v2/ProviderRuntimeRecoveryService.ts +++ b/apps/server/src/orchestration-v2/ProviderRuntimeRecoveryService.ts @@ -18,7 +18,7 @@ import * as Schema from "effect/Schema"; import * as EffectOutbox from "./EffectOutbox.ts"; import * as EventSink from "./EventSink.ts"; -import * as IdAllocator from "./IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import * as ProjectionStore from "./ProjectionStore.ts"; import * as ServerSettings from "../serverSettings.ts"; import { restartContinuationRun } from "./RestartContinuation.ts"; diff --git a/apps/server/src/orchestration-v2/ProviderSelectionTransition.test.ts b/apps/server/src/orchestration-v2/ProviderSelectionTransition.test.ts index 2e1911bceb8ed092bf6540e428fc05f742c83280..4a6d6a6a91d12ddde755bbd3052f7dcb0f23423c 100644 --- a/apps/server/src/orchestration-v2/ProviderSelectionTransition.test.ts +++ b/apps/server/src/orchestration-v2/ProviderSelectionTransition.test.ts @@ -7,7 +7,7 @@ import { } from "@t3tools/contracts"; import { AcpProviderCapabilitiesV2 } from "./Adapters/AcpAdapterV2.ts"; -import { acpSelectionTransition } from "./ProviderSelectionTransition.ts"; +import { acpSelectionTransition } from "@t3tools/provider-core/server/selectionTransition"; const selection = (model: string, effort = "medium"): ModelSelection => ({ instanceId: ProviderInstanceId.make("acp_test"), diff --git a/apps/server/src/orchestration-v2/ProviderSessionManager.test.ts b/apps/server/src/orchestration-v2/ProviderSessionManager.test.ts index 2f2b0402f6205624354a6d02d56ff60476505da9..bb994377f4bf624e69f0f5a3dc2c2b8ec9a0e9dd 100644 --- a/apps/server/src/orchestration-v2/ProviderSessionManager.test.ts +++ b/apps/server/src/orchestration-v2/ProviderSessionManager.test.ts @@ -35,14 +35,14 @@ import { HttpServer } from "effect/http"; import { ProviderWorkspaceMissingError } from "../provider/Errors.ts"; import * as ServerEnvironment from "../environment/ServerEnvironment.ts"; import * as ProjectService from "../project/ProjectService.ts"; -import * as McpProviderSession from "../mcp/McpProviderSession.ts"; +import * as McpProviderSession from "@t3tools/provider-core/server/mcpSession"; import * as McpSessionRegistry from "../mcp/McpSessionRegistry.ts"; import * as SqlitePersistence from "../persistence/Sqlite.ts"; import * as ServerSettings from "../serverSettings.ts"; import { CodexProviderCapabilitiesV2 } from "./Adapters/CodexAdapterV2.ts"; import * as EventSink from "./EventSink.ts"; import * as EventStore from "./EventStore.ts"; -import * as IdAllocator from "./IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import * as ProjectionStore from "./ProjectionStore.ts"; import { ProviderAdapterEventStreamError, @@ -51,7 +51,7 @@ import { type ProviderAdapterV2RuntimePolicy, type ProviderAdapterV2SessionRuntime, type ProviderAdapterV2Shape, -} from "./ProviderAdapter.ts"; +} from "@t3tools/provider-core/server/ProviderAdapter"; import * as ProviderAdapterRegistry from "./ProviderAdapterRegistry.ts"; import * as ProviderEventIngestor from "./ProviderEventIngestor.ts"; import * as ThreadCommandExecutor from "./ThreadCommandExecutor.ts"; diff --git a/apps/server/src/orchestration-v2/ProviderSessionManager.ts b/apps/server/src/orchestration-v2/ProviderSessionManager.ts index d181497ec2754f6b2a6641cca95989aee3dd9012..f467b8527e89297454b82a98cf1d4998f4fdf913 100644 --- a/apps/server/src/orchestration-v2/ProviderSessionManager.ts +++ b/apps/server/src/orchestration-v2/ProviderSessionManager.ts @@ -40,11 +40,11 @@ import { } from "../observability/Metrics.ts"; import { ProviderWorkspaceMissingError } from "../provider/Errors.ts"; import * as ProjectService from "../project/ProjectService.ts"; -import * as McpProviderSession from "../mcp/McpProviderSession.ts"; +import * as McpProviderSession from "@t3tools/provider-core/server/mcpSession"; import * as ServerSettings from "../serverSettings.ts"; import * as McpSessionRegistry from "../mcp/McpSessionRegistry.ts"; import * as EventSink from "./EventSink.ts"; -import * as IdAllocator from "./IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import * as ProviderEventIngestor from "./ProviderEventIngestor.ts"; import { ProviderAdapterEventStreamError, @@ -53,7 +53,7 @@ import { type ProviderAdapterV2Event, type ProviderAdapterV2EventSubscription, type ProviderAdapterV2SessionRuntime, -} from "./ProviderAdapter.ts"; +} from "@t3tools/provider-core/server/ProviderAdapter"; import * as ProviderAdapterRegistry from "./ProviderAdapterRegistry.ts"; import * as ProjectionStore from "./ProjectionStore.ts"; diff --git a/apps/server/src/orchestration-v2/ProviderSessionTransitionPolicy.ts b/apps/server/src/orchestration-v2/ProviderSessionTransitionPolicy.ts index 50c7e561de63d7d7d8121b556801da7e915dc8d8..784d03de6dcb13f90960ffd298928cae16a955b6 100644 --- a/apps/server/src/orchestration-v2/ProviderSessionTransitionPolicy.ts +++ b/apps/server/src/orchestration-v2/ProviderSessionTransitionPolicy.ts @@ -7,8 +7,8 @@ import type { } from "@t3tools/contracts"; import { modelSelectionsEqual } from "@t3tools/shared/model"; -import type { ProviderContinuationIdentity } from "../provider/ProviderDriver.ts"; -import type { ProviderSelectionTransitionPlan } from "./ProviderSelectionTransition.ts"; +import type { ProviderContinuationIdentity } from "@t3tools/provider-core/server/driver"; +import type { ProviderSelectionTransitionPlan } from "@t3tools/provider-core/server/selectionTransition"; export type ProviderSessionTransition = | { readonly type: "reuse" } diff --git a/apps/server/src/orchestration-v2/ProviderSwitchService.test.ts b/apps/server/src/orchestration-v2/ProviderSwitchService.test.ts index 5cf3f9246c6b45d22c37f069d392b91364ed5a60..712b9e6e10f35905491899bd7ead731a7af0ebfe 100644 --- a/apps/server/src/orchestration-v2/ProviderSwitchService.test.ts +++ b/apps/server/src/orchestration-v2/ProviderSwitchService.test.ts @@ -12,9 +12,9 @@ import * as Effect from "effect/Effect"; import * as Layer from "effect/Layer"; import { CodexProviderCapabilitiesV2 } from "./Adapters/CodexAdapterV2.ts"; -import type { ProviderAdapterV2Shape } from "./ProviderAdapter.ts"; +import type { ProviderAdapterV2Shape } from "@t3tools/provider-core/server/ProviderAdapter"; import * as ProviderAdapterRegistry from "./ProviderAdapterRegistry.ts"; -import { acpSelectionTransition } from "./ProviderSelectionTransition.ts"; +import { acpSelectionTransition } from "@t3tools/provider-core/server/selectionTransition"; import * as ProviderSwitch from "./ProviderSwitchService.ts"; const driver = ProviderDriverKind.make("codex"); diff --git a/apps/server/src/orchestration-v2/ProviderTurnControlService.test.ts b/apps/server/src/orchestration-v2/ProviderTurnControlService.test.ts index 0808386da538865a3ea92d505ac3384372266a1d..42b3943e71d0cae880c0142b8c96a111d7278ed2 100644 --- a/apps/server/src/orchestration-v2/ProviderTurnControlService.test.ts +++ b/apps/server/src/orchestration-v2/ProviderTurnControlService.test.ts @@ -24,7 +24,7 @@ import * as Stream from "effect/Stream"; import { CodexProviderCapabilitiesV2 } from "./Adapters/CodexAdapterV2.ts"; import * as ProjectionStore from "./ProjectionStore.ts"; -import type { ProviderAdapterV2SessionRuntime } from "./ProviderAdapter.ts"; +import type { ProviderAdapterV2SessionRuntime } from "@t3tools/provider-core/server/ProviderAdapter"; import * as ProviderSessionManager from "./ProviderSessionManager.ts"; import * as ProviderTurnControlService from "./ProviderTurnControlService.ts"; diff --git a/apps/server/src/orchestration-v2/ProviderTurnStartService.test.ts b/apps/server/src/orchestration-v2/ProviderTurnStartService.test.ts index 06761c13b3fdefe799b61b52a3add9aa44ea2763..54e55c40a3ccfcc7132fea4d487f71d5917795b4 100644 --- a/apps/server/src/orchestration-v2/ProviderTurnStartService.test.ts +++ b/apps/server/src/orchestration-v2/ProviderTurnStartService.test.ts @@ -29,10 +29,10 @@ import * as ProjectService from "../project/ProjectService.ts"; import * as ProviderAuthService from "../provider/ProviderAuthService.ts"; import * as ContextHandoffService from "./ContextHandoffService.ts"; import * as EventSink from "./EventSink.ts"; -import * as IdAllocator from "./IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import { CodexProviderCapabilitiesV2 } from "./Adapters/CodexAdapterV2.ts"; import * as ProjectionStore from "./ProjectionStore.ts"; -import { ProviderAdapterEventStreamError } from "./ProviderAdapter.ts"; +import { ProviderAdapterEventStreamError } from "@t3tools/provider-core/server/ProviderAdapter"; import * as ProviderSessionManager from "./ProviderSessionManager.ts"; import * as ProviderTurnStart from "./ProviderTurnStartService.ts"; import * as RunExecutionService from "./RunExecutionService.ts"; diff --git a/apps/server/src/orchestration-v2/ProviderTurnStartService.ts b/apps/server/src/orchestration-v2/ProviderTurnStartService.ts index 227aab2256e2757e31bb57ec57a84e5183234efc..9bf834c0efa4e21ec9e2a84375a4763af6c5359f 100644 --- a/apps/server/src/orchestration-v2/ProviderTurnStartService.ts +++ b/apps/server/src/orchestration-v2/ProviderTurnStartService.ts @@ -42,11 +42,11 @@ import { type ProviderAdapterV2Error, type ProviderAdapterV2HistoricalContext, type ProviderAdapterV2SessionRuntime, -} from "./ProviderAdapter.ts"; -import * as IdAllocator from "./IdAllocator.ts"; +} from "@t3tools/provider-core/server/ProviderAdapter"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import * as ProjectionStore from "./ProjectionStore.ts"; import * as ProviderSessionManager from "./ProviderSessionManager.ts"; -import { makeProviderFailure } from "./ProviderFailure.ts"; +import { makeProviderFailure } from "@t3tools/provider-core/server/failure"; import * as RunExecutionService from "./RunExecutionService.ts"; import * as RuntimePolicy from "./RuntimePolicy.ts"; import { diff --git a/apps/server/src/orchestration-v2/RestartContinuation.test.ts b/apps/server/src/orchestration-v2/RestartContinuation.test.ts index 6a790c966eab872304fac33829aef432df6720e3..dcbf4aa637284749e645402564fef9ff39498e8a 100644 --- a/apps/server/src/orchestration-v2/RestartContinuation.test.ts +++ b/apps/server/src/orchestration-v2/RestartContinuation.test.ts @@ -21,7 +21,7 @@ import * as ThreadManagementService from "./ThreadManagementService.ts"; import * as ProviderRuntimeRecovery from "./ProviderRuntimeRecoveryService.ts"; import * as ProjectionStore from "./ProjectionStore.ts"; import * as EventSink from "./EventSink.ts"; -import * as IdAllocator from "./IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import * as EffectWorker from "./EffectWorker.ts"; import * as EffectOutbox from "./EffectOutbox.ts"; diff --git a/apps/server/src/orchestration-v2/RunExecutionService.test.ts b/apps/server/src/orchestration-v2/RunExecutionService.test.ts index f1510296255559b0df166e43eb2886af7fa84448..c7434605807740977ba041115ef47a9866e06272 100644 --- a/apps/server/src/orchestration-v2/RunExecutionService.test.ts +++ b/apps/server/src/orchestration-v2/RunExecutionService.test.ts @@ -42,7 +42,7 @@ import * as ServerSettings from "../serverSettings.ts"; import * as CheckpointService from "./CheckpointService.ts"; import type { PendingOrchestrationEffectV2 } from "./EffectOutbox.ts"; import * as EventSink from "./EventSink.ts"; -import * as IdAllocator from "./IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import { ProviderAdapterEventStreamError, ProviderAdapterTurnStartError, @@ -50,7 +50,7 @@ import { type ProviderAdapterV2Event, type ProviderAdapterV2SessionRuntime, type ProviderAdapterV2TurnInput, -} from "./ProviderAdapter.ts"; +} from "@t3tools/provider-core/server/ProviderAdapter"; import * as ProjectionStore from "./ProjectionStore.ts"; import * as ProviderEventIngestor from "./ProviderEventIngestor.ts"; import * as McpAppModelContext from "../mcpApps/McpAppModelContext.ts"; diff --git a/apps/server/src/orchestration-v2/RunExecutionService.ts b/apps/server/src/orchestration-v2/RunExecutionService.ts index 5f3e36ffd66a9c474e88abfde971c8d0e7e7f2bc..111aced2865e3abc00ab9d30e372ab4f5dd2083d 100644 --- a/apps/server/src/orchestration-v2/RunExecutionService.ts +++ b/apps/server/src/orchestration-v2/RunExecutionService.ts @@ -40,17 +40,20 @@ import * as McpAppModelContext from "../mcpApps/McpAppModelContext.ts"; import * as ServerSettings from "../serverSettings.ts"; import * as CheckpointService from "./CheckpointService.ts"; import * as EventSink from "./EventSink.ts"; -import * as IdAllocator from "./IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import type { ProviderAdapterV2Event, ProviderAdapterV2RuntimePolicy, ProviderAdapterV2SessionRuntime, ProviderAdapterV2TurnMessage, -} from "./ProviderAdapter.ts"; -import { ProviderAdapterTurnStartError } from "./ProviderAdapter.ts"; +} from "@t3tools/provider-core/server/ProviderAdapter"; +import { ProviderAdapterTurnStartError } from "@t3tools/provider-core/server/ProviderAdapter"; import * as ProviderEventIngestor from "./ProviderEventIngestor.ts"; import type { ProjectionStoreV2Error } from "./ProjectionStore.ts"; -import { makeProviderFailure, makeProviderFailureTurnItem } from "./ProviderFailure.ts"; +import { + makeProviderFailure, + makeProviderFailureTurnItem, +} from "@t3tools/provider-core/server/failure"; import * as RunFinalizationService from "./RunFinalizationService.ts"; export interface ProviderEventRoutingState { diff --git a/apps/server/src/orchestration-v2/RuntimePolicy.test.ts b/apps/server/src/orchestration-v2/RuntimePolicy.test.ts index b4cf0630fb8aa49add2b54d44ad03afc62d4d499..6719486d5377198c60787af12c0e30381b874086 100644 --- a/apps/server/src/orchestration-v2/RuntimePolicy.test.ts +++ b/apps/server/src/orchestration-v2/RuntimePolicy.test.ts @@ -14,7 +14,7 @@ import * as Layer from "effect/Layer"; import * as Option from "effect/Option"; import * as Stream from "effect/Stream"; -import type { ProviderInstance } from "../provider/ProviderDriver.ts"; +import type { ProviderInstance } from "@t3tools/provider-core/server/driver"; import * as ProviderInstanceRegistry from "../provider/ProviderInstanceRegistry.ts"; import * as ProjectStore from "./ProjectStore.ts"; import * as RuntimePolicy from "./RuntimePolicy.ts"; diff --git a/apps/server/src/orchestration-v2/RuntimePolicy.ts b/apps/server/src/orchestration-v2/RuntimePolicy.ts index 7387de15748fd368092d8157e7dd18f61edeb52f..a512b7dcabe95cc4ecdbd57a86ff2cf0b2d0e785 100644 --- a/apps/server/src/orchestration-v2/RuntimePolicy.ts +++ b/apps/server/src/orchestration-v2/RuntimePolicy.ts @@ -15,7 +15,7 @@ import * as ProviderInstanceRegistry from "../provider/ProviderInstanceRegistry. import { ProviderAdapterV2RuntimePolicy, type ProviderAdapterV2RuntimePolicy as ProviderAdapterV2RuntimePolicyType, -} from "./ProviderAdapter.ts"; +} from "@t3tools/provider-core/server/ProviderAdapter"; import * as ProjectStore from "./ProjectStore.ts"; /** diff --git a/apps/server/src/orchestration-v2/RuntimeRequestService.test.ts b/apps/server/src/orchestration-v2/RuntimeRequestService.test.ts index 6bad62ca2675d4ee07743af0c47a8afe3cc7536c..eb4670258101a09b26516414112e662818e39625 100644 --- a/apps/server/src/orchestration-v2/RuntimeRequestService.test.ts +++ b/apps/server/src/orchestration-v2/RuntimeRequestService.test.ts @@ -12,7 +12,7 @@ import * as Effect from "effect/Effect"; import * as Layer from "effect/Layer"; import * as Option from "effect/Option"; -import type { ProviderAdapterV2RuntimeRequestResponseInput } from "./ProviderAdapter.ts"; +import type { ProviderAdapterV2RuntimeRequestResponseInput } from "@t3tools/provider-core/server/ProviderAdapter"; import * as ProjectionStore from "./ProjectionStore.ts"; import * as ProviderSessionManager from "./ProviderSessionManager.ts"; import * as RuntimeRequestService from "./RuntimeRequestService.ts"; diff --git a/apps/server/src/orchestration-v2/SelectionRestart.integration.test.ts b/apps/server/src/orchestration-v2/SelectionRestart.integration.test.ts index 0737be290afd375df5b42c4fc5e149db223f9caa..425336ac29e00530d80ff4200c144cdf563e7cc1 100644 --- a/apps/server/src/orchestration-v2/SelectionRestart.integration.test.ts +++ b/apps/server/src/orchestration-v2/SelectionRestart.integration.test.ts @@ -33,10 +33,10 @@ import { type ProviderAdapterV2Event, type ProviderAdapterV2Shape, type ProviderAdapterV2TurnInput, -} from "./ProviderAdapter.ts"; +} from "@t3tools/provider-core/server/ProviderAdapter"; import * as ProviderAdapterRegistry from "./ProviderAdapterRegistry.ts"; import * as ProviderReplayHarness from "./testkit/ProviderReplayHarness.ts"; -import { checkpointWorkspace } from "./testkit/ReplayFixtureWorkspace.ts"; +import { checkpointWorkspace } from "@t3tools/provider-testing/replayWorkspace"; const driver = ProviderDriverKind.make("codex"); const providerInstanceId = ProviderInstanceId.make("codex-restart-test"); diff --git a/apps/server/src/orchestration-v2/SteeringCompletion.integration.test.ts b/apps/server/src/orchestration-v2/SteeringCompletion.integration.test.ts index bbea47cee599b1a9e775be26a295575fa5e23ded..8c28cbc03ce906b3077a613c27a8500bee76ef8d 100644 --- a/apps/server/src/orchestration-v2/SteeringCompletion.integration.test.ts +++ b/apps/server/src/orchestration-v2/SteeringCompletion.integration.test.ts @@ -28,10 +28,10 @@ import { type ProviderAdapterV2Event, type ProviderAdapterV2Shape, type ProviderAdapterV2TurnInput, -} from "./ProviderAdapter.ts"; +} from "@t3tools/provider-core/server/ProviderAdapter"; import * as ProviderAdapterRegistry from "./ProviderAdapterRegistry.ts"; import * as ProviderReplayHarness from "./testkit/ProviderReplayHarness.ts"; -import { checkpointWorkspace } from "./testkit/ReplayFixtureWorkspace.ts"; +import { checkpointWorkspace } from "@t3tools/provider-testing/replayWorkspace"; const driver = ProviderDriverKind.make("codex"); const instanceId = ProviderInstanceId.make("codex"); diff --git a/apps/server/src/orchestration-v2/ThreadDeletion.test.ts b/apps/server/src/orchestration-v2/ThreadDeletion.test.ts index d9a87e0df7578ccf64a1e77f6bd1d40102116a19..3a502e9e1b96e49157122d963ecdba5eddfd56ff 100644 --- a/apps/server/src/orchestration-v2/ThreadDeletion.test.ts +++ b/apps/server/src/orchestration-v2/ThreadDeletion.test.ts @@ -20,7 +20,7 @@ import * as DateTime from "effect/DateTime"; import * as Effect from "effect/Effect"; import { CodexProviderCapabilitiesV2 } from "./Adapters/CodexAdapterV2.ts"; -import * as IdAllocator from "./IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import { applyToProjection, emptyProjection } from "./ProjectionStore.ts"; import { planThreadDeletion } from "./ThreadDeletion.ts"; diff --git a/apps/server/src/orchestration-v2/ThreadDeletion.ts b/apps/server/src/orchestration-v2/ThreadDeletion.ts index 86d1e805026762770871ba8be518d1c7d96d97c5..077aa5726bd09ea2a8b53acf269794bf2b8101b1 100644 --- a/apps/server/src/orchestration-v2/ThreadDeletion.ts +++ b/apps/server/src/orchestration-v2/ThreadDeletion.ts @@ -7,7 +7,7 @@ import type * as DateTime from "effect/DateTime"; import * as Effect from "effect/Effect"; import type { PendingOrchestrationEffectV2 } from "./EffectOutbox.ts"; -import type { IdAllocatorV2, IdAllocatorV2Error } from "./IdAllocator.ts"; +import type { IdAllocatorV2, IdAllocatorV2Error } from "@t3tools/provider-core/server/IdAllocator"; export interface ThreadDeletionPlan { readonly events: ReadonlyArray; diff --git a/apps/server/src/orchestration-v2/ThreadFork.execution.test.ts b/apps/server/src/orchestration-v2/ThreadFork.execution.test.ts index 3fe92c6b49fcc23dd4ffa23462f0066b8460e6c4..77e95378c8bcd406ea8702257bf91c4ffc0a734b 100644 --- a/apps/server/src/orchestration-v2/ThreadFork.execution.test.ts +++ b/apps/server/src/orchestration-v2/ThreadFork.execution.test.ts @@ -21,7 +21,7 @@ import { CodexProviderCapabilitiesV2 } from "./Adapters/CodexAdapterV2.ts"; import { ClaudeProviderCapabilitiesV2 } from "./Adapters/ClaudeAdapterV2.ts"; import * as EventSink from "./EventSink.ts"; import * as Orchestrator from "./Orchestrator.ts"; -import type { ProviderAdapterV2Shape } from "./ProviderAdapter.ts"; +import type { ProviderAdapterV2Shape } from "@t3tools/provider-core/server/ProviderAdapter"; import * as ProviderAdapterRegistry from "./ProviderAdapterRegistry.ts"; import * as ProviderReplayHarness from "./testkit/ProviderReplayHarness.ts"; diff --git a/apps/server/src/orchestration-v2/ThreadLaunchService.test.ts b/apps/server/src/orchestration-v2/ThreadLaunchService.test.ts index 3395c03204604e8e8744aa839025285d1468f5c2..bfbd078e00c5d0d63075ac237af47e7bf4f0f741 100644 --- a/apps/server/src/orchestration-v2/ThreadLaunchService.test.ts +++ b/apps/server/src/orchestration-v2/ThreadLaunchService.test.ts @@ -53,8 +53,8 @@ import * as TextGeneration from "../textGeneration/TextGeneration.ts"; import { CodexProviderCapabilitiesV2 } from "./Adapters/CodexAdapterV2.ts"; import * as CommandReceiptStore from "./CommandReceiptStore.ts"; import * as EffectOutbox from "./EffectOutbox.ts"; -import * as IdAllocator from "./IdAllocator.ts"; -import type { ProviderAdapterV2Shape } from "./ProviderAdapter.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; +import type { ProviderAdapterV2Shape } from "@t3tools/provider-core/server/ProviderAdapter"; import * as ProviderAdapterRegistry from "./ProviderAdapterRegistry.ts"; import * as ThreadLaunch from "./ThreadLaunchService.ts"; import * as ThreadManagement from "./ThreadManagementService.ts"; diff --git a/apps/server/src/orchestration-v2/ThreadLaunchService.ts b/apps/server/src/orchestration-v2/ThreadLaunchService.ts index b4a6a9ce8f420bcad1321ed9e020b743989a1a2c..10af1aef454d2d00e6b9f1b4d2de68d70d392aff 100644 --- a/apps/server/src/orchestration-v2/ThreadLaunchService.ts +++ b/apps/server/src/orchestration-v2/ThreadLaunchService.ts @@ -43,10 +43,10 @@ import * as ProviderRegistry from "../provider/ProviderRegistry.ts"; import * as ServerSettings from "../serverSettings.ts"; import * as TextGeneration from "../textGeneration/TextGeneration.ts"; import * as CommandReceiptStore from "./CommandReceiptStore.ts"; -import * as IdAllocator from "./IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import type * as Orchestrator from "./Orchestrator.ts"; -import { makeProviderFailure } from "./ProviderFailure.ts"; -import { randomUuidV4 } from "./RandomUuid.ts"; +import { makeProviderFailure } from "@t3tools/provider-core/server/failure"; +import { randomUuidV4 } from "@t3tools/provider-core/server/randomUuid"; import * as ThreadManagement from "./ThreadManagementService.ts"; export type ThreadLaunchWorkspaceStrategy = diff --git a/apps/server/src/orchestration-v2/ThreadStop.test.ts b/apps/server/src/orchestration-v2/ThreadStop.test.ts index 60a251d019fa7ca0a4bfba5ebc951b914e8bd3c2..43a77a50e75c0b927a2f4ae232ad671e16ea46d6 100644 --- a/apps/server/src/orchestration-v2/ThreadStop.test.ts +++ b/apps/server/src/orchestration-v2/ThreadStop.test.ts @@ -24,7 +24,7 @@ import { CodexProviderCapabilitiesV2 } from "./Adapters/CodexAdapterV2.ts"; import { OrchestrationEffectRequestV2 } from "./EffectOutbox.ts"; import * as Orchestrator from "./Orchestrator.ts"; import * as ProjectionStore from "./ProjectionStore.ts"; -import type { ProviderAdapterV2Shape } from "./ProviderAdapter.ts"; +import type { ProviderAdapterV2Shape } from "@t3tools/provider-core/server/ProviderAdapter"; import * as ProviderAdapterRegistry from "./ProviderAdapterRegistry.ts"; import * as ThreadManagementService from "./ThreadManagementService.ts"; import * as ProviderReplayHarness from "./testkit/ProviderReplayHarness.ts"; diff --git a/apps/server/src/orchestration-v2/ThreadTitleRegenerationService.test.ts b/apps/server/src/orchestration-v2/ThreadTitleRegenerationService.test.ts index 837f08927164f583eb7d3ea73978e2977d716f21..392dc3fdaee75b981ce762c53cb0bce39dc09711 100644 --- a/apps/server/src/orchestration-v2/ThreadTitleRegenerationService.test.ts +++ b/apps/server/src/orchestration-v2/ThreadTitleRegenerationService.test.ts @@ -22,7 +22,7 @@ import * as ServerSettings from "../serverSettings.ts"; import * as TextGeneration from "../textGeneration/TextGeneration.ts"; import { CodexProviderCapabilitiesV2 } from "./Adapters/CodexAdapterV2.ts"; import * as EffectOutbox from "./EffectOutbox.ts"; -import type { ProviderAdapterV2Shape } from "./ProviderAdapter.ts"; +import type { ProviderAdapterV2Shape } from "@t3tools/provider-core/server/ProviderAdapter"; import * as ProviderAdapterRegistry from "./ProviderAdapterRegistry.ts"; import * as ThreadManagement from "./ThreadManagementService.ts"; import * as ThreadTitleRegeneration from "./ThreadTitleRegenerationService.ts"; diff --git a/apps/server/src/orchestration-v2/ThreadTitleRegenerationService.ts b/apps/server/src/orchestration-v2/ThreadTitleRegenerationService.ts index 4d3961019314e832603fcabb6109d9be7314ed26..dd3aeb52797f1fc86ead2208ac43cf92bd40c41c 100644 --- a/apps/server/src/orchestration-v2/ThreadTitleRegenerationService.ts +++ b/apps/server/src/orchestration-v2/ThreadTitleRegenerationService.ts @@ -19,8 +19,8 @@ import type { OrchestratorV2Error } from "./Orchestrator.ts"; import * as ProjectStore from "./ProjectStore.ts"; import * as ThreadManagementService from "./ThreadManagementService.ts"; -import { formatThreadTitleContext } from "../textGeneration/ThreadTitleContext.ts"; -export { formatThreadTitleContext } from "../textGeneration/ThreadTitleContext.ts"; +import { formatThreadTitleContext } from "@t3tools/provider-core/server/threadTitleContext"; +export { formatThreadTitleContext } from "@t3tools/provider-core/server/threadTitleContext"; export class ThreadTitleRegenerationService extends Context.Service< ThreadTitleRegenerationService, diff --git a/apps/server/src/orchestration-v2/assistantStreaming.test.ts b/apps/server/src/orchestration-v2/assistantStreaming.test.ts index 72b7cb065b1cf08ac970da1e5a8c43f3e81978b8..2580936b0dfb1f6cf3b0b2e5351898033113f024 100644 --- a/apps/server/src/orchestration-v2/assistantStreaming.test.ts +++ b/apps/server/src/orchestration-v2/assistantStreaming.test.ts @@ -2,7 +2,7 @@ import { describe, expect, it } from "vite-plus/test"; import { MessageId, NodeId, ProviderDriverKind, ThreadId, TurnItemId } from "@t3tools/contracts"; import * as DateTime from "effect/DateTime"; import { makeAssistantStreamingFilter, splitBufferedAssistantText } from "./assistantStreaming.ts"; -import type { ProviderAdapterV2Event } from "./ProviderAdapter.ts"; +import type { ProviderAdapterV2Event } from "@t3tools/provider-core/server/ProviderAdapter"; const message = (text: string, streaming = true): ProviderAdapterV2Event => ({ type: "message.updated", diff --git a/apps/server/src/orchestration-v2/assistantStreaming.ts b/apps/server/src/orchestration-v2/assistantStreaming.ts index fbac5013d635e645332a12662f0507db5c38539f..4c70dbbfc35e3b84ba6be3a3a8d4a39b1116614e 100644 --- a/apps/server/src/orchestration-v2/assistantStreaming.ts +++ b/apps/server/src/orchestration-v2/assistantStreaming.ts @@ -1,5 +1,5 @@ import type { ResponseStreamingMode } from "@t3tools/contracts"; -import type { ProviderAdapterV2Event } from "./ProviderAdapter.ts"; +import type { ProviderAdapterV2Event } from "@t3tools/provider-core/server/ProviderAdapter"; // An opening fence may sit at any indentation, since fences inside list // items are indented past the marker. A closing fence may be indented at most diff --git a/apps/server/src/orchestration-v2/builtInProviderAdapterDrivers.ts b/apps/server/src/orchestration-v2/builtInProviderAdapterDrivers.ts index 4e912c4d6a2ff2b49ecb90997643fd9ec1caed84..c9d2b397471375862550ee087c69e2be5029765e 100644 --- a/apps/server/src/orchestration-v2/builtInProviderAdapterDrivers.ts +++ b/apps/server/src/orchestration-v2/builtInProviderAdapterDrivers.ts @@ -19,7 +19,7 @@ import { type OpenCodeAdapterV2DriverEnv, } from "./Adapters/OpenCodeAdapterV2.ts"; import { PiAdapterV2Driver, type PiAdapterV2DriverEnv } from "./Adapters/PiAdapterV2.ts"; -import type { AnyProviderAdapterDriver } from "./ProviderAdapterDriver.ts"; +import type { AnyProviderAdapterDriver } from "@t3tools/provider-core/server/adapterDriver"; export type BuiltInProviderAdapterDriversV2Env = | AcpRegistryAdapterV2DriverEnv diff --git a/apps/server/src/orchestration-v2/legacy/LegacyV1Cutover.integration.test.ts b/apps/server/src/orchestration-v2/legacy/LegacyV1Cutover.integration.test.ts index 65d8100d9195dba2da6f8c5b98e86173e6d1c1ce..803bc7ce09029e9caf0ea1a75b8ddf05a55afaaa 100644 --- a/apps/server/src/orchestration-v2/legacy/LegacyV1Cutover.integration.test.ts +++ b/apps/server/src/orchestration-v2/legacy/LegacyV1Cutover.integration.test.ts @@ -48,10 +48,10 @@ import { ProviderAdapterProtocolError, type ProviderAdapterV2Event, type ProviderAdapterV2Shape, -} from "../ProviderAdapter.ts"; +} from "@t3tools/provider-core/server/ProviderAdapter"; import * as ProviderAdapterRegistry from "../ProviderAdapterRegistry.ts"; import * as ProviderReplayHarness from "../testkit/ProviderReplayHarness.ts"; -import { checkpointWorkspace } from "../testkit/ReplayFixtureWorkspace.ts"; +import { checkpointWorkspace } from "@t3tools/provider-testing/replayWorkspace"; const PROJECT_ID = "project:cutover"; const ACTIVE_THREAD = "thread:cutover:active"; diff --git a/apps/server/src/orchestration-v2/legacy/LegacyV1ThreadImporter.ts b/apps/server/src/orchestration-v2/legacy/LegacyV1ThreadImporter.ts index 86fcff68b7daae263124c44d72ec7bc756b33782..90c29723407a73c3123970754eb50240f8d5b8af 100644 --- a/apps/server/src/orchestration-v2/legacy/LegacyV1ThreadImporter.ts +++ b/apps/server/src/orchestration-v2/legacy/LegacyV1ThreadImporter.ts @@ -31,7 +31,7 @@ import * as Schema from "effect/Schema"; import * as SqlClient from "effect/sql/SqlClient"; import * as EventSink from "../EventSink.ts"; -import { randomUuidV4 } from "../RandomUuid.ts"; +import { randomUuidV4 } from "@t3tools/provider-core/server/randomUuid"; const IMPORT_EVENT_PREFIX = "migration:v1"; const TRANSCRIPT_EVENT_BATCH_SIZE = 100; diff --git a/apps/server/src/orchestration-v2/runtimeLayer.test.ts b/apps/server/src/orchestration-v2/runtimeLayer.test.ts index 79411e6fcc55ffad3f7e881153dcbac42b2aada7..aed7f73e6c0f705ed96923be5be33976dd7f5d2b 100644 --- a/apps/server/src/orchestration-v2/runtimeLayer.test.ts +++ b/apps/server/src/orchestration-v2/runtimeLayer.test.ts @@ -50,7 +50,7 @@ import * as ProjectService from "../project/ProjectService.ts"; import * as ServerSettings from "../serverSettings.ts"; import * as McpSessionRegistryTestkit from "../mcp/McpSessionRegistry.testkit.ts"; import * as ProviderInstanceRegistry from "../provider/ProviderInstanceRegistry.ts"; -import type { ProviderInstance } from "../provider/ProviderDriver.ts"; +import type { ProviderInstance } from "@t3tools/provider-core/server/driver"; import * as VcsDriverRegistry from "../vcs/VcsDriverRegistry.ts"; import * as VcsProcess from "../vcs/VcsProcess.ts"; import * as WorkspacePaths from "../workspace/WorkspacePaths.ts"; @@ -67,7 +67,10 @@ import * as PullRequestWatchReactor from "./PullRequestWatchReactor.ts"; import { PullRequestProviderError } from "../pullRequest/PullRequestProvider.ts"; import * as PullRequestService from "../pullRequest/PullRequestService.ts"; import * as ProjectStore from "./ProjectStore.ts"; -import type { ProviderAdapterV2SessionRuntime, ProviderAdapterV2Shape } from "./ProviderAdapter.ts"; +import type { + ProviderAdapterV2SessionRuntime, + ProviderAdapterV2Shape, +} from "@t3tools/provider-core/server/ProviderAdapter"; import * as ProviderSessionManager from "./ProviderSessionManager.ts"; import * as RuntimeLayer from "./runtimeLayer.ts"; import { shellStreamItemFromThreadShell } from "./ShellStream.ts"; diff --git a/apps/server/src/orchestration-v2/runtimeLayer.ts b/apps/server/src/orchestration-v2/runtimeLayer.ts index 9cf3351f5d252200f9fc273bc2b3cc87816e6043..d12491cc0eb091f862e6e7bc17cff4116c211343 100644 --- a/apps/server/src/orchestration-v2/runtimeLayer.ts +++ b/apps/server/src/orchestration-v2/runtimeLayer.ts @@ -23,7 +23,7 @@ import * as EffectOutbox from "./EffectOutbox.ts"; import * as EffectWorker from "./EffectWorker.ts"; import * as EventSink from "./EventSink.ts"; import * as EventStore from "./EventStore.ts"; -import * as IdAllocator from "./IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import * as LegacyV1ThreadImporter from "./legacy/LegacyV1ThreadImporter.ts"; import * as Orchestrator from "./Orchestrator.ts"; import * as ProjectionStore from "./ProjectionStore.ts"; diff --git a/apps/server/src/orchestration-v2/testkit/ClaudeReplayFixtures.integration.test.ts b/apps/server/src/orchestration-v2/testkit/ClaudeReplayFixtures.integration.test.ts index d20a8d0b6160e6af2bc8c9b12432137553061dfe..67f7aa9468151de2f90060f876ca2b9cc004513d 100644 --- a/apps/server/src/orchestration-v2/testkit/ClaudeReplayFixtures.integration.test.ts +++ b/apps/server/src/orchestration-v2/testkit/ClaudeReplayFixtures.integration.test.ts @@ -11,7 +11,7 @@ import * as Effect from "effect/Effect"; import { classifyClaudeNativeTool } from "../Adapters/ClaudeAdapterV2.ts"; import { ClaudeOrchestratorReplayHarness } from "../Adapters/ClaudeAdapterV2.testkit.ts"; -import * as IdAllocator from "../IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import * as Orchestrator from "../Orchestrator.ts"; import { userFacingDispatchErrorMessage } from "../UserFacingErrors.ts"; import { provideDeterministicTestRuntime } from "./DeterministicRuntime.ts"; @@ -19,7 +19,7 @@ import { ORCHESTRATOR_REPLAY_FIXTURES } from "./fixtures/index.ts"; import { subagentInput } from "./fixtures/subagent/input.ts"; import { runOrchestratorV2Scenario } from "./OrchestratorScenario.ts"; import * as ProviderReplayHarness from "./ProviderReplayHarness.ts"; -import { materializeReplayTranscriptRuntimeInstructions } from "./ReplayTranscriptNdjson.ts"; +import { materializeReplayTranscriptRuntimeInstructions } from "./ReplayRuntimeInstructions.ts"; import { CLAUDE_MODEL_SELECTION, materializeFixtureInput } from "./fixtures/shared.ts"; import { THREAD_FORK_NATIVE_CONTINUE_FORK_MARKER, @@ -33,7 +33,7 @@ import { THREAD_MERGE_BACK_SIBLINGS_SOURCE_MARKER, THREAD_MERGE_BACK_SOURCE_MARKER, } from "./fixtures/shared.ts"; -import { readProviderReplayTranscript } from "./ReplayTranscriptNdjson.ts"; +import { readProviderReplayTranscript } from "@t3tools/provider-testing/replayTranscript"; const readTranscript = Effect.fn("readClaudeReplayFixture")(function* (file: URL) { return yield* readProviderReplayTranscript(file); diff --git a/apps/server/src/orchestration-v2/testkit/CodexReplayFixtures.integration.test.ts b/apps/server/src/orchestration-v2/testkit/CodexReplayFixtures.integration.test.ts index c04f9b326c816443e9cbf4690f0808633a782b4a..eb2482cb6547b023e6c0634ab1d5a3abec5c9b2b 100644 --- a/apps/server/src/orchestration-v2/testkit/CodexReplayFixtures.integration.test.ts +++ b/apps/server/src/orchestration-v2/testkit/CodexReplayFixtures.integration.test.ts @@ -18,7 +18,7 @@ import { THREAD_MERGE_BACK_SIBLINGS_SOURCE_MARKER, THREAD_MERGE_BACK_SOURCE_MARKER, } from "./fixtures/shared.ts"; -import { readProviderReplayTranscript } from "./ReplayTranscriptNdjson.ts"; +import { readProviderReplayTranscript } from "@t3tools/provider-testing/replayTranscript"; const PROVIDER_THREAD_RESUME_FIRST_FINAL = "provider thread resume fixture first turn complete"; const PROVIDER_THREAD_RESUME_SECOND_FINAL = "provider thread resume fixture second turn complete"; diff --git a/apps/server/src/orchestration-v2/testkit/OrchestratorReplayFixtures.contract.test.ts b/apps/server/src/orchestration-v2/testkit/OrchestratorReplayFixtures.contract.test.ts index e0cd30fe5ba3bac933bd1cfa5aec0d17ff6901c8..3b0956ecb540e8275ac1992de22439c9efbe98da 100644 --- a/apps/server/src/orchestration-v2/testkit/OrchestratorReplayFixtures.contract.test.ts +++ b/apps/server/src/orchestration-v2/testkit/OrchestratorReplayFixtures.contract.test.ts @@ -4,11 +4,11 @@ import { OrchestrationV2Command, ProviderInstanceId } from "@t3tools/contracts"; import * as Effect from "effect/Effect"; import * as Schema from "effect/Schema"; -import * as IdAllocator from "../IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import { provideDeterministicTestRuntime } from "./DeterministicRuntime.ts"; import { ORCHESTRATOR_REPLAY_FIXTURES } from "./fixtures/index.ts"; import { materializeFixtureInput } from "./fixtures/shared.ts"; -import { readProviderReplayTranscript } from "./ReplayTranscriptNdjson.ts"; +import { readProviderReplayTranscript } from "@t3tools/provider-testing/replayTranscript"; const decodeCommand = Schema.decodeUnknownEffect(OrchestrationV2Command); const readTranscript = Effect.fn("readOrchestratorReplayContractTranscript")(function* (file: URL) { diff --git a/apps/server/src/orchestration-v2/testkit/OrchestratorReplayFixtures.integration.test.ts b/apps/server/src/orchestration-v2/testkit/OrchestratorReplayFixtures.integration.test.ts index a3925ea409c9d42db0b64c77c8265ded1e17978c..db7ee893b355d9ba276bb07c0516f8bab1af66ff 100644 --- a/apps/server/src/orchestration-v2/testkit/OrchestratorReplayFixtures.integration.test.ts +++ b/apps/server/src/orchestration-v2/testkit/OrchestratorReplayFixtures.integration.test.ts @@ -21,7 +21,7 @@ import { } from "../Adapters/OpenCode2AdapterV2.testkit.ts"; import { MuseOrchestratorReplayHarness } from "../Adapters/MuseAdapterV2.testkit.ts"; import { PiOrchestratorReplayHarness } from "../Adapters/PiAdapterV2.testkit.ts"; -import * as IdAllocator from "../IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import { provideDeterministicTestRuntime } from "./DeterministicRuntime.ts"; import { ORCHESTRATOR_REPLAY_FIXTURES } from "./fixtures/index.ts"; import { messageRestartInput } from "./fixtures/message_steering/input.ts"; @@ -36,12 +36,12 @@ import { runOrchestratorV2ProviderReplayScenario, type OrchestratorV2ProviderReplayHarness, } from "./ProviderReplayHarness.ts"; -import { checkpointWorkspace } from "./ReplayFixtureWorkspace.ts"; +import { checkpointWorkspace } from "@t3tools/provider-testing/replayWorkspace"; +import { materializeReplayTranscriptRuntimeInstructions } from "./ReplayRuntimeInstructions.ts"; import { - materializeReplayTranscriptRuntimeInstructions, materializeReplayTranscriptWorkspace, readProviderReplayTranscript, -} from "./ReplayTranscriptNdjson.ts"; +} from "@t3tools/provider-testing/replayTranscript"; const readTranscript = Effect.fn("readOrchestratorReplayTranscript")(function* (file: URL) { return yield* readProviderReplayTranscript(file); diff --git a/apps/server/src/orchestration-v2/testkit/OrchestratorReplayRecovery.integration.test.ts b/apps/server/src/orchestration-v2/testkit/OrchestratorReplayRecovery.integration.test.ts index 21ba303966ecbf92d459c1083224ef0a74916bb7..b3c979715b850fb634488e12b89057739a4cdb84 100644 --- a/apps/server/src/orchestration-v2/testkit/OrchestratorReplayRecovery.integration.test.ts +++ b/apps/server/src/orchestration-v2/testkit/OrchestratorReplayRecovery.integration.test.ts @@ -20,7 +20,7 @@ import { makeCursorAgentSdkReplayRunner, } from "../Adapters/CursorAdapterV2.testkit.ts"; import * as CursorAdapterV2Testkit from "../Adapters/CursorAdapterV2.testkit.ts"; -import * as IdAllocator from "../IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import * as SqlitePersistence from "../../persistence/Sqlite.ts"; import { provideDeterministicTestRuntime } from "./DeterministicRuntime.ts"; import { @@ -43,12 +43,12 @@ import { projectionFor, } from "./fixtures/shared.ts"; import { runOrchestratorV2ProviderReplayScenario } from "./ProviderReplayHarness.ts"; -import { checkpointWorkspace } from "./ReplayFixtureWorkspace.ts"; +import { checkpointWorkspace } from "@t3tools/provider-testing/replayWorkspace"; +import { materializeReplayTranscriptRuntimeInstructions } from "./ReplayRuntimeInstructions.ts"; import { - materializeReplayTranscriptRuntimeInstructions, materializeReplayTranscriptWorkspace, readProviderReplayTranscript, -} from "./ReplayTranscriptNdjson.ts"; +} from "@t3tools/provider-testing/replayTranscript"; const FIRST_FINAL = "provider thread resume fixture first turn complete"; const SECOND_FINAL = "provider thread resume fixture second turn complete"; diff --git a/apps/server/src/orchestration-v2/testkit/OrchestratorReplayRestartBackgroundNote.integration.test.ts b/apps/server/src/orchestration-v2/testkit/OrchestratorReplayRestartBackgroundNote.integration.test.ts index 320310a94717e513063c0dca05a065dcb7fe33a5..574eaa40e147d614c49d5b81328ee23beb2be2a1 100644 --- a/apps/server/src/orchestration-v2/testkit/OrchestratorReplayRestartBackgroundNote.integration.test.ts +++ b/apps/server/src/orchestration-v2/testkit/OrchestratorReplayRestartBackgroundNote.integration.test.ts @@ -10,7 +10,7 @@ import { ClaudeOrchestratorReplayHarness, makeClaudeRestartReplayHarness, } from "../Adapters/ClaudeAdapterV2.testkit.ts"; -import * as IdAllocator from "../IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import * as EffectWorker from "../EffectWorker.ts"; import * as SqlitePersistence from "../../persistence/Sqlite.ts"; import { provideDeterministicTestRuntime } from "./DeterministicRuntime.ts"; @@ -23,8 +23,8 @@ import { import { runOrchestratorV2ProviderReplayScenario } from "./ProviderReplayHarness.ts"; import * as ProviderReplayHarness from "./ProviderReplayHarness.ts"; import { runOrchestratorV2Scenario } from "./OrchestratorScenario.ts"; -import { checkpointWorkspace } from "./ReplayFixtureWorkspace.ts"; -import { readProviderReplayTranscript } from "./ReplayTranscriptNdjson.ts"; +import { checkpointWorkspace } from "@t3tools/provider-testing/replayWorkspace"; +import { readProviderReplayTranscript } from "@t3tools/provider-testing/replayTranscript"; const SCENARIO = "claude_background_subagent_after_root"; const SESSION_ID = "cca274e4-25ae-4171-b972-bbb31118517e"; diff --git a/apps/server/src/orchestration-v2/testkit/OrchestratorScenario.ts b/apps/server/src/orchestration-v2/testkit/OrchestratorScenario.ts index 0bb2d5053b4bb3ef81c7c34f8464c408edca0f02..3d8ef589050e68d583ddf542add8591e8086294f 100644 --- a/apps/server/src/orchestration-v2/testkit/OrchestratorScenario.ts +++ b/apps/server/src/orchestration-v2/testkit/OrchestratorScenario.ts @@ -23,7 +23,7 @@ import * as Stream from "effect/Stream"; import { TestClock } from "effect/testing"; import * as Orchestrator from "../Orchestrator.ts"; -import type { ProviderReplayGate } from "./ProviderReplayGate.testkit.ts"; +import type { ProviderReplayGate } from "@t3tools/provider-testing/replayGate"; export type OrchestratorV2ScenarioStep = | { diff --git a/apps/server/src/orchestration-v2/testkit/ProviderReplayHarness.ts b/apps/server/src/orchestration-v2/testkit/ProviderReplayHarness.ts index 230ad7aa0feb8e8fcc5c2db14a5e98d711610f6f..1307b2a77df6489fae9b0408a7690421cb8f0ff2 100644 --- a/apps/server/src/orchestration-v2/testkit/ProviderReplayHarness.ts +++ b/apps/server/src/orchestration-v2/testkit/ProviderReplayHarness.ts @@ -29,7 +29,7 @@ import * as EffectOutbox from "../EffectOutbox.ts"; import * as EffectWorker from "../EffectWorker.ts"; import * as EventSink from "../EventSink.ts"; import * as EventStore from "../EventStore.ts"; -import * as IdAllocator from "../IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import * as Orchestrator from "../Orchestrator.ts"; import * as ProjectionStore from "../ProjectionStore.ts"; import * as ProjectStore from "../ProjectStore.ts"; @@ -59,7 +59,10 @@ import { type OrchestratorV2Scenario, type OrchestratorV2ScenarioResult, } from "./OrchestratorScenario.ts"; -import { makeProviderReplayGate, type ProviderReplayGate } from "./ProviderReplayGate.testkit.ts"; +import { + makeProviderReplayGate, + type ProviderReplayGate, +} from "@t3tools/provider-testing/replayGate"; export function makeReplayServerConfig( scenario: string, diff --git a/apps/server/src/orchestration-v2/testkit/ProviderSwitch.integration.test.ts b/apps/server/src/orchestration-v2/testkit/ProviderSwitch.integration.test.ts index 40569de3c7b55ae9456cde29cad3349dffd0387a..732e04408c276f47ded4e61bb6856ad3ddd93ae9 100644 --- a/apps/server/src/orchestration-v2/testkit/ProviderSwitch.integration.test.ts +++ b/apps/server/src/orchestration-v2/testkit/ProviderSwitch.integration.test.ts @@ -59,9 +59,9 @@ import { ProviderAdapterTurnStartError, type ProviderAdapterV2Shape, type ProviderAdapterV2SessionRuntime, -} from "../ProviderAdapter.ts"; +} from "@t3tools/provider-core/server/ProviderAdapter"; import * as ProviderAdapterRegistry from "../ProviderAdapterRegistry.ts"; -import { makeProviderFailure } from "../ProviderFailure.ts"; +import { makeProviderFailure } from "@t3tools/provider-core/server/failure"; import { CLAUDE_MODEL_SELECTION, CODEX_MODEL_SELECTION, @@ -69,7 +69,7 @@ import { GROK_MODEL_SELECTION, } from "./fixtures/shared.ts"; import * as ProviderReplayHarness from "./ProviderReplayHarness.ts"; -import { checkpointWorkspace } from "./ReplayFixtureWorkspace.ts"; +import { checkpointWorkspace } from "@t3tools/provider-testing/replayWorkspace"; const encodeJson = Schema.encodeEffect(Schema.fromJsonString(Schema.Unknown)); diff --git a/apps/server/src/orchestration-v2/testkit/ProviderTurnStartMemory.fixture.mjs b/apps/server/src/orchestration-v2/testkit/ProviderTurnStartMemory.fixture.mjs index f17d4b5ef48385d5c8333615ec3c8cf7663c2948..203360ee9215b9f91dea4eb0b5775f0e5320b5dc 100644 --- a/apps/server/src/orchestration-v2/testkit/ProviderTurnStartMemory.fixture.mjs +++ b/apps/server/src/orchestration-v2/testkit/ProviderTurnStartMemory.fixture.mjs @@ -13,6 +13,8 @@ const [Effect, Layer, FileSystem] = await Promise.all([ load("FileSystem"), ]); const app = (file) => import(NodeURL.pathToFileURL(root + "/apps/server/src/" + file + ".ts")); +const providerCore = (file) => + import(NodeURL.pathToFileURL(root + "/packages/provider-core/src/server/" + file + ".ts")); const [Start, Projection, Run, Sessions, Policy, Id, Sink, Handoff, Git, Project, Auth] = await Promise.all([ app("orchestration-v2/ProviderTurnStartService"), @@ -20,7 +22,7 @@ const [Start, Projection, Run, Sessions, Policy, Id, Sink, Handoff, Git, Project app("orchestration-v2/RunExecutionService"), app("orchestration-v2/ProviderSessionManager"), app("orchestration-v2/RuntimePolicy"), - app("orchestration-v2/IdAllocator"), + providerCore("IdAllocator"), app("orchestration-v2/EventSink"), app("orchestration-v2/ContextHandoffService"), app("git/GitWorkflowService"), diff --git a/apps/server/src/orchestration-v2/testkit/ReplayRuntimeInstructions.ts b/apps/server/src/orchestration-v2/testkit/ReplayRuntimeInstructions.ts new file mode 100644 index 0000000000000000000000000000000000000000..18f87d1f7a4f299ff4c28cd2efe119f098bc502e --- /dev/null +++ b/apps/server/src/orchestration-v2/testkit/ReplayRuntimeInstructions.ts @@ -0,0 +1,70 @@ +import type { ProviderDriverKind, ProviderReplayTranscript } from "@t3tools/contracts"; + +import { buildRuntimeInstructions } from "../../provider/RuntimeInstructions.ts"; + +/** Adds current runtime context to legacy prompt expectations, keeping outbound matching exact. */ +export function materializeReplayTranscriptRuntimeInstructions( + transcript: ProviderReplayTranscript, + runtime: { readonly driver: ProviderDriverKind; readonly model: string }, +): ProviderReplayTranscript { + const harness = + runtime.driver === "cursor" + ? "Cursor" + : runtime.driver === "grok" + ? "Grok" + : runtime.driver === "acpRegistry" + ? "acpRegistry" + : undefined; + if (harness === undefined) return transcript; + const instructions = buildRuntimeInstructions({ harness, model: runtime.model }); + + return { + ...transcript, + entries: transcript.entries.map((entry) => { + if (entry.type !== "expect_outbound") return entry; + const frame = entry.frame; + if (typeof frame !== "object" || frame === null) return entry; + if ( + runtime.driver === "cursor" && + "type" in frame && + frame.type === "run.start" && + "message" in frame && + typeof frame.message === "string" + ) { + return frame.message.endsWith(instructions) + ? entry + : { ...entry, frame: { ...frame, message: `${frame.message}\n\n${instructions}` } }; + } + if ( + "method" in frame && + frame.method === "session/prompt" && + "params" in frame && + typeof frame.params === "object" && + frame.params !== null && + "prompt" in frame.params && + Array.isArray(frame.params.prompt) + ) { + const prompt: ReadonlyArray = frame.params.prompt; + const lastPart = prompt.at(-1); + if ( + typeof lastPart === "object" && + lastPart !== null && + "type" in lastPart && + lastPart.type === "text" && + "text" in lastPart && + lastPart.text === instructions + ) { + return entry; + } + return { + ...entry, + frame: { + ...frame, + params: { ...frame.params, prompt: [...prompt, { type: "text", text: instructions }] }, + }, + }; + } + return entry; + }), + }; +} diff --git a/apps/server/src/orchestration-v2/testkit/ThreadFork.integration.test.ts b/apps/server/src/orchestration-v2/testkit/ThreadFork.integration.test.ts index a40cb9f5d8637c85c5c5c532f6b16e4f4181d71a..96ba1fe2c172a12fac3c0c851b2c39c4006a168a 100644 --- a/apps/server/src/orchestration-v2/testkit/ThreadFork.integration.test.ts +++ b/apps/server/src/orchestration-v2/testkit/ThreadFork.integration.test.ts @@ -18,7 +18,7 @@ import { ChildProcess, ChildProcessSpawner } from "effect/process"; import { ClaudeOrchestratorReplayHarness } from "../Adapters/ClaudeAdapterV2.testkit.ts"; import { CodexOrchestratorReplayHarness } from "../Adapters/CodexAdapterV2.testkit.ts"; -import * as IdAllocator from "../IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import { provideDeterministicTestRuntime } from "./DeterministicRuntime.ts"; import { THREAD_FORK_NATIVE_PRIOR_TURN_ALPHA_PROMPT, @@ -31,7 +31,7 @@ import { runOrchestratorV2ProviderReplayScenario } from "./ProviderReplayHarness import { decodeProviderReplayNdjson, materializeReplayTranscriptWorkspace, -} from "./ReplayTranscriptNdjson.ts"; +} from "@t3tools/provider-testing/replayTranscript"; const CODEX_MODEL_SELECTION = { instanceId: ProviderInstanceId.make("codex"), diff --git a/apps/server/src/orchestration-v2/testkit/ThreadMergeBack.integration.test.ts b/apps/server/src/orchestration-v2/testkit/ThreadMergeBack.integration.test.ts index e22d847037ab6bea218cc96b6fb15e69bb55f35f..30928887d308c7e8735850a604bd2126508c936d 100644 --- a/apps/server/src/orchestration-v2/testkit/ThreadMergeBack.integration.test.ts +++ b/apps/server/src/orchestration-v2/testkit/ThreadMergeBack.integration.test.ts @@ -19,7 +19,7 @@ import * as ProviderAdapterRegistry from "../ProviderAdapterRegistry.ts"; import { ClaudeOrchestratorReplayHarness } from "../Adapters/ClaudeAdapterV2.testkit.ts"; import { CodexOrchestratorReplayHarness } from "../Adapters/CodexAdapterV2.testkit.ts"; -import * as IdAllocator from "../IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import { provideDeterministicTestRuntime } from "./DeterministicRuntime.ts"; import { CODEX_MODEL_SELECTION, @@ -37,11 +37,11 @@ import { THREAD_MERGE_BACK_SOURCE_PROMPT, } from "./fixtures/shared.ts"; import { runOrchestratorV2ProviderReplayScenario } from "./ProviderReplayHarness.ts"; -import { makeCheckpointWorkspace } from "./ReplayFixtureWorkspace.ts"; +import { makeCheckpointWorkspace } from "@t3tools/provider-testing/replayWorkspace"; import { decodeProviderReplayNdjson, materializeReplayTranscriptWorkspace, -} from "./ReplayTranscriptNdjson.ts"; +} from "@t3tools/provider-testing/replayTranscript"; // These recorded 0.137 rollouts predate injection. Preserve their native fork // and turn exchanges, and assert the new history delivery at the adapter boundary. diff --git a/apps/server/src/orchestration-v2/testkit/fixtures/shared.ts b/apps/server/src/orchestration-v2/testkit/fixtures/shared.ts index ed2a32ad6eb6adaa163a200432dcf5bf894d658f..1fda1cbf649d37984aa7a7255cd14de0dcb44b0c 100644 --- a/apps/server/src/orchestration-v2/testkit/fixtures/shared.ts +++ b/apps/server/src/orchestration-v2/testkit/fixtures/shared.ts @@ -27,7 +27,7 @@ import type { OrchestratorV2ScenarioResult, OrchestratorV2ScenarioStep, } from "../OrchestratorScenario.ts"; -import * as IdAllocator from "../../IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import type { RuntimePolicyV2Override } from "../../RuntimePolicy.ts"; export const SIMPLE_PROMPT = "Respond with the following text: fixture simple ok"; diff --git a/apps/server/src/processRunner.ts b/apps/server/src/processRunner.ts index 3fd4734069f35aca715224a205951263de752595..2a6cc235d7e000abc72b3d16629200f72fe5ecc5 100644 --- a/apps/server/src/processRunner.ts +++ b/apps/server/src/processRunner.ts @@ -9,13 +9,12 @@ import * as Scope from "effect/Scope"; import * as Stream from "effect/Stream"; import * as ChildProcess from "effect/process/ChildProcess"; import * as ChildProcessSpawner from "effect/process/ChildProcessSpawner"; -import { HostProcessPlatform } from "@t3tools/shared/hostProcess"; import { resolveSpawnCommand } from "@t3tools/shared/shell"; import { collectUint8StreamText, decodeUtf8, type CollectedUint8StreamText, -} from "./stream/collectUint8StreamText.ts"; +} from "@t3tools/provider-core/server/collectStreamText"; export interface ProcessRunInput { readonly command: string; @@ -149,27 +148,7 @@ export class ProcessRunner extends Context.Service< const DEFAULT_TIMEOUT = "60 seconds"; const DEFAULT_MAX_OUTPUT_BYTES = 8 * 1024 * 1024; -const WINDOWS_COMMAND_NOT_FOUND_PATTERNS = [ - /is not recognized as an internal or external command/i, - /n.o . reconhecido como um comando interno/i, - /non . riconosciuto come comando interno o esterno/i, - /n.est pas reconnu en tant que commande interne/i, - /no se reconoce como un comando interno o externo/i, - /wird nicht als interner oder externer befehl/i, -] as const; - -function hasWindowsCommandNotFoundMessage(output: string): boolean { - return WINDOWS_COMMAND_NOT_FOUND_PATTERNS.some((pattern) => pattern.test(output)); -} - -export const isWindowsCommandNotFound = Effect.fn("processRunner.isWindowsCommandNotFound")( - function* (code: number | null, stderr: string) { - const platform = yield* HostProcessPlatform; - if (platform !== "win32") return false; - if (code === 9009) return true; - return hasWindowsCommandNotFoundMessage(stderr); - }, -); +export { isWindowsCommandNotFound } from "@t3tools/provider-core/server/snapshotProbe"; // Untraced: no attributes, and its time is the runProcessCore span. Errors fail that span. const collectText = Effect.fnUntraced(function* (input: { diff --git a/apps/server/src/project/AgentSessionImporter.test.ts b/apps/server/src/project/AgentSessionImporter.test.ts index 182426b83751eeb266c7d9ee147c9b6e7527d217..3a1ab5d0a7e6b72fb4af72f02f7bbc8640375e90 100644 --- a/apps/server/src/project/AgentSessionImporter.test.ts +++ b/apps/server/src/project/AgentSessionImporter.test.ts @@ -11,7 +11,7 @@ import * as Option from "effect/Option"; import * as Stream from "effect/Stream"; import * as EventSink from "../orchestration-v2/EventSink.ts"; -import * as IdAllocator from "../orchestration-v2/IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import * as Orchestrator from "../orchestration-v2/Orchestrator.ts"; import * as ProviderSessionRuntime from "../persistence/ProviderSessionRuntime.ts"; import * as AgentSessionImporter from "./AgentSessionImporter.ts"; diff --git a/apps/server/src/project/AgentSessionImporter.ts b/apps/server/src/project/AgentSessionImporter.ts index 43ce8096b8ea7fba542c3af4cc0a322ee0bba99e..2c8d6a49d4c7d8129a6295a382f4f944e8428cf4 100644 --- a/apps/server/src/project/AgentSessionImporter.ts +++ b/apps/server/src/project/AgentSessionImporter.ts @@ -32,7 +32,7 @@ import * as Schema from "effect/Schema"; import * as Stream from "effect/Stream"; import * as EventSink from "../orchestration-v2/EventSink.ts"; -import * as IdAllocator from "../orchestration-v2/IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import * as Orchestrator from "../orchestration-v2/Orchestrator.ts"; import * as ProviderSessionRuntime from "../persistence/ProviderSessionRuntime.ts"; import * as AgentSessionScanner from "./AgentSessionScanner.ts"; diff --git a/apps/server/src/project/AgentSessionScanner.ts b/apps/server/src/project/AgentSessionScanner.ts index bc30691784db42955682d43d8989d0d4aab64b46..d67b5d72639c17ac5491ba7a852390c03b48d9b3 100644 --- a/apps/server/src/project/AgentSessionScanner.ts +++ b/apps/server/src/project/AgentSessionScanner.ts @@ -50,7 +50,7 @@ import { normalizeProjectPathForComparison } from "@t3tools/shared/path"; import * as ServerConfig from "../config.ts"; import * as ProjectStore from "../orchestration-v2/ProjectStore.ts"; import { resolveCodexHomeLayout } from "../provider/Drivers/CodexHomeLayout.ts"; -import { expandHomePath } from "../pathExpansion.ts"; +import { expandHomePath } from "@t3tools/provider-core/server/pathExpansion"; import * as ServerSettings from "../serverSettings.ts"; import { createTranscriptJsonReader, diff --git a/apps/server/src/project/ProjectService.deletion.test.ts b/apps/server/src/project/ProjectService.deletion.test.ts index 48ad979d151bde653cd9d307f7cdb71613a64f74..746c139f6fc8b831f26ff082858ec2e359c1be42 100644 --- a/apps/server/src/project/ProjectService.deletion.test.ts +++ b/apps/server/src/project/ProjectService.deletion.test.ts @@ -20,7 +20,7 @@ import * as ServerConfig from "../config.ts"; import { OrchestrationEffectRequestV2 } from "../orchestration-v2/EffectOutbox.ts"; import * as EventSink from "../orchestration-v2/EventSink.ts"; import * as EventStore from "../orchestration-v2/EventStore.ts"; -import * as IdAllocator from "../orchestration-v2/IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import * as LegacyV1ThreadImporter from "../orchestration-v2/legacy/LegacyV1ThreadImporter.ts"; import * as ProjectionMaintenance from "../orchestration-v2/ProjectionMaintenance.ts"; import * as ProjectionStore from "../orchestration-v2/ProjectionStore.ts"; diff --git a/apps/server/src/project/ProjectService.test.ts b/apps/server/src/project/ProjectService.test.ts index 809184b36d098c91af7e55606cce742c5f4c6eb8..09d4f82297718fc2aad3672c6372c2b60a26d3c8 100644 --- a/apps/server/src/project/ProjectService.test.ts +++ b/apps/server/src/project/ProjectService.test.ts @@ -12,7 +12,7 @@ import * as SqlClient from "effect/sql/SqlClient"; import * as ServerConfig from "../config.ts"; import * as EventSink from "../orchestration-v2/EventSink.ts"; -import * as IdAllocator from "../orchestration-v2/IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import * as LegacyV1ThreadImporter from "../orchestration-v2/legacy/LegacyV1ThreadImporter.ts"; import * as ProjectionStore from "../orchestration-v2/ProjectionStore.ts"; import * as ProjectStore from "../orchestration-v2/ProjectStore.ts"; diff --git a/apps/server/src/project/ProjectService.ts b/apps/server/src/project/ProjectService.ts index 247ff0aaa925aa9e70313d75141cfbbba473c79f..f37b4e383061f71fe97d5cb3775e93ef7959a5b3 100644 --- a/apps/server/src/project/ProjectService.ts +++ b/apps/server/src/project/ProjectService.ts @@ -18,7 +18,7 @@ import * as Result from "effect/Result"; import * as Schema from "effect/Schema"; import * as EventSink from "../orchestration-v2/EventSink.ts"; -import * as IdAllocator from "../orchestration-v2/IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import * as LegacyV1ThreadImporter from "../orchestration-v2/legacy/LegacyV1ThreadImporter.ts"; import * as ProjectionStore from "../orchestration-v2/ProjectionStore.ts"; import { diff --git a/apps/server/src/provider/AntigravityProvider.test.ts b/apps/server/src/provider/AntigravityProvider.test.ts index 259b5d5cf4cc0fc771a016202e6dfc48636c9831..77a436aaf7be2094feec3bcf1883c98186ced1db 100644 --- a/apps/server/src/provider/AntigravityProvider.test.ts +++ b/apps/server/src/provider/AntigravityProvider.test.ts @@ -1,3 +1,4 @@ +import * as NodeServices from "@effect/platform-node/NodeServices"; import { describe, expect, it } from "@effect/vitest"; import { ANTIGRAVITY_DEFAULT_MODEL, @@ -18,7 +19,9 @@ import * as EffectAcpErrors from "effect-acp/errors"; import type * as EffectAcpSchema from "effect-acp/compat"; import * as BackgroundPolicy from "../background/BackgroundPolicy.ts"; +import * as ServerConfig from "../config.ts"; import * as ServerSettings from "../serverSettings.ts"; +import * as ProviderHostLive from "./ProviderHostLive.ts"; import type { AcpSessionRuntimeStartResult } from "./acp/AcpSessionRuntime.ts"; import { buildAntigravityModelsFromSession, @@ -106,11 +109,18 @@ const expectedCommands = [ { name: "logout", description: "Sign out of Google" }, ]; -const layerTest = Layer.merge( - Layer.mock(BackgroundPolicy.BackgroundPolicy)({ - shouldRunScopeWork: () => Effect.succeed(false), - }), - ServerSettings.layerTest(), +const layerTest = ProviderHostLive.layer.pipe( + Layer.provideMerge( + Layer.mock(BackgroundPolicy.BackgroundPolicy)({ + shouldRunScopeWork: () => Effect.succeed(false), + }), + ), + Layer.provideMerge(ServerSettings.layerTest()), + Layer.provide( + ServerConfig.layerTest(process.cwd(), { prefix: "t3-antigravity-provider-test-" }).pipe( + Layer.provide(NodeServices.layer), + ), + ), ); type ProbeError = EffectAcpErrors.AcpError | ProviderSetupError; diff --git a/apps/server/src/provider/AntigravityProvider.ts b/apps/server/src/provider/AntigravityProvider.ts index a644b020d38c32547aa7ca469bddbc88705f5789..ca6c0391491af25894755f637337234c3f44b4ec 100644 --- a/apps/server/src/provider/AntigravityProvider.ts +++ b/apps/server/src/provider/AntigravityProvider.ts @@ -23,12 +23,12 @@ import { makeManagedServerProvider } from "./makeManagedServerProvider.ts"; import { makeManualOnlyProviderMaintenanceCapabilities, type ProviderMaintenanceCapabilities, -} from "./providerMaintenance.ts"; +} from "@t3tools/provider-core/server/maintenanceResolver"; import { buildServerProvider, isCommandMissingCause, type ServerProviderDraft, -} from "./providerSnapshot.ts"; +} from "@t3tools/provider-core/server/snapshotProbe"; const EMPTY_MODEL_CAPABILITIES = createModelCapabilities({ optionDescriptors: [] }); const MAX_WORKSPACE_SNAPSHOTS = 32; diff --git a/apps/server/src/provider/ClaudeCapabilitiesProbe.test.ts b/apps/server/src/provider/ClaudeCapabilitiesProbe.test.ts index 831df2d172ec2c60239d5512071f2fcfb8635e94..5d63060493d952c88ac2167c0695158cc5a1865b 100644 --- a/apps/server/src/provider/ClaudeCapabilitiesProbe.test.ts +++ b/apps/server/src/provider/ClaudeCapabilitiesProbe.test.ts @@ -24,7 +24,7 @@ import { probeClaudeCapabilities, probeClaudeWorkspaceSnapshot, } from "./ClaudeProvider.ts"; -import { COMPACT_SLASH_COMMAND } from "./providerSnapshot.ts"; +import { COMPACT_SLASH_COMMAND } from "@t3tools/provider-core/server/snapshotProbe"; vi.mock("@anthropic-ai/claude-agent-sdk", { spy: true }); diff --git a/apps/server/src/provider/ClaudeProvider.ts b/apps/server/src/provider/ClaudeProvider.ts index 37945bbb79af746a53828f62876fbb40cf486a60..0770a50f873a06b3c2b4d427e8fe87287b120bf5 100644 --- a/apps/server/src/provider/ClaudeProvider.ts +++ b/apps/server/src/provider/ClaudeProvider.ts @@ -33,12 +33,12 @@ import { providerModelsFromSettings, spawnAndCollect, type ServerProviderDraft, -} from "./providerSnapshot.ts"; +} from "@t3tools/provider-core/server/snapshotProbe"; import { resolveClaudeSdkExecutablePath } from "./Drivers/ClaudeExecutable.ts"; import { makeClaudeEnvironment } from "./Drivers/ClaudeHome.ts"; import { discoverClaudeSkills } from "./Drivers/ClaudeSkills.ts"; -import type { ProviderWorkspaceSnapshot } from "./ProviderDriver.ts"; -import { makeUnavailableUsageLimits } from "./providerUsageLimits.ts"; +import type { ProviderWorkspaceSnapshot } from "@t3tools/provider-core/server/driver"; +import { makeUnavailableUsageLimits } from "@t3tools/provider-core/server/usageLimits"; import { type ClaudeScopedLimitNames, claudeUsageResponseToLimits, diff --git a/apps/server/src/provider/CodexDeveloperInstructions.ts b/apps/server/src/provider/CodexDeveloperInstructions.ts index e498ed03a13e6da6ecbdc166b18151e2c5a61174..e9cbe27997abb1e80c97a560830f02d3cf91de84 100644 --- a/apps/server/src/provider/CodexDeveloperInstructions.ts +++ b/apps/server/src/provider/CodexDeveloperInstructions.ts @@ -5,7 +5,7 @@ import { buildRuntimeInstructions } from "./RuntimeInstructions.ts"; import { T3_CODE_BROWSER_TOOL_INSTRUCTIONS, T3_CODE_ORCHESTRATION_INSTRUCTIONS, -} from "./T3OrchestrationInstructions.ts"; +} from "@t3tools/provider-core/server/orchestrationInstructions"; const T3_CODE_DEVICE_TOOL_INSTRUCTIONS = `## T3 Code devices diff --git a/apps/server/src/provider/CodexProvider.ts b/apps/server/src/provider/CodexProvider.ts index 979849e95cbcbf7002aceceeba61982e2c7f9e87..ac3b299b18bf003dc2f285dba45bdb9683e05578 100644 --- a/apps/server/src/provider/CodexProvider.ts +++ b/apps/server/src/provider/CodexProvider.ts @@ -38,9 +38,9 @@ import { buildServerProvider, COMPACT_SLASH_COMMAND, type ServerProviderDraft, -} from "./providerSnapshot.ts"; -import { expandHomePath } from "../pathExpansion.ts"; -import { makeUnavailableUsageLimits } from "./providerUsageLimits.ts"; +} from "@t3tools/provider-core/server/snapshotProbe"; +import { expandHomePath } from "@t3tools/provider-core/server/pathExpansion"; +import { makeUnavailableUsageLimits } from "@t3tools/provider-core/server/usageLimits"; import { codexRateLimitsFailureMessage, codexRateLimitsToLimits, diff --git a/apps/server/src/provider/CodexToolPresentation.ts b/apps/server/src/provider/CodexToolPresentation.ts index 42561286caec7414b27ac8eed77df1b8fc96d607..323d068aa067ef357c5f9717ba57954c1db80d48 100644 --- a/apps/server/src/provider/CodexToolPresentation.ts +++ b/apps/server/src/provider/CodexToolPresentation.ts @@ -12,7 +12,7 @@ import { mcpToolPresentation as integrationToolPresentation, normalizeMcpHttpUrl as normalizedHttpUrl, normalizeMcpText as normalizedDisplayName, -} from "./McpToolPresentation.ts"; +} from "@t3tools/provider-core/server/mcpToolPresentation"; type CodexLifecycleItem = EffectCodexSchema.V2ItemCompletedNotification["item"]; diff --git a/apps/server/src/provider/CursorProvider.ts b/apps/server/src/provider/CursorProvider.ts index 7c0ab4d2e868df09d21fc2e5386134d2595f79ea..473a7bb8c5aae0ea255d111bb196b7e65fb3053c 100644 --- a/apps/server/src/provider/CursorProvider.ts +++ b/apps/server/src/provider/CursorProvider.ts @@ -20,7 +20,7 @@ import { buildServerProvider, providerModelsFromSettings, type ServerProviderDraft, -} from "./providerSnapshot.ts"; +} from "@t3tools/provider-core/server/snapshotProbe"; import * as CursorSdkCatalog from "./CursorSdkCatalog.ts"; const CURSOR_PRESENTATION = { diff --git a/apps/server/src/provider/Drivers/AcpRegistryDriver.ts b/apps/server/src/provider/Drivers/AcpRegistryDriver.ts index 4d01dcf6aa8651858d973bbc843c1677dbe83cad..da992744b36fb0a6110ffa3857befb99831cdc1d 100644 --- a/apps/server/src/provider/Drivers/AcpRegistryDriver.ts +++ b/apps/server/src/provider/Drivers/AcpRegistryDriver.ts @@ -21,24 +21,23 @@ import * as Schema from "effect/Schema"; import * as Semaphore from "effect/Semaphore"; import { ChildProcessSpawner } from "effect/process"; -import * as BackgroundPolicy from "../../background/BackgroundPolicy.ts"; +import { ProviderHost } from "@t3tools/provider-core/server/ProviderHost"; import * as ServerConfig from "../../config.ts"; import { AcpRegistryAdapterV2Driver, type AcpRegistryAdapterV2DriverEnv, } from "../../orchestration-v2/Adapters/AcpRegistryAdapterV2.ts"; -import * as ServerSettings from "../../serverSettings.ts"; import type { TextGeneration } from "../../textGeneration/TextGeneration.ts"; import { ProviderDriverError } from "../Errors.ts"; import { makeManagedServerProvider } from "../makeManagedServerProvider.ts"; -import { mergeProviderInstanceEnvironment } from "../ProviderInstanceEnvironment.ts"; +import { mergeProviderInstanceEnvironment } from "@t3tools/provider-core/server/instanceEnvironment"; import { defaultProviderContinuationIdentity, type ProviderDriver, type ProviderInstance, -} from "../ProviderDriver.ts"; -import { providerModelsFromSettings } from "../providerSnapshot.ts"; -import { makeManualOnlyProviderMaintenanceCapabilities } from "../providerMaintenance.ts"; +} from "@t3tools/provider-core/server/driver"; +import { providerModelsFromSettings } from "@t3tools/provider-core/server/snapshotProbe"; +import { makeManualOnlyProviderMaintenanceCapabilities } from "@t3tools/provider-core/server/maintenanceResolver"; import { haveProviderSnapshotSettingsChanged, makeProviderSnapshotSettingsSource, @@ -460,10 +459,7 @@ export const checkAcpRegistryProviderReadiness = Effect.fn( : snapshot; }); -export type AcpRegistryDriverEnv = - | AcpRegistryAdapterV2DriverEnv - | BackgroundPolicy.BackgroundPolicy - | ServerSettings.ServerSettingsService; +export type AcpRegistryDriverEnv = AcpRegistryAdapterV2DriverEnv | ProviderHost; /** Canonical provider-instance wrapper for ACP Registry orchestration adapters. */ export const AcpRegistryDriver: ProviderDriver = { @@ -493,7 +489,7 @@ export const AcpRegistryDriver: ProviderDriver >({ diff --git a/apps/server/src/provider/Drivers/AntigravityDriver.test.ts b/apps/server/src/provider/Drivers/AntigravityDriver.test.ts index e0c52801bc81abaea6e51ce4c3fb7273a24ecf82..d08cacb60dcde9c5dd60d2ea532e0543f07c6dc3 100644 --- a/apps/server/src/provider/Drivers/AntigravityDriver.test.ts +++ b/apps/server/src/provider/Drivers/AntigravityDriver.test.ts @@ -31,8 +31,9 @@ import { } from "../antigravityAuthSupport.ts"; import * as ProviderEventLoggers from "../ProviderEventLoggers.ts"; import * as ModelManifest from "../ModelManifest.ts"; -import * as IdAllocator from "../../orchestration-v2/IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import { AntigravityDriver } from "./AntigravityDriver.ts"; +import * as ProviderHostLive from "../ProviderHostLive.ts"; const hostPlatform = HostProcessPlatform.defaultValue(); const windowsHost = hostPlatform === "win32"; @@ -244,7 +245,7 @@ const makeHarness = Effect.fn("makeAntigravityDriverHarness")(function* ( }; }); -const layerTest = ServerConfig.layerTest(process.cwd(), { +const layerDeps = ServerConfig.layerTest(process.cwd(), { prefix: "t3-antigravity-driver-config-", }).pipe( Layer.provideMerge(NodeServices.layer), @@ -263,6 +264,7 @@ const layerTest = ServerConfig.layerTest(process.cwd(), { Layer.provideMerge(ModelManifest.layerTest), Layer.provideMerge(IdAllocator.layer), ); +const layerTest = ProviderHostLive.layer.pipe(Layer.provideMerge(layerDeps)); it.layer(layerTest)("AntigravityDriver", (it) => { it.effect.skipIf(windowsHost)( diff --git a/apps/server/src/provider/Drivers/AntigravityDriver.ts b/apps/server/src/provider/Drivers/AntigravityDriver.ts index 29e103c453b68c53c754b0305e8f8798f0dee146..817dbff73570d394720e0424d8032c5a48fc0ffc 100644 --- a/apps/server/src/provider/Drivers/AntigravityDriver.ts +++ b/apps/server/src/provider/Drivers/AntigravityDriver.ts @@ -1,4 +1,4 @@ -import { withAgentDeviceEnvironment } from "../../mcp/McpProviderSession.ts"; +import { withAgentDeviceEnvironment } from "@t3tools/provider-core/server/mcpSession"; import { AntigravitySettings, ProviderDriverKind, ProviderSetupError } from "@t3tools/contracts"; import { HostProcessPlatform } from "@t3tools/shared/hostProcess"; import { resolveSelfInvocation } from "@t3tools/shared/nodeRuntime"; @@ -18,9 +18,8 @@ import * as Stream from "effect/Stream"; import * as ChildProcessSpawner from "effect/process/ChildProcessSpawner"; import type { AcpError } from "effect-acp/errors"; -import * as BackgroundPolicy from "../../background/BackgroundPolicy.ts"; +import { ProviderHost } from "@t3tools/provider-core/server/ProviderHost"; import * as ServerConfig from "../../config.ts"; -import * as ServerSettings from "../../serverSettings.ts"; import { isAntigravityTextGenerationAvailable, makeAntigravityTextGeneration, @@ -42,12 +41,12 @@ import { type AntigravityAcpRuntimeInput, } from "../acp/AntigravityAcpSupport.ts"; import type { AcpSessionRuntime, AcpSessionRuntimeStartResult } from "../acp/AcpSessionRuntime.ts"; -import type { ServerProviderDraft } from "../providerSnapshot.ts"; +import type { ServerProviderDraft } from "@t3tools/provider-core/server/snapshotProbe"; import { removeAntigravityRuntimeTempDirs, removeAntigravitySessionFiles, } from "../acp/AntigravitySessionFiles.ts"; -import * as IdAllocator from "../../orchestration-v2/IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import * as ProviderContinuationRequests from "../../orchestration-v2/ProviderContinuationRequests.ts"; import { makeAntigravityAdapterV2 } from "../../orchestration-v2/Adapters/AntigravityAdapterV2.ts"; import { makeAcpNativeLoggerFactory } from "../acp/AcpNativeLogging.ts"; @@ -59,8 +58,8 @@ import { defaultProviderContinuationIdentity, type ProviderDriver, type ProviderInstance, -} from "../ProviderDriver.ts"; -import { mergeProviderInstanceEnvironment } from "../ProviderInstanceEnvironment.ts"; +} from "@t3tools/provider-core/server/driver"; +import { mergeProviderInstanceEnvironment } from "@t3tools/provider-core/server/instanceEnvironment"; import { withInstanceIdentity } from "./instanceIdentity.ts"; import { discoverAntigravitySkills, resolveAntigravityUserHome } from "./AntigravitySkills.ts"; @@ -70,7 +69,7 @@ const isNodeRuntimeUnavailableError = Schema.is(NodeRuntimeUnavailableError); export type AntigravityDriverEnv = | AntigravityInstallation.AntigravityInstallation - | BackgroundPolicy.BackgroundPolicy + | ProviderHost | ChildProcessSpawner.ChildProcessSpawner | Crypto.Crypto | FileSystem.FileSystem @@ -78,8 +77,7 @@ export type AntigravityDriverEnv = | ModelManifest.ModelManifest | Path.Path | ProviderEventLoggers.ProviderEventLoggers - | ServerConfig.ServerConfig - | ServerSettings.ServerSettingsService; + | ServerConfig.ServerConfig; /** Each instance owns its Google profile. Executable releases are shared by the environment. */ export const AntigravityDriver: ProviderDriver = { diff --git a/apps/server/src/provider/Drivers/ClaudeDriver.ts b/apps/server/src/provider/Drivers/ClaudeDriver.ts index 4f32cf9d2b5aae262fa58160635e239aa5752ef6..55dfe036b98ec6aa89a6cf0d792cc9c11b4f5d74 100644 --- a/apps/server/src/provider/Drivers/ClaudeDriver.ts +++ b/apps/server/src/provider/Drivers/ClaudeDriver.ts @@ -24,15 +24,14 @@ import { HttpClient } from "effect/http"; import { ChildProcessSpawner } from "effect/process"; import { makeClaudeTextGeneration } from "../../textGeneration/ClaudeTextGeneration.ts"; -import * as BackgroundPolicy from "../../background/BackgroundPolicy.ts"; +import { ProviderHost } from "@t3tools/provider-core/server/ProviderHost"; import * as ServerConfig from "../../config.ts"; -import { expandHomePath } from "../../pathExpansion.ts"; +import { expandHomePath } from "@t3tools/provider-core/server/pathExpansion"; import * as ProviderEventLoggers from "../ProviderEventLoggers.ts"; import { createClaudeAdapterV2, type ClaudeAdapterV2DriverEnv, } from "../../orchestration-v2/Adapters/ClaudeAdapterV2.ts"; -import * as ServerSettings from "../../serverSettings.ts"; import { ProviderDriverError } from "../Errors.ts"; import { makeClaudeScopedLimitNames } from "../claudeUsageLimits.ts"; import * as ClaudeResetCredits from "../claudeResetCredits.ts"; @@ -50,16 +49,16 @@ import { defaultProviderContinuationIdentity, type ProviderDriver, type ProviderInstance, -} from "../ProviderDriver.ts"; +} from "@t3tools/provider-core/server/driver"; import { withInstanceIdentity } from "./instanceIdentity.ts"; -import { mergeProviderInstanceEnvironment } from "../ProviderInstanceEnvironment.ts"; +import { mergeProviderInstanceEnvironment } from "@t3tools/provider-core/server/instanceEnvironment"; import { enrichProviderSnapshotWithVersionAdvisory, makeCachedProviderMaintenanceResolution, makePackageManagedProviderMaintenanceResolver, normalizeCommandPath, resolveProviderMaintenanceCapabilitiesEffect, -} from "../providerMaintenance.ts"; +} from "@t3tools/provider-core/server/maintenanceResolver"; import { haveProviderSnapshotSettingsChanged, makeProviderSnapshotSettingsSource, @@ -95,7 +94,7 @@ const UPDATE = makePackageManagedProviderMaintenanceResolver({ export type ClaudeDriverEnv = | ClaudeAdapterV2DriverEnv - | BackgroundPolicy.BackgroundPolicy + | ProviderHost | ChildProcessSpawner.ChildProcessSpawner | ResetCreditCoordinator.ResetCreditCoordinator | Crypto.Crypto @@ -104,8 +103,7 @@ export type ClaudeDriverEnv = | ModelManifest.ModelManifest | Path.Path | ProviderEventLoggers.ProviderEventLoggers - | ServerConfig.ServerConfig - | ServerSettings.ServerSettingsService; + | ServerConfig.ServerConfig; export const ClaudeDriver: ProviderDriver = { driverKind: DRIVER_KIND, @@ -123,7 +121,7 @@ export const ClaudeDriver: ProviderDriver = { const { cwd } = yield* ServerConfig.ServerConfig; const httpClient = yield* HttpClient.HttpClient; const resetCreditCoordinator = yield* ResetCreditCoordinator.ResetCreditCoordinator; - const serverSettings = yield* ServerSettings.ServerSettingsService; + const host = yield* ProviderHost; const modelManifest = yield* ModelManifest.ModelManifest; const modelCatalog = modelManifest.current.pipe(Effect.map(resolveClaudeModelCatalog)); const processEnv = mergeProviderInstanceEnvironment(environment); @@ -237,7 +235,7 @@ export const ClaudeDriver: ProviderDriver = { Effect.provideService(Path.Path, path), ); - const snapshotSettings = makeProviderSnapshotSettingsSource(effectiveConfig, serverSettings); + const snapshotSettings = makeProviderSnapshotSettingsSource(effectiveConfig, host.settings); const snapshot = yield* makeManagedServerProvider>({ resolveMaintenance, getSettings: snapshotSettings.getSettings, diff --git a/apps/server/src/provider/Drivers/ClaudeHome.ts b/apps/server/src/provider/Drivers/ClaudeHome.ts index 70699ca669e86e25ed5e3b6e935e97bf6d0ef1bb..8104401868a3f318d13a0b88e9c1f44e9f4c1807 100644 --- a/apps/server/src/provider/Drivers/ClaudeHome.ts +++ b/apps/server/src/provider/Drivers/ClaudeHome.ts @@ -5,7 +5,7 @@ import * as Effect from "effect/Effect"; import * as Path from "effect/Path"; import * as Schema from "effect/Schema"; -import { expandHomePath } from "../../pathExpansion.ts"; +import { expandHomePath } from "@t3tools/provider-core/server/pathExpansion"; const quotePath = Schema.encodeSync(Schema.fromJsonString(Schema.String)); diff --git a/apps/server/src/provider/Drivers/ClaudeSkills.ts b/apps/server/src/provider/Drivers/ClaudeSkills.ts index 8c9c9c669faad44d84fee95e2cb5679c03e7850f..3ef7d925e031d12cc5e8df6c4fddc5cb9dc01bc5 100644 --- a/apps/server/src/provider/Drivers/ClaudeSkills.ts +++ b/apps/server/src/provider/Drivers/ClaudeSkills.ts @@ -24,7 +24,7 @@ import { HostProcessPlatform } from "@t3tools/shared/hostProcess"; import { fromLenientJson } from "@t3tools/shared/schemaJson"; import { parse as parseYamlDocument } from "yaml"; -import { expandHomePath } from "../../pathExpansion.ts"; +import { expandHomePath } from "@t3tools/provider-core/server/pathExpansion"; type ClaudeSkillScope = "user" | "project"; diff --git a/apps/server/src/provider/Drivers/CodexDriver.test.ts b/apps/server/src/provider/Drivers/CodexDriver.test.ts index f732d6d5bba53036298a1eb5913d7b1a6c7b6a86..72340b7471cf08f3d327aa23d8bce79f710ad6c4 100644 --- a/apps/server/src/provider/Drivers/CodexDriver.test.ts +++ b/apps/server/src/provider/Drivers/CodexDriver.test.ts @@ -32,14 +32,15 @@ import { createProviderVersionAdvisory, ProviderVersionCache, resolveLatestProviderVersion, -} from "../providerMaintenance.ts"; +} from "@t3tools/provider-core/server/maintenanceResolver"; import { CodexDriver } from "./CodexDriver.ts"; import * as CodexAdapterV2 from "../../orchestration-v2/Adapters/CodexAdapterV2.ts"; -import * as IdAllocator from "../../orchestration-v2/IdAllocator.ts"; -import { ProviderAdapterV2RuntimePolicy } from "../../orchestration-v2/ProviderAdapter.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; +import { ProviderAdapterV2RuntimePolicy } from "@t3tools/provider-core/server/ProviderAdapter"; import * as ProviderCredentialStore from "../ProviderCredentialStore.ts"; +import * as ProviderHostLive from "../ProviderHostLive.ts"; -const layerTest = ServerConfig.layerTest(process.cwd(), { +const layerDeps = ServerConfig.layerTest(process.cwd(), { prefix: "t3-codex-driver-maintenance-", }).pipe( Layer.provideMerge(NodeServices.layer), @@ -81,6 +82,7 @@ const layerTest = ServerConfig.layerTest(process.cwd(), { ), ), ); +const layerTest = ProviderHostLive.layer.pipe(Layer.provideMerge(layerDeps)); // The `#!/bin/sh` stub below cannot be resolved as an executable on Windows. const windowsHost = HostProcessPlatform.defaultValue() === "win32"; diff --git a/apps/server/src/provider/Drivers/CodexDriver.ts b/apps/server/src/provider/Drivers/CodexDriver.ts index 0b958e2978a5f8f12ba09c53ad68794049d52e5c..885a89b65c66eedd7caf2c3dd5e0d1a328f14dbd 100644 --- a/apps/server/src/provider/Drivers/CodexDriver.ts +++ b/apps/server/src/provider/Drivers/CodexDriver.ts @@ -31,15 +31,14 @@ import { HttpClient } from "effect/http"; import { ChildProcessSpawner } from "effect/process"; import { makeCodexTextGeneration } from "../../textGeneration/CodexTextGeneration.ts"; -import * as BackgroundPolicy from "../../background/BackgroundPolicy.ts"; +import { ProviderHost } from "@t3tools/provider-core/server/ProviderHost"; import * as ServerConfig from "../../config.ts"; -import { expandHomePath } from "../../pathExpansion.ts"; +import { expandHomePath } from "@t3tools/provider-core/server/pathExpansion"; import * as ProviderEventLoggers from "../ProviderEventLoggers.ts"; import { createCodexAdapterV2, type CodexAdapterV2DriverEnv, } from "../../orchestration-v2/Adapters/CodexAdapterV2.ts"; -import * as ServerSettings from "../../serverSettings.ts"; import { ProviderDriverError } from "../Errors.ts"; import * as ResetCreditCoordinator from "../resetCreditCoordinator.ts"; import { @@ -51,16 +50,16 @@ import { import { resolveCodexLaunchArgs } from "../codexLaunchArgs.ts"; import { makeManagedServerProvider } from "../makeManagedServerProvider.ts"; import * as ModelManifest from "../ModelManifest.ts"; -import type { ProviderDriver, ProviderInstance } from "../ProviderDriver.ts"; +import type { ProviderDriver, ProviderInstance } from "@t3tools/provider-core/server/driver"; import { withInstanceIdentity } from "./instanceIdentity.ts"; -import { mergeProviderInstanceEnvironment } from "../ProviderInstanceEnvironment.ts"; +import { mergeProviderInstanceEnvironment } from "@t3tools/provider-core/server/instanceEnvironment"; import { enrichProviderSnapshotWithVersionAdvisory, makeCachedProviderMaintenanceResolution, makePackageManagedProviderMaintenanceResolver, normalizeCommandPath, resolveProviderMaintenanceCapabilitiesEffect, -} from "../providerMaintenance.ts"; +} from "@t3tools/provider-core/server/maintenanceResolver"; import { haveProviderSnapshotSettingsChanged, makeProviderSnapshotSettingsSource, @@ -109,7 +108,7 @@ function makeCodexMaintenanceResolver(sharedHomePath: string) { */ export type CodexDriverEnv = | CodexAdapterV2DriverEnv - | BackgroundPolicy.BackgroundPolicy + | ProviderHost | ChildProcessSpawner.ChildProcessSpawner | ResetCreditCoordinator.ResetCreditCoordinator | Crypto.Crypto @@ -119,7 +118,6 @@ export type CodexDriverEnv = | Path.Path | ProviderEventLoggers.ProviderEventLoggers | ServerConfig.ServerConfig - | ServerSettings.ServerSettingsService | ServerSecretStore.ServerSecretStore | ServerEnvironment.ServerEnvironmentIdentity | CodexInstallation.CodexInstallation; @@ -148,7 +146,7 @@ export const CodexDriver: ProviderDriver = { const fileSystem = yield* FileSystem.FileSystem; const pathService = yield* Path.Path; const httpClient = yield* HttpClient.HttpClient; - const serverSettings = yield* ServerSettings.ServerSettingsService; + const host = yield* ProviderHost; const modelManifest = yield* ModelManifest.ModelManifest; const processEnv = mergeProviderInstanceEnvironment(environment); const homeLayout = yield* resolveCodexHomeLayout(config); @@ -232,7 +230,7 @@ export const CodexDriver: ProviderDriver = { ), Effect.provideService(ChildProcessSpawner.ChildProcessSpawner, spawner), ); - const snapshotSettings = makeProviderSnapshotSettingsSource(effectiveConfig, serverSettings); + const snapshotSettings = makeProviderSnapshotSettingsSource(effectiveConfig, host.settings); const snapshot = yield* makeManagedServerProvider>({ resolveMaintenance, getSettings: snapshotSettings.getSettings, diff --git a/apps/server/src/provider/Drivers/CodexHomeLayout.ts b/apps/server/src/provider/Drivers/CodexHomeLayout.ts index 8efd0b5d994abf66dd5acae0e9cca00d63584919..544e0574483269bbb87dfdc3ee4c199429530731 100644 --- a/apps/server/src/provider/Drivers/CodexHomeLayout.ts +++ b/apps/server/src/provider/Drivers/CodexHomeLayout.ts @@ -7,7 +7,7 @@ import * as Path from "effect/Path"; import * as Schema from "effect/Schema"; import * as PlatformError from "effect/PlatformError"; -import { expandHomePath } from "../../pathExpansion.ts"; +import { expandHomePath } from "@t3tools/provider-core/server/pathExpansion"; export interface CodexHomeLayout { readonly mode: "direct" | "authOverlay"; diff --git a/apps/server/src/provider/Drivers/CodexManagedProvider.ts b/apps/server/src/provider/Drivers/CodexManagedProvider.ts index b75e1edd5414e9e26822f21d1903dd887ccc811b..e702548000dc4303d6091cf1158b20d51a455278 100644 --- a/apps/server/src/provider/Drivers/CodexManagedProvider.ts +++ b/apps/server/src/provider/Drivers/CodexManagedProvider.ts @@ -4,7 +4,7 @@ import * as Stream from "effect/Stream"; import * as Option from "effect/Option"; import { ChildProcessSpawner } from "effect/process"; import { makeCodexTextGeneration } from "../../textGeneration/CodexTextGeneration.ts"; -import { ServerSettingsService } from "../../serverSettings.ts"; +import { ProviderHost } from "@t3tools/provider-core/server/ProviderHost"; import { chatGptModels } from "../CodexChatGptModels.ts"; import { makeCodexManagedRuntime } from "../CodexManagedRuntime.ts"; import { ProviderDriverError } from "../Errors.ts"; @@ -15,8 +15,11 @@ import { probeCodexSkillsForCwd, } from "../CodexProvider.ts"; import { makeManagedServerProvider } from "../makeManagedServerProvider.ts"; -import { mergeProviderInstanceEnvironment } from "../ProviderInstanceEnvironment.ts"; -import { type ProviderDriverCreateInput, type ProviderInstance } from "../ProviderDriver.ts"; +import { mergeProviderInstanceEnvironment } from "@t3tools/provider-core/server/instanceEnvironment"; +import { + type ProviderDriverCreateInput, + type ProviderInstance, +} from "@t3tools/provider-core/server/driver"; import { codexContinuationIdentity } from "./CodexHomeLayout.ts"; import { withInstanceIdentity } from "./instanceIdentity.ts"; import { HttpClient } from "effect/http"; @@ -28,7 +31,7 @@ export const makeManagedCodexProvider = Effect.fn("makeManagedCodexProvider")(fu const { instanceId, enabled, displayName, accentColor, config } = input; const http = yield* HttpClient.HttpClient; const spawner = yield* ChildProcessSpawner.ChildProcessSpawner; - const settings = yield* ServerSettingsService; + const host = yield* ProviderHost; const runtime = yield* makeCodexManagedRuntime({ instanceId, enabled, @@ -190,8 +193,8 @@ export const makeManagedCodexProvider = Effect.fn("makeManagedCodexProvider")(fu }).pipe(Effect.provideService(ChildProcessSpawner.ChildProcessSpawner, spawner)); const snapshot = yield* makeManagedServerProvider({ resolveMaintenance: () => Effect.succeed({ provider: DRIVER, packageName: null, update: null }), - getSettings: settings.getSettings, - streamSettings: settings.streamChanges, + getSettings: host.settings.get, + streamSettings: host.settings.changes, haveSettingsChanged: () => false, initialSnapshot: () => pending, checkProvider: check, diff --git a/apps/server/src/provider/Drivers/CursorDriver.test.ts b/apps/server/src/provider/Drivers/CursorDriver.test.ts index b0f9c2ad0d4a374e4ece4ea4fd94d984c7ce8dbc..8aae15d1c575a51aaf05808df6f18b4abfc9f4bb 100644 --- a/apps/server/src/provider/Drivers/CursorDriver.test.ts +++ b/apps/server/src/provider/Drivers/CursorDriver.test.ts @@ -17,11 +17,12 @@ import * as ServerSettings from "../../serverSettings.ts"; import * as ProviderEventLoggers from "../ProviderEventLoggers.ts"; import { CursorDriver } from "./CursorDriver.ts"; import * as CursorAgentSdk from "../../orchestration-v2/Adapters/CursorAgentSdk.ts"; -import * as IdAllocator from "../../orchestration-v2/IdAllocator.ts"; -import { ProviderAdapterV2RuntimePolicy } from "../../orchestration-v2/ProviderAdapter.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; +import { ProviderAdapterV2RuntimePolicy } from "@t3tools/provider-core/server/ProviderAdapter"; import { Cursor } from "../cursorSdk.ts"; +import * as ProviderHostLive from "../ProviderHostLive.ts"; -const layerTest = ServerSecretStore.layer.pipe( +const layerDeps = ServerSecretStore.layer.pipe( Layer.provideMerge( ServerConfig.layerTest(process.cwd(), { prefix: "t3-cursor-driver-copy-command-", @@ -53,6 +54,7 @@ const layerTest = ServerSecretStore.layer.pipe( ), ), ); +const layerTest = ProviderHostLive.layer.pipe(Layer.provideMerge(layerDeps)); it.layer(layerTest)("CursorDriver", (it) => { it.effect( diff --git a/apps/server/src/provider/Drivers/CursorDriver.ts b/apps/server/src/provider/Drivers/CursorDriver.ts index f0f55a8cb34801d675aab0f99d032aaa9a422f30..e8bd2eee22e61ed494d1006145a02361abde87b5 100644 --- a/apps/server/src/provider/Drivers/CursorDriver.ts +++ b/apps/server/src/provider/Drivers/CursorDriver.ts @@ -15,7 +15,7 @@ import * as Schema from "effect/Schema"; import { HttpClient } from "effect/http"; import { readCursorUsageLimits } from "../cursorUsageLimits.ts"; -import * as BackgroundPolicy from "../../background/BackgroundPolicy.ts"; +import { ProviderHost } from "@t3tools/provider-core/server/ProviderHost"; import * as ServerConfig from "../../config.ts"; import * as ServerSettings from "../../serverSettings.ts"; import { makeCursorTextGeneration } from "../../textGeneration/CursorTextGeneration.ts"; @@ -34,10 +34,10 @@ import { defaultProviderContinuationIdentity, type ProviderDriver, type ProviderInstance, -} from "../ProviderDriver.ts"; +} from "@t3tools/provider-core/server/driver"; import { withInstanceIdentity } from "./instanceIdentity.ts"; -import { mergeProviderInstanceEnvironment } from "../ProviderInstanceEnvironment.ts"; -import { makeManualOnlyProviderMaintenanceCapabilities } from "../providerMaintenance.ts"; +import { mergeProviderInstanceEnvironment } from "@t3tools/provider-core/server/instanceEnvironment"; +import { makeManualOnlyProviderMaintenanceCapabilities } from "@t3tools/provider-core/server/maintenanceResolver"; import { haveProviderSnapshotSettingsChanged, makeProviderSnapshotSettingsSource, @@ -63,7 +63,7 @@ export type CursorDriverEnv = | FileSystem.FileSystem | Path.Path | HttpClient.HttpClient - | BackgroundPolicy.BackgroundPolicy + | ProviderHost | ServerConfig.ServerConfig | ServerSecretStore.ServerSecretStore | ServerSettings.ServerSettingsService; @@ -79,6 +79,7 @@ export const CursorDriver: ProviderDriver = { create: ({ instanceId, displayName, accentColor, environment, enabled, config }) => Effect.gen(function* () { const serverSettings = yield* ServerSettings.ServerSettingsService; + const host = yield* ProviderHost; const fileSystem = yield* FileSystem.FileSystem; const path = yield* Path.Path; const httpClient = yield* HttpClient.HttpClient; @@ -234,7 +235,7 @@ export const CursorDriver: ProviderDriver = { Effect.provide(CursorSdkCatalog.layer), ); - const snapshotSettings = makeProviderSnapshotSettingsSource(effectiveConfig, serverSettings); + const snapshotSettings = makeProviderSnapshotSettingsSource(effectiveConfig, host.settings); const snapshot = yield* makeManagedServerProvider>({ resolveMaintenance: () => Effect.succeed(MAINTENANCE_CAPABILITIES), getSettings: snapshotSettings.getSettings, diff --git a/apps/server/src/provider/Drivers/GrokDriver.test.ts b/apps/server/src/provider/Drivers/GrokDriver.test.ts index f6d70d1a3476283bdc2f3a119b4ecf890770a8c4..f1737f71f39121909d16fec0cf5daa387821b3bf 100644 --- a/apps/server/src/provider/Drivers/GrokDriver.test.ts +++ b/apps/server/src/provider/Drivers/GrokDriver.test.ts @@ -15,9 +15,10 @@ import * as ServerSettings from "../../serverSettings.ts"; import * as ProviderEventLoggers from "../ProviderEventLoggers.ts"; import { GrokDriver } from "./GrokDriver.ts"; -import * as IdAllocator from "../../orchestration-v2/IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; +import * as ProviderHostLive from "../ProviderHostLive.ts"; -const layerTest = ServerConfig.layerTest(process.cwd(), { +const layerDeps = ServerConfig.layerTest(process.cwd(), { prefix: "t3-grok-driver-update-", }).pipe( Layer.provideMerge(NodeServices.layer), @@ -41,6 +42,7 @@ const layerTest = ServerConfig.layerTest(process.cwd(), { ), ), ); +const layerTest = ProviderHostLive.layer.pipe(Layer.provideMerge(layerDeps)); const noSpawner = ChildProcessSpawner.make(() => Effect.die("Disabled Grok must not spawn a process"), diff --git a/apps/server/src/provider/Drivers/GrokDriver.ts b/apps/server/src/provider/Drivers/GrokDriver.ts index 08ca7d5c715f6ce0100fbeeafedc1a1844d1e09b..c253401b53e65fe5ca462476cc944ba1d897f4c1 100644 --- a/apps/server/src/provider/Drivers/GrokDriver.ts +++ b/apps/server/src/provider/Drivers/GrokDriver.ts @@ -7,10 +7,9 @@ import * as Schema from "effect/Schema"; import { HttpClient } from "effect/http"; import { ChildProcessSpawner } from "effect/process"; -import * as BackgroundPolicy from "../../background/BackgroundPolicy.ts"; +import { ProviderHost } from "@t3tools/provider-core/server/ProviderHost"; import * as ServerConfig from "../../config.ts"; import * as ProviderEventLoggers from "../ProviderEventLoggers.ts"; -import * as ServerSettings from "../../serverSettings.ts"; import { makeGrokTextGeneration } from "../../textGeneration/GrokTextGeneration.ts"; import { GrokAdapterV2Driver, @@ -28,9 +27,9 @@ import { defaultProviderContinuationIdentity, type ProviderDriver, type ProviderInstance, -} from "../ProviderDriver.ts"; +} from "@t3tools/provider-core/server/driver"; import { withInstanceIdentity } from "./instanceIdentity.ts"; -import { mergeProviderInstanceEnvironment } from "../ProviderInstanceEnvironment.ts"; +import { mergeProviderInstanceEnvironment } from "@t3tools/provider-core/server/instanceEnvironment"; import { discoverGrokSkills } from "./GrokSkills.ts"; import { makeCachedProviderMaintenanceResolution, @@ -38,7 +37,7 @@ import { makeProviderMaintenanceCapabilities, type ProviderMaintenanceCapabilitiesResolver, resolveProviderMaintenanceCapabilitiesEffect, -} from "../providerMaintenance.ts"; +} from "@t3tools/provider-core/server/maintenanceResolver"; import { haveProviderSnapshotSettingsChanged, makeProviderSnapshotSettingsSource, @@ -76,15 +75,14 @@ const UPDATE: ProviderMaintenanceCapabilitiesResolver = { export type GrokDriverEnv = | GrokAdapterV2DriverEnv - | BackgroundPolicy.BackgroundPolicy + | ProviderHost | ChildProcessSpawner.ChildProcessSpawner | Crypto.Crypto | FileSystem.FileSystem | HttpClient.HttpClient | Path.Path | ProviderEventLoggers.ProviderEventLoggers - | ServerConfig.ServerConfig - | ServerSettings.ServerSettingsService; + | ServerConfig.ServerConfig; export const GrokDriver: ProviderDriver = { driverKind: DRIVER_KIND, @@ -101,7 +99,7 @@ export const GrokDriver: ProviderDriver = { const httpClient = yield* HttpClient.HttpClient; const fileSystem = yield* FileSystem.FileSystem; const path = yield* Path.Path; - const serverSettings = yield* ServerSettings.ServerSettingsService; + const host = yield* ProviderHost; const { cwd } = yield* ServerConfig.ServerConfig; const processEnv = mergeProviderInstanceEnvironment(environment); const continuationIdentity = defaultProviderContinuationIdentity({ @@ -166,7 +164,7 @@ export const GrokDriver: ProviderDriver = { Effect.provideService(ChildProcessSpawner.ChildProcessSpawner, spawner), ); - const snapshotSettings = makeProviderSnapshotSettingsSource(effectiveConfig, serverSettings); + const snapshotSettings = makeProviderSnapshotSettingsSource(effectiveConfig, host.settings); const snapshot = yield* makeManagedServerProvider>({ resolveMaintenance, getSettings: snapshotSettings.getSettings, diff --git a/apps/server/src/provider/Drivers/GrokSkills.ts b/apps/server/src/provider/Drivers/GrokSkills.ts index 9d0d45d4820eeb00489610a194db308ffd3ab68a..f552b0f4b2bcc676a163ba6ea13bca2d89005d7e 100644 --- a/apps/server/src/provider/Drivers/GrokSkills.ts +++ b/apps/server/src/provider/Drivers/GrokSkills.ts @@ -22,7 +22,7 @@ import * as Schema from "effect/Schema"; import { ChildProcess } from "effect/process"; import { resolveSpawnCommand } from "@t3tools/shared/shell"; -import { spawnAndCollect } from "../providerSnapshot.ts"; +import { spawnAndCollect } from "@t3tools/provider-core/server/snapshotProbe"; const GROK_SKILLS_PROBE_TIMEOUT_MS = 4_000; diff --git a/apps/server/src/provider/Drivers/MuseDriver.ts b/apps/server/src/provider/Drivers/MuseDriver.ts index d881e34a4d924d9a319d34c898addf97a3130e4c..63e164d9db96095f77a209ebc01dc026b376c911 100644 --- a/apps/server/src/provider/Drivers/MuseDriver.ts +++ b/apps/server/src/provider/Drivers/MuseDriver.ts @@ -7,14 +7,13 @@ import * as Schema from "effect/Schema"; import { HttpClient } from "effect/http"; import { ChildProcessSpawner } from "effect/process"; -import * as BackgroundPolicy from "../../background/BackgroundPolicy.ts"; +import { ProviderHost } from "@t3tools/provider-core/server/ProviderHost"; import * as ServerConfig from "../../config.ts"; -import { expandHomePath } from "../../pathExpansion.ts"; -import * as ServerSettings from "../../serverSettings.ts"; +import { expandHomePath } from "@t3tools/provider-core/server/pathExpansion"; import { makeMuseTextGeneration } from "../../textGeneration/MuseTextGeneration.ts"; import { ProviderDriverError } from "../Errors.ts"; import { makeMuseAdapterV2 } from "../../orchestration-v2/Adapters/MuseAdapterV2.ts"; -import * as IdAllocator from "../../orchestration-v2/IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import * as ProviderContinuationRequests from "../../orchestration-v2/ProviderContinuationRequests.ts"; import { checkMuseProviderStatus, makePendingMuseProvider } from "../MuseProvider.ts"; import * as ProviderEventLoggers from "../ProviderEventLoggers.ts"; @@ -25,12 +24,12 @@ import { defaultProviderContinuationIdentity, type ProviderDriver, type ProviderInstance, -} from "../ProviderDriver.ts"; -import { mergeProviderInstanceEnvironment } from "../ProviderInstanceEnvironment.ts"; +} from "@t3tools/provider-core/server/driver"; +import { mergeProviderInstanceEnvironment } from "@t3tools/provider-core/server/instanceEnvironment"; import { makeCachedProviderMaintenanceResolution, resolveProviderMaintenanceCapabilitiesEffect, -} from "../providerMaintenance.ts"; +} from "@t3tools/provider-core/server/maintenanceResolver"; import { haveProviderSnapshotSettingsChanged, makeProviderSnapshotSettingsSource, @@ -43,14 +42,13 @@ const decodeMuseSettings = Schema.decodeSync(MuseSettings); export type MuseDriverEnv = | IdAllocator.IdAllocatorV2 - | BackgroundPolicy.BackgroundPolicy + | ProviderHost | ChildProcessSpawner.ChildProcessSpawner | FileSystem.FileSystem | HttpClient.HttpClient | Path.Path | ProviderEventLoggers.ProviderEventLoggers - | ServerConfig.ServerConfig - | ServerSettings.ServerSettingsService; + | ServerConfig.ServerConfig; export const MuseDriver: ProviderDriver = { driverKind: DRIVER_KIND, @@ -63,7 +61,7 @@ export const MuseDriver: ProviderDriver = { const fileSystem = yield* FileSystem.FileSystem; const path = yield* Path.Path; const httpClient = yield* HttpClient.HttpClient; - const serverSettings = yield* ServerSettings.ServerSettingsService; + const host = yield* ProviderHost; const eventLoggers = yield* ProviderEventLoggers.ProviderEventLoggers; const serverConfig = yield* ServerConfig.ServerConfig; const { cwd } = serverConfig; @@ -91,7 +89,7 @@ export const MuseDriver: ProviderDriver = { accentColor, continuationGroupKey: continuationIdentity.continuationKey, }); - const snapshotSettings = makeProviderSnapshotSettingsSource(effectiveConfig, serverSettings); + const snapshotSettings = makeProviderSnapshotSettingsSource(effectiveConfig, host.settings); const resolveInstallation = yield* makeCachedProviderMaintenanceResolution( resolveProviderMaintenanceCapabilitiesEffect(museMaintenance, { binaryPath: effectiveConfig.binaryPath, diff --git a/apps/server/src/provider/Drivers/OpenCodeDriver.test.ts b/apps/server/src/provider/Drivers/OpenCodeDriver.test.ts index c1989ee335a5e46ffee35985c3378adb155bd4de..072e9e22df79873cdd532024ce4731c5245badc1 100644 --- a/apps/server/src/provider/Drivers/OpenCodeDriver.test.ts +++ b/apps/server/src/provider/Drivers/OpenCodeDriver.test.ts @@ -16,10 +16,10 @@ import { ChildProcessSpawner } from "effect/process"; import * as BackgroundPolicy from "../../background/BackgroundPolicy.ts"; import * as ServerConfig from "../../config.ts"; -import * as IdAllocator from "../../orchestration-v2/IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import * as ServerSettings from "../../serverSettings.ts"; import * as ProviderEventLoggers from "../ProviderEventLoggers.ts"; -import * as ProviderMaintenance from "../providerMaintenance.ts"; +import * as ProviderMaintenance from "@t3tools/provider-core/server/maintenanceResolver"; import * as OpenCodeRuntime from "../opencodeRuntime.ts"; import { OPENCODE_2_RESPONSES, @@ -27,6 +27,7 @@ import { replayOpenCodeServer, } from "../testFixtures/opencodeProbeResponses.ts"; import { OpenCodeDriver, openCodeUpdateFor } from "./OpenCodeDriver.ts"; +import * as ProviderHostLive from "../ProviderHostLive.ts"; const serverStarts: Array = []; const reachedServer = (operation: string) => @@ -47,7 +48,7 @@ const openCode2Runtime = { connectToOpenCodeServer: () => reachedServer("connect"), } as unknown as OpenCodeRuntime.OpenCodeRuntimeShape; -const layer = Layer.mergeAll( +const layerDeps = Layer.mergeAll( ServerConfig.layerTest(process.cwd(), { prefix: "t3-opencode-driver-" }), IdAllocator.layer, ServerSettings.layerTest(), @@ -58,6 +59,7 @@ const layer = Layer.mergeAll( ), Layer.succeed(OpenCodeRuntime.OpenCodeRuntime, openCode2Runtime), ).pipe(Layer.provideMerge(NodeServices.layer)); +const layer = ProviderHostLive.layer.pipe(Layer.provideMerge(layerDeps)); const create = (config: Partial, http: HttpClient.HttpClient) => OpenCodeDriver.create({ @@ -211,7 +213,7 @@ const changingRuntime = { startOpenCodeServerProcess: () => reachedServer("start"), connectToOpenCodeServer: () => reachedServer("connect"), } as unknown as OpenCodeRuntime.OpenCodeRuntimeShape; -const layerUpdate = Layer.mergeAll( +const layerUpdateDeps = Layer.mergeAll( ServerConfig.layerTest(process.cwd(), { prefix: "t3-opencode-driver-update-" }), IdAllocator.layer, ServerSettings.layerTest(), @@ -222,6 +224,7 @@ const layerUpdate = Layer.mergeAll( ), Layer.succeed(OpenCodeRuntime.OpenCodeRuntime, changingRuntime), ).pipe(Layer.provideMerge(NodeServices.layer)); +const layerUpdate = ProviderHostLive.layer.pipe(Layer.provideMerge(layerUpdateDeps)); it.layer(layerUpdate)("OpenCodeDriver updates", (it) => { it.effect("never runs the binary for a disabled instance's update check", () => diff --git a/apps/server/src/provider/Drivers/OpenCodeDriver.ts b/apps/server/src/provider/Drivers/OpenCodeDriver.ts index 688ac83db4245bd4d62cc480b5bb506414596b94..db4a9caa9e61326516244d8eedd7151382d3a5b8 100644 --- a/apps/server/src/provider/Drivers/OpenCodeDriver.ts +++ b/apps/server/src/provider/Drivers/OpenCodeDriver.ts @@ -26,12 +26,11 @@ import { ChildProcessSpawner } from "effect/process"; import * as OpenCode2TextGeneration from "../../textGeneration/OpenCode2TextGeneration.ts"; import { makeOpenCodeTextGeneration } from "../../textGeneration/OpenCodeTextGeneration.ts"; -import * as BackgroundPolicy from "../../background/BackgroundPolicy.ts"; +import { ProviderHost } from "@t3tools/provider-core/server/ProviderHost"; import * as ServerConfig from "../../config.ts"; import * as OpenCodeAdapterV2 from "../../orchestration-v2/Adapters/OpenCodeAdapterV2.ts"; import * as OpenCode2AdapterV2 from "../../orchestration-v2/Adapters/OpenCode2AdapterV2.ts"; -import type { ProviderAdapterV2Shape } from "../../orchestration-v2/ProviderAdapter.ts"; -import * as ServerSettings from "../../serverSettings.ts"; +import type { ProviderAdapterV2Shape } from "@t3tools/provider-core/server/ProviderAdapter"; import type { TextGeneration } from "../../textGeneration/TextGeneration.ts"; import { ProviderDriverError } from "../Errors.ts"; import { readOpenCodeGoUsageLimits } from "../openCodeUsageLimits.ts"; @@ -59,9 +58,9 @@ import { defaultProviderContinuationIdentity, type ProviderDriver, type ProviderInstance, -} from "../ProviderDriver.ts"; +} from "@t3tools/provider-core/server/driver"; import { withInstanceIdentity } from "./instanceIdentity.ts"; -import { mergeProviderInstanceEnvironment } from "../ProviderInstanceEnvironment.ts"; +import { mergeProviderInstanceEnvironment } from "@t3tools/provider-core/server/instanceEnvironment"; import { enrichProviderSnapshotWithVersionAdvisory, makeCachedProviderMaintenanceResolution, @@ -69,7 +68,7 @@ import { makePackageManagedProviderMaintenanceResolver, normalizeCommandPath, resolveProviderMaintenanceCapabilitiesEffect, -} from "../providerMaintenance.ts"; +} from "@t3tools/provider-core/server/maintenanceResolver"; import { haveProviderSnapshotSettingsChanged, makeProviderSnapshotSettingsSource, @@ -173,15 +172,14 @@ function selectOpenCodeRuntimeTextGeneration( export type OpenCodeDriverEnv = | OpenCodeAdapterV2.OpenCodeAdapterV2DriverEnv - | BackgroundPolicy.BackgroundPolicy + | ProviderHost | ChildProcessSpawner.ChildProcessSpawner | Crypto.Crypto | FileSystem.FileSystem | HttpClient.HttpClient | OpenCodeRuntime.OpenCodeRuntime | Path.Path - | ServerConfig.ServerConfig - | ServerSettings.ServerSettingsService; + | ServerConfig.ServerConfig; export const OpenCodeDriver: ProviderDriver = { driverKind: DRIVER_KIND, @@ -200,7 +198,7 @@ export const OpenCodeDriver: ProviderDriver const serverConfig = yield* ServerConfig.ServerConfig; const httpClient = yield* HttpClient.HttpClient; const crypto = yield* Crypto.Crypto; - const serverSettings = yield* ServerSettings.ServerSettingsService; + const host = yield* ProviderHost; const processEnv = mergeProviderInstanceEnvironment(environment); const continuationIdentity = defaultProviderContinuationIdentity({ driverKind: DRIVER_KIND, @@ -449,7 +447,7 @@ export const OpenCodeDriver: ProviderDriver ), ); - const snapshotSettings = makeProviderSnapshotSettingsSource(effectiveConfig, serverSettings); + const snapshotSettings = makeProviderSnapshotSettingsSource(effectiveConfig, host.settings); const snapshot = yield* makeManagedServerProvider>( { resolveMaintenance, diff --git a/apps/server/src/provider/Drivers/PiDriver.test.ts b/apps/server/src/provider/Drivers/PiDriver.test.ts index 7202f1784a8e27e7274aed4055c3d95bac30cded..2c4751ddf812997fe272f07587ddd8694a2dd79f 100644 --- a/apps/server/src/provider/Drivers/PiDriver.test.ts +++ b/apps/server/src/provider/Drivers/PiDriver.test.ts @@ -15,11 +15,12 @@ import { ChildProcess, ChildProcessSpawner } from "effect/process"; import * as BackgroundPolicy from "../../background/BackgroundPolicy.ts"; import * as ServerConfig from "../../config.ts"; -import * as IdAllocator from "../../orchestration-v2/IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import * as ServerSettings from "../../serverSettings.ts"; +import * as ProviderHostLive from "../ProviderHostLive.ts"; import { PiDriver } from "./PiDriver.ts"; -const layerTest = Layer.mergeAll( +const layerDeps = Layer.mergeAll( ServerConfig.layerTest("/machine", { prefix: "t3-pi-driver-" }), IdAllocator.layer, ServerSettings.layerTest({ enableProviderUpdateChecks: false }), @@ -32,6 +33,8 @@ const layerTest = Layer.mergeAll( ), ).pipe(Layer.provideMerge(NodeServices.layer)); +const layerTest = ProviderHostLive.layer.pipe(Layer.provideMerge(layerDeps)); + const decodeRequest = Schema.decodeSync( Schema.fromJsonString(Schema.Record(Schema.String, Schema.Unknown)), ); diff --git a/apps/server/src/provider/Drivers/PiDriver.ts b/apps/server/src/provider/Drivers/PiDriver.ts index 9a7ec6320b7d06b8b3d66828e0d454f57788ddc1..6bfc0ac15421d852444f23dbc3c013cdeca75f4a 100644 --- a/apps/server/src/provider/Drivers/PiDriver.ts +++ b/apps/server/src/provider/Drivers/PiDriver.ts @@ -14,9 +14,7 @@ import * as Schema from "effect/Schema"; import { HttpClient } from "effect/http"; import { ChildProcessSpawner } from "effect/process"; -import * as BackgroundPolicy from "../../background/BackgroundPolicy.ts"; -import * as ServerConfig from "../../config.ts"; -import * as ServerSettings from "../../serverSettings.ts"; +import { ProviderHost } from "@t3tools/provider-core/server/ProviderHost"; import { makePiTextGeneration } from "../../textGeneration/PiTextGeneration.ts"; import { PiAdapterV2Driver, @@ -34,14 +32,14 @@ import { defaultProviderContinuationIdentity, type ProviderDriver, type ProviderInstance, -} from "../ProviderDriver.ts"; -import type { ServerProviderDraft } from "../providerSnapshot.ts"; -import { mergeProviderInstanceEnvironment } from "../ProviderInstanceEnvironment.ts"; +} from "@t3tools/provider-core/server/driver"; +import type { ServerProviderDraft } from "@t3tools/provider-core/server/snapshotProbe"; +import { mergeProviderInstanceEnvironment } from "@t3tools/provider-core/server/instanceEnvironment"; import { makeCachedProviderMaintenanceResolution, makePackageManagedProviderMaintenanceResolver, resolveProviderMaintenanceCapabilitiesEffect, -} from "../providerMaintenance.ts"; +} from "@t3tools/provider-core/server/maintenanceResolver"; import { haveProviderSnapshotSettingsChanged, makeProviderSnapshotSettingsSource, @@ -60,13 +58,11 @@ const UPDATE = makePackageManagedProviderMaintenanceResolver({ export type PiDriverEnv = | PiAdapterV2DriverEnv - | BackgroundPolicy.BackgroundPolicy + | ProviderHost | ChildProcessSpawner.ChildProcessSpawner | FileSystem.FileSystem | HttpClient.HttpClient - | Path.Path - | ServerConfig.ServerConfig - | ServerSettings.ServerSettingsService; + | Path.Path; const withInstanceIdentity = (input: { @@ -98,8 +94,8 @@ export const PiDriver: ProviderDriver = { const fileSystem = yield* FileSystem.FileSystem; const pathService = yield* Path.Path; const httpClient = yield* HttpClient.HttpClient; - const { cwd } = yield* ServerConfig.ServerConfig; - const serverSettings = yield* ServerSettings.ServerSettingsService; + const host = yield* ProviderHost; + const { cwd } = host.paths; const processEnv = mergeProviderInstanceEnvironment(environment); const continuationIdentity = defaultProviderContinuationIdentity({ driverKind: DRIVER_KIND, @@ -148,7 +144,7 @@ export const PiDriver: ProviderDriver = { Effect.provideService(ChildProcessSpawner.ChildProcessSpawner, spawner), ); - const snapshotSettings = makeProviderSnapshotSettingsSource(effectiveConfig, serverSettings); + const snapshotSettings = makeProviderSnapshotSettingsSource(effectiveConfig, host.settings); const snapshot = yield* makeManagedServerProvider>({ resolveMaintenance, getSettings: snapshotSettings.getSettings, diff --git a/apps/server/src/provider/Drivers/instanceIdentity.ts b/apps/server/src/provider/Drivers/instanceIdentity.ts index 2fbc1c4a9f082a53e067645462b30ca1ff65cb5e..757e6457786f15706b96f61f46d0fc3cb5eb7a86 100644 --- a/apps/server/src/provider/Drivers/instanceIdentity.ts +++ b/apps/server/src/provider/Drivers/instanceIdentity.ts @@ -1,7 +1,7 @@ import type { ProviderDriverKind, ServerProvider } from "@t3tools/contracts"; -import type { ProviderInstance } from "../ProviderDriver.ts"; -import type { ServerProviderDraft } from "../providerSnapshot.ts"; +import type { ProviderInstance } from "@t3tools/provider-core/server/driver"; +import type { ServerProviderDraft } from "@t3tools/provider-core/server/snapshotProbe"; /** * Stamp instance identity onto a `ServerProvider` snapshot produced by the diff --git a/apps/server/src/provider/Errors.ts b/apps/server/src/provider/Errors.ts index 681d9784ded2dfd283375bf9f93be2b0e38c8283..50c7d2a3133bcf97a848fe834ebae28af3094d08 100644 --- a/apps/server/src/provider/Errors.ts +++ b/apps/server/src/provider/Errors.ts @@ -21,24 +21,7 @@ export class ProviderInstanceNotFoundError extends Schema.TaggedError()( - "ProviderDriverError", - { - driver: Schema.String, - instanceId: Schema.String, - detail: Schema.String, - cause: Schema.optional(Schema.Defect()), - }, -) { - override get message(): string { - return `Provider driver '${this.driver}' failed to create instance '${this.instanceId}': ${this.detail}`; - } -} +export { ProviderDriverError } from "@t3tools/provider-core/server/errors"; /** * ProviderWorkspaceMissingError - The session's working directory no longer diff --git a/apps/server/src/provider/GrokProvider.ts b/apps/server/src/provider/GrokProvider.ts index bab2921e71998b6eea176c081a901e6bf453fcb2..2e6a51bf211435be5cd62f1e552851764a5c49c6 100644 --- a/apps/server/src/provider/GrokProvider.ts +++ b/apps/server/src/provider/GrokProvider.ts @@ -30,11 +30,11 @@ import { providerModelsFromSettings, spawnAndCollect, type ServerProviderDraft, -} from "./providerSnapshot.ts"; +} from "@t3tools/provider-core/server/snapshotProbe"; import { enrichProviderSnapshotWithVersionAdvisory, type ProviderMaintenanceCapabilities, -} from "./providerMaintenance.ts"; +} from "@t3tools/provider-core/server/maintenanceResolver"; import { GROK_DEFAULT_MODEL_SLUG, GROK_SUPPORTED_RUNTIME_MODES, diff --git a/apps/server/src/provider/ModelManifest.ts b/apps/server/src/provider/ModelManifest.ts index c22efb8a094de3ab177eb2fae1ba1a7bd0f0fdca..402102c93425f10c3f2e6945421488eb033e74f2 100644 --- a/apps/server/src/provider/ModelManifest.ts +++ b/apps/server/src/provider/ModelManifest.ts @@ -36,7 +36,7 @@ import * as ServerSettings from "../serverSettings.ts"; import { hasValidClaudeManifestAdapters } from "./ClaudeModelManifest.ts"; import bundledManifestJson from "./model-manifest.json" with { type: "json" }; import { ProviderCompatibilityPolicy } from "./providerCompatibility.ts"; -import type { ServerProviderDraft } from "./providerSnapshot.ts"; +import type { ServerProviderDraft } from "@t3tools/provider-core/server/snapshotProbe"; const MODEL_MANIFEST_URL = "https://raw.githubusercontent.com/pingdotgg/t3code/main/apps/server/src/provider/model-manifest.json"; diff --git a/apps/server/src/provider/MuseProvider.test.ts b/apps/server/src/provider/MuseProvider.test.ts index 70cea88d5b9a80a7c753c80d5dc0d9c0f9919027..be7cafdbd6a152b16c0e05bb184eb76d167f042d 100644 --- a/apps/server/src/provider/MuseProvider.test.ts +++ b/apps/server/src/provider/MuseProvider.test.ts @@ -8,7 +8,7 @@ import { vi } from "vite-plus/test"; import { writeFakeCli } from "../testUtils/fakeCli.ts"; import type { MuseSdkHost } from "./museSdk.ts"; -import { COMPACT_SLASH_COMMAND } from "./providerSnapshot.ts"; +import { COMPACT_SLASH_COMMAND } from "@t3tools/provider-core/server/snapshotProbe"; import { checkMuseProviderStatus } from "./MuseProvider.ts"; const settings = Schema.decodeSync(MuseSettings); diff --git a/apps/server/src/provider/MuseProvider.ts b/apps/server/src/provider/MuseProvider.ts index 00d9d78526279e784dfed549256aab119004effc..3d44431d0564bb70d064efb708c00f9d5d74d27c 100644 --- a/apps/server/src/provider/MuseProvider.ts +++ b/apps/server/src/provider/MuseProvider.ts @@ -17,7 +17,7 @@ import { providerModelsFromSettings, spawnAndCollect, type ProviderProbeResult, -} from "./providerSnapshot.ts"; +} from "@t3tools/provider-core/server/snapshotProbe"; const MUSE_PRESENTATION = { displayName: "Muse Code", diff --git a/apps/server/src/provider/OpenCodeProvider.ts b/apps/server/src/provider/OpenCodeProvider.ts index ff4580e00e2da24d9c941acef3b8e3d12680bc71..0b638c47821c70497a9a87bd1c4e54becdd6a247 100644 --- a/apps/server/src/provider/OpenCodeProvider.ts +++ b/apps/server/src/provider/OpenCodeProvider.ts @@ -19,7 +19,7 @@ import { nonEmptyTrimmed, providerModelsFromSettings, type ServerProviderDraft, -} from "./providerSnapshot.ts"; +} from "@t3tools/provider-core/server/snapshotProbe"; import * as OpenCodeRuntime from "./opencodeRuntime.ts"; import type { ProbedOpenCode } from "./opencodeVersionProbe.ts"; import type { Agent, ProviderListResponse } from "@opencode-ai/sdk/v2"; diff --git a/apps/server/src/provider/OpenCodeServerLedger.ts b/apps/server/src/provider/OpenCodeServerLedger.ts index c6b74aeb88f135eabb32b581a4999f30b075b19c..8243e37f048135ea5ed4c3d721a327bac990b9d5 100644 --- a/apps/server/src/provider/OpenCodeServerLedger.ts +++ b/apps/server/src/provider/OpenCodeServerLedger.ts @@ -10,7 +10,7 @@ import { ChildProcess, ChildProcessSpawner } from "effect/process"; import { writeFileStringAtomically } from "../atomicWrite.ts"; import * as ServerConfig from "../config.ts"; -import { signalProcessGroup } from "../process/processGroup.ts"; +import { signalProcessGroup } from "@t3tools/provider-core/server/processGroup"; const ProcessIdentity = Schema.Struct({ pid: Schema.Int, startTime: Schema.String }); type ProcessIdentity = typeof ProcessIdentity.Type; diff --git a/apps/server/src/provider/PiProvider.ts b/apps/server/src/provider/PiProvider.ts index 2aaf9ab72e8d32b775fb08c1c64b5beffe06077a..4ea63f02ea494959a159be0dc9cbe4c2993a6a54 100644 --- a/apps/server/src/provider/PiProvider.ts +++ b/apps/server/src/provider/PiProvider.ts @@ -44,11 +44,11 @@ import { providerModelsFromSettings, spawnAndCollect, type ServerProviderDraft, -} from "./providerSnapshot.ts"; +} from "@t3tools/provider-core/server/snapshotProbe"; import { enrichProviderSnapshotWithVersionAdvisory, type ProviderMaintenanceCapabilities, -} from "./providerMaintenance.ts"; +} from "@t3tools/provider-core/server/maintenanceResolver"; import { EMPTY_PI_MODEL_CAPABILITIES, thinkingCapabilitiesForPiModel, diff --git a/apps/server/src/provider/ProviderAuthService.test.ts b/apps/server/src/provider/ProviderAuthService.test.ts index 46d27902b461de8b5f96dc29e12041e56ff30924..82a7c8dd288be00aac691e8d20a4616b239264c1 100644 --- a/apps/server/src/provider/ProviderAuthService.test.ts +++ b/apps/server/src/provider/ProviderAuthService.test.ts @@ -23,7 +23,7 @@ import * as SubscriptionRef from "effect/SubscriptionRef"; import * as ProjectionStore from "../orchestration-v2/ProjectionStore.ts"; import * as ProviderSessionManager from "../orchestration-v2/ProviderSessionManager.ts"; import { AcpProviderCapabilitiesV2 } from "../orchestration-v2/Adapters/AcpAdapterV2.ts"; -import type { ProviderInstance } from "./ProviderDriver.ts"; +import type { ProviderInstance } from "@t3tools/provider-core/server/driver"; import * as ProviderAuthService from "./ProviderAuthService.ts"; import * as ProviderInstanceRegistry from "./ProviderInstanceRegistry.ts"; diff --git a/apps/server/src/provider/ProviderAuthService.ts b/apps/server/src/provider/ProviderAuthService.ts index 9dabd57104ca6d01203f9aaa6286c016a751d5bb..24f176dd709515c8df35e41acde32afa51417be2 100644 --- a/apps/server/src/provider/ProviderAuthService.ts +++ b/apps/server/src/provider/ProviderAuthService.ts @@ -18,53 +18,9 @@ import * as Semaphore from "effect/Semaphore"; import * as ProviderSessionManager from "../orchestration-v2/ProviderSessionManager.ts"; import * as ProjectionStore from "../orchestration-v2/ProjectionStore.ts"; import * as ProviderInstanceRegistry from "./ProviderInstanceRegistry.ts"; +import type { ProviderAuthController } from "@t3tools/provider-core/server/auth"; -export interface ProviderAuthController { - /** Equal keys mean these instances share credentials on this environment. */ - readonly credentialBinding?: { readonly owner: "provider" | "t3"; readonly key: string }; - readonly reconnectProfile?: ( - methodId: string, - ) => Effect.Effect; - readonly importProfile?: ( - profile: ChatGptTransferredProfile, - stopSessions: Effect.Effect, - ) => Effect.Effect; - readonly adoptCredentials?: ( - update: Effect.Effect, - stopSessions: Effect.Effect, - ) => Effect.Effect; - readonly isChangingCredentials?: Effect.Effect; - readonly invalidate?: Effect.Effect; - readonly refreshMethods?: Effect.Effect; - readonly withAccess?: ( - task: Effect.Effect, - ) => Effect.Effect; - readonly start: ( - ownerSessionId: string, - stopSessions?: Effect.Effect, - methodId?: string, - returnUrl?: string, - callbackMode?: "server" | "client", - ) => Effect.Effect; - readonly complete: ( - ownerSessionId: string, - input: { readonly flowId: string; readonly callbackUrl: string }, - ) => Effect.Effect; - readonly cancel: ( - ownerSessionId: string, - flowId: string, - ) => Effect.Effect; - readonly respond?: ( - ownerSessionId: string, - input: ProviderAuthRespondInput, - ) => Effect.Effect; - /** The controller closes process admission before it stops routed sessions. */ - readonly logout: ( - stopSessions: Effect.Effect, - ) => Effect.Effect; - readonly subscribe: (ownerSessionId: string) => Stream.Stream; - readonly isLogoutPrompt?: (text: string, hasAttachments: boolean) => boolean; -} +export type { ProviderAuthController } from "@t3tools/provider-core/server/auth"; interface ProviderAuthTarget { readonly instanceId: ProviderInstanceId; diff --git a/apps/server/src/provider/ProviderHostLive.ts b/apps/server/src/provider/ProviderHostLive.ts new file mode 100644 index 0000000000000000000000000000000000000000..965cb47e365f51849fbaa0dc4dfc0138a2e4b18c --- /dev/null +++ b/apps/server/src/provider/ProviderHostLive.ts @@ -0,0 +1,39 @@ +/** + * The server's implementation of `ProviderHost`, the only server surface + * provider drivers and adapters may use. + * + * @module provider/ProviderHostLive + */ +import { ProviderHost } from "@t3tools/provider-core/server/ProviderHost"; +import * as Effect from "effect/Effect"; +import * as Layer from "effect/Layer"; + +import { resolveAttachmentPath } from "../attachmentStore.ts"; +import * as BackgroundPolicy from "../background/BackgroundPolicy.ts"; +import * as ServerConfig from "../config.ts"; +import * as ServerSettings from "../serverSettings.ts"; + +export const layer = Layer.effect( + ProviderHost, + Effect.gen(function* () { + const config = yield* ServerConfig.ServerConfig; + const serverSettings = yield* ServerSettings.ServerSettingsService; + const backgroundPolicy = yield* BackgroundPolicy.BackgroundPolicy; + return ProviderHost.of({ + paths: { + cwd: config.cwd, + baseDir: config.baseDir, + stateDir: config.stateDir, + providerStatusCacheDir: config.providerStatusCacheDir, + }, + settings: { + get: serverSettings.getSettings, + changes: serverSettings.streamChanges, + subscribe: serverSettings.subscribeChanges, + }, + shouldRunBackgroundWork: backgroundPolicy.shouldRunScopeWork, + resolveAttachmentPath: (attachment) => + resolveAttachmentPath({ attachmentsDir: config.attachmentsDir, attachment }), + }); + }), +); diff --git a/apps/server/src/provider/ProviderInstanceRegistry.test.ts b/apps/server/src/provider/ProviderInstanceRegistry.test.ts index 7a132b40fc8888a5c5d631c9457a6c23efca596f..8050e426dd6c20eafd5366dd01d73ff9c8914b0d 100644 --- a/apps/server/src/provider/ProviderInstanceRegistry.test.ts +++ b/apps/server/src/provider/ProviderInstanceRegistry.test.ts @@ -50,7 +50,7 @@ import { HttpClient, HttpClientResponse } from "effect/http"; import * as BackgroundPolicy from "../background/BackgroundPolicy.ts"; import * as AntigravityInstallation from "./AntigravityInstallation.ts"; import * as ServerConfig from "../config.ts"; -import { expandHomePath } from "../pathExpansion.ts"; +import { expandHomePath } from "@t3tools/provider-core/server/pathExpansion"; import * as ServerSettings from "../serverSettings.ts"; import { ClaudeDriver, type ClaudeDriverEnv } from "./Drivers/ClaudeDriver.ts"; import { CodexDriver, type CodexDriverEnv } from "./Drivers/CodexDriver.ts"; @@ -64,6 +64,7 @@ import * as ResetCreditCoordinator from "./resetCreditCoordinator.ts"; import * as ProviderEventLoggers from "./ProviderEventLoggers.ts"; import { makeProviderInstanceRegistry } from "./ProviderInstanceRegistry.ts"; import * as ProviderOrchestrationAdapterInfrastructure from "./ProviderOrchestrationAdapterInfrastructure.ts"; +import * as ProviderHostLive from "./ProviderHostLive.ts"; const layerTestHttpClient = Layer.succeed( HttpClient.HttpClient, @@ -200,7 +201,7 @@ describe("ProviderInstanceRegistry — multi-instance codex slice", () => { // `NodeServices.layer` through `Layer.provideMerge` to satisfy that // dependency while still surfacing NodeServices to the test body (the // codex driver's `create` yields `ChildProcessSpawner` directly). - const layerBase = ServerConfig.layerTest(process.cwd(), { + const layerBaseDeps = ServerConfig.layerTest(process.cwd(), { prefix: "provider-instance-registry-test", }).pipe( Layer.provideMerge(NodeServices.layer), @@ -230,6 +231,7 @@ describe("ProviderInstanceRegistry — multi-instance codex slice", () => { Layer.provideMerge(ModelManifest.layerTest), Layer.provideMerge(ResetCreditCoordinator.layerTest), ); + const layerBase = ProviderHostLive.layer.pipe(Layer.provideMerge(layerBaseDeps)); const layerTest = ProviderOrchestrationAdapterInfrastructure.layer.pipe( Layer.provideMerge(layerBase), ); @@ -589,7 +591,7 @@ describe("ProviderInstanceRegistry — all drivers slice", () => { }), ), ); - const layerBase = AntigravityInstallation.AntigravityInstallation.layer.pipe( + const layerBaseDeps = AntigravityInstallation.AntigravityInstallation.layer.pipe( Layer.provideMerge(ServerSecretStore.layer), Layer.provideMerge( ServerConfig.layerTest(process.cwd(), { @@ -610,6 +612,7 @@ describe("ProviderInstanceRegistry — all drivers slice", () => { Layer.provideMerge(ModelManifest.layerTest), Layer.provideMerge(ResetCreditCoordinator.layerTest), ); + const layerBase = ProviderHostLive.layer.pipe(Layer.provideMerge(layerBaseDeps)); const layerTest = ProviderOrchestrationAdapterInfrastructure.layer.pipe( Layer.provideMerge(layerBase), ); diff --git a/apps/server/src/provider/ProviderInstanceRegistry.ts b/apps/server/src/provider/ProviderInstanceRegistry.ts index eecd4fc5cbecdedb2697285b99bfcfcd61fa04a3..8b0ca5d6404af2ca596f7a9c9cb460a1d88989a6 100644 --- a/apps/server/src/provider/ProviderInstanceRegistry.ts +++ b/apps/server/src/provider/ProviderInstanceRegistry.ts @@ -69,7 +69,7 @@ import * as Stream from "effect/Stream"; import { buildUnavailableProviderSnapshot } from "./unavailableProviderSnapshot.ts"; import * as ProviderInstanceRegistryMutator from "./ProviderInstanceRegistryMutator.ts"; -import type { AnyProviderDriver, ProviderInstance } from "./ProviderDriver.ts"; +import type { AnyProviderDriver, ProviderInstance } from "@t3tools/provider-core/server/driver"; export class ProviderInstanceRegistry extends Context.Service< ProviderInstanceRegistry, diff --git a/apps/server/src/provider/ProviderInstanceRegistryHydration.ts b/apps/server/src/provider/ProviderInstanceRegistryHydration.ts index 922eb48175d3b7dac99d216f57e1316f77c219b8..50627de3d337361d8b4ee694bf5ceef3b616934c 100644 --- a/apps/server/src/provider/ProviderInstanceRegistryHydration.ts +++ b/apps/server/src/provider/ProviderInstanceRegistryHydration.ts @@ -58,14 +58,22 @@ import * as ProviderInstanceRegistryMutator from "./ProviderInstanceRegistryMuta import * as ProviderOrchestrationAdapterInfrastructure from "./ProviderOrchestrationAdapterInfrastructure.ts"; import * as AcpRegistrySupport from "./acp/AcpRegistrySupport.ts"; import * as AcpRegistryCatalog from "./AcpRegistryCatalog.ts"; +import * as ProviderHostLive from "./ProviderHostLive.ts"; +import type { ProviderHost } from "@t3tools/provider-core/server/ProviderHost"; +import type * as BackgroundPolicy from "../background/BackgroundPolicy.ts"; +import type * as ServerConfig from "../config.ts"; type ProviderInstanceRegistryHydrationEnv = | Exclude< BuiltInDriversEnv, | ProviderOrchestrationAdapterInfrastructure.ProviderOrchestrationAdapterInfrastructure | AcpRegistrySupport.AcpRegistryCatalog + | ProviderHost > - | Settings.ServerSettingsService; + | Settings.ServerSettingsService + // Requirements of the `ProviderHost` the drivers receive. + | BackgroundPolicy.BackgroundPolicy + | ServerConfig.ServerConfig; /** * Synthesize a `ProviderInstanceConfigMap` from a `ServerSettings` snapshot. @@ -181,6 +189,7 @@ export const layer: Layer.Layer< }).pipe( Layer.provide(ProviderOrchestrationAdapterInfrastructure.layer), Layer.provide(AcpRegistryCatalog.layer), + Layer.provide(ProviderHostLive.layer), ); return layerSettingsWatcher.pipe(Layer.provideMerge(layerMutable)); diff --git a/apps/server/src/provider/ProviderOrchestrationAdapterInfrastructure.ts b/apps/server/src/provider/ProviderOrchestrationAdapterInfrastructure.ts index 204ef10a2721a0232b256607d1fa70b81dda48b2..130a63262fc4d29a876173669f2308f581e748a6 100644 --- a/apps/server/src/provider/ProviderOrchestrationAdapterInfrastructure.ts +++ b/apps/server/src/provider/ProviderOrchestrationAdapterInfrastructure.ts @@ -3,7 +3,7 @@ import * as Layer from "effect/Layer"; import * as ClaudeAdapterV2 from "../orchestration-v2/Adapters/ClaudeAdapterV2.ts"; import * as CodexAdapterV2 from "../orchestration-v2/Adapters/CodexAdapterV2.ts"; import * as CursorAgentSdk from "../orchestration-v2/Adapters/CursorAgentSdk.ts"; -import * as IdAllocator from "../orchestration-v2/IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import * as ProviderContinuationRequests from "../orchestration-v2/ProviderContinuationRequests.ts"; export type ProviderOrchestrationAdapterInfrastructure = diff --git a/apps/server/src/provider/ProviderRegistry.test.ts b/apps/server/src/provider/ProviderRegistry.test.ts index bfbff2e3db4c41f50885066dfd953cd0fdb3898c..d5fc2b2a580945d71772c772f8c0557becec2aa1 100644 --- a/apps/server/src/provider/ProviderRegistry.test.ts +++ b/apps/server/src/provider/ProviderRegistry.test.ts @@ -56,11 +56,14 @@ import { resolveProviderStatusCachePath, writeProviderStatusCache, } from "./providerStatusCache.ts"; -import { COMPACT_SLASH_COMMAND } from "./providerSnapshot.ts"; -import type { ProviderInstance, ProviderWorkspaceSnapshot } from "./ProviderDriver.ts"; +import { COMPACT_SLASH_COMMAND } from "@t3tools/provider-core/server/snapshotProbe"; +import type { + ProviderInstance, + ProviderWorkspaceSnapshot, +} from "@t3tools/provider-core/server/driver"; import * as ProviderInstanceRegistry from "./ProviderInstanceRegistry.ts"; import * as ProviderRegistry from "./ProviderRegistry.ts"; -import { makeManualOnlyProviderMaintenanceCapabilities } from "./providerMaintenance.ts"; +import { makeManualOnlyProviderMaintenanceCapabilities } from "@t3tools/provider-core/server/maintenanceResolver"; const decodeServerSettings = Schema.decodeSync(ServerSettings); const encodeServerSettings = Schema.encodeSync(ServerSettings); const encodedDefaultServerSettings = encodeServerSettings(DEFAULT_SERVER_SETTINGS); diff --git a/apps/server/src/provider/ProviderRegistry.ts b/apps/server/src/provider/ProviderRegistry.ts index 97b80f270e90b87a4e1f78c8c74215496fb8df49..a76ad34c833345769b5e359e5ca73fe349971985 100644 --- a/apps/server/src/provider/ProviderRegistry.ts +++ b/apps/server/src/provider/ProviderRegistry.ts @@ -62,11 +62,14 @@ import { resolveProviderStatusCachePath, writeProviderStatusCache, } from "./providerStatusCache.ts"; -import type { ProviderInstance, ProviderWorkspaceSnapshot } from "./ProviderDriver.ts"; +import type { + ProviderInstance, + ProviderWorkspaceSnapshot, +} from "@t3tools/provider-core/server/driver"; import { makeManualOnlyProviderMaintenanceCapabilities, type ProviderMaintenanceCapabilities, -} from "./providerMaintenance.ts"; +} from "@t3tools/provider-core/server/maintenanceResolver"; import type { ProviderSnapshotSource } from "./builtInProviderCatalog.ts"; export type ProviderMaintenanceActionKind = "update"; diff --git a/apps/server/src/provider/acp/AcpRegistrySupport.ts b/apps/server/src/provider/acp/AcpRegistrySupport.ts index 5eb8842f56677e66d3eba8e499eec76b85776a8a..c62f93dae4006dc9a5e1162fd2054413f29c627a 100644 --- a/apps/server/src/provider/acp/AcpRegistrySupport.ts +++ b/apps/server/src/provider/acp/AcpRegistrySupport.ts @@ -41,7 +41,7 @@ import { sha256 } from "@noble/hashes/sha2"; import { HttpClient, HttpClientRequest, HttpClientResponse } from "effect/http"; import { ChildProcess, ChildProcessSpawner } from "effect/process"; -import { collectUint8StreamText } from "../../stream/collectUint8StreamText.ts"; +import { collectUint8StreamText } from "@t3tools/provider-core/server/collectStreamText"; import * as ServerSettings from "../../serverSettings.ts"; import type { AcpSpawnInput } from "./AcpSessionRuntime.ts"; diff --git a/apps/server/src/provider/acp/AcpSessionRuntime.ts b/apps/server/src/provider/acp/AcpSessionRuntime.ts index 3ab2154b91fe6ff62ee086565c7c000b23f989f2..9c2cb395f3074b0e78dd23998702fe261aba53ad 100644 --- a/apps/server/src/provider/acp/AcpSessionRuntime.ts +++ b/apps/server/src/provider/acp/AcpSessionRuntime.ts @@ -29,7 +29,7 @@ import type * as EffectAcpProtocol from "effect-acp/protocol"; import { resolveSpawnCommand } from "@t3tools/shared/shell"; import { HostProcessPlatform } from "@t3tools/shared/hostProcess"; -import { signalProcessGroup } from "../../process/processGroup.ts"; +import { signalProcessGroup } from "@t3tools/provider-core/server/processGroup"; import { appendAcpStderrTail, sanitizeAcpStderrExcerpt } from "./AcpStderr.ts"; import { collectSessionConfigOptionValues, diff --git a/apps/server/src/provider/antigravityAuthSupport.ts b/apps/server/src/provider/antigravityAuthSupport.ts index 7a87854b19db517d108cc50f0e6109a3de8257bd..ea5aff4b4c77468302eaefa85012e15930759595 100644 --- a/apps/server/src/provider/antigravityAuthSupport.ts +++ b/apps/server/src/provider/antigravityAuthSupport.ts @@ -16,7 +16,7 @@ import * as ChildProcess from "effect/process/ChildProcess"; import * as ChildProcessSpawner from "effect/process/ChildProcessSpawner"; import * as AcpErrors from "effect-acp/errors"; -import { collectUint8StreamText } from "../stream/collectUint8StreamText.ts"; +import { collectUint8StreamText } from "@t3tools/provider-core/server/collectStreamText"; import type { AcpSpawnInput } from "./acp/AcpSessionRuntime.ts"; import { antigravityUserSkillDirectories, diff --git a/apps/server/src/provider/builtInDrivers.ts b/apps/server/src/provider/builtInDrivers.ts index 92d798945fc86f0ecbb25e27d2508ef75e4f8aba..ffaf812e4c840cd039fa403fd380aaede832d4e9 100644 --- a/apps/server/src/provider/builtInDrivers.ts +++ b/apps/server/src/provider/builtInDrivers.ts @@ -29,7 +29,7 @@ import { GrokDriver, type GrokDriverEnv } from "./Drivers/GrokDriver.ts"; import { OpenCodeDriver, type OpenCodeDriverEnv } from "./Drivers/OpenCodeDriver.ts"; import { MuseDriver, type MuseDriverEnv } from "./Drivers/MuseDriver.ts"; import { PiDriver, type PiDriverEnv } from "./Drivers/PiDriver.ts"; -import type { AnyProviderDriver } from "./ProviderDriver.ts"; +import type { AnyProviderDriver } from "@t3tools/provider-core/server/driver"; /** * Union of infrastructure services required to construct any built-in diff --git a/apps/server/src/provider/builtInProviderCatalog.ts b/apps/server/src/provider/builtInProviderCatalog.ts index 98336dbef0bfaf146a048e01a3fef26aff507294..115ad692ff5e7a0a45a6b46b0814bf40caa7b677 100644 --- a/apps/server/src/provider/builtInProviderCatalog.ts +++ b/apps/server/src/provider/builtInProviderCatalog.ts @@ -1,6 +1,6 @@ import type { ProviderDriverKind, ProviderInstanceId, ServerProvider } from "@t3tools/contracts"; import type * as Stream from "effect/Stream"; -import type { ServerProviderShape } from "./ServerProvider.ts"; +import type { ServerProviderShape } from "@t3tools/provider-core/server/snapshot"; export type ProviderSnapshotSource = { /** diff --git a/apps/server/src/provider/claudeUsageLimits.ts b/apps/server/src/provider/claudeUsageLimits.ts index 3fae307afb563a9dd48256a020521e914a607ae0..200aa6e713f238edd10213776b4f1bb770b7b9bc 100644 --- a/apps/server/src/provider/claudeUsageLimits.ts +++ b/apps/server/src/provider/claudeUsageLimits.ts @@ -25,7 +25,7 @@ import { clampPercent, makeUnavailableUsageLimits, makeUsageLimits, -} from "./providerUsageLimits.ts"; +} from "@t3tools/provider-core/server/usageLimits"; const SESSION_MINS = 5 * 60; const WEEK_MINS = 7 * 24 * 60; diff --git a/apps/server/src/provider/codexUsageLimits.ts b/apps/server/src/provider/codexUsageLimits.ts index 32a7a1f07a9cf766a01755c2182a879e49754801..b32f701de33051fa96db14aa863d7d7bb5c3d6ac 100644 --- a/apps/server/src/provider/codexUsageLimits.ts +++ b/apps/server/src/provider/codexUsageLimits.ts @@ -16,7 +16,7 @@ import * as DateTime from "effect/DateTime"; import * as Option from "effect/Option"; import type * as CodexErrors from "effect-codex-app-server/errors"; -import { clampPercent, makeUsageLimits } from "./providerUsageLimits.ts"; +import { clampPercent, makeUsageLimits } from "@t3tools/provider-core/server/usageLimits"; interface CodexRateLimitWindow { readonly usedPercent: number; diff --git a/apps/server/src/provider/cursorUsageLimits.ts b/apps/server/src/provider/cursorUsageLimits.ts index eeacd46a7d79275920726d7d83f39da7e53ed8d4..987eeda748503469bdc30ede212f3b04a678f085 100644 --- a/apps/server/src/provider/cursorUsageLimits.ts +++ b/apps/server/src/provider/cursorUsageLimits.ts @@ -13,7 +13,7 @@ import { clampPercent, makeUnavailableUsageLimits, makeUsageLimits, -} from "./providerUsageLimits.ts"; +} from "@t3tools/provider-core/server/usageLimits"; import { readMacCursorAccessToken } from "./cursorKeychainToken.ts"; const CursorCredentials = Schema.Struct({ accessToken: Schema.optional(Schema.String) }); diff --git a/apps/server/src/provider/grokUsageLimits.ts b/apps/server/src/provider/grokUsageLimits.ts index b0eaa6dc51f2b1a162ba5b877742dfdfc0c61a29..f200956b56b17a016411f41dda58c59833183300 100644 --- a/apps/server/src/provider/grokUsageLimits.ts +++ b/apps/server/src/provider/grokUsageLimits.ts @@ -11,7 +11,7 @@ import { clampPercent, makeUnavailableUsageLimits, makeUsageLimits, -} from "./providerUsageLimits.ts"; +} from "@t3tools/provider-core/server/usageLimits"; const GrokCredentials = Schema.Record( Schema.String, diff --git a/apps/server/src/provider/makeManagedServerProvider.test.ts b/apps/server/src/provider/makeManagedServerProvider.test.ts index 17c1e442adb70f662485935cbac2b4367d87f1eb..767ed192b25d98bd04d54adcceb6d7726c37e372 100644 --- a/apps/server/src/provider/makeManagedServerProvider.test.ts +++ b/apps/server/src/provider/makeManagedServerProvider.test.ts @@ -1,3 +1,4 @@ +import * as NodeServices from "@effect/platform-node/NodeServices"; import { describe, it, assert } from "@effect/vitest"; import { DEFAULT_SERVER_SETTINGS, @@ -18,8 +19,10 @@ import * as Stream from "effect/Stream"; import { TestClock } from "effect/testing"; import * as BackgroundPolicy from "../background/BackgroundPolicy.ts"; +import * as ServerConfig from "../config.ts"; import * as ServerSettings from "../serverSettings.ts"; import { makeManagedServerProvider } from "./makeManagedServerProvider.ts"; +import * as ProviderHostLive from "./ProviderHostLive.ts"; const emptyCapabilities = createModelCapabilities({ optionDescriptors: [] }); const TEST_EPOCH = DateTime.makeUnsafe("1970-01-01T00:00:00.000Z"); @@ -133,8 +136,26 @@ function layerBackgroundPolicy(shouldRunScopeWork: boolean) { const layerBackgroundPolicyAlwaysRun = layerBackgroundPolicy(true); const layerBackgroundPolicyNeverRun = layerBackgroundPolicy(false); const layerServerSettingsTest = ServerSettings.layerTest(); -const layerAlwaysRunTest = Layer.merge(layerBackgroundPolicyAlwaysRun, layerServerSettingsTest); -const layerNeverRunTest = Layer.merge(layerBackgroundPolicyNeverRun, layerServerSettingsTest); +const layerServerConfigTest = ServerConfig.layerTest(process.cwd(), { + prefix: "t3-managed-provider-test-", +}).pipe(Layer.provide(NodeServices.layer)); + +function layerProviderHost( + layerBackground: Layer.Layer, + layerSettings: Layer.Layer, +) { + return ProviderHostLive.layer.pipe( + Layer.provideMerge(layerBackground), + Layer.provideMerge(layerSettings), + Layer.provide(layerServerConfigTest), + ); +} + +const layerAlwaysRunTest = layerProviderHost( + layerBackgroundPolicyAlwaysRun, + layerServerSettingsTest, +); +const layerNeverRunTest = layerProviderHost(layerBackgroundPolicyNeverRun, layerServerSettingsTest); const enrichedSnapshotSecond: ServerProvider = { ...refreshedSnapshotSecond, @@ -326,7 +347,9 @@ describe("makeManagedServerProvider", () => { ), Effect.as(refreshedSnapshot), ), - }).pipe(Effect.provide(Layer.merge(layerBackgroundPolicyAlwaysRun, layerServerSettings))); + }).pipe( + Effect.provide(layerProviderHost(layerBackgroundPolicyAlwaysRun, layerServerSettings)), + ); yield* Deferred.await(initialCheckDone); const nextServerSettings = { diff --git a/apps/server/src/provider/makeManagedServerProvider.ts b/apps/server/src/provider/makeManagedServerProvider.ts index 389bf83f3f78dc85a30a6d085e1ed5bba70dce0a..e2637cc1a146d8ab45efa916d42e57deb27731f6 100644 --- a/apps/server/src/provider/makeManagedServerProvider.ts +++ b/apps/server/src/provider/makeManagedServerProvider.ts @@ -15,10 +15,12 @@ import * as Scope from "effect/Scope"; import * as Stream from "effect/Stream"; import * as Semaphore from "effect/Semaphore"; -import * as BackgroundPolicy from "../background/BackgroundPolicy.ts"; -import * as ServerSettings from "../serverSettings.ts"; -import { applyUsageLimitsUpdate, resolveUsageLimitsAfterProbe } from "./providerUsageLimits.ts"; -import type { ServerProviderShape } from "./ServerProvider.ts"; +import { ProviderHost } from "@t3tools/provider-core/server/ProviderHost"; +import { + applyUsageLimitsUpdate, + resolveUsageLimitsAfterProbe, +} from "@t3tools/provider-core/server/usageLimits"; +import type { ServerProviderShape } from "@t3tools/provider-core/server/snapshot"; interface ProviderSnapshotState { readonly snapshot: ServerProvider; @@ -54,13 +56,8 @@ export const makeManagedServerProvider = Effect.fn("makeManagedServerProvider")( readonly refreshInterval?: Duration.Input; readonly refreshOnInterval?: boolean; readonly checkProviderOnSettingsChange?: (previous: Settings, next: Settings) => boolean; -}): Effect.fn.Return< - ServerProviderShape, - ServerSettingsError, - Scope.Scope | BackgroundPolicy.BackgroundPolicy | ServerSettings.ServerSettingsService -> { - const backgroundPolicy = yield* BackgroundPolicy.BackgroundPolicy; - const serverSettings = yield* ServerSettings.ServerSettingsService; +}): Effect.fn.Return { + const host = yield* ProviderHost; const refreshSemaphore = yield* Semaphore.make(1); const changesPubSub = yield* Effect.acquireRelease( PubSub.unbounded(), @@ -213,8 +210,8 @@ export const makeManagedServerProvider = Effect.fn("makeManagedServerProvider")( const state = yield* Ref.get(snapshotStateRef); const instanceId = state.snapshot.instanceId; const [genericDemand, instanceDemand] = yield* Effect.all([ - backgroundPolicy.shouldRunScopeWork({ type: "provider-status" }), - backgroundPolicy.shouldRunScopeWork({ type: "provider-status", instanceId }), + host.shouldRunBackgroundWork({ type: "provider-status" }), + host.shouldRunBackgroundWork({ type: "provider-status", instanceId }), ]); return genericDemand || instanceDemand; }); @@ -222,7 +219,7 @@ export const makeManagedServerProvider = Effect.fn("makeManagedServerProvider")( const getRefreshInterval = input.refreshInterval !== undefined ? Effect.succeed(input.refreshInterval) - : serverSettings.getSettings.pipe( + : host.settings.get.pipe( Effect.map( (settings) => resolveServerBackgroundActivitySettings(settings).providerHealthRefreshInterval, @@ -232,7 +229,7 @@ export const makeManagedServerProvider = Effect.fn("makeManagedServerProvider")( const refreshIntervalChanges = yield* Queue.sliding(1); if (input.refreshInterval === undefined) { - const serverSettingsChanges = yield* serverSettings.subscribeChanges; + const serverSettingsChanges = yield* host.settings.subscribe; yield* serverSettingsChanges.pipe( Stream.map((settings) => Duration.toMillis( diff --git a/apps/server/src/provider/museMaintenance.test.ts b/apps/server/src/provider/museMaintenance.test.ts index e3a3ea2f16ac0760bf7260f16fd09d53991eea07..59d0868e768ddb528947d2ca3bdb2ccf63025bd4 100644 --- a/apps/server/src/provider/museMaintenance.test.ts +++ b/apps/server/src/provider/museMaintenance.test.ts @@ -15,7 +15,7 @@ import { import { ProviderVersionCache, makeManualOnlyProviderMaintenanceCapabilities, -} from "./providerMaintenance.ts"; +} from "@t3tools/provider-core/server/maintenanceResolver"; const maintenanceCapabilities = { ...makeManualOnlyProviderMaintenanceCapabilities({ diff --git a/apps/server/src/provider/museMaintenance.ts b/apps/server/src/provider/museMaintenance.ts index 616c2dc06da53c3dea998664090ea968ca043050..0770b494a819176657236f0ca502d1d83c8c8c42 100644 --- a/apps/server/src/provider/museMaintenance.ts +++ b/apps/server/src/provider/museMaintenance.ts @@ -13,8 +13,8 @@ import { ProviderVersionCache, type ProviderMaintenanceCapabilities, type ProviderMaintenanceCapabilitiesResolver, -} from "./providerMaintenance.ts"; -import { parseGenericCliVersion } from "./providerSnapshot.ts"; +} from "@t3tools/provider-core/server/maintenanceResolver"; +import { parseGenericCliVersion } from "@t3tools/provider-core/server/snapshotProbe"; const DRIVER = ProviderDriverKind.make("muse"); /** Mirrors the official launcher, which reads MUSE_CHANNEL and accepts only these two. */ diff --git a/apps/server/src/provider/openCodeUsageLimits.ts b/apps/server/src/provider/openCodeUsageLimits.ts index 80a44821ac8b92ab6ff862042b14556f89cd9d6e..2192e75a7b3d854e6b82601b1e336e0af866d9e3 100644 --- a/apps/server/src/provider/openCodeUsageLimits.ts +++ b/apps/server/src/provider/openCodeUsageLimits.ts @@ -15,7 +15,7 @@ import { clampPercent, makeUnavailableUsageLimits, makeUsageLimits, -} from "./providerUsageLimits.ts"; +} from "@t3tools/provider-core/server/usageLimits"; const AuthFile = Schema.Struct({ "opencode-go": Schema.optionalKey(Schema.Unknown) }); const ApiAuth = Schema.Struct({ type: Schema.Literal("api"), key: Schema.String }); diff --git a/apps/server/src/provider/opencodeRuntime.ts b/apps/server/src/provider/opencodeRuntime.ts index 885ee191fb5dc1de62f83a08ceef6f7610d7329b..979cacc75b145897770e3381992e2465f34e0539 100644 --- a/apps/server/src/provider/opencodeRuntime.ts +++ b/apps/server/src/provider/opencodeRuntime.ts @@ -30,10 +30,10 @@ import * as Schema from "effect/Schema"; import * as Stream from "effect/Stream"; import { ChildProcess, ChildProcessSpawner } from "effect/process"; -import { signalProcessGroup } from "../process/processGroup.ts"; +import { signalProcessGroup } from "@t3tools/provider-core/server/processGroup"; import { isWindowsCommandNotFound } from "../processRunner.ts"; import * as OpenCodeServerLedger from "./OpenCodeServerLedger.ts"; -import { collectStreamAsString } from "./providerSnapshot.ts"; +import { collectStreamAsString } from "@t3tools/provider-core/server/snapshotProbe"; import * as NetService from "@t3tools/shared/Net"; import { HostProcessPlatform } from "@t3tools/shared/hostProcess"; import { compareSemverVersions, parseSemver } from "@t3tools/shared/semver"; diff --git a/apps/server/src/provider/opencodeVersionProbe.ts b/apps/server/src/provider/opencodeVersionProbe.ts index d6f9f1bce8e12582445720a1c4f10faa139796f8..aca8ab2e8189e0800a2538426ac2ffb090bed833 100644 --- a/apps/server/src/provider/opencodeVersionProbe.ts +++ b/apps/server/src/provider/opencodeVersionProbe.ts @@ -9,7 +9,7 @@ import * as Schema from "effect/Schema"; import { HttpClient, HttpClientRequest } from "effect/http"; import * as OpenCodeRuntime from "./opencodeRuntime.ts"; -import { parseGenericCliVersion } from "./providerSnapshot.ts"; +import { parseGenericCliVersion } from "@t3tools/provider-core/server/snapshotProbe"; export interface ProbedOpenCode { readonly generation: "v1" | "v2"; diff --git a/apps/server/src/provider/providerCompatibility.test.ts b/apps/server/src/provider/providerCompatibility.test.ts index c677e876de6769ac84f87688f1985bbe07e6b204..bc7291157e5dac6f7ce7eefdf3614172cf501b23 100644 --- a/apps/server/src/provider/providerCompatibility.test.ts +++ b/apps/server/src/provider/providerCompatibility.test.ts @@ -12,8 +12,8 @@ import * as ServerConfig from "../config.ts"; import * as ModelManifest from "./ModelManifest.ts"; import * as ProviderRegistry from "./ProviderRegistry.ts"; import * as ProviderInstanceRegistry from "./ProviderInstanceRegistry.ts"; -import type { ProviderInstance } from "./ProviderDriver.ts"; -import { makeManualOnlyProviderMaintenanceCapabilities } from "./providerMaintenance.ts"; +import type { ProviderInstance } from "@t3tools/provider-core/server/driver"; +import { makeManualOnlyProviderMaintenanceCapabilities } from "@t3tools/provider-core/server/maintenanceResolver"; import { BUILT_IN_DRIVERS } from "./builtInDrivers.ts"; import * as Schema from "effect/Schema"; import { diff --git a/apps/server/src/provider/providerInstallation.test.ts b/apps/server/src/provider/providerInstallation.test.ts index 61cfbf730976eace801146fca6311bfc0318b0a1..d180b0e2dd99bce6543ee5cb0e63cd3eaecc0af0 100644 --- a/apps/server/src/provider/providerInstallation.test.ts +++ b/apps/server/src/provider/providerInstallation.test.ts @@ -15,7 +15,7 @@ import * as Stream from "effect/Stream"; import * as ServerSettings from "../serverSettings.ts"; import * as CodexInstallation from "./CodexInstallation.ts"; import * as AntigravityInstallation from "./AntigravityInstallation.ts"; -import type { ProviderInstance } from "./ProviderDriver.ts"; +import type { ProviderInstance } from "@t3tools/provider-core/server/driver"; import { makeProviderInstallation } from "./providerInstallation.ts"; import * as ProviderInstanceRegistry from "./ProviderInstanceRegistry.ts"; import * as ProviderRegistry from "./ProviderRegistry.ts"; diff --git a/apps/server/src/provider/providerInstallation.ts b/apps/server/src/provider/providerInstallation.ts index 6c8fe697b8a037edf643213044f01e1fc95ae8ef..d888725b3ba925af0aac8e5773f8a6ba428502f2 100644 --- a/apps/server/src/provider/providerInstallation.ts +++ b/apps/server/src/provider/providerInstallation.ts @@ -18,7 +18,7 @@ import * as AntigravityInstallation from "./AntigravityInstallation.ts"; import { deriveProviderInstanceConfigMap } from "./ProviderInstanceRegistryHydration.ts"; import * as ProviderInstanceRegistry from "./ProviderInstanceRegistry.ts"; import * as ProviderRegistry from "./ProviderRegistry.ts"; -import { mergeProviderInstanceEnvironment } from "./ProviderInstanceEnvironment.ts"; +import { mergeProviderInstanceEnvironment } from "@t3tools/provider-core/server/instanceEnvironment"; const ANTIGRAVITY = ProviderDriverKind.make("antigravity"); const hasBinaryPath = Schema.is(Schema.Struct({ binaryPath: Schema.String })); diff --git a/apps/server/src/provider/providerMaintenanceRunner.test.ts b/apps/server/src/provider/providerMaintenanceRunner.test.ts index b6580c78856da81e631edc80b9328dab134e984c..a3c494e504b0316280c851e63efdd01a7858a75b 100644 --- a/apps/server/src/provider/providerMaintenanceRunner.test.ts +++ b/apps/server/src/provider/providerMaintenanceRunner.test.ts @@ -30,7 +30,7 @@ import { makeProviderMaintenanceCapabilities, ProviderVersionCache, type ProviderMaintenanceCapabilities, -} from "./providerMaintenance.ts"; +} from "@t3tools/provider-core/server/maintenanceResolver"; const isServerProviderUpdateError = Schema.is(ServerProviderUpdateError); const CODEX_DRIVER = ProviderDriverKind.make("codex"); diff --git a/apps/server/src/provider/providerMaintenanceRunner.ts b/apps/server/src/provider/providerMaintenanceRunner.ts index cc8b3728785f29e014abdc6a57e3bc5ce3a4b0e8..5ef57660e01fe987fc3363d4162b03d78141a079 100644 --- a/apps/server/src/provider/providerMaintenanceRunner.ts +++ b/apps/server/src/provider/providerMaintenanceRunner.ts @@ -34,9 +34,9 @@ import { resolveLatestProviderVersion, type ProviderMaintenanceCommandAction, ProviderVersionCache, -} from "./providerMaintenance.ts"; -import type { ProviderMaintenanceCapabilities } from "./providerMaintenance.ts"; -import { collectUint8StreamText } from "../stream/collectUint8StreamText.ts"; +} from "@t3tools/provider-core/server/maintenanceResolver"; +import type { ProviderMaintenanceCapabilities } from "@t3tools/provider-core/server/maintenanceResolver"; +import { collectUint8StreamText } from "@t3tools/provider-core/server/collectStreamText"; const isServerProviderUpdateError = Schema.is(ServerProviderUpdateError); const UPDATE_TIMEOUT_MS = 5 * 60_000; diff --git a/apps/server/src/provider/providerUpdateSettings.ts b/apps/server/src/provider/providerUpdateSettings.ts index 30ad2bf8a286cb33389fe57003203418f81fc84b..f61061439730634c798cdfa07fb33d9c28c6484d 100644 --- a/apps/server/src/provider/providerUpdateSettings.ts +++ b/apps/server/src/provider/providerUpdateSettings.ts @@ -3,7 +3,7 @@ import * as Effect from "effect/Effect"; import * as Equal from "effect/Equal"; import * as Stream from "effect/Stream"; -import type * as ServerSettingsModule from "../serverSettings.ts"; +import type { ProviderHostShape } from "@t3tools/provider-core/server/ProviderHost"; export interface ProviderSnapshotSettings { readonly provider: Settings; @@ -29,7 +29,7 @@ export function haveProviderSnapshotSettingsChanged( export function makeProviderSnapshotSettingsSource( provider: Settings, - serverSettings: ServerSettingsModule.ServerSettingsService["Service"], + settings: ProviderHostShape["settings"], ): { readonly getSettings: Effect.Effect, ServerSettingsError>; readonly streamSettings: Stream.Stream>; @@ -37,7 +37,7 @@ export function makeProviderSnapshotSettingsSource( const mapSettings = (settings: ServerSettings) => makeProviderSnapshotSettings(provider, settings); return { - getSettings: serverSettings.getSettings.pipe(Effect.map(mapSettings)), - streamSettings: serverSettings.streamChanges.pipe(Stream.map(mapSettings)), + getSettings: settings.get.pipe(Effect.map(mapSettings)), + streamSettings: settings.changes.pipe(Stream.map(mapSettings)), }; } diff --git a/apps/server/src/provider/testUtils/providerRegistryMock.ts b/apps/server/src/provider/testUtils/providerRegistryMock.ts index aa27bc94608c6fbcb1ed8ad22772596ec789fa9d..41b5c9b9ca35355d6067f3297cc7cc3f0f3fbb99 100644 --- a/apps/server/src/provider/testUtils/providerRegistryMock.ts +++ b/apps/server/src/provider/testUtils/providerRegistryMock.ts @@ -3,7 +3,7 @@ import type { ServerProvider } from "@t3tools/contracts"; import * as Effect from "effect/Effect"; import * as Layer from "effect/Layer"; import * as Stream from "effect/Stream"; -import { makeManualOnlyProviderMaintenanceCapabilities } from "../providerMaintenance.ts"; +import { makeManualOnlyProviderMaintenanceCapabilities } from "@t3tools/provider-core/server/maintenanceResolver"; const makeProviderRegistryMock = ( providers: ReadonlyArray = [], diff --git a/apps/server/src/provider/unavailableProviderSnapshot.ts b/apps/server/src/provider/unavailableProviderSnapshot.ts index de0c799a8cd338f8b1f822f7327a872be516eedf..2c296b4ff89847cba1d9f477b862e6f299ac4d30 100644 --- a/apps/server/src/provider/unavailableProviderSnapshot.ts +++ b/apps/server/src/provider/unavailableProviderSnapshot.ts @@ -18,7 +18,7 @@ import { import * as DateTime from "effect/DateTime"; import * as Effect from "effect/Effect"; -import { buildServerProvider } from "./providerSnapshot.ts"; +import { buildServerProvider } from "@t3tools/provider-core/server/snapshotProbe"; export interface UnavailableProviderSnapshotInput { readonly driverKind: ProviderDriverKind | string; diff --git a/apps/server/src/sourceControl/BitbucketApi.ts b/apps/server/src/sourceControl/BitbucketApi.ts index 18ff81af1c1945b045ffcbdf777f4f8eb4a55b71..fbff83dfedb56e8b68762d7b34dd18bf0e4c785d 100644 --- a/apps/server/src/sourceControl/BitbucketApi.ts +++ b/apps/server/src/sourceControl/BitbucketApi.ts @@ -28,7 +28,7 @@ import { normalizeBitbucketPullRequestRecord, type NormalizedBitbucketPullRequestRecord, } from "./bitbucketPullRequests.ts"; -import { collectUint8StreamText } from "../stream/collectUint8StreamText.ts"; +import { collectUint8StreamText } from "@t3tools/provider-core/server/collectStreamText"; import * as SourceControlProvider from "./SourceControlProvider.ts"; import * as ServerSettings from "../serverSettings.ts"; import * as GitVcsDriver from "../vcs/GitVcsDriver.ts"; diff --git a/apps/server/src/sourceControl/ForgejoCli.ts b/apps/server/src/sourceControl/ForgejoCli.ts index c9298efb9d1d8bdfd3e6a0d8dbd3fac0700b4a6c..eb284af237c84b5ef4c883e0f374e12857884ad3 100644 --- a/apps/server/src/sourceControl/ForgejoCli.ts +++ b/apps/server/src/sourceControl/ForgejoCli.ts @@ -14,7 +14,7 @@ import { ChildProcessSpawner } from "effect/process"; import { decodeJsonResult } from "@t3tools/shared/schemaJson"; import { HostProcessPlatform } from "@t3tools/shared/hostProcess"; import * as VcsProcess from "../vcs/VcsProcess.ts"; -import { collectUint8StreamText } from "../stream/collectUint8StreamText.ts"; +import { collectUint8StreamText } from "@t3tools/provider-core/server/collectStreamText"; import type { SourceControlProviderContext } from "./SourceControlProvider.ts"; const encodeApiBody = Schema.encodeEffect(Schema.fromJsonString(Schema.Unknown)); diff --git a/apps/server/src/sourceControl/GitHubApi.ts b/apps/server/src/sourceControl/GitHubApi.ts index 5f29e8b4053d186c996f22967196dccb09adf911..5a99cf68943b12fc8a6fde117c6afbeba9ccff19 100644 --- a/apps/server/src/sourceControl/GitHubApi.ts +++ b/apps/server/src/sourceControl/GitHubApi.ts @@ -10,7 +10,7 @@ import * as Schema from "effect/Schema"; import * as Semaphore from "effect/Semaphore"; import { HttpClient, HttpClientRequest, type HttpClientResponse } from "effect/http"; -import { collectUint8StreamText } from "../stream/collectUint8StreamText.ts"; +import { collectUint8StreamText } from "@t3tools/provider-core/server/collectStreamText"; import * as GitHubCredentials from "./GitHubCredentials.ts"; import * as GitHubQuota from "./githubQuota.ts"; import * as SourceControlRateLimit from "./SourceControlRateLimit.ts"; diff --git a/apps/server/src/sourceControl/SourceControlRepositoryService.ts b/apps/server/src/sourceControl/SourceControlRepositoryService.ts index f1c149b18f2b26f7ed91bfdd726591d1c66225e8..180d19ccee3551106d666be1e7c3f817f2c500be 100644 --- a/apps/server/src/sourceControl/SourceControlRepositoryService.ts +++ b/apps/server/src/sourceControl/SourceControlRepositoryService.ts @@ -21,7 +21,7 @@ import { } from "@t3tools/contracts"; import * as ServerConfig from "../config.ts"; -import { expandHomePathWith } from "../pathExpansion.ts"; +import { expandHomePathWith } from "@t3tools/provider-core/server/pathExpansion"; import { parseGitCloneProgressLine, type GitCloneProgressLine, diff --git a/apps/server/src/terminal/Manager.ts b/apps/server/src/terminal/Manager.ts index 3c71a8849475f4698a68fdea10b37642b157ff04..23b9e549e0de056605142d23e9f7fbed7bcdf780 100644 --- a/apps/server/src/terminal/Manager.ts +++ b/apps/server/src/terminal/Manager.ts @@ -63,7 +63,7 @@ import * as Scope from "effect/Scope"; import * as SynchronizedRef from "effect/SynchronizedRef"; import * as ServerConfig from "../config.ts"; -import { mergeProviderInstanceEnvironment } from "../provider/ProviderInstanceEnvironment.ts"; +import { mergeProviderInstanceEnvironment } from "@t3tools/provider-core/server/instanceEnvironment"; import { resolveCodexHomeLayout } from "../provider/Drivers/CodexHomeLayout.ts"; import { makeClaudeEnvironment } from "../provider/Drivers/ClaudeHome.ts"; import { deriveProviderInstanceConfigMap } from "../provider/ProviderInstanceRegistryHydration.ts"; @@ -73,7 +73,7 @@ import { terminalRestartsTotal, terminalSessionsTotal, } from "../observability/Metrics.ts"; -import { expandHomePath } from "../pathExpansion.ts"; +import { expandHomePath } from "@t3tools/provider-core/server/pathExpansion"; import * as ProcessRunner from "../processRunner.ts"; import * as PortScanner from "../preview/PortScanner.ts"; import * as NativeTelemetryClient from "../resourceTelemetry/NativeTelemetryClient.ts"; diff --git a/apps/server/src/textGeneration/AntigravityTextGeneration.ts b/apps/server/src/textGeneration/AntigravityTextGeneration.ts index 27144025c0bf18a3d38f036a67739164f04cc1b7..2ff9cb659e8b2102e06b9ddee910ecdb627672fc 100644 --- a/apps/server/src/textGeneration/AntigravityTextGeneration.ts +++ b/apps/server/src/textGeneration/AntigravityTextGeneration.ts @@ -14,7 +14,7 @@ import { type AcpError, AcpRequestError } from "effect-acp/errors"; import { applyAntigravityAcpModelSelection } from "../provider/acp/AntigravityAcpSupport.ts"; import { removeAntigravitySessionFiles } from "../provider/acp/AntigravitySessionFiles.ts"; import type { AcpSessionRuntime } from "../provider/acp/AcpSessionRuntime.ts"; -import * as TextGenerationOperations from "./TextGenerationOperations.ts"; +import * as TextGenerationOperations from "@t3tools/provider-core/server/textGenerationOperations"; const ANTIGRAVITY_TIMEOUT_MS = 180_000; const MAX_OUTPUT_CHARS = 128_000; diff --git a/apps/server/src/textGeneration/ClaudeTextGeneration.test.ts b/apps/server/src/textGeneration/ClaudeTextGeneration.test.ts index 0ee4b8763cfc0a100bc1d9a7c14c73ea4c7b8fb9..46e015123df24b0f9ba9335616be751cd1432d6d 100644 --- a/apps/server/src/textGeneration/ClaudeTextGeneration.test.ts +++ b/apps/server/src/textGeneration/ClaudeTextGeneration.test.ts @@ -19,7 +19,7 @@ import { SYNTHETIC_CLAUDE_THINKING_MODEL, } from "../provider/ClaudeModelCatalog.testFixtures.ts"; import * as TextGeneration from "./TextGeneration.ts"; -import { sanitizeThreadTitle } from "./TextGenerationUtils.ts"; +import { sanitizeThreadTitle } from "@t3tools/provider-core/server/textGenerationUtils"; import { makeClaudeTextGeneration } from "./ClaudeTextGeneration.ts"; import { writeFakeCli } from "../testUtils/fakeCli.ts"; const decodeClaudeSettings = Schema.decodeSync(ClaudeSettings); diff --git a/apps/server/src/textGeneration/ClaudeTextGeneration.ts b/apps/server/src/textGeneration/ClaudeTextGeneration.ts index 5140ce3cdc30406fcbccc5669fe49f77f6e71ed4..25695f7fdefae498d680a221db7f0fb7df647fb6 100644 --- a/apps/server/src/textGeneration/ClaudeTextGeneration.ts +++ b/apps/server/src/textGeneration/ClaudeTextGeneration.ts @@ -17,8 +17,11 @@ import { ChildProcess, ChildProcessSpawner } from "effect/process"; import { type ClaudeSettings, TextGenerationError } from "@t3tools/contracts"; import { resolveSpawnCommand } from "@t3tools/shared/shell"; -import * as TextGenerationOperations from "./TextGenerationOperations.ts"; -import { normalizeCliError, toJsonSchemaObject } from "./TextGenerationUtils.ts"; +import * as TextGenerationOperations from "@t3tools/provider-core/server/textGenerationOperations"; +import { + normalizeCliError, + toJsonSchemaObject, +} from "@t3tools/provider-core/server/textGenerationUtils"; import { getModelSelectionStringOptionValue, getProviderOptionDescriptors, diff --git a/apps/server/src/textGeneration/CodexTextGeneration.ts b/apps/server/src/textGeneration/CodexTextGeneration.ts index 25b4578bead6f4d608f50c913def9b650728b6a2..0477c7fa163be5da381ce04262a66a905a8e6672 100644 --- a/apps/server/src/textGeneration/CodexTextGeneration.ts +++ b/apps/server/src/textGeneration/CodexTextGeneration.ts @@ -17,10 +17,13 @@ import { resolveSpawnCommand } from "@t3tools/shared/shell"; import { resolveAttachmentPath } from "../attachmentStore.ts"; import * as ServerConfig from "../config.ts"; -import { expandHomePath } from "../pathExpansion.ts"; +import { expandHomePath } from "@t3tools/provider-core/server/pathExpansion"; import { codexExecLaunchArgs, resolveCodexLaunchArgs } from "../provider/codexLaunchArgs.ts"; -import * as TextGenerationOperations from "./TextGenerationOperations.ts"; -import { normalizeCliError, toJsonSchemaObject } from "./TextGenerationUtils.ts"; +import * as TextGenerationOperations from "@t3tools/provider-core/server/textGenerationOperations"; +import { + normalizeCliError, + toJsonSchemaObject, +} from "@t3tools/provider-core/server/textGenerationUtils"; import { codexModelFamily, getModelSelectionStringOptionValue } from "@t3tools/shared/model"; import { getCodexServiceTierOptionValue } from "../codexModelOptions.ts"; diff --git a/apps/server/src/textGeneration/CursorTextGeneration.ts b/apps/server/src/textGeneration/CursorTextGeneration.ts index a147d2f1ae459a26f352bd4dba44c639a77f918e..fb796438158b168bcd85b180ad88a4e3cf3fdb95 100644 --- a/apps/server/src/textGeneration/CursorTextGeneration.ts +++ b/apps/server/src/textGeneration/CursorTextGeneration.ts @@ -13,7 +13,7 @@ import { TextGenerationError, } from "@t3tools/contracts"; -import * as TextGenerationOperations from "./TextGenerationOperations.ts"; +import * as TextGenerationOperations from "@t3tools/provider-core/server/textGenerationOperations"; import { cursorSdkModelSelection } from "../provider/cursorSdkModel.ts"; import type { CursorAuth } from "../provider/CursorAuth.ts"; diff --git a/apps/server/src/textGeneration/GrokTextGeneration.ts b/apps/server/src/textGeneration/GrokTextGeneration.ts index 77f252c45d1eb680d5868d988c08619777cbe362..6e14fa101ee278d244e38be792603b3f99e154f7 100644 --- a/apps/server/src/textGeneration/GrokTextGeneration.ts +++ b/apps/server/src/textGeneration/GrokTextGeneration.ts @@ -9,7 +9,7 @@ import type * as EffectAcpErrors from "effect-acp/errors"; import { type GrokSettings, TextGenerationError } from "@t3tools/contracts"; import { getModelSelectionStringOptionValue } from "@t3tools/shared/model"; -import * as TextGenerationOperations from "./TextGenerationOperations.ts"; +import * as TextGenerationOperations from "@t3tools/provider-core/server/textGenerationOperations"; import { applyGrokAcpModelSelection, currentGrokModelIdFromSessionSetup, diff --git a/apps/server/src/textGeneration/MuseTextGeneration.ts b/apps/server/src/textGeneration/MuseTextGeneration.ts index 7b3b3e76ad672c57ad2eac9e2ad1dc8c109a0868..e0d4f3f3afa519ead68c1d325083c1e89146d4e5 100644 --- a/apps/server/src/textGeneration/MuseTextGeneration.ts +++ b/apps/server/src/textGeneration/MuseTextGeneration.ts @@ -26,13 +26,13 @@ import { buildCommitMessagePrompt, buildPrContentPrompt, buildThreadTitlePrompt, -} from "./TextGenerationPrompts.ts"; +} from "@t3tools/provider-core/server/textGenerationPrompts"; import { sanitizeCommitSubject, sanitizePrTitle, sanitizeThreadTitle, toJsonSchemaObject, -} from "./TextGenerationUtils.ts"; +} from "@t3tools/provider-core/server/textGenerationUtils"; const SessionStarted = Schema.Struct({ session: Schema.Struct({ sessionId: Schema.String }) }); const ItemNotification = Schema.Struct({ diff --git a/apps/server/src/textGeneration/OpenCode2TextGeneration.ts b/apps/server/src/textGeneration/OpenCode2TextGeneration.ts index e0557a3a131782b571b1fbd5a028c7e083177d5a..f6ceb7252a8e1e70df12cbb9c21cd3861973ad10 100644 --- a/apps/server/src/textGeneration/OpenCode2TextGeneration.ts +++ b/apps/server/src/textGeneration/OpenCode2TextGeneration.ts @@ -19,7 +19,7 @@ import { resolveAttachmentPath } from "../attachmentStore.ts"; import type { OpenCode2Connection } from "../provider/opencode2/OpenCode2Server.ts"; import * as OpenCode2Server from "../provider/opencode2/OpenCode2Server.ts"; import { parseOpenCodeModelSlug } from "../provider/opencodeRuntime.ts"; -import * as TextGenerationOperations from "./TextGenerationOperations.ts"; +import * as TextGenerationOperations from "@t3tools/provider-core/server/textGenerationOperations"; const isTextGenerationError = Schema.is(TextGenerationError); diff --git a/apps/server/src/textGeneration/OpenCodeTextGeneration.ts b/apps/server/src/textGeneration/OpenCodeTextGeneration.ts index b47a020715c30b29eefb2fbb034c82f66ded8543..5ffcf45661852267f5bfe8a9dc05b2ca6047bacf 100644 --- a/apps/server/src/textGeneration/OpenCodeTextGeneration.ts +++ b/apps/server/src/textGeneration/OpenCodeTextGeneration.ts @@ -6,7 +6,7 @@ import { getModelSelectionStringOptionValue } from "@t3tools/shared/model"; import * as ServerConfig from "../config.ts"; import { resolveAttachmentPath } from "../attachmentStore.ts"; -import * as TextGenerationOperations from "./TextGenerationOperations.ts"; +import * as TextGenerationOperations from "@t3tools/provider-core/server/textGenerationOperations"; import * as OpenCodeRuntime from "../provider/opencodeRuntime.ts"; import * as OpenCodeServerOwner from "../provider/OpenCodeServerOwner.ts"; diff --git a/apps/server/src/textGeneration/PiTextGeneration.ts b/apps/server/src/textGeneration/PiTextGeneration.ts index e4d56d0d5271095f3e54d11c322982e80efda30c..7d52e4e08e6597ce1645f83897e766d04a1a36e8 100644 --- a/apps/server/src/textGeneration/PiTextGeneration.ts +++ b/apps/server/src/textGeneration/PiTextGeneration.ts @@ -17,7 +17,7 @@ import { buildPiRpcLaunch, resolvePiLaunchArgs, } from "../orchestration-v2/Adapters/piT3McpInjection.ts"; -import * as TextGenerationOperations from "./TextGenerationOperations.ts"; +import * as TextGenerationOperations from "@t3tools/provider-core/server/textGenerationOperations"; const PI_TIMEOUT_MS = 180_000; diff --git a/apps/server/src/textGeneration/TextGeneration.test.ts b/apps/server/src/textGeneration/TextGeneration.test.ts index ff95b780c31d8bafb094c52a39be217dbcf37297..61baaebe4dc20b916baac9f648a02c8488ea8f05 100644 --- a/apps/server/src/textGeneration/TextGeneration.test.ts +++ b/apps/server/src/textGeneration/TextGeneration.test.ts @@ -8,12 +8,12 @@ import { describe, expect } from "vite-plus/test"; import { ProviderInstanceId } from "@t3tools/contracts"; import { createModelSelection } from "@t3tools/shared/model"; -import type { ProviderInstance } from "../provider/ProviderDriver.ts"; +import type { ProviderInstance } from "@t3tools/provider-core/server/driver"; import * as ProviderInstanceRegistry from "../provider/ProviderInstanceRegistry.ts"; import * as TextGeneration from "./TextGeneration.ts"; import * as SourceControlProviderRegistry from "../sourceControl/SourceControlProviderRegistry.ts"; import * as Layer from "effect/Layer"; -import { buildThreadTitlePrompt } from "./TextGenerationPrompts.ts"; +import { buildThreadTitlePrompt } from "@t3tools/provider-core/server/textGenerationPrompts"; const makeStubTextGeneration = ( overrides: Partial, diff --git a/apps/server/src/textGeneration/TextGeneration.ts b/apps/server/src/textGeneration/TextGeneration.ts index f6ef94290db9cbe92b38d9b7465d9cac6b121f79..ee6f18e7b217bbde235b26d4a66fc1cdee2f046b 100644 --- a/apps/server/src/textGeneration/TextGeneration.ts +++ b/apps/server/src/textGeneration/TextGeneration.ts @@ -1,119 +1,32 @@ import * as Context from "effect/Context"; import * as Effect from "effect/Effect"; import * as Layer from "effect/Layer"; -import type { - BranchNamingOptions, - ChatAttachment, - ModelSelection, - ProviderInstanceId, -} from "@t3tools/contracts"; +import type { ProviderInstanceId } from "@t3tools/contracts"; +import type { ProviderTextGeneration } from "@t3tools/provider-core/server/textGeneration"; import { TextGenerationError } from "@t3tools/contracts"; import * as ProviderInstanceRegistry from "../provider/ProviderInstanceRegistry.ts"; -import type { ProviderInstance } from "../provider/ProviderDriver.ts"; +import type { ProviderInstance } from "@t3tools/provider-core/server/driver"; import * as SourceControlProviderRegistry from "../sourceControl/SourceControlProviderRegistry.ts"; import * as ThreadTitleLinks from "./ThreadTitleLinks.ts"; -import type { TextGenerationPolicy } from "./TextGenerationPolicy.ts"; -export interface CommitMessageGenerationInput { - cwd: string; - branch: string | null; - stagedSummary: string; - stagedPatch: string; - /** When true, the model also returns a semantic branch name for the change. */ - includeBranch?: boolean; - policy?: TextGenerationPolicy | undefined; - /** What model and provider to use for generation. */ - modelSelection: ModelSelection; -} - -export interface CommitMessageGenerationResult { - subject: string; - body: string; - /** Only present when `includeBranch` was set on the input. */ - branch?: string | undefined; -} - -export interface PrContentGenerationInput { - cwd: string; - baseBranch: string; - headBranch: string; - commitSummary: string; - diffSummary: string; - diffPatch: string; - changeRequestTemplate?: string | undefined; - policy?: TextGenerationPolicy | undefined; - /** What model and provider to use for generation. */ - modelSelection: ModelSelection; -} - -export interface PrContentGenerationResult { - title: string; - body: string; -} - -export interface BranchNameGenerationInput { - naming?: BranchNamingOptions | undefined; - cwd: string; - message: string; - attachments?: ReadonlyArray | undefined; - /** What model and provider to use for generation. */ - modelSelection: ModelSelection; -} - -export interface BranchNameGenerationResult { - branch: string; -} - -export interface ThreadTitleGenerationInput { - linkedContext?: string | undefined; - cwd: string; - message: string; - /** Present when replacing an existing title from the current thread history. */ - previousTitle?: string | undefined; - attachments?: ReadonlyArray | undefined; - /** What model and provider to use for generation. */ - modelSelection: ModelSelection; -} - -export interface ThreadTitleGenerationResult { - title: string; - needsRefinement?: boolean | undefined; -} +export type { + BranchNameGenerationInput, + BranchNameGenerationResult, + CommitMessageGenerationInput, + CommitMessageGenerationResult, + PrContentGenerationInput, + PrContentGenerationResult, + ThreadTitleGenerationInput, + ThreadTitleGenerationResult, +} from "@t3tools/provider-core/server/textGeneration"; /** * TextGeneration - Service tag for commit and change request text generation. */ -export class TextGeneration extends Context.Service< - TextGeneration, - { - /** - * Generate a commit message from staged change context. - */ - readonly generateCommitMessage: ( - input: CommitMessageGenerationInput, - ) => Effect.Effect; - - /** - * Generate change request title/body from branch and diff context. - */ - readonly generatePrContent: ( - input: PrContentGenerationInput, - ) => Effect.Effect; - - /** - * Generate a concise branch name from a user message. - */ - readonly generateBranchName: ( - input: BranchNameGenerationInput, - ) => Effect.Effect; - - /** Generate a concise thread title from a first message or thread history. */ - readonly generateThreadTitle: ( - input: ThreadTitleGenerationInput, - ) => Effect.Effect; - } ->()("t3/textGeneration/TextGeneration") {} +export class TextGeneration extends Context.Service()( + "t3/textGeneration/TextGeneration", +) {} type TextGenerationOp = | "generateCommitMessage" diff --git a/apps/server/src/textGeneration/TextGenerationOperations.ts b/apps/server/src/textGeneration/TextGenerationOperations.ts deleted file mode 100644 index b1fc905cae06709126a81d5654491b2e128a676f..0000000000000000000000000000000000000000 --- a/apps/server/src/textGeneration/TextGenerationOperations.ts +++ /dev/null @@ -1,153 +0,0 @@ -/** - * The text generation operations every provider shares. A provider supplies a - * runner that sends one prompt and decodes the reply; prompts, linked source - * control context, and output sanitizing live here so providers cannot drift - * on them. - * - * @module textGeneration/TextGenerationOperations - */ -import * as Effect from "effect/Effect"; -import * as Schema from "effect/Schema"; - -import { type ChatAttachment, type ModelSelection, TextGenerationError } from "@t3tools/contracts"; -import { formatGeneratedBranchName, sanitizeFeatureBranchName } from "@t3tools/shared/git"; -import { extractJsonObject } from "@t3tools/shared/schemaJson"; - -import type * as TextGeneration from "./TextGeneration.ts"; -import { - buildBranchNamePrompt, - buildCommitMessagePrompt, - buildPrContentPrompt, - buildThreadTitlePrompt, -} from "./TextGenerationPrompts.ts"; -import { - sanitizeCommitSubject, - sanitizePrTitle, - sanitizeThreadTitle, -} from "./TextGenerationUtils.ts"; - -export type Operation = keyof TextGeneration.TextGeneration["Service"]; - -/** One prompt for a provider to run. */ -export interface Request { - readonly operation: Operation; - readonly cwd: string; - readonly prompt: string; - readonly outputSchema: S; - readonly modelSelection: ModelSelection; - /** The user's attachments, already listed in the prompt. Providers that accept images send them. */ - readonly attachments?: ReadonlyArray | undefined; -} - -/** Runs one request and decodes the reply as its `outputSchema`. */ -export type Runner = ( - request: Request, -) => Effect.Effect; - -/** Decodes the JSON object in a text reply, which models often wrap in prose. */ -export const decodeJsonReply = ( - request: Pick, "operation" | "outputSchema">, - provider: string, - text: string, -) => { - // Each request builds its own output schema, so the decoder cannot be hoisted. - const decodeOutput = Schema.decodeEffect(Schema.fromJsonString(request.outputSchema)); - return decodeOutput(extractJsonObject(text)).pipe( - Effect.mapError( - (cause) => - new TextGenerationError({ - operation: request.operation, - detail: `${provider} returned invalid structured output.`, - cause, - }), - ), - ); -}; - -/** The text generation service over `run`. `name` prefixes each operation's span. */ -export function fromRunner(name: string, run: Runner): TextGeneration.TextGeneration["Service"] { - const generateCommitMessage: TextGeneration.TextGeneration["Service"]["generateCommitMessage"] = - Effect.fn(`${name}.generateCommitMessage`)(function* (input) { - const generated = yield* run({ - operation: "generateCommitMessage", - cwd: input.cwd, - modelSelection: input.modelSelection, - ...buildCommitMessagePrompt({ - branch: input.branch, - stagedSummary: input.stagedSummary, - stagedPatch: input.stagedPatch, - includeBranch: input.includeBranch === true, - policy: input.policy, - }), - }); - return { - subject: sanitizeCommitSubject(generated.subject), - body: generated.body.trim(), - ...("branch" in generated && typeof generated.branch === "string" - ? { branch: sanitizeFeatureBranchName(generated.branch) } - : {}), - }; - }); - - const generatePrContent: TextGeneration.TextGeneration["Service"]["generatePrContent"] = - Effect.fn(`${name}.generatePrContent`)(function* (input) { - const generated = yield* run({ - operation: "generatePrContent", - cwd: input.cwd, - modelSelection: input.modelSelection, - ...buildPrContentPrompt({ - baseBranch: input.baseBranch, - headBranch: input.headBranch, - commitSummary: input.commitSummary, - diffSummary: input.diffSummary, - diffPatch: input.diffPatch, - policy: input.policy, - changeRequestTemplate: input.changeRequestTemplate, - }), - }); - return { title: sanitizePrTitle(generated.title), body: generated.body.trim() }; - }); - - const generateBranchName: TextGeneration.TextGeneration["Service"]["generateBranchName"] = - Effect.fn(`${name}.generateBranchName`)(function* (input) { - const generated = yield* run({ - operation: "generateBranchName", - cwd: input.cwd, - modelSelection: input.modelSelection, - attachments: input.attachments, - ...buildBranchNamePrompt({ - message: input.message, - attachments: input.attachments, - naming: input.naming, - }), - }); - return { branch: formatGeneratedBranchName(generated.branch, input.naming) }; - }); - - const generateThreadTitle: TextGeneration.TextGeneration["Service"]["generateThreadTitle"] = - Effect.fn(`${name}.generateThreadTitle`)(function* (input) { - const generated = yield* run({ - operation: "generateThreadTitle", - cwd: input.cwd, - modelSelection: input.modelSelection, - attachments: input.attachments, - ...buildThreadTitlePrompt({ - message: input.message, - previousTitle: input.previousTitle, - linkedContext: input.linkedContext, - attachments: input.attachments, - }), - }); - return { - title: sanitizeThreadTitle(generated.title), - ...(generated.needsRefinement ? { needsRefinement: true } : {}), - }; - }); - - return { - generateCommitMessage, - generatePrContent, - generateBranchName, - generateThreadTitle, - } satisfies TextGeneration.TextGeneration["Service"]; -} diff --git a/apps/server/src/textGeneration/TextGenerationPresets.ts b/apps/server/src/textGeneration/TextGenerationPresets.ts index 5fab9219080fabdbf225acb6a8721c08b20987b7..b53ecc543597d051633181c93fda57758d0fb32e 100644 --- a/apps/server/src/textGeneration/TextGenerationPresets.ts +++ b/apps/server/src/textGeneration/TextGenerationPresets.ts @@ -1,4 +1,4 @@ -import type { TextGenerationPolicy } from "./TextGenerationPolicy.ts"; +import type { TextGenerationPolicy } from "@t3tools/provider-core/server/textGenerationPolicy"; export const conventionalCommitsTextGenerationPolicy: TextGenerationPolicy = { kind: "conventional_commits", diff --git a/apps/server/src/usage/UsageService.ts b/apps/server/src/usage/UsageService.ts index c06c025158986132dd23329f1b4b747f91215a39..4ff2bbce9ef668148579fef97a4306b37808c39d 100644 --- a/apps/server/src/usage/UsageService.ts +++ b/apps/server/src/usage/UsageService.ts @@ -54,11 +54,11 @@ import { HttpClient, HttpClientResponse } from "effect/http"; import { writeFileStringAtomically } from "../atomicWrite.ts"; import * as ServerConfig from "../config.ts"; -import { expandHomePath } from "../pathExpansion.ts"; +import { expandHomePath } from "@t3tools/provider-core/server/pathExpansion"; import * as ServerSettings from "../serverSettings.ts"; import { resolveCodexHomeLayout } from "../provider/Drivers/CodexHomeLayout.ts"; import { resolveAntigravityInstanceDirectories } from "../provider/antigravityAuthSupport.ts"; -import { mergeProviderInstanceEnvironment } from "../provider/ProviderInstanceEnvironment.ts"; +import { mergeProviderInstanceEnvironment } from "@t3tools/provider-core/server/instanceEnvironment"; import { readOpenCodeUsage } from "./opencodeUsageReader.ts"; import { makeAntigravityUsageCache, readAntigravityUsage } from "./antigravityUsageReader.ts"; import { diff --git a/apps/server/src/usage/cliproxyApi.ts b/apps/server/src/usage/cliproxyApi.ts index 3804b96491058e531da608077a8fa3a35c06f2e4..c50ebb57f40eb2ee43196c64ad563fdb97604ee2 100644 --- a/apps/server/src/usage/cliproxyApi.ts +++ b/apps/server/src/usage/cliproxyApi.ts @@ -15,7 +15,7 @@ import { HttpClient, HttpClientRequest, HttpClientResponse } from "effect/http"; import { codexPlanLabel } from "../provider/CodexProvider.ts"; import { codexRateLimitsToLimits } from "../provider/codexUsageLimits.ts"; import { claudeUsageResponseToLimits } from "../provider/claudeUsageLimits.ts"; -import { makeUnavailableUsageLimits } from "../provider/providerUsageLimits.ts"; +import { makeUnavailableUsageLimits } from "@t3tools/provider-core/server/usageLimits"; const AuthFile = Schema.Struct({ id: Schema.String, diff --git a/apps/server/src/workspace/WorkspaceEntries.ts b/apps/server/src/workspace/WorkspaceEntries.ts index d575f944d885c24df69daec6a5de708496ca9fb2..1a39c754b16525232860df82e49ae5cd20a1e8ba 100644 --- a/apps/server/src/workspace/WorkspaceEntries.ts +++ b/apps/server/src/workspace/WorkspaceEntries.ts @@ -23,7 +23,7 @@ import { HostProcessPlatform } from "@t3tools/shared/hostProcess"; import { isExplicitRelativePath, isWindowsAbsolutePath } from "@t3tools/shared/path"; import { normalizeSearchQuery } from "@t3tools/shared/searchRanking"; -import { expandHomePathWith } from "../pathExpansion.ts"; +import { expandHomePathWith } from "@t3tools/provider-core/server/pathExpansion"; import * as VcsProcess from "../vcs/VcsProcess.ts"; import * as WorkspacePaths from "./WorkspacePaths.ts"; import * as WorkspaceSearchIndex from "./WorkspaceSearchIndex.ts"; diff --git a/apps/server/src/workspace/WorkspacePaths.ts b/apps/server/src/workspace/WorkspacePaths.ts index 29c00e2b3da6151817e0b62bc40cfa0962338f83..82dedf3b159a7dd1582523759b2ae84d571a68e9 100644 --- a/apps/server/src/workspace/WorkspacePaths.ts +++ b/apps/server/src/workspace/WorkspacePaths.ts @@ -14,7 +14,7 @@ import * as Layer from "effect/Layer"; import * as Path from "effect/Path"; import * as Schema from "effect/Schema"; -import { expandHomePathWith } from "../pathExpansion.ts"; +import { expandHomePathWith } from "@t3tools/provider-core/server/pathExpansion"; export class WorkspaceRootNotExistsError extends Schema.TaggedError()( "WorkspaceRootNotExistsError", diff --git a/apps/server/src/worktreesDirectory.ts b/apps/server/src/worktreesDirectory.ts index 5d4652393747c4b8e11c88fdba087c818baaa716..2496a593fd2d62ff6b058c10ce38874e6654a62e 100644 --- a/apps/server/src/worktreesDirectory.ts +++ b/apps/server/src/worktreesDirectory.ts @@ -1,6 +1,6 @@ import type * as Path from "effect/Path"; -import { expandHomePathWith } from "./pathExpansion.ts"; +import { expandHomePathWith } from "@t3tools/provider-core/server/pathExpansion"; /** * Directory new worktrees are created under: the `worktreesDirectory` diff --git a/apps/server/src/ws.ts b/apps/server/src/ws.ts index 2a11852ecbc50fa884fa8dffde2c25f60e095dfd..5e2dfc6b5dc77f5ccef5dcfae89b9807559913e8 100644 --- a/apps/server/src/ws.ts +++ b/apps/server/src/ws.ts @@ -121,7 +121,7 @@ import * as McpAppRequests from "./mcpApps/McpAppRequests.ts"; import * as ProviderSessionManager from "./orchestration-v2/ProviderSessionManager.ts"; import * as ThreadLaunchService from "./orchestration-v2/ThreadLaunchService.ts"; import * as ThreadMessageIntake from "./orchestration-v2/ThreadMessageIntake.ts"; -import * as IdAllocator from "./orchestration-v2/IdAllocator.ts"; +import * as IdAllocator from "@t3tools/provider-core/server/IdAllocator"; import * as ScheduledTasks from "./scheduledTasks/ScheduledTaskService.ts"; import * as SecretRequests from "./secrets/SecretRequests.ts"; import { @@ -168,7 +168,7 @@ import * as ProviderInstanceRegistry from "./provider/ProviderInstanceRegistry.t import * as AcpRegistrySupport from "./provider/acp/AcpRegistrySupport.ts"; import * as AcpRegistryRuntimeCoordinator from "./provider/acp/AcpRegistryRuntimeCoordinator.ts"; import * as ModelManifest from "./provider/ModelManifest.ts"; -import * as ProviderMaintenance from "./provider/providerMaintenance.ts"; +import * as ProviderMaintenance from "@t3tools/provider-core/server/maintenanceResolver"; import * as ProviderMaintenanceRunner from "./provider/providerMaintenanceRunner.ts"; import * as ProviderAuthService from "./provider/ProviderAuthService.ts"; import { makeProviderInstallation } from "./provider/providerInstallation.ts"; diff --git a/apps/web/package.json b/apps/web/package.json index 20e180aad46b50d3a95e796f52cb7bab890d9a80..53547e6cfc2219e18fa7c0da95561aab5b75afe9 100644 --- a/apps/web/package.json +++ b/apps/web/package.json @@ -28,6 +28,7 @@ "@pierre/trees": "1.0.0-beta.6", "@t3tools/client-runtime": "workspace:*", "@t3tools/contracts": "workspace:*", + "@t3tools/provider-core": "workspace:*", "@t3tools/shared": "workspace:*", "@tanstack/react-pacer": "^0.19.4", "@tanstack/react-router": "^1.160.2", diff --git a/apps/web/src/components/chat/ComposerUsageLimits.tsx b/apps/web/src/components/chat/ComposerUsageLimits.tsx index 04d32f610855b034072c1614141f412454d02a8c..514f379d9f3363858930ad53d05bfc399b8674f1 100644 --- a/apps/web/src/components/chat/ComposerUsageLimits.tsx +++ b/apps/web/src/components/chat/ComposerUsageLimits.tsx @@ -4,7 +4,7 @@ import { GaugeIcon } from "lucide-react"; import { ensureLocalApi } from "../../localApi"; import { Button } from "../ui/button"; -import { getDriverOption } from "../settings/providerDriverMeta"; +import { providerClients } from "../settings/providerDriverMeta"; import { RedactedSensitiveText } from "../settings/RedactedSensitiveText"; import { LimitWindows, ResetCredits } from "../usage/UsageLimits"; import { ComposerBanner } from "./ComposerBanner"; @@ -13,7 +13,7 @@ import type { ComposerBannerStackItem } from "./ComposerBannerStack"; /** Driver name, then the instance when there could be more than one of that driver. */ function accountLabel(account: UsageLimitsReport["accounts"][number]): string { if (!account.instanceId) return account.label; - const driver = getDriverOption(account.driver)?.label ?? String(account.driver); + const driver = providerClients.get(account.driver)?.label ?? String(account.driver); const instance = account.displayName?.trim() || (String(account.instanceId) !== String(account.driver) ? account.instanceId : ""); diff --git a/apps/web/src/components/onboarding/WelcomeWizard.import.test.tsx b/apps/web/src/components/onboarding/WelcomeWizard.import.test.tsx index 8b052d76168a0924e501fe9f7bd5793778ecf707..79d10c3c6bb2adf037a2258637023f811d56d22f 100644 --- a/apps/web/src/components/onboarding/WelcomeWizard.import.test.tsx +++ b/apps/web/src/components/onboarding/WelcomeWizard.import.test.tsx @@ -132,7 +132,9 @@ vi.mock("../settings/CodexSetupSection", () => ({ CodexSetupSection: () => null, AddManagedCodexAccountDialog: () => null, })); -vi.mock("../settings/providerDriverMeta", () => ({ getDriverOption: () => ({ label: "Agent" }) })); +vi.mock("../settings/providerDriverMeta", () => ({ + providerClients: { get: () => ({ label: "Agent" }) }, +})); vi.mock("../settings/providerStatus", () => ({ getProviderSummary: () => ({ headline: "Checking", detail: null }), })); diff --git a/apps/web/src/components/onboarding/WelcomeWizard.terminal.test.tsx b/apps/web/src/components/onboarding/WelcomeWizard.terminal.test.tsx index cf7c38ec5875d74adbdd460a9d77b37edcf41656..0a3ae9abc311f94df29ebe4b206f1219acdf0850 100644 --- a/apps/web/src/components/onboarding/WelcomeWizard.terminal.test.tsx +++ b/apps/web/src/components/onboarding/WelcomeWizard.terminal.test.tsx @@ -119,7 +119,7 @@ vi.mock("../settings/CodexSetupSection", () => ({ AddManagedCodexAccountDialog: () => null, })); vi.mock("../settings/providerDriverMeta", () => ({ - getDriverOption: (driver: string) => ({ label: driver }), + providerClients: { get: (driver: string) => ({ label: driver }) }, })); vi.mock("../settings/providerStatus", () => ({ getProviderSummary: () => ({ headline: "Setup required" }), diff --git a/apps/web/src/components/onboarding/WelcomeWizard.tsx b/apps/web/src/components/onboarding/WelcomeWizard.tsx index e94078271799b64e6cca634a91bd2c25d2c47d6c..9a4549efc9faaa8bb5495e8eb971f179b99c2d8a 100644 --- a/apps/web/src/components/onboarding/WelcomeWizard.tsx +++ b/apps/web/src/components/onboarding/WelcomeWizard.tsx @@ -74,7 +74,7 @@ import { terminalEnvironment } from "../../state/terminal"; import { useAtomCommand } from "../../state/use-atom-command"; import { connectPairing } from "../../connection/onboarding"; import { getProviderSummary } from "../settings/providerStatus"; -import { getDriverOption } from "../settings/providerDriverMeta"; +import { providerClients } from "../settings/providerDriverMeta"; import { ChatGptWelcomeCoordinator } from "../settings/ChatGptWelcomeCoordinator"; import { AddManagedCodexAccountDialog, CodexSetupSection } from "../settings/CodexSetupSection"; import { readCodexSetupMode } from "../settings/CodexSetupSection.logic"; @@ -969,7 +969,7 @@ function AgentCard({ readonly terminalAvailable: boolean; readonly onOpenTerminal: () => void; }) { - const meta = getDriverOption(ProviderDriverKind.make(driver)); + const meta = providerClients.get(ProviderDriverKind.make(driver)); const displayName = provider?.displayName || (driver === "claudeAgent" ? "Claude Code" : (meta?.label ?? driver)); const summary = getProviderSummary(provider); diff --git a/apps/web/src/components/settings/AddProviderInstanceDialog.tsx b/apps/web/src/components/settings/AddProviderInstanceDialog.tsx index b329d6ef134bd0d39fbef53d060ba10c166b1665..e923a081b6e43c8919b05e76db1564a36624f442 100644 --- a/apps/web/src/components/settings/AddProviderInstanceDialog.tsx +++ b/apps/web/src/components/settings/AddProviderInstanceDialog.tsx @@ -33,7 +33,7 @@ import { Badge } from "../ui/badge"; import { Input } from "../ui/input"; import { RadioGroup } from "../ui/radio-group"; import { toastManager } from "../ui/toast"; -import { DRIVER_OPTION_BY_VALUE, DRIVER_OPTIONS } from "./providerDriverMeta"; +import { providerClients } from "./providerDriverMeta"; import { ProviderAccentColorPicker } from "./ProviderAccentColorPicker"; import { SettingsGroup } from "./SettingsGroup"; import { SettingsRow } from "./settingsLayout"; @@ -81,7 +81,7 @@ function deriveInstanceId(driver: ProviderDriverKind, label: string): string { const INSTANCE_ID_PATTERN = /^[a-zA-Z][a-zA-Z0-9_-]*$/; const DEFAULT_DRIVER_KIND = ProviderDriverKind.make("codex"); const ACP_REGISTRY_DRIVER_KIND = ProviderDriverKind.make("acpRegistry"); -const DEFAULT_DRIVER_OPTION = DRIVER_OPTIONS[0]!; +const DEFAULT_DRIVER_OPTION = providerClients.definitions[0]!; const EMPTY_CONFIG_DRAFT: Record = {}; /** * Validate an instance id against the same slug rules the server applies in @@ -149,7 +149,7 @@ export function AddProviderInstanceDialog({ return ids; }, [settings.providerInstances, settings.providers]); - const driverOption = DRIVER_OPTION_BY_VALUE[driver] ?? DEFAULT_DRIVER_OPTION; + const driverOption = providerClients.get(driver) ?? DEFAULT_DRIVER_OPTION; const isAcpRegistry = driver === ACP_REGISTRY_DRIVER_KIND; const defaultIdentity: ProviderIdentityDraft = { label: driverOption.label, @@ -433,16 +433,17 @@ export function AddProviderInstanceDialog({ aria-labelledby="add-instance-driver-label" className="grid grid-cols-1 sm:grid-cols-2" > - {DRIVER_OPTIONS.filter((option) => option.value !== ACP_REGISTRY_DRIVER_KIND).map( - (option) => { + {providerClients.definitions + .filter((option) => option.driverKind !== ACP_REGISTRY_DRIVER_KIND) + .map((option) => { return ( @@ -462,8 +463,7 @@ export function AddProviderInstanceDialog({ ) : null} ); - }, - )} + })} diff --git a/apps/web/src/components/settings/ProviderInstanceCard.tsx b/apps/web/src/components/settings/ProviderInstanceCard.tsx index eab2fba04cb28a9b4e3df086eb744bf273cbca3f..e147dd2cb44770e526606f2c329608f34ce75be7 100644 --- a/apps/web/src/components/settings/ProviderInstanceCard.tsx +++ b/apps/web/src/components/settings/ProviderInstanceCard.tsx @@ -46,7 +46,10 @@ import { Popover, PopoverPopup, PopoverTrigger } from "../ui/popover"; import { Switch } from "../ui/switch"; import { stackedThreadToast, toastManager } from "../ui/toast"; import { Tooltip, TooltipPopup, TooltipTrigger } from "../ui/tooltip"; -import type { DriverOption, ProviderEnvironmentFieldDefinition } from "./providerDriverMeta"; +import type { + ProviderClientDefinition, + ProviderEnvironmentField, +} from "@t3tools/provider-core/client"; import { deriveProviderSettingsFields, ProviderSettingsForm } from "./ProviderSettingsForm"; import { ProviderModelsSection } from "./ProviderModelsSection"; import { ProviderInstanceIcon } from "../chat/ProviderInstanceIcon"; @@ -216,7 +219,7 @@ export function providerEnvironmentWithoutNames( export function nextProviderEnvironmentWithFieldValue( environment: ReadonlyArray | undefined, - field: ProviderEnvironmentFieldDefinition, + field: ProviderEnvironmentField, value: string, ): ReadonlyArray { const trimmed = value.trim(); @@ -250,11 +253,11 @@ export function nextProviderEnvironmentWithFieldValue( } function ProviderEnvironmentFieldRow(props: { - readonly field: ProviderEnvironmentFieldDefinition; + readonly field: ProviderEnvironmentField; readonly variable: ProviderInstanceEnvironmentVariable | undefined; readonly idPrefix: string; - readonly onCommit: (field: ProviderEnvironmentFieldDefinition, value: string) => void; - readonly onRemove: (field: ProviderEnvironmentFieldDefinition) => void; + readonly onCommit: (field: ProviderEnvironmentField, value: string) => void; + readonly onRemove: (field: ProviderEnvironmentField) => void; }) { const inputId = `${props.idPrefix}-environment-${props.field.name}`; const value = props.variable?.valueRedacted ? "" : (props.variable?.value ?? ""); @@ -472,7 +475,7 @@ export function ProviderEnvironmentSection(props: { interface ProviderInstanceCardProps { readonly instanceId: ProviderInstanceId; readonly instance: ProviderInstanceConfig; - readonly driverOption: DriverOption | undefined; + readonly driverOption: ProviderClientDefinition | undefined; readonly liveProvider: ServerProvider | undefined; readonly mode: "list" | "editor"; readonly selected?: boolean | undefined; @@ -719,10 +722,10 @@ export function ProviderInstanceCard({ ); updateEnvironment([...dedicatedEnvironment, ...environment]); }; - const updateEnvironmentField = (field: ProviderEnvironmentFieldDefinition, value: string) => { + const updateEnvironmentField = (field: ProviderEnvironmentField, value: string) => { updateEnvironment(nextProviderEnvironmentWithFieldValue(instance.environment, field, value)); }; - const removeEnvironmentField = (field: ProviderEnvironmentFieldDefinition) => { + const removeEnvironmentField = (field: ProviderEnvironmentField) => { updateEnvironment(providerEnvironmentWithoutNames(instance.environment, new Set([field.name]))); }; diff --git a/apps/web/src/components/settings/ProviderSettingsForm.test.ts b/apps/web/src/components/settings/ProviderSettingsForm.test.ts index 6edeedb307405b57140f64f83c78161ca371da1b..ff1de91addc9c863f6b90fe5fa7b0d7c0950f467 100644 --- a/apps/web/src/components/settings/ProviderSettingsForm.test.ts +++ b/apps/web/src/components/settings/ProviderSettingsForm.test.ts @@ -1,7 +1,7 @@ import { describe, expect, it } from "vite-plus/test"; import { ProviderDriverKind } from "@t3tools/contracts"; -import { DRIVER_OPTION_BY_VALUE } from "./providerDriverMeta"; +import { providerClients } from "./providerDriverMeta"; import { deriveProviderSettingsFields, nextProviderConfigWithFieldValue, @@ -9,7 +9,7 @@ import { describe("ProviderSettingsForm helpers", () => { it("derives visible provider config fields from the client definition schema", () => { - const codex = DRIVER_OPTION_BY_VALUE[ProviderDriverKind.make("codex")]; + const codex = providerClients.get(ProviderDriverKind.make("codex")); expect(codex).toBeDefined(); expect(deriveProviderSettingsFields(codex!).map((field) => field.key)).toEqual([ @@ -21,7 +21,7 @@ describe("ProviderSettingsForm helpers", () => { }); it("sources labels and descriptions from schema annotations", () => { - const opencode = DRIVER_OPTION_BY_VALUE[ProviderDriverKind.make("opencode")]; + const opencode = providerClients.get(ProviderDriverKind.make("opencode")); expect(opencode).toBeDefined(); const serverPassword = deriveProviderSettingsFields(opencode!).find( @@ -36,7 +36,7 @@ describe("ProviderSettingsForm helpers", () => { }); it("uses a dedicated environment field instead of legacy Cursor CLI settings", () => { - const cursor = DRIVER_OPTION_BY_VALUE[ProviderDriverKind.make("cursor")]; + const cursor = providerClients.get(ProviderDriverKind.make("cursor")); expect(cursor).toBeDefined(); expect(deriveProviderSettingsFields(cursor!)).toEqual([]); @@ -52,7 +52,7 @@ describe("ProviderSettingsForm helpers", () => { }); it("exposes ACP Registry as an instance-only configurable driver", () => { - const acpRegistry = DRIVER_OPTION_BY_VALUE[ProviderDriverKind.make("acpRegistry")]; + const acpRegistry = providerClients.get(ProviderDriverKind.make("acpRegistry")); expect(acpRegistry).toBeDefined(); expect(acpRegistry?.hasDefaultInstance).toBe(false); @@ -65,14 +65,14 @@ describe("ProviderSettingsForm helpers", () => { }); it("shows the local executable without registry identity or authentication fields", () => { - const acpRegistry = DRIVER_OPTION_BY_VALUE[ProviderDriverKind.make("acpRegistry")]; + const acpRegistry = providerClients.get(ProviderDriverKind.make("acpRegistry")); expect( deriveProviderSettingsFields(acpRegistry!, { source: "local" }).map((field) => field.key), ).toEqual(["source", "commandPath"]); }); it("derives a select control with its choices for the Antigravity sign-in method", () => { - const antigravity = DRIVER_OPTION_BY_VALUE[ProviderDriverKind.make("antigravity")]; + const antigravity = providerClients.get(ProviderDriverKind.make("antigravity")); expect(antigravity).toBeDefined(); const fields = deriveProviderSettingsFields(antigravity!); @@ -95,7 +95,7 @@ describe("ProviderSettingsForm helpers", () => { }); it("shows the auto-compaction threshold for Claude providers", () => { - const claude = DRIVER_OPTION_BY_VALUE[ProviderDriverKind.make("claudeAgent")]; + const claude = providerClients.get(ProviderDriverKind.make("claudeAgent")); expect(claude).toBeDefined(); expect(deriveProviderSettingsFields(claude!).map((field) => field.key)).toEqual([ @@ -107,7 +107,7 @@ describe("ProviderSettingsForm helpers", () => { }); it("preserves unknown config keys while omitting empty configurable fields", () => { - const opencode = DRIVER_OPTION_BY_VALUE[ProviderDriverKind.make("opencode")]; + const opencode = providerClients.get(ProviderDriverKind.make("opencode")); expect(opencode).toBeDefined(); const serverUrl = deriveProviderSettingsFields(opencode!).find( diff --git a/apps/web/src/components/settings/ProviderSettingsForm.tsx b/apps/web/src/components/settings/ProviderSettingsForm.tsx index dfb35facbd60d4070be8f686d11d04d13f4ff794..d772585c74f30006be65fdfacb270fab0090399d 100644 --- a/apps/web/src/components/settings/ProviderSettingsForm.tsx +++ b/apps/web/src/components/settings/ProviderSettingsForm.tsx @@ -18,7 +18,7 @@ import { Input } from "../ui/input"; import { Select, SelectItem, SelectPopup, SelectTrigger, SelectValue } from "../ui/select"; import { Switch } from "../ui/switch"; import { Textarea } from "../ui/textarea"; -import type { ProviderClientDefinition } from "./providerDriverMeta"; +import type { ProviderClientDefinition } from "@t3tools/provider-core/client"; import { SettingsRow } from "./settingsLayout"; export interface ProviderSettingsFieldModel { @@ -81,7 +81,8 @@ export function deriveProviderSettingsFields( value?: unknown, ): ReadonlyArray { const isLocalAcp = - definition.value === "acpRegistry" && readProviderConfigString(value, "source") === "local"; + definition.driverKind === "acpRegistry" && + readProviderConfigString(value, "source") === "local"; const schemaAnnotation = readProviderSettingsFormSchemaAnnotation(definition); const orderedKeys = new Map( (schemaAnnotation.order ?? []).map((key, index) => [key, index] as const), @@ -537,7 +538,8 @@ export function ProviderSettingsForm({ [definition, value], ); const isLocalAcp = - definition.value === "acpRegistry" && readProviderConfigString(value, "source") === "local"; + definition.driverKind === "acpRegistry" && + readProviderConfigString(value, "source") === "local"; if (fields.length === 0) { return null; diff --git a/apps/web/src/components/settings/ProviderSettingsPanel.tsx b/apps/web/src/components/settings/ProviderSettingsPanel.tsx index 37b986217d29d111a48932c10b8bbe958b596fc9..dd471b4d14e8791494de0b358649aa21a7a89424 100644 --- a/apps/web/src/components/settings/ProviderSettingsPanel.tsx +++ b/apps/web/src/components/settings/ProviderSettingsPanel.tsx @@ -95,7 +95,7 @@ import { ProviderSetupSection, readAntigravityAuthMethod } from "./ProviderSetup import { ProviderAuthenticationSection } from "./ProviderAuthenticationSection"; import { CodexSetupSection, CodexManagedRuntimeFields } from "./CodexSetupSection"; import { readCodexSetupMode } from "./CodexSetupSection.logic"; -import { DRIVER_OPTIONS, getDriverOption } from "./providerDriverMeta"; +import { providerClients } from "./providerDriverMeta"; import { searchableSetting } from "./settingsSearch"; import { backgroundActivityOverrideSettings, @@ -145,8 +145,8 @@ function providerConfigString(config: unknown, key: string): string | null { return typeof value === "string" && value.trim().length > 0 ? value.trim() : null; } -const PROVIDER_SETTINGS = DRIVER_OPTIONS.map((definition) => ({ - provider: definition.value, +const PROVIDER_SETTINGS = providerClients.definitions.map((definition) => ({ + provider: definition.driverKind, })); function configuredBinaryPath(config: unknown): string { @@ -975,7 +975,7 @@ export function EnvironmentProviderSettings({ }; const renderProviderInstance = (row: InstanceRow, mode: "list" | "editor") => { - const driverOption = getDriverOption(row.driver); + const driverOption = providerClients.get(row.driver); const liveProvider = serverProviders.find( (candidate) => candidate.instanceId === row.instanceId, ); diff --git a/apps/web/src/components/settings/providerDriverMeta.ts b/apps/web/src/components/settings/providerDriverMeta.ts index c576082fd025703b1304a25cdcbb450da7fc0d70..60d2d346d13bb4c3519fbc6a8dc6948500984df5 100644 --- a/apps/web/src/components/settings/providerDriverMeta.ts +++ b/apps/web/src/components/settings/providerDriverMeta.ts @@ -10,56 +10,22 @@ import { MuseSettings, ProviderDriverKind, } from "@t3tools/contracts"; -import type * as Schema from "effect/Schema"; +import { makeProviderClientRegistry } from "@t3tools/provider-core/client"; -type ProviderSettingsSchema = { - readonly fields: Readonly>; -} & Schema.Top; - -/** - * Browser-safe provider definition. This is deliberately shaped like the - * future provider package client export: the core web app gets a schema with - * field annotations plus provider-level presentation metadata, then renders - * settings generically. - */ -export interface ProviderClientDefinition { - readonly value: ProviderDriverKind; - readonly label: string; - readonly settingsSchema: ProviderSettingsSchema; - readonly environmentFields?: readonly ProviderEnvironmentFieldDefinition[]; - /** Whether this driver has a built-in default instance backed by legacy settings. */ - readonly hasDefaultInstance?: boolean; - /** - * Optional short label rendered as a `variant="warning"` badge next to - * the instance title. Used to flag drivers that still ship under an - * early-access or preview gate — the flag is a property of the driver - * kind (not a specific instance), so every instance of that driver — - * built-in default or custom — advertises the same marker. - */ - readonly badgeLabel?: string; -} - -export interface ProviderEnvironmentFieldDefinition { - readonly name: string; - readonly label: string; - readonly description?: string; - readonly placeholder?: string; - readonly sensitive?: boolean; -} - -const PROVIDER_CLIENT_DEFINITIONS: readonly ProviderClientDefinition[] = [ +/** The provider client definitions this web build ships, in presentation order. */ +export const providerClients = makeProviderClientRegistry([ { - value: ProviderDriverKind.make("codex"), + driverKind: ProviderDriverKind.make("codex"), label: "Codex", settingsSchema: CodexSettings, }, { - value: ProviderDriverKind.make("claudeAgent"), + driverKind: ProviderDriverKind.make("claudeAgent"), label: "Claude", settingsSchema: ClaudeSettings, }, { - value: ProviderDriverKind.make("cursor"), + driverKind: ProviderDriverKind.make("cursor"), label: "Cursor", settingsSchema: CursorSettings, environmentFields: [ @@ -73,55 +39,35 @@ const PROVIDER_CLIENT_DEFINITIONS: readonly ProviderClientDefinition[] = [ ], }, { - value: ProviderDriverKind.make("grok"), + driverKind: ProviderDriverKind.make("grok"), label: "Grok", settingsSchema: GrokSettings, }, { - value: ProviderDriverKind.make("opencode"), + driverKind: ProviderDriverKind.make("opencode"), label: "OpenCode", settingsSchema: OpenCodeSettings, }, { - value: ProviderDriverKind.make("antigravity"), + driverKind: ProviderDriverKind.make("antigravity"), label: "Antigravity", settingsSchema: AntigravitySettings, }, { - value: ProviderDriverKind.make("muse"), + driverKind: ProviderDriverKind.make("muse"), label: "Muse Code", settingsSchema: MuseSettings, badgeLabel: "Beta", }, { - value: ProviderDriverKind.make("pi"), + driverKind: ProviderDriverKind.make("pi"), label: "Pi", settingsSchema: PiSettings, }, { - value: ProviderDriverKind.make("acpRegistry"), + driverKind: ProviderDriverKind.make("acpRegistry"), label: "ACP Registry", settingsSchema: AcpRegistrySettings, hasDefaultInstance: false, }, -]; - -const PROVIDER_CLIENT_DEFINITION_BY_VALUE: Partial< - Record -> = Object.fromEntries( - PROVIDER_CLIENT_DEFINITIONS.map((definition) => [definition.value, definition]), -); - -export const DRIVER_OPTIONS = PROVIDER_CLIENT_DEFINITIONS; -export const DRIVER_OPTION_BY_VALUE = PROVIDER_CLIENT_DEFINITION_BY_VALUE; -export type DriverOption = ProviderClientDefinition; - -/** - * Look up the driver metadata for an instance's `driver` field. Accepts - * Returns `undefined` for fork / unknown drivers so callers can decide how - * to render them — typically by falling back to a generic card. - */ -export function getDriverOption(driver: ProviderDriverKind | undefined): DriverOption | undefined { - if (driver === undefined) return undefined; - return PROVIDER_CLIENT_DEFINITION_BY_VALUE[driver]; -} +]); diff --git a/apps/web/src/components/usage/UsageLimitsPooled.tsx b/apps/web/src/components/usage/UsageLimitsPooled.tsx index 9ebe499179b06590712bf9fc820cf43e3cd32b04..be48577555aa8129ee7038564bc834bff55e6144 100644 --- a/apps/web/src/components/usage/UsageLimitsPooled.tsx +++ b/apps/web/src/components/usage/UsageLimitsPooled.tsx @@ -21,7 +21,7 @@ import { usePrimarySettings } from "../../hooks/useSettings"; import { cn } from "../../lib/utils"; import { formatUpcomingTimestamp } from "../../timestampFormat"; import { ProviderInstanceIcon } from "../chat/ProviderInstanceIcon"; -import { getDriverOption } from "../settings/providerDriverMeta"; +import { providerClients } from "../settings/providerDriverMeta"; import { RedactedSensitiveText } from "../settings/RedactedSensitiveText"; import { Button } from "../ui/button"; import { OpenAI } from "../Icons"; @@ -81,7 +81,9 @@ function AccountAvatar({ - {getDriverOption(account.driver)?.label ?? String(account.driver)} + {providerClients.get(account.driver)?.label ?? String(account.driver)} ); } @@ -166,7 +168,7 @@ function SegmentPopover({ - {account.displayName ?? getDriverOption(account.driver)?.label ?? account.driver} + {account.displayName ?? providerClients.get(account.driver)?.label ?? account.driver} {account.email ? ( @@ -531,7 +533,7 @@ function PoolWindowCard({ function PoolSection({ pool, now }: { readonly pool: LimitPool; readonly now: number }) { const color = barColor(pool.driver); - const label = getDriverOption(pool.driver)?.label ?? String(pool.driver); + const label = providerClients.get(pool.driver)?.label ?? String(pool.driver); const windows = displayLimitWindows(pool); return (
diff --git a/apps/web/src/components/usage/UsagePage.refresh.test.tsx b/apps/web/src/components/usage/UsagePage.refresh.test.tsx index bbe53e36936a5c0ff6c43d000118f76c8385639e..ff19e20fc84d5bb1264af5755377222572d85048 100644 --- a/apps/web/src/components/usage/UsagePage.refresh.test.tsx +++ b/apps/web/src/components/usage/UsagePage.refresh.test.tsx @@ -91,7 +91,9 @@ vi.mock("./UsageProviderChart", () => ({ UsageProviderChart: "div" })); vi.mock("./UsagePriceOverrides", () => ({ UsagePriceOverrides: () => null })); vi.mock("../chat/ProviderInstanceIcon", () => ({ ProviderInstanceIcon: () => null })); vi.mock("../settings/RedactedSensitiveText", () => ({ RedactedSensitiveText: "span" })); -vi.mock("../settings/providerDriverMeta", () => ({ getDriverOption: () => ({ label: "Codex" }) })); +vi.mock("../settings/providerDriverMeta", () => ({ + providerClients: { get: () => ({ label: "Codex" }) }, +})); import { UsagePage } from "./UsagePage"; diff --git a/docs/internals/adding-a-provider.md b/docs/internals/adding-a-provider.md index 3184f5a1266949fcccadc9c59269cff323360781..d11c0e367d1f7a1fba00e6b805b4137950d2d049 100644 --- a/docs/internals/adding-a-provider.md +++ b/docs/internals/adding-a-provider.md @@ -13,7 +13,7 @@ whether a turn runs. This page lists the decisions and evidence a new driver nee [shared ACP adapter](../../apps/server/src/orchestration-v2/Adapters/AcpAdapterV2.ts), like Grok and Antigravity. Never add agent-id checks to the generic registry adapter. - **Other protocols** get a native adapter that implements - [`ProviderAdapterV2`](../../apps/server/src/orchestration-v2/ProviderAdapter.ts), like Codex, + [`ProviderAdapterV2`](../../packages/provider-core/src/server/ProviderAdapter.ts), like Codex, Claude, Cursor, OpenCode, Pi, and Muse. Provider-specific behavior stays in the adapter and driver. Orchestration and clients read diff --git a/docs/internals/providers.md b/docs/internals/providers.md index 912cd3045531831aef9512b46dc5d34c505563a2..3da603d9ce015e74a8814100c0aa77e7977674b3 100644 --- a/docs/internals/providers.md +++ b/docs/internals/providers.md @@ -2,7 +2,7 @@ Orchestration records intent and state without knowing which provider runs a thread. Provider protocols, account ownership, permissions, and capabilities belong at the -[adapter boundary](../../apps/server/src/orchestration-v2/ProviderAdapter.ts). Normalize there +[adapter boundary](../../packages/provider-core/src/server/ProviderAdapter.ts). Normalize there instead of spreading provider checks through orchestration and clients. A driver kind identifies an integration; an instance identifies one configuration and account diff --git a/package.json b/package.json index 559801c550c7457a6ab8a31e1108be4fb5ea7800..078da2b294523b092d5d8d488d6fa3d4375066b8 100644 --- a/package.json +++ b/package.json @@ -28,7 +28,7 @@ "tc": "vp run -r --concurrency-limit 2 typecheck", "lint": "vp lint --report-unused-disable-directives", "knip": "knip --preprocessor ./scripts/knip-schemas.ts", - "knip:check": "knip --include files,dependencies --no-config-hints && knip --workspace apps/server --workspace apps/desktop --workspace apps/web --workspace packages/client-runtime --workspace packages/contracts --workspace packages/effect-acp --workspace packages/effect-codex-app-server --workspace packages/shared --workspace packages/ssh --workspace packages/tailscale --exports --preprocessor ./scripts/knip-schemas.ts --no-config-hints", + "knip:check": "knip --include files,dependencies --no-config-hints && knip --workspace apps/server --workspace apps/desktop --workspace apps/web --workspace packages/client-runtime --workspace packages/contracts --workspace packages/effect-acp --workspace packages/effect-codex-app-server --workspace packages/shared --workspace packages/ssh --workspace packages/tailscale --workspace packages/provider-core --workspace packages/provider-testing --exports --preprocessor ./scripts/knip-schemas.ts --no-config-hints", "knip:production": "knip --production --preprocessor ./scripts/knip-schemas.ts", "lint:mobile": "node scripts/mobile-native-static-check.ts", "test": "vp run -r test", diff --git a/packages/provider-core/package.json b/packages/provider-core/package.json new file mode 100644 index 0000000000000000000000000000000000000000..23ac2a66e8467dc091dddbfa945c364a8c29ce2d --- /dev/null +++ b/packages/provider-core/package.json @@ -0,0 +1,138 @@ +{ + "name": "@t3tools/provider-core", + "private": true, + "type": "module", + "exports": { + "./client": { + "types": "./src/client.ts", + "import": "./src/client.ts" + }, + "./server/adapterDriver": { + "types": "./src/server/adapterDriver.ts", + "import": "./src/server/adapterDriver.ts" + }, + "./server/auth": { + "types": "./src/server/auth.ts", + "import": "./src/server/auth.ts" + }, + "./server/collectStreamText": { + "types": "./src/server/collectStreamText.ts", + "import": "./src/server/collectStreamText.ts" + }, + "./server/driver": { + "types": "./src/server/driver.ts", + "import": "./src/server/driver.ts" + }, + "./server/errors": { + "types": "./src/server/errors.ts", + "import": "./src/server/errors.ts" + }, + "./server/failure": { + "types": "./src/server/failure.ts", + "import": "./src/server/failure.ts" + }, + "./server/IdAllocator": { + "types": "./src/server/IdAllocator.ts", + "import": "./src/server/IdAllocator.ts" + }, + "./server/instanceEnvironment": { + "types": "./src/server/instanceEnvironment.ts", + "import": "./src/server/instanceEnvironment.ts" + }, + "./server/maintenance": { + "types": "./src/server/maintenance.ts", + "import": "./src/server/maintenance.ts" + }, + "./server/maintenanceResolver": { + "types": "./src/server/maintenanceResolver.ts", + "import": "./src/server/maintenanceResolver.ts" + }, + "./server/mcpSession": { + "types": "./src/server/mcpSession.ts", + "import": "./src/server/mcpSession.ts" + }, + "./server/mcpToolPresentation": { + "types": "./src/server/mcpToolPresentation.ts", + "import": "./src/server/mcpToolPresentation.ts" + }, + "./server/orchestrationInstructions": { + "types": "./src/server/orchestrationInstructions.ts", + "import": "./src/server/orchestrationInstructions.ts" + }, + "./server/pathExpansion": { + "types": "./src/server/pathExpansion.ts", + "import": "./src/server/pathExpansion.ts" + }, + "./server/processGroup": { + "types": "./src/server/processGroup.ts", + "import": "./src/server/processGroup.ts" + }, + "./server/ProviderAdapter": { + "types": "./src/server/ProviderAdapter.ts", + "import": "./src/server/ProviderAdapter.ts" + }, + "./server/ProviderHost": { + "types": "./src/server/ProviderHost.ts", + "import": "./src/server/ProviderHost.ts" + }, + "./server/randomUuid": { + "types": "./src/server/randomUuid.ts", + "import": "./src/server/randomUuid.ts" + }, + "./server/selectionTransition": { + "types": "./src/server/selectionTransition.ts", + "import": "./src/server/selectionTransition.ts" + }, + "./server/snapshot": { + "types": "./src/server/snapshot.ts", + "import": "./src/server/snapshot.ts" + }, + "./server/snapshotProbe": { + "types": "./src/server/snapshotProbe.ts", + "import": "./src/server/snapshotProbe.ts" + }, + "./server/textGeneration": { + "types": "./src/server/textGeneration.ts", + "import": "./src/server/textGeneration.ts" + }, + "./server/textGenerationOperations": { + "types": "./src/server/textGenerationOperations.ts", + "import": "./src/server/textGenerationOperations.ts" + }, + "./server/textGenerationPolicy": { + "types": "./src/server/textGenerationPolicy.ts", + "import": "./src/server/textGenerationPolicy.ts" + }, + "./server/textGenerationPrompts": { + "types": "./src/server/textGenerationPrompts.ts", + "import": "./src/server/textGenerationPrompts.ts" + }, + "./server/textGenerationUtils": { + "types": "./src/server/textGenerationUtils.ts", + "import": "./src/server/textGenerationUtils.ts" + }, + "./server/threadTitleContext": { + "types": "./src/server/threadTitleContext.ts", + "import": "./src/server/threadTitleContext.ts" + }, + "./server/usageLimits": { + "types": "./src/server/usageLimits.ts", + "import": "./src/server/usageLimits.ts" + } + }, + "scripts": { + "typecheck": "tsc --noEmit", + "test": "vp test run --config ../../vite.config.ts --dir ." + }, + "dependencies": { + "@t3tools/contracts": "workspace:*", + "@t3tools/shared": "workspace:*", + "effect": "catalog:" + }, + "devDependencies": { + "@effect/platform-node": "catalog:", + "@effect/vitest": "catalog:", + "@types/node": "catalog:", + "vite-plus": "catalog:" + } +} diff --git a/packages/provider-core/src/client.test.ts b/packages/provider-core/src/client.test.ts new file mode 100644 index 0000000000000000000000000000000000000000..25fa59325de1df7a2278d1f691cf3e886ff659d2 --- /dev/null +++ b/packages/provider-core/src/client.test.ts @@ -0,0 +1,34 @@ +import { ProviderDriverKind } from "@t3tools/contracts"; +import * as Schema from "effect/Schema"; +import { describe, expect, it } from "vite-plus/test"; + +import { defineProviderClient, makeProviderClientRegistry } from "./client.ts"; + +const settingsSchema = Schema.Struct({ binaryPath: Schema.String }); + +describe("makeProviderClientRegistry", () => { + it("looks definitions up by driver kind and keeps unknown drivers undefined", () => { + const codex = defineProviderClient({ + driverKind: ProviderDriverKind.make("codex"), + label: "Codex", + settingsSchema, + }); + const registry = makeProviderClientRegistry([codex]); + + expect(registry.get(ProviderDriverKind.make("codex"))).toBe(codex); + expect(registry.get(ProviderDriverKind.make("forkDriver"))).toBeUndefined(); + expect(registry.get(undefined)).toBeUndefined(); + }); + + it("rejects two definitions for one driver kind", () => { + const definition = defineProviderClient({ + driverKind: ProviderDriverKind.make("codex"), + label: "Codex", + settingsSchema, + }); + + expect(() => makeProviderClientRegistry([definition, definition])).toThrow( + "Provider driver 'codex' is defined more than once.", + ); + }); +}); diff --git a/packages/provider-core/src/client.ts b/packages/provider-core/src/client.ts new file mode 100644 index 0000000000000000000000000000000000000000..18c64cede5956df11d5cca39e5210ad94fe66d93 --- /dev/null +++ b/packages/provider-core/src/client.ts @@ -0,0 +1,77 @@ +/** + * The client half of a provider package. + * + * Every provider package exports a `ProviderClientDefinition` from its + * `./client` entry point. Clients render settings, labels, and badges from + * these definitions plus the server's `ServerProvider` snapshots, so a new + * provider needs no per-driver branches in web or mobile. + * + * Definitions are browser- and React Native-safe: plain data and Effect + * schemas, no platform UI imports. + * + * @module provider-core/client + */ +import type { ProviderDriverKind } from "@t3tools/contracts"; +import type * as Schema from "effect/Schema"; + +/** + * A provider's instance settings schema. Fields carry `providerSettingsForm` + * annotations, which the settings form renders generically. + */ +export type ProviderSettingsSchema = { + readonly fields: Readonly>; +} & Schema.Top; + +/** An environment variable the settings UI offers for every instance of a driver. */ +export interface ProviderEnvironmentField { + readonly name: string; + readonly label: string; + readonly description?: string; + readonly placeholder?: string; + readonly sensitive?: boolean; +} + +export interface ProviderClientDefinition { + readonly driverKind: ProviderDriverKind; + readonly label: string; + readonly settingsSchema: ProviderSettingsSchema; + readonly environmentFields?: ReadonlyArray; + /** Whether the driver has a default instance backed by legacy `providers.` settings. */ + readonly hasDefaultInstance?: boolean; + /** + * Short warning badge beside every instance of the driver, such as "Beta". + * It marks the driver kind, so built-in and custom instances show it alike. + */ + readonly badgeLabel?: string; +} + +export function defineProviderClient( + definition: Definition, +): Definition { + return definition; +} + +/** The provider definitions a client loaded, in presentation order. */ +export interface ProviderClientRegistry { + readonly definitions: ReadonlyArray; + /** `undefined` for drivers this client does not ship, such as a fork's driver. */ + readonly get: ( + driverKind: ProviderDriverKind | undefined, + ) => ProviderClientDefinition | undefined; +} + +export function makeProviderClientRegistry( + definitions: ReadonlyArray, +): ProviderClientRegistry { + const byDriverKind = new Map(); + for (const definition of definitions) { + if (byDriverKind.has(definition.driverKind)) { + throw new Error(`Provider driver '${definition.driverKind}' is defined more than once.`); + } + byDriverKind.set(definition.driverKind, definition); + } + return { + definitions, + get: (driverKind) => (driverKind === undefined ? undefined : byDriverKind.get(driverKind)), + }; +} diff --git a/apps/server/src/orchestration-v2/IdAllocator.ts b/packages/provider-core/src/server/IdAllocator.ts similarity index 99% rename from apps/server/src/orchestration-v2/IdAllocator.ts rename to packages/provider-core/src/server/IdAllocator.ts index f619e45095c09059a44930674e36a9e03db76d10..cb31cfb5895f7ff0e509bacca4c6e4e610dc42d1 100644 --- a/apps/server/src/orchestration-v2/IdAllocator.ts +++ b/packages/provider-core/src/server/IdAllocator.ts @@ -26,7 +26,7 @@ import * as Effect from "effect/Effect"; import * as Layer from "effect/Layer"; import * as Schema from "effect/Schema"; -import { randomUuidV4 } from "./RandomUuid.ts"; +import { randomUuidV4 } from "./randomUuid.ts"; export const IdAllocatorV2Kind = Schema.Literals([ "command", @@ -186,7 +186,7 @@ export interface IdAllocatorV2Shape { } export class IdAllocatorV2 extends Context.Service()( - "t3/orchestration-v2/IdAllocator/IdAllocatorV2", + "@t3tools/provider-core/server/IdAllocator/IdAllocatorV2", ) {} const encodePart = (part: string | number): string => encodeURIComponent(String(part)); diff --git a/apps/server/src/orchestration-v2/ProviderAdapter.ts b/packages/provider-core/src/server/ProviderAdapter.ts similarity index 99% rename from apps/server/src/orchestration-v2/ProviderAdapter.ts rename to packages/provider-core/src/server/ProviderAdapter.ts index 298bbf9a9fe12326ef142bc0ffd707579e6b40b2..3cc27acd6d5e5fc778d8680e730fdaf399e5d500 100644 --- a/apps/server/src/orchestration-v2/ProviderAdapter.ts +++ b/packages/provider-core/src/server/ProviderAdapter.ts @@ -42,7 +42,7 @@ import type * as Stream from "effect/Stream"; import type { ProviderSelectionTransitionInput, ProviderSelectionTransitionPlan, -} from "./ProviderSelectionTransition.ts"; +} from "./selectionTransition.ts"; export const ProviderAdapterV2RuntimePolicy = Schema.Struct({ runtimeMode: RuntimeMode, @@ -641,5 +641,5 @@ export interface ProviderAdapterV2Shape { } export class ProviderAdapterV2 extends Context.Service()( - "t3/orchestration-v2/ProviderAdapter/ProviderAdapterV2", + "@t3tools/provider-core/server/ProviderAdapter/ProviderAdapterV2", ) {} diff --git a/packages/provider-core/src/server/ProviderHost.ts b/packages/provider-core/src/server/ProviderHost.ts new file mode 100644 index 0000000000000000000000000000000000000000..f0a695da43d404eddf47d8c3ff16fd39eb381dcb --- /dev/null +++ b/packages/provider-core/src/server/ProviderHost.ts @@ -0,0 +1,54 @@ +/** + * ProviderHost — what a provider package may ask of the server it runs in. + * + * Drivers and adapters run inside a T3 server but must not import it. The + * server provides this one service; everything a provider needs from its + * environment (directories, server settings, background demand, attachment + * files) goes through it, so a provider package depends only on + * `@t3tools/provider-core` and its own protocol code. + * + * @module provider-core/server/host + */ +import type { + BackgroundScope, + ChatAttachment, + ServerSettings, + ServerSettingsError, +} from "@t3tools/contracts"; +import * as Context from "effect/Context"; +import type * as Effect from "effect/Effect"; +import type * as Scope from "effect/Scope"; +import type * as Stream from "effect/Stream"; + +export interface ProviderHostPaths { + /** Directory the server was started in; the fallback cwd for sessions without a project. */ + readonly cwd: string; + /** T3 home. */ + readonly baseDir: string; + /** Server-owned state directory under the T3 home. */ + readonly stateDir: string; + /** Scratch space for provider probes and generated helper files. */ + readonly providerStatusCacheDir: string; +} + +export interface ProviderHostShape { + readonly paths: ProviderHostPaths; + readonly settings: { + readonly get: Effect.Effect; + /** Every settings change after subscription, starting with the next one. */ + readonly changes: Stream.Stream; + /** Changes buffered from the moment the scoped subscription is acquired. */ + readonly subscribe: Effect.Effect, never, Scope.Scope>; + }; + /** Whether background work for `scope` should run now (client demand and host power). */ + readonly shouldRunBackgroundWork: (scope: BackgroundScope) => Effect.Effect; + /** + * Absolute path of a stored chat attachment, or `null` when its id does not + * resolve inside the attachments directory. + */ + readonly resolveAttachmentPath: (attachment: ChatAttachment) => string | null; +} + +export class ProviderHost extends Context.Service()( + "@t3tools/provider-core/server/ProviderHost", +) {} diff --git a/apps/server/src/orchestration-v2/ProviderAdapterDriver.ts b/packages/provider-core/src/server/adapterDriver.ts similarity index 94% rename from apps/server/src/orchestration-v2/ProviderAdapterDriver.ts rename to packages/provider-core/src/server/adapterDriver.ts index 765abd21af0f9f87ac6c512d383cde07f4fc3f7a..6a2e57daab0bb6121a8bd78e411ac574c5314710 100644 --- a/apps/server/src/orchestration-v2/ProviderAdapterDriver.ts +++ b/packages/provider-core/src/server/adapterDriver.ts @@ -7,7 +7,7 @@ import * as Schema from "effect/Schema"; import type * as Effect from "effect/Effect"; import type * as Scope from "effect/Scope"; -import type { ProviderAdapterV2Shape } from "./ProviderAdapter.ts"; +import type { ProviderAdapterV2Shape } from "@t3tools/provider-core/server/ProviderAdapter"; export class ProviderAdapterDriverCreateError extends Schema.TaggedError()( "ProviderAdapterDriverCreateError", diff --git a/packages/provider-core/src/server/auth.ts b/packages/provider-core/src/server/auth.ts new file mode 100644 index 0000000000000000000000000000000000000000..9954249b67968d32a54bd4a32eaf57c5e203b0f6 --- /dev/null +++ b/packages/provider-core/src/server/auth.ts @@ -0,0 +1,57 @@ +import type { + ChatGptReconnectProfile, + ChatGptTransferredProfile, + ProviderAuthRespondInput, + ProviderAuthState, + ProviderSetupError, +} from "@t3tools/contracts"; +import type * as Effect from "effect/Effect"; +import type * as Scope from "effect/Scope"; +import type * as Stream from "effect/Stream"; + +export interface ProviderAuthController { + /** Equal keys mean these instances share credentials on this environment. */ + readonly credentialBinding?: { readonly owner: "provider" | "t3"; readonly key: string }; + readonly reconnectProfile?: ( + methodId: string, + ) => Effect.Effect; + readonly importProfile?: ( + profile: ChatGptTransferredProfile, + stopSessions: Effect.Effect, + ) => Effect.Effect; + readonly adoptCredentials?: ( + update: Effect.Effect, + stopSessions: Effect.Effect, + ) => Effect.Effect; + readonly isChangingCredentials?: Effect.Effect; + readonly invalidate?: Effect.Effect; + readonly refreshMethods?: Effect.Effect; + readonly withAccess?: ( + task: Effect.Effect, + ) => Effect.Effect; + readonly start: ( + ownerSessionId: string, + stopSessions?: Effect.Effect, + methodId?: string, + returnUrl?: string, + callbackMode?: "server" | "client", + ) => Effect.Effect; + readonly complete: ( + ownerSessionId: string, + input: { readonly flowId: string; readonly callbackUrl: string }, + ) => Effect.Effect; + readonly cancel: ( + ownerSessionId: string, + flowId: string, + ) => Effect.Effect; + readonly respond?: ( + ownerSessionId: string, + input: ProviderAuthRespondInput, + ) => Effect.Effect; + /** The controller closes process admission before it stops routed sessions. */ + readonly logout: ( + stopSessions: Effect.Effect, + ) => Effect.Effect; + readonly subscribe: (ownerSessionId: string) => Stream.Stream; + readonly isLogoutPrompt?: (text: string, hasAttachments: boolean) => boolean; +} diff --git a/apps/server/src/stream/collectUint8StreamText.test.ts b/packages/provider-core/src/server/collectStreamText.test.ts similarity index 96% rename from apps/server/src/stream/collectUint8StreamText.test.ts rename to packages/provider-core/src/server/collectStreamText.test.ts index 4a41cf11ec68b1503946b722aaead14bde0a552e..c36bfcf3b9fc656402117f9d6cbe9f21ec91ab65 100644 --- a/apps/server/src/stream/collectUint8StreamText.test.ts +++ b/packages/provider-core/src/server/collectStreamText.test.ts @@ -2,7 +2,7 @@ import { assert, describe, it } from "@effect/vitest"; import * as Effect from "effect/Effect"; import * as Stream from "effect/Stream"; -import { collectUint8StreamText } from "./collectUint8StreamText.ts"; +import { collectUint8StreamText } from "./collectStreamText.ts"; const encoder = new TextEncoder(); diff --git a/apps/server/src/stream/collectUint8StreamText.ts b/packages/provider-core/src/server/collectStreamText.ts similarity index 100% rename from apps/server/src/stream/collectUint8StreamText.ts rename to packages/provider-core/src/server/collectStreamText.ts diff --git a/apps/server/src/provider/ProviderDriver.ts b/packages/provider-core/src/server/driver.ts similarity index 95% rename from apps/server/src/provider/ProviderDriver.ts rename to packages/provider-core/src/server/driver.ts index d51061731b509d96b75959219b1bf9241c9a4b8c..ed91c24d883317501a730c43b0b1c8e97833f771 100644 --- a/apps/server/src/provider/ProviderDriver.ts +++ b/packages/provider-core/src/server/driver.ts @@ -19,7 +19,7 @@ * ChildProcessSpawner, …) on its `create` return type; the registry * layer's R is the union of those, and the runtime layer satisfies it. * - * @module provider/ProviderDriver + * @module provider-core/server/driver */ import type { ProviderConsumeResetCreditOutcome, @@ -37,11 +37,11 @@ import type * as Effect from "effect/Effect"; import type * as Schema from "effect/Schema"; import type * as Scope from "effect/Scope"; -import type { TextGeneration } from "../textGeneration/TextGeneration.ts"; -import type { ProviderAdapterV2Shape } from "../orchestration-v2/ProviderAdapter.ts"; -import type { ProviderDriverError } from "./Errors.ts"; -import type { ProviderAuthController } from "./ProviderAuthService.ts"; -import type { ServerProviderShape } from "./ServerProvider.ts"; +import type { ProviderAdapterV2Shape } from "./ProviderAdapter.ts"; +import type { ProviderAuthController } from "./auth.ts"; +import type { ProviderDriverError } from "./errors.ts"; +import type { ServerProviderShape } from "./snapshot.ts"; +import type { ProviderTextGeneration } from "./textGeneration.ts"; /** * Static metadata advertised by a driver. Used for default presentation @@ -96,7 +96,7 @@ export interface ProviderInstance { ProviderDriverError >; readonly orchestrationAdapter: ProviderAdapterV2Shape; - readonly textGeneration: TextGeneration["Service"]; + readonly textGeneration: ProviderTextGeneration; readonly auth?: ProviderAuthController; readonly acpSessionManagement?: { readonly listSessions: (input: { diff --git a/packages/provider-core/src/server/errors.ts b/packages/provider-core/src/server/errors.ts new file mode 100644 index 0000000000000000000000000000000000000000..eda2eaa686ecef6c18b89e1fe66ca821d62ce7f5 --- /dev/null +++ b/packages/provider-core/src/server/errors.ts @@ -0,0 +1,21 @@ +import { ProviderDriverKind, ProviderInstanceId } from "@t3tools/contracts"; +import * as Schema from "effect/Schema"; + +/** + * ProviderDriverError - A driver `create` call failed before producing an + * instance. Surfaced to the registry, which marks the offending entry as + * an "unavailable" shadow snapshot rather than crashing the server. + */ +export class ProviderDriverError extends Schema.TaggedError()( + "ProviderDriverError", + { + driver: ProviderDriverKind, + instanceId: ProviderInstanceId, + detail: Schema.String, + cause: Schema.optional(Schema.Defect()), + }, +) { + override get message(): string { + return `Provider driver '${this.driver}' failed to create instance '${this.instanceId}': ${this.detail}`; + } +} diff --git a/apps/server/src/orchestration-v2/ProviderFailure.test.ts b/packages/provider-core/src/server/failure.test.ts similarity index 97% rename from apps/server/src/orchestration-v2/ProviderFailure.test.ts rename to packages/provider-core/src/server/failure.test.ts index f05d3e91cd8a0b11d55578ec9771bd39b8ea38f4..47fe4c724eb101d932ecac42a5d119cdfb4b68ef 100644 --- a/apps/server/src/orchestration-v2/ProviderFailure.test.ts +++ b/packages/provider-core/src/server/failure.test.ts @@ -16,10 +16,10 @@ import { makeProviderFailureTurnItem, MAX_PROVIDER_FAILURE_CODE_LENGTH, MAX_PROVIDER_FAILURE_MESSAGE_LENGTH, -} from "./ProviderFailure.ts"; + ContextHandoffBudgetError, +} from "./failure.ts"; import * as IdAllocator from "./IdAllocator.ts"; -import { ContextHandoffBudgetError } from "./ContextHandoffDelivery.ts"; -import { ProviderAdapterTurnStartError } from "./ProviderAdapter.ts"; +import { ProviderAdapterTurnStartError } from "@t3tools/provider-core/server/ProviderAdapter"; it("redacts credentials and URL secrets from provider failures", () => { const failure = makeProviderFailure({ diff --git a/apps/server/src/orchestration-v2/ProviderFailure.ts b/packages/provider-core/src/server/failure.ts similarity index 94% rename from apps/server/src/orchestration-v2/ProviderFailure.ts rename to packages/provider-core/src/server/failure.ts index 6cb9275017d910c20ddcaa347baaf8d8c015dfcc..53e663a4c8d960a4c985cbb5d5d29df53e1d9827 100644 --- a/apps/server/src/orchestration-v2/ProviderFailure.ts +++ b/packages/provider-core/src/server/failure.ts @@ -14,7 +14,17 @@ import * as DateTime from "effect/DateTime"; import * as Cause from "effect/Cause"; import type { IdAllocatorV2Shape } from "./IdAllocator.ts"; -import { ContextHandoffBudgetError } from "./ContextHandoffDelivery.ts"; +import * as Schema from "effect/Schema"; + +/** Raised when portable history does not fit the target provider's context window. */ +export class ContextHandoffBudgetError extends Schema.TaggedError()( + "ContextHandoffBudgetError", + {}, +) { + override get message() { + return "Insufficient context allowance for the provider handoff. Compact the target conversation or use a larger-context model; the current request has not been truncated."; + } +} export const MAX_PROVIDER_FAILURE_MESSAGE_LENGTH = 4_096; export const MAX_PROVIDER_FAILURE_CODE_LENGTH = 128; diff --git a/apps/server/src/provider/ProviderInstanceEnvironment.test.ts b/packages/provider-core/src/server/instanceEnvironment.test.ts similarity index 96% rename from apps/server/src/provider/ProviderInstanceEnvironment.test.ts rename to packages/provider-core/src/server/instanceEnvironment.test.ts index 7d6bbe61a2aa758bae3c0a7f292728cb476ad23d..73d2ae3c313cca9ca13ec390c59c6cfe59d1b121 100644 --- a/apps/server/src/provider/ProviderInstanceEnvironment.test.ts +++ b/packages/provider-core/src/server/instanceEnvironment.test.ts @@ -5,7 +5,7 @@ import { describe, expect, it } from "@effect/vitest"; import * as Effect from "effect/Effect"; import * as Path from "effect/Path"; -import { mergeProviderInstanceEnvironment } from "./ProviderInstanceEnvironment.ts"; +import { mergeProviderInstanceEnvironment } from "./instanceEnvironment.ts"; describe("mergeProviderInstanceEnvironment", () => { it.effect.each([ diff --git a/apps/server/src/provider/ProviderInstanceEnvironment.ts b/packages/provider-core/src/server/instanceEnvironment.ts similarity index 92% rename from apps/server/src/provider/ProviderInstanceEnvironment.ts rename to packages/provider-core/src/server/instanceEnvironment.ts index 77c0c6c2dc888188b458f1c635fda16cfd808b87..ff8c9815731a202c81a3d2224a44c358cc69445d 100644 --- a/apps/server/src/provider/ProviderInstanceEnvironment.ts +++ b/packages/provider-core/src/server/instanceEnvironment.ts @@ -1,6 +1,6 @@ import type { ProviderInstanceEnvironment } from "@t3tools/contracts"; -import { expandHomePath } from "../pathExpansion.ts"; +import { expandHomePath } from "./pathExpansion.ts"; export function mergeProviderInstanceEnvironment( environment: ProviderInstanceEnvironment | undefined, diff --git a/packages/provider-core/src/server/maintenance.ts b/packages/provider-core/src/server/maintenance.ts new file mode 100644 index 0000000000000000000000000000000000000000..62f9a2ab63a61a76f70576871829f07a259476fd --- /dev/null +++ b/packages/provider-core/src/server/maintenance.ts @@ -0,0 +1,30 @@ +import type { ProviderDriverKind } from "@t3tools/contracts"; + +export interface ProviderMaintenanceCapabilities { + readonly provider: ProviderDriverKind; + readonly packageName: string | null; + readonly update: ProviderMaintenanceCommandAction | null; + /** + * Latest version reported by the installer that owns the executable. + * `undefined` means the installer has no channel of its own and the npm + * registry entry for `packageName` is authoritative; `null` means the + * installer was asked and did not know. + */ + readonly latestVersion?: string | null; + /** Compare native release revisions when the provider does not use plain semver. */ + readonly compareVersions?: (current: string, latest: string) => number; +} + +export interface ProviderMaintenanceCommandAction { + readonly command: string; + readonly executable: string; + readonly args: ReadonlyArray; + readonly lockKey: string; + /** + * Extra environment for the spawned updater, on top of the server's own. + * A native updater finds its install through the same variables the + * provider runs with (e.g. `CODEX_HOME`), so an instance with a custom home + * must update that home and not the default one. + */ + readonly env?: NodeJS.ProcessEnv; +} diff --git a/apps/server/src/provider/providerMaintenance.test.ts b/packages/provider-core/src/server/maintenanceResolver.test.ts similarity index 99% rename from apps/server/src/provider/providerMaintenance.test.ts rename to packages/provider-core/src/server/maintenanceResolver.test.ts index b4bf670375efac03c21984bd48958e46a240f23b..f93f35624c43d94affdad1caab34b6f846652494 100644 --- a/apps/server/src/provider/providerMaintenance.test.ts +++ b/packages/provider-core/src/server/maintenanceResolver.test.ts @@ -31,7 +31,7 @@ import { resolvePackageManagedProviderMaintenance, resolveProviderMaintenanceCapabilitiesEffect, type ProviderMaintenanceCapabilities, -} from "./providerMaintenance.ts"; +} from "./maintenanceResolver.ts"; import { symlinksSupported } from "@t3tools/shared/testing/symlinks"; const driver = (value: string) => ProviderDriverKind.make(value); diff --git a/apps/server/src/provider/providerMaintenance.ts b/packages/provider-core/src/server/maintenanceResolver.ts similarity index 96% rename from apps/server/src/provider/providerMaintenance.ts rename to packages/provider-core/src/server/maintenanceResolver.ts index 5dac5153a4f6ff7fedb9f931f31a8b12041f9fa8..65667281ac6a995aab46af9bdd81df7dc43f3da2 100644 --- a/apps/server/src/provider/providerMaintenance.ts +++ b/packages/provider-core/src/server/maintenanceResolver.ts @@ -1,3 +1,11 @@ +export type { + ProviderMaintenanceCapabilities, + ProviderMaintenanceCommandAction, +} from "@t3tools/provider-core/server/maintenance"; +import type { + ProviderMaintenanceCapabilities, + ProviderMaintenanceCommandAction, +} from "@t3tools/provider-core/server/maintenance"; import { ProviderDriverKind, type ServerProvider, @@ -21,7 +29,7 @@ import * as Stream from "effect/Stream"; import { HttpClient, HttpClientRequest } from "effect/http"; import { ChildProcess, ChildProcessSpawner } from "effect/process"; -import { collectUint8StreamText } from "../stream/collectUint8StreamText.ts"; +import { collectUint8StreamText } from "./collectStreamText.ts"; const LATEST_VERSION_CACHE_TTL_MS = 60 * 60 * 1_000; const LATEST_VERSION_TIMEOUT_MS = 4_000; @@ -56,35 +64,6 @@ const CommandLookupEnvConfig = Config.all({ const readCommandLookupEnv = CommandLookupEnvConfig.pipe(Effect.orElseSucceed(() => ({}))); -export interface ProviderMaintenanceCapabilities { - readonly provider: ProviderDriverKind; - readonly packageName: string | null; - readonly update: ProviderMaintenanceCommandAction | null; - /** - * Latest version reported by the installer that owns the executable. - * `undefined` means the installer has no channel of its own and the npm - * registry entry for `packageName` is authoritative; `null` means the - * installer was asked and did not know. - */ - readonly latestVersion?: string | null; - /** Compare native release revisions when the provider does not use plain semver. */ - readonly compareVersions?: (current: string, latest: string) => number; -} - -export interface ProviderMaintenanceCommandAction { - readonly command: string; - readonly executable: string; - readonly args: ReadonlyArray; - readonly lockKey: string; - /** - * Extra environment for the spawned updater, on top of the server's own. - * A native updater finds its install through the same variables the - * provider runs with (e.g. `CODEX_HOME`), so an instance with a custom home - * must update that home and not the default one. - */ - readonly env?: NodeJS.ProcessEnv; -} - /** Where the provider executable was found; every path is absolute. */ export interface ProviderMaintenanceResolutionContext { readonly binaryPath: string; diff --git a/apps/server/src/mcp/McpProviderSession.test.ts b/packages/provider-core/src/server/mcpSession.test.ts similarity index 94% rename from apps/server/src/mcp/McpProviderSession.test.ts rename to packages/provider-core/src/server/mcpSession.test.ts index 1c3c3af5091e565eb162e7caa7656afba3de18e1..eb69826d3dc39035479f012738a943dba483c1a7 100644 --- a/apps/server/src/mcp/McpProviderSession.test.ts +++ b/packages/provider-core/src/server/mcpSession.test.ts @@ -1,5 +1,5 @@ import { describe, expect, it } from "vite-plus/test"; -import { withAgentDeviceEnvironment } from "./McpProviderSession.ts"; +import { withAgentDeviceEnvironment } from "./mcpSession.ts"; describe("device CLI environment", () => { it("preserves provider credentials and commands while routing devices to the owned daemon", () => { diff --git a/apps/server/src/mcp/McpProviderSession.ts b/packages/provider-core/src/server/mcpSession.ts similarity index 100% rename from apps/server/src/mcp/McpProviderSession.ts rename to packages/provider-core/src/server/mcpSession.ts diff --git a/apps/server/src/provider/McpToolPresentation.test.ts b/packages/provider-core/src/server/mcpToolPresentation.test.ts similarity index 98% rename from apps/server/src/provider/McpToolPresentation.test.ts rename to packages/provider-core/src/server/mcpToolPresentation.test.ts index 5218d05ebeb8bc730bf3c43dd22a9680f630cc97..e53f0f37185f1159c7c98437d7231c9dc72e02cf 100644 --- a/apps/server/src/provider/McpToolPresentation.test.ts +++ b/packages/provider-core/src/server/mcpToolPresentation.test.ts @@ -1,5 +1,5 @@ import { describe, expect, it } from "@effect/vitest"; -import { mcpToolPresentation } from "./McpToolPresentation.ts"; +import { mcpToolPresentation } from "./mcpToolPresentation.ts"; describe("mcpToolPresentation", () => { it("uses supplied names and logos while retaining the server identity", () => { diff --git a/apps/server/src/provider/McpToolPresentation.ts b/packages/provider-core/src/server/mcpToolPresentation.ts similarity index 100% rename from apps/server/src/provider/McpToolPresentation.ts rename to packages/provider-core/src/server/mcpToolPresentation.ts diff --git a/apps/server/src/provider/T3OrchestrationInstructions.test.ts b/packages/provider-core/src/server/orchestrationInstructions.test.ts similarity index 98% rename from apps/server/src/provider/T3OrchestrationInstructions.test.ts rename to packages/provider-core/src/server/orchestrationInstructions.test.ts index e625e40c11255f84463c3a5a38aa3914914432b4..4dd04c8ee8cdde96e19392b0020e900c493ecdac 100644 --- a/apps/server/src/provider/T3OrchestrationInstructions.test.ts +++ b/packages/provider-core/src/server/orchestrationInstructions.test.ts @@ -5,7 +5,7 @@ import { t3AcpPromptWithInstructions, t3OrchestrationPromptForFirstRun, t3OrchestrationSystemPrompt, -} from "./T3OrchestrationInstructions.ts"; +} from "./orchestrationInstructions.ts"; describe("T3 orchestration provider instructions", () => { it("distinguishes delegated subagents from ordinary top-level threads", () => { diff --git a/apps/server/src/provider/T3OrchestrationInstructions.ts b/packages/provider-core/src/server/orchestrationInstructions.ts similarity index 100% rename from apps/server/src/provider/T3OrchestrationInstructions.ts rename to packages/provider-core/src/server/orchestrationInstructions.ts diff --git a/apps/server/src/pathExpansion.test.ts b/packages/provider-core/src/server/pathExpansion.test.ts similarity index 100% rename from apps/server/src/pathExpansion.test.ts rename to packages/provider-core/src/server/pathExpansion.test.ts diff --git a/apps/server/src/pathExpansion.ts b/packages/provider-core/src/server/pathExpansion.ts similarity index 100% rename from apps/server/src/pathExpansion.ts rename to packages/provider-core/src/server/pathExpansion.ts diff --git a/apps/server/src/process/processGroup.test.ts b/packages/provider-core/src/server/processGroup.test.ts similarity index 100% rename from apps/server/src/process/processGroup.test.ts rename to packages/provider-core/src/server/processGroup.test.ts diff --git a/apps/server/src/process/processGroup.ts b/packages/provider-core/src/server/processGroup.ts similarity index 100% rename from apps/server/src/process/processGroup.ts rename to packages/provider-core/src/server/processGroup.ts diff --git a/apps/server/src/orchestration-v2/RandomUuid.ts b/packages/provider-core/src/server/randomUuid.ts similarity index 100% rename from apps/server/src/orchestration-v2/RandomUuid.ts rename to packages/provider-core/src/server/randomUuid.ts diff --git a/apps/server/src/orchestration-v2/ProviderSelectionTransition.ts b/packages/provider-core/src/server/selectionTransition.ts similarity index 100% rename from apps/server/src/orchestration-v2/ProviderSelectionTransition.ts rename to packages/provider-core/src/server/selectionTransition.ts diff --git a/apps/server/src/provider/ServerProvider.ts b/packages/provider-core/src/server/snapshot.ts similarity index 92% rename from apps/server/src/provider/ServerProvider.ts rename to packages/provider-core/src/server/snapshot.ts index 77c16c14ee229cae75e02cc5ce80b76f1be4bf00..a6f2a985fd5786077159a1d08178b97f5899bc76 100644 --- a/apps/server/src/provider/ServerProvider.ts +++ b/packages/provider-core/src/server/snapshot.ts @@ -1,7 +1,7 @@ import type { ProviderUsageLimitsUpdate, ServerProvider } from "@t3tools/contracts"; import type * as Effect from "effect/Effect"; import type * as Stream from "effect/Stream"; -import type { ProviderMaintenanceCapabilities } from "./providerMaintenance.ts"; +import type { ProviderMaintenanceCapabilities } from "./maintenance.ts"; export interface ServerProviderShape { /** diff --git a/apps/server/src/provider/providerSnapshot.test.ts b/packages/provider-core/src/server/snapshotProbe.test.ts similarity index 99% rename from apps/server/src/provider/providerSnapshot.test.ts rename to packages/provider-core/src/server/snapshotProbe.test.ts index 32d8649d269960eade5376e1a3f43d93a3758bc2..d15e8744cc0c7a538055683f731d3b954db72ccc 100644 --- a/apps/server/src/provider/providerSnapshot.test.ts +++ b/packages/provider-core/src/server/snapshotProbe.test.ts @@ -14,7 +14,7 @@ import { parseGenericCliVersion, providerModelsFromSettings, spawnAndCollect, -} from "./providerSnapshot.ts"; +} from "./snapshotProbe.ts"; const OPENCODE_CUSTOM_MODEL_CAPABILITIES: ModelCapabilities = createModelCapabilities({ optionDescriptors: [ diff --git a/apps/server/src/provider/providerSnapshot.ts b/packages/provider-core/src/server/snapshotProbe.ts similarity index 89% rename from apps/server/src/provider/providerSnapshot.ts rename to packages/provider-core/src/server/snapshotProbe.ts index f180c5facb1c95a7489db8b55ba2e0da9fd536a3..b29abeed7cc2c4160960f2c530c12ef4960f5e6b 100644 --- a/apps/server/src/provider/providerSnapshot.ts +++ b/packages/provider-core/src/server/snapshotProbe.ts @@ -17,9 +17,30 @@ import * as Schema from "effect/Schema"; import * as Stream from "effect/Stream"; import { ChildProcess, ChildProcessSpawner } from "effect/process"; import { readCustomModelEntries } from "@t3tools/shared/model"; -import { isWindowsCommandNotFound } from "../processRunner.ts"; -import { createProviderVersionAdvisory } from "./providerMaintenance.ts"; -import { collectUint8StreamText } from "../stream/collectUint8StreamText.ts"; +import { HostProcessPlatform } from "@t3tools/shared/hostProcess"; +import { createProviderVersionAdvisory } from "./maintenanceResolver.ts"; +import { collectUint8StreamText } from "./collectStreamText.ts"; + +// Localized cmd.exe "not recognized" messages for a missing executable. +const WINDOWS_COMMAND_NOT_FOUND_PATTERNS = [ + /is not recognized as an internal or external command/i, + /n.o . reconhecido como um comando interno/i, + /non . riconosciuto come comando interno o esterno/i, + /n.est pas reconnu en tant que commande interne/i, + /no se reconoce como un comando interno o externo/i, + /wird nicht als interner oder externer befehl/i, +] as const; + +/** Whether a Windows exit means the command was not found rather than that it failed. */ +export const isWindowsCommandNotFound = Effect.fn("isWindowsCommandNotFound")(function* ( + code: number | null, + stderr: string, +) { + const platform = yield* HostProcessPlatform; + if (platform !== "win32") return false; + if (code === 9009) return true; + return WINDOWS_COMMAND_NOT_FOUND_PATTERNS.some((pattern) => pattern.test(stderr)); +}); export const DEFAULT_TIMEOUT_MS = 4_000; // Auth status checks involve disk/network lookups and can be slow on first run (especially Windows) diff --git a/packages/provider-core/src/server/textGeneration.ts b/packages/provider-core/src/server/textGeneration.ts new file mode 100644 index 0000000000000000000000000000000000000000..95039c2d17ff3ddf543c23b7058a813cf143bbe1 --- /dev/null +++ b/packages/provider-core/src/server/textGeneration.ts @@ -0,0 +1,104 @@ +import type { + BranchNamingOptions, + ChatAttachment, + ModelSelection, + TextGenerationError, +} from "@t3tools/contracts"; +import type * as Effect from "effect/Effect"; + +import type { TextGenerationPolicy } from "./textGenerationPolicy.ts"; + +export interface CommitMessageGenerationInput { + cwd: string; + branch: string | null; + stagedSummary: string; + stagedPatch: string; + /** When true, the model also returns a semantic branch name for the change. */ + includeBranch?: boolean; + policy?: TextGenerationPolicy | undefined; + /** What model and provider to use for generation. */ + modelSelection: ModelSelection; +} + +export interface CommitMessageGenerationResult { + subject: string; + body: string; + /** Only present when `includeBranch` was set on the input. */ + branch?: string | undefined; +} + +export interface PrContentGenerationInput { + cwd: string; + baseBranch: string; + headBranch: string; + commitSummary: string; + diffSummary: string; + diffPatch: string; + changeRequestTemplate?: string | undefined; + policy?: TextGenerationPolicy | undefined; + /** What model and provider to use for generation. */ + modelSelection: ModelSelection; +} + +export interface PrContentGenerationResult { + title: string; + body: string; +} + +export interface BranchNameGenerationInput { + naming?: BranchNamingOptions | undefined; + cwd: string; + message: string; + attachments?: ReadonlyArray | undefined; + /** What model and provider to use for generation. */ + modelSelection: ModelSelection; +} + +export interface BranchNameGenerationResult { + branch: string; +} + +export interface ThreadTitleGenerationInput { + linkedContext?: string | undefined; + cwd: string; + message: string; + /** Present when replacing an existing title from the current thread history. */ + previousTitle?: string | undefined; + attachments?: ReadonlyArray | undefined; + /** What model and provider to use for generation. */ + modelSelection: ModelSelection; +} + +export interface ThreadTitleGenerationResult { + title: string; + needsRefinement?: boolean | undefined; +} + +/** Commit, change request, branch, and title generation backed by one provider instance. */ +export interface ProviderTextGeneration { + /** + * Generate a commit message from staged change context. + */ + readonly generateCommitMessage: ( + input: CommitMessageGenerationInput, + ) => Effect.Effect; + + /** + * Generate change request title/body from branch and diff context. + */ + readonly generatePrContent: ( + input: PrContentGenerationInput, + ) => Effect.Effect; + + /** + * Generate a concise branch name from a user message. + */ + readonly generateBranchName: ( + input: BranchNameGenerationInput, + ) => Effect.Effect; + + /** Generate a concise thread title from a first message or thread history. */ + readonly generateThreadTitle: ( + input: ThreadTitleGenerationInput, + ) => Effect.Effect; +} diff --git a/packages/provider-core/src/server/textGenerationOperations.ts b/packages/provider-core/src/server/textGenerationOperations.ts new file mode 100644 index 0000000000000000000000000000000000000000..723095f3e95aeeeb521e08631965825551dab0f3 --- /dev/null +++ b/packages/provider-core/src/server/textGenerationOperations.ts @@ -0,0 +1,157 @@ +/** + * The text generation operations every provider shares. A provider supplies a + * runner that sends one prompt and decodes the reply; prompts, linked source + * control context, and output sanitizing live here so providers cannot drift + * on them. + * + * @module textGeneration/TextGenerationOperations + */ +import * as Effect from "effect/Effect"; +import * as Schema from "effect/Schema"; + +import { type ChatAttachment, type ModelSelection, TextGenerationError } from "@t3tools/contracts"; +import { formatGeneratedBranchName, sanitizeFeatureBranchName } from "@t3tools/shared/git"; +import { extractJsonObject } from "@t3tools/shared/schemaJson"; + +import type { ProviderTextGeneration } from "./textGeneration.ts"; +import { + buildBranchNamePrompt, + buildCommitMessagePrompt, + buildPrContentPrompt, + buildThreadTitlePrompt, +} from "./textGenerationPrompts.ts"; +import { + sanitizeCommitSubject, + sanitizePrTitle, + sanitizeThreadTitle, +} from "./textGenerationUtils.ts"; + +export type Operation = keyof ProviderTextGeneration; + +/** One prompt for a provider to run. */ +export interface Request { + readonly operation: Operation; + readonly cwd: string; + readonly prompt: string; + readonly outputSchema: S; + readonly modelSelection: ModelSelection; + /** The user's attachments, already listed in the prompt. Providers that accept images send them. */ + readonly attachments?: ReadonlyArray | undefined; +} + +/** Runs one request and decodes the reply as its `outputSchema`. */ +export type Runner = ( + request: Request, +) => Effect.Effect; + +/** Decodes the JSON object in a text reply, which models often wrap in prose. */ +export const decodeJsonReply = ( + request: Pick, "operation" | "outputSchema">, + provider: string, + text: string, +) => { + // Each request builds its own output schema, so the decoder cannot be hoisted. + const decodeOutput = Schema.decodeEffect(Schema.fromJsonString(request.outputSchema)); + return decodeOutput(extractJsonObject(text)).pipe( + Effect.mapError( + (cause) => + new TextGenerationError({ + operation: request.operation, + detail: `${provider} returned invalid structured output.`, + cause, + }), + ), + ); +}; + +/** The text generation service over `run`. `name` prefixes each operation's span. */ +export function fromRunner(name: string, run: Runner): ProviderTextGeneration { + const generateCommitMessage: ProviderTextGeneration["generateCommitMessage"] = Effect.fn( + `${name}.generateCommitMessage`, + )(function* (input) { + const generated = yield* run({ + operation: "generateCommitMessage", + cwd: input.cwd, + modelSelection: input.modelSelection, + ...buildCommitMessagePrompt({ + branch: input.branch, + stagedSummary: input.stagedSummary, + stagedPatch: input.stagedPatch, + includeBranch: input.includeBranch === true, + policy: input.policy, + }), + }); + return { + subject: sanitizeCommitSubject(generated.subject), + body: generated.body.trim(), + ...("branch" in generated && typeof generated.branch === "string" + ? { branch: sanitizeFeatureBranchName(generated.branch) } + : {}), + }; + }); + + const generatePrContent: ProviderTextGeneration["generatePrContent"] = Effect.fn( + `${name}.generatePrContent`, + )(function* (input) { + const generated = yield* run({ + operation: "generatePrContent", + cwd: input.cwd, + modelSelection: input.modelSelection, + ...buildPrContentPrompt({ + baseBranch: input.baseBranch, + headBranch: input.headBranch, + commitSummary: input.commitSummary, + diffSummary: input.diffSummary, + diffPatch: input.diffPatch, + policy: input.policy, + changeRequestTemplate: input.changeRequestTemplate, + }), + }); + return { title: sanitizePrTitle(generated.title), body: generated.body.trim() }; + }); + + const generateBranchName: ProviderTextGeneration["generateBranchName"] = Effect.fn( + `${name}.generateBranchName`, + )(function* (input) { + const generated = yield* run({ + operation: "generateBranchName", + cwd: input.cwd, + modelSelection: input.modelSelection, + attachments: input.attachments, + ...buildBranchNamePrompt({ + message: input.message, + attachments: input.attachments, + naming: input.naming, + }), + }); + return { branch: formatGeneratedBranchName(generated.branch, input.naming) }; + }); + + const generateThreadTitle: ProviderTextGeneration["generateThreadTitle"] = Effect.fn( + `${name}.generateThreadTitle`, + )(function* (input) { + const generated = yield* run({ + operation: "generateThreadTitle", + cwd: input.cwd, + modelSelection: input.modelSelection, + attachments: input.attachments, + ...buildThreadTitlePrompt({ + message: input.message, + previousTitle: input.previousTitle, + linkedContext: input.linkedContext, + attachments: input.attachments, + }), + }); + return { + title: sanitizeThreadTitle(generated.title), + ...(generated.needsRefinement ? { needsRefinement: true } : {}), + }; + }); + + return { + generateCommitMessage, + generatePrContent, + generateBranchName, + generateThreadTitle, + } satisfies ProviderTextGeneration; +} diff --git a/apps/server/src/textGeneration/TextGenerationPolicy.ts b/packages/provider-core/src/server/textGenerationPolicy.ts similarity index 100% rename from apps/server/src/textGeneration/TextGenerationPolicy.ts rename to packages/provider-core/src/server/textGenerationPolicy.ts diff --git a/apps/server/src/textGeneration/TextGenerationPrompts.test.ts b/packages/provider-core/src/server/textGenerationPrompts.test.ts similarity index 99% rename from apps/server/src/textGeneration/TextGenerationPrompts.test.ts rename to packages/provider-core/src/server/textGenerationPrompts.test.ts index fada659aded1778c252357a1657ec5c56f0d6579..d4446502a915185cf05c65c11235fbcae6386026 100644 --- a/apps/server/src/textGeneration/TextGenerationPrompts.test.ts +++ b/packages/provider-core/src/server/textGenerationPrompts.test.ts @@ -5,12 +5,12 @@ import { buildCommitMessagePrompt, buildPrContentPrompt, buildThreadTitlePrompt, -} from "./TextGenerationPrompts.ts"; +} from "./textGenerationPrompts.ts"; import { normalizeCliError, sanitizeThreadTitle, toJsonSchemaObject, -} from "./TextGenerationUtils.ts"; +} from "./textGenerationUtils.ts"; import { TextGenerationError } from "@t3tools/contracts"; describe("buildCommitMessagePrompt", () => { diff --git a/apps/server/src/textGeneration/TextGenerationPrompts.ts b/packages/provider-core/src/server/textGenerationPrompts.ts similarity index 98% rename from apps/server/src/textGeneration/TextGenerationPrompts.ts rename to packages/provider-core/src/server/textGenerationPrompts.ts index 2366361210957aa9e980621c4b5d00f9c39ebf49..aaf19aeb6ee274ba8ad36cff7b05c6de7ad1e64e 100644 --- a/apps/server/src/textGeneration/TextGenerationPrompts.ts +++ b/packages/provider-core/src/server/textGenerationPrompts.ts @@ -8,11 +8,11 @@ */ import * as Schema from "effect/Schema"; import * as Effect from "effect/Effect"; -import { limitTitleMessage } from "./ThreadTitleContext.ts"; +import { limitTitleMessage } from "./threadTitleContext.ts"; import type { BranchNamingOptions, ChatAttachment } from "@t3tools/contracts"; -import { limitSection } from "./TextGenerationUtils.ts"; -import type { TextGenerationPolicy } from "./TextGenerationPolicy.ts"; +import { limitSection } from "./textGenerationUtils.ts"; +import type { TextGenerationPolicy } from "@t3tools/provider-core/server/textGenerationPolicy"; const EARLIER_CONTENT_TRUNCATION_MARKER = "[Earlier content truncated]\n\n"; diff --git a/apps/server/src/textGeneration/TextGenerationUtils.ts b/packages/provider-core/src/server/textGenerationUtils.ts similarity index 100% rename from apps/server/src/textGeneration/TextGenerationUtils.ts rename to packages/provider-core/src/server/textGenerationUtils.ts diff --git a/apps/server/src/textGeneration/ThreadTitleContext.test.ts b/packages/provider-core/src/server/threadTitleContext.test.ts similarity index 97% rename from apps/server/src/textGeneration/ThreadTitleContext.test.ts rename to packages/provider-core/src/server/threadTitleContext.test.ts index 14b9de23ab90c52f557c3343c5e31fa8ff38b42f..99debc552eabf6e45a97a303fad08c5aa38f459e 100644 --- a/apps/server/src/textGeneration/ThreadTitleContext.test.ts +++ b/packages/provider-core/src/server/threadTitleContext.test.ts @@ -1,5 +1,5 @@ import { describe, expect, it } from "vite-plus/test"; -import { formatThreadTitleContext, limitTitleMessage } from "./ThreadTitleContext.ts"; +import { formatThreadTitleContext, limitTitleMessage } from "./threadTitleContext.ts"; describe("thread title context", () => { it("keeps a user's scope change despite long assistant output", () => { diff --git a/apps/server/src/textGeneration/ThreadTitleContext.ts b/packages/provider-core/src/server/threadTitleContext.ts similarity index 100% rename from apps/server/src/textGeneration/ThreadTitleContext.ts rename to packages/provider-core/src/server/threadTitleContext.ts diff --git a/apps/server/src/provider/providerUsageLimits.test.ts b/packages/provider-core/src/server/usageLimits.test.ts similarity index 98% rename from apps/server/src/provider/providerUsageLimits.test.ts rename to packages/provider-core/src/server/usageLimits.test.ts index 6e288ddd3a36bbe781de13807a735fd65ad89880..9b305a74b98eb52e3a028fe3b81bd1dd0b7e010f 100644 --- a/apps/server/src/provider/providerUsageLimits.test.ts +++ b/packages/provider-core/src/server/usageLimits.test.ts @@ -1,6 +1,6 @@ import { describe, expect, it } from "vite-plus/test"; -import { applyUsageLimitsUpdate, resolveUsageLimitsAfterProbe } from "./providerUsageLimits.ts"; +import { applyUsageLimitsUpdate, resolveUsageLimitsAfterProbe } from "./usageLimits.ts"; const checkedAt = "2026-09-03T12:00:00.000Z"; const session = { diff --git a/apps/server/src/provider/providerUsageLimits.ts b/packages/provider-core/src/server/usageLimits.ts similarity index 100% rename from apps/server/src/provider/providerUsageLimits.ts rename to packages/provider-core/src/server/usageLimits.ts diff --git a/packages/provider-core/tsconfig.json b/packages/provider-core/tsconfig.json new file mode 100644 index 0000000000000000000000000000000000000000..374bac55202ddcad695ede1c567ec219a61e9c48 --- /dev/null +++ b/packages/provider-core/tsconfig.json @@ -0,0 +1,7 @@ +{ + "extends": "../../tsconfig.base.json", + "compilerOptions": { + "types": ["node"] + }, + "include": ["src"] +} diff --git a/packages/provider-testing/package.json b/packages/provider-testing/package.json new file mode 100644 index 0000000000000000000000000000000000000000..35e3941ba87d70c7a70727a64ae577e958cb92f7 --- /dev/null +++ b/packages/provider-testing/package.json @@ -0,0 +1,38 @@ +{ + "name": "@t3tools/provider-testing", + "private": true, + "type": "module", + "exports": { + "./replayTranscript": { + "types": "./src/replayTranscript.ts", + "import": "./src/replayTranscript.ts" + }, + "./replayGate": { + "types": "./src/replayGate.ts", + "import": "./src/replayGate.ts" + }, + "./replayWorkspace": { + "types": "./src/replayWorkspace.ts", + "import": "./src/replayWorkspace.ts" + }, + "./host": { + "types": "./src/host.ts", + "import": "./src/host.ts" + } + }, + "scripts": { + "typecheck": "tsc --noEmit", + "test": "vp test run --config ../../vite.config.ts --dir ." + }, + "dependencies": { + "@effect/platform-node": "catalog:", + "@t3tools/contracts": "workspace:*", + "@t3tools/provider-core": "workspace:*", + "effect": "catalog:" + }, + "devDependencies": { + "@effect/vitest": "catalog:", + "@types/node": "catalog:", + "vite-plus": "catalog:" + } +} diff --git a/packages/provider-testing/src/host.ts b/packages/provider-testing/src/host.ts new file mode 100644 index 0000000000000000000000000000000000000000..1b3e74922eb57c835dae063548b1ba6468f12e2e --- /dev/null +++ b/packages/provider-testing/src/host.ts @@ -0,0 +1,54 @@ +/** + * A `ProviderHost` for driver and adapter tests. Its directories live in a + * scoped temp directory, settings are fixed, and background work always runs + * unless the test says otherwise. + * + * @module provider-testing/host + */ +import { DEFAULT_SERVER_SETTINGS, type ServerSettings } from "@t3tools/contracts"; +import { ProviderHost } from "@t3tools/provider-core/server/ProviderHost"; +import * as Effect from "effect/Effect"; +import * as FileSystem from "effect/FileSystem"; +import * as Layer from "effect/Layer"; +import * as Path from "effect/Path"; +import * as Stream from "effect/Stream"; + +export interface TestProviderHostOptions { + /** Session fallback cwd. Defaults to the test process cwd. */ + readonly cwd?: string; + readonly settings?: ServerSettings; + /** Whether background work such as status probes may run. Defaults to `true`. */ + readonly runBackgroundWork?: boolean; +} + +export const layerTestProviderHost = ( + options: TestProviderHostOptions = {}, +): Layer.Layer => + Layer.effect( + ProviderHost, + Effect.gen(function* () { + const fileSystem = yield* FileSystem.FileSystem; + const path = yield* Path.Path; + const baseDir = yield* fileSystem + .makeTempDirectoryScoped({ prefix: "t3-provider-host-" }) + .pipe(Effect.orDie); + const stateDir = path.join(baseDir, "userdata"); + const providerStatusCacheDir = path.join(baseDir, "caches"); + const attachmentsDir = path.join(stateDir, "attachments"); + for (const directory of [stateDir, providerStatusCacheDir, attachmentsDir]) { + yield* fileSystem.makeDirectory(directory, { recursive: true }).pipe(Effect.orDie); + } + const settings = options.settings ?? DEFAULT_SERVER_SETTINGS; + return ProviderHost.of({ + paths: { cwd: options.cwd ?? process.cwd(), baseDir, stateDir, providerStatusCacheDir }, + settings: { + get: Effect.succeed(settings), + changes: Stream.empty, + subscribe: Effect.succeed(Stream.empty), + }, + shouldRunBackgroundWork: () => Effect.succeed(options.runBackgroundWork ?? true), + // Tests store attachments flat under the attachments directory by id. + resolveAttachmentPath: (attachment) => path.join(attachmentsDir, attachment.id), + }); + }), + ); diff --git a/packages/provider-testing/src/replayGate.test.ts b/packages/provider-testing/src/replayGate.test.ts new file mode 100644 index 0000000000000000000000000000000000000000..72382ab823d47390c0598718b2be6886e53dd729 --- /dev/null +++ b/packages/provider-testing/src/replayGate.test.ts @@ -0,0 +1,38 @@ +import { describe, expect, it } from "vite-plus/test"; + +import { makeProviderReplayGate } from "./replayGate.ts"; + +describe("makeProviderReplayGate", () => { + it("holds a gated emit until its label is released", async () => { + const gate = makeProviderReplayGate(["approval"]); + let emitted = false; + const emit = gate.beforeEmit("approval").then(() => { + emitted = true; + }); + + expect(await gate.waitForReached("approval")).toBe(true); + expect(emitted).toBe(false); + expect(gate.release("approval")).toBe(true); + await emit; + expect(emitted).toBe(true); + expect(gate.release("approval")).toBe(false); + }); + + it("passes ungated labels through and stops waiting when the emit is aborted", async () => { + const gate = makeProviderReplayGate(["approval"]); + await gate.beforeEmit(undefined); + await gate.beforeEmit("other"); + + const controller = new AbortController(); + const emit = gate.beforeEmit("approval", controller.signal); + controller.abort(); + await emit; + expect(gate.hasReached("approval")).toBe(true); + }); + + it("rejects duplicate labels", () => { + expect(() => makeProviderReplayGate(["approval", "approval"])).toThrow( + "Duplicate provider replay gate label approval.", + ); + }); +}); diff --git a/apps/server/src/orchestration-v2/testkit/ProviderReplayGate.testkit.ts b/packages/provider-testing/src/replayGate.ts similarity index 100% rename from apps/server/src/orchestration-v2/testkit/ProviderReplayGate.testkit.ts rename to packages/provider-testing/src/replayGate.ts diff --git a/packages/provider-testing/src/replayTranscript.test.ts b/packages/provider-testing/src/replayTranscript.test.ts new file mode 100644 index 0000000000000000000000000000000000000000..fc5fe57adaf20925249f0db64b1c7c7a10866eca --- /dev/null +++ b/packages/provider-testing/src/replayTranscript.test.ts @@ -0,0 +1,96 @@ +import { assert, describe, it } from "@effect/vitest"; +import * as Effect from "effect/Effect"; + +import { + decodeProviderReplayNdjson, + materializeReplayTranscriptWorkspace, +} from "./replayTranscript.ts"; + +const header = JSON.stringify({ + type: "transcript_start", + provider: "codex", + protocol: "codex.app-server", + version: "0.156.1", + scenario: "simple", +}); + +describe("decodeProviderReplayNdjson", () => { + it.effect("reads the header and entries, skipping blank lines", () => + Effect.gen(function* () { + const transcript = yield* decodeProviderReplayNdjson( + [ + header, + "", + JSON.stringify({ type: "expect_outbound", frame: { method: "initialize" } }), + JSON.stringify({ type: "emit_inbound", frame: { result: {} } }), + ].join("\n"), + ); + + assert.strictEqual(transcript.provider, "codex"); + assert.strictEqual(transcript.scenario, "simple"); + assert.deepStrictEqual( + transcript.entries.map((entry) => entry.type), + ["expect_outbound", "emit_inbound"], + ); + }), + ); + + it.effect("rejects a second transcript_start record", () => + Effect.gen(function* () { + const error = yield* Effect.flip(decodeProviderReplayNdjson([header, header].join("\n"))); + + assert.strictEqual(error._tag, "ProviderReplayNdjsonLineParseError"); + assert.strictEqual( + error._tag === "ProviderReplayNdjsonLineParseError" && error.lineNumber, + 2, + ); + }), + ); + + it.effect("requires a header unless fallback metadata is given", () => + Effect.gen(function* () { + const entry = JSON.stringify({ type: "emit_inbound", frame: {} }); + + const error = yield* Effect.flip(decodeProviderReplayNdjson(entry)); + assert.strictEqual(error._tag, "ProviderReplayNdjsonMissingHeaderError"); + + const transcript = yield* decodeProviderReplayNdjson(entry, { + provider: "pi", + protocol: "pi.rpc-jsonl", + version: "1", + scenario: "fallback", + }); + assert.strictEqual(transcript.entries.length, 1); + }), + ); +}); + +describe("materializeReplayTranscriptWorkspace", () => { + it("replaces workspace placeholders in outbound frames only", () => { + const transcript = materializeReplayTranscriptWorkspace( + { + provider: "codex", + protocol: "codex.app-server", + version: "0.156.1", + scenario: "simple", + entries: [ + { + type: "expect_outbound", + frame: { params: { cwd: "", argv: [""] } }, + }, + { type: "emit_inbound", frame: { cwd: "" } }, + ], + }, + "/tmp/fixture", + ); + + assert.deepStrictEqual(transcript.entries[0], { + type: "expect_outbound", + frame: { params: { cwd: "/tmp/fixture", argv: ["/tmp/fixture"] } }, + }); + assert.deepStrictEqual(transcript.entries[1], { + type: "emit_inbound", + frame: { cwd: "" }, + }); + }); +}); diff --git a/apps/server/src/orchestration-v2/testkit/ReplayTranscriptNdjson.ts b/packages/provider-testing/src/replayTranscript.ts similarity index 70% rename from apps/server/src/orchestration-v2/testkit/ReplayTranscriptNdjson.ts rename to packages/provider-testing/src/replayTranscript.ts index 1b62ca0f126ec675f2737977a66a12d98f088473..67bd754f5d2d24f92a15cc27f19b4a63dd0eb403 100644 --- a/apps/server/src/orchestration-v2/testkit/ReplayTranscriptNdjson.ts +++ b/packages/provider-testing/src/replayTranscript.ts @@ -2,7 +2,6 @@ import { ProviderReplayEntry, ProviderReplayNdjsonRecord, ProviderReplayTranscript, - type ProviderDriverKind, type ProviderReplayTranscriptHeader, } from "@t3tools/contracts"; import * as Effect from "effect/Effect"; @@ -10,8 +9,6 @@ import * as FileSystem from "effect/FileSystem"; import * as Path from "effect/Path"; import * as Schema from "effect/Schema"; -import { buildRuntimeInstructions } from "../../provider/RuntimeInstructions.ts"; - export class ProviderReplayNdjsonLineParseError extends Schema.TaggedError()( "ProviderReplayNdjsonLineParseError", { @@ -93,73 +90,6 @@ export function materializeReplayTranscriptWorkspace( }; } -/** Adds current runtime context to legacy prompt expectations, keeping outbound matching exact. */ -export function materializeReplayTranscriptRuntimeInstructions( - transcript: ProviderReplayTranscript, - runtime: { readonly driver: ProviderDriverKind; readonly model: string }, -): ProviderReplayTranscript { - const harness = - runtime.driver === "cursor" - ? "Cursor" - : runtime.driver === "grok" - ? "Grok" - : runtime.driver === "acpRegistry" - ? "acpRegistry" - : undefined; - if (harness === undefined) return transcript; - const instructions = buildRuntimeInstructions({ harness, model: runtime.model }); - - return { - ...transcript, - entries: transcript.entries.map((entry) => { - if (entry.type !== "expect_outbound") return entry; - const frame = entry.frame; - if (typeof frame !== "object" || frame === null) return entry; - if ( - runtime.driver === "cursor" && - "type" in frame && - frame.type === "run.start" && - "message" in frame && - typeof frame.message === "string" - ) { - return frame.message.endsWith(instructions) - ? entry - : { ...entry, frame: { ...frame, message: `${frame.message}\n\n${instructions}` } }; - } - if ( - "method" in frame && - frame.method === "session/prompt" && - "params" in frame && - typeof frame.params === "object" && - frame.params !== null && - "prompt" in frame.params && - Array.isArray(frame.params.prompt) - ) { - const prompt: ReadonlyArray = frame.params.prompt; - const lastPart = prompt.at(-1); - if ( - typeof lastPart === "object" && - lastPart !== null && - "type" in lastPart && - lastPart.type === "text" && - "text" in lastPart && - lastPart.text === instructions - ) { - return entry; - } - return { - ...entry, - frame: { - ...frame, - params: { ...frame.params, prompt: [...prompt, { type: "text", text: instructions }] }, - }, - }; - } - return entry; - }), - }; -} - const decodeReplayRecord = Schema.decodeUnknownSync( Schema.fromJsonString(ProviderReplayNdjsonRecord), ); diff --git a/apps/server/src/orchestration-v2/testkit/ReplayFixtureWorkspace.ts b/packages/provider-testing/src/replayWorkspace.ts similarity index 100% rename from apps/server/src/orchestration-v2/testkit/ReplayFixtureWorkspace.ts rename to packages/provider-testing/src/replayWorkspace.ts diff --git a/packages/provider-testing/tsconfig.json b/packages/provider-testing/tsconfig.json new file mode 100644 index 0000000000000000000000000000000000000000..374bac55202ddcad695ede1c567ec219a61e9c48 --- /dev/null +++ b/packages/provider-testing/tsconfig.json @@ -0,0 +1,7 @@ +{ + "extends": "../../tsconfig.base.json", + "compilerOptions": { + "types": ["node"] + }, + "include": ["src"] +} diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index eed53ec3b6556dbe8c3e35bba708adc2e8a5c3c4..a3da3784edd8443670dbb24d7a2126a5fd59c689 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -594,6 +594,9 @@ importers: '@opencode/schema': specifier: 2.0.23 version: 2.0.23(patch_hash=650f1b8602789407c010861284272dcb6bd6de01ec6a75bf3c0904a0e7596d59) + '@t3tools/provider-core': + specifier: workspace:* + version: link:../../packages/provider-core diff: specifier: 8.0.3 version: 8.0.3 @@ -634,6 +637,9 @@ importers: '@t3tools/contracts': specifier: workspace:* version: link:../../packages/contracts + '@t3tools/provider-testing': + specifier: workspace:* + version: link:../../packages/provider-testing '@t3tools/shared': specifier: workspace:* version: link:../../packages/shared @@ -715,6 +721,9 @@ importers: '@t3tools/contracts': specifier: workspace:* version: link:../../packages/contracts + '@t3tools/provider-core': + specifier: workspace:* + version: link:../../packages/provider-core '@t3tools/shared': specifier: workspace:* version: link:../../packages/shared @@ -1053,6 +1062,56 @@ importers: specifier: 1.0.0 version: 1.0.0(@types/node@24.12.4)(@vitest/ui@5.0.1(vitest@5.0.1))(bufferutil@4.1.0)(esbuild@0.28.2)(jiti@2.7.0)(jsdom@30.1.0(@noble/hashes@1.8.0))(msw@2.12.11(@types/node@24.12.4)(typescript@7.0.2))(terser@5.48.0)(typescript@7.0.2)(unrun@0.2.39)(utf-8-validate@6.0.6)(yaml@2.9.0) + packages/provider-core: + dependencies: + '@t3tools/contracts': + specifier: workspace:* + version: link:../contracts + '@t3tools/shared': + specifier: workspace:* + version: link:../shared + effect: + specifier: 4.0.1 + version: 4.0.1(patch_hash=a33cba07c41f32374c2aaa86ea4a84d3ab9a872a78c94b65e929b19f8361856f) + devDependencies: + '@effect/platform-node': + specifier: 4.0.1 + version: 4.0.1(bufferutil@4.1.0)(effect@4.0.1(patch_hash=a33cba07c41f32374c2aaa86ea4a84d3ab9a872a78c94b65e929b19f8361856f))(redis@6.2.1)(utf-8-validate@6.0.6) + '@effect/vitest': + specifier: 4.0.1 + version: 4.0.1(patch_hash=359f6fb2f7b3ec145bb72208edb9034f02489791aa2491a55cdbd69bd56ee0d2)(@types/node@24.12.4)(@vitest/ui@5.0.1)(bufferutil@4.1.0)(effect@4.0.1(patch_hash=a33cba07c41f32374c2aaa86ea4a84d3ab9a872a78c94b65e929b19f8361856f))(esbuild@0.28.2)(jiti@2.7.0)(jsdom@30.1.0(@noble/hashes@1.8.0))(msw@2.12.11(@types/node@24.12.4)(typescript@7.0.2))(terser@5.48.0)(typescript@7.0.2)(unrun@0.2.39)(utf-8-validate@6.0.6)(yaml@2.9.0) + '@types/node': + specifier: 24.12.4 + version: 24.12.4 + vite-plus: + specifier: 1.0.0 + version: 1.0.0(@types/node@24.12.4)(@vitest/ui@5.0.1(vitest@5.0.1))(bufferutil@4.1.0)(esbuild@0.28.2)(jiti@2.7.0)(jsdom@30.1.0(@noble/hashes@1.8.0))(msw@2.12.11(@types/node@24.12.4)(typescript@7.0.2))(terser@5.48.0)(typescript@7.0.2)(unrun@0.2.39)(utf-8-validate@6.0.6)(yaml@2.9.0) + + packages/provider-testing: + dependencies: + '@effect/platform-node': + specifier: 4.0.1 + version: 4.0.1(bufferutil@4.1.0)(effect@4.0.1(patch_hash=a33cba07c41f32374c2aaa86ea4a84d3ab9a872a78c94b65e929b19f8361856f))(redis@6.2.1)(utf-8-validate@6.0.6) + '@t3tools/contracts': + specifier: workspace:* + version: link:../contracts + '@t3tools/provider-core': + specifier: workspace:* + version: link:../provider-core + effect: + specifier: 4.0.1 + version: 4.0.1(patch_hash=a33cba07c41f32374c2aaa86ea4a84d3ab9a872a78c94b65e929b19f8361856f) + devDependencies: + '@effect/vitest': + specifier: 4.0.1 + version: 4.0.1(patch_hash=359f6fb2f7b3ec145bb72208edb9034f02489791aa2491a55cdbd69bd56ee0d2)(@types/node@24.12.4)(@vitest/ui@5.0.1)(bufferutil@4.1.0)(effect@4.0.1(patch_hash=a33cba07c41f32374c2aaa86ea4a84d3ab9a872a78c94b65e929b19f8361856f))(esbuild@0.28.2)(jiti@2.7.0)(jsdom@30.1.0(@noble/hashes@1.8.0))(msw@2.12.11(@types/node@24.12.4)(typescript@7.0.2))(terser@5.48.0)(typescript@7.0.2)(unrun@0.2.39)(utf-8-validate@6.0.6)(yaml@2.9.0) + '@types/node': + specifier: 24.12.4 + version: 24.12.4 + vite-plus: + specifier: 1.0.0 + version: 1.0.0(@types/node@24.12.4)(@vitest/ui@5.0.1(vitest@5.0.1))(bufferutil@4.1.0)(esbuild@0.28.2)(jiti@2.7.0)(jsdom@30.1.0(@noble/hashes@1.8.0))(msw@2.12.11(@types/node@24.12.4)(typescript@7.0.2))(terser@5.48.0)(typescript@7.0.2)(unrun@0.2.39)(utf-8-validate@6.0.6)(yaml@2.9.0) + packages/shared: dependencies: '@noble/curves': diff --git a/scripts/release-smoke.ts b/scripts/release-smoke.ts index 963232dbbbd2fa01666cb6f044cd645062e289ab..296b3ac1441ff12623743d598581f08807a68de5 100644 --- a/scripts/release-smoke.ts +++ b/scripts/release-smoke.ts @@ -28,6 +28,8 @@ const workspaceFiles = [ "packages/shared/package.json", "packages/ssh/package.json", "packages/tailscale/package.json", + "packages/provider-core/package.json", + "packages/provider-testing/package.json", "packages/effect-acp/package.json", "packages/effect-codex-app-server/package.json", "scripts/package.json", -- 2.54.0