import type { AuthContext } from '../auth/AuthContext'; import type { EmbeddingService } from '../../ai/service/EmbeddingService'; /** * 创建 Vector Store 请求 */ export interface CreateVectorStoreRequest { /** 知识库名称 */ name?: string; /** Container URL */ url: string; /** Chunking 策略 */ chunking_strategy?: 'auto' | 'static'; /** 元数据 */ metadata?: Record; } /** * 修改 Vector Store 请求 */ export interface ModifyVectorStoreRequest { name?: string; chunking_strategy?: 'auto' | 'static'; metadata?: Record; } /** * Vector Store 对象(OpenAI 兼容格式) */ export interface VectorStoreObject { id: string; object: 'vector_store'; created_at: number; name: string; status: 'in_progress' | 'completed' | 'expired'; usage_bytes: number; file_counts: { in_progress: number; completed: number; failed: number; cancelled: number; total: number; }; last_active_at: number | null; metadata: Record; url: string; chunking_strategy: string; } /** * Pod AI 配置 */ export interface PodAIConfig { embeddingModel: string; migrationStatus: 'idle' | 'in_progress' | 'completed' | 'failed'; previousModel?: string; migrationProgress?: number; } /** * 搜索请求 */ export interface SearchRequest { query: string | string[]; max_num_results?: number; filters?: Record; ranking_options?: { ranker?: string; score_threshold?: number; }; rewrite_query?: boolean; } /** * 搜索结果 */ export interface SearchResult { file_id: string; file_url: string; filename: string; score: number; attributes: Record; content: Array<{ type: 'text'; text: string; }>; } export interface VectorStoreServiceOptions { /** CSS base URL */ cssBaseUrl: string; /** Token endpoint for login */ tokenEndpoint: string; /** Embedding service */ embeddingService: EmbeddingService; /** Webhook URL for receiving notifications (optional) */ webhookUrl?: string; } /** * VectorStoreService - 知识库管理服务 * * 提供 OpenAI 兼容的 Vector Store API */ export declare class VectorStoreService { private readonly logger; private readonly cssBaseUrl; private readonly tokenEndpoint; private readonly embeddingService; private readonly webhookUrl?; constructor(options: VectorStoreServiceOptions); /** * 创建 Vector Store(配置文件夹为知识库) */ createVectorStore(request: CreateVectorStoreRequest, auth: AuthContext, accessToken?: string): Promise; /** * 列出所有 Vector Store */ listVectorStores(auth: AuthContext, options?: { limit?: number; order?: 'asc' | 'desc'; after?: string; before?: string; }): Promise<{ object: 'list'; data: VectorStoreObject[]; has_more: boolean; }>; /** * 获取单个 Vector Store */ getVectorStore(id: string, auth: AuthContext): Promise; /** * 修改 Vector Store */ modifyVectorStore(id: string, request: ModifyVectorStoreRequest, auth: AuthContext): Promise; /** * 删除 Vector Store */ deleteVectorStore(id: string, auth: AuthContext): Promise<{ id: string; object: 'vector_store.deleted'; deleted: boolean; }>; /** * 索引文件(由 webhook 调用) * * @param vectorStoreId Vector Store ID * @param fileUrl 文件 URL * @param auth 认证上下文 * @param accessToken 访问令牌 */ indexFile(fileUrl: string, auth: AuthContext, accessToken: string): Promise<{ id: string; status: string; vectorId: number; }>; /** * 获取文件应使用的分块策略(查找最近的父级 VectorStore) */ private getChunkingStrategyForFile; /** * 删除文件索引(由 webhook 调用) */ removeFileIndex(fileUrl: string, auth: AuthContext, accessToken: string): Promise<{ deleted: boolean; }>; /** * 获取 Container 下的 file_counts 统计(基于 fileUrl 前缀匹配) */ getFileCounts(containerUrl: string, auth: AuthContext): Promise<{ in_progress: number; completed: number; failed: number; cancelled: number; total: number; }>; /** * 通过 vectorId 查找文件 URL(供 search 使用) * 注意:文件只索引一份,用 vectorId 即可查找 */ getFileUrlByVectorId(vectorId: number, auth: AuthContext): Promise; /** * 根据 Container URL 查找 VectorStore */ findVectorStoreByContainer(containerUrl: string, auth: AuthContext): Promise; /** * 根据文件 URL 查找所有匹配的 VectorStore(包括父级容器) * * 例如:文件 https://alice.pod/A/B/c.txt 会匹配: * - https://alice.pod/A/B/ (直接父级) * - https://alice.pod/A/ (祖先级) * - https://alice.pod/ (Pod 根) * * 这样文件可以被索引到多个知识库中 */ findVectorStoresByFileUrl(fileUrl: string, auth: AuthContext): Promise; /** * 搜索 Vector Store */ search(vectorStoreId: string, request: SearchRequest, auth: AuthContext, accessToken: string): Promise<{ object: 'vector_store.search_results.page'; search_query: string; data: SearchResult[]; has_more: boolean; }>; private generateId; /** * Hash subject + aspect 为向量 ID(供 webhook 索引使用) */ hashSubjectAspect(subject: string, aspect: string): number; private extractContainerName; private extractFilename; private extractModelId; private modelResource; private getPodBaseUrl; private buildVectorStoreObject; private getPodDb; private getAiCredential; /** * 获取 Pod 级别的 AI 配置(全局 embedding model) */ getAIConfig(auth: AuthContext): Promise; /** * 设置全局 embedding model * 如果更换了模型,自动触发迁移(后台重新索引所有文件) */ setEmbeddingModel(newModel: string, auth: AuthContext, accessToken: string): Promise<{ success: boolean; migrationTriggered: boolean; message: string; }>; /** * 开始迁移:重新索引所有文件 */ private startMigration; /** * 获取资源内容(供 webhook 索引使用) */ fetchResourceContent(url: string, accessToken: string): Promise; private extractText; private extractTextFromTurtle; private extractTextFromJsonLd; private extractTextFromHtml; /** * Upsert 向量到 CSS(供 webhook 索引使用) */ upsertVector(model: string, id: number, vector: number[], accessToken: string): Promise; /** * 删除向量(供 webhook 索引使用) */ deleteVector(model: string, id: number, accessToken: string): Promise; private searchVectors; private unreadableVectorIdsForContainer; private canReadResource; /** * 订阅 Container 的变更通知(WebhookChannel2023) * * @param containerUrl Container URL * @param accessToken 访问令牌 */ private subscribeToContainer; /** * 发现 Solid Notification 端点 * * 通过 HEAD 请求获取 Link header 中的 describedby,然后获取订阅端点 */ private discoverNotificationEndpoint; /** * 解析 Link header */ private parseLinkHeader; }