import { BaseHttpClient } from './BaseHttpClient'; import { ApiRespProviderRequesters, ApiRespProviderRequester, ApiRespProviderLLMModels, ApiRespProviderLLMModel, LLMModel, ApiRespPipelines, Pipeline, ApiRespPlatformAdapters, ApiRespPlatformAdapter, ApiRespPlatformBots, ApiRespPlatformBot, Bot, ApiRespPlugins, ApiRespPlugin, ApiRespPluginConfig, AsyncTaskCreatedResp, ApiRespSystemInfo, ApiRespAsyncTasks, ApiRespUserToken, GetPipelineResponseData, GetPipelineMetadataResponseData, AsyncTask, ApiRespWebChatMessages, ApiRespKnowledgeBases, ApiRespKnowledgeBase, KnowledgeBase, ApiRespKnowledgeBaseFiles, ApiRespKnowledgeBaseRetrieve, ApiRespProviderEmbeddingModels, ApiRespProviderEmbeddingModel, EmbeddingModel, ApiRespProviderRerankModels, ApiRespProviderRerankModel, RerankModel, ApiRespPluginSystemStatus, ApiRespBoxStatus, BoxSessionInfo, ApiRespMCPServers, ApiRespMCPServer, MCPServer, ApiRespModelProviders, ApiRespModelProvider, ApiRespScannedProviderModels, ModelProvider, ApiRespKnowledgeEngines, ApiRespParsers, RagMigrationStatusResp, ApiRespTools, ApiRespToolDetail, Skill, ApiRespSkills, ApiRespSkill, } from '@/app/infra/entities/api'; import { Plugin } from '@/app/infra/entities/plugin'; import { GetBotLogsRequest } from '@/app/infra/http/requestParam/bots/GetBotLogsRequest'; import { GetBotLogsResponse } from '@/app/infra/http/requestParam/bots/GetBotLogsResponse'; /** * 后端服务客户端 * 负责与后端 API 的所有交互 */ export class BackendClient extends BaseHttpClient { constructor(baseURL: string) { super(baseURL, false); } // ============ Provider API ============ public getProviderRequesters( model_type?: string, ): Promise { return this.get('/api/v1/provider/requesters', { type: model_type }); } public getProviderRequester(name: string): Promise { return this.get(`/api/v1/provider/requesters/${name}`); } public getProviderRequesterIconURL(name: string): string { if (this.instance.defaults.baseURL === '/') { const url = window.location.href; const baseURL = url.split('/').slice(0, 3).join('/'); return `${baseURL}/api/v1/provider/requesters/${name}/icon`; } return ( this.instance.defaults.baseURL + `/api/v1/provider/requesters/${name}/icon` ); } // ============ Model Providers ============ public getModelProviders(): Promise { return this.get('/api/v1/provider/providers'); } public getModelProvider(uuid: string): Promise { return this.get(`/api/v1/provider/providers/${uuid}`); } public createModelProvider( provider: Omit, ): Promise<{ uuid: string }> { return this.post('/api/v1/provider/providers', provider); } public updateModelProvider( uuid: string, provider: Partial, ): Promise { return this.put(`/api/v1/provider/providers/${uuid}`, provider); } public deleteModelProvider(uuid: string): Promise { return this.delete(`/api/v1/provider/providers/${uuid}`); } public scanProviderModels( uuid: string, modelType?: 'llm' | 'embedding' | 'rerank', ): Promise { const params = modelType ? { type: modelType } : {}; return this.get(`/api/v1/provider/providers/${uuid}/scan-models`, params); } // ============ Provider Model LLM ============ public getProviderLLMModels( providerUuid?: string, ): Promise { const params = providerUuid ? { provider_uuid: providerUuid } : {}; return this.get('/api/v1/provider/models/llm', params); } public getProviderLLMModel(uuid: string): Promise { return this.get(`/api/v1/provider/models/llm/${uuid}`); } public createProviderLLMModel(model: LLMModel): Promise { return this.post('/api/v1/provider/models/llm', model); } public deleteProviderLLMModel(uuid: string): Promise { return this.delete(`/api/v1/provider/models/llm/${uuid}`); } public updateProviderLLMModel( uuid: string, model: LLMModel, ): Promise { return this.put(`/api/v1/provider/models/llm/${uuid}`, model); } public testLLMModel(uuid: string, model: LLMModel): Promise { return this.post(`/api/v1/provider/models/llm/${uuid}/test`, model); } // ============ Provider Model Embedding ============ public getProviderEmbeddingModels( providerUuid?: string, ): Promise { const params = providerUuid ? { provider_uuid: providerUuid } : {}; return this.get('/api/v1/provider/models/embedding', params); } public getProviderEmbeddingModel( uuid: string, ): Promise { return this.get(`/api/v1/provider/models/embedding/${uuid}`); } public createProviderEmbeddingModel(model: EmbeddingModel): Promise { return this.post('/api/v1/provider/models/embedding', model); } public deleteProviderEmbeddingModel(uuid: string): Promise { return this.delete(`/api/v1/provider/models/embedding/${uuid}`); } public updateProviderEmbeddingModel( uuid: string, model: EmbeddingModel, ): Promise { return this.put(`/api/v1/provider/models/embedding/${uuid}`, model); } public testEmbeddingModel( uuid: string, model: EmbeddingModel, ): Promise { return this.post(`/api/v1/provider/models/embedding/${uuid}/test`, model); } // ============ Provider Model Rerank ============ public getProviderRerankModels( providerUuid?: string, ): Promise { const params = providerUuid ? { provider_uuid: providerUuid } : {}; return this.get('/api/v1/provider/models/rerank', params); } public getProviderRerankModel( uuid: string, ): Promise { return this.get(`/api/v1/provider/models/rerank/${uuid}`); } public createProviderRerankModel(model: RerankModel): Promise { return this.post('/api/v1/provider/models/rerank', model); } public deleteProviderRerankModel(uuid: string): Promise { return this.delete(`/api/v1/provider/models/rerank/${uuid}`); } public updateProviderRerankModel( uuid: string, model: RerankModel, ): Promise { return this.put(`/api/v1/provider/models/rerank/${uuid}`, model); } public testRerankModel(uuid: string, model: RerankModel): Promise { return this.post(`/api/v1/provider/models/rerank/${uuid}/test`, model); } // ============ Pipeline API ============ public getGeneralPipelineMetadata(): Promise { // as designed, this method will be deprecated, and only for developer to check the prefered config schema return this.get('/api/v1/pipelines/_/metadata'); } public getPipelines( sortBy?: string, sortOrder?: string, ): Promise { const params = new URLSearchParams(); if (sortBy) params.append('sort_by', sortBy); if (sortOrder) params.append('sort_order', sortOrder); const queryString = params.toString(); return this.get(`/api/v1/pipelines${queryString ? `?${queryString}` : ''}`); } public getPipeline(uuid: string): Promise { return this.get(`/api/v1/pipelines/${uuid}`); } public createPipeline(pipeline: Pipeline): Promise<{ uuid: string; }> { return this.post('/api/v1/pipelines', pipeline); } public updatePipeline(uuid: string, pipeline: Pipeline): Promise { return this.put(`/api/v1/pipelines/${uuid}`, pipeline); } public deletePipeline(uuid: string): Promise { return this.delete(`/api/v1/pipelines/${uuid}`); } public copyPipeline(uuid: string): Promise<{ uuid: string }> { return this.post(`/api/v1/pipelines/${uuid}/copy`); } public getPipelineExtensions(uuid: string): Promise<{ enable_all_plugins: boolean; enable_all_mcp_servers: boolean; enable_all_skills: boolean; bound_plugins: Array<{ author: string; name: string }>; available_plugins: Plugin[]; bound_mcp_servers: string[]; available_mcp_servers: MCPServer[]; bound_skills: string[]; available_skills: Skill[]; }> { return this.get(`/api/v1/pipelines/${uuid}/extensions`); } public updatePipelineExtensions( uuid: string, bound_plugins: Array<{ author: string; name: string }>, bound_mcp_servers: string[], enable_all_plugins: boolean = true, enable_all_mcp_servers: boolean = true, bound_skills: string[] = [], enable_all_skills: boolean = true, ): Promise { return this.put(`/api/v1/pipelines/${uuid}/extensions`, { bound_plugins, bound_mcp_servers, enable_all_plugins, enable_all_mcp_servers, bound_skills, enable_all_skills, }); } // ============ WebSocket Chat API ============ public getWebSocketHistoryMessages( pipelineId: string, sessionType: string, ): Promise { return this.get( `/api/v1/pipelines/${pipelineId}/ws/messages/${sessionType}`, ); } public async uploadWebSocketImage( pipelineId: string, imageFile: File, ): Promise<{ file_key: string }> { const formData = new FormData(); formData.append('file', imageFile); return this.postFile(`/api/v1/files/images`, formData); } public resetWebSocketSession( pipelineId: string, sessionType: string, ): Promise<{ message: string }> { return this.post(`/api/v1/pipelines/${pipelineId}/ws/reset/${sessionType}`); } public getWebSocketConnections(pipelineId: string): Promise<{ stats: { total_connections: number; pipelines: number; connections_by_pipeline: Record; connections_by_session_type: Record; }; connections: Array<{ connection_id: string; session_type: string; created_at: string; last_active: string; is_active: boolean; }>; }> { return this.get(`/api/v1/pipelines/${pipelineId}/ws/connections`); } public broadcastWebSocketMessage( pipelineId: string, message: string, ): Promise<{ message: string }> { return this.post(`/api/v1/pipelines/${pipelineId}/ws/broadcast`, { message, }); } // ============ Platform API ============ public getAdapters(): Promise { return this.get('/api/v1/platform/adapters'); } public getAdapter(name: string): Promise { return this.get(`/api/v1/platform/adapters/${name}`); } public getAdapterIconURL(name: string): string { if (this.instance.defaults.baseURL === '/') { // 获取用户访问的URL const url = window.location.href; const baseURL = url.split('/').slice(0, 3).join('/'); return `${baseURL}/api/v1/platform/adapters/${name}/icon`; } return ( this.instance.defaults.baseURL + `/api/v1/platform/adapters/${name}/icon` ); } // ============ Platform Bots ============ public getBots(): Promise { return this.get('/api/v1/platform/bots'); } public getBot(uuid: string): Promise { return this.get(`/api/v1/platform/bots/${uuid}`); } public createBot(bot: Bot): Promise<{ uuid: string }> { return this.post('/api/v1/platform/bots', bot); } public updateBot(uuid: string, bot: Bot): Promise { return this.put(`/api/v1/platform/bots/${uuid}`, bot); } public deleteBot(uuid: string): Promise { return this.delete(`/api/v1/platform/bots/${uuid}`); } public getBotLogs( botId: string, request: GetBotLogsRequest, ): Promise { return this.post(`/api/v1/platform/bots/${botId}/logs`, request); } public getBotSessions( botId: string, limit: number = 100, offset: number = 0, ): Promise<{ sessions: Array<{ session_id: string; bot_id: string; bot_name: string; pipeline_id: string; pipeline_name: string; message_count: number; start_time: string; last_activity: string; is_active: boolean; platform: string | null; user_id: string | null; user_name: string | null; }>; total: number; }> { const queryParams = new URLSearchParams(); queryParams.append('botId', botId); queryParams.append('limit', limit.toString()); queryParams.append('offset', offset.toString()); return this.get(`/api/v1/monitoring/sessions?${queryParams.toString()}`); } public getSessionMessages( sessionId: string, limit: number = 200, offset: number = 0, ): Promise<{ messages: Array<{ id: string; timestamp: string; bot_id: string; bot_name: string; pipeline_id: string; pipeline_name: string; message_content: string; session_id: string; status: string; level: string; platform: string | null; user_id: string | null; user_name: string | null; runner_name: string | null; variables: string | null; role: string | null; }>; total: number; }> { const queryParams = new URLSearchParams(); queryParams.append('sessionId', sessionId); queryParams.append('limit', limit.toString()); queryParams.append('offset', offset.toString()); return this.get(`/api/v1/monitoring/messages?${queryParams.toString()}`); } // ============ File management API ============ public uploadDocumentFile(file: File): Promise<{ file_id: string }> { const formData = new FormData(); formData.append('file', file); return this.request<{ file_id: string }>({ method: 'post', url: '/api/v1/files/documents', data: formData, headers: { 'Content-Type': 'multipart/form-data', }, }); } // ============ Knowledge Base API ============ public getKnowledgeBases(): Promise { return this.get('/api/v1/knowledge/bases'); } public getKnowledgeBase(uuid: string): Promise { return this.get(`/api/v1/knowledge/bases/${uuid}`); } public createKnowledgeBase(base: KnowledgeBase): Promise<{ uuid: string }> { return this.post('/api/v1/knowledge/bases', base); } public updateKnowledgeBase( uuid: string, base: KnowledgeBase, ): Promise<{ uuid: string }> { return this.put(`/api/v1/knowledge/bases/${uuid}`, base); } public uploadKnowledgeBaseFile( uuid: string, file_id: string, parserPluginId?: string, ): Promise { return this.post(`/api/v1/knowledge/bases/${uuid}/files`, { file_id, parser_plugin_id: parserPluginId, }); } public getKnowledgeBaseFiles( uuid: string, ): Promise { return this.get(`/api/v1/knowledge/bases/${uuid}/files`); } public deleteKnowledgeBaseFile( uuid: string, file_id: string, ): Promise { return this.delete(`/api/v1/knowledge/bases/${uuid}/files/${file_id}`); } public deleteKnowledgeBase(uuid: string): Promise { return this.delete(`/api/v1/knowledge/bases/${uuid}`); } public retrieveKnowledgeBase( uuid: string, query: string, retrievalSettings?: Record, ): Promise { return this.post(`/api/v1/knowledge/bases/${uuid}/retrieve`, { query, retrieval_settings: retrievalSettings ?? {}, }); } // ============ Knowledge Engines API ============ public getKnowledgeEngines(): Promise { return this.get('/api/v1/knowledge/engines'); } // ============ Parsers API ============ public listParsers(mimeType?: string): Promise { const params = mimeType ? `?mime_type=${encodeURIComponent(mimeType)}` : ''; return this.get(`/api/v1/knowledge/parsers${params}`); } // ============ Plugins API ============ public getPlugins(): Promise { return this.get('/api/v1/plugins'); } public getPlugin(author: string, name: string): Promise { return this.get(`/api/v1/plugins/${author}/${name}`); } public getPluginConfig( author: string, name: string, ): Promise { return this.get(`/api/v1/plugins/${author}/${name}/config`); } public updatePluginConfig( author: string, name: string, config: object, ): Promise { return this.put(`/api/v1/plugins/${author}/${name}/config`, config); } public uploadPluginConfigFile(file: File): Promise<{ file_key: string }> { const formData = new FormData(); formData.append('file', file); return this.request<{ file_key: string }>({ method: 'post', url: '/api/v1/plugins/config-files', data: formData, headers: { 'Content-Type': 'multipart/form-data', }, }); } public deletePluginConfigFile( fileKey: string, ): Promise<{ deleted: boolean }> { return this.delete(`/api/v1/plugins/config-files/${fileKey}`); } public getPluginReadme( author: string, name: string, language: string = 'en', ): Promise<{ readme: string }> { return this.get( `/api/v1/plugins/${author}/${name}/readme?language=${language}`, ); } public getPluginAssetURL( author: string, name: string, filepath: string, ): string { return ( this.instance.defaults.baseURL + `/api/v1/plugins/${author}/${name}/assets/${filepath}` ); } public async pluginPageApi( author: string, name: string, pageId: string, endpoint: string, method: string = 'POST', body?: unknown, ): Promise { const resp = await this.instance.request({ url: `/api/v1/plugins/${author}/${name}/page-api`, method: 'POST', data: { page_id: pageId, endpoint, method, body, }, }); return resp.data?.data; } public getPluginIconURL(author: string, name: string): string { if (this.instance.defaults.baseURL === '/') { const url = window.location.href; const baseURL = url.split('/').slice(0, 3).join('/'); return `${baseURL}/api/v1/plugins/${author}/${name}/icon`; } return ( this.instance.defaults.baseURL + `/api/v1/plugins/${author}/${name}/icon` ); } public installPluginFromGithub( assetUrl: string, owner: string, repo: string, releaseTag: string, ): Promise { return this.post('/api/v1/plugins/install/github', { asset_url: assetUrl, owner, repo, release_tag: releaseTag, }); } public getGithubReleases(repoUrl: string): Promise<{ releases: Array<{ id: number; tag_name: string; name: string; published_at: string; prerelease: boolean; draft: boolean; source_type?: 'release' | 'tag' | 'branch'; archive_url?: string; }>; owner: string; repo: string; source_subdir?: string; }> { return this.post('/api/v1/plugins/github/releases', { repo_url: repoUrl }); } public getGithubReleaseAssets( owner: string, repo: string, releaseId: number, releaseTag?: string, sourceType?: 'release' | 'tag' | 'branch', archiveUrl?: string, ): Promise<{ assets: Array<{ id: number; name: string; size: number; download_url: string; content_type: string; }>; }> { return this.post('/api/v1/plugins/github/release-assets', { owner, repo, release_id: releaseId, release_tag: releaseTag, source_type: sourceType, archive_url: archiveUrl, }); } public installPluginFromLocal(file: File): Promise { const formData = new FormData(); formData.append('file', file); return this.postFile('/api/v1/plugins/install/local', formData); } // ============ Skill Install API ============ public installSkillFromGithub( assetUrl: string, owner: string, repo: string, releaseTag: string, sourcePaths?: string[], sourceSubdir?: string, ): Promise { return this.post('/api/v1/skills/install/github', { asset_url: assetUrl, owner, repo, release_tag: releaseTag, source_paths: sourcePaths, source_subdir: sourceSubdir, }); } public previewSkillInstallFromGithub( assetUrl: string, owner: string, repo: string, releaseTag: string, sourceSubdir?: string, ): Promise<{ skills: Skill[] }> { return this.post('/api/v1/skills/install/github/preview', { asset_url: assetUrl, owner, repo, release_tag: releaseTag, source_subdir: sourceSubdir, }); } public previewSkillInstallFromUpload( file: File, ): Promise<{ skills: Skill[] }> { const formData = new FormData(); formData.append('file', file); return this.postFile('/api/v1/skills/install/upload/preview', formData); } public installSkillFromUpload( file: File, sourcePaths?: string[], ): Promise { const formData = new FormData(); formData.append('file', file); for (const sourcePath of sourcePaths || []) { formData.append('source_paths', sourcePath); } return this.postFile('/api/v1/skills/install/upload', formData); } public installPluginFromMarketplace( author: string, name: string, version: string, ): Promise { return this.post('/api/v1/plugins/install/marketplace', { plugin_author: author, plugin_name: name, plugin_version: version, }); } public removePlugin( author: string, name: string, deleteData: boolean = false, ): Promise { return this.delete( `/api/v1/plugins/${author}/${name}?delete_data=${deleteData}`, ); } public upgradePlugin( author: string, name: string, ): Promise { return this.post(`/api/v1/plugins/${author}/${name}/upgrade`); } // ============ MCP API ============ public getMCPServers(): Promise { return this.get('/api/v1/mcp/servers'); } // ========== Tools ========== public getTools(): Promise { return this.get('/api/v1/tools'); } public getToolDetail(toolName: string): Promise { return this.get(`/api/v1/tools/${toolName}`); } public getMCPServer(serverName: string): Promise { return this.get(`/api/v1/mcp/servers/${encodeURIComponent(serverName)}`); } public createMCPServer(server: MCPServer): Promise { return this.post('/api/v1/mcp/servers', server); } public updateMCPServer( serverName: string, server: Partial, ): Promise { return this.put(`/api/v1/mcp/servers/${encodeURIComponent(serverName)}`, server); } public deleteMCPServer(serverName: string): Promise { return this.delete(`/api/v1/mcp/servers/${encodeURIComponent(serverName)}`); } public toggleMCPServer( serverName: string, target_enabled: boolean, ): Promise { return this.put(`/api/v1/mcp/servers/${encodeURIComponent(serverName)}`, { enable: target_enabled, }); } public testMCPServer( serverName: string, serverData: object, ): Promise { return this.post(`/api/v1/mcp/servers/${encodeURIComponent(serverName)}/test`, serverData); } public installMCPServerFromGithub( source: string, ): Promise { return this.post('/api/v1/mcp/install/github', { source }); } public installMCPServerFromSSE( source: object, ): Promise { return this.post('/api/v1/mcp/servers', { source }); } // ============ System API ============ public getSystemInfo(): Promise { return this.get('/api/v1/system/info'); } public updateWizardStatus(status: 'skipped' | 'completed'): Promise { return this.post('/api/v1/system/wizard/completed', { status }); } public saveWizardProgress(progress: { step: number; selected_adapter: string | null; created_bot_uuid: string | null; bot_saved: boolean; selected_runner: string | null; }): Promise { return this.put('/api/v1/system/wizard/progress', progress); } public getAsyncTasks(params?: { type?: string; kind?: string; }): Promise { const query = new URLSearchParams(); if (params?.type) query.set('type', params.type); if (params?.kind) query.set('kind', params.kind); const qs = query.toString(); return this.get(`/api/v1/system/tasks${qs ? `?${qs}` : ''}`); } public getAsyncTask(id: number): Promise { return this.get(`/api/v1/system/tasks/${id}`); } public getPluginSystemStatus(): Promise { return this.get('/api/v1/system/status/plugin-system'); } // ============ RAG Migration API ============ public getRagMigrationStatus(): Promise { return this.get('/api/v1/knowledge/migration/status'); } public executeRagMigration( installPlugin: boolean = true, ): Promise { return this.post('/api/v1/knowledge/migration/execute', { install_plugin: installPlugin, }); } public dismissRagMigration(): Promise { return this.post('/api/v1/knowledge/migration/dismiss'); } public getPluginDebugInfo(): Promise<{ debug_url: string; plugin_debug_key: string; }> { return this.get('/api/v1/plugins/debug-info'); } public getBoxStatus(): Promise { return this.get('/api/v1/box/status'); } public getBoxSessions(): Promise { return this.get('/api/v1/box/sessions'); } // ============ User API ============ public checkIfInited(): Promise<{ initialized: boolean }> { return this.get('/api/v1/user/init'); } public initUser(user: string, password: string): Promise { return this.post('/api/v1/user/init', { user, password }); } public authUser(user: string, password: string): Promise { return this.post('/api/v1/user/auth', { user, password }); } public checkUserToken(): Promise { return this.get('/api/v1/user/check-token'); } public resetPassword( user: string, recoveryKey: string, newPassword: string, ): Promise<{ user: string }> { return this.post('/api/v1/user/reset-password', { user, recovery_key: recoveryKey, new_password: newPassword, }); } public changePassword( currentPassword: string, newPassword: string, ): Promise<{ user: string }> { return this.post('/api/v1/user/change-password', { current_password: currentPassword, new_password: newPassword, }); } public getUserInfo(): Promise<{ user: string; account_type: 'local' | 'space'; has_password: boolean; }> { return this.get('/api/v1/user/info'); } public getSpaceCredits(): Promise<{ credits: number | null }> { return this.get('/api/v1/user/space-credits'); } public getAccountInfo(): Promise<{ initialized: boolean; account_type?: 'local' | 'space'; has_password?: boolean; }> { return this.get('/api/v1/user/account-info'); } public setPassword( newPassword: string, currentPassword?: string, ): Promise<{ user: string }> { return this.post('/api/v1/user/set-password', { new_password: newPassword, current_password: currentPassword, }); } public async bindSpaceAccount( code: string, state: string, ): Promise<{ token: string; user: string; account_type: 'local' | 'space'; }> { const response = await this.instance.post('/api/v1/user/bind-space', { code, state, }); if (response.data.code !== 0) { throw { code: response.data.code, msg: response.data.msg || 'Unknown error', }; } return response.data.data; } // ============ Space OAuth API (Redirect Flow) ============ public getSpaceAuthorizeUrl( redirectUri: string, state?: string, ): Promise<{ authorize_url: string; }> { const params: Record = { redirect_uri: redirectUri }; if (state) { params.state = state; } return this.get('/api/v1/user/space/authorize-url', params); } public async exchangeSpaceOAuthCode(code: string): Promise<{ token: string; user: string; }> { const response = await this.instance.post('/api/v1/user/space/callback', { code, }); if (response.data.code !== 0) { throw { code: response.data.code, msg: response.data.msg || 'Unknown error', }; } return response.data.data; } // ============ Monitoring API ============ public getMonitoringData(params: { botId?: string[]; pipelineId?: string[]; startTime?: string; endTime?: string; limit?: number; }): Promise<{ overview: { total_messages: number; llm_calls: number; embedding_calls: number; model_calls: number; success_rate: number; active_sessions: number; }; messages: Array<{ id: string; timestamp: string; bot_id: string; bot_name: string; pipeline_id: string; pipeline_name: string; message_content: string; session_id: string; status: string; level: string; platform?: string; user_id?: string; runner_name?: string; variables?: string; }>; llmCalls: Array<{ id: string; timestamp: string; model_name: string; input_tokens: number; output_tokens: number; total_tokens: number; duration: number; cost?: number; status: string; bot_id: string; bot_name: string; pipeline_id: string; pipeline_name: string; error_message?: string; message_id?: string; }>; embeddingCalls: Array<{ id: string; timestamp: string; model_name: string; prompt_tokens: number; total_tokens: number; duration: number; input_count: number; status: string; error_message?: string; knowledge_base_id?: string; query_text?: string; session_id?: string; message_id?: string; call_type?: string; }>; sessions: Array<{ session_id: string; bot_id: string; bot_name: string; pipeline_id: string; pipeline_name: string; message_count: number; last_activity: string; start_time: string; platform?: string; user_id?: string; }>; errors: Array<{ id: string; timestamp: string; error_type: string; error_message: string; bot_id: string; bot_name: string; pipeline_id: string; pipeline_name: string; session_id?: string; stack_trace?: string; message_id?: string; }>; totalCount: { messages: number; llmCalls: number; embeddingCalls: number; sessions: number; errors: number; }; }> { const queryParams = new URLSearchParams(); if (params.botId) { params.botId.forEach((id) => queryParams.append('botId', id)); } if (params.pipelineId) { params.pipelineId.forEach((id) => queryParams.append('pipelineId', id)); } if (params.startTime) { queryParams.append('startTime', params.startTime); } if (params.endTime) { queryParams.append('endTime', params.endTime); } if (params.limit) { queryParams.append('limit', params.limit.toString()); } return this.get(`/api/v1/monitoring/data?${queryParams.toString()}`); } public getMonitoringOverview(params: { botId?: string[]; pipelineId?: string[]; startTime?: string; endTime?: string; }): Promise<{ total_messages: number; llm_calls: number; success_rate: number; active_sessions: number; }> { const queryParams = new URLSearchParams(); if (params.botId) { params.botId.forEach((id) => queryParams.append('botId', id)); } if (params.pipelineId) { params.pipelineId.forEach((id) => queryParams.append('pipelineId', id)); } if (params.startTime) { queryParams.append('startTime', params.startTime); } if (params.endTime) { queryParams.append('endTime', params.endTime); } return this.get(`/api/v1/monitoring/overview?${queryParams.toString()}`); } // ============ Survey API ============ public getSurveyPending(): Promise<{ survey: { survey_id: string; version: number; title: Record; description: Record; questions: SurveyQuestion[]; } | null; }> { return this.get('/api/v1/survey/pending'); } public submitSurveyResponse( surveyId: string, answers: Record, completed: boolean = true, ): Promise { return this.post('/api/v1/survey/respond', { survey_id: surveyId, answers, completed, }); } public dismissSurvey(surveyId: string): Promise { return this.post('/api/v1/survey/dismiss', { survey_id: surveyId }); } // ============ Skills API ============ public getSkills(): Promise { return this.get('/api/v1/skills'); } public getSkill(name: string): Promise { return this.get(`/api/v1/skills/${name}`); } public createSkill( skill: Omit & { name: string }, ): Promise { return this.post('/api/v1/skills', skill); } public updateSkill( name: string, skill: Partial, ): Promise { return this.put(`/api/v1/skills/${name}`, skill); } public deleteSkill(name: string): Promise { return this.delete(`/api/v1/skills/${name}`); } public previewSkill(name: string): Promise<{ instructions: string }> { return this.get(`/api/v1/skills/${name}/preview`); } public getSkillIndex(pipelineUuid?: string): Promise<{ index: string }> { const params = pipelineUuid ? { pipeline_uuid: pipelineUuid } : {}; return this.get('/api/v1/skills/index', params); } public scanSkillDirectory(path: string): Promise<{ package_root: string; name: string; display_name?: string; description: string; instructions: string; auto_activate?: boolean; }> { return this.get('/api/v1/skills/scan', { path }); } } export interface SurveyQuestion { id: string; type: 'single_select' | 'multi_select' | 'text'; title: Record; subtitle?: Record; required: boolean; options?: SurveyOption[]; placeholder?: Record; max_length?: number; } export interface SurveyOption { id: string; label: Record; has_input?: boolean; }