@db3.ai/app 0.1.0-beta.1 → 0.1.0-beta.4
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +68 -9
- package/agent-instructions.md +76 -0
- package/dist/ai/AIErrors.d.ts +7 -1
- package/dist/ai/AIErrors.js +8 -1
- package/dist/ai/AIFailover.d.ts +10 -0
- package/dist/ai/AIFailover.js +3 -2
- package/dist/ai/AIProviderAdmission.d.ts +101 -0
- package/dist/ai/AIProviderAdmission.js +336 -0
- package/dist/ai/AIRateLimiter.d.ts +11 -2
- package/dist/ai/AIRateLimiter.js +125 -10
- package/dist/ai/AIRequestTrackingError.d.ts +22 -0
- package/dist/ai/AIRequestTrackingError.js +33 -0
- package/dist/ai/Agent.d.ts +7 -7
- package/dist/ai/Agent.js +84 -56
- package/dist/ai/Ai.d.ts +11 -3
- package/dist/ai/Ai.js +94 -44
- package/dist/ai/OpenAIProviderError.js +1 -1
- package/dist/ai/ProviderSseObserver.d.ts +19 -0
- package/dist/ai/ProviderSseObserver.js +98 -0
- package/dist/ai/aiServiceTier.d.ts +5 -0
- package/dist/ai/aiServiceTier.js +14 -0
- package/dist/ai/chunkEmbeddingText.d.ts +14 -0
- package/dist/ai/chunkEmbeddingText.js +147 -0
- package/dist/ai/contracts/AI.d.ts +16 -0
- package/dist/ai/contracts/AIRequestErrorDiagnostics.d.ts +12 -0
- package/dist/ai/contracts/AIRequestErrorDiagnostics.js +1 -0
- package/dist/ai/contracts/AIServiceTier.d.ts +2 -0
- package/dist/ai/contracts/AIServiceTier.js +1 -0
- package/dist/ai/contracts/Agent.d.ts +3 -0
- package/dist/ai/contracts/EmbeddingTextChunk.d.ts +25 -0
- package/dist/ai/contracts/EmbeddingTextChunk.js +1 -0
- package/dist/ai/contracts/Pricing.d.ts +7 -1
- package/dist/ai/contracts/Providers.d.ts +2 -0
- package/dist/ai/contracts/index.d.ts +2 -0
- package/dist/ai/contracts/index.js +1 -0
- package/dist/ai/index.d.ts +8 -2
- package/dist/ai/index.js +5 -2
- package/dist/ai/{Models.d.ts → modelPricing.d.ts} +2 -2
- package/dist/ai/{Models.js → modelPricing.js} +38 -4
- package/dist/apps/AppInstallation.d.ts +21 -0
- package/dist/apps/AppInstallation.js +16 -0
- package/dist/apps/AppRouteError.d.ts +6 -0
- package/dist/apps/AppRouteError.js +10 -0
- package/dist/apps/AppService.d.ts +24 -0
- package/dist/apps/AppService.js +21 -0
- package/dist/apps/Apps.d.ts +59 -0
- package/dist/apps/Apps.js +566 -0
- package/dist/apps/appsPlugin.d.ts +3 -0
- package/dist/apps/appsPlugin.js +36 -0
- package/dist/apps/commands/disableApp.d.ts +2 -0
- package/dist/apps/commands/disableApp.js +5 -0
- package/dist/apps/commands/enableApp.d.ts +2 -0
- package/dist/apps/commands/enableApp.js +5 -0
- package/dist/apps/commands/index.d.ts +10 -0
- package/dist/apps/commands/index.js +27 -0
- package/dist/apps/commands/installApp.d.ts +2 -0
- package/dist/apps/commands/installApp.js +5 -0
- package/dist/apps/commands/listApps.d.ts +2 -0
- package/dist/apps/commands/listApps.js +5 -0
- package/dist/apps/commands/makeAppMigration.d.ts +2 -0
- package/dist/apps/commands/makeAppMigration.js +9 -0
- package/dist/apps/commands/rollbackApp.d.ts +2 -0
- package/dist/apps/commands/rollbackApp.js +5 -0
- package/dist/apps/commands/uninstallApp.d.ts +2 -0
- package/dist/apps/commands/uninstallApp.js +5 -0
- package/dist/apps/contracts/AppAction.d.ts +2 -0
- package/dist/apps/contracts/AppAction.js +1 -0
- package/dist/apps/contracts/AppDefinition.d.ts +45 -0
- package/dist/apps/contracts/AppDefinition.js +1 -0
- package/dist/apps/contracts/AppDescription.d.ts +32 -0
- package/dist/apps/contracts/AppDescription.js +1 -0
- package/dist/apps/contracts/AppManifest.d.ts +30 -0
- package/dist/apps/contracts/AppManifest.js +1 -0
- package/dist/apps/contracts/AppNavigation.d.ts +9 -0
- package/dist/apps/contracts/AppNavigation.js +1 -0
- package/dist/apps/contracts/AppNavigationBadge.d.ts +6 -0
- package/dist/apps/contracts/AppNavigationBadge.js +1 -0
- package/dist/apps/contracts/AppNavigationContext.d.ts +8 -0
- package/dist/apps/contracts/AppNavigationContext.js +1 -0
- package/dist/apps/contracts/AppNavigationResult.d.ts +12 -0
- package/dist/apps/contracts/AppNavigationResult.js +1 -0
- package/dist/apps/contracts/AppRoute.d.ts +19 -0
- package/dist/apps/contracts/AppRoute.js +1 -0
- package/dist/apps/contracts/DiscoveredApp.d.ts +10 -0
- package/dist/apps/contracts/DiscoveredApp.js +1 -0
- package/dist/apps/contracts/InstalledApps.d.ts +3 -0
- package/dist/apps/contracts/InstalledApps.js +1 -0
- package/dist/apps/contracts/index.d.ts +11 -0
- package/dist/apps/contracts/index.js +1 -0
- package/dist/apps/defineApp.d.ts +7 -0
- package/dist/apps/defineApp.js +8 -0
- package/dist/apps/discoverApps.d.ts +3 -0
- package/dist/apps/discoverApps.js +62 -0
- package/dist/apps/fastify.d.ts +1 -0
- package/dist/apps/fastify.js +1 -0
- package/dist/apps/index.d.ts +7 -0
- package/dist/apps/index.js +7 -0
- package/dist/apps/normalizeAppNavigation.d.ts +3 -0
- package/dist/apps/normalizeAppNavigation.js +30 -0
- package/dist/apps/registerAppRoutes.d.ts +6 -0
- package/dist/apps/registerAppRoutes.js +52 -0
- package/dist/apps/validateAppDefinitions.d.ts +3 -0
- package/dist/apps/validateAppDefinitions.js +65 -0
- package/dist/apps/vite.d.ts +1 -0
- package/dist/apps/vite.js +1 -0
- package/dist/apps/writeAppTypes.d.ts +2 -0
- package/dist/apps/writeAppTypes.js +13 -0
- package/dist/auth/Auth.d.ts +18 -0
- package/dist/auth/Auth.js +89 -13
- package/dist/auth/PasswordLoginAttempt.d.ts +50 -0
- package/dist/auth/PasswordLoginAttempt.js +60 -0
- package/dist/auth/PasswordSuspendedError.d.ts +10 -0
- package/dist/auth/PasswordSuspendedError.js +13 -0
- package/dist/auth/contracts/PasswordAuthProviderOptions.d.ts +26 -0
- package/dist/auth/contracts/PasswordAuthProviderOptions.js +1 -0
- package/dist/auth/contracts/PasswordSuspension.d.ts +7 -0
- package/dist/auth/contracts/PasswordSuspension.js +1 -0
- package/dist/auth/contracts/PasswordSuspensionOptions.d.ts +10 -0
- package/dist/auth/contracts/PasswordSuspensionOptions.js +1 -0
- package/dist/auth/contracts/index.d.ts +3 -0
- package/dist/auth/contracts/index.js +3 -0
- package/dist/auth/index.d.ts +2 -0
- package/dist/auth/index.js +2 -0
- package/dist/auth/providers/PasswordAuthProvider.d.ts +19 -23
- package/dist/auth/providers/PasswordAuthProvider.js +96 -8
- package/dist/auth/providers/resolveAuthProviders.js +1 -0
- package/dist/cli/Cli.d.ts +2 -0
- package/dist/cli/Cli.js +8 -0
- package/dist/cli/commands/repl.js +2 -1
- package/dist/cli/contracts/CliCommand.d.ts +2 -0
- package/dist/cli/contracts/CliCommandInfo.d.ts +12 -0
- package/dist/cli/contracts/CliCommandInfo.js +1 -0
- package/dist/cli/contracts/index.d.ts +1 -0
- package/dist/cli/index.d.ts +1 -0
- package/dist/cli/index.js +1 -0
- package/dist/cli/listDb3Commands.d.ts +8 -0
- package/dist/cli/listDb3Commands.js +10 -0
- package/dist/cli/runDb3.d.ts +3 -6
- package/dist/cli/runDb3.js +5 -59
- package/dist/cli/withDb3Cli.d.ts +4 -0
- package/dist/cli/withDb3Cli.js +60 -0
- package/dist/db/ActiveQueryBuilder.d.ts +8 -0
- package/dist/db/ActiveQueryBuilder.js +11 -0
- package/dist/db/ActiveRecord.d.ts +6 -0
- package/dist/db/ActiveRecord.js +8 -0
- package/dist/db/connection.js +14 -2
- package/dist/db/fields/TimestampField.d.ts +1 -1
- package/dist/db/fields/TimestampField.js +7 -12
- package/dist/db/migrations/DatabaseMigrationManager.d.ts +3 -1
- package/dist/db/migrations/DatabaseMigrationManager.js +9 -3
- package/dist/db/migrations/contracts/DatabaseMigration.d.ts +7 -0
- package/dist/db/migrations/index.d.ts +1 -1
- package/dist/db/migrations/index.js +1 -1
- package/dist/db/migrations/{KnexMigrationRenderer.d.ts → renderKnexMigration.d.ts} +4 -3
- package/dist/db/migrations/{KnexMigrationRenderer.js → renderKnexMigration.js} +7 -6
- package/dist/flows/FlowCompiler.js +1 -1
- package/dist/flows/Flows.js +1 -1
- package/dist/flows/index.d.ts +1 -1
- package/dist/flows/index.js +1 -1
- package/dist/health/Health.d.ts +41 -0
- package/dist/health/Health.js +153 -0
- package/dist/health/contracts/Health.d.ts +36 -0
- package/dist/health/contracts/Health.js +1 -0
- package/dist/health/contracts/HealthHttp.d.ts +15 -0
- package/dist/health/contracts/HealthHttp.js +1 -0
- package/dist/health/contracts/index.d.ts +2 -0
- package/dist/health/contracts/index.js +1 -0
- package/dist/health/databaseHealthCheck.d.ts +15 -0
- package/dist/health/databaseHealthCheck.js +18 -0
- package/dist/health/fastify.d.ts +13 -0
- package/dist/health/fastify.js +44 -0
- package/dist/health/index.d.ts +3 -0
- package/dist/health/index.js +2 -0
- package/dist/in-app/InApp.d.ts +33 -0
- package/dist/in-app/InApp.js +191 -0
- package/dist/in-app/InAppError.d.ts +6 -0
- package/dist/in-app/InAppError.js +10 -0
- package/dist/in-app/InAppRecord.d.ts +36 -0
- package/dist/in-app/InAppRecord.js +24 -0
- package/dist/in-app/contracts/InAppInbox.d.ts +45 -0
- package/dist/in-app/contracts/InAppInbox.js +1 -0
- package/dist/in-app/contracts/InAppMessage.d.ts +22 -0
- package/dist/in-app/contracts/InAppMessage.js +1 -0
- package/dist/in-app/contracts/InAppScope.d.ts +17 -0
- package/dist/in-app/contracts/InAppScope.js +1 -0
- package/dist/in-app/contracts/index.d.ts +3 -0
- package/dist/in-app/contracts/index.js +3 -0
- package/dist/in-app/index.d.ts +4 -0
- package/dist/in-app/index.js +4 -0
- package/dist/in-app/validation.d.ts +21 -0
- package/dist/in-app/validation.js +50 -0
- package/dist/index.d.ts +2 -14
- package/dist/index.js +2 -5
- package/dist/logging/DevelopmentConsole.d.ts +42 -0
- package/dist/logging/DevelopmentConsole.js +162 -0
- package/dist/logging/Log.d.ts +3 -1
- package/dist/logging/Log.js +5 -2
- package/dist/logging/PrettyLogFormatter.d.ts +16 -0
- package/dist/logging/PrettyLogFormatter.js +151 -0
- package/dist/logging/acquireDevelopmentConsole.d.ts +6 -0
- package/dist/logging/acquireDevelopmentConsole.js +21 -0
- package/dist/logging/contracts/DevelopmentConsoleOptions.d.ts +16 -0
- package/dist/logging/contracts/DevelopmentConsoleOptions.js +1 -0
- package/dist/logging/contracts/EmailLogOptions.d.ts +8 -0
- package/dist/logging/contracts/EmailLogOptions.js +1 -0
- package/dist/logging/contracts/HttpExchangeMonitorOptions.d.ts +12 -0
- package/dist/logging/contracts/HttpExchangeMonitorOptions.js +1 -0
- package/dist/logging/contracts/LogTransportOptions.d.ts +19 -0
- package/dist/logging/contracts/LogTransportOptions.js +1 -0
- package/dist/logging/contracts/LoggingOptions.d.ts +12 -1
- package/dist/logging/contracts/index.d.ts +4 -0
- package/dist/logging/contracts/index.js +4 -0
- package/dist/logging/drivers/PinoLoggerDriver.d.ts +3 -1
- package/dist/logging/drivers/PinoLoggerDriver.js +75 -16
- package/dist/logging/formatLogEmail.d.ts +4 -0
- package/dist/logging/formatLogEmail.js +21 -0
- package/dist/logging/highlightQueueMessage.d.ts +11 -0
- package/dist/logging/highlightQueueMessage.js +36 -0
- package/dist/logging/httpBodyCapture.d.ts +24 -0
- package/dist/logging/httpBodyCapture.js +321 -0
- package/dist/logging/index.d.ts +2 -0
- package/dist/logging/index.js +2 -0
- package/dist/logging/redactLogEmail.d.ts +2 -0
- package/dist/logging/redactLogEmail.js +12 -0
- package/dist/logging/registerHttpExchangeMonitor.d.ts +10 -0
- package/dist/logging/registerHttpExchangeMonitor.js +43 -0
- package/dist/logging/transports/EmailLogTransport.d.ts +18 -0
- package/dist/logging/transports/EmailLogTransport.js +47 -0
- package/dist/mail/Mail.d.ts +2 -0
- package/dist/mail/Mail.js +3 -0
- package/dist/mail/MailDeliveryError.d.ts +9 -0
- package/dist/mail/MailDeliveryError.js +16 -0
- package/dist/mail/index.d.ts +1 -0
- package/dist/mail/index.js +1 -0
- package/dist/mail/transports/MailgunTransport.js +2 -0
- package/dist/mail/transports/ResendTransport.d.ts +3 -2
- package/dist/mail/transports/ResendTransport.js +22 -14
- package/dist/media/MediaManager.d.ts +4 -2
- package/dist/media/MediaManager.js +40 -8
- package/dist/network/BlockedUrlError.d.ts +16 -0
- package/dist/network/BlockedUrlError.js +19 -0
- package/dist/network/assertPublicUrl.d.ts +22 -0
- package/dist/network/assertPublicUrl.js +67 -0
- package/dist/network/contracts/GuardedFetch.d.ts +35 -0
- package/dist/network/contracts/GuardedFetch.js +1 -0
- package/dist/network/contracts/PublicUrlOptions.d.ts +17 -0
- package/dist/network/contracts/PublicUrlOptions.js +1 -0
- package/dist/network/contracts/index.d.ts +2 -0
- package/dist/network/contracts/index.js +2 -0
- package/dist/network/guardedFetch.d.ts +29 -0
- package/dist/network/guardedFetch.js +133 -0
- package/dist/network/index.d.ts +6 -0
- package/dist/network/index.js +6 -0
- package/dist/network/playwright/GuardedBrowserProxy.d.ts +32 -0
- package/dist/network/playwright/GuardedBrowserProxy.js +172 -0
- package/dist/network/playwright/contracts/GuardedBrowserContextOptions.d.ts +37 -0
- package/dist/network/playwright/contracts/GuardedBrowserContextOptions.js +1 -0
- package/dist/network/playwright/contracts/index.d.ts +1 -0
- package/dist/network/playwright/contracts/index.js +1 -0
- package/dist/network/playwright/index.d.ts +2 -0
- package/dist/network/playwright/index.js +2 -0
- package/dist/network/playwright/newGuardedBrowserContext.d.ts +21 -0
- package/dist/network/playwright/newGuardedBrowserContext.js +86 -0
- package/dist/network/privateNetworkAddresses.d.ts +44 -0
- package/dist/network/privateNetworkAddresses.js +157 -0
- package/dist/network/publicAddressLookup.d.ts +26 -0
- package/dist/network/publicAddressLookup.js +42 -0
- package/dist/notifications/Notifications.d.ts +27 -0
- package/dist/notifications/Notifications.js +99 -0
- package/dist/notifications/contracts/Notification.d.ts +56 -0
- package/dist/notifications/contracts/Notification.js +1 -0
- package/dist/notifications/contracts/NotificationDelivery.d.ts +11 -0
- package/dist/notifications/contracts/NotificationDelivery.js +1 -0
- package/dist/notifications/contracts/index.d.ts +2 -0
- package/dist/notifications/contracts/index.js +2 -0
- package/dist/notifications/index.d.ts +2 -0
- package/dist/notifications/index.js +2 -0
- package/dist/queue/JobRunAttempt.d.ts +16 -0
- package/dist/queue/JobRunAttempt.js +17 -0
- package/dist/queue/JobRunEvent.d.ts +15 -0
- package/dist/queue/JobRunEvent.js +16 -0
- package/dist/queue/JobRunStoppedError.d.ts +6 -0
- package/dist/queue/JobRunStoppedError.js +10 -0
- package/dist/queue/Queue.d.ts +19 -4
- package/dist/queue/Queue.js +122 -9
- package/dist/queue/QueueTerminalError.d.ts +9 -0
- package/dist/queue/QueueTerminalError.js +12 -0
- package/dist/queue/QueueWorker.d.ts +12 -5
- package/dist/queue/QueueWorker.js +94 -9
- package/dist/queue/QueueWorkerReporter.d.ts +17 -0
- package/dist/queue/QueueWorkerReporter.js +71 -0
- package/dist/queue/QueueableJob.d.ts +2 -2
- package/dist/queue/RunnableJob.d.ts +78 -0
- package/dist/queue/RunnableJob.js +284 -0
- package/dist/queue/console.d.ts +8 -0
- package/dist/queue/console.js +53 -19
- package/dist/queue/contracts/QueueDriver.d.ts +8 -0
- package/dist/queue/contracts/QueueJobRunner.d.ts +4 -0
- package/dist/queue/contracts/QueueJobRunner.js +1 -0
- package/dist/queue/contracts/QueuePayload.d.ts +1 -1
- package/dist/queue/contracts/QueueSelection.d.ts +11 -0
- package/dist/queue/contracts/QueueSelection.js +1 -0
- package/dist/queue/contracts/QueueService.d.ts +18 -4
- package/dist/queue/contracts/QueueWorkerLifecycle.d.ts +2 -2
- package/dist/queue/contracts/QueueWorkerSnapshot.d.ts +14 -0
- package/dist/queue/contracts/QueueWorkerSnapshot.js +1 -0
- package/dist/queue/contracts/QueueableJob.d.ts +7 -3
- package/dist/queue/contracts/QueueableJobContract.d.ts +12 -0
- package/dist/queue/contracts/QueueableJobContract.js +1 -0
- package/dist/queue/contracts/index.d.ts +4 -0
- package/dist/queue/contracts/index.js +2 -0
- package/dist/queue/drivers/DatabaseQueueDriver.d.ts +4 -0
- package/dist/queue/drivers/DatabaseQueueDriver.js +27 -3
- package/dist/queue/drivers/RedisQueueDriver.d.ts +7 -0
- package/dist/queue/drivers/RedisQueueDriver.js +37 -0
- package/dist/queue/index.d.ts +5 -0
- package/dist/queue/index.js +5 -0
- package/dist/queue/jobEnvelopeHasPrefix.d.ts +3 -0
- package/dist/queue/jobEnvelopeHasPrefix.js +4 -0
- package/dist/scheduler/ScheduledEvent.d.ts +8 -4
- package/dist/scheduler/ScheduledEvent.js +17 -3
- package/dist/scheduler/ScheduledJob.d.ts +1 -1
- package/dist/scheduler/Scheduler.d.ts +5 -0
- package/dist/scheduler/Scheduler.js +92 -28
- package/dist/scheduler/SchedulerCheckpointRecord.d.ts +16 -0
- package/dist/scheduler/SchedulerCheckpointRecord.js +53 -0
- package/dist/scheduler/SchedulerWorker.d.ts +3 -5
- package/dist/scheduler/SchedulerWorker.js +58 -14
- package/dist/scheduler/console.js +3 -1
- package/dist/scheduler/contracts/Schedule.d.ts +19 -0
- package/dist/scheduler/contracts/Schedule.js +1 -0
- package/dist/scheduler/contracts/Scheduler.d.ts +18 -6
- package/dist/scheduler/contracts/SchedulerCheckpoint.d.ts +23 -0
- package/dist/scheduler/contracts/SchedulerCheckpoint.js +1 -0
- package/dist/scheduler/contracts/SchedulerConsole.d.ts +5 -0
- package/dist/scheduler/contracts/SchedulerWorker.d.ts +6 -1
- package/dist/scheduler/contracts/index.d.ts +2 -0
- package/dist/scheduler/contracts/index.js +2 -0
- package/dist/scheduler/index.d.ts +1 -0
- package/dist/scheduler/index.js +1 -0
- package/dist/server/App.d.ts +36 -4
- package/dist/server/App.js +57 -7
- package/dist/server/contracts/HttpErrorHandlerOptions.d.ts +29 -0
- package/dist/server/contracts/HttpErrorHandlerOptions.js +1 -0
- package/dist/server/contracts/index.d.ts +1 -0
- package/dist/server/contracts/index.js +1 -0
- package/dist/server/index.d.ts +4 -0
- package/dist/server/index.js +4 -0
- package/dist/server/publicServerErrorMessage.d.ts +11 -0
- package/dist/server/publicServerErrorMessage.js +16 -0
- package/dist/server/registerBrowserJsonFormatting.d.ts +16 -0
- package/dist/server/registerBrowserJsonFormatting.js +100 -0
- package/dist/server/registerHttpErrorHandler.d.ts +20 -0
- package/dist/server/registerHttpErrorHandler.js +93 -0
- package/dist/ssr/vite/contracts/ViteSsrOptions.d.ts +2 -0
- package/dist/ssr/vite/fastifyViteSsr.js +4 -3
- package/dist/storage/drivers/FlystorageDisk.js +2 -2
- package/dist/storage/index.d.ts +2 -2
- package/dist/storage/index.js +2 -2
- package/dist/websocket/WebSocketChannels.d.ts +18 -0
- package/dist/websocket/WebSocketChannels.js +129 -0
- package/dist/websocket/WebSocketConnection.d.ts +25 -0
- package/dist/websocket/WebSocketConnection.js +244 -0
- package/dist/websocket/WebSockets.d.ts +41 -0
- package/dist/websocket/WebSockets.js +194 -0
- package/dist/websocket/client/WebSocketClient.d.ts +21 -0
- package/dist/websocket/client/WebSocketClient.js +230 -0
- package/dist/websocket/client/index.d.ts +3 -0
- package/dist/websocket/client/index.js +1 -0
- package/dist/websocket/contracts/WebSocketChannel.d.ts +20 -0
- package/dist/websocket/contracts/WebSocketChannel.js +1 -0
- package/dist/websocket/contracts/WebSocketClient.d.ts +45 -0
- package/dist/websocket/contracts/WebSocketClient.js +1 -0
- package/dist/websocket/contracts/WebSocketEndpoint.d.ts +43 -0
- package/dist/websocket/contracts/WebSocketEndpoint.js +1 -0
- package/dist/websocket/contracts/WebSocketOptions.d.ts +48 -0
- package/dist/websocket/contracts/WebSocketOptions.js +1 -0
- package/dist/websocket/contracts/WebSocketPresence.d.ts +6 -0
- package/dist/websocket/contracts/WebSocketPresence.js +1 -0
- package/dist/websocket/contracts/WebSocketServiceOptions.d.ts +12 -0
- package/dist/websocket/contracts/WebSocketServiceOptions.js +1 -0
- package/dist/websocket/contracts/index.d.ts +6 -0
- package/dist/websocket/contracts/index.js +1 -0
- package/dist/websocket/defineChannel.d.ts +8 -0
- package/dist/websocket/defineChannel.js +13 -0
- package/dist/websocket/defineWebSocket.d.ts +14 -0
- package/dist/websocket/defineWebSocket.js +4 -0
- package/dist/websocket/fastify.d.ts +11 -0
- package/dist/websocket/fastify.js +38 -0
- package/dist/websocket/index.d.ts +5 -0
- package/dist/websocket/index.js +4 -0
- package/package.json +108 -7
- package/src/ai/AIErrors.ts +10 -0
- package/src/ai/AIFailover.ts +3 -2
- package/src/ai/AIProviderAdmission.ts +329 -0
- package/src/ai/AIRateLimiter.ts +134 -10
- package/src/ai/AIRequestTrackingError.ts +37 -0
- package/src/ai/Agent.ts +85 -71
- package/src/ai/Ai.ts +104 -48
- package/src/ai/OpenAIProviderError.ts +1 -1
- package/src/ai/ProviderSseObserver.ts +89 -0
- package/src/ai/README.md +216 -11
- package/src/ai/aiServiceTier.ts +14 -0
- package/src/ai/chunkEmbeddingText.ts +137 -0
- package/src/ai/contracts/AI.ts +17 -0
- package/src/ai/contracts/AIRequestErrorDiagnostics.ts +12 -0
- package/src/ai/contracts/AIServiceTier.ts +2 -0
- package/src/ai/contracts/Agent.ts +3 -0
- package/src/ai/contracts/EmbeddingTextChunk.ts +26 -0
- package/src/ai/contracts/Pricing.ts +7 -1
- package/src/ai/contracts/Providers.ts +2 -0
- package/src/ai/contracts/index.ts +2 -0
- package/src/ai/examples/prepareDocumentEmbeddings.ts +20 -0
- package/src/ai/index.ts +9 -2
- package/src/ai/{Models.ts → modelPricing.ts} +37 -4
- package/src/apps/AppInstallation.ts +25 -0
- package/src/apps/AppRouteError.ts +8 -0
- package/src/apps/AppService.ts +30 -0
- package/src/apps/Apps.ts +508 -0
- package/src/apps/README.md +354 -0
- package/src/apps/appsPlugin.ts +34 -0
- package/src/apps/commands/disableApp.ts +6 -0
- package/src/apps/commands/enableApp.ts +6 -0
- package/src/apps/commands/index.ts +29 -0
- package/src/apps/commands/installApp.ts +6 -0
- package/src/apps/commands/listApps.ts +6 -0
- package/src/apps/commands/makeAppMigration.ts +9 -0
- package/src/apps/commands/rollbackApp.ts +6 -0
- package/src/apps/commands/uninstallApp.ts +6 -0
- package/src/apps/contracts/AppAction.ts +2 -0
- package/src/apps/contracts/AppDefinition.ts +49 -0
- package/src/apps/contracts/AppDescription.ts +27 -0
- package/src/apps/contracts/AppManifest.ts +32 -0
- package/src/apps/contracts/AppNavigation.ts +10 -0
- package/src/apps/contracts/AppNavigationBadge.ts +6 -0
- package/src/apps/contracts/AppNavigationContext.ts +6 -0
- package/src/apps/contracts/AppNavigationResult.ts +9 -0
- package/src/apps/contracts/AppRoute.ts +18 -0
- package/src/apps/contracts/DiscoveredApp.ts +11 -0
- package/src/apps/contracts/InstalledApps.ts +2 -0
- package/src/apps/contracts/index.ts +11 -0
- package/src/apps/defineApp.ts +10 -0
- package/src/apps/discoverApps.ts +56 -0
- package/src/apps/fastify.ts +1 -0
- package/src/apps/index.ts +7 -0
- package/src/apps/normalizeAppNavigation.ts +29 -0
- package/src/apps/registerAppRoutes.ts +48 -0
- package/src/apps/validateAppDefinitions.ts +52 -0
- package/src/apps/vite.ts +1 -0
- package/src/apps/writeAppTypes.ts +14 -0
- package/src/auth/Auth.ts +89 -23
- package/src/auth/PasswordLoginAttempt.ts +72 -0
- package/src/auth/PasswordSuspendedError.ts +13 -0
- package/src/auth/README.md +94 -4
- package/src/auth/contracts/PasswordAuthProviderOptions.ts +30 -0
- package/src/auth/contracts/PasswordSuspension.ts +7 -0
- package/src/auth/contracts/PasswordSuspensionOptions.ts +10 -0
- package/src/auth/contracts/index.ts +3 -0
- package/src/auth/examples/runPasswordAuth.ts +6 -6
- package/src/auth/index.ts +2 -0
- package/src/auth/providers/PasswordAuthProvider.ts +96 -30
- package/src/auth/providers/resolveAuthProviders.ts +1 -0
- package/src/cli/Cli.ts +9 -0
- package/src/cli/README.md +19 -0
- package/src/cli/commands/repl.ts +2 -1
- package/src/cli/contracts/CliCommand.ts +2 -0
- package/src/cli/contracts/CliCommandInfo.ts +13 -0
- package/src/cli/contracts/index.ts +1 -0
- package/src/cli/index.ts +1 -0
- package/src/cli/listDb3Commands.ts +12 -0
- package/src/cli/runDb3.ts +5 -51
- package/src/cli/withDb3Cli.ts +55 -0
- package/src/db/ActiveQueryBuilder.ts +12 -0
- package/src/db/ActiveRecord.ts +9 -0
- package/src/db/README.md +45 -1
- package/src/db/connection.ts +12 -1
- package/src/db/examples/FieldNote.ts +7 -13
- package/src/db/examples/KnowledgeNote.ts +7 -13
- package/src/db/examples/runNoteMigrations.ts +11 -11
- package/src/db/fields/TimestampField.ts +8 -17
- package/src/db/migrations/DatabaseMigrationManager.ts +12 -4
- package/src/db/migrations/contracts/DatabaseMigration.ts +9 -0
- package/src/db/migrations/index.ts +1 -1
- package/src/db/migrations/{KnexMigrationRenderer.ts → renderKnexMigration.ts} +8 -14
- package/src/flows/FlowCompiler.ts +1 -1
- package/src/flows/Flows.ts +1 -1
- package/src/flows/index.ts +1 -1
- package/src/health/Health.ts +163 -0
- package/src/health/README.md +46 -0
- package/src/health/contracts/Health.ts +47 -0
- package/src/health/contracts/HealthHttp.ts +19 -0
- package/src/health/contracts/index.ts +2 -0
- package/src/health/databaseHealthCheck.ts +21 -0
- package/src/health/fastify.ts +49 -0
- package/src/health/index.ts +3 -0
- package/src/in-app/InApp.ts +173 -0
- package/src/in-app/InAppError.ts +8 -0
- package/src/in-app/InAppRecord.ts +41 -0
- package/src/in-app/README.md +193 -0
- package/src/in-app/contracts/InAppInbox.ts +51 -0
- package/src/in-app/contracts/InAppMessage.ts +19 -0
- package/src/in-app/contracts/InAppScope.ts +12 -0
- package/src/in-app/contracts/index.ts +3 -0
- package/src/in-app/examples/sendReportReady.ts +14 -0
- package/src/in-app/index.ts +4 -0
- package/src/in-app/validation.ts +49 -0
- package/src/index.ts +2 -22
- package/src/logging/DevelopmentConsole.ts +154 -0
- package/src/logging/Log.ts +5 -2
- package/src/logging/PrettyLogFormatter.ts +165 -0
- package/src/logging/README.md +52 -109
- package/src/logging/acquireDevelopmentConsole.ts +19 -0
- package/src/logging/contracts/DevelopmentConsoleOptions.ts +13 -0
- package/src/logging/contracts/EmailLogOptions.ts +9 -0
- package/src/logging/contracts/HttpExchangeMonitorOptions.ts +13 -0
- package/src/logging/contracts/LogTransportOptions.ts +10 -0
- package/src/logging/contracts/LoggingOptions.ts +12 -1
- package/src/logging/contracts/index.ts +4 -0
- package/src/logging/development/README.md +88 -0
- package/src/logging/drivers/PinoLoggerDriver.ts +72 -20
- package/src/logging/examples/runDevelopmentLogs.ts +36 -0
- package/src/logging/formatLogEmail.ts +24 -0
- package/src/logging/highlightQueueMessage.ts +38 -0
- package/src/logging/httpBodyCapture.ts +393 -0
- package/src/logging/index.ts +2 -0
- package/src/logging/redactLogEmail.ts +12 -0
- package/src/logging/registerHttpExchangeMonitor.ts +45 -0
- package/src/logging/transports/EmailLogTransport.ts +46 -0
- package/src/mail/Mail.ts +5 -0
- package/src/mail/MailDeliveryError.ts +8 -0
- package/src/mail/README.md +11 -1
- package/src/mail/index.ts +1 -0
- package/src/mail/transports/MailgunTransport.ts +2 -0
- package/src/mail/transports/ResendTransport.ts +24 -22
- package/src/media/MediaManager.ts +31 -10
- package/src/media/README.md +4 -0
- package/src/media/examples/runPrivateFiles.ts +2 -2
- package/src/network/BlockedUrlError.ts +19 -0
- package/src/network/README.md +133 -0
- package/src/network/assertPublicUrl.ts +77 -0
- package/src/network/contracts/GuardedFetch.ts +40 -0
- package/src/network/contracts/PublicUrlOptions.ts +17 -0
- package/src/network/contracts/index.ts +2 -0
- package/src/network/examples/runGuardedFetch.ts +35 -0
- package/src/network/guardedFetch.ts +150 -0
- package/src/network/index.ts +6 -0
- package/src/network/playwright/GuardedBrowserProxy.ts +172 -0
- package/src/network/playwright/contracts/GuardedBrowserContextOptions.ts +43 -0
- package/src/network/playwright/contracts/index.ts +1 -0
- package/src/network/playwright/index.ts +2 -0
- package/src/network/playwright/newGuardedBrowserContext.ts +74 -0
- package/src/network/privateNetworkAddresses.ts +166 -0
- package/src/network/publicAddressLookup.ts +49 -0
- package/src/notifications/Notifications.ts +105 -0
- package/src/notifications/README.md +59 -0
- package/src/notifications/contracts/Notification.ts +65 -0
- package/src/notifications/contracts/NotificationDelivery.ts +11 -0
- package/src/notifications/contracts/index.ts +2 -0
- package/src/notifications/examples/ReportReadyNotification.ts +31 -0
- package/src/notifications/index.ts +2 -0
- package/src/queue/JobRunAttempt.ts +17 -0
- package/src/queue/JobRunEvent.ts +16 -0
- package/src/queue/JobRunStoppedError.ts +8 -0
- package/src/queue/Queue.ts +112 -11
- package/src/queue/QueueTerminalError.ts +12 -0
- package/src/queue/QueueWorker.ts +86 -7
- package/src/queue/QueueWorkerReporter.ts +59 -0
- package/src/queue/QueueableJob.ts +2 -2
- package/src/queue/README.md +142 -1
- package/src/queue/RunnableJob.ts +272 -0
- package/src/queue/console.ts +54 -21
- package/src/queue/contracts/QueueDriver.ts +9 -0
- package/src/queue/contracts/QueueJobRunner.ts +4 -0
- package/src/queue/contracts/QueuePayload.ts +1 -1
- package/src/queue/contracts/QueueSelection.ts +11 -0
- package/src/queue/contracts/QueueService.ts +19 -4
- package/src/queue/contracts/QueueWorkerLifecycle.ts +2 -2
- package/src/queue/contracts/QueueWorkerSnapshot.ts +15 -0
- package/src/queue/contracts/QueueableJob.ts +7 -3
- package/src/queue/contracts/QueueableJobContract.ts +13 -0
- package/src/queue/contracts/index.ts +6 -0
- package/src/queue/drivers/DatabaseQueueDriver.ts +25 -3
- package/src/queue/drivers/RedisQueueDriver.ts +36 -0
- package/src/queue/examples/runQueueSelection.ts +34 -0
- package/src/queue/index.ts +7 -0
- package/src/queue/jobEnvelopeHasPrefix.ts +6 -0
- package/src/scheduler/README.md +50 -9
- package/src/scheduler/ScheduledEvent.ts +20 -5
- package/src/scheduler/ScheduledJob.ts +1 -1
- package/src/scheduler/Scheduler.ts +73 -27
- package/src/scheduler/SchedulerCheckpointRecord.ts +51 -0
- package/src/scheduler/SchedulerWorker.ts +54 -19
- package/src/scheduler/console.ts +3 -1
- package/src/scheduler/contracts/Schedule.ts +22 -0
- package/src/scheduler/contracts/Scheduler.ts +21 -6
- package/src/scheduler/contracts/SchedulerCheckpoint.ts +23 -0
- package/src/scheduler/contracts/SchedulerConsole.ts +5 -0
- package/src/scheduler/contracts/SchedulerWorker.ts +6 -1
- package/src/scheduler/contracts/index.ts +2 -0
- package/src/scheduler/examples/runSchedulerWindow.ts +54 -0
- package/src/scheduler/index.ts +1 -0
- package/src/server/App.ts +73 -10
- package/src/server/README.md +95 -2
- package/src/server/contracts/HttpErrorHandlerOptions.ts +29 -0
- package/src/server/contracts/index.ts +1 -0
- package/src/server/examples/createFirstServer.ts +5 -3
- package/src/server/index.ts +4 -0
- package/src/server/publicServerErrorMessage.ts +17 -0
- package/src/server/registerBrowserJsonFormatting.ts +94 -0
- package/src/server/registerHttpErrorHandler.ts +96 -0
- package/src/ssr/README.md +6 -0
- package/src/ssr/vite/contracts/ViteSsrOptions.ts +2 -0
- package/src/ssr/vite/fastifyViteSsr.ts +4 -3
- package/src/storage/drivers/FlystorageDisk.ts +2 -2
- package/src/storage/index.ts +2 -2
- package/src/websocket/README.md +458 -0
- package/src/websocket/WebSocketChannels.ts +99 -0
- package/src/websocket/WebSocketConnection.ts +162 -0
- package/src/websocket/WebSockets.ts +157 -0
- package/src/websocket/client/WebSocketClient.ts +188 -0
- package/src/websocket/client/index.ts +3 -0
- package/src/websocket/contracts/WebSocketChannel.ts +23 -0
- package/src/websocket/contracts/WebSocketClient.ts +48 -0
- package/src/websocket/contracts/WebSocketEndpoint.ts +46 -0
- package/src/websocket/contracts/WebSocketOptions.ts +50 -0
- package/src/websocket/contracts/WebSocketPresence.ts +6 -0
- package/src/websocket/contracts/WebSocketServiceOptions.ts +12 -0
- package/src/websocket/contracts/index.ts +6 -0
- package/src/websocket/defineChannel.ts +14 -0
- package/src/websocket/defineWebSocket.ts +15 -0
- package/src/websocket/examples/board/LiveBoard.ts +97 -0
- package/src/websocket/examples/board/SummarizeBoardJob.ts +52 -0
- package/src/websocket/examples/board/boardSnapshot.ts +16 -0
- package/src/websocket/examples/board/createBoardClient.ts +43 -0
- package/src/websocket/examples/board/createBoardStore.ts +58 -0
- package/src/websocket/examples/board/registerBoardRoutes.ts +31 -0
- package/src/websocket/examples/createChannelSync.ts +66 -0
- package/src/websocket/examples/deploymentEndpoint.ts +13 -0
- package/src/websocket/examples/deploymentSnapshot.ts +36 -0
- package/src/websocket/examples/resourceChannels.ts +18 -0
- package/src/websocket/examples/userEndpoint.ts +27 -0
- package/src/websocket/fastify.ts +39 -0
- package/src/websocket/index.ts +5 -0
- package/templates/AGENTS.md +33 -2
- /package/dist/flows/{FlowValueValidator.d.ts → flowValueValidator.d.ts} +0 -0
- /package/dist/flows/{FlowValueValidator.js → flowValueValidator.js} +0 -0
- /package/dist/storage/{mime.d.ts → mimeTypeFromPath.d.ts} +0 -0
- /package/dist/storage/{mime.js → mimeTypeFromPath.js} +0 -0
- /package/dist/storage/{contents.d.ts → storageContentsToBuffer.d.ts} +0 -0
- /package/dist/storage/{contents.js → storageContentsToBuffer.js} +0 -0
- /package/src/flows/{FlowValueValidator.ts → flowValueValidator.ts} +0 -0
- /package/src/storage/{mime.ts → mimeTypeFromPath.ts} +0 -0
- /package/src/storage/{contents.ts → storageContentsToBuffer.ts} +0 -0
package/src/ai/README.md
CHANGED
|
@@ -39,17 +39,57 @@ returns final output and saved IDs; `stream(message, emit)` emits typed events
|
|
|
39
39
|
and returns null after a `run.error` event. A conversation can be resumed by
|
|
40
40
|
supplying its ID with matching user, scope and agent identity.
|
|
41
41
|
|
|
42
|
+
Agents default to a maximum of eight model turns per run. Override the protected
|
|
43
|
+
`maxTurns` property with a number to change that limit, or with `null` to allow
|
|
44
|
+
the agent to finish without a turn ceiling. For example,
|
|
45
|
+
`protected override readonly maxTurns = null;` applies to live runs, queued runs
|
|
46
|
+
and resumed conversations. A model turn can request tools or produce the final
|
|
47
|
+
answer; the agent stops naturally when it returns its final answer.
|
|
48
|
+
|
|
42
49
|
Register `AgentRunJob` on the queue and call `registerQueuedAgent(name, Class)`
|
|
43
50
|
at boot in both web and worker processes before using `agent.queue(message)`.
|
|
44
51
|
Its constructor context must be serializable. Queued agents require the normal
|
|
45
52
|
queue models and a worker listening on the selected queue.
|
|
46
53
|
|
|
54
|
+
## Browser computer tools
|
|
55
|
+
|
|
56
|
+
`computerTool` and the `Computer` type are exported from `@db3.ai/app/ai`.
|
|
57
|
+
Implement the SDK `Computer` contract in an application-owned browser adapter:
|
|
58
|
+
return PNG base64 from `screenshot()`, expose the matching viewport dimensions,
|
|
59
|
+
and delegate mouse, keyboard, scroll and drag actions to that isolated browser.
|
|
60
|
+
Add `computerTool({ name: 'computer', computer: adapter })` to the agent's tools
|
|
61
|
+
with its normal title/description metadata. The existing Agents SDK runs the
|
|
62
|
+
native computer-call/screenshot loop; do not create a second provider loop.
|
|
63
|
+
A compatible model such as `gpt-6-luna` can combine this tool with ordinary
|
|
64
|
+
function tools in the same run.
|
|
65
|
+
|
|
66
|
+
The application owns allocation, navigation restrictions, deadlines, recordings,
|
|
67
|
+
cleanup and evidence semantics. Provider-requested safety checks need explicit
|
|
68
|
+
handling: returning `false` only omits acknowledgement and does not stop the SDK
|
|
69
|
+
from executing input. Throw from `onSafetyCheck` when unattended execution must
|
|
70
|
+
stop for review. Native tool-action errors may return an empty screenshot through
|
|
71
|
+
the SDK; never treat the final model message alone as evidence of success.
|
|
72
|
+
Screenshot inputs and tool outputs can be retained in local AI request records;
|
|
73
|
+
apply the same access and retention rules as other private prompts. Resuming an
|
|
74
|
+
AI conversation does not restore its browser session. See
|
|
75
|
+
[OpenAI's computer-use guide](https://developers.openai.com/api/docs/guides/tools-computer-use)
|
|
76
|
+
for the provider contract.
|
|
77
|
+
|
|
47
78
|
## Images, embeddings and structured output
|
|
48
79
|
|
|
49
80
|
- `generateImage(input, { store })` returns image bytes and an optional app-owned
|
|
50
81
|
storage reference. See [createHelpImage.ts](./examples/createHelpImage.ts).
|
|
51
82
|
- `generateEmbedding(text, model?, options?)` returns a vector, model and request
|
|
52
83
|
ID. The app owns indexing, source revisions and authorized retrieval.
|
|
84
|
+
- `chunkEmbeddingText(text, { context })` prepares extracted text for the
|
|
85
|
+
`text-embedding-3-small`/`large` models using their `cl100k_base` tokenizer.
|
|
86
|
+
Documents that fit stay whole. Oversized documents split at headings,
|
|
87
|
+
paragraphs, sentences or whitespace, retaining bounded source context,
|
|
88
|
+
heading ancestry and up to 128 tokens of preceding overlap. Every complete
|
|
89
|
+
input stays within 8,000 tokens by default, including those prefixes.
|
|
90
|
+
Source offsets and exact text slices remain available for retrieval.
|
|
91
|
+
This helper makes no provider calls and does not extract HTML or generate
|
|
92
|
+
summaries. Context metadata is capped to leave room for source text.
|
|
53
93
|
- `generateStructured({ instructions, input, schemaName, schema })` returns
|
|
54
94
|
locally validated `data`, text and tracking IDs. Schemas use Zod.
|
|
55
95
|
|
|
@@ -57,6 +97,11 @@ Agent instances expose these same methods. Calls made inside an executing tool
|
|
|
57
97
|
inherit the current conversation and parent request, including calls through
|
|
58
98
|
`app().ai`. Nested calls cannot carry a second independent usage charge.
|
|
59
99
|
|
|
100
|
+
See [prepareDocumentEmbeddings.ts](./examples/prepareDocumentEmbeddings.ts) for
|
|
101
|
+
preparing and embedding passages. Applications own atomic publication, retries,
|
|
102
|
+
source revision checks and permission-scoped retrieval. Keep the original
|
|
103
|
+
source and its identity so a matching passage can be read in its wider context.
|
|
104
|
+
|
|
60
105
|
## Conversations and request records
|
|
61
106
|
|
|
62
107
|
`AiConversation`, `AiMessage` and `AiRequest` are shipped ActiveRecord classes.
|
|
@@ -85,22 +130,35 @@ may contain private information. Apply your app's access and retention policy.
|
|
|
85
130
|
`saveAiResponse: false` opts direct service calls out of record persistence.
|
|
86
131
|
OpenAI text requests set `store: false`; that does not disable local tracking or
|
|
87
132
|
all provider retention. Never expose provider credentials in client code.
|
|
133
|
+
If a pending embedding request cannot be saved, `generateEmbedding()` throws
|
|
134
|
+
`AIRequestTrackingError` before contacting the provider. Its `stage` identifies
|
|
135
|
+
the pending write and its `code` includes only recognized database lock codes;
|
|
136
|
+
the error deliberately omits the SQL exception because bindings may contain the
|
|
137
|
+
input text. This is separate from a provider rejection or a terminal usage-save
|
|
138
|
+
failure after provider execution.
|
|
88
139
|
|
|
89
140
|
## Models and cost estimates
|
|
90
141
|
|
|
91
|
-
Select `gpt-6-astra` through a per-call `model`
|
|
92
|
-
in your app's AI config.
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
142
|
+
Select `gpt-6-astra`, `gpt-6-sol` or `gpt-6-luna` through a per-call `model`
|
|
143
|
+
override or a named agent model in your app's AI config. Astra is intended for
|
|
144
|
+
the hardest tasks, Sol for demanding agent workflows, and Luna for focused,
|
|
145
|
+
high-volume work. OpenAI agents already use the Responses API required for
|
|
146
|
+
reasoning with tools. Preserve the workload's existing reasoning effort when
|
|
147
|
+
migrating. All three support `low` through `xhigh` in the framework; Sol and
|
|
148
|
+
Luna also support `none`. Do not use `minimal`, or custom `temperature`, `top_p`
|
|
149
|
+
or log probabilities with reasoning enabled. Availability depends on the API
|
|
150
|
+
project. Validate output quality and latency on representative application
|
|
151
|
+
tasks before a production rollout.
|
|
96
152
|
|
|
97
153
|
The shared `AI_MODEL_PRICING` table was checked against
|
|
98
154
|
[OpenAI's API prices](https://developers.openai.com/api/docs/pricing) on
|
|
99
|
-
2026-09-
|
|
155
|
+
2026-09-25. Standard USD prices per million tokens are:
|
|
100
156
|
|
|
101
157
|
| Model | Input | Cache read | Cache write | Output |
|
|
102
158
|
| --- | ---: | ---: | ---: | ---: |
|
|
103
159
|
| `gpt-6-astra` | $10.00 | $1.00 | $12.50 | $50.00 |
|
|
160
|
+
| `gpt-6-sol` | $2.00 | $0.20 | $2.50 | $10.00 |
|
|
161
|
+
| `gpt-6-luna` | $0.10 | $0.01 | $0.125 | $0.50 |
|
|
104
162
|
| `gpt-5.6-sol` | $4.00 | $0.40 | $5.00 | $20.00 |
|
|
105
163
|
| `gpt-5.6-terra` | $2.00 | $0.20 | $2.50 | $12.00 |
|
|
106
164
|
| `gpt-5.6-luna` | $0.20 | $0.02 | $0.25 | $1.20 |
|
|
@@ -108,15 +166,31 @@ The shared `AI_MODEL_PRICING` table was checked against
|
|
|
108
166
|
For these models, a request above 272,000 input tokens costs 2x all input
|
|
109
167
|
rates and 1.5x output rates for the full request. Agent runs calculate this
|
|
110
168
|
per provider request, so several short turns do not trigger the higher rates
|
|
111
|
-
merely because their combined usage exceeds the threshold. Sol's published
|
|
169
|
+
merely because their combined usage exceeds the threshold. GPT-5.6 Sol's published
|
|
112
170
|
promotional rates are available at least through 2026-11-21; recheck the rate
|
|
113
171
|
card when that period ends rather than assuming a future price.
|
|
114
172
|
|
|
115
|
-
Direct OpenAI text and agent requests
|
|
116
|
-
|
|
173
|
+
Direct OpenAI text and agent requests default to Standard processing. Pass
|
|
174
|
+
`serviceTier: 'flex'` to `generateText`, `generateTextWithResponse` or
|
|
175
|
+
`generateStructured`, or override `protected readonly serviceTier: AIServiceTier = 'flex'`
|
|
176
|
+
on an `Agent` subclass (import the type from `@db3.ai/app/ai`). The property
|
|
177
|
+
defaults to `'default'`; queued runs preserve the selected tier. Streaming and
|
|
178
|
+
tool turns use the same tier. Separate calls inside tools do not inherit it.
|
|
179
|
+
Nondefault tiers require an entirely OpenAI provider chain.
|
|
180
|
+
|
|
181
|
+
For the six models above, Flex token rates are half Standard and Fast/Priority
|
|
182
|
+
rates are twice Standard. Costs use each response's reported tier and model;
|
|
183
|
+
unconfirmed nonstandard tiers or missing tier rate cards remain unpriced.
|
|
184
|
+
Hosted-tool fees are unchanged. Estimates exclude regional surcharges. OpenRouter and xAI
|
|
117
185
|
use their provider-reported billed costs. Updates affect new estimates and
|
|
118
186
|
new request records; they do not rewrite stored costs or change app model defaults.
|
|
119
187
|
|
|
188
|
+
The default `gpt-4.1-mini` model and its dated snapshots also have a rate card:
|
|
189
|
+
$0.40 input, $0.10 cached input and $1.60 output per million tokens, verified
|
|
190
|
+
against [the model documentation](https://developers.openai.com/api/docs/models/gpt-4.1-mini)
|
|
191
|
+
on 2026-10-01. This estimate supports small browser agents such as Cloud's
|
|
192
|
+
AI Test Engineer; interrupted requests with missing usage remain unpriced.
|
|
193
|
+
|
|
120
194
|
Image pricing includes `gpt-image-2.5-flare` and `gpt-image-2`: $5 text input,
|
|
121
195
|
$1.25 cached text input, $8 image input, $2 cached image input and $30 image
|
|
122
196
|
output per million tokens. Dated Flare snapshots resolve to the same rate card.
|
|
@@ -138,17 +212,130 @@ OpenAI adapter and do not fail over. Other protocols need a driver implementatio
|
|
|
138
212
|
Transient network, rate-limit, quota and server failures can advance to another
|
|
139
213
|
provider. Authentication and request validation failures do not. Agent failover
|
|
140
214
|
stops once the SDK emits an event, avoiding automatic replay of tool effects.
|
|
141
|
-
The per-request timeout defaults to 60 seconds
|
|
215
|
+
The per-request timeout defaults to 60 seconds for Standard and 15 minutes for
|
|
216
|
+
Flex; an explicit `ai.timeoutMs` overrides either. Recovery-probe leases cover
|
|
217
|
+
the selected timeout. SDK automatic retries remain off; existing bounded retry,
|
|
218
|
+
deferral and provider-stop rules still apply. This option does not add durable
|
|
219
|
+
checkpoints or guarantee multi-hour recovery. A partial stream or exhausted
|
|
220
|
+
retry window can still fail; test locally before enabling workflows.
|
|
142
221
|
|
|
143
222
|
The SQL-backed `AIRateLimiter` coordinates provider capacity across workers.
|
|
144
223
|
Agents reserve capacity for each SDK HTTP request and record response headers
|
|
145
224
|
before consuming the stream. Reservations are released before tools execute,
|
|
146
225
|
so a tool can call the same model without waiting on its own parent agent.
|
|
147
226
|
Transport failures also release reservations; later model turns reserve again.
|
|
148
|
-
|
|
227
|
+
|
|
228
|
+
Bucket observation and reservation release are best-effort bookkeeping after
|
|
229
|
+
provider work when they run as autocommit writes. Recognized SQL deadlocks and
|
|
230
|
+
lock timeouts retry the same write up to three times, with 25 ms and 50 ms
|
|
231
|
+
pauses; this never repeats the provider call or changes its saved outcome,
|
|
232
|
+
usage or cost. Three attempts limit the number of writes, not total elapsed
|
|
233
|
+
time: each attempt still uses the database session's lock-wait timeout.
|
|
234
|
+
Release uses a conditional database update and only then marks the lease
|
|
235
|
+
released in memory. Reusing a lease can therefore retry a failed release, while
|
|
236
|
+
an already released or deleted row remains an idempotent success.
|
|
237
|
+
|
|
238
|
+
A caller-owned transaction gets one attempt. Any bookkeeping or cleanup error
|
|
239
|
+
propagates unchanged to that transaction's owner, and the limiter performs no
|
|
240
|
+
further writes in the failed transaction. InnoDB can roll back the entire
|
|
241
|
+
transaction on a deadlock, including earlier request/usage writes; swallowing
|
|
242
|
+
that error would falsely imply a successful commit. Keep paid provider calls
|
|
243
|
+
outside retryable database transactions. The limiter does not retry the whole
|
|
244
|
+
transaction or replay a provider request.
|
|
245
|
+
|
|
246
|
+
If an autocommit observation or release still fails, the original provider
|
|
247
|
+
result or error continues. The previous database capacity remains in force,
|
|
248
|
+
and an unreleased reservation stops counting at its existing ten-minute expiry.
|
|
249
|
+
Global cleanup remains best effort outside caller-owned transactions and may
|
|
250
|
+
be retried by application maintenance policy. Structured warnings identify
|
|
251
|
+
`bucket:observe`, `reservation:release` or `reservation:cleanup`, with allowlisted
|
|
252
|
+
SQL lock codes, attempt count, recovery state, whether the caller transaction
|
|
253
|
+
failed, coordination/request IDs and expiry. They omit SQL, bindings, exception
|
|
254
|
+
messages, prompts and responses. Monitor these warnings to investigate recurring
|
|
255
|
+
contention; preserving the provider outcome does not establish its lock holder.
|
|
256
|
+
|
|
257
|
+
Flare image buckets use a conservative local fallback of five requests per
|
|
258
|
+
minute when response headers omit capacity; this is an admission policy, not
|
|
259
|
+
an assertion about the account's provider tier. Observed headers remain authoritative.
|
|
260
|
+
An image attempt deferred before provider execution is finalized in the audit
|
|
261
|
+
trail rather than left pending. Queue owners retain durable waiting state separately.
|
|
262
|
+
Direct text, image and embedding HTTP rejections throw `AIRequestError` with
|
|
263
|
+
`code`, `status` and `requestId` when supplied; missing fields remain `null`.
|
|
264
|
+
These identifiers exclude the provider payload and inputs. Known quota codes
|
|
265
|
+
(`insufficient_quota`, `billing_hard_limit_reached`) and explicit “no credits
|
|
266
|
+
remaining” responses are terminal direct-call failures, including code-less
|
|
267
|
+
HTTP 429 responses. They do not become queue capacity deferrals. Ordinary
|
|
268
|
+
throttling still raises `AIRateLimitDeferredError`. Existing agent quota retry
|
|
269
|
+
and configured provider failover policies are separate from this direct-call path.
|
|
270
|
+
Capacity deferrals integrate with queue retries. The `allowance` hook
|
|
149
271
|
checks application budgets separately. Override `usageCharge()` and
|
|
150
272
|
`settleUsage()` in an agent when your app needs an idempotent commercial ledger.
|
|
151
273
|
|
|
274
|
+
## Provider account admission and recovery
|
|
275
|
+
|
|
276
|
+
`AIProviderAdmission` shares account availability through a dedicated existing
|
|
277
|
+
`ai_rate_limit_buckets` row. Its metadata is keyed by provider, normalized base
|
|
278
|
+
URL and a one-way key digest, across models/endpoints and workers. Separate API keys are separate identities even if the provider funds them from the same billing account; the framework cannot infer that relationship. Raw keys,
|
|
279
|
+
provider messages and prompts are never stored in this account state. Capacity
|
|
280
|
+
limiting can be disabled without disabling account admission.
|
|
281
|
+
|
|
282
|
+
Explicit `insufficient_quota`, `billing_hard_limit_reached` or “no credits
|
|
283
|
+
remaining” responses immediately stop the account. Ordinary 429 capacity stays
|
|
284
|
+
with the existing limiter. Network/timeouts/408/5xx and explicit overload/server
|
|
285
|
+
errors start one continuous outage episode. Explicit caller cancellation does not
|
|
286
|
+
trip an account outage or prove recovery; an existing recovery lease remains
|
|
287
|
+
bounded. This lets independently authorized cleanup and later runs continue. `ai.providerAdmission` configures
|
|
288
|
+
`initialSeconds` (30), `maxSeconds` (300), `failureWindowSeconds` (900) and
|
|
289
|
+
`recoveryLeaseSeconds` (request timeout plus 30). Values must be positive; the
|
|
290
|
+
recovery lease must exceed the request timeout. These conservative defaults
|
|
291
|
+
limit a fifteen-minute outage to a few real recovery attempts, without assuming
|
|
292
|
+
that credits will return automatically or using paid background probes.
|
|
293
|
+
|
|
294
|
+
After cooldown only one real waiting request owns recovery. A crash leaves a
|
|
295
|
+
bounded lease; generations and lease tokens prevent stale successes from
|
|
296
|
+
clearing a newer outage or credit stop. The fixed episode deadline also stops
|
|
297
|
+
newly dispatched jobs. Expired episodes and exhausted accounts remain stopped
|
|
298
|
+
across restarts. `AIProviderDeferredError` releases queue reservations without
|
|
299
|
+
spending a try; `AIProviderStoppedError` terminates immediately with a failed-job
|
|
300
|
+
record and normal final-failure hooks, even when more tries were configured.
|
|
301
|
+
After a completed model/tool turn, agents retry only the current model request
|
|
302
|
+
when the SDK has emitted no event for that request. The SDK retains completed
|
|
303
|
+
tools and exact current input, waits for shared admission, and allows at most
|
|
304
|
+
eight retries inside the existing fifteen-minute episode deadline. Each retry
|
|
305
|
+
reacquires capacity and exclusive recovery admission. Queue lease renewal remains
|
|
306
|
+
active while this bounded in-process wait occupies the worker; it is not a durable
|
|
307
|
+
checkpoint and a worker crash cannot promise continuation. Cancellation, exhausted
|
|
308
|
+
quota, stateful requests and any current-request SDK event veto this recovery.
|
|
309
|
+
Failures after such events still stop instead of replaying the whole agent.
|
|
310
|
+
Saved attempts and results remain.
|
|
311
|
+
Terminal errors expose `stopStage`: `quota` for exhausted admission, `deadline`
|
|
312
|
+
for expired outage admission, and `stream-output` for an individual run stopped
|
|
313
|
+
while the account may still be in cooldown. A streamed-output stop does not
|
|
314
|
+
establish that the account deadline elapsed or require resetting the account.
|
|
315
|
+
Observed deferrals carry recognized provider codes, rejection HTTP status and
|
|
316
|
+
bounded support request IDs into the terminal error; blocked siblings retain
|
|
317
|
+
unknown fields. Raw provider messages and payloads are not attached.
|
|
318
|
+
|
|
319
|
+
After independently repairing availability or credits, an authorized server
|
|
320
|
+
operator can select the configured account and reset its admission state:
|
|
321
|
+
|
|
322
|
+
```ts
|
|
323
|
+
const attempt = app().ai.resolveProviders()[0];
|
|
324
|
+
if (!attempt) throw new Error('No configured provider account.');
|
|
325
|
+
await app().ai.providerAdmission.reset(attempt);
|
|
326
|
+
```
|
|
327
|
+
|
|
328
|
+
This executes no HTTP, changes no key/model/billing setting and dispatches or
|
|
329
|
+
replays no job. Failed jobs require a separately authorized retry. The reset
|
|
330
|
+
must run on the deployed app/database with trusted server-side configuration;
|
|
331
|
+
never expose credentials or this operation to an unscoped client.
|
|
332
|
+
|
|
333
|
+
`generateEmbedding(..., { retainResult: true })` opts into retaining the completed
|
|
334
|
+
vector in the existing request response. Applications may use this for partial
|
|
335
|
+
workflow resume after authorizing scope and matching the exact full input/model.
|
|
336
|
+
Default audits still keep dimensions only. Retention/access remain app policy.
|
|
337
|
+
No new tables or migrations are required by this change.
|
|
338
|
+
|
|
152
339
|
## Verification
|
|
153
340
|
|
|
154
341
|
### Maintenance map
|
|
@@ -180,8 +367,26 @@ Framework maintainers run `npm run test:service --workspace @db3.ai/app -- ai`.
|
|
|
180
367
|
Tests use real App, SDK, SQL and Storage with synthetic provider responses. The
|
|
181
368
|
integration suite covers tools, history, ownership, queue reconstruction, nested
|
|
182
369
|
request parentage, failover, image storage, embeddings and structured output.
|
|
370
|
+
Limiter contention tests use disposable MariaDB and independent persisted-state
|
|
371
|
+
reads to verify deadlock recovery, retry exhaustion, cleanup and preservation of
|
|
372
|
+
provider success, rejection, deferral and transport failure. A real ambient
|
|
373
|
+
deadlock regression also verifies rollback of an earlier caller write, error
|
|
374
|
+
propagation and the absence of follow-up limiter queries in that transaction.
|
|
183
375
|
The package is also installed and type-checked in an independent consumer.
|
|
184
376
|
|
|
185
377
|
Installed app developers run their own tests using a disposable database and
|
|
186
378
|
an injected `ai.fetch`. No live key is needed for simulated provider tests.
|
|
187
379
|
See the [AI guides](https://db3.ai/docs/ai) for app-focused examples.
|
|
380
|
+
|
|
381
|
+
SSE recovery requires an explicit `response.completed` event or compatible
|
|
382
|
+
`[DONE]` marker, a complete event boundary and clean body EOF. The observer joins
|
|
383
|
+
multiline `data` fields and supports LF, CR and CRLF across arbitrary UTF-8 byte
|
|
384
|
+
fragments; it forwards original bytes unchanged. Malformed JSON, uncertain UTF-8,
|
|
385
|
+
oversized events, incomplete EOF and cancellation retain the bounded recovery
|
|
386
|
+
lease rather than asserting success. Retained lines/events are limited to one
|
|
387
|
+
MiB of decoded characters; oversized events are discarded only by the observer
|
|
388
|
+
until their blank boundary, and later valid quota events still stop the account.
|
|
389
|
+
|
|
390
|
+
### Optional request failure isolation
|
|
391
|
+
|
|
392
|
+
Text and structured calls may set `transientFailureScope: "request"` for optional work. Timeouts, transport failures and server errors then fail that request without opening the shared account outage circuit. Existing account admission stops and explicit quota exhaustion remain shared. Capacity limits, allowance checks and usage tracking still apply. This does not guarantee provider availability or remove the cost of a request.
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
import type { AIServiceTier } from './contracts/AIServiceTier';
|
|
2
|
+
import { AIConfigurationError } from './AIErrors';
|
|
3
|
+
|
|
4
|
+
/** Validates explicit tiers before provider work; other providers retain their own defaults. */
|
|
5
|
+
export function assertAIServiceTier(provider: string, tier: AIServiceTier): void {
|
|
6
|
+
if (!['default', 'flex', 'fast', 'priority'].includes(tier)) throw new AIConfigurationError('Unsupported AI service tier.');
|
|
7
|
+
if (provider !== 'openai' && tier !== 'default') throw new AIConfigurationError('Explicit AI service tiers require the OpenAI provider.');
|
|
8
|
+
}
|
|
9
|
+
|
|
10
|
+
/** Resolves billed tier without treating an unconfirmed Flex/Fast request as discounted usage. */
|
|
11
|
+
export function effectiveAIServiceTier(reported: unknown, requested: unknown): string | null {
|
|
12
|
+
if (typeof reported === 'string' && reported.length > 0) return reported;
|
|
13
|
+
return requested === undefined || requested === 'default' ? 'default' : null;
|
|
14
|
+
}
|
|
@@ -0,0 +1,137 @@
|
|
|
1
|
+
import { Tiktoken } from 'js-tiktoken/lite';
|
|
2
|
+
import cl100kBase from 'js-tiktoken/ranks/cl100k_base';
|
|
3
|
+
import type { EmbeddingTextChunk, EmbeddingTextChunkOptions } from './contracts/EmbeddingTextChunk';
|
|
4
|
+
|
|
5
|
+
let tokenizer: Tiktoken | undefined;
|
|
6
|
+
|
|
7
|
+
/** Counts ordinary text, including literal special-token spellings, with cl100k_base. */
|
|
8
|
+
function tokens(text: string): number {
|
|
9
|
+
tokenizer ??= new Tiktoken(cl100kBase);
|
|
10
|
+
return tokenizer.encode(text, [], []).length;
|
|
11
|
+
}
|
|
12
|
+
|
|
13
|
+
/**
|
|
14
|
+
* Keeps fitting documents whole and splits oversized Markdown at natural boundaries.
|
|
15
|
+
* Each passage retains source offsets, bounded shared context, its heading hierarchy
|
|
16
|
+
* and a small overlap. Uses cl100k_base, as used by text-embedding-3-small/large.
|
|
17
|
+
* No provider requests or generated summaries are involved.
|
|
18
|
+
*
|
|
19
|
+
* @param text - Extracted text or Markdown; HTML extraction belongs to the caller.
|
|
20
|
+
* @param options - Context and token budgets for the complete embedding input.
|
|
21
|
+
* @returns Ordered passages whose source ranges cover all of the original text.
|
|
22
|
+
* @example
|
|
23
|
+
* const chunks = chunkEmbeddingText(page.text, { context: `Title: ${page.title}` });
|
|
24
|
+
*/
|
|
25
|
+
export function chunkEmbeddingText(text: string, options: EmbeddingTextChunkOptions = {}): EmbeddingTextChunk[] {
|
|
26
|
+
const maximum = options.maxTokens ?? 8000;
|
|
27
|
+
const overlap = options.overlapTokens ?? Math.min(128, Math.floor(maximum / 8));
|
|
28
|
+
if (!Number.isInteger(maximum) || maximum < 64 || maximum > 8191) throw new Error('Embedding chunks require maxTokens between 64 and 8191.');
|
|
29
|
+
if (!Number.isInteger(overlap) || overlap < 0 || overlap >= maximum / 2) throw new Error('Embedding overlap must be non-negative and smaller than half the input budget.');
|
|
30
|
+
if (!text.trim()) return [];
|
|
31
|
+
const contextBudget = Math.min(512, Math.floor(maximum / 8));
|
|
32
|
+
const context = boundedPrefix(options.context?.trim() ?? '', contextBudget);
|
|
33
|
+
const headings = markdownHeadings(text);
|
|
34
|
+
const chunks: EmbeddingTextChunk[] = [];
|
|
35
|
+
const fullInput = embeddingInput(context, null, text);
|
|
36
|
+
if (tokens(fullInput) <= maximum) return [{ index: 0, text, heading: null, input: fullInput, start: 0, end: text.length, tokens: tokens(fullInput) }];
|
|
37
|
+
let start = 0;
|
|
38
|
+
let contentStart = 0;
|
|
39
|
+
while (start < text.length) {
|
|
40
|
+
const activeHeading = headings.filter(heading => heading.start <= contentStart).at(-1)?.title ?? null;
|
|
41
|
+
const heading = activeHeading ? boundedPrefix(activeHeading, contextBudget) : null;
|
|
42
|
+
const prefix = embeddingInput(context, heading, '');
|
|
43
|
+
const available = maximum - tokens(prefix) - 8;
|
|
44
|
+
let end = start + fittingPrefixLength(text.slice(start), available);
|
|
45
|
+
if (end < text.length) end = naturalBoundary(text, start, end, headings.map(item => item.start));
|
|
46
|
+
let input = embeddingInput(context, heading, text.slice(start, end));
|
|
47
|
+
// BPE merges across the prefix boundary are verified against the final input.
|
|
48
|
+
while (tokens(input) > maximum && end > start) {
|
|
49
|
+
end = previousCharacter(text, end);
|
|
50
|
+
input = embeddingInput(context, heading, text.slice(start, end));
|
|
51
|
+
}
|
|
52
|
+
if (end <= start) throw new Error('Embedding context leaves no room for source text.');
|
|
53
|
+
chunks.push({ index: chunks.length, text: text.slice(start, end), heading, input, start, end, tokens: tokens(input) });
|
|
54
|
+
if (end === text.length) break;
|
|
55
|
+
contentStart = end;
|
|
56
|
+
const previousText = text.slice(start, end);
|
|
57
|
+
const overlapStart = overlap ? fittingSuffixStart(previousText, overlap) + start : end;
|
|
58
|
+
// Prefer a whole final paragraph when it fits inside the overlap budget.
|
|
59
|
+
const paragraphStart = text.lastIndexOf('\n\n', end - 3) + 2;
|
|
60
|
+
start = paragraphStart >= overlapStart && paragraphStart < end && paragraphStart > start
|
|
61
|
+
? paragraphStart : overlapStart > start ? overlapStart : end;
|
|
62
|
+
}
|
|
63
|
+
return chunks;
|
|
64
|
+
}
|
|
65
|
+
|
|
66
|
+
/** Builds a deterministic context prefix without rewriting source evidence. */
|
|
67
|
+
function embeddingInput(context: string, heading: string | null, text: string): string {
|
|
68
|
+
return `${context ? `${context}\n` : ''}${heading ? `section: ${heading}\n` : ''}content:\n${text}`;
|
|
69
|
+
}
|
|
70
|
+
|
|
71
|
+
/** Finds a token-bounded prefix without cutting a Unicode code point. */
|
|
72
|
+
function fittingPrefixLength(text: string, maximum: number): number {
|
|
73
|
+
if (tokens(text) <= maximum) return text.length;
|
|
74
|
+
let low = 0;
|
|
75
|
+
let high = text.length;
|
|
76
|
+
while (low < high) {
|
|
77
|
+
const middle = Math.ceil((low + high) / 2);
|
|
78
|
+
if (tokens(text.slice(0, middle)) <= maximum) low = middle;
|
|
79
|
+
else high = middle - 1;
|
|
80
|
+
}
|
|
81
|
+
if (low > 0 && /[\uD800-\uDBFF]/.test(text[low - 1])) low -= 1;
|
|
82
|
+
return low;
|
|
83
|
+
}
|
|
84
|
+
|
|
85
|
+
/** Bounds repeated context so even unusually long metadata leaves room for source text. */
|
|
86
|
+
function boundedPrefix(text: string, maximum: number): string {
|
|
87
|
+
return text.slice(0, fittingPrefixLength(text, maximum)).trim();
|
|
88
|
+
}
|
|
89
|
+
|
|
90
|
+
/** Locates a bounded overlap suffix on Unicode code-point boundaries. */
|
|
91
|
+
function fittingSuffixStart(text: string, maximum: number): number {
|
|
92
|
+
let low = 0;
|
|
93
|
+
let high = text.length;
|
|
94
|
+
while (low < high) {
|
|
95
|
+
const middle = Math.floor((low + high) / 2);
|
|
96
|
+
if (tokens(text.slice(middle)) <= maximum) high = middle;
|
|
97
|
+
else low = middle + 1;
|
|
98
|
+
}
|
|
99
|
+
if (/[\uDC00-\uDFFF]/.test(text[low] ?? '')) low += 1;
|
|
100
|
+
return low;
|
|
101
|
+
}
|
|
102
|
+
|
|
103
|
+
/** Moves backwards by one Unicode code point. */
|
|
104
|
+
function previousCharacter(text: string, end: number): number {
|
|
105
|
+
return end > 1 && /[\uDC00-\uDFFF]/.test(text[end - 1]) ? end - 2 : end - 1;
|
|
106
|
+
}
|
|
107
|
+
|
|
108
|
+
/** Prefers a heading or paragraph boundary, then sentences and whitespace, without emitting tiny fragments. */
|
|
109
|
+
function naturalBoundary(text: string, start: number, end: number, headings: number[]): number {
|
|
110
|
+
const minimum = start + Math.floor((end - start) / 2);
|
|
111
|
+
const heading = headings.filter(position => position >= minimum && position <= end).at(-1);
|
|
112
|
+
if (heading !== undefined) return heading;
|
|
113
|
+
const candidate = text.slice(minimum, end);
|
|
114
|
+
for (const pattern of [/\n\s*\n/g, /[.!?。!?][\s]+/g, /\s+/g]) {
|
|
115
|
+
const match = [...candidate.matchAll(pattern)].at(-1);
|
|
116
|
+
if (match) return minimum + match.index! + match[0].length;
|
|
117
|
+
}
|
|
118
|
+
return end;
|
|
119
|
+
}
|
|
120
|
+
|
|
121
|
+
/** Reads Markdown heading ancestry while ignoring headings inside fenced code blocks. */
|
|
122
|
+
function markdownHeadings(text: string): Array<{ start: number; title: string }> {
|
|
123
|
+
const headings: Array<{ start: number; title: string }> = [];
|
|
124
|
+
const hierarchy: string[] = [];
|
|
125
|
+
let fence: string | null = null;
|
|
126
|
+
for (const line of text.matchAll(/^.*(?:\n|$)/gm)) {
|
|
127
|
+
const delimiter = line[0].match(/^\s*(`{3,}|~{3,})/)?.[1];
|
|
128
|
+
if (delimiter) { fence = fence ? (delimiter[0] === fence[0] ? null : fence) : delimiter; continue; }
|
|
129
|
+
if (fence) continue;
|
|
130
|
+
const heading = line[0].match(/^(#{1,6})\s+(.+?)(?:\s+#+)?\s*$/);
|
|
131
|
+
if (!heading) continue;
|
|
132
|
+
hierarchy.length = heading[1].length;
|
|
133
|
+
hierarchy[heading[1].length - 1] = heading[2];
|
|
134
|
+
headings.push({ start: line.index!, title: hierarchy.filter(Boolean).join(' > ') });
|
|
135
|
+
}
|
|
136
|
+
return headings;
|
|
137
|
+
}
|
package/src/ai/contracts/AI.ts
CHANGED
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
import type { AIServiceTier } from './AIServiceTier';
|
|
1
2
|
import type { TextResponsePayload } from '@db3.ai/pure';
|
|
2
3
|
import type { ZodType } from 'zod';
|
|
3
4
|
import type { AiConversation } from '../AiConversation.js';
|
|
@@ -140,6 +141,8 @@ export interface AIOptions {
|
|
|
140
141
|
fetch?: typeof fetch;
|
|
141
142
|
/** Rate limiter used before provider requests. Pass false only in isolated tests. */
|
|
142
143
|
rateLimiter?: AIRateLimiter | false;
|
|
144
|
+
/** Durable account admission policy; capacity limiter disabling never bypasses it. */
|
|
145
|
+
providerAdmission?: import('../AIProviderAdmission').AIProviderAdmissionOptions;
|
|
143
146
|
/** Optional customer allowance hook. Defaults to no-op until billing limits exist. */
|
|
144
147
|
allowance?: AIAllowanceChecker | false;
|
|
145
148
|
}
|
|
@@ -148,6 +151,10 @@ export interface AIOptions {
|
|
|
148
151
|
* Plain text request sent to the Responses API.
|
|
149
152
|
*/
|
|
150
153
|
export interface GenerateTextInput {
|
|
154
|
+
/** Keep transient failures local to optional work; account quota and existing admission stops still apply. */
|
|
155
|
+
transientFailureScope?: 'account' | 'request';
|
|
156
|
+
/** Explicit OpenAI processing tier; defaults to Standard. No automatic tier fallback. */
|
|
157
|
+
serviceTier?: AIServiceTier;
|
|
151
158
|
/** Optional per-call model override for the OpenAI provider entry. */
|
|
152
159
|
model?: string;
|
|
153
160
|
/** Optional provider failover chain overriding the app default for this call. */
|
|
@@ -224,6 +231,10 @@ export interface AIResponseLogOptions extends Record<string, unknown> {
|
|
|
224
231
|
|
|
225
232
|
/** Untrusted provider text response, including optional token usage. */
|
|
226
233
|
export interface TextResponsePayloadWithUsage extends TextResponsePayload {
|
|
234
|
+
/** Actual model reported by the provider for billing. */
|
|
235
|
+
model?: unknown;
|
|
236
|
+
/** Actual processing tier reported by OpenAI, not the requested tier. */
|
|
237
|
+
service_tier?: unknown;
|
|
227
238
|
/** Provider completion status; omitted by some compatible endpoints. */
|
|
228
239
|
status?: unknown;
|
|
229
240
|
usage?: unknown;
|
|
@@ -378,3 +389,9 @@ export interface AIModels {
|
|
|
378
389
|
request: typeof AiRequest;
|
|
379
390
|
message: typeof import('../AiMessage').AiMessage;
|
|
380
391
|
}
|
|
392
|
+
|
|
393
|
+
/** Embedding persistence policy for workflows that must resume partial provider work. */
|
|
394
|
+
export interface GenerateEmbeddingOptions extends RequestLogOptions {
|
|
395
|
+
/** Persist the completed vector in the existing request response for authorized resume. Defaults to false. */
|
|
396
|
+
retainResult?: boolean;
|
|
397
|
+
}
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Provider response identifiers retained on a direct AI request failure.
|
|
3
|
+
*
|
|
4
|
+
* These fields exclude response bodies, credentials and customer inputs. Missing
|
|
5
|
+
* fields stay unknown rather than inferring an HTTP status from an error message.
|
|
6
|
+
*/
|
|
7
|
+
export interface AIRequestErrorDiagnostics {
|
|
8
|
+
/** HTTP response status, when a provider response was received. */
|
|
9
|
+
status?: number | null;
|
|
10
|
+
/** Provider request identifier from response headers, for support correlation. */
|
|
11
|
+
requestId?: string | null;
|
|
12
|
+
}
|
|
@@ -3,6 +3,7 @@ import type { QueueJobId } from '@db3.ai/app/queue';
|
|
|
3
3
|
import type { SerializedValueEnvelope } from '@db3.ai/app/serialization';
|
|
4
4
|
import type { AiConversation } from '../AiConversation.js';
|
|
5
5
|
import type { AiRequest, AiRequestRunCostSummary } from '../AiRequest.js';
|
|
6
|
+
import type { AIServiceTier } from './AIServiceTier';
|
|
6
7
|
import type { AgentCitation } from '@db3.ai/pure';
|
|
7
8
|
|
|
8
9
|
export type { AgentCitation } from '@db3.ai/pure';
|
|
@@ -406,6 +407,8 @@ export interface BaseAgentContext {
|
|
|
406
407
|
* Serializable payload stored on the queue for deferred agent execution.
|
|
407
408
|
*/
|
|
408
409
|
export interface QueuedAgentRunPayload extends Record<string, unknown> {
|
|
410
|
+
/** Captured processing tier. Legacy payloads retain Standard processing. */
|
|
411
|
+
serviceTier?: AIServiceTier;
|
|
409
412
|
/**
|
|
410
413
|
* Registered agent name used for worker registration and queue observability.
|
|
411
414
|
*/
|
|
@@ -0,0 +1,26 @@
|
|
|
1
|
+
/** A source-backed passage prepared for the cl100k_base OpenAI embedding models. */
|
|
2
|
+
export interface EmbeddingTextChunk {
|
|
3
|
+
/** Zero-based position within this source revision. */
|
|
4
|
+
index: number;
|
|
5
|
+
/** Exact source slice, including any overlap with the preceding chunk. */
|
|
6
|
+
text: string;
|
|
7
|
+
/** Heading hierarchy active at the new source text, excluding preceding overlap. */
|
|
8
|
+
heading: string | null;
|
|
9
|
+
/** Complete provider input, with bounded source context and heading prefix. */
|
|
10
|
+
input: string;
|
|
11
|
+
/** UTF-16 offsets into the original text; end is exclusive. */
|
|
12
|
+
start: number;
|
|
13
|
+
end: number;
|
|
14
|
+
/** Token count of the complete input, including context and overlap. */
|
|
15
|
+
tokens: number;
|
|
16
|
+
}
|
|
17
|
+
|
|
18
|
+
/** Controls deterministic text preparation; callers retain extraction, storage and authorization. */
|
|
19
|
+
export interface EmbeddingTextChunkOptions {
|
|
20
|
+
/** Source title, description or other trusted context repeated on every passage. */
|
|
21
|
+
context?: string;
|
|
22
|
+
/** Complete input ceiling, including prefixes. Defaults to 8,000; cannot exceed 8,191. */
|
|
23
|
+
maxTokens?: number;
|
|
24
|
+
/** Maximum preceding text carried into the next passage. Defaults to 128 tokens. */
|
|
25
|
+
overlapTokens?: number;
|
|
26
|
+
}
|
|
@@ -5,13 +5,15 @@
|
|
|
5
5
|
* the rates. `outputUSDPer1M` is null for input-only models such as embeddings.
|
|
6
6
|
*/
|
|
7
7
|
export interface AIModelPricing {
|
|
8
|
+
/** Verified tier multipliers for this model only; absent tiers remain unpriced. */
|
|
9
|
+
serviceTierMultipliers?: Partial<Record<'flex' | 'fast' | 'priority', number>>;
|
|
8
10
|
inputUSDPer1M: number;
|
|
9
11
|
cachedInputUSDPer1M: number | null;
|
|
10
12
|
outputUSDPer1M: number | null;
|
|
11
13
|
/**
|
|
12
14
|
* Multiplier applied to input tokens written into the provider prompt cache.
|
|
13
15
|
*
|
|
14
|
-
* GPT-5.6 and GPT-6
|
|
16
|
+
* GPT-5.6 and GPT-6 models report cache writes separately and bill them above
|
|
15
17
|
* the ordinary uncached input rate. Models without that charge omit it.
|
|
16
18
|
*/
|
|
17
19
|
cacheWriteInputMultiplier?: number;
|
|
@@ -47,6 +49,8 @@ export interface AIImageModelPricing {
|
|
|
47
49
|
* Normalized token counts captured from a tracked AI provider response.
|
|
48
50
|
*/
|
|
49
51
|
export interface AIRequestCostUsage {
|
|
52
|
+
/** Actual provider tier. Undefined retains legacy Standard; null means unknown. */
|
|
53
|
+
serviceTier?: string | null;
|
|
50
54
|
inputTokens: number | null;
|
|
51
55
|
outputTokens: number | null;
|
|
52
56
|
cachedTokens?: number | null;
|
|
@@ -58,6 +62,8 @@ export interface AIRequestCostUsage {
|
|
|
58
62
|
* Per-provider-request usage retained from an aggregate Agents SDK run.
|
|
59
63
|
*/
|
|
60
64
|
export interface AIRequestCostUsageEntry extends AIRequestCostUsage {
|
|
65
|
+
/** Actual provider model, when supplied with this completed response. */
|
|
66
|
+
model?: string;
|
|
61
67
|
/** Provider endpoint that reported this usage entry, when available. */
|
|
62
68
|
endpoint?: string;
|
|
63
69
|
}
|
|
@@ -23,6 +23,8 @@ export interface AIProviderConfig {
|
|
|
23
23
|
* One resolved, fully configured provider attempt in a failover chain.
|
|
24
24
|
*/
|
|
25
25
|
export interface AIProviderAttempt {
|
|
26
|
+
/** Optional work isolates transient transport failures; quota and existing account stops remain shared. */
|
|
27
|
+
transientFailureScope?: 'account' | 'request';
|
|
26
28
|
/** Stable provider id persisted on tracking rows and bucket keys. */
|
|
27
29
|
provider: AIProvider;
|
|
28
30
|
/** Model sent to this provider. */
|
|
@@ -1,4 +1,5 @@
|
|
|
1
1
|
export * from './AI';
|
|
2
|
+
export * from './EmbeddingTextChunk';
|
|
2
3
|
export * from './Agent';
|
|
3
4
|
export * from './AiRequestRunCostSummary';
|
|
4
5
|
export * from './Pricing';
|
|
@@ -6,3 +7,4 @@ export * from './Providers';
|
|
|
6
7
|
export * from './RateLimits';
|
|
7
8
|
export * from './ResponsesProviderCall';
|
|
8
9
|
export * from './QuotaRetry';
|
|
10
|
+
export type { AIRequestErrorDiagnostics } from './AIRequestErrorDiagnostics';
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
import { chunkEmbeddingText, type Ai } from '@db3.ai/app/ai';
|
|
2
|
+
|
|
3
|
+
/**
|
|
4
|
+
* Prepares source-backed passages before making tracked embedding requests.
|
|
5
|
+
* The application supplies its configured AI service and publishes the returned
|
|
6
|
+
* collection only if the original source revision is still current.
|
|
7
|
+
*
|
|
8
|
+
* @param ai - Application AI service with its provider and allowance policy.
|
|
9
|
+
* @param text - Extracted source text or Markdown, without raw HTML.
|
|
10
|
+
* @param title - Source title repeated as context on every passage.
|
|
11
|
+
* @returns Ordered passages with their vectors, model and request identifiers.
|
|
12
|
+
*/
|
|
13
|
+
export async function prepareDocumentEmbeddings(ai: Ai, text: string, title: string) {
|
|
14
|
+
const results = [];
|
|
15
|
+
for (const chunk of chunkEmbeddingText(text, { context: `title: ${title}` })) {
|
|
16
|
+
const embedding = await ai.generateEmbedding(chunk.input);
|
|
17
|
+
results.push({ chunk, ...embedding });
|
|
18
|
+
}
|
|
19
|
+
return results;
|
|
20
|
+
}
|