UNPKG

capsule-ai-cli

Version:

The AI Model Orchestrator - Intelligent multi-model workflows with device-locked licensing

104 lines 4.42 kB
import { BaseProvider } from './base.js'; import { authService } from '../services/auth.js'; import { analyticsService } from '../services/analytics.js'; import chalk from 'chalk'; export class ManagedProvider extends BaseProvider { name; models = []; supportsStreaming = true; supportsTools = true; userProvider; capsuleProvider; providerName; constructor(providerName, userProvider, capsuleProvider) { super('managed', undefined); this.providerName = providerName; this.name = providerName; this.userProvider = userProvider; this.capsuleProvider = capsuleProvider; if (userProvider) { this.models = userProvider.models; this.supportsStreaming = userProvider.supportsStreaming; this.supportsTools = userProvider.supportsTools; } else if (capsuleProvider) { this.models = capsuleProvider.models; this.supportsStreaming = capsuleProvider.supportsStreaming; this.supportsTools = capsuleProvider.supportsTools; } } async complete(messages, options) { const auth = await authService.getStatus(); if (auth.tier === 'super' && auth.remainingRUs && auth.remainingRUs > 0 && this.capsuleProvider) { try { console.log(chalk.gray(`Using Capsule managed API (${auth.remainingRUs} RUs remaining)`)); const response = await this.capsuleProvider.complete(messages, options); await authService.deductRUs(response.usage); const cost = this.calculateCost(response.usage); await analyticsService.trackCompletion(this.providerName, options?.model || this.models[0], response.usage, cost); return response; } catch (error) { if (error.message.includes('Insufficient RUs') || error.message.includes('402')) { console.log(chalk.yellow('RUs exhausted, falling back to your API keys...')); } else { throw error; } } } if (!this.userProvider) { throw new Error(`Please provide your ${this.providerName} API key:\n` + `capsule config set providers.${this.providerName}.apiKey YOUR_KEY`); } const response = await this.userProvider.complete(messages, options); const cost = this.calculateCost(response.usage); await analyticsService.trackCompletion(this.providerName, options?.model || this.models[0], response.usage, cost); return response; } async *stream(messages, options) { const auth = await authService.getStatus(); if (auth.tier === 'super' && auth.remainingRUs && auth.remainingRUs > 0 && this.capsuleProvider) { try { console.log(chalk.gray(`Using Capsule managed API (${auth.remainingRUs} RUs remaining)`)); let totalTokens = 0; for await (const chunk of this.capsuleProvider.stream(messages, options)) { totalTokens += chunk.usage?.totalTokens || 0; yield chunk; } await authService.deductRUs({ totalTokens }); return; } catch (error) { if (error.message.includes('Insufficient RUs') || error.message.includes('402')) { console.log(chalk.yellow('RUs exhausted, falling back to your API keys...')); } else { throw error; } } } if (!this.userProvider) { throw new Error(`Please provide your ${this.providerName} API key:\n` + `capsule config set providers.${this.providerName}.apiKey YOUR_KEY`); } yield* this.userProvider.stream(messages, options); } calculateCost(usage, model) { if (this.userProvider) { return this.userProvider.calculateCost(usage, model); } else if (this.capsuleProvider) { return this.capsuleProvider.calculateCost(usage, model); } return { amount: 0, currency: 'USD', breakdown: { prompt: 0, completion: 0 } }; } } //# sourceMappingURL=managed.js.map