@cloudbase/agent-adapter-yuanqi 0.0.22 → 0.0.23

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 CHANGED
@@ -141,6 +141,7 @@ The following protected methods can be overridden in subclasses to customize cha
141
141
  // Get chat history from database and combine with current message
142
142
  protected async getChatHistory(
143
143
  subscriber: Subscriber<BaseEvent>,
144
+ input: RunAgentInput,
144
145
  latestUserMessage: Message
145
146
  ): Promise<ChatMessage[]>
146
147
 
package/dist/index.d.mts CHANGED
@@ -49,7 +49,7 @@ declare class YuanqiAgent extends AbstractAgent {
49
49
  }): YuanqiChatRequest;
50
50
  run(input: RunAgentInput): Observable<BaseEvent>;
51
51
  private _run;
52
- protected getChatHistory(subscriber: Subscriber<BaseEvent>, latestUserMessage: Message): Promise<OpenAI.Chat.Completions.ChatCompletionMessageParam[]>;
52
+ protected getChatHistory(subscriber: Subscriber<BaseEvent>, input: RunAgentInput, latestUserMessage: Message): Promise<OpenAI.Chat.Completions.ChatCompletionMessageParam[]>;
53
53
  protected saveChatHistory(subscriber: Subscriber<BaseEvent>, input: RunAgentInput, userRecordId: string, assistantRecordId: string, userContent: string, assistantContent: string): Promise<void>;
54
54
  private getTcbClient;
55
55
  private checkIsDatabaseReady;
@@ -167,9 +167,10 @@ declare function describeChatHistory({ tcbClient, botId, sort, pageSize, pageNum
167
167
  triggerSrc?: string;
168
168
  }): Promise<[ChatHistoryEntity[], number]>;
169
169
  declare function transDataToChatEntity(item: ChatHistoryData): ChatHistoryEntity;
170
- declare function queryForLLM({ tcbClient, botId, pageSize, startCreatedAt, triggerSrc, }: {
170
+ declare function queryForLLM({ tcbClient, botId, conversation, pageSize, startCreatedAt, triggerSrc, }: {
171
171
  tcbClient: tcb.CloudBase;
172
172
  botId: string;
173
+ conversation: string;
173
174
  pageSize?: number;
174
175
  startCreatedAt?: number;
175
176
  triggerSrc?: string;
package/dist/index.d.ts CHANGED
@@ -49,7 +49,7 @@ declare class YuanqiAgent extends AbstractAgent {
49
49
  }): YuanqiChatRequest;
50
50
  run(input: RunAgentInput): Observable<BaseEvent>;
51
51
  private _run;
52
- protected getChatHistory(subscriber: Subscriber<BaseEvent>, latestUserMessage: Message): Promise<OpenAI.Chat.Completions.ChatCompletionMessageParam[]>;
52
+ protected getChatHistory(subscriber: Subscriber<BaseEvent>, input: RunAgentInput, latestUserMessage: Message): Promise<OpenAI.Chat.Completions.ChatCompletionMessageParam[]>;
53
53
  protected saveChatHistory(subscriber: Subscriber<BaseEvent>, input: RunAgentInput, userRecordId: string, assistantRecordId: string, userContent: string, assistantContent: string): Promise<void>;
54
54
  private getTcbClient;
55
55
  private checkIsDatabaseReady;
@@ -167,9 +167,10 @@ declare function describeChatHistory({ tcbClient, botId, sort, pageSize, pageNum
167
167
  triggerSrc?: string;
168
168
  }): Promise<[ChatHistoryEntity[], number]>;
169
169
  declare function transDataToChatEntity(item: ChatHistoryData): ChatHistoryEntity;
170
- declare function queryForLLM({ tcbClient, botId, pageSize, startCreatedAt, triggerSrc, }: {
170
+ declare function queryForLLM({ tcbClient, botId, conversation, pageSize, startCreatedAt, triggerSrc, }: {
171
171
  tcbClient: tcb.CloudBase;
172
172
  botId: string;
173
+ conversation: string;
173
174
  pageSize?: number;
174
175
  startCreatedAt?: number;
175
176
  triggerSrc?: string;
package/dist/index.js CHANGED
@@ -390,6 +390,7 @@ function transDataToChatEntity(item) {
390
390
  async function queryForLLM({
391
391
  tcbClient,
392
392
  botId,
393
+ conversation,
393
394
  pageSize = 10,
394
395
  startCreatedAt,
395
396
  triggerSrc
@@ -403,6 +404,7 @@ async function queryForLLM({
403
404
  botId,
404
405
  sort: "desc",
405
406
  pageSize,
407
+ conversation,
406
408
  startCreatedAt,
407
409
  triggerSrc
408
410
  });
@@ -523,6 +525,7 @@ var YuanqiAgent = class extends import_client2.AbstractAgent {
523
525
  }
524
526
  const allMessages = await this.getChatHistory(
525
527
  subscriber,
528
+ input,
526
529
  latestUserMessage
527
530
  );
528
531
  const body = this.generateRequestBody({
@@ -588,8 +591,9 @@ var YuanqiAgent = class extends import_client2.AbstractAgent {
588
591
  }
589
592
  }
590
593
  // Can be override by subclasses
591
- async getChatHistory(subscriber, latestUserMessage) {
594
+ async getChatHistory(subscriber, input, latestUserMessage) {
592
595
  const botId = `bot-yuanqi-${this.finalAppId}`;
596
+ const { threadId } = input;
593
597
  const tcbClient = this.getTcbClient();
594
598
  const isDBReady = await this.checkIsDatabaseReady();
595
599
  if (!isDBReady) {
@@ -607,6 +611,7 @@ var YuanqiAgent = class extends import_client2.AbstractAgent {
607
611
  const historyRecords = await queryForLLM({
608
612
  tcbClient,
609
613
  botId,
614
+ conversation: threadId,
610
615
  pageSize: historyCount
611
616
  });
612
617
  historyMessages = historyRecords.map((record) => ({
package/dist/index.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"sources":["../src/index.ts","../src/agent.ts","../src/utils.ts","../src/stream.ts","../src/constant.ts","../src/chat_history.ts"],"sourcesContent":["export * from \"./agent\";\n\nexport * from \"./types\";\n\nexport * from \"./stream\";\n\nexport * from \"./chat_history\";\n","import {\n RunAgentInput,\n Message,\n AbstractAgent,\n AgentConfig,\n BaseEvent,\n EventType,\n RunStartedEvent,\n RunFinishedEvent,\n RunErrorEvent,\n TextMessageContentEvent,\n ToolCall,\n} from \"@ag-ui/client\";\nimport tcb from \"@cloudbase/node-sdk\";\nimport managedTcb from \"@cloudbase/manager-node\";\nimport OpenAI from \"openai\";\nimport { randomUUID } from \"crypto\";\nimport { camelToSnakeKeys } from \"./utils\";\nimport { processYuanqiStream } from \"./stream\";\nimport { Observable, Subscriber } from \"rxjs\";\nimport {\n createChatHistory,\n queryForLLM,\n ChatHistoryEntity,\n} from \"./chat_history\";\nimport { CHAT_HISTORY_DATA_SOURCE } from \"./constant\";\nimport { YuanqiConfig, ChatMessage, YuanqiChatRequest } from \"./types\";\n\nexport class YuanqiAgentError extends Error {\n code?: string;\n constructor(message: string, code?: string) {\n super(message);\n this.name = \"YuanqiAgentError\";\n if (code) this.code = code;\n }\n}\n\nexport class YuanqiAgent extends AbstractAgent {\n protected yuanqiConfig: YuanqiConfig;\n private finalAppId: string;\n private finalCloudCredential: {\n secretId?: string;\n secretKey?: string;\n token?: string;\n } = {};\n private model: OpenAI;\n constructor(config: AgentConfig & { yuanqiConfig: YuanqiConfig }) {\n super(config);\n this.yuanqiConfig = config.yuanqiConfig;\n this.model = new OpenAI({\n apiKey: \"\",\n baseURL:\n this.yuanqiConfig.request?.baseUrl ||\n \"https://yuanqi.tencent.com/openapi/v1/agent\",\n });\n this.finalAppId =\n this.yuanqiConfig.appId ||\n this.yuanqiConfig.request?.body?.assistantId ||\n process.env.YUANQI_APP_ID ||\n \"\";\n this.finalCloudCredential = {\n secretId:\n this.yuanqiConfig.credential?.secretId ||\n process.env.TENCENTCLOUD_SECRETID,\n secretKey:\n this.yuanqiConfig.credential?.secretKey ||\n process.env.TENCENTCLOUD_SECRETKEY,\n token:\n this.yuanqiConfig.credential?.token ||\n process.env.TENCENTCLOUD_SESSIONTOKEN,\n };\n }\n\n generateRequestBody({\n messages,\n input,\n }: {\n messages: ChatMessage[];\n input: RunAgentInput;\n }): YuanqiChatRequest {\n const { state, forwardedProps } = input;\n const requestBody: YuanqiChatRequest = {\n stream: true,\n ...(this.yuanqiConfig.request?.body || {}),\n ...(forwardedProps || {}),\n\n assistantId: this.finalAppId,\n userId:\n state?.__request_context__?.user?.id ||\n forwardedProps?.userId ||\n randomUUID(),\n messages,\n };\n return requestBody;\n }\n\n run(input: RunAgentInput): Observable<BaseEvent> {\n return new Observable<BaseEvent>((subscriber) => {\n this._run(subscriber, input);\n });\n }\n\n private async _run(\n subscriber: Subscriber<BaseEvent>,\n input: RunAgentInput\n ): Promise<void> {\n try {\n const { messages, runId } = input;\n\n const openai = this.model as OpenAI;\n const threadId = input.threadId || randomUUID();\n\n subscriber.next({\n type: EventType.RUN_STARTED,\n threadId,\n runId,\n } as RunStartedEvent);\n\n if (!this.finalAppId) {\n throw new YuanqiAgentError(\n \"YUANQI_APP_ID is required, check your env variables or config passed with the adapter\",\n \"MISSING_YUANQI_APP_ID\"\n );\n }\n if (!this.yuanqiConfig.appKey && !process.env.YUANQI_APP_KEY) {\n throw new YuanqiAgentError(\n \"YUANQI_APP_KEY is required, check your env variables or config passed with the adapter\",\n \"MISSING_YUANQI_APP_KEY\"\n );\n }\n\n // Warn user if messages are being trimmed (only using latest user message)\n const trimmedCount = messages.length - 1;\n if (trimmedCount > 0) {\n subscriber.next({\n type: EventType.RAW,\n rawEvent: {\n message: `Yuanqi handles message history itself, so that a total of ${trimmedCount} messages before the last user message will be trimmed.`,\n type: \"warn\",\n },\n });\n }\n\n // Get the latest user message for saving to history\n const latestUserMessage = messages.filter((m) => m.role === \"user\").pop();\n if (!latestUserMessage) {\n throw new YuanqiAgentError(\n \"No user message found, please send a message first.\",\n \"MESSAGE_FORMAT_ERROR\"\n );\n }\n\n const allMessages = await this.getChatHistory(\n subscriber,\n latestUserMessage\n );\n\n const body = this.generateRequestBody({\n messages: allMessages,\n input,\n });\n\n const stream = await openai.chat.completions.create(\n {\n stream: true,\n messages: [],\n model: \"\",\n },\n {\n body: camelToSnakeKeys(body),\n headers: {\n ...this.yuanqiConfig.request?.headers,\n Authorization: `Bearer ${\n this.yuanqiConfig.appKey || process.env.YUANQI_APP_KEY\n }`,\n },\n }\n );\n\n // Process stream and emit AGUI events, collect full response\n const userRecordId = `record-${randomUUID().slice(0, 8)}`;\n const assistantRecordId = `record-${randomUUID().slice(0, 8)}`;\n const context = { threadId, runId, messageId: userRecordId };\n\n let fullAssistantContent = \"\";\n\n for await (const event of processYuanqiStream(stream, context)) {\n subscriber.next(event);\n // Collect assistant content from TEXT_MESSAGE_CONTENT events\n if (\n event.type === EventType.TEXT_MESSAGE_CONTENT &&\n (event as TextMessageContentEvent).delta\n ) {\n fullAssistantContent += (event as TextMessageContentEvent).delta;\n }\n }\n\n const userContent =\n typeof latestUserMessage?.content === \"string\"\n ? latestUserMessage.content\n : latestUserMessage?.content\n ?.filter((c) => c.type === \"text\")\n .map((c) => c.text)\n .join(\"\") || \"\";\n\n await this.saveChatHistory(\n subscriber,\n input,\n userRecordId,\n assistantRecordId,\n userContent,\n fullAssistantContent\n );\n\n subscriber.next({\n type: EventType.RUN_FINISHED,\n threadId,\n runId,\n } as RunFinishedEvent);\n } catch (e: unknown) {\n console.error(\"[ERROR] Uncaught error: \", JSON.stringify(e));\n let code = \"UNKNOWN_ERROR\";\n let message = JSON.stringify(e);\n if (e instanceof YuanqiAgentError) {\n code = e.code || \"AGENT_ERROR\";\n message = e.message;\n } else if (e instanceof Error) {\n code = e.name || \"ERROR\";\n message = e.message;\n }\n subscriber.next({\n type: EventType.RUN_ERROR,\n code,\n message: `Sorry, an error occurred while running the agent: Error code ${code}, ${message}`,\n } as RunErrorEvent);\n } finally {\n subscriber.complete();\n }\n }\n\n // Can be override by subclasses\n protected async getChatHistory(\n subscriber: Subscriber<BaseEvent>,\n latestUserMessage: Message\n ) {\n const botId = `bot-yuanqi-${this.finalAppId}`;\n\n const tcbClient = this.getTcbClient();\n\n const isDBReady = await this.checkIsDatabaseReady();\n if (!isDBReady) {\n subscriber.next({\n type: EventType.RAW,\n rawEvent: {\n message: `Chat history database is not ready, skip history loading.`,\n type: \"warn\",\n },\n });\n return convertMessagesToOpenAI([latestUserMessage]);\n }\n\n // Fetch chat history from database using queryForLLM\n let historyMessages: ChatMessage[] = [];\n\n const historyCount = this.yuanqiConfig.historyCount ?? 10;\n const historyRecords = await queryForLLM({\n tcbClient,\n botId,\n pageSize: historyCount,\n });\n\n // Convert queryForLLM result to ChatMessage format\n historyMessages = historyRecords.map((record) => ({\n role: record.role as \"user\" | \"assistant\",\n content: [{ type: \"text\" as const, text: record.content }],\n }));\n\n // Combine history messages with current messages\n const allMessages = historyMessages.concat(\n convertMessagesToOpenAI([latestUserMessage])\n );\n return allMessages;\n }\n\n // Can be override by subclasses\n protected async saveChatHistory(\n subscriber: Subscriber<BaseEvent>,\n input: RunAgentInput,\n userRecordId: string,\n assistantRecordId: string,\n userContent: string,\n assistantContent: string\n ) {\n const botId = `bot-yuanqi-${this.finalAppId}`;\n\n const { threadId, runId } = input;\n\n const tcbClient = this.getTcbClient();\n\n const isDBReady = await this.checkIsDatabaseReady();\n if (!isDBReady) {\n subscriber.next({\n type: EventType.RAW,\n rawEvent: {\n message: `Chat history database is not ready, skip history saving.`,\n type: \"warn\",\n },\n });\n return;\n }\n\n // Save message pair to history\n const userEntity = new ChatHistoryEntity();\n userEntity.recordId = userRecordId;\n userEntity.botId = botId;\n userEntity.role = \"user\";\n userEntity.content = userContent;\n userEntity.conversation = threadId;\n userEntity.reply = assistantRecordId;\n userEntity.triggerSrc = \"\";\n userEntity.traceId = randomUUID();\n\n await createChatHistory({ tcbClient, chatHistoryEntity: userEntity });\n\n const assistantEntity = new ChatHistoryEntity();\n assistantEntity.recordId = assistantRecordId;\n assistantEntity.botId = botId;\n assistantEntity.role = \"assistant\";\n assistantEntity.content = assistantContent;\n assistantEntity.conversation = threadId;\n assistantEntity.replyTo = userRecordId;\n assistantEntity.triggerSrc = \"\";\n assistantEntity.traceId = runId;\n assistantEntity.status = \"done\";\n\n await createChatHistory({\n tcbClient,\n chatHistoryEntity: assistantEntity,\n });\n }\n\n private getTcbClient() {\n const envId = this.yuanqiConfig.envId || getCloudbaseEnvId();\n\n const tcbClient = tcb.init({\n env: envId,\n secretId: this.finalCloudCredential.secretId,\n secretKey: this.finalCloudCredential.secretKey,\n sessionToken: this.finalCloudCredential.token,\n });\n return tcbClient;\n }\n\n private async checkIsDatabaseReady() {\n try {\n const envId = this.yuanqiConfig.envId || getCloudbaseEnvId();\n if (!envId) {\n throw new YuanqiAgentError(\n \"When saving chat history to CloudBase, CLOUDBASE_ENV_ID is required, check your env variables or config passed with the adapter\",\n \"MISSING_CLOUDBASE_ENV_ID\"\n );\n }\n if (!this.finalCloudCredential.token) {\n if (!this.finalCloudCredential.secretId) {\n throw new YuanqiAgentError(\n \"When saving chat history to CloudBase, TENCENTCLOUD_SECRETID is required, check your env variables or config passed with the adapter\",\n \"MISSING_SECRET_ID\"\n );\n }\n if (!this.finalCloudCredential.secretKey) {\n throw new YuanqiAgentError(\n \"When saving chat history to CloudBase, TENCENTCLOUD_SECRETKEY is required, check your env variables or config passed with the adapter\",\n \"MISSING_SECRET_KEY\"\n );\n }\n }\n const managedTcbClient = managedTcb.init({\n envId,\n secretId: this.finalCloudCredential.secretId,\n secretKey: this.finalCloudCredential.secretKey,\n token: this.finalCloudCredential.token,\n });\n\n const checkDBRes = await managedTcbClient.database.checkCollectionExists(\n CHAT_HISTORY_DATA_SOURCE\n );\n if (checkDBRes && checkDBRes.Exists) {\n return true;\n } else if (checkDBRes && !checkDBRes.Exists) {\n await managedTcbClient.database.createCollection(\n CHAT_HISTORY_DATA_SOURCE\n );\n return true;\n } else {\n throw new Error(\"Check database exists failed\");\n }\n } catch (dbError) {\n console.error(\n \"[ERROR] Failed to check/create chat history collection:\",\n JSON.stringify(dbError)\n );\n return false;\n }\n }\n}\n\nfunction getCloudbaseEnvId() {\n if (process.env.CBR_ENV_ID) {\n return process.env.CBR_ENV_ID;\n } else if (process.env.SCF_NAMESPACE) {\n return process.env.SCF_NAMESPACE;\n } else {\n return process.env.CLOUDBASE_ENV_ID || \"\";\n }\n}\n\n/**\n * Convert AGUI messages to OpenAI chat completion format\n */\nexport function convertMessagesToOpenAI(\n messages: Message[],\n systemPrompt?: string\n): ChatMessage[] {\n const openaiMessages: ChatMessage[] = [];\n\n // Add system prompt if provided\n if (systemPrompt) {\n openaiMessages.push({\n role: \"system\",\n content: systemPrompt,\n });\n }\n\n // Convert messages\n for (const msg of messages) {\n if (msg.role === \"user\") {\n openaiMessages.push({\n role: \"user\",\n content:\n typeof msg.content === \"string\"\n ? [{ type: \"text\", text: msg.content }]\n : msg.content.map((item) => {\n if (item.type === \"text\") {\n return { type: \"text\", text: item.text };\n } else {\n return {\n type: \"image_url\",\n image_url: { url: item.url || \"\" },\n };\n }\n }),\n });\n } else if (msg.role === \"assistant\") {\n openaiMessages.push({\n role: \"assistant\",\n content: msg.content ? [{ type: \"text\", text: msg.content }] : [],\n tool_calls: msg.toolCalls?.map((tc: ToolCall) => ({\n id: tc.id,\n type: \"function\" as const,\n function: {\n name: tc.function.name,\n arguments: tc.function.arguments,\n },\n })),\n });\n } else if (msg.role === \"tool\") {\n openaiMessages.push({\n role: \"tool\",\n tool_call_id: msg.toolCallId,\n content: msg.content ? [{ type: \"text\", text: msg.content }] : [],\n });\n }\n }\n\n return openaiMessages;\n}\n","/**\n * 将小驼峰字符串转换为下划线格式\n * 例如: \"userName\" -> \"user_name\"\n */\nfunction camelToSnake(str: string): string {\n return str.replace(/[A-Z]/g, (letter) => `_${letter.toLowerCase()}`);\n}\n\n/**\n * 递归地将对象的所有小驼峰属性名转换为下划线格式\n */\nexport function camelToSnakeKeys<T>(obj: T): T {\n if (obj === null || obj === undefined) {\n return obj;\n }\n\n if (Array.isArray(obj)) {\n return obj.map((item) => camelToSnakeKeys(item)) as T;\n }\n\n if (typeof obj === \"object\") {\n const result: Record<string, unknown> = {};\n for (const [key, value] of Object.entries(obj)) {\n const snakeKey = camelToSnake(key);\n result[snakeKey] = camelToSnakeKeys(value);\n }\n return result as T;\n }\n\n return obj;\n}\n\nexport function genRandomStr(length: number): string {\n const chars = \"abcdefghijklmnopqrstuvwxyz0123456789\";\n let result = \"\";\n for (let i = 0; i < length; i++) {\n result += chars.charAt(Math.floor(Math.random() * chars.length));\n }\n return result;\n}\n","import OpenAI from \"openai\";\nimport { EventType } from \"@ag-ui/client\";\n\nexport interface StreamContext {\n threadId: string;\n runId: string;\n messageId: string;\n}\n\nexport interface StreamState {\n hasStarted: boolean;\n fullContent: string;\n toolCallsMap: Map<string, { name: string; args: string }>;\n}\n\nexport type Delta =\n OpenAI.Chat.Completions.ChatCompletionChunk[\"choices\"][number][\"delta\"] & {\n reasoning_content?: string;\n };\n\nexport async function* processYuanqiStream(\n stream: AsyncIterable<OpenAI.Chat.Completions.ChatCompletionChunk>,\n context: StreamContext\n) {\n const { threadId, runId, messageId } = context;\n const state: StreamState = {\n hasStarted: false,\n fullContent: \"\",\n toolCallsMap: new Map(),\n };\n const reasoningState: StreamState = {\n hasStarted: false,\n fullContent: \"\",\n toolCallsMap: new Map(),\n };\n\n for await (const chunk of stream) {\n const delta = chunk.choices[0]?.delta as Delta;\n if (!delta) continue;\n\n if (delta.role === \"tool\") {\n const toolCallId = (delta as any).tool_call_id;\n if (toolCallId) {\n if (state.toolCallsMap.has(toolCallId)) {\n yield {\n type: EventType.TOOL_CALL_END,\n threadId,\n runId,\n toolCallId,\n };\n state.toolCallsMap.delete(toolCallId);\n }\n yield {\n type: EventType.TOOL_CALL_RESULT,\n threadId,\n runId,\n toolCallId,\n content: delta.content || \"\",\n };\n }\n continue;\n }\n\n // Handle text content\n if (delta.content) {\n // End reasoning message if it was started\n if (reasoningState.hasStarted) {\n reasoningState.hasStarted = false;\n yield {\n type: EventType.THINKING_TEXT_MESSAGE_END,\n threadId,\n runId,\n messageId,\n };\n yield {\n type: EventType.THINKING_END,\n threadId,\n runId,\n messageId,\n };\n }\n\n if (!state.hasStarted) {\n yield {\n type: EventType.TEXT_MESSAGE_START,\n threadId,\n runId,\n messageId,\n role: \"assistant\",\n };\n state.hasStarted = true;\n }\n\n state.fullContent += delta.content;\n yield {\n type: EventType.TEXT_MESSAGE_CONTENT,\n threadId,\n runId,\n messageId,\n delta: delta.content,\n };\n }\n\n // Handle reasoning content\n if (delta.reasoning_content) {\n if (!reasoningState.hasStarted) {\n yield {\n type: EventType.THINKING_START,\n threadId,\n runId,\n messageId,\n };\n yield {\n type: EventType.THINKING_TEXT_MESSAGE_START,\n threadId,\n runId,\n messageId,\n role: \"assistant\",\n };\n reasoningState.hasStarted = true;\n }\n\n reasoningState.fullContent += delta.reasoning_content;\n yield {\n type: EventType.THINKING_TEXT_MESSAGE_CONTENT,\n threadId,\n runId,\n messageId,\n delta: delta.reasoning_content,\n };\n }\n\n // Handle tool calls\n if (delta.tool_calls) {\n for (const toolCall of delta.tool_calls) {\n const toolCallId = toolCall.id || `tool_${toolCall.index}`;\n\n if (toolCall.function?.name) {\n // Tool call start\n yield {\n type: EventType.TOOL_CALL_START,\n threadId,\n runId,\n toolCallId,\n toolCallName: toolCall.function.name,\n };\n\n // If first chunk contains arguments, emit TOOL_CALL_ARGS event\n if (toolCall.function.arguments) {\n yield {\n type: EventType.TOOL_CALL_ARGS,\n threadId,\n runId,\n toolCallId,\n delta: toolCall.function.arguments,\n };\n }\n\n state.toolCallsMap.set(toolCallId, {\n name: toolCall.function.name,\n args: toolCall.function.arguments || \"\",\n });\n } else if (toolCall.function?.arguments) {\n // Tool call arguments delta\n const existing = state.toolCallsMap.get(toolCallId);\n if (existing) {\n existing.args += toolCall.function.arguments;\n\n yield {\n type: EventType.TOOL_CALL_ARGS,\n threadId,\n runId,\n toolCallId,\n delta: toolCall.function.arguments,\n };\n }\n }\n }\n }\n }\n\n // Emit TEXT_MESSAGE_END if we had text content\n if (state.hasStarted) {\n yield {\n type: EventType.TEXT_MESSAGE_END,\n threadId,\n runId,\n messageId,\n };\n }\n\n if (reasoningState.hasStarted) {\n yield {\n type: EventType.THINKING_TEXT_MESSAGE_END,\n threadId,\n runId,\n messageId,\n };\n yield {\n type: EventType.THINKING_END,\n threadId,\n runId,\n messageId,\n };\n }\n\n // Emit TOOL_CALL_END for all tool calls\n for (const [toolCallId] of state.toolCallsMap) {\n yield {\n type: EventType.TOOL_CALL_END,\n threadId,\n runId,\n toolCallId,\n };\n }\n}\n","// 对话数据模型\nexport const CHAT_HISTORY_DATA_SOURCE = \"ai_bot_chat_history_5hobd2b\";\n","import tcb from \"@cloudbase/node-sdk\";\nimport { CHAT_HISTORY_DATA_SOURCE } from \"./constant\";\nimport { genRandomStr } from \"./utils\";\n\nfunction genRecordId(): string {\n return \"record-\" + genRandomStr(8);\n}\n\n// Create a new chat history record\nexport async function createChatHistory({\n tcbClient,\n chatHistoryEntity,\n}: {\n tcbClient: tcb.CloudBase;\n chatHistoryEntity: ChatHistoryEntity;\n}): Promise<string | undefined> {\n try {\n const recordId = chatHistoryEntity.recordId || genRecordId();\n const data = {\n record_id: recordId,\n bot_id: chatHistoryEntity.botId,\n role: chatHistoryEntity.role,\n content: chatHistoryEntity.content,\n sender: chatHistoryEntity.sender,\n conversation: chatHistoryEntity.conversation,\n type: chatHistoryEntity.type,\n image: chatHistoryEntity.image,\n trigger_src: chatHistoryEntity.triggerSrc,\n origin_msg: chatHistoryEntity.originMsg,\n reply_to: chatHistoryEntity.replyTo,\n reply: chatHistoryEntity.reply,\n trace_id: chatHistoryEntity.traceId,\n need_async_reply: chatHistoryEntity.needAsyncReply,\n async_reply: chatHistoryEntity.asyncReply,\n createdAt: Date.now(),\n updatedAt: Date.now(),\n };\n\n const db = tcbClient.database();\n const collection = db.collection(CHAT_HISTORY_DATA_SOURCE);\n const result = await collection.add(data);\n\n // console.log(\n // `Create record: chatHistoryEntity:${JSON.stringify(\n // chatHistoryEntity\n // )}, result: ${JSON.stringify(result)}`\n // );\n return recordId;\n } catch (error) {\n console.error(\"Failed to create chat history record, error:\", error);\n return undefined;\n }\n}\n\n// Update chat history by record ID\nexport async function updateChatHistoryByRecordId({\n tcbClient,\n recordId,\n chatHistoryEntity,\n}: {\n tcbClient: tcb.CloudBase;\n recordId: string;\n chatHistoryEntity: ChatHistoryEntity;\n}): Promise<string | undefined> {\n try {\n const db = tcbClient.database();\n const _ = db.command;\n const collection = db.collection(CHAT_HISTORY_DATA_SOURCE);\n\n const result = await collection\n .where({ record_id: _.eq(recordId) })\n .update({\n content: chatHistoryEntity.content,\n image: chatHistoryEntity.image,\n async_reply: chatHistoryEntity.asyncReply,\n recommend_questions: chatHistoryEntity.recommendQuestions,\n status: chatHistoryEntity.status,\n origin_msg: chatHistoryEntity.originMsg,\n updatedAt: Date.now(),\n });\n\n // console.log(\n // `Update record: recordId: ${recordId}, chatHistoryEntity:${JSON.stringify(\n // chatHistoryEntity\n // )}, result: ${JSON.stringify(result)}`\n // );\n return chatHistoryEntity.recordId;\n } catch (error) {\n console.error(\"Failed to update chat history, error:\", error);\n return undefined;\n }\n}\n\n// Query chat history from database\nexport async function describeChatHistory({\n tcbClient,\n botId,\n sort,\n pageSize = 10,\n pageNumber = 1,\n conversation,\n startCreatedAt,\n triggerSrc,\n}: {\n tcbClient: tcb.CloudBase;\n botId: string;\n sort: \"asc\" | \"desc\";\n pageSize?: number;\n pageNumber?: number;\n conversation?: string;\n startCreatedAt?: number;\n triggerSrc?: string;\n}): Promise<[ChatHistoryEntity[], number]> {\n if (!sort || sort.length === 0) {\n sort = \"desc\";\n }\n\n try {\n const db = tcbClient.database();\n const _ = db.command;\n const collection = db.collection(CHAT_HISTORY_DATA_SOURCE);\n\n // Build where conditions\n const whereConditions: Record<string, unknown> = {\n bot_id: _.eq(botId),\n };\n\n // Add optional filters\n if (conversation) {\n whereConditions.conversation = _.eq(conversation);\n }\n\n if (startCreatedAt !== undefined) {\n whereConditions.createdAt = _.gt(startCreatedAt);\n }\n\n if (triggerSrc) {\n whereConditions.trigger_src = _.eq(triggerSrc);\n }\n\n // Calculate skip for pagination\n const skip = (pageNumber - 1) * pageSize;\n\n // Query records\n const result = await collection\n .where(whereConditions)\n .orderBy(\"createdAt\", sort)\n .skip(skip)\n .limit(pageSize)\n .get();\n\n // Get total count\n const countResult = await collection.where(whereConditions).count();\n const total = countResult.total || 0;\n\n const records = result?.data || [];\n\n const entityList: ChatHistoryEntity[] = records.map(\n (item: ChatHistoryData) => transDataToChatEntity(item)\n );\n\n return [entityList, total];\n } catch (error) {\n console.error(\"Failed to query chat history, error:\", error);\n return [[], 0];\n }\n}\n\n// Transform data to ChatHistoryEntity structure\nexport function transDataToChatEntity(\n item: ChatHistoryData\n): ChatHistoryEntity {\n if (!item) {\n return new ChatHistoryEntity();\n }\n const chatEntity: ChatHistoryEntity = new ChatHistoryEntity();\n chatEntity.botId = item.bot_id;\n chatEntity.recordId = item.record_id;\n chatEntity.role = item.role;\n chatEntity.status = item.status;\n chatEntity.content = item.content;\n chatEntity.sender = item.sender;\n chatEntity.conversation = item.conversation;\n chatEntity.type = item.type;\n chatEntity.triggerSrc = item.trigger_src;\n chatEntity.originMsg = item.origin_msg;\n chatEntity.replyTo = item.reply_to;\n chatEntity.reply = item.reply;\n chatEntity.traceId = item.trace_id;\n chatEntity.needAsyncReply = item.need_async_reply;\n chatEntity.asyncReply = item.async_reply;\n chatEntity.createdAt = item.createdAt;\n chatEntity.updatedAt = item.updatedAt;\n return chatEntity;\n}\n\n// Query history records for LLM, get the most recent 10 conversation pairs (20 records)\nexport async function queryForLLM({\n tcbClient,\n botId,\n pageSize = 10,\n startCreatedAt,\n triggerSrc,\n}: {\n tcbClient: tcb.CloudBase;\n botId: string;\n pageSize?: number;\n startCreatedAt?: number;\n triggerSrc?: string;\n}): Promise<{ role: string; content: string }[]> {\n if (startCreatedAt === undefined) {\n startCreatedAt = Date.now() - 24 * 60 * 60 * 1000;\n }\n const recordEntityList: ChatHistoryEntity[] = [];\n\n const [recordList] = await describeChatHistory({\n tcbClient,\n botId,\n sort: \"desc\",\n pageSize,\n startCreatedAt,\n triggerSrc,\n });\n recordEntityList.push(...recordList.reverse());\n\n const entityMap = new Map<string, ChatHistoryEntity>();\n recordEntityList\n .filter((item) => {\n if (item.needAsyncReply === true) {\n return !!item.asyncReply;\n } else {\n return !!item.content;\n }\n })\n .forEach((item) => {\n entityMap.set(item.recordId, item);\n });\n\n const result: { role: string; content: string }[] = [];\n /*\n 1. Strongly depends on database history data, model history data has role order requirements\n 2. Need to ensure that no matter what bug occurs, always get a complete and usable user + assistant pair, otherwise the request will fail\n */\n recordEntityList.forEach((item) => {\n const { role, content, reply } = item;\n // When calling LLM, empty content will cause failure, so filter out conversations with empty content\n if (role === \"user\" && content?.length !== 0) {\n if (entityMap.has(reply)) {\n result.push({ role, content });\n result.push({\n role: entityMap.get(reply)!.role,\n content: entityMap.get(reply)!.content,\n });\n }\n }\n });\n if (result.length % 2 === 1) {\n result.splice(-1, 1);\n }\n return result;\n}\n\nexport interface ChatHistoryData {\n bot_id: string;\n record_id: string;\n role: string;\n status: string;\n content: string;\n sender: string;\n conversation: string;\n type: string;\n trigger_src: string;\n origin_msg: string;\n reply_to: string;\n reply: string;\n trace_id: string;\n need_async_reply: boolean;\n async_reply: string;\n createdAt: number;\n updatedAt: number;\n}\n\nexport class ChatHistoryEntity {\n id: number;\n botId: string;\n // 对话唯一id\n recordId: string;\n role: string;\n content: string;\n recommendQuestions: string[];\n sender: string;\n conversation: string;\n type: string;\n /**\n * 消息状态,pending done error cancel\n */\n status: string;\n image: string;\n triggerSrc: string;\n originMsg: string;\n replyTo: string;\n reply: string;\n traceId: string;\n needAsyncReply: boolean;\n asyncReply: string;\n createTime: string;\n updateTime: string;\n createdAt: number;\n updatedAt: number;\n event: string;\n}\n"],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;;;ACAA,IAAAA,iBAYO;AACP,sBAAgB;AAChB,0BAAuB;AACvB,oBAAmB;AACnB,oBAA2B;;;ACZ3B,SAAS,aAAa,KAAqB;AACzC,SAAO,IAAI,QAAQ,UAAU,CAAC,WAAW,IAAI,OAAO,YAAY,CAAC,EAAE;AACrE;AAKO,SAAS,iBAAoB,KAAW;AAC7C,MAAI,QAAQ,QAAQ,QAAQ,QAAW;AACrC,WAAO;AAAA,EACT;AAEA,MAAI,MAAM,QAAQ,GAAG,GAAG;AACtB,WAAO,IAAI,IAAI,CAAC,SAAS,iBAAiB,IAAI,CAAC;AAAA,EACjD;AAEA,MAAI,OAAO,QAAQ,UAAU;AAC3B,UAAM,SAAkC,CAAC;AACzC,eAAW,CAAC,KAAK,KAAK,KAAK,OAAO,QAAQ,GAAG,GAAG;AAC9C,YAAM,WAAW,aAAa,GAAG;AACjC,aAAO,QAAQ,IAAI,iBAAiB,KAAK;AAAA,IAC3C;AACA,WAAO;AAAA,EACT;AAEA,SAAO;AACT;AAEO,SAAS,aAAa,QAAwB;AACnD,QAAM,QAAQ;AACd,MAAI,SAAS;AACb,WAAS,IAAI,GAAG,IAAI,QAAQ,KAAK;AAC/B,cAAU,MAAM,OAAO,KAAK,MAAM,KAAK,OAAO,IAAI,MAAM,MAAM,CAAC;AAAA,EACjE;AACA,SAAO;AACT;;;ACtCA,oBAA0B;AAmB1B,gBAAuB,oBACrB,QACA,SACA;AACA,QAAM,EAAE,UAAU,OAAO,UAAU,IAAI;AACvC,QAAM,QAAqB;AAAA,IACzB,YAAY;AAAA,IACZ,aAAa;AAAA,IACb,cAAc,oBAAI,IAAI;AAAA,EACxB;AACA,QAAM,iBAA8B;AAAA,IAClC,YAAY;AAAA,IACZ,aAAa;AAAA,IACb,cAAc,oBAAI,IAAI;AAAA,EACxB;AAEA,mBAAiB,SAAS,QAAQ;AAChC,UAAM,QAAQ,MAAM,QAAQ,CAAC,GAAG;AAChC,QAAI,CAAC,MAAO;AAEZ,QAAI,MAAM,SAAS,QAAQ;AACzB,YAAM,aAAc,MAAc;AAClC,UAAI,YAAY;AACd,YAAI,MAAM,aAAa,IAAI,UAAU,GAAG;AACtC,gBAAM;AAAA,YACJ,MAAM,wBAAU;AAAA,YAChB;AAAA,YACA;AAAA,YACA;AAAA,UACF;AACA,gBAAM,aAAa,OAAO,UAAU;AAAA,QACtC;AACA,cAAM;AAAA,UACJ,MAAM,wBAAU;AAAA,UAChB;AAAA,UACA;AAAA,UACA;AAAA,UACA,SAAS,MAAM,WAAW;AAAA,QAC5B;AAAA,MACF;AACA;AAAA,IACF;AAGA,QAAI,MAAM,SAAS;AAEjB,UAAI,eAAe,YAAY;AAC7B,uBAAe,aAAa;AAC5B,cAAM;AAAA,UACJ,MAAM,wBAAU;AAAA,UAChB;AAAA,UACA;AAAA,UACA;AAAA,QACF;AACA,cAAM;AAAA,UACJ,MAAM,wBAAU;AAAA,UAChB;AAAA,UACA;AAAA,UACA;AAAA,QACF;AAAA,MACF;AAEA,UAAI,CAAC,MAAM,YAAY;AACrB,cAAM;AAAA,UACJ,MAAM,wBAAU;AAAA,UAChB;AAAA,UACA;AAAA,UACA;AAAA,UACA,MAAM;AAAA,QACR;AACA,cAAM,aAAa;AAAA,MACrB;AAEA,YAAM,eAAe,MAAM;AAC3B,YAAM;AAAA,QACJ,MAAM,wBAAU;AAAA,QAChB;AAAA,QACA;AAAA,QACA;AAAA,QACA,OAAO,MAAM;AAAA,MACf;AAAA,IACF;AAGA,QAAI,MAAM,mBAAmB;AAC3B,UAAI,CAAC,eAAe,YAAY;AAC9B,cAAM;AAAA,UACJ,MAAM,wBAAU;AAAA,UAChB;AAAA,UACA;AAAA,UACA;AAAA,QACF;AACA,cAAM;AAAA,UACJ,MAAM,wBAAU;AAAA,UAChB;AAAA,UACA;AAAA,UACA;AAAA,UACA,MAAM;AAAA,QACR;AACA,uBAAe,aAAa;AAAA,MAC9B;AAEA,qBAAe,eAAe,MAAM;AACpC,YAAM;AAAA,QACJ,MAAM,wBAAU;AAAA,QAChB;AAAA,QACA;AAAA,QACA;AAAA,QACA,OAAO,MAAM;AAAA,MACf;AAAA,IACF;AAGA,QAAI,MAAM,YAAY;AACpB,iBAAW,YAAY,MAAM,YAAY;AACvC,cAAM,aAAa,SAAS,MAAM,QAAQ,SAAS,KAAK;AAExD,YAAI,SAAS,UAAU,MAAM;AAE3B,gBAAM;AAAA,YACJ,MAAM,wBAAU;AAAA,YAChB;AAAA,YACA;AAAA,YACA;AAAA,YACA,cAAc,SAAS,SAAS;AAAA,UAClC;AAGA,cAAI,SAAS,SAAS,WAAW;AAC/B,kBAAM;AAAA,cACJ,MAAM,wBAAU;AAAA,cAChB;AAAA,cACA;AAAA,cACA;AAAA,cACA,OAAO,SAAS,SAAS;AAAA,YAC3B;AAAA,UACF;AAEA,gBAAM,aAAa,IAAI,YAAY;AAAA,YACjC,MAAM,SAAS,SAAS;AAAA,YACxB,MAAM,SAAS,SAAS,aAAa;AAAA,UACvC,CAAC;AAAA,QACH,WAAW,SAAS,UAAU,WAAW;AAEvC,gBAAM,WAAW,MAAM,aAAa,IAAI,UAAU;AAClD,cAAI,UAAU;AACZ,qBAAS,QAAQ,SAAS,SAAS;AAEnC,kBAAM;AAAA,cACJ,MAAM,wBAAU;AAAA,cAChB;AAAA,cACA;AAAA,cACA;AAAA,cACA,OAAO,SAAS,SAAS;AAAA,YAC3B;AAAA,UACF;AAAA,QACF;AAAA,MACF;AAAA,IACF;AAAA,EACF;AAGA,MAAI,MAAM,YAAY;AACpB,UAAM;AAAA,MACJ,MAAM,wBAAU;AAAA,MAChB;AAAA,MACA;AAAA,MACA;AAAA,IACF;AAAA,EACF;AAEA,MAAI,eAAe,YAAY;AAC7B,UAAM;AAAA,MACJ,MAAM,wBAAU;AAAA,MAChB;AAAA,MACA;AAAA,MACA;AAAA,IACF;AACA,UAAM;AAAA,MACJ,MAAM,wBAAU;AAAA,MAChB;AAAA,MACA;AAAA,MACA;AAAA,IACF;AAAA,EACF;AAGA,aAAW,CAAC,UAAU,KAAK,MAAM,cAAc;AAC7C,UAAM;AAAA,MACJ,MAAM,wBAAU;AAAA,MAChB;AAAA,MACA;AAAA,MACA;AAAA,IACF;AAAA,EACF;AACF;;;AFpMA,kBAAuC;;;AGlBhC,IAAM,2BAA2B;;;ACGxC,SAAS,cAAsB;AAC7B,SAAO,YAAY,aAAa,CAAC;AACnC;AAGA,eAAsB,kBAAkB;AAAA,EACtC;AAAA,EACA;AACF,GAGgC;AAC9B,MAAI;AACF,UAAM,WAAW,kBAAkB,YAAY,YAAY;AAC3D,UAAM,OAAO;AAAA,MACX,WAAW;AAAA,MACX,QAAQ,kBAAkB;AAAA,MAC1B,MAAM,kBAAkB;AAAA,MACxB,SAAS,kBAAkB;AAAA,MAC3B,QAAQ,kBAAkB;AAAA,MAC1B,cAAc,kBAAkB;AAAA,MAChC,MAAM,kBAAkB;AAAA,MACxB,OAAO,kBAAkB;AAAA,MACzB,aAAa,kBAAkB;AAAA,MAC/B,YAAY,kBAAkB;AAAA,MAC9B,UAAU,kBAAkB;AAAA,MAC5B,OAAO,kBAAkB;AAAA,MACzB,UAAU,kBAAkB;AAAA,MAC5B,kBAAkB,kBAAkB;AAAA,MACpC,aAAa,kBAAkB;AAAA,MAC/B,WAAW,KAAK,IAAI;AAAA,MACpB,WAAW,KAAK,IAAI;AAAA,IACtB;AAEA,UAAM,KAAK,UAAU,SAAS;AAC9B,UAAM,aAAa,GAAG,WAAW,wBAAwB;AACzD,UAAM,SAAS,MAAM,WAAW,IAAI,IAAI;AAOxC,WAAO;AAAA,EACT,SAAS,OAAO;AACd,YAAQ,MAAM,gDAAgD,KAAK;AACnE,WAAO;AAAA,EACT;AACF;AAGA,eAAsB,4BAA4B;AAAA,EAChD;AAAA,EACA;AAAA,EACA;AACF,GAIgC;AAC9B,MAAI;AACF,UAAM,KAAK,UAAU,SAAS;AAC9B,UAAM,IAAI,GAAG;AACb,UAAM,aAAa,GAAG,WAAW,wBAAwB;AAEzD,UAAM,SAAS,MAAM,WAClB,MAAM,EAAE,WAAW,EAAE,GAAG,QAAQ,EAAE,CAAC,EACnC,OAAO;AAAA,MACN,SAAS,kBAAkB;AAAA,MAC3B,OAAO,kBAAkB;AAAA,MACzB,aAAa,kBAAkB;AAAA,MAC/B,qBAAqB,kBAAkB;AAAA,MACvC,QAAQ,kBAAkB;AAAA,MAC1B,YAAY,kBAAkB;AAAA,MAC9B,WAAW,KAAK,IAAI;AAAA,IACtB,CAAC;AAOH,WAAO,kBAAkB;AAAA,EAC3B,SAAS,OAAO;AACd,YAAQ,MAAM,yCAAyC,KAAK;AAC5D,WAAO;AAAA,EACT;AACF;AAGA,eAAsB,oBAAoB;AAAA,EACxC;AAAA,EACA;AAAA,EACA;AAAA,EACA,WAAW;AAAA,EACX,aAAa;AAAA,EACb;AAAA,EACA;AAAA,EACA;AACF,GAS2C;AACzC,MAAI,CAAC,QAAQ,KAAK,WAAW,GAAG;AAC9B,WAAO;AAAA,EACT;AAEA,MAAI;AACF,UAAM,KAAK,UAAU,SAAS;AAC9B,UAAM,IAAI,GAAG;AACb,UAAM,aAAa,GAAG,WAAW,wBAAwB;AAGzD,UAAM,kBAA2C;AAAA,MAC/C,QAAQ,EAAE,GAAG,KAAK;AAAA,IACpB;AAGA,QAAI,cAAc;AAChB,sBAAgB,eAAe,EAAE,GAAG,YAAY;AAAA,IAClD;AAEA,QAAI,mBAAmB,QAAW;AAChC,sBAAgB,YAAY,EAAE,GAAG,cAAc;AAAA,IACjD;AAEA,QAAI,YAAY;AACd,sBAAgB,cAAc,EAAE,GAAG,UAAU;AAAA,IAC/C;AAGA,UAAM,QAAQ,aAAa,KAAK;AAGhC,UAAM,SAAS,MAAM,WAClB,MAAM,eAAe,EACrB,QAAQ,aAAa,IAAI,EACzB,KAAK,IAAI,EACT,MAAM,QAAQ,EACd,IAAI;AAGP,UAAM,cAAc,MAAM,WAAW,MAAM,eAAe,EAAE,MAAM;AAClE,UAAM,QAAQ,YAAY,SAAS;AAEnC,UAAM,UAAU,QAAQ,QAAQ,CAAC;AAEjC,UAAM,aAAkC,QAAQ;AAAA,MAC9C,CAAC,SAA0B,sBAAsB,IAAI;AAAA,IACvD;AAEA,WAAO,CAAC,YAAY,KAAK;AAAA,EAC3B,SAAS,OAAO;AACd,YAAQ,MAAM,wCAAwC,KAAK;AAC3D,WAAO,CAAC,CAAC,GAAG,CAAC;AAAA,EACf;AACF;AAGO,SAAS,sBACd,MACmB;AACnB,MAAI,CAAC,MAAM;AACT,WAAO,IAAI,kBAAkB;AAAA,EAC/B;AACA,QAAM,aAAgC,IAAI,kBAAkB;AAC5D,aAAW,QAAQ,KAAK;AACxB,aAAW,WAAW,KAAK;AAC3B,aAAW,OAAO,KAAK;AACvB,aAAW,SAAS,KAAK;AACzB,aAAW,UAAU,KAAK;AAC1B,aAAW,SAAS,KAAK;AACzB,aAAW,eAAe,KAAK;AAC/B,aAAW,OAAO,KAAK;AACvB,aAAW,aAAa,KAAK;AAC7B,aAAW,YAAY,KAAK;AAC5B,aAAW,UAAU,KAAK;AAC1B,aAAW,QAAQ,KAAK;AACxB,aAAW,UAAU,KAAK;AAC1B,aAAW,iBAAiB,KAAK;AACjC,aAAW,aAAa,KAAK;AAC7B,aAAW,YAAY,KAAK;AAC5B,aAAW,YAAY,KAAK;AAC5B,SAAO;AACT;AAGA,eAAsB,YAAY;AAAA,EAChC;AAAA,EACA;AAAA,EACA,WAAW;AAAA,EACX;AAAA,EACA;AACF,GAMiD;AAC/C,MAAI,mBAAmB,QAAW;AAChC,qBAAiB,KAAK,IAAI,IAAI,KAAK,KAAK,KAAK;AAAA,EAC/C;AACA,QAAM,mBAAwC,CAAC;AAE/C,QAAM,CAAC,UAAU,IAAI,MAAM,oBAAoB;AAAA,IAC7C;AAAA,IACA;AAAA,IACA,MAAM;AAAA,IACN;AAAA,IACA;AAAA,IACA;AAAA,EACF,CAAC;AACD,mBAAiB,KAAK,GAAG,WAAW,QAAQ,CAAC;AAE7C,QAAM,YAAY,oBAAI,IAA+B;AACrD,mBACG,OAAO,CAAC,SAAS;AAChB,QAAI,KAAK,mBAAmB,MAAM;AAChC,aAAO,CAAC,CAAC,KAAK;AAAA,IAChB,OAAO;AACL,aAAO,CAAC,CAAC,KAAK;AAAA,IAChB;AAAA,EACF,CAAC,EACA,QAAQ,CAAC,SAAS;AACjB,cAAU,IAAI,KAAK,UAAU,IAAI;AAAA,EACnC,CAAC;AAEH,QAAM,SAA8C,CAAC;AAKrD,mBAAiB,QAAQ,CAAC,SAAS;AACjC,UAAM,EAAE,MAAM,SAAS,MAAM,IAAI;AAEjC,QAAI,SAAS,UAAU,SAAS,WAAW,GAAG;AAC5C,UAAI,UAAU,IAAI,KAAK,GAAG;AACxB,eAAO,KAAK,EAAE,MAAM,QAAQ,CAAC;AAC7B,eAAO,KAAK;AAAA,UACV,MAAM,UAAU,IAAI,KAAK,EAAG;AAAA,UAC5B,SAAS,UAAU,IAAI,KAAK,EAAG;AAAA,QACjC,CAAC;AAAA,MACH;AAAA,IACF;AAAA,EACF,CAAC;AACD,MAAI,OAAO,SAAS,MAAM,GAAG;AAC3B,WAAO,OAAO,IAAI,CAAC;AAAA,EACrB;AACA,SAAO;AACT;AAsBO,IAAM,oBAAN,MAAwB;AA4B/B;;;AJ1RO,IAAM,mBAAN,cAA+B,MAAM;AAAA,EAE1C,YAAY,SAAiB,MAAe;AAC1C,UAAM,OAAO;AACb,SAAK,OAAO;AACZ,QAAI,KAAM,MAAK,OAAO;AAAA,EACxB;AACF;AAEO,IAAM,cAAN,cAA0B,6BAAc;AAAA,EAS7C,YAAY,QAAsD;AAChE,UAAM,MAAM;AAPd,SAAQ,uBAIJ,CAAC;AAIH,SAAK,eAAe,OAAO;AAC3B,SAAK,QAAQ,IAAI,cAAAC,QAAO;AAAA,MACtB,QAAQ;AAAA,MACR,SACE,KAAK,aAAa,SAAS,WAC3B;AAAA,IACJ,CAAC;AACD,SAAK,aACH,KAAK,aAAa,SAClB,KAAK,aAAa,SAAS,MAAM,eACjC,QAAQ,IAAI,iBACZ;AACF,SAAK,uBAAuB;AAAA,MAC1B,UACE,KAAK,aAAa,YAAY,YAC9B,QAAQ,IAAI;AAAA,MACd,WACE,KAAK,aAAa,YAAY,aAC9B,QAAQ,IAAI;AAAA,MACd,OACE,KAAK,aAAa,YAAY,SAC9B,QAAQ,IAAI;AAAA,IAChB;AAAA,EACF;AAAA,EAEA,oBAAoB;AAAA,IAClB;AAAA,IACA;AAAA,EACF,GAGsB;AACpB,UAAM,EAAE,OAAO,eAAe,IAAI;AAClC,UAAM,cAAiC;AAAA,MACrC,QAAQ;AAAA,MACR,GAAI,KAAK,aAAa,SAAS,QAAQ,CAAC;AAAA,MACxC,GAAI,kBAAkB,CAAC;AAAA,MAEvB,aAAa,KAAK;AAAA,MAClB,QACE,OAAO,qBAAqB,MAAM,MAClC,gBAAgB,cAChB,0BAAW;AAAA,MACb;AAAA,IACF;AACA,WAAO;AAAA,EACT;AAAA,EAEA,IAAI,OAA6C;AAC/C,WAAO,IAAI,uBAAsB,CAAC,eAAe;AAC/C,WAAK,KAAK,YAAY,KAAK;AAAA,IAC7B,CAAC;AAAA,EACH;AAAA,EAEA,MAAc,KACZ,YACA,OACe;AACf,QAAI;AACF,YAAM,EAAE,UAAU,MAAM,IAAI;AAE5B,YAAM,SAAS,KAAK;AACpB,YAAM,WAAW,MAAM,gBAAY,0BAAW;AAE9C,iBAAW,KAAK;AAAA,QACd,MAAM,yBAAU;AAAA,QAChB;AAAA,QACA;AAAA,MACF,CAAoB;AAEpB,UAAI,CAAC,KAAK,YAAY;AACpB,cAAM,IAAI;AAAA,UACR;AAAA,UACA;AAAA,QACF;AAAA,MACF;AACA,UAAI,CAAC,KAAK,aAAa,UAAU,CAAC,QAAQ,IAAI,gBAAgB;AAC5D,cAAM,IAAI;AAAA,UACR;AAAA,UACA;AAAA,QACF;AAAA,MACF;AAGA,YAAM,eAAe,SAAS,SAAS;AACvC,UAAI,eAAe,GAAG;AACpB,mBAAW,KAAK;AAAA,UACd,MAAM,yBAAU;AAAA,UAChB,UAAU;AAAA,YACR,SAAS,6DAA6D,YAAY;AAAA,YAClF,MAAM;AAAA,UACR;AAAA,QACF,CAAC;AAAA,MACH;AAGA,YAAM,oBAAoB,SAAS,OAAO,CAAC,MAAM,EAAE,SAAS,MAAM,EAAE,IAAI;AACxE,UAAI,CAAC,mBAAmB;AACtB,cAAM,IAAI;AAAA,UACR;AAAA,UACA;AAAA,QACF;AAAA,MACF;AAEA,YAAM,cAAc,MAAM,KAAK;AAAA,QAC7B;AAAA,QACA;AAAA,MACF;AAEA,YAAM,OAAO,KAAK,oBAAoB;AAAA,QACpC,UAAU;AAAA,QACV;AAAA,MACF,CAAC;AAED,YAAM,SAAS,MAAM,OAAO,KAAK,YAAY;AAAA,QAC3C;AAAA,UACE,QAAQ;AAAA,UACR,UAAU,CAAC;AAAA,UACX,OAAO;AAAA,QACT;AAAA,QACA;AAAA,UACE,MAAM,iBAAiB,IAAI;AAAA,UAC3B,SAAS;AAAA,YACP,GAAG,KAAK,aAAa,SAAS;AAAA,YAC9B,eAAe,UACb,KAAK,aAAa,UAAU,QAAQ,IAAI,cAC1C;AAAA,UACF;AAAA,QACF;AAAA,MACF;AAGA,YAAM,eAAe,cAAU,0BAAW,EAAE,MAAM,GAAG,CAAC,CAAC;AACvD,YAAM,oBAAoB,cAAU,0BAAW,EAAE,MAAM,GAAG,CAAC,CAAC;AAC5D,YAAM,UAAU,EAAE,UAAU,OAAO,WAAW,aAAa;AAE3D,UAAI,uBAAuB;AAE3B,uBAAiB,SAAS,oBAAoB,QAAQ,OAAO,GAAG;AAC9D,mBAAW,KAAK,KAAK;AAErB,YACE,MAAM,SAAS,yBAAU,wBACxB,MAAkC,OACnC;AACA,kCAAyB,MAAkC;AAAA,QAC7D;AAAA,MACF;AAEA,YAAM,cACJ,OAAO,mBAAmB,YAAY,WAClC,kBAAkB,UAClB,mBAAmB,SACf,OAAO,CAAC,MAAM,EAAE,SAAS,MAAM,EAChC,IAAI,CAAC,MAAM,EAAE,IAAI,EACjB,KAAK,EAAE,KAAK;AAErB,YAAM,KAAK;AAAA,QACT;AAAA,QACA;AAAA,QACA;AAAA,QACA;AAAA,QACA;AAAA,QACA;AAAA,MACF;AAEA,iBAAW,KAAK;AAAA,QACd,MAAM,yBAAU;AAAA,QAChB;AAAA,QACA;AAAA,MACF,CAAqB;AAAA,IACvB,SAAS,GAAY;AACnB,cAAQ,MAAM,4BAA4B,KAAK,UAAU,CAAC,CAAC;AAC3D,UAAI,OAAO;AACX,UAAI,UAAU,KAAK,UAAU,CAAC;AAC9B,UAAI,aAAa,kBAAkB;AACjC,eAAO,EAAE,QAAQ;AACjB,kBAAU,EAAE;AAAA,MACd,WAAW,aAAa,OAAO;AAC7B,eAAO,EAAE,QAAQ;AACjB,kBAAU,EAAE;AAAA,MACd;AACA,iBAAW,KAAK;AAAA,QACd,MAAM,yBAAU;AAAA,QAChB;AAAA,QACA,SAAS,gEAAgE,IAAI,KAAK,OAAO;AAAA,MAC3F,CAAkB;AAAA,IACpB,UAAE;AACA,iBAAW,SAAS;AAAA,IACtB;AAAA,EACF;AAAA;AAAA,EAGA,MAAgB,eACd,YACA,mBACA;AACA,UAAM,QAAQ,cAAc,KAAK,UAAU;AAE3C,UAAM,YAAY,KAAK,aAAa;AAEpC,UAAM,YAAY,MAAM,KAAK,qBAAqB;AAClD,QAAI,CAAC,WAAW;AACd,iBAAW,KAAK;AAAA,QACd,MAAM,yBAAU;AAAA,QAChB,UAAU;AAAA,UACR,SAAS;AAAA,UACT,MAAM;AAAA,QACR;AAAA,MACF,CAAC;AACD,aAAO,wBAAwB,CAAC,iBAAiB,CAAC;AAAA,IACpD;AAGA,QAAI,kBAAiC,CAAC;AAEtC,UAAM,eAAe,KAAK,aAAa,gBAAgB;AACvD,UAAM,iBAAiB,MAAM,YAAY;AAAA,MACvC;AAAA,MACA;AAAA,MACA,UAAU;AAAA,IACZ,CAAC;AAGD,sBAAkB,eAAe,IAAI,CAAC,YAAY;AAAA,MAChD,MAAM,OAAO;AAAA,MACb,SAAS,CAAC,EAAE,MAAM,QAAiB,MAAM,OAAO,QAAQ,CAAC;AAAA,IAC3D,EAAE;AAGF,UAAM,cAAc,gBAAgB;AAAA,MAClC,wBAAwB,CAAC,iBAAiB,CAAC;AAAA,IAC7C;AACA,WAAO;AAAA,EACT;AAAA;AAAA,EAGA,MAAgB,gBACd,YACA,OACA,cACA,mBACA,aACA,kBACA;AACA,UAAM,QAAQ,cAAc,KAAK,UAAU;AAE3C,UAAM,EAAE,UAAU,MAAM,IAAI;AAE5B,UAAM,YAAY,KAAK,aAAa;AAEpC,UAAM,YAAY,MAAM,KAAK,qBAAqB;AAClD,QAAI,CAAC,WAAW;AACd,iBAAW,KAAK;AAAA,QACd,MAAM,yBAAU;AAAA,QAChB,UAAU;AAAA,UACR,SAAS;AAAA,UACT,MAAM;AAAA,QACR;AAAA,MACF,CAAC;AACD;AAAA,IACF;AAGA,UAAM,aAAa,IAAI,kBAAkB;AACzC,eAAW,WAAW;AACtB,eAAW,QAAQ;AACnB,eAAW,OAAO;AAClB,eAAW,UAAU;AACrB,eAAW,eAAe;AAC1B,eAAW,QAAQ;AACnB,eAAW,aAAa;AACxB,eAAW,cAAU,0BAAW;AAEhC,UAAM,kBAAkB,EAAE,WAAW,mBAAmB,WAAW,CAAC;AAEpE,UAAM,kBAAkB,IAAI,kBAAkB;AAC9C,oBAAgB,WAAW;AAC3B,oBAAgB,QAAQ;AACxB,oBAAgB,OAAO;AACvB,oBAAgB,UAAU;AAC1B,oBAAgB,eAAe;AAC/B,oBAAgB,UAAU;AAC1B,oBAAgB,aAAa;AAC7B,oBAAgB,UAAU;AAC1B,oBAAgB,SAAS;AAEzB,UAAM,kBAAkB;AAAA,MACtB;AAAA,MACA,mBAAmB;AAAA,IACrB,CAAC;AAAA,EACH;AAAA,EAEQ,eAAe;AACrB,UAAM,QAAQ,KAAK,aAAa,SAAS,kBAAkB;AAE3D,UAAM,YAAY,gBAAAC,QAAI,KAAK;AAAA,MACzB,KAAK;AAAA,MACL,UAAU,KAAK,qBAAqB;AAAA,MACpC,WAAW,KAAK,qBAAqB;AAAA,MACrC,cAAc,KAAK,qBAAqB;AAAA,IAC1C,CAAC;AACD,WAAO;AAAA,EACT;AAAA,EAEA,MAAc,uBAAuB;AACnC,QAAI;AACF,YAAM,QAAQ,KAAK,aAAa,SAAS,kBAAkB;AAC3D,UAAI,CAAC,OAAO;AACV,cAAM,IAAI;AAAA,UACR;AAAA,UACA;AAAA,QACF;AAAA,MACF;AACA,UAAI,CAAC,KAAK,qBAAqB,OAAO;AACpC,YAAI,CAAC,KAAK,qBAAqB,UAAU;AACvC,gBAAM,IAAI;AAAA,YACR;AAAA,YACA;AAAA,UACF;AAAA,QACF;AACA,YAAI,CAAC,KAAK,qBAAqB,WAAW;AACxC,gBAAM,IAAI;AAAA,YACR;AAAA,YACA;AAAA,UACF;AAAA,QACF;AAAA,MACF;AACA,YAAM,mBAAmB,oBAAAC,QAAW,KAAK;AAAA,QACvC;AAAA,QACA,UAAU,KAAK,qBAAqB;AAAA,QACpC,WAAW,KAAK,qBAAqB;AAAA,QACrC,OAAO,KAAK,qBAAqB;AAAA,MACnC,CAAC;AAED,YAAM,aAAa,MAAM,iBAAiB,SAAS;AAAA,QACjD;AAAA,MACF;AACA,UAAI,cAAc,WAAW,QAAQ;AACnC,eAAO;AAAA,MACT,WAAW,cAAc,CAAC,WAAW,QAAQ;AAC3C,cAAM,iBAAiB,SAAS;AAAA,UAC9B;AAAA,QACF;AACA,eAAO;AAAA,MACT,OAAO;AACL,cAAM,IAAI,MAAM,8BAA8B;AAAA,MAChD;AAAA,IACF,SAAS,SAAS;AAChB,cAAQ;AAAA,QACN;AAAA,QACA,KAAK,UAAU,OAAO;AAAA,MACxB;AACA,aAAO;AAAA,IACT;AAAA,EACF;AACF;AAEA,SAAS,oBAAoB;AAC3B,MAAI,QAAQ,IAAI,YAAY;AAC1B,WAAO,QAAQ,IAAI;AAAA,EACrB,WAAW,QAAQ,IAAI,eAAe;AACpC,WAAO,QAAQ,IAAI;AAAA,EACrB,OAAO;AACL,WAAO,QAAQ,IAAI,oBAAoB;AAAA,EACzC;AACF;AAKO,SAAS,wBACd,UACA,cACe;AACf,QAAM,iBAAgC,CAAC;AAGvC,MAAI,cAAc;AAChB,mBAAe,KAAK;AAAA,MAClB,MAAM;AAAA,MACN,SAAS;AAAA,IACX,CAAC;AAAA,EACH;AAGA,aAAW,OAAO,UAAU;AAC1B,QAAI,IAAI,SAAS,QAAQ;AACvB,qBAAe,KAAK;AAAA,QAClB,MAAM;AAAA,QACN,SACE,OAAO,IAAI,YAAY,WACnB,CAAC,EAAE,MAAM,QAAQ,MAAM,IAAI,QAAQ,CAAC,IACpC,IAAI,QAAQ,IAAI,CAAC,SAAS;AACxB,cAAI,KAAK,SAAS,QAAQ;AACxB,mBAAO,EAAE,MAAM,QAAQ,MAAM,KAAK,KAAK;AAAA,UACzC,OAAO;AACL,mBAAO;AAAA,cACL,MAAM;AAAA,cACN,WAAW,EAAE,KAAK,KAAK,OAAO,GAAG;AAAA,YACnC;AAAA,UACF;AAAA,QACF,CAAC;AAAA,MACT,CAAC;AAAA,IACH,WAAW,IAAI,SAAS,aAAa;AACnC,qBAAe,KAAK;AAAA,QAClB,MAAM;AAAA,QACN,SAAS,IAAI,UAAU,CAAC,EAAE,MAAM,QAAQ,MAAM,IAAI,QAAQ,CAAC,IAAI,CAAC;AAAA,QAChE,YAAY,IAAI,WAAW,IAAI,CAAC,QAAkB;AAAA,UAChD,IAAI,GAAG;AAAA,UACP,MAAM;AAAA,UACN,UAAU;AAAA,YACR,MAAM,GAAG,SAAS;AAAA,YAClB,WAAW,GAAG,SAAS;AAAA,UACzB;AAAA,QACF,EAAE;AAAA,MACJ,CAAC;AAAA,IACH,WAAW,IAAI,SAAS,QAAQ;AAC9B,qBAAe,KAAK;AAAA,QAClB,MAAM;AAAA,QACN,cAAc,IAAI;AAAA,QAClB,SAAS,IAAI,UAAU,CAAC,EAAE,MAAM,QAAQ,MAAM,IAAI,QAAQ,CAAC,IAAI,CAAC;AAAA,MAClE,CAAC;AAAA,IACH;AAAA,EACF;AAEA,SAAO;AACT;","names":["import_client","OpenAI","tcb","managedTcb"]}
1
+ {"version":3,"sources":["../src/index.ts","../src/agent.ts","../src/utils.ts","../src/stream.ts","../src/constant.ts","../src/chat_history.ts"],"sourcesContent":["export * from \"./agent\";\n\nexport * from \"./types\";\n\nexport * from \"./stream\";\n\nexport * from \"./chat_history\";\n","import {\n RunAgentInput,\n Message,\n AbstractAgent,\n AgentConfig,\n BaseEvent,\n EventType,\n RunStartedEvent,\n RunFinishedEvent,\n RunErrorEvent,\n TextMessageContentEvent,\n ToolCall,\n} from \"@ag-ui/client\";\nimport tcb from \"@cloudbase/node-sdk\";\nimport managedTcb from \"@cloudbase/manager-node\";\nimport OpenAI from \"openai\";\nimport { randomUUID } from \"crypto\";\nimport { camelToSnakeKeys } from \"./utils\";\nimport { processYuanqiStream } from \"./stream\";\nimport { Observable, Subscriber } from \"rxjs\";\nimport {\n createChatHistory,\n queryForLLM,\n ChatHistoryEntity,\n} from \"./chat_history\";\nimport { CHAT_HISTORY_DATA_SOURCE } from \"./constant\";\nimport { YuanqiConfig, ChatMessage, YuanqiChatRequest } from \"./types\";\n\nexport class YuanqiAgentError extends Error {\n code?: string;\n constructor(message: string, code?: string) {\n super(message);\n this.name = \"YuanqiAgentError\";\n if (code) this.code = code;\n }\n}\n\nexport class YuanqiAgent extends AbstractAgent {\n protected yuanqiConfig: YuanqiConfig;\n private finalAppId: string;\n private finalCloudCredential: {\n secretId?: string;\n secretKey?: string;\n token?: string;\n } = {};\n private model: OpenAI;\n constructor(config: AgentConfig & { yuanqiConfig: YuanqiConfig }) {\n super(config);\n this.yuanqiConfig = config.yuanqiConfig;\n this.model = new OpenAI({\n apiKey: \"\",\n baseURL:\n this.yuanqiConfig.request?.baseUrl ||\n \"https://yuanqi.tencent.com/openapi/v1/agent\",\n });\n this.finalAppId =\n this.yuanqiConfig.appId ||\n this.yuanqiConfig.request?.body?.assistantId ||\n process.env.YUANQI_APP_ID ||\n \"\";\n this.finalCloudCredential = {\n secretId:\n this.yuanqiConfig.credential?.secretId ||\n process.env.TENCENTCLOUD_SECRETID,\n secretKey:\n this.yuanqiConfig.credential?.secretKey ||\n process.env.TENCENTCLOUD_SECRETKEY,\n token:\n this.yuanqiConfig.credential?.token ||\n process.env.TENCENTCLOUD_SESSIONTOKEN,\n };\n }\n\n generateRequestBody({\n messages,\n input,\n }: {\n messages: ChatMessage[];\n input: RunAgentInput;\n }): YuanqiChatRequest {\n const { state, forwardedProps } = input;\n const requestBody: YuanqiChatRequest = {\n stream: true,\n ...(this.yuanqiConfig.request?.body || {}),\n ...(forwardedProps || {}),\n\n assistantId: this.finalAppId,\n userId:\n state?.__request_context__?.user?.id ||\n forwardedProps?.userId ||\n randomUUID(),\n messages,\n };\n return requestBody;\n }\n\n run(input: RunAgentInput): Observable<BaseEvent> {\n return new Observable<BaseEvent>((subscriber) => {\n this._run(subscriber, input);\n });\n }\n\n private async _run(\n subscriber: Subscriber<BaseEvent>,\n input: RunAgentInput\n ): Promise<void> {\n try {\n const { messages, runId } = input;\n\n const openai = this.model as OpenAI;\n const threadId = input.threadId || randomUUID();\n\n subscriber.next({\n type: EventType.RUN_STARTED,\n threadId,\n runId,\n } as RunStartedEvent);\n\n if (!this.finalAppId) {\n throw new YuanqiAgentError(\n \"YUANQI_APP_ID is required, check your env variables or config passed with the adapter\",\n \"MISSING_YUANQI_APP_ID\"\n );\n }\n if (!this.yuanqiConfig.appKey && !process.env.YUANQI_APP_KEY) {\n throw new YuanqiAgentError(\n \"YUANQI_APP_KEY is required, check your env variables or config passed with the adapter\",\n \"MISSING_YUANQI_APP_KEY\"\n );\n }\n\n // Warn user if messages are being trimmed (only using latest user message)\n const trimmedCount = messages.length - 1;\n if (trimmedCount > 0) {\n subscriber.next({\n type: EventType.RAW,\n rawEvent: {\n message: `Yuanqi handles message history itself, so that a total of ${trimmedCount} messages before the last user message will be trimmed.`,\n type: \"warn\",\n },\n });\n }\n\n // Get the latest user message for saving to history\n const latestUserMessage = messages.filter((m) => m.role === \"user\").pop();\n if (!latestUserMessage) {\n throw new YuanqiAgentError(\n \"No user message found, please send a message first.\",\n \"MESSAGE_FORMAT_ERROR\"\n );\n }\n\n const allMessages = await this.getChatHistory(\n subscriber,\n input,\n latestUserMessage\n );\n\n const body = this.generateRequestBody({\n messages: allMessages,\n input,\n });\n\n const stream = await openai.chat.completions.create(\n {\n stream: true,\n messages: [],\n model: \"\",\n },\n {\n body: camelToSnakeKeys(body),\n headers: {\n ...this.yuanqiConfig.request?.headers,\n Authorization: `Bearer ${\n this.yuanqiConfig.appKey || process.env.YUANQI_APP_KEY\n }`,\n },\n }\n );\n\n // Process stream and emit AGUI events, collect full response\n const userRecordId = `record-${randomUUID().slice(0, 8)}`;\n const assistantRecordId = `record-${randomUUID().slice(0, 8)}`;\n const context = { threadId, runId, messageId: userRecordId };\n\n let fullAssistantContent = \"\";\n\n for await (const event of processYuanqiStream(stream, context)) {\n subscriber.next(event);\n // Collect assistant content from TEXT_MESSAGE_CONTENT events\n if (\n event.type === EventType.TEXT_MESSAGE_CONTENT &&\n (event as TextMessageContentEvent).delta\n ) {\n fullAssistantContent += (event as TextMessageContentEvent).delta;\n }\n }\n\n const userContent =\n typeof latestUserMessage?.content === \"string\"\n ? latestUserMessage.content\n : latestUserMessage?.content\n ?.filter((c) => c.type === \"text\")\n .map((c) => c.text)\n .join(\"\") || \"\";\n\n await this.saveChatHistory(\n subscriber,\n input,\n userRecordId,\n assistantRecordId,\n userContent,\n fullAssistantContent\n );\n\n subscriber.next({\n type: EventType.RUN_FINISHED,\n threadId,\n runId,\n } as RunFinishedEvent);\n } catch (e: unknown) {\n console.error(\"[ERROR] Uncaught error: \", JSON.stringify(e));\n let code = \"UNKNOWN_ERROR\";\n let message = JSON.stringify(e);\n if (e instanceof YuanqiAgentError) {\n code = e.code || \"AGENT_ERROR\";\n message = e.message;\n } else if (e instanceof Error) {\n code = e.name || \"ERROR\";\n message = e.message;\n }\n subscriber.next({\n type: EventType.RUN_ERROR,\n code,\n message: `Sorry, an error occurred while running the agent: Error code ${code}, ${message}`,\n } as RunErrorEvent);\n } finally {\n subscriber.complete();\n }\n }\n\n // Can be override by subclasses\n protected async getChatHistory(\n subscriber: Subscriber<BaseEvent>,\n input: RunAgentInput,\n latestUserMessage: Message\n ) {\n const botId = `bot-yuanqi-${this.finalAppId}`;\n\n const { threadId } = input;\n\n const tcbClient = this.getTcbClient();\n\n const isDBReady = await this.checkIsDatabaseReady();\n if (!isDBReady) {\n subscriber.next({\n type: EventType.RAW,\n rawEvent: {\n message: `Chat history database is not ready, skip history loading.`,\n type: \"warn\",\n },\n });\n return convertMessagesToOpenAI([latestUserMessage]);\n }\n\n // Fetch chat history from database using queryForLLM\n let historyMessages: ChatMessage[] = [];\n\n const historyCount = this.yuanqiConfig.historyCount ?? 10;\n const historyRecords = await queryForLLM({\n tcbClient,\n botId,\n conversation: threadId,\n pageSize: historyCount,\n });\n\n // Convert queryForLLM result to ChatMessage format\n historyMessages = historyRecords.map((record) => ({\n role: record.role as \"user\" | \"assistant\",\n content: [{ type: \"text\" as const, text: record.content }],\n }));\n\n // Combine history messages with current messages\n const allMessages = historyMessages.concat(\n convertMessagesToOpenAI([latestUserMessage])\n );\n return allMessages;\n }\n\n // Can be override by subclasses\n protected async saveChatHistory(\n subscriber: Subscriber<BaseEvent>,\n input: RunAgentInput,\n userRecordId: string,\n assistantRecordId: string,\n userContent: string,\n assistantContent: string\n ) {\n const botId = `bot-yuanqi-${this.finalAppId}`;\n\n const { threadId, runId } = input;\n\n const tcbClient = this.getTcbClient();\n\n const isDBReady = await this.checkIsDatabaseReady();\n if (!isDBReady) {\n subscriber.next({\n type: EventType.RAW,\n rawEvent: {\n message: `Chat history database is not ready, skip history saving.`,\n type: \"warn\",\n },\n });\n return;\n }\n\n // Save message pair to history\n const userEntity = new ChatHistoryEntity();\n userEntity.recordId = userRecordId;\n userEntity.botId = botId;\n userEntity.role = \"user\";\n userEntity.content = userContent;\n userEntity.conversation = threadId;\n userEntity.reply = assistantRecordId;\n userEntity.triggerSrc = \"\";\n userEntity.traceId = randomUUID();\n\n await createChatHistory({ tcbClient, chatHistoryEntity: userEntity });\n\n const assistantEntity = new ChatHistoryEntity();\n assistantEntity.recordId = assistantRecordId;\n assistantEntity.botId = botId;\n assistantEntity.role = \"assistant\";\n assistantEntity.content = assistantContent;\n assistantEntity.conversation = threadId;\n assistantEntity.replyTo = userRecordId;\n assistantEntity.triggerSrc = \"\";\n assistantEntity.traceId = runId;\n assistantEntity.status = \"done\";\n\n await createChatHistory({\n tcbClient,\n chatHistoryEntity: assistantEntity,\n });\n }\n\n private getTcbClient() {\n const envId = this.yuanqiConfig.envId || getCloudbaseEnvId();\n\n const tcbClient = tcb.init({\n env: envId,\n secretId: this.finalCloudCredential.secretId,\n secretKey: this.finalCloudCredential.secretKey,\n sessionToken: this.finalCloudCredential.token,\n });\n return tcbClient;\n }\n\n private async checkIsDatabaseReady() {\n try {\n const envId = this.yuanqiConfig.envId || getCloudbaseEnvId();\n if (!envId) {\n throw new YuanqiAgentError(\n \"When saving chat history to CloudBase, CLOUDBASE_ENV_ID is required, check your env variables or config passed with the adapter\",\n \"MISSING_CLOUDBASE_ENV_ID\"\n );\n }\n if (!this.finalCloudCredential.token) {\n if (!this.finalCloudCredential.secretId) {\n throw new YuanqiAgentError(\n \"When saving chat history to CloudBase, TENCENTCLOUD_SECRETID is required, check your env variables or config passed with the adapter\",\n \"MISSING_SECRET_ID\"\n );\n }\n if (!this.finalCloudCredential.secretKey) {\n throw new YuanqiAgentError(\n \"When saving chat history to CloudBase, TENCENTCLOUD_SECRETKEY is required, check your env variables or config passed with the adapter\",\n \"MISSING_SECRET_KEY\"\n );\n }\n }\n const managedTcbClient = managedTcb.init({\n envId,\n secretId: this.finalCloudCredential.secretId,\n secretKey: this.finalCloudCredential.secretKey,\n token: this.finalCloudCredential.token,\n });\n\n const checkDBRes = await managedTcbClient.database.checkCollectionExists(\n CHAT_HISTORY_DATA_SOURCE\n );\n if (checkDBRes && checkDBRes.Exists) {\n return true;\n } else if (checkDBRes && !checkDBRes.Exists) {\n await managedTcbClient.database.createCollection(\n CHAT_HISTORY_DATA_SOURCE\n );\n return true;\n } else {\n throw new Error(\"Check database exists failed\");\n }\n } catch (dbError) {\n console.error(\n \"[ERROR] Failed to check/create chat history collection:\",\n JSON.stringify(dbError)\n );\n return false;\n }\n }\n}\n\nfunction getCloudbaseEnvId() {\n if (process.env.CBR_ENV_ID) {\n return process.env.CBR_ENV_ID;\n } else if (process.env.SCF_NAMESPACE) {\n return process.env.SCF_NAMESPACE;\n } else {\n return process.env.CLOUDBASE_ENV_ID || \"\";\n }\n}\n\n/**\n * Convert AGUI messages to OpenAI chat completion format\n */\nexport function convertMessagesToOpenAI(\n messages: Message[],\n systemPrompt?: string\n): ChatMessage[] {\n const openaiMessages: ChatMessage[] = [];\n\n // Add system prompt if provided\n if (systemPrompt) {\n openaiMessages.push({\n role: \"system\",\n content: systemPrompt,\n });\n }\n\n // Convert messages\n for (const msg of messages) {\n if (msg.role === \"user\") {\n openaiMessages.push({\n role: \"user\",\n content:\n typeof msg.content === \"string\"\n ? [{ type: \"text\", text: msg.content }]\n : msg.content.map((item) => {\n if (item.type === \"text\") {\n return { type: \"text\", text: item.text };\n } else {\n return {\n type: \"image_url\",\n image_url: { url: item.url || \"\" },\n };\n }\n }),\n });\n } else if (msg.role === \"assistant\") {\n openaiMessages.push({\n role: \"assistant\",\n content: msg.content ? [{ type: \"text\", text: msg.content }] : [],\n tool_calls: msg.toolCalls?.map((tc: ToolCall) => ({\n id: tc.id,\n type: \"function\" as const,\n function: {\n name: tc.function.name,\n arguments: tc.function.arguments,\n },\n })),\n });\n } else if (msg.role === \"tool\") {\n openaiMessages.push({\n role: \"tool\",\n tool_call_id: msg.toolCallId,\n content: msg.content ? [{ type: \"text\", text: msg.content }] : [],\n });\n }\n }\n\n return openaiMessages;\n}\n","/**\n * 将小驼峰字符串转换为下划线格式\n * 例如: \"userName\" -> \"user_name\"\n */\nfunction camelToSnake(str: string): string {\n return str.replace(/[A-Z]/g, (letter) => `_${letter.toLowerCase()}`);\n}\n\n/**\n * 递归地将对象的所有小驼峰属性名转换为下划线格式\n */\nexport function camelToSnakeKeys<T>(obj: T): T {\n if (obj === null || obj === undefined) {\n return obj;\n }\n\n if (Array.isArray(obj)) {\n return obj.map((item) => camelToSnakeKeys(item)) as T;\n }\n\n if (typeof obj === \"object\") {\n const result: Record<string, unknown> = {};\n for (const [key, value] of Object.entries(obj)) {\n const snakeKey = camelToSnake(key);\n result[snakeKey] = camelToSnakeKeys(value);\n }\n return result as T;\n }\n\n return obj;\n}\n\nexport function genRandomStr(length: number): string {\n const chars = \"abcdefghijklmnopqrstuvwxyz0123456789\";\n let result = \"\";\n for (let i = 0; i < length; i++) {\n result += chars.charAt(Math.floor(Math.random() * chars.length));\n }\n return result;\n}\n","import OpenAI from \"openai\";\nimport { EventType } from \"@ag-ui/client\";\n\nexport interface StreamContext {\n threadId: string;\n runId: string;\n messageId: string;\n}\n\nexport interface StreamState {\n hasStarted: boolean;\n fullContent: string;\n toolCallsMap: Map<string, { name: string; args: string }>;\n}\n\nexport type Delta =\n OpenAI.Chat.Completions.ChatCompletionChunk[\"choices\"][number][\"delta\"] & {\n reasoning_content?: string;\n };\n\nexport async function* processYuanqiStream(\n stream: AsyncIterable<OpenAI.Chat.Completions.ChatCompletionChunk>,\n context: StreamContext\n) {\n const { threadId, runId, messageId } = context;\n const state: StreamState = {\n hasStarted: false,\n fullContent: \"\",\n toolCallsMap: new Map(),\n };\n const reasoningState: StreamState = {\n hasStarted: false,\n fullContent: \"\",\n toolCallsMap: new Map(),\n };\n\n for await (const chunk of stream) {\n const delta = chunk.choices[0]?.delta as Delta;\n if (!delta) continue;\n\n if (delta.role === \"tool\") {\n const toolCallId = (delta as any).tool_call_id;\n if (toolCallId) {\n if (state.toolCallsMap.has(toolCallId)) {\n yield {\n type: EventType.TOOL_CALL_END,\n threadId,\n runId,\n toolCallId,\n };\n state.toolCallsMap.delete(toolCallId);\n }\n yield {\n type: EventType.TOOL_CALL_RESULT,\n threadId,\n runId,\n toolCallId,\n content: delta.content || \"\",\n };\n }\n continue;\n }\n\n // Handle text content\n if (delta.content) {\n // End reasoning message if it was started\n if (reasoningState.hasStarted) {\n reasoningState.hasStarted = false;\n yield {\n type: EventType.THINKING_TEXT_MESSAGE_END,\n threadId,\n runId,\n messageId,\n };\n yield {\n type: EventType.THINKING_END,\n threadId,\n runId,\n messageId,\n };\n }\n\n if (!state.hasStarted) {\n yield {\n type: EventType.TEXT_MESSAGE_START,\n threadId,\n runId,\n messageId,\n role: \"assistant\",\n };\n state.hasStarted = true;\n }\n\n state.fullContent += delta.content;\n yield {\n type: EventType.TEXT_MESSAGE_CONTENT,\n threadId,\n runId,\n messageId,\n delta: delta.content,\n };\n }\n\n // Handle reasoning content\n if (delta.reasoning_content) {\n if (!reasoningState.hasStarted) {\n yield {\n type: EventType.THINKING_START,\n threadId,\n runId,\n messageId,\n };\n yield {\n type: EventType.THINKING_TEXT_MESSAGE_START,\n threadId,\n runId,\n messageId,\n role: \"assistant\",\n };\n reasoningState.hasStarted = true;\n }\n\n reasoningState.fullContent += delta.reasoning_content;\n yield {\n type: EventType.THINKING_TEXT_MESSAGE_CONTENT,\n threadId,\n runId,\n messageId,\n delta: delta.reasoning_content,\n };\n }\n\n // Handle tool calls\n if (delta.tool_calls) {\n for (const toolCall of delta.tool_calls) {\n const toolCallId = toolCall.id || `tool_${toolCall.index}`;\n\n if (toolCall.function?.name) {\n // Tool call start\n yield {\n type: EventType.TOOL_CALL_START,\n threadId,\n runId,\n toolCallId,\n toolCallName: toolCall.function.name,\n };\n\n // If first chunk contains arguments, emit TOOL_CALL_ARGS event\n if (toolCall.function.arguments) {\n yield {\n type: EventType.TOOL_CALL_ARGS,\n threadId,\n runId,\n toolCallId,\n delta: toolCall.function.arguments,\n };\n }\n\n state.toolCallsMap.set(toolCallId, {\n name: toolCall.function.name,\n args: toolCall.function.arguments || \"\",\n });\n } else if (toolCall.function?.arguments) {\n // Tool call arguments delta\n const existing = state.toolCallsMap.get(toolCallId);\n if (existing) {\n existing.args += toolCall.function.arguments;\n\n yield {\n type: EventType.TOOL_CALL_ARGS,\n threadId,\n runId,\n toolCallId,\n delta: toolCall.function.arguments,\n };\n }\n }\n }\n }\n }\n\n // Emit TEXT_MESSAGE_END if we had text content\n if (state.hasStarted) {\n yield {\n type: EventType.TEXT_MESSAGE_END,\n threadId,\n runId,\n messageId,\n };\n }\n\n if (reasoningState.hasStarted) {\n yield {\n type: EventType.THINKING_TEXT_MESSAGE_END,\n threadId,\n runId,\n messageId,\n };\n yield {\n type: EventType.THINKING_END,\n threadId,\n runId,\n messageId,\n };\n }\n\n // Emit TOOL_CALL_END for all tool calls\n for (const [toolCallId] of state.toolCallsMap) {\n yield {\n type: EventType.TOOL_CALL_END,\n threadId,\n runId,\n toolCallId,\n };\n }\n}\n","// 对话数据模型\nexport const CHAT_HISTORY_DATA_SOURCE = \"ai_bot_chat_history_5hobd2b\";\n","import tcb from \"@cloudbase/node-sdk\";\nimport { CHAT_HISTORY_DATA_SOURCE } from \"./constant\";\nimport { genRandomStr } from \"./utils\";\n\nfunction genRecordId(): string {\n return \"record-\" + genRandomStr(8);\n}\n\n// Create a new chat history record\nexport async function createChatHistory({\n tcbClient,\n chatHistoryEntity,\n}: {\n tcbClient: tcb.CloudBase;\n chatHistoryEntity: ChatHistoryEntity;\n}): Promise<string | undefined> {\n try {\n const recordId = chatHistoryEntity.recordId || genRecordId();\n const data = {\n record_id: recordId,\n bot_id: chatHistoryEntity.botId,\n role: chatHistoryEntity.role,\n content: chatHistoryEntity.content,\n sender: chatHistoryEntity.sender,\n conversation: chatHistoryEntity.conversation,\n type: chatHistoryEntity.type,\n image: chatHistoryEntity.image,\n trigger_src: chatHistoryEntity.triggerSrc,\n origin_msg: chatHistoryEntity.originMsg,\n reply_to: chatHistoryEntity.replyTo,\n reply: chatHistoryEntity.reply,\n trace_id: chatHistoryEntity.traceId,\n need_async_reply: chatHistoryEntity.needAsyncReply,\n async_reply: chatHistoryEntity.asyncReply,\n createdAt: Date.now(),\n updatedAt: Date.now(),\n };\n\n const db = tcbClient.database();\n const collection = db.collection(CHAT_HISTORY_DATA_SOURCE);\n const result = await collection.add(data);\n\n // console.log(\n // `Create record: chatHistoryEntity:${JSON.stringify(\n // chatHistoryEntity\n // )}, result: ${JSON.stringify(result)}`\n // );\n return recordId;\n } catch (error) {\n console.error(\"Failed to create chat history record, error:\", error);\n return undefined;\n }\n}\n\n// Update chat history by record ID\nexport async function updateChatHistoryByRecordId({\n tcbClient,\n recordId,\n chatHistoryEntity,\n}: {\n tcbClient: tcb.CloudBase;\n recordId: string;\n chatHistoryEntity: ChatHistoryEntity;\n}): Promise<string | undefined> {\n try {\n const db = tcbClient.database();\n const _ = db.command;\n const collection = db.collection(CHAT_HISTORY_DATA_SOURCE);\n\n const result = await collection\n .where({ record_id: _.eq(recordId) })\n .update({\n content: chatHistoryEntity.content,\n image: chatHistoryEntity.image,\n async_reply: chatHistoryEntity.asyncReply,\n recommend_questions: chatHistoryEntity.recommendQuestions,\n status: chatHistoryEntity.status,\n origin_msg: chatHistoryEntity.originMsg,\n updatedAt: Date.now(),\n });\n\n // console.log(\n // `Update record: recordId: ${recordId}, chatHistoryEntity:${JSON.stringify(\n // chatHistoryEntity\n // )}, result: ${JSON.stringify(result)}`\n // );\n return chatHistoryEntity.recordId;\n } catch (error) {\n console.error(\"Failed to update chat history, error:\", error);\n return undefined;\n }\n}\n\n// Query chat history from database\nexport async function describeChatHistory({\n tcbClient,\n botId,\n sort,\n pageSize = 10,\n pageNumber = 1,\n conversation,\n startCreatedAt,\n triggerSrc,\n}: {\n tcbClient: tcb.CloudBase;\n botId: string;\n sort: \"asc\" | \"desc\";\n pageSize?: number;\n pageNumber?: number;\n conversation?: string;\n startCreatedAt?: number;\n triggerSrc?: string;\n}): Promise<[ChatHistoryEntity[], number]> {\n if (!sort || sort.length === 0) {\n sort = \"desc\";\n }\n\n try {\n const db = tcbClient.database();\n const _ = db.command;\n const collection = db.collection(CHAT_HISTORY_DATA_SOURCE);\n\n // Build where conditions\n const whereConditions: Record<string, unknown> = {\n bot_id: _.eq(botId),\n };\n\n // Add optional filters\n if (conversation) {\n whereConditions.conversation = _.eq(conversation);\n }\n\n if (startCreatedAt !== undefined) {\n whereConditions.createdAt = _.gt(startCreatedAt);\n }\n\n if (triggerSrc) {\n whereConditions.trigger_src = _.eq(triggerSrc);\n }\n\n // Calculate skip for pagination\n const skip = (pageNumber - 1) * pageSize;\n\n // Query records\n const result = await collection\n .where(whereConditions)\n .orderBy(\"createdAt\", sort)\n .skip(skip)\n .limit(pageSize)\n .get();\n\n // Get total count\n const countResult = await collection.where(whereConditions).count();\n const total = countResult.total || 0;\n\n const records = result?.data || [];\n\n const entityList: ChatHistoryEntity[] = records.map(\n (item: ChatHistoryData) => transDataToChatEntity(item)\n );\n\n return [entityList, total];\n } catch (error) {\n console.error(\"Failed to query chat history, error:\", error);\n return [[], 0];\n }\n}\n\n// Transform data to ChatHistoryEntity structure\nexport function transDataToChatEntity(\n item: ChatHistoryData\n): ChatHistoryEntity {\n if (!item) {\n return new ChatHistoryEntity();\n }\n const chatEntity: ChatHistoryEntity = new ChatHistoryEntity();\n chatEntity.botId = item.bot_id;\n chatEntity.recordId = item.record_id;\n chatEntity.role = item.role;\n chatEntity.status = item.status;\n chatEntity.content = item.content;\n chatEntity.sender = item.sender;\n chatEntity.conversation = item.conversation;\n chatEntity.type = item.type;\n chatEntity.triggerSrc = item.trigger_src;\n chatEntity.originMsg = item.origin_msg;\n chatEntity.replyTo = item.reply_to;\n chatEntity.reply = item.reply;\n chatEntity.traceId = item.trace_id;\n chatEntity.needAsyncReply = item.need_async_reply;\n chatEntity.asyncReply = item.async_reply;\n chatEntity.createdAt = item.createdAt;\n chatEntity.updatedAt = item.updatedAt;\n return chatEntity;\n}\n\n// Query history records for LLM, get the most recent 10 conversation pairs (20 records)\nexport async function queryForLLM({\n tcbClient,\n botId,\n conversation,\n pageSize = 10,\n startCreatedAt,\n triggerSrc,\n}: {\n tcbClient: tcb.CloudBase;\n botId: string;\n conversation: string;\n pageSize?: number;\n startCreatedAt?: number;\n triggerSrc?: string;\n}): Promise<{ role: string; content: string }[]> {\n if (startCreatedAt === undefined) {\n startCreatedAt = Date.now() - 24 * 60 * 60 * 1000;\n }\n const recordEntityList: ChatHistoryEntity[] = [];\n\n const [recordList] = await describeChatHistory({\n tcbClient,\n botId,\n sort: \"desc\",\n pageSize,\n conversation,\n startCreatedAt,\n triggerSrc,\n });\n recordEntityList.push(...recordList.reverse());\n\n const entityMap = new Map<string, ChatHistoryEntity>();\n recordEntityList\n .filter((item) => {\n if (item.needAsyncReply === true) {\n return !!item.asyncReply;\n } else {\n return !!item.content;\n }\n })\n .forEach((item) => {\n entityMap.set(item.recordId, item);\n });\n\n const result: { role: string; content: string }[] = [];\n /*\n 1. Strongly depends on database history data, model history data has role order requirements\n 2. Need to ensure that no matter what bug occurs, always get a complete and usable user + assistant pair, otherwise the request will fail\n */\n recordEntityList.forEach((item) => {\n const { role, content, reply } = item;\n // When calling LLM, empty content will cause failure, so filter out conversations with empty content\n if (role === \"user\" && content?.length !== 0) {\n if (entityMap.has(reply)) {\n result.push({ role, content });\n result.push({\n role: entityMap.get(reply)!.role,\n content: entityMap.get(reply)!.content,\n });\n }\n }\n });\n if (result.length % 2 === 1) {\n result.splice(-1, 1);\n }\n return result;\n}\n\nexport interface ChatHistoryData {\n bot_id: string;\n record_id: string;\n role: string;\n status: string;\n content: string;\n sender: string;\n conversation: string;\n type: string;\n trigger_src: string;\n origin_msg: string;\n reply_to: string;\n reply: string;\n trace_id: string;\n need_async_reply: boolean;\n async_reply: string;\n createdAt: number;\n updatedAt: number;\n}\n\nexport class ChatHistoryEntity {\n id: number;\n botId: string;\n // 对话唯一id\n recordId: string;\n role: string;\n content: string;\n recommendQuestions: string[];\n sender: string;\n conversation: string;\n type: string;\n /**\n * 消息状态,pending done error cancel\n */\n status: string;\n image: string;\n triggerSrc: string;\n originMsg: string;\n replyTo: string;\n reply: string;\n traceId: string;\n needAsyncReply: boolean;\n asyncReply: string;\n createTime: string;\n updateTime: string;\n createdAt: number;\n updatedAt: number;\n event: string;\n}\n"],"mappings":"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","names":["import_client","OpenAI","tcb","managedTcb"]}
package/dist/index.mjs CHANGED
@@ -348,6 +348,7 @@ function transDataToChatEntity(item) {
348
348
  async function queryForLLM({
349
349
  tcbClient,
350
350
  botId,
351
+ conversation,
351
352
  pageSize = 10,
352
353
  startCreatedAt,
353
354
  triggerSrc
@@ -361,6 +362,7 @@ async function queryForLLM({
361
362
  botId,
362
363
  sort: "desc",
363
364
  pageSize,
365
+ conversation,
364
366
  startCreatedAt,
365
367
  triggerSrc
366
368
  });
@@ -481,6 +483,7 @@ var YuanqiAgent = class extends AbstractAgent {
481
483
  }
482
484
  const allMessages = await this.getChatHistory(
483
485
  subscriber,
486
+ input,
484
487
  latestUserMessage
485
488
  );
486
489
  const body = this.generateRequestBody({
@@ -546,8 +549,9 @@ var YuanqiAgent = class extends AbstractAgent {
546
549
  }
547
550
  }
548
551
  // Can be override by subclasses
549
- async getChatHistory(subscriber, latestUserMessage) {
552
+ async getChatHistory(subscriber, input, latestUserMessage) {
550
553
  const botId = `bot-yuanqi-${this.finalAppId}`;
554
+ const { threadId } = input;
551
555
  const tcbClient = this.getTcbClient();
552
556
  const isDBReady = await this.checkIsDatabaseReady();
553
557
  if (!isDBReady) {
@@ -565,6 +569,7 @@ var YuanqiAgent = class extends AbstractAgent {
565
569
  const historyRecords = await queryForLLM({
566
570
  tcbClient,
567
571
  botId,
572
+ conversation: threadId,
568
573
  pageSize: historyCount
569
574
  });
570
575
  historyMessages = historyRecords.map((record) => ({
@@ -1 +1 @@
1
- {"version":3,"sources":["../src/agent.ts","../src/utils.ts","../src/stream.ts","../src/constant.ts","../src/chat_history.ts"],"sourcesContent":["import {\n RunAgentInput,\n Message,\n AbstractAgent,\n AgentConfig,\n BaseEvent,\n EventType,\n RunStartedEvent,\n RunFinishedEvent,\n RunErrorEvent,\n TextMessageContentEvent,\n ToolCall,\n} from \"@ag-ui/client\";\nimport tcb from \"@cloudbase/node-sdk\";\nimport managedTcb from \"@cloudbase/manager-node\";\nimport OpenAI from \"openai\";\nimport { randomUUID } from \"crypto\";\nimport { camelToSnakeKeys } from \"./utils\";\nimport { processYuanqiStream } from \"./stream\";\nimport { Observable, Subscriber } from \"rxjs\";\nimport {\n createChatHistory,\n queryForLLM,\n ChatHistoryEntity,\n} from \"./chat_history\";\nimport { CHAT_HISTORY_DATA_SOURCE } from \"./constant\";\nimport { YuanqiConfig, ChatMessage, YuanqiChatRequest } from \"./types\";\n\nexport class YuanqiAgentError extends Error {\n code?: string;\n constructor(message: string, code?: string) {\n super(message);\n this.name = \"YuanqiAgentError\";\n if (code) this.code = code;\n }\n}\n\nexport class YuanqiAgent extends AbstractAgent {\n protected yuanqiConfig: YuanqiConfig;\n private finalAppId: string;\n private finalCloudCredential: {\n secretId?: string;\n secretKey?: string;\n token?: string;\n } = {};\n private model: OpenAI;\n constructor(config: AgentConfig & { yuanqiConfig: YuanqiConfig }) {\n super(config);\n this.yuanqiConfig = config.yuanqiConfig;\n this.model = new OpenAI({\n apiKey: \"\",\n baseURL:\n this.yuanqiConfig.request?.baseUrl ||\n \"https://yuanqi.tencent.com/openapi/v1/agent\",\n });\n this.finalAppId =\n this.yuanqiConfig.appId ||\n this.yuanqiConfig.request?.body?.assistantId ||\n process.env.YUANQI_APP_ID ||\n \"\";\n this.finalCloudCredential = {\n secretId:\n this.yuanqiConfig.credential?.secretId ||\n process.env.TENCENTCLOUD_SECRETID,\n secretKey:\n this.yuanqiConfig.credential?.secretKey ||\n process.env.TENCENTCLOUD_SECRETKEY,\n token:\n this.yuanqiConfig.credential?.token ||\n process.env.TENCENTCLOUD_SESSIONTOKEN,\n };\n }\n\n generateRequestBody({\n messages,\n input,\n }: {\n messages: ChatMessage[];\n input: RunAgentInput;\n }): YuanqiChatRequest {\n const { state, forwardedProps } = input;\n const requestBody: YuanqiChatRequest = {\n stream: true,\n ...(this.yuanqiConfig.request?.body || {}),\n ...(forwardedProps || {}),\n\n assistantId: this.finalAppId,\n userId:\n state?.__request_context__?.user?.id ||\n forwardedProps?.userId ||\n randomUUID(),\n messages,\n };\n return requestBody;\n }\n\n run(input: RunAgentInput): Observable<BaseEvent> {\n return new Observable<BaseEvent>((subscriber) => {\n this._run(subscriber, input);\n });\n }\n\n private async _run(\n subscriber: Subscriber<BaseEvent>,\n input: RunAgentInput\n ): Promise<void> {\n try {\n const { messages, runId } = input;\n\n const openai = this.model as OpenAI;\n const threadId = input.threadId || randomUUID();\n\n subscriber.next({\n type: EventType.RUN_STARTED,\n threadId,\n runId,\n } as RunStartedEvent);\n\n if (!this.finalAppId) {\n throw new YuanqiAgentError(\n \"YUANQI_APP_ID is required, check your env variables or config passed with the adapter\",\n \"MISSING_YUANQI_APP_ID\"\n );\n }\n if (!this.yuanqiConfig.appKey && !process.env.YUANQI_APP_KEY) {\n throw new YuanqiAgentError(\n \"YUANQI_APP_KEY is required, check your env variables or config passed with the adapter\",\n \"MISSING_YUANQI_APP_KEY\"\n );\n }\n\n // Warn user if messages are being trimmed (only using latest user message)\n const trimmedCount = messages.length - 1;\n if (trimmedCount > 0) {\n subscriber.next({\n type: EventType.RAW,\n rawEvent: {\n message: `Yuanqi handles message history itself, so that a total of ${trimmedCount} messages before the last user message will be trimmed.`,\n type: \"warn\",\n },\n });\n }\n\n // Get the latest user message for saving to history\n const latestUserMessage = messages.filter((m) => m.role === \"user\").pop();\n if (!latestUserMessage) {\n throw new YuanqiAgentError(\n \"No user message found, please send a message first.\",\n \"MESSAGE_FORMAT_ERROR\"\n );\n }\n\n const allMessages = await this.getChatHistory(\n subscriber,\n latestUserMessage\n );\n\n const body = this.generateRequestBody({\n messages: allMessages,\n input,\n });\n\n const stream = await openai.chat.completions.create(\n {\n stream: true,\n messages: [],\n model: \"\",\n },\n {\n body: camelToSnakeKeys(body),\n headers: {\n ...this.yuanqiConfig.request?.headers,\n Authorization: `Bearer ${\n this.yuanqiConfig.appKey || process.env.YUANQI_APP_KEY\n }`,\n },\n }\n );\n\n // Process stream and emit AGUI events, collect full response\n const userRecordId = `record-${randomUUID().slice(0, 8)}`;\n const assistantRecordId = `record-${randomUUID().slice(0, 8)}`;\n const context = { threadId, runId, messageId: userRecordId };\n\n let fullAssistantContent = \"\";\n\n for await (const event of processYuanqiStream(stream, context)) {\n subscriber.next(event);\n // Collect assistant content from TEXT_MESSAGE_CONTENT events\n if (\n event.type === EventType.TEXT_MESSAGE_CONTENT &&\n (event as TextMessageContentEvent).delta\n ) {\n fullAssistantContent += (event as TextMessageContentEvent).delta;\n }\n }\n\n const userContent =\n typeof latestUserMessage?.content === \"string\"\n ? latestUserMessage.content\n : latestUserMessage?.content\n ?.filter((c) => c.type === \"text\")\n .map((c) => c.text)\n .join(\"\") || \"\";\n\n await this.saveChatHistory(\n subscriber,\n input,\n userRecordId,\n assistantRecordId,\n userContent,\n fullAssistantContent\n );\n\n subscriber.next({\n type: EventType.RUN_FINISHED,\n threadId,\n runId,\n } as RunFinishedEvent);\n } catch (e: unknown) {\n console.error(\"[ERROR] Uncaught error: \", JSON.stringify(e));\n let code = \"UNKNOWN_ERROR\";\n let message = JSON.stringify(e);\n if (e instanceof YuanqiAgentError) {\n code = e.code || \"AGENT_ERROR\";\n message = e.message;\n } else if (e instanceof Error) {\n code = e.name || \"ERROR\";\n message = e.message;\n }\n subscriber.next({\n type: EventType.RUN_ERROR,\n code,\n message: `Sorry, an error occurred while running the agent: Error code ${code}, ${message}`,\n } as RunErrorEvent);\n } finally {\n subscriber.complete();\n }\n }\n\n // Can be override by subclasses\n protected async getChatHistory(\n subscriber: Subscriber<BaseEvent>,\n latestUserMessage: Message\n ) {\n const botId = `bot-yuanqi-${this.finalAppId}`;\n\n const tcbClient = this.getTcbClient();\n\n const isDBReady = await this.checkIsDatabaseReady();\n if (!isDBReady) {\n subscriber.next({\n type: EventType.RAW,\n rawEvent: {\n message: `Chat history database is not ready, skip history loading.`,\n type: \"warn\",\n },\n });\n return convertMessagesToOpenAI([latestUserMessage]);\n }\n\n // Fetch chat history from database using queryForLLM\n let historyMessages: ChatMessage[] = [];\n\n const historyCount = this.yuanqiConfig.historyCount ?? 10;\n const historyRecords = await queryForLLM({\n tcbClient,\n botId,\n pageSize: historyCount,\n });\n\n // Convert queryForLLM result to ChatMessage format\n historyMessages = historyRecords.map((record) => ({\n role: record.role as \"user\" | \"assistant\",\n content: [{ type: \"text\" as const, text: record.content }],\n }));\n\n // Combine history messages with current messages\n const allMessages = historyMessages.concat(\n convertMessagesToOpenAI([latestUserMessage])\n );\n return allMessages;\n }\n\n // Can be override by subclasses\n protected async saveChatHistory(\n subscriber: Subscriber<BaseEvent>,\n input: RunAgentInput,\n userRecordId: string,\n assistantRecordId: string,\n userContent: string,\n assistantContent: string\n ) {\n const botId = `bot-yuanqi-${this.finalAppId}`;\n\n const { threadId, runId } = input;\n\n const tcbClient = this.getTcbClient();\n\n const isDBReady = await this.checkIsDatabaseReady();\n if (!isDBReady) {\n subscriber.next({\n type: EventType.RAW,\n rawEvent: {\n message: `Chat history database is not ready, skip history saving.`,\n type: \"warn\",\n },\n });\n return;\n }\n\n // Save message pair to history\n const userEntity = new ChatHistoryEntity();\n userEntity.recordId = userRecordId;\n userEntity.botId = botId;\n userEntity.role = \"user\";\n userEntity.content = userContent;\n userEntity.conversation = threadId;\n userEntity.reply = assistantRecordId;\n userEntity.triggerSrc = \"\";\n userEntity.traceId = randomUUID();\n\n await createChatHistory({ tcbClient, chatHistoryEntity: userEntity });\n\n const assistantEntity = new ChatHistoryEntity();\n assistantEntity.recordId = assistantRecordId;\n assistantEntity.botId = botId;\n assistantEntity.role = \"assistant\";\n assistantEntity.content = assistantContent;\n assistantEntity.conversation = threadId;\n assistantEntity.replyTo = userRecordId;\n assistantEntity.triggerSrc = \"\";\n assistantEntity.traceId = runId;\n assistantEntity.status = \"done\";\n\n await createChatHistory({\n tcbClient,\n chatHistoryEntity: assistantEntity,\n });\n }\n\n private getTcbClient() {\n const envId = this.yuanqiConfig.envId || getCloudbaseEnvId();\n\n const tcbClient = tcb.init({\n env: envId,\n secretId: this.finalCloudCredential.secretId,\n secretKey: this.finalCloudCredential.secretKey,\n sessionToken: this.finalCloudCredential.token,\n });\n return tcbClient;\n }\n\n private async checkIsDatabaseReady() {\n try {\n const envId = this.yuanqiConfig.envId || getCloudbaseEnvId();\n if (!envId) {\n throw new YuanqiAgentError(\n \"When saving chat history to CloudBase, CLOUDBASE_ENV_ID is required, check your env variables or config passed with the adapter\",\n \"MISSING_CLOUDBASE_ENV_ID\"\n );\n }\n if (!this.finalCloudCredential.token) {\n if (!this.finalCloudCredential.secretId) {\n throw new YuanqiAgentError(\n \"When saving chat history to CloudBase, TENCENTCLOUD_SECRETID is required, check your env variables or config passed with the adapter\",\n \"MISSING_SECRET_ID\"\n );\n }\n if (!this.finalCloudCredential.secretKey) {\n throw new YuanqiAgentError(\n \"When saving chat history to CloudBase, TENCENTCLOUD_SECRETKEY is required, check your env variables or config passed with the adapter\",\n \"MISSING_SECRET_KEY\"\n );\n }\n }\n const managedTcbClient = managedTcb.init({\n envId,\n secretId: this.finalCloudCredential.secretId,\n secretKey: this.finalCloudCredential.secretKey,\n token: this.finalCloudCredential.token,\n });\n\n const checkDBRes = await managedTcbClient.database.checkCollectionExists(\n CHAT_HISTORY_DATA_SOURCE\n );\n if (checkDBRes && checkDBRes.Exists) {\n return true;\n } else if (checkDBRes && !checkDBRes.Exists) {\n await managedTcbClient.database.createCollection(\n CHAT_HISTORY_DATA_SOURCE\n );\n return true;\n } else {\n throw new Error(\"Check database exists failed\");\n }\n } catch (dbError) {\n console.error(\n \"[ERROR] Failed to check/create chat history collection:\",\n JSON.stringify(dbError)\n );\n return false;\n }\n }\n}\n\nfunction getCloudbaseEnvId() {\n if (process.env.CBR_ENV_ID) {\n return process.env.CBR_ENV_ID;\n } else if (process.env.SCF_NAMESPACE) {\n return process.env.SCF_NAMESPACE;\n } else {\n return process.env.CLOUDBASE_ENV_ID || \"\";\n }\n}\n\n/**\n * Convert AGUI messages to OpenAI chat completion format\n */\nexport function convertMessagesToOpenAI(\n messages: Message[],\n systemPrompt?: string\n): ChatMessage[] {\n const openaiMessages: ChatMessage[] = [];\n\n // Add system prompt if provided\n if (systemPrompt) {\n openaiMessages.push({\n role: \"system\",\n content: systemPrompt,\n });\n }\n\n // Convert messages\n for (const msg of messages) {\n if (msg.role === \"user\") {\n openaiMessages.push({\n role: \"user\",\n content:\n typeof msg.content === \"string\"\n ? [{ type: \"text\", text: msg.content }]\n : msg.content.map((item) => {\n if (item.type === \"text\") {\n return { type: \"text\", text: item.text };\n } else {\n return {\n type: \"image_url\",\n image_url: { url: item.url || \"\" },\n };\n }\n }),\n });\n } else if (msg.role === \"assistant\") {\n openaiMessages.push({\n role: \"assistant\",\n content: msg.content ? [{ type: \"text\", text: msg.content }] : [],\n tool_calls: msg.toolCalls?.map((tc: ToolCall) => ({\n id: tc.id,\n type: \"function\" as const,\n function: {\n name: tc.function.name,\n arguments: tc.function.arguments,\n },\n })),\n });\n } else if (msg.role === \"tool\") {\n openaiMessages.push({\n role: \"tool\",\n tool_call_id: msg.toolCallId,\n content: msg.content ? [{ type: \"text\", text: msg.content }] : [],\n });\n }\n }\n\n return openaiMessages;\n}\n","/**\n * 将小驼峰字符串转换为下划线格式\n * 例如: \"userName\" -> \"user_name\"\n */\nfunction camelToSnake(str: string): string {\n return str.replace(/[A-Z]/g, (letter) => `_${letter.toLowerCase()}`);\n}\n\n/**\n * 递归地将对象的所有小驼峰属性名转换为下划线格式\n */\nexport function camelToSnakeKeys<T>(obj: T): T {\n if (obj === null || obj === undefined) {\n return obj;\n }\n\n if (Array.isArray(obj)) {\n return obj.map((item) => camelToSnakeKeys(item)) as T;\n }\n\n if (typeof obj === \"object\") {\n const result: Record<string, unknown> = {};\n for (const [key, value] of Object.entries(obj)) {\n const snakeKey = camelToSnake(key);\n result[snakeKey] = camelToSnakeKeys(value);\n }\n return result as T;\n }\n\n return obj;\n}\n\nexport function genRandomStr(length: number): string {\n const chars = \"abcdefghijklmnopqrstuvwxyz0123456789\";\n let result = \"\";\n for (let i = 0; i < length; i++) {\n result += chars.charAt(Math.floor(Math.random() * chars.length));\n }\n return result;\n}\n","import OpenAI from \"openai\";\nimport { EventType } from \"@ag-ui/client\";\n\nexport interface StreamContext {\n threadId: string;\n runId: string;\n messageId: string;\n}\n\nexport interface StreamState {\n hasStarted: boolean;\n fullContent: string;\n toolCallsMap: Map<string, { name: string; args: string }>;\n}\n\nexport type Delta =\n OpenAI.Chat.Completions.ChatCompletionChunk[\"choices\"][number][\"delta\"] & {\n reasoning_content?: string;\n };\n\nexport async function* processYuanqiStream(\n stream: AsyncIterable<OpenAI.Chat.Completions.ChatCompletionChunk>,\n context: StreamContext\n) {\n const { threadId, runId, messageId } = context;\n const state: StreamState = {\n hasStarted: false,\n fullContent: \"\",\n toolCallsMap: new Map(),\n };\n const reasoningState: StreamState = {\n hasStarted: false,\n fullContent: \"\",\n toolCallsMap: new Map(),\n };\n\n for await (const chunk of stream) {\n const delta = chunk.choices[0]?.delta as Delta;\n if (!delta) continue;\n\n if (delta.role === \"tool\") {\n const toolCallId = (delta as any).tool_call_id;\n if (toolCallId) {\n if (state.toolCallsMap.has(toolCallId)) {\n yield {\n type: EventType.TOOL_CALL_END,\n threadId,\n runId,\n toolCallId,\n };\n state.toolCallsMap.delete(toolCallId);\n }\n yield {\n type: EventType.TOOL_CALL_RESULT,\n threadId,\n runId,\n toolCallId,\n content: delta.content || \"\",\n };\n }\n continue;\n }\n\n // Handle text content\n if (delta.content) {\n // End reasoning message if it was started\n if (reasoningState.hasStarted) {\n reasoningState.hasStarted = false;\n yield {\n type: EventType.THINKING_TEXT_MESSAGE_END,\n threadId,\n runId,\n messageId,\n };\n yield {\n type: EventType.THINKING_END,\n threadId,\n runId,\n messageId,\n };\n }\n\n if (!state.hasStarted) {\n yield {\n type: EventType.TEXT_MESSAGE_START,\n threadId,\n runId,\n messageId,\n role: \"assistant\",\n };\n state.hasStarted = true;\n }\n\n state.fullContent += delta.content;\n yield {\n type: EventType.TEXT_MESSAGE_CONTENT,\n threadId,\n runId,\n messageId,\n delta: delta.content,\n };\n }\n\n // Handle reasoning content\n if (delta.reasoning_content) {\n if (!reasoningState.hasStarted) {\n yield {\n type: EventType.THINKING_START,\n threadId,\n runId,\n messageId,\n };\n yield {\n type: EventType.THINKING_TEXT_MESSAGE_START,\n threadId,\n runId,\n messageId,\n role: \"assistant\",\n };\n reasoningState.hasStarted = true;\n }\n\n reasoningState.fullContent += delta.reasoning_content;\n yield {\n type: EventType.THINKING_TEXT_MESSAGE_CONTENT,\n threadId,\n runId,\n messageId,\n delta: delta.reasoning_content,\n };\n }\n\n // Handle tool calls\n if (delta.tool_calls) {\n for (const toolCall of delta.tool_calls) {\n const toolCallId = toolCall.id || `tool_${toolCall.index}`;\n\n if (toolCall.function?.name) {\n // Tool call start\n yield {\n type: EventType.TOOL_CALL_START,\n threadId,\n runId,\n toolCallId,\n toolCallName: toolCall.function.name,\n };\n\n // If first chunk contains arguments, emit TOOL_CALL_ARGS event\n if (toolCall.function.arguments) {\n yield {\n type: EventType.TOOL_CALL_ARGS,\n threadId,\n runId,\n toolCallId,\n delta: toolCall.function.arguments,\n };\n }\n\n state.toolCallsMap.set(toolCallId, {\n name: toolCall.function.name,\n args: toolCall.function.arguments || \"\",\n });\n } else if (toolCall.function?.arguments) {\n // Tool call arguments delta\n const existing = state.toolCallsMap.get(toolCallId);\n if (existing) {\n existing.args += toolCall.function.arguments;\n\n yield {\n type: EventType.TOOL_CALL_ARGS,\n threadId,\n runId,\n toolCallId,\n delta: toolCall.function.arguments,\n };\n }\n }\n }\n }\n }\n\n // Emit TEXT_MESSAGE_END if we had text content\n if (state.hasStarted) {\n yield {\n type: EventType.TEXT_MESSAGE_END,\n threadId,\n runId,\n messageId,\n };\n }\n\n if (reasoningState.hasStarted) {\n yield {\n type: EventType.THINKING_TEXT_MESSAGE_END,\n threadId,\n runId,\n messageId,\n };\n yield {\n type: EventType.THINKING_END,\n threadId,\n runId,\n messageId,\n };\n }\n\n // Emit TOOL_CALL_END for all tool calls\n for (const [toolCallId] of state.toolCallsMap) {\n yield {\n type: EventType.TOOL_CALL_END,\n threadId,\n runId,\n toolCallId,\n };\n }\n}\n","// 对话数据模型\nexport const CHAT_HISTORY_DATA_SOURCE = \"ai_bot_chat_history_5hobd2b\";\n","import tcb from \"@cloudbase/node-sdk\";\nimport { CHAT_HISTORY_DATA_SOURCE } from \"./constant\";\nimport { genRandomStr } from \"./utils\";\n\nfunction genRecordId(): string {\n return \"record-\" + genRandomStr(8);\n}\n\n// Create a new chat history record\nexport async function createChatHistory({\n tcbClient,\n chatHistoryEntity,\n}: {\n tcbClient: tcb.CloudBase;\n chatHistoryEntity: ChatHistoryEntity;\n}): Promise<string | undefined> {\n try {\n const recordId = chatHistoryEntity.recordId || genRecordId();\n const data = {\n record_id: recordId,\n bot_id: chatHistoryEntity.botId,\n role: chatHistoryEntity.role,\n content: chatHistoryEntity.content,\n sender: chatHistoryEntity.sender,\n conversation: chatHistoryEntity.conversation,\n type: chatHistoryEntity.type,\n image: chatHistoryEntity.image,\n trigger_src: chatHistoryEntity.triggerSrc,\n origin_msg: chatHistoryEntity.originMsg,\n reply_to: chatHistoryEntity.replyTo,\n reply: chatHistoryEntity.reply,\n trace_id: chatHistoryEntity.traceId,\n need_async_reply: chatHistoryEntity.needAsyncReply,\n async_reply: chatHistoryEntity.asyncReply,\n createdAt: Date.now(),\n updatedAt: Date.now(),\n };\n\n const db = tcbClient.database();\n const collection = db.collection(CHAT_HISTORY_DATA_SOURCE);\n const result = await collection.add(data);\n\n // console.log(\n // `Create record: chatHistoryEntity:${JSON.stringify(\n // chatHistoryEntity\n // )}, result: ${JSON.stringify(result)}`\n // );\n return recordId;\n } catch (error) {\n console.error(\"Failed to create chat history record, error:\", error);\n return undefined;\n }\n}\n\n// Update chat history by record ID\nexport async function updateChatHistoryByRecordId({\n tcbClient,\n recordId,\n chatHistoryEntity,\n}: {\n tcbClient: tcb.CloudBase;\n recordId: string;\n chatHistoryEntity: ChatHistoryEntity;\n}): Promise<string | undefined> {\n try {\n const db = tcbClient.database();\n const _ = db.command;\n const collection = db.collection(CHAT_HISTORY_DATA_SOURCE);\n\n const result = await collection\n .where({ record_id: _.eq(recordId) })\n .update({\n content: chatHistoryEntity.content,\n image: chatHistoryEntity.image,\n async_reply: chatHistoryEntity.asyncReply,\n recommend_questions: chatHistoryEntity.recommendQuestions,\n status: chatHistoryEntity.status,\n origin_msg: chatHistoryEntity.originMsg,\n updatedAt: Date.now(),\n });\n\n // console.log(\n // `Update record: recordId: ${recordId}, chatHistoryEntity:${JSON.stringify(\n // chatHistoryEntity\n // )}, result: ${JSON.stringify(result)}`\n // );\n return chatHistoryEntity.recordId;\n } catch (error) {\n console.error(\"Failed to update chat history, error:\", error);\n return undefined;\n }\n}\n\n// Query chat history from database\nexport async function describeChatHistory({\n tcbClient,\n botId,\n sort,\n pageSize = 10,\n pageNumber = 1,\n conversation,\n startCreatedAt,\n triggerSrc,\n}: {\n tcbClient: tcb.CloudBase;\n botId: string;\n sort: \"asc\" | \"desc\";\n pageSize?: number;\n pageNumber?: number;\n conversation?: string;\n startCreatedAt?: number;\n triggerSrc?: string;\n}): Promise<[ChatHistoryEntity[], number]> {\n if (!sort || sort.length === 0) {\n sort = \"desc\";\n }\n\n try {\n const db = tcbClient.database();\n const _ = db.command;\n const collection = db.collection(CHAT_HISTORY_DATA_SOURCE);\n\n // Build where conditions\n const whereConditions: Record<string, unknown> = {\n bot_id: _.eq(botId),\n };\n\n // Add optional filters\n if (conversation) {\n whereConditions.conversation = _.eq(conversation);\n }\n\n if (startCreatedAt !== undefined) {\n whereConditions.createdAt = _.gt(startCreatedAt);\n }\n\n if (triggerSrc) {\n whereConditions.trigger_src = _.eq(triggerSrc);\n }\n\n // Calculate skip for pagination\n const skip = (pageNumber - 1) * pageSize;\n\n // Query records\n const result = await collection\n .where(whereConditions)\n .orderBy(\"createdAt\", sort)\n .skip(skip)\n .limit(pageSize)\n .get();\n\n // Get total count\n const countResult = await collection.where(whereConditions).count();\n const total = countResult.total || 0;\n\n const records = result?.data || [];\n\n const entityList: ChatHistoryEntity[] = records.map(\n (item: ChatHistoryData) => transDataToChatEntity(item)\n );\n\n return [entityList, total];\n } catch (error) {\n console.error(\"Failed to query chat history, error:\", error);\n return [[], 0];\n }\n}\n\n// Transform data to ChatHistoryEntity structure\nexport function transDataToChatEntity(\n item: ChatHistoryData\n): ChatHistoryEntity {\n if (!item) {\n return new ChatHistoryEntity();\n }\n const chatEntity: ChatHistoryEntity = new ChatHistoryEntity();\n chatEntity.botId = item.bot_id;\n chatEntity.recordId = item.record_id;\n chatEntity.role = item.role;\n chatEntity.status = item.status;\n chatEntity.content = item.content;\n chatEntity.sender = item.sender;\n chatEntity.conversation = item.conversation;\n chatEntity.type = item.type;\n chatEntity.triggerSrc = item.trigger_src;\n chatEntity.originMsg = item.origin_msg;\n chatEntity.replyTo = item.reply_to;\n chatEntity.reply = item.reply;\n chatEntity.traceId = item.trace_id;\n chatEntity.needAsyncReply = item.need_async_reply;\n chatEntity.asyncReply = item.async_reply;\n chatEntity.createdAt = item.createdAt;\n chatEntity.updatedAt = item.updatedAt;\n return chatEntity;\n}\n\n// Query history records for LLM, get the most recent 10 conversation pairs (20 records)\nexport async function queryForLLM({\n tcbClient,\n botId,\n pageSize = 10,\n startCreatedAt,\n triggerSrc,\n}: {\n tcbClient: tcb.CloudBase;\n botId: string;\n pageSize?: number;\n startCreatedAt?: number;\n triggerSrc?: string;\n}): Promise<{ role: string; content: string }[]> {\n if (startCreatedAt === undefined) {\n startCreatedAt = Date.now() - 24 * 60 * 60 * 1000;\n }\n const recordEntityList: ChatHistoryEntity[] = [];\n\n const [recordList] = await describeChatHistory({\n tcbClient,\n botId,\n sort: \"desc\",\n pageSize,\n startCreatedAt,\n triggerSrc,\n });\n recordEntityList.push(...recordList.reverse());\n\n const entityMap = new Map<string, ChatHistoryEntity>();\n recordEntityList\n .filter((item) => {\n if (item.needAsyncReply === true) {\n return !!item.asyncReply;\n } else {\n return !!item.content;\n }\n })\n .forEach((item) => {\n entityMap.set(item.recordId, item);\n });\n\n const result: { role: string; content: string }[] = [];\n /*\n 1. Strongly depends on database history data, model history data has role order requirements\n 2. Need to ensure that no matter what bug occurs, always get a complete and usable user + assistant pair, otherwise the request will fail\n */\n recordEntityList.forEach((item) => {\n const { role, content, reply } = item;\n // When calling LLM, empty content will cause failure, so filter out conversations with empty content\n if (role === \"user\" && content?.length !== 0) {\n if (entityMap.has(reply)) {\n result.push({ role, content });\n result.push({\n role: entityMap.get(reply)!.role,\n content: entityMap.get(reply)!.content,\n });\n }\n }\n });\n if (result.length % 2 === 1) {\n result.splice(-1, 1);\n }\n return result;\n}\n\nexport interface ChatHistoryData {\n bot_id: string;\n record_id: string;\n role: string;\n status: string;\n content: string;\n sender: string;\n conversation: string;\n type: string;\n trigger_src: string;\n origin_msg: string;\n reply_to: string;\n reply: string;\n trace_id: string;\n need_async_reply: boolean;\n async_reply: string;\n createdAt: number;\n updatedAt: number;\n}\n\nexport class ChatHistoryEntity {\n id: number;\n botId: string;\n // 对话唯一id\n recordId: string;\n role: string;\n content: string;\n recommendQuestions: string[];\n sender: string;\n conversation: string;\n type: string;\n /**\n * 消息状态,pending done error cancel\n */\n status: string;\n image: string;\n triggerSrc: string;\n originMsg: string;\n replyTo: string;\n reply: string;\n traceId: string;\n needAsyncReply: boolean;\n asyncReply: string;\n createTime: string;\n updateTime: string;\n createdAt: number;\n updatedAt: number;\n event: string;\n}\n"],"mappings":"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","names":["EventType","EventType"]}
1
+ {"version":3,"sources":["../src/agent.ts","../src/utils.ts","../src/stream.ts","../src/constant.ts","../src/chat_history.ts"],"sourcesContent":["import {\n RunAgentInput,\n Message,\n AbstractAgent,\n AgentConfig,\n BaseEvent,\n EventType,\n RunStartedEvent,\n RunFinishedEvent,\n RunErrorEvent,\n TextMessageContentEvent,\n ToolCall,\n} from \"@ag-ui/client\";\nimport tcb from \"@cloudbase/node-sdk\";\nimport managedTcb from \"@cloudbase/manager-node\";\nimport OpenAI from \"openai\";\nimport { randomUUID } from \"crypto\";\nimport { camelToSnakeKeys } from \"./utils\";\nimport { processYuanqiStream } from \"./stream\";\nimport { Observable, Subscriber } from \"rxjs\";\nimport {\n createChatHistory,\n queryForLLM,\n ChatHistoryEntity,\n} from \"./chat_history\";\nimport { CHAT_HISTORY_DATA_SOURCE } from \"./constant\";\nimport { YuanqiConfig, ChatMessage, YuanqiChatRequest } from \"./types\";\n\nexport class YuanqiAgentError extends Error {\n code?: string;\n constructor(message: string, code?: string) {\n super(message);\n this.name = \"YuanqiAgentError\";\n if (code) this.code = code;\n }\n}\n\nexport class YuanqiAgent extends AbstractAgent {\n protected yuanqiConfig: YuanqiConfig;\n private finalAppId: string;\n private finalCloudCredential: {\n secretId?: string;\n secretKey?: string;\n token?: string;\n } = {};\n private model: OpenAI;\n constructor(config: AgentConfig & { yuanqiConfig: YuanqiConfig }) {\n super(config);\n this.yuanqiConfig = config.yuanqiConfig;\n this.model = new OpenAI({\n apiKey: \"\",\n baseURL:\n this.yuanqiConfig.request?.baseUrl ||\n \"https://yuanqi.tencent.com/openapi/v1/agent\",\n });\n this.finalAppId =\n this.yuanqiConfig.appId ||\n this.yuanqiConfig.request?.body?.assistantId ||\n process.env.YUANQI_APP_ID ||\n \"\";\n this.finalCloudCredential = {\n secretId:\n this.yuanqiConfig.credential?.secretId ||\n process.env.TENCENTCLOUD_SECRETID,\n secretKey:\n this.yuanqiConfig.credential?.secretKey ||\n process.env.TENCENTCLOUD_SECRETKEY,\n token:\n this.yuanqiConfig.credential?.token ||\n process.env.TENCENTCLOUD_SESSIONTOKEN,\n };\n }\n\n generateRequestBody({\n messages,\n input,\n }: {\n messages: ChatMessage[];\n input: RunAgentInput;\n }): YuanqiChatRequest {\n const { state, forwardedProps } = input;\n const requestBody: YuanqiChatRequest = {\n stream: true,\n ...(this.yuanqiConfig.request?.body || {}),\n ...(forwardedProps || {}),\n\n assistantId: this.finalAppId,\n userId:\n state?.__request_context__?.user?.id ||\n forwardedProps?.userId ||\n randomUUID(),\n messages,\n };\n return requestBody;\n }\n\n run(input: RunAgentInput): Observable<BaseEvent> {\n return new Observable<BaseEvent>((subscriber) => {\n this._run(subscriber, input);\n });\n }\n\n private async _run(\n subscriber: Subscriber<BaseEvent>,\n input: RunAgentInput\n ): Promise<void> {\n try {\n const { messages, runId } = input;\n\n const openai = this.model as OpenAI;\n const threadId = input.threadId || randomUUID();\n\n subscriber.next({\n type: EventType.RUN_STARTED,\n threadId,\n runId,\n } as RunStartedEvent);\n\n if (!this.finalAppId) {\n throw new YuanqiAgentError(\n \"YUANQI_APP_ID is required, check your env variables or config passed with the adapter\",\n \"MISSING_YUANQI_APP_ID\"\n );\n }\n if (!this.yuanqiConfig.appKey && !process.env.YUANQI_APP_KEY) {\n throw new YuanqiAgentError(\n \"YUANQI_APP_KEY is required, check your env variables or config passed with the adapter\",\n \"MISSING_YUANQI_APP_KEY\"\n );\n }\n\n // Warn user if messages are being trimmed (only using latest user message)\n const trimmedCount = messages.length - 1;\n if (trimmedCount > 0) {\n subscriber.next({\n type: EventType.RAW,\n rawEvent: {\n message: `Yuanqi handles message history itself, so that a total of ${trimmedCount} messages before the last user message will be trimmed.`,\n type: \"warn\",\n },\n });\n }\n\n // Get the latest user message for saving to history\n const latestUserMessage = messages.filter((m) => m.role === \"user\").pop();\n if (!latestUserMessage) {\n throw new YuanqiAgentError(\n \"No user message found, please send a message first.\",\n \"MESSAGE_FORMAT_ERROR\"\n );\n }\n\n const allMessages = await this.getChatHistory(\n subscriber,\n input,\n latestUserMessage\n );\n\n const body = this.generateRequestBody({\n messages: allMessages,\n input,\n });\n\n const stream = await openai.chat.completions.create(\n {\n stream: true,\n messages: [],\n model: \"\",\n },\n {\n body: camelToSnakeKeys(body),\n headers: {\n ...this.yuanqiConfig.request?.headers,\n Authorization: `Bearer ${\n this.yuanqiConfig.appKey || process.env.YUANQI_APP_KEY\n }`,\n },\n }\n );\n\n // Process stream and emit AGUI events, collect full response\n const userRecordId = `record-${randomUUID().slice(0, 8)}`;\n const assistantRecordId = `record-${randomUUID().slice(0, 8)}`;\n const context = { threadId, runId, messageId: userRecordId };\n\n let fullAssistantContent = \"\";\n\n for await (const event of processYuanqiStream(stream, context)) {\n subscriber.next(event);\n // Collect assistant content from TEXT_MESSAGE_CONTENT events\n if (\n event.type === EventType.TEXT_MESSAGE_CONTENT &&\n (event as TextMessageContentEvent).delta\n ) {\n fullAssistantContent += (event as TextMessageContentEvent).delta;\n }\n }\n\n const userContent =\n typeof latestUserMessage?.content === \"string\"\n ? latestUserMessage.content\n : latestUserMessage?.content\n ?.filter((c) => c.type === \"text\")\n .map((c) => c.text)\n .join(\"\") || \"\";\n\n await this.saveChatHistory(\n subscriber,\n input,\n userRecordId,\n assistantRecordId,\n userContent,\n fullAssistantContent\n );\n\n subscriber.next({\n type: EventType.RUN_FINISHED,\n threadId,\n runId,\n } as RunFinishedEvent);\n } catch (e: unknown) {\n console.error(\"[ERROR] Uncaught error: \", JSON.stringify(e));\n let code = \"UNKNOWN_ERROR\";\n let message = JSON.stringify(e);\n if (e instanceof YuanqiAgentError) {\n code = e.code || \"AGENT_ERROR\";\n message = e.message;\n } else if (e instanceof Error) {\n code = e.name || \"ERROR\";\n message = e.message;\n }\n subscriber.next({\n type: EventType.RUN_ERROR,\n code,\n message: `Sorry, an error occurred while running the agent: Error code ${code}, ${message}`,\n } as RunErrorEvent);\n } finally {\n subscriber.complete();\n }\n }\n\n // Can be override by subclasses\n protected async getChatHistory(\n subscriber: Subscriber<BaseEvent>,\n input: RunAgentInput,\n latestUserMessage: Message\n ) {\n const botId = `bot-yuanqi-${this.finalAppId}`;\n\n const { threadId } = input;\n\n const tcbClient = this.getTcbClient();\n\n const isDBReady = await this.checkIsDatabaseReady();\n if (!isDBReady) {\n subscriber.next({\n type: EventType.RAW,\n rawEvent: {\n message: `Chat history database is not ready, skip history loading.`,\n type: \"warn\",\n },\n });\n return convertMessagesToOpenAI([latestUserMessage]);\n }\n\n // Fetch chat history from database using queryForLLM\n let historyMessages: ChatMessage[] = [];\n\n const historyCount = this.yuanqiConfig.historyCount ?? 10;\n const historyRecords = await queryForLLM({\n tcbClient,\n botId,\n conversation: threadId,\n pageSize: historyCount,\n });\n\n // Convert queryForLLM result to ChatMessage format\n historyMessages = historyRecords.map((record) => ({\n role: record.role as \"user\" | \"assistant\",\n content: [{ type: \"text\" as const, text: record.content }],\n }));\n\n // Combine history messages with current messages\n const allMessages = historyMessages.concat(\n convertMessagesToOpenAI([latestUserMessage])\n );\n return allMessages;\n }\n\n // Can be override by subclasses\n protected async saveChatHistory(\n subscriber: Subscriber<BaseEvent>,\n input: RunAgentInput,\n userRecordId: string,\n assistantRecordId: string,\n userContent: string,\n assistantContent: string\n ) {\n const botId = `bot-yuanqi-${this.finalAppId}`;\n\n const { threadId, runId } = input;\n\n const tcbClient = this.getTcbClient();\n\n const isDBReady = await this.checkIsDatabaseReady();\n if (!isDBReady) {\n subscriber.next({\n type: EventType.RAW,\n rawEvent: {\n message: `Chat history database is not ready, skip history saving.`,\n type: \"warn\",\n },\n });\n return;\n }\n\n // Save message pair to history\n const userEntity = new ChatHistoryEntity();\n userEntity.recordId = userRecordId;\n userEntity.botId = botId;\n userEntity.role = \"user\";\n userEntity.content = userContent;\n userEntity.conversation = threadId;\n userEntity.reply = assistantRecordId;\n userEntity.triggerSrc = \"\";\n userEntity.traceId = randomUUID();\n\n await createChatHistory({ tcbClient, chatHistoryEntity: userEntity });\n\n const assistantEntity = new ChatHistoryEntity();\n assistantEntity.recordId = assistantRecordId;\n assistantEntity.botId = botId;\n assistantEntity.role = \"assistant\";\n assistantEntity.content = assistantContent;\n assistantEntity.conversation = threadId;\n assistantEntity.replyTo = userRecordId;\n assistantEntity.triggerSrc = \"\";\n assistantEntity.traceId = runId;\n assistantEntity.status = \"done\";\n\n await createChatHistory({\n tcbClient,\n chatHistoryEntity: assistantEntity,\n });\n }\n\n private getTcbClient() {\n const envId = this.yuanqiConfig.envId || getCloudbaseEnvId();\n\n const tcbClient = tcb.init({\n env: envId,\n secretId: this.finalCloudCredential.secretId,\n secretKey: this.finalCloudCredential.secretKey,\n sessionToken: this.finalCloudCredential.token,\n });\n return tcbClient;\n }\n\n private async checkIsDatabaseReady() {\n try {\n const envId = this.yuanqiConfig.envId || getCloudbaseEnvId();\n if (!envId) {\n throw new YuanqiAgentError(\n \"When saving chat history to CloudBase, CLOUDBASE_ENV_ID is required, check your env variables or config passed with the adapter\",\n \"MISSING_CLOUDBASE_ENV_ID\"\n );\n }\n if (!this.finalCloudCredential.token) {\n if (!this.finalCloudCredential.secretId) {\n throw new YuanqiAgentError(\n \"When saving chat history to CloudBase, TENCENTCLOUD_SECRETID is required, check your env variables or config passed with the adapter\",\n \"MISSING_SECRET_ID\"\n );\n }\n if (!this.finalCloudCredential.secretKey) {\n throw new YuanqiAgentError(\n \"When saving chat history to CloudBase, TENCENTCLOUD_SECRETKEY is required, check your env variables or config passed with the adapter\",\n \"MISSING_SECRET_KEY\"\n );\n }\n }\n const managedTcbClient = managedTcb.init({\n envId,\n secretId: this.finalCloudCredential.secretId,\n secretKey: this.finalCloudCredential.secretKey,\n token: this.finalCloudCredential.token,\n });\n\n const checkDBRes = await managedTcbClient.database.checkCollectionExists(\n CHAT_HISTORY_DATA_SOURCE\n );\n if (checkDBRes && checkDBRes.Exists) {\n return true;\n } else if (checkDBRes && !checkDBRes.Exists) {\n await managedTcbClient.database.createCollection(\n CHAT_HISTORY_DATA_SOURCE\n );\n return true;\n } else {\n throw new Error(\"Check database exists failed\");\n }\n } catch (dbError) {\n console.error(\n \"[ERROR] Failed to check/create chat history collection:\",\n JSON.stringify(dbError)\n );\n return false;\n }\n }\n}\n\nfunction getCloudbaseEnvId() {\n if (process.env.CBR_ENV_ID) {\n return process.env.CBR_ENV_ID;\n } else if (process.env.SCF_NAMESPACE) {\n return process.env.SCF_NAMESPACE;\n } else {\n return process.env.CLOUDBASE_ENV_ID || \"\";\n }\n}\n\n/**\n * Convert AGUI messages to OpenAI chat completion format\n */\nexport function convertMessagesToOpenAI(\n messages: Message[],\n systemPrompt?: string\n): ChatMessage[] {\n const openaiMessages: ChatMessage[] = [];\n\n // Add system prompt if provided\n if (systemPrompt) {\n openaiMessages.push({\n role: \"system\",\n content: systemPrompt,\n });\n }\n\n // Convert messages\n for (const msg of messages) {\n if (msg.role === \"user\") {\n openaiMessages.push({\n role: \"user\",\n content:\n typeof msg.content === \"string\"\n ? [{ type: \"text\", text: msg.content }]\n : msg.content.map((item) => {\n if (item.type === \"text\") {\n return { type: \"text\", text: item.text };\n } else {\n return {\n type: \"image_url\",\n image_url: { url: item.url || \"\" },\n };\n }\n }),\n });\n } else if (msg.role === \"assistant\") {\n openaiMessages.push({\n role: \"assistant\",\n content: msg.content ? [{ type: \"text\", text: msg.content }] : [],\n tool_calls: msg.toolCalls?.map((tc: ToolCall) => ({\n id: tc.id,\n type: \"function\" as const,\n function: {\n name: tc.function.name,\n arguments: tc.function.arguments,\n },\n })),\n });\n } else if (msg.role === \"tool\") {\n openaiMessages.push({\n role: \"tool\",\n tool_call_id: msg.toolCallId,\n content: msg.content ? [{ type: \"text\", text: msg.content }] : [],\n });\n }\n }\n\n return openaiMessages;\n}\n","/**\n * 将小驼峰字符串转换为下划线格式\n * 例如: \"userName\" -> \"user_name\"\n */\nfunction camelToSnake(str: string): string {\n return str.replace(/[A-Z]/g, (letter) => `_${letter.toLowerCase()}`);\n}\n\n/**\n * 递归地将对象的所有小驼峰属性名转换为下划线格式\n */\nexport function camelToSnakeKeys<T>(obj: T): T {\n if (obj === null || obj === undefined) {\n return obj;\n }\n\n if (Array.isArray(obj)) {\n return obj.map((item) => camelToSnakeKeys(item)) as T;\n }\n\n if (typeof obj === \"object\") {\n const result: Record<string, unknown> = {};\n for (const [key, value] of Object.entries(obj)) {\n const snakeKey = camelToSnake(key);\n result[snakeKey] = camelToSnakeKeys(value);\n }\n return result as T;\n }\n\n return obj;\n}\n\nexport function genRandomStr(length: number): string {\n const chars = \"abcdefghijklmnopqrstuvwxyz0123456789\";\n let result = \"\";\n for (let i = 0; i < length; i++) {\n result += chars.charAt(Math.floor(Math.random() * chars.length));\n }\n return result;\n}\n","import OpenAI from \"openai\";\nimport { EventType } from \"@ag-ui/client\";\n\nexport interface StreamContext {\n threadId: string;\n runId: string;\n messageId: string;\n}\n\nexport interface StreamState {\n hasStarted: boolean;\n fullContent: string;\n toolCallsMap: Map<string, { name: string; args: string }>;\n}\n\nexport type Delta =\n OpenAI.Chat.Completions.ChatCompletionChunk[\"choices\"][number][\"delta\"] & {\n reasoning_content?: string;\n };\n\nexport async function* processYuanqiStream(\n stream: AsyncIterable<OpenAI.Chat.Completions.ChatCompletionChunk>,\n context: StreamContext\n) {\n const { threadId, runId, messageId } = context;\n const state: StreamState = {\n hasStarted: false,\n fullContent: \"\",\n toolCallsMap: new Map(),\n };\n const reasoningState: StreamState = {\n hasStarted: false,\n fullContent: \"\",\n toolCallsMap: new Map(),\n };\n\n for await (const chunk of stream) {\n const delta = chunk.choices[0]?.delta as Delta;\n if (!delta) continue;\n\n if (delta.role === \"tool\") {\n const toolCallId = (delta as any).tool_call_id;\n if (toolCallId) {\n if (state.toolCallsMap.has(toolCallId)) {\n yield {\n type: EventType.TOOL_CALL_END,\n threadId,\n runId,\n toolCallId,\n };\n state.toolCallsMap.delete(toolCallId);\n }\n yield {\n type: EventType.TOOL_CALL_RESULT,\n threadId,\n runId,\n toolCallId,\n content: delta.content || \"\",\n };\n }\n continue;\n }\n\n // Handle text content\n if (delta.content) {\n // End reasoning message if it was started\n if (reasoningState.hasStarted) {\n reasoningState.hasStarted = false;\n yield {\n type: EventType.THINKING_TEXT_MESSAGE_END,\n threadId,\n runId,\n messageId,\n };\n yield {\n type: EventType.THINKING_END,\n threadId,\n runId,\n messageId,\n };\n }\n\n if (!state.hasStarted) {\n yield {\n type: EventType.TEXT_MESSAGE_START,\n threadId,\n runId,\n messageId,\n role: \"assistant\",\n };\n state.hasStarted = true;\n }\n\n state.fullContent += delta.content;\n yield {\n type: EventType.TEXT_MESSAGE_CONTENT,\n threadId,\n runId,\n messageId,\n delta: delta.content,\n };\n }\n\n // Handle reasoning content\n if (delta.reasoning_content) {\n if (!reasoningState.hasStarted) {\n yield {\n type: EventType.THINKING_START,\n threadId,\n runId,\n messageId,\n };\n yield {\n type: EventType.THINKING_TEXT_MESSAGE_START,\n threadId,\n runId,\n messageId,\n role: \"assistant\",\n };\n reasoningState.hasStarted = true;\n }\n\n reasoningState.fullContent += delta.reasoning_content;\n yield {\n type: EventType.THINKING_TEXT_MESSAGE_CONTENT,\n threadId,\n runId,\n messageId,\n delta: delta.reasoning_content,\n };\n }\n\n // Handle tool calls\n if (delta.tool_calls) {\n for (const toolCall of delta.tool_calls) {\n const toolCallId = toolCall.id || `tool_${toolCall.index}`;\n\n if (toolCall.function?.name) {\n // Tool call start\n yield {\n type: EventType.TOOL_CALL_START,\n threadId,\n runId,\n toolCallId,\n toolCallName: toolCall.function.name,\n };\n\n // If first chunk contains arguments, emit TOOL_CALL_ARGS event\n if (toolCall.function.arguments) {\n yield {\n type: EventType.TOOL_CALL_ARGS,\n threadId,\n runId,\n toolCallId,\n delta: toolCall.function.arguments,\n };\n }\n\n state.toolCallsMap.set(toolCallId, {\n name: toolCall.function.name,\n args: toolCall.function.arguments || \"\",\n });\n } else if (toolCall.function?.arguments) {\n // Tool call arguments delta\n const existing = state.toolCallsMap.get(toolCallId);\n if (existing) {\n existing.args += toolCall.function.arguments;\n\n yield {\n type: EventType.TOOL_CALL_ARGS,\n threadId,\n runId,\n toolCallId,\n delta: toolCall.function.arguments,\n };\n }\n }\n }\n }\n }\n\n // Emit TEXT_MESSAGE_END if we had text content\n if (state.hasStarted) {\n yield {\n type: EventType.TEXT_MESSAGE_END,\n threadId,\n runId,\n messageId,\n };\n }\n\n if (reasoningState.hasStarted) {\n yield {\n type: EventType.THINKING_TEXT_MESSAGE_END,\n threadId,\n runId,\n messageId,\n };\n yield {\n type: EventType.THINKING_END,\n threadId,\n runId,\n messageId,\n };\n }\n\n // Emit TOOL_CALL_END for all tool calls\n for (const [toolCallId] of state.toolCallsMap) {\n yield {\n type: EventType.TOOL_CALL_END,\n threadId,\n runId,\n toolCallId,\n };\n }\n}\n","// 对话数据模型\nexport const CHAT_HISTORY_DATA_SOURCE = \"ai_bot_chat_history_5hobd2b\";\n","import tcb from \"@cloudbase/node-sdk\";\nimport { CHAT_HISTORY_DATA_SOURCE } from \"./constant\";\nimport { genRandomStr } from \"./utils\";\n\nfunction genRecordId(): string {\n return \"record-\" + genRandomStr(8);\n}\n\n// Create a new chat history record\nexport async function createChatHistory({\n tcbClient,\n chatHistoryEntity,\n}: {\n tcbClient: tcb.CloudBase;\n chatHistoryEntity: ChatHistoryEntity;\n}): Promise<string | undefined> {\n try {\n const recordId = chatHistoryEntity.recordId || genRecordId();\n const data = {\n record_id: recordId,\n bot_id: chatHistoryEntity.botId,\n role: chatHistoryEntity.role,\n content: chatHistoryEntity.content,\n sender: chatHistoryEntity.sender,\n conversation: chatHistoryEntity.conversation,\n type: chatHistoryEntity.type,\n image: chatHistoryEntity.image,\n trigger_src: chatHistoryEntity.triggerSrc,\n origin_msg: chatHistoryEntity.originMsg,\n reply_to: chatHistoryEntity.replyTo,\n reply: chatHistoryEntity.reply,\n trace_id: chatHistoryEntity.traceId,\n need_async_reply: chatHistoryEntity.needAsyncReply,\n async_reply: chatHistoryEntity.asyncReply,\n createdAt: Date.now(),\n updatedAt: Date.now(),\n };\n\n const db = tcbClient.database();\n const collection = db.collection(CHAT_HISTORY_DATA_SOURCE);\n const result = await collection.add(data);\n\n // console.log(\n // `Create record: chatHistoryEntity:${JSON.stringify(\n // chatHistoryEntity\n // )}, result: ${JSON.stringify(result)}`\n // );\n return recordId;\n } catch (error) {\n console.error(\"Failed to create chat history record, error:\", error);\n return undefined;\n }\n}\n\n// Update chat history by record ID\nexport async function updateChatHistoryByRecordId({\n tcbClient,\n recordId,\n chatHistoryEntity,\n}: {\n tcbClient: tcb.CloudBase;\n recordId: string;\n chatHistoryEntity: ChatHistoryEntity;\n}): Promise<string | undefined> {\n try {\n const db = tcbClient.database();\n const _ = db.command;\n const collection = db.collection(CHAT_HISTORY_DATA_SOURCE);\n\n const result = await collection\n .where({ record_id: _.eq(recordId) })\n .update({\n content: chatHistoryEntity.content,\n image: chatHistoryEntity.image,\n async_reply: chatHistoryEntity.asyncReply,\n recommend_questions: chatHistoryEntity.recommendQuestions,\n status: chatHistoryEntity.status,\n origin_msg: chatHistoryEntity.originMsg,\n updatedAt: Date.now(),\n });\n\n // console.log(\n // `Update record: recordId: ${recordId}, chatHistoryEntity:${JSON.stringify(\n // chatHistoryEntity\n // )}, result: ${JSON.stringify(result)}`\n // );\n return chatHistoryEntity.recordId;\n } catch (error) {\n console.error(\"Failed to update chat history, error:\", error);\n return undefined;\n }\n}\n\n// Query chat history from database\nexport async function describeChatHistory({\n tcbClient,\n botId,\n sort,\n pageSize = 10,\n pageNumber = 1,\n conversation,\n startCreatedAt,\n triggerSrc,\n}: {\n tcbClient: tcb.CloudBase;\n botId: string;\n sort: \"asc\" | \"desc\";\n pageSize?: number;\n pageNumber?: number;\n conversation?: string;\n startCreatedAt?: number;\n triggerSrc?: string;\n}): Promise<[ChatHistoryEntity[], number]> {\n if (!sort || sort.length === 0) {\n sort = \"desc\";\n }\n\n try {\n const db = tcbClient.database();\n const _ = db.command;\n const collection = db.collection(CHAT_HISTORY_DATA_SOURCE);\n\n // Build where conditions\n const whereConditions: Record<string, unknown> = {\n bot_id: _.eq(botId),\n };\n\n // Add optional filters\n if (conversation) {\n whereConditions.conversation = _.eq(conversation);\n }\n\n if (startCreatedAt !== undefined) {\n whereConditions.createdAt = _.gt(startCreatedAt);\n }\n\n if (triggerSrc) {\n whereConditions.trigger_src = _.eq(triggerSrc);\n }\n\n // Calculate skip for pagination\n const skip = (pageNumber - 1) * pageSize;\n\n // Query records\n const result = await collection\n .where(whereConditions)\n .orderBy(\"createdAt\", sort)\n .skip(skip)\n .limit(pageSize)\n .get();\n\n // Get total count\n const countResult = await collection.where(whereConditions).count();\n const total = countResult.total || 0;\n\n const records = result?.data || [];\n\n const entityList: ChatHistoryEntity[] = records.map(\n (item: ChatHistoryData) => transDataToChatEntity(item)\n );\n\n return [entityList, total];\n } catch (error) {\n console.error(\"Failed to query chat history, error:\", error);\n return [[], 0];\n }\n}\n\n// Transform data to ChatHistoryEntity structure\nexport function transDataToChatEntity(\n item: ChatHistoryData\n): ChatHistoryEntity {\n if (!item) {\n return new ChatHistoryEntity();\n }\n const chatEntity: ChatHistoryEntity = new ChatHistoryEntity();\n chatEntity.botId = item.bot_id;\n chatEntity.recordId = item.record_id;\n chatEntity.role = item.role;\n chatEntity.status = item.status;\n chatEntity.content = item.content;\n chatEntity.sender = item.sender;\n chatEntity.conversation = item.conversation;\n chatEntity.type = item.type;\n chatEntity.triggerSrc = item.trigger_src;\n chatEntity.originMsg = item.origin_msg;\n chatEntity.replyTo = item.reply_to;\n chatEntity.reply = item.reply;\n chatEntity.traceId = item.trace_id;\n chatEntity.needAsyncReply = item.need_async_reply;\n chatEntity.asyncReply = item.async_reply;\n chatEntity.createdAt = item.createdAt;\n chatEntity.updatedAt = item.updatedAt;\n return chatEntity;\n}\n\n// Query history records for LLM, get the most recent 10 conversation pairs (20 records)\nexport async function queryForLLM({\n tcbClient,\n botId,\n conversation,\n pageSize = 10,\n startCreatedAt,\n triggerSrc,\n}: {\n tcbClient: tcb.CloudBase;\n botId: string;\n conversation: string;\n pageSize?: number;\n startCreatedAt?: number;\n triggerSrc?: string;\n}): Promise<{ role: string; content: string }[]> {\n if (startCreatedAt === undefined) {\n startCreatedAt = Date.now() - 24 * 60 * 60 * 1000;\n }\n const recordEntityList: ChatHistoryEntity[] = [];\n\n const [recordList] = await describeChatHistory({\n tcbClient,\n botId,\n sort: \"desc\",\n pageSize,\n conversation,\n startCreatedAt,\n triggerSrc,\n });\n recordEntityList.push(...recordList.reverse());\n\n const entityMap = new Map<string, ChatHistoryEntity>();\n recordEntityList\n .filter((item) => {\n if (item.needAsyncReply === true) {\n return !!item.asyncReply;\n } else {\n return !!item.content;\n }\n })\n .forEach((item) => {\n entityMap.set(item.recordId, item);\n });\n\n const result: { role: string; content: string }[] = [];\n /*\n 1. Strongly depends on database history data, model history data has role order requirements\n 2. Need to ensure that no matter what bug occurs, always get a complete and usable user + assistant pair, otherwise the request will fail\n */\n recordEntityList.forEach((item) => {\n const { role, content, reply } = item;\n // When calling LLM, empty content will cause failure, so filter out conversations with empty content\n if (role === \"user\" && content?.length !== 0) {\n if (entityMap.has(reply)) {\n result.push({ role, content });\n result.push({\n role: entityMap.get(reply)!.role,\n content: entityMap.get(reply)!.content,\n });\n }\n }\n });\n if (result.length % 2 === 1) {\n result.splice(-1, 1);\n }\n return result;\n}\n\nexport interface ChatHistoryData {\n bot_id: string;\n record_id: string;\n role: string;\n status: string;\n content: string;\n sender: string;\n conversation: string;\n type: string;\n trigger_src: string;\n origin_msg: string;\n reply_to: string;\n reply: string;\n trace_id: string;\n need_async_reply: boolean;\n async_reply: string;\n createdAt: number;\n updatedAt: number;\n}\n\nexport class ChatHistoryEntity {\n id: number;\n botId: string;\n // 对话唯一id\n recordId: string;\n role: string;\n content: string;\n recommendQuestions: string[];\n sender: string;\n conversation: string;\n type: string;\n /**\n * 消息状态,pending done error cancel\n */\n status: string;\n image: string;\n triggerSrc: string;\n originMsg: string;\n replyTo: string;\n reply: string;\n traceId: string;\n needAsyncReply: boolean;\n asyncReply: string;\n createTime: string;\n updateTime: string;\n createdAt: number;\n updatedAt: number;\n event: string;\n}\n"],"mappings":"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","names":["EventType","EventType"]}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@cloudbase/agent-adapter-yuanqi",
3
- "version": "0.0.22",
3
+ "version": "0.0.23",
4
4
  "description": "Tencent Yuanqi adapter for AG-Kit agents",
5
5
  "files": [
6
6
  "dist/",