From 9251a345c39e3e582643325fe1e7d51126201bba Mon Sep 17 00:00:00 2001 From: interstellarmt <787982239@qq.com> Date: Fri, 18 Jul 2025 16:43:08 +0800 Subject: [PATCH 1/2] feat: simplify the code, remove unnecessary prompts, and optimize prompts for complex tasks --- src/tools/extract_antv_topic.ts | 294 +++++++------------------ src/tools/query_antv_document.ts | 360 ++++++++++--------------------- 2 files changed, 191 insertions(+), 463 deletions(-) diff --git a/src/tools/extract_antv_topic.ts b/src/tools/extract_antv_topic.ts index 5893f71..51aa1a6 100644 --- a/src/tools/extract_antv_topic.ts +++ b/src/tools/extract_antv_topic.ts @@ -1,10 +1,6 @@ /** - * AntV Intelligent Assistant Preprocessing Tool - * - * 处理所有与 AntV 可视化库相关的用户查询,智能识别、解析并结构化用户需求。 - * 支持自动识别库类型、提取技术主题关键词、判断用户意图,并为后续 query_antv_document 工具准备结构化信息。 + * AntV Topic Extraction Tool - Preprocesses user queries for AntV libraries */ - import { z } from 'zod'; import type { AntVLibrary } from '../types'; import { logger } from '../utils'; @@ -51,251 +47,117 @@ interface ExtractAntVTopicArgs { } function generateExtractionPrompt(args: ExtractAntVTopicArgs): string { - const libraryContext = args.library - ? getLibraryConfig(args.library) - : undefined; - return generateUnifiedPrompt(args.query, args.maxTopics, libraryContext); -} - -function generateUnifiedPrompt( - query: string, - maxTopics: number, - libraryContext?: { id: AntVLibrary; name: string }, -): string { - const isLibrarySpecified = !!libraryContext; - const allLibraries = Object.values(ANTV_LIBRARY_META); - const libraryDeterminationSection = isLibrarySpecified - ? generateLibrarySpecifiedSection(libraryContext) - : generateLibraryDetectionSection(allLibraries); - const extractionRulesSection = generateExtractionRulesSection( - maxTopics, - libraryContext, - ); - const outputFormatSection = generateOutputFormatSection(); - const examplesSection = generateExamplesSection(); - return `# AntV ${isLibrarySpecified ? 'Topic and Intent Extraction' : 'Smart Library Detection and Topic Extraction'} Task - -## Task Objective -${ - isLibrarySpecified - ? `Extract the most relevant technical topic phrases and user intent from user queries for ${libraryContext.name} documentation retrieval.` - : `1. First: Detect and recommend the most suitable AntV library based on query intent and installed dependencies - 2. Second: Extract relevant technical topics and user intent for the determined library` -} - -## User Query -\`\`\` -${query} -\`\`\` - -${libraryDeterminationSection} - -${extractionRulesSection} - -## Output Format - -${outputFormatSection} - -## Examples - -${examplesSection} - -Now please begin ${isLibrarySpecified ? 'extraction' : 'the detection and extraction process'}: + const { query, library, maxTopics } = args; -## Important Notice -**MANDATORY NEXT STEP**: After completing this task, immediately call the \`query_antv_document\` tool with the extracted parameters. - -**Requirements:** -- Always use extracted library, topic, intent parameters with \`query_antv_document\` tool -- Never skip \`query_antv_document\` tool call and answer directly -- For complex tasks: pass subTasks parameter; for simple tasks: use basic parameters`; -} - -function generateLibrarySpecifiedSection(libraryContext: { - id: AntVLibrary; - name: string; -}): string { - return `## Phase 1: Library Context - **Target Library**: ${libraryContext.name} (${libraryContext.id})`; -} - -function generateLibraryDetectionSection( - allLibraries: Array<{ id: AntVLibrary; name: string; description: string }>, -): string { - // 动态生成库映射列表 + // Generate library mappings const libraryMappings = Object.values(ANTV_LIBRARY_META) - .map((lib) => ` - \`@antv/${lib.id}\` → ${lib.name}`) + .map((lib) => ` - **${lib.name} (${lib.id})**: ${lib.description}`) .join('\n'); - return `## Phase 1: Library Detection and Recommendation - -**Your first task is to determine the most suitable AntV library for this query.** + // Get library-specific context if specified + const libraryContext = library + ? { + name: getLibraryConfig(library).name, + keywords: getLibraryKeywords(library), + } + : null; -### Step 1.1: Project Dependency Scan -Scan the user's current project for installed AntV dependencies: -1. **Check package.json**: Look for AntV-related dependencies in both \`dependencies\` and \`devDependencies\` -2. **Look for patterns**: -${libraryMappings} + const libraryTerminology = libraryContext + ? libraryContext.keywords + : 'Use the terminology and components specific to the determined target library'; -### Step 1.2: Smart Library Recommendation -Based on query content and detected dependencies, recommend the most suitable library: + return `# AntV Query Analysis & Topic Extraction -**Library Selection Rules (Priority Order):** -1. **Query Intent Match**: Select library that best matches the technical requirements: - ${allLibraries - .map((lib) => `- **${lib.name} (${lib.id})**: ${lib.description}`) - .join('\n ')} +## User Query +**Query**: ${query} +**Max Topics**: ${maxTopics} +${library ? `**Specified Library**: ${getLibraryConfig(library).name} (${library})` : '**Library**: Auto-detect'} -2. **Installed Dependency Priority**: If multiple libraries match the intent, prioritize installed ones -3. **Best Practice Guidance**: Consider the most commonly used library for the specific use case +## Task Instructions -**Output the recommended library and reason before proceeding to Phase 2.**`; -} +### Phase 1: Library Detection ${library ? '(Skipped - Library Specified)' : ''} +${ + library + ? `Using specified library: **${getLibraryConfig(library).name} (${library})**` + : `**Determine the most suitable AntV library:** -function generateExtractionRulesSection( - maxTopics: number, - libraryContext?: { id: AntVLibrary; name: string }, -): string { - const libraryTerminology = libraryContext - ? getLibraryKeywords(libraryContext.id) - : 'Use the terminology and components specific to the determined target library'; - const librarySpecificPriority = libraryContext - ? `${libraryContext.name} specific component concepts and APIs` - : 'Target library specific component concepts and APIs'; - return `## Phase 2: Topic Extraction and Intent Recognition +Available Libraries: +${libraryMappings} -Once you have the target library (either specified or determined), proceed with: +**Selection Priority:** +1. Match query intent with library purpose +2. Check for existing project dependencies +3. Consider common use cases for the query type` +} -### 2.1: Complex Task Detection -Determine whether the user query is a complex task. Characteristics of complex tasks: -- Contains multiple technical concepts or functional points -- Requires multiple steps to complete -- Involves multiple chart types or multiple functions -- Has clear workflow or combination requirements +### Phase 2: Topic Extraction & Analysis -### 2.2: Topic Phrase Extraction -- **Source Limitation**: Extract only from user query content, do not add concepts not present in the query -- **CRITICAL: All topics MUST be in English** - Use official AntV English terminology from: ${ - libraryContext - ? getLibraryKeywords(libraryContext.id) - : 'Use the terminology and components specific to the determined target library' - } -- 翻译和提取时,务必优先使用上方列出的官方组件英文名称,保持与官方文档一致,避免自创或误译,保持技术准确性 -- **Quantity Requirement**: Maximum ${maxTopics} items, can be fewer than this number -- **Format Requirements**: - - Extract meaningful phrase combinations (1-4 words) - - Avoid single words or overly long sentences - - Ensure diversity between terms, avoid repetition - - **MANDATORY**: Output only English technical terms for documentation search -- **Components, Concepts, Terminology**: ${libraryTerminology} -- **Priority**: - 1. ${librarySpecificPriority} - 2. Chart types and visualization concepts - 3. Interaction, animation effects, data processing and configuration +**Extract up to ${maxTopics} key technical topics covering ALL aspects mentioned:** +- Extract only from user query content, no additional concepts +- Use official AntV English terminology${libraryContext ? `: ${libraryContext.keywords}` : ''} +- Format as meaningful phrases (1-4 words), output in English only +- **Cover these technical aspects in priority order**: + 1. Chart types and core components + 2. Visual styling (colors, thickness, backgrounds, opacity) + 3. Interactions (hover, click, tooltip, zoom) + 4. Configurations (data processing, scales, axis, animations) -### 2.3: User Intent Recognition +**Determine User Intent:** Based on the tone and content of the query, select the most matching intent: - **learn**: Learning and understanding (e.g., what is, how to understand, introduce) - **implement**: Implementing functionality (e.g., how to create, how to implement, code examples) - **solve**: Solving problems (e.g., errors, not working, fixing issues) -### 2.4: Complex Task Decomposition -If determined to be a complex task, decompose into 2-4 subtasks, each subtask should: +**Assess Task Complexity:** +Determine if the query is complex based on: +- Extracted topics exceed 5 +- Involves more than 2 components or features +- Other cases where the query appears complex based on overall assessment (e.g., multi-step processes, combinations of features) + + +If complex, decompose into 2-4 subtasks, each subtask should: - Focus on a specific technical point or functionality - Be able to independently obtain answers through documentation queries - Be arranged in logical order (basic → advanced) - Subtask topics must be clear, concise, and follow the format requirements above -**Note**: For complex tasks, provide the decomposed subtask list to the query_antv_document tool for one-time processing.`; -} +### Phase 3: Output Format -function generateOutputFormatSection(): string { - return `### Simple Task Output Format: +**For Simple Tasks:** \`\`\`json { - "topic": "actually extracted topic1, topic2, topic3", + "library": "detected_or_specified_library", + "topic": "topic1, topic2, topic3", "intent": "learn|implement|solve", - "library": "the target library (either specified or determined)", "isComplexTask": false } \`\`\` -### Complex Task Output Format: +**For Complex Tasks:** \`\`\`json { - "topic": "summary of all related topics", - "intent": "overall intent", - "library": "the target library (either specified or determined)", + "library": "detected_or_specified_library", + "topic": "overall_topic_summary", + "intent": "overall_intent", "isComplexTask": true, "subTasks": [ { - "query": "specific question for subtask 1", - "topic": "topic for subtask 1", - "intent": "intent for subtask 1" + "query": "specific_subtask_question_1", + "topic": "subtask_topic_1" }, { - "query": "specific question for subtask 2", - "topic": "topic for subtask 2", - "intent": "intent for subtask 2" + "query": "specific_subtask_question_2", + "topic": "subtask_topic_2" } ] } -\`\`\``; -} - -function generateExamplesSection(): string { - return `**Example 1 - Simple Task (English Query)** -Query: "What is G2?" -Output: -\`\`\`json -{ - "topic": "G2 introduction", - "intent": "learn", - "library": "g2", - "isComplexTask": false -} \`\`\` -**Example 2 - Simple Task (Chinese Query)** -Query: "如何修改G2图表的颜色?" -Output: -\`\`\`json -{ - "topic": "chart color, styling", - "intent": "implement", - "library": "g2", - "isComplexTask": false -} -\`\`\` +**Analyze the query and provide the structured output above.** -**Example 3 - Complex Task** -Query: "How to create an animated bar chart with hover interaction in G2?" -Output: -\`\`\`json -{ - "topic": "animated bar chart, chart animation, hover interaction, mouse events", - "intent": "implement", - "library": "g2", - "isComplexTask": true, - "subTasks": [ - { - "query": "How to create a basic bar chart in G2?", - "topic": "bar chart, chart creation", - "intent": "implement" - }, - { - "query": "How to add animation effects to G2 charts?", - "topic": "chart animation, animation effects", - "intent": "implement" - }, - { - "query": "How to add hover interaction to G2 charts?", - "topic": "hover interaction, mouse events", - "intent": "implement" - } - ] -} -\`\`\``; +## Important Notice +**MANDATORY NEXT STEP**: After completing this task, immediately call the \`query_antv_document\` tool with the extracted parameters. +`; } export const ExtractAntVTopicTool = { @@ -321,8 +183,8 @@ Key features: const startTime = Date.now(); try { const extractionPrompt = generateExtractionPrompt(args); - const maxTopics = args.maxTopics; const processingTime = Date.now() - startTime; + return { content: [ { @@ -333,8 +195,8 @@ Key features: _meta: { topic: '', // Will be filled by LLM intent: '', // Will be filled by LLM - library: args.library || 'g2', - maxTopics, + library: args.library || 'auto-detect', + maxTopics: args.maxTopics, promptGenerated: true, next_tools: ['query_antv_document'], isComplexTask: false, // Will be determined and filled by LLM @@ -344,18 +206,8 @@ Key features: }; } catch (error) { logger.error('Failed to generate extraction prompt:', error); - // Use safe fallbacks since validation might have failed - const fallbackLibrary = - args.library && Object.keys(ANTV_LIBRARY_META).includes(args.library) - ? args.library - : 'g2'; - const fallbackMaxTopics = - typeof args.maxTopics === 'number' && - args.maxTopics >= 3 && - args.maxTopics <= 8 - ? args.maxTopics - : 5; const processingTime = Date.now() - startTime; + return { content: [ { @@ -369,8 +221,8 @@ Key features: _meta: { topic: '', intent: '', - library: fallbackLibrary, - maxTopics: fallbackMaxTopics, + library: args.library || 'auto-detect', + maxTopics: args.maxTopics, promptGenerated: false, next_tools: ['query_antv_document'], isComplexTask: false, diff --git a/src/tools/query_antv_document.ts b/src/tools/query_antv_document.ts index 860d099..15f26cc 100644 --- a/src/tools/query_antv_document.ts +++ b/src/tools/query_antv_document.ts @@ -1,14 +1,8 @@ /** - * AntV Professional Documentation Assistant - * - * Provides accurate and detailed visualization solutions based on official AntV documentation. - * Suitable for all AntV-related follow-up queries and supplementary questions. - * After initial queries, if users propose any AntV-related corrections, optimizations, supplements, or new requirements, this tool should be called. - * Supports both simple queries and complex task processing, providing code examples and best practice recommendations. Covers the entire AntV ecosystem. + * AntV Documentation Query Tool - Provides visualization solutions from official docs */ - import { z } from 'zod'; -import type { AntVConfig, AntVLibrary } from '../types'; +import type { AntVLibrary } from '../types'; import { logger, getLibraryId, fetchLibraryDocumentation } from '../utils'; import { getLibraryConfig, @@ -16,271 +10,155 @@ import { CONTEXT7_TOKENS, } from '../constant'; -type QueryAntVDocumentArgs = { - library: AntVLibrary; - query: string; - tokens: number; - topic: string; - intent: string; - subTasks?: Array<{ - query: string; - topic: string; - }>; -}; - const QueryAntVDocumentInputSchema = z.object({ - library: z - .enum( - Object.keys(ANTV_LIBRARY_META) as [ - keyof typeof ANTV_LIBRARY_META, - ...Array, - ], - { - errorMap: () => ({ - message: `Unsupported library. Must be one of: ${Object.keys(ANTV_LIBRARY_META).join(', ')}`, - }), - }, - ) - .describe( - 'Specified AntV library type, intelligently identified based on user query', - ), - query: z - .string() - .min(1, 'Query cannot be empty') - .trim() - .describe('User specific question or requirement description'), - tokens: z - .number() - .int('Tokens must be an integer') - .min(CONTEXT7_TOKENS.min, `Tokens must be at least ${CONTEXT7_TOKENS.min}`) - .max(CONTEXT7_TOKENS.max, `Tokens cannot exceed ${CONTEXT7_TOKENS.max}`) + library: z.enum(Object.keys(ANTV_LIBRARY_META) as [AntVLibrary, ...AntVLibrary[]]) + .describe('Specified AntV library type, intelligently identified based on user query'), + query: z.string().min(1).describe('User specific question or requirement description'), + topic: z.string().min(1).describe('Technical topic keywords (comma-separated). Provided by `extract_antv_topic` or directly extracted from simple questions.'), + intent: z.string().min(1).describe('Extracted user intent, provided by extract_antv_topic tool or directly extracted from simple questions.'), + tokens: z.number().int() + .min(CONTEXT7_TOKENS.min) + .max(CONTEXT7_TOKENS.max) .default(CONTEXT7_TOKENS.default) .describe('tokens for returned content'), - topic: z - .string() - .min(1, 'Topic cannot be empty') - .trim() - .describe( - 'Technical topic keywords (comma-separated). Provided by `extract_antv_topic` or directly extracted from simple questions.', - ), - intent: z - .string() - .min(1, 'Intent cannot be empty') - .trim() - .describe( - 'Extracted user intent, provided by extract_antv_topic tool or directly extracted from simple questions.', - ), - subTasks: z - .array( - z.object({ - query: z - .string() - .min(1, 'Subtask query cannot be empty') - .trim() - .describe('Subtask query'), - topic: z - .string() - .min(1, 'Subtask topic cannot be empty') - .trim() - .describe('Subtask topic'), - }), - ) - .describe( - 'Decomposed subtask list for complex tasks, supports batch processing', - ) - .optional(), + subTasks: z.array(z.object({ + query: z.string().min(1).describe('Subtask query'), + topic: z.string().min(1).describe('Subtask topic') + })).optional().describe('Decomposed subtask list for complex tasks, supports batch processing') }); -async function handleComplexTaskWithDocCheck( +type QueryAntVDocumentArgs = z.infer; + +async function handleComplexTask( args: QueryAntVDocumentArgs, libraryId: string, - subTasks: Array<{ query: string; topic: string }>, + subTasks: Array<{ query: string; topic: string }> ): Promise<{ response: string; hasDocumentation: boolean }> { const libraryConfig = getLibraryConfig(args.library); - const library = libraryConfig.name; - let response = `# ${library} Complex Task Response\n\n`; - response += `**User Question**: ${args.query}\n`; - response += `**Task Type**: Complex task (decomposed into ${subTasks.length} subtasks)\n`; - response += `\n---\n\n`; - const tokenPerSubTask = Math.min( - Math.floor(args.tokens / subTasks.length), - 1000, - ); + const tokenPerSubTask = Math.min(Math.floor(args.tokens / subTasks.length), 1000); + + let response = `# ${libraryConfig.name} Complex Task Solution\n\n`; + response += `**Question**: ${args.query}\n`; + response += `**Complexity**: Decomposed into ${subTasks.length} subtasks\n\n---\n\n`; + const subTaskPromises = subTasks.map(async (subTask, index) => { try { - logger.info( - `Processing subtask ${index + 1}/${subTasks.length}: ${subTask.topic}`, - ); - const { documentation, error: docError } = - await fetchLibraryDocumentation( - libraryId, - subTask.topic, - tokenPerSubTask, - ); - return { task: subTask, documentation, error: docError }; + logger.info(`Processing subtask ${index + 1}/${subTasks.length}: ${subTask.topic}`); + const { documentation, error } = await fetchLibraryDocumentation(libraryId, subTask.topic, tokenPerSubTask); + return { task: subTask, documentation, error }; } catch (error) { logger.error(`Failed to process subtask ${index + 1}:`, error); return { task: subTask, documentation: null, - error: error instanceof Error ? error.message : String(error), + error: error instanceof Error ? error.message : String(error) }; } }); - const subTaskResults = await Promise.all(subTaskPromises); - const hasValidDocumentation = subTaskResults.some( - (result) => - result.documentation !== null && result.documentation.trim() !== '', - ); - for (const [index, result] of subTaskResults.entries()) { - response += `## 📋 Subtask ${index + 1}\n\n`; - response += `**Subtask Query**: ${result.task.query}\n`; - response += `**Subtask Topic**: ${result.task.topic}\n\n`; + + const results = await Promise.all(subTaskPromises); + const hasDocumentation = results.some(r => r.documentation !== null && r.documentation.trim() !== ''); + + // Generate subtask responses + for (const [index, result] of results.entries()) { + response += `## 📋 Subtask ${index + 1}: ${result.task.query}\n\n`; if (result.documentation) { response += `${result.documentation}\n\n`; } else { - response += `⚠️ Could not retrieve relevant documentation content\n\n`; + response += `⚠️ No relevant documentation found for this subtask.\n`; if (result.error) { - response += `\nError: ${result.error}\n`; - } else { - response += `\n`; + response += `Error: ${result.error}\n`; } - response += `\n`; } response += `---\n\n`; } - response += `## 🎯 Task Integration Recommendations\n\n`; - response += generateComplexTaskSummary(subTaskResults); - response += generateIntentSpecificGuidance(args.intent, libraryConfig); - response += generateFollowUpGuidance(); - return { response, hasDocumentation: hasValidDocumentation }; -} -function generateComplexTaskSummary( - subTaskResults: Array<{ - task: any; - documentation: string | null; - error: string | undefined; - }>, -): string { - const successCount = subTaskResults.filter((r) => r.documentation).length; - const totalCount = subTaskResults.length; - let summary = `Based on ${successCount}/${totalCount} subtask documentation query results:\n\n`; - if (successCount === totalCount) { - summary += `✅ **Complete Answer**: All subtasks found relevant documentation`; - } else if (successCount > totalCount / 2) { - summary += `⚠️ **Partial Answer**: Most subtasks found relevant documentation. Recommendations:\n\n`; - summary += `1. Implement features with documentation support first\n`; - summary += `2. For parts lacking documentation, consult official resources or example code\n`; - summary += `3. Gradually improve solutions through practice\n\n`; + // Add integration summary + const successCount = results.filter(r => r.documentation).length; + response += `## 🎯 Integration Summary\n\n`; + + if (successCount === results.length) { + response += `✅ **Complete Solution**: Found documentation for all ${successCount} subtasks.\n\n`; + response += `**Next Steps**: Combine the solutions above into your implementation.\n\n`; + } else if (successCount > 0) { + response += `⚠️ **Partial Solution**: Found documentation for ${successCount}/${results.length} subtasks.\n\n`; + response += `**Recommendations**:\n`; + response += `- Implement features with available documentation first\n`; + response += `- For missing parts, check official examples or community resources\n\n`; } else { - summary += `❌ **Insufficient Documentation**: Most subtasks lack documentation support. Recommendations:\n\n`; - summary += `1. Refine query keywords\n`; - summary += `2. Consult official documentation and examples\n`; - summary += `3. Look for community resources and best practices\n\n`; + response += `❌ **Limited Results**: No documentation found for the subtasks.\n\n`; + response += `**Suggestions**:\n`; + response += `- Try refining the query with more specific keywords\n`; + response += `- Check the official ${libraryConfig.name} documentation directly\n\n`; } - return summary; + + response += generateImplementationGuidance(args.intent); + response += generateFollowUpNotice(); + + return { response, hasDocumentation }; } -function generateResponse( - args: QueryAntVDocumentArgs, - context: string | null, - errorMsg?: string | undefined, -): string { +function generateSimpleResponse(args: QueryAntVDocumentArgs, documentation: string | null, error?: string): string { const libraryConfig = getLibraryConfig(args.library); - const library = libraryConfig.name; - let response = `# ${library} Q&A\n\n`; - response += `**User Question**: ${args.query}\n`; - response += `**Search Topic**: ${args.topic}\n`; - response += `\n---\n\n`; - if (context) { - response += `## 📚 Related Documentation\n\n${context}\n\n`; - response += generateIntentSpecificGuidance(args.intent, libraryConfig); - } else { - response += `## ⚠️ Documentation Retrieval Failed\n\n`; - response += `\nError: ${errorMsg}\n`; - response += `Could not retrieve relevant documentation content. Recommendations:\n`; - response += `1. Check if search topics are accurate\n`; - response += `2. Try using more specific technical terms\n`; - response += `3. Refer to ${library} official documentation\n`; + + if (!documentation) { + return `# ${libraryConfig.name} Query Result\n\n` + + `**Question**: ${args.query}\n\n` + + `❌ **No Documentation Found**\n\n` + + `${error ? `Error: ${error}\n\n` : ''}` + + `**Suggestions**:\n` + + `- Try refining your search terms\n` + + `- Check the official ${libraryConfig.name} documentation\n` + + `- Ensure you're using the correct library for your use case\n\n` + + generateFollowUpNotice(); } - response += generateFollowUpGuidance(); + + let response = `# ${libraryConfig.name} Solution\n\n`; + response += `**Question**: ${args.query}\n\n`; + response += `${documentation}\n\n`; + response += generateImplementationGuidance(args.intent); + response += generateFollowUpNotice(); + return response; } -function generateIntentSpecificGuidance( - intent: string, - libraryConfig: AntVConfig, -): string { +function generateImplementationGuidance(intent: string): string { switch (intent) { case 'learn': - return generateLearnGuidance(); + return `## 💡 Learning Tips\n\n` + + `- Review the concepts and examples above\n` + + `- Try running the code examples in your development environment\n` + + `- Start with basic implementations before adding complexity\n\n`; + case 'implement': - return generateImplementGuidance(libraryConfig); + return `## 🛠️ Implementation Guide\n\n` + + `- Follow the code examples and patterns shown above\n` + + `- Pay attention to required vs optional parameters\n` + + `- Test with simple data first, then use your real data\n` + + `- Check browser console for any errors during development\n\n`; + case 'solve': - return generateSolveGuidance(libraryConfig); + return `## 🔧 Troubleshooting\n\n` + + `- Compare your code with the examples above\n` + + `- Verify all required dependencies are installed\n` + + `- Check for version compatibility issues\n` + + `- Look for error messages in browser console\n\n`; + default: - return generateDefaultGuidance(libraryConfig); + return `## 📖 Next Steps\n\n` + + `- Review the documentation above carefully\n` + + `- Adapt the examples to your specific requirements\n` + + `- Test incrementally and iterate as needed\n\n`; } } -function generateLearnGuidance(): string { - return `## 💡 Learning Recommendations - -- First understand the core concepts and basic usage in the documentation -- Run example code to observe effects and parameter functions -- Start with simple examples, gradually try complex features -- Consult official documentation when encountering problems - -`; -} - -function generateImplementGuidance(libraryConfig: AntVConfig): string { - return `## 🛠️ Implementation Recommendations -- Follow the code style and best practices of the library: ${libraryConfig.codeStyle} -- Refer to example code in the documentation -- Pay attention to required and optional parameter configurations -- Implement basic features first, then add advanced features -- Don't over-optimize, focus on user requirements -- Merge multiple examples into one final solution with only core functionality -`; -} - -function generateSolveGuidance(libraryConfig: AntVConfig): string { - return `## 🔧 Troubleshooting - -- Check error messages and parameter configurations -- Compare your code with documentation examples for differences -- Confirm ${libraryConfig.name} version and dependency compatibility -- If problems persist, check official GitHub Issues - -`; -} - -function generateDefaultGuidance(libraryConfig: AntVConfig): string { - return `## 📖 Usage Recommendations - -- Carefully read the above documentation content -- Practice with reference to code examples -- Adjust relevant parameters according to requirements -- Consult ${libraryConfig.name} official documentation for more information - -`; -} - -function generateFollowUpGuidance(): string { - return ` - ---- - -## 🔄 Important Notice - -**For subsequent AntV queries:** -- **MANDATORY**: Always use \`query_antv_document\` tool for ANY AntV-related query (including simple modifications) -- **For new questions**: Use \`extract_antv_topic\` first, then \`query_antv_document\` -- **Never** provide AntV solutions without querying official documentation through tools - -`; +function generateFollowUpNotice(): string { + return `---\n\n` + + `## 🔄 Important Notice\n\n` + + `**For subsequent AntV queries:**\n` + + `- **MANDATORY**: Always use \`query_antv_document\` tool for ANY AntV-related query (including simple modifications)\n` + + `- **For new questions**: Use \`extract_antv_topic\` first, then \`query_antv_document\`\n` + + `- **Never** provide AntV solutions without querying official documentation through tools\n\n`; } export const QueryAntVDocumentTool = { @@ -301,23 +179,20 @@ When to use this tool: try { const libraryId = getLibraryId(args.library); let response: string; - let subTaskResults: any[] = []; - let isComplexTask = false; let hasDocumentation = false; + if (args.subTasks && args.subTasks.length > 0) { - isComplexTask = true; - const { response: taskResponse, hasDocumentation: taskHasDoc } = - await handleComplexTaskWithDocCheck(args, libraryId, args.subTasks); - response = taskResponse; - hasDocumentation = taskHasDoc; - subTaskResults = args.subTasks; + // Handle complex task with subtasks + const result = await handleComplexTask(args, libraryId, args.subTasks); + response = result.response; + hasDocumentation = result.hasDocumentation; } else { - const { documentation, error: docError } = - await fetchLibraryDocumentation(libraryId, args.topic, args.tokens); - hasDocumentation = - documentation !== null && documentation.trim() !== ''; - response = generateResponse(args, documentation, docError); + // Handle simple query + const { documentation, error } = await fetchLibraryDocumentation(libraryId, args.topic, args.tokens); + hasDocumentation = documentation !== null && documentation.trim() !== ''; + response = generateSimpleResponse(args, documentation, error); } + const processingTime = Date.now() - startTime; return { content: [{ type: 'text', text: response }], @@ -330,8 +205,9 @@ When to use this tool: }, }; } catch (error) { - logger.error('Failed to execute assistant tool:', error); + logger.error('Failed to execute query tool:', error); const processingTime = Date.now() - startTime; + return { content: [ { From 5fb85ed332ce0410bc06d119a82883e95cfb70c6 Mon Sep 17 00:00:00 2001 From: interstellarmt <787982239@qq.com> Date: Fri, 18 Jul 2025 17:13:15 +0800 Subject: [PATCH 2/2] fix: context7 query with topic --- src/tools/query_antv_document.ts | 167 +++++++++++++++++++++---------- 1 file changed, 113 insertions(+), 54 deletions(-) diff --git a/src/tools/query_antv_document.ts b/src/tools/query_antv_document.ts index 15f26cc..8b4daa2 100644 --- a/src/tools/query_antv_document.ts +++ b/src/tools/query_antv_document.ts @@ -11,20 +11,45 @@ import { } from '../constant'; const QueryAntVDocumentInputSchema = z.object({ - library: z.enum(Object.keys(ANTV_LIBRARY_META) as [AntVLibrary, ...AntVLibrary[]]) - .describe('Specified AntV library type, intelligently identified based on user query'), - query: z.string().min(1).describe('User specific question or requirement description'), - topic: z.string().min(1).describe('Technical topic keywords (comma-separated). Provided by `extract_antv_topic` or directly extracted from simple questions.'), - intent: z.string().min(1).describe('Extracted user intent, provided by extract_antv_topic tool or directly extracted from simple questions.'), - tokens: z.number().int() + library: z + .enum(Object.keys(ANTV_LIBRARY_META) as [AntVLibrary, ...AntVLibrary[]]) + .describe( + 'Specified AntV library type, intelligently identified based on user query', + ), + query: z + .string() + .min(1) + .describe('User specific question or requirement description'), + topic: z + .string() + .min(1) + .describe( + 'Technical topic keywords (comma-separated). Provided by `extract_antv_topic` or directly extracted from simple questions.', + ), + intent: z + .string() + .min(1) + .describe( + 'Extracted user intent, provided by extract_antv_topic tool or directly extracted from simple questions.', + ), + tokens: z + .number() + .int() .min(CONTEXT7_TOKENS.min) .max(CONTEXT7_TOKENS.max) .default(CONTEXT7_TOKENS.default) .describe('tokens for returned content'), - subTasks: z.array(z.object({ - query: z.string().min(1).describe('Subtask query'), - topic: z.string().min(1).describe('Subtask topic') - })).optional().describe('Decomposed subtask list for complex tasks, supports batch processing') + subTasks: z + .array( + z.object({ + query: z.string().min(1).describe('Subtask query'), + topic: z.string().min(1).describe('Subtask topic'), + }), + ) + .optional() + .describe( + 'Decomposed subtask list for complex tasks, supports batch processing', + ), }); type QueryAntVDocumentArgs = z.infer; @@ -32,10 +57,13 @@ type QueryAntVDocumentArgs = z.infer; async function handleComplexTask( args: QueryAntVDocumentArgs, libraryId: string, - subTasks: Array<{ query: string; topic: string }> + subTasks: Array<{ query: string; topic: string }>, ): Promise<{ response: string; hasDocumentation: boolean }> { const libraryConfig = getLibraryConfig(args.library); - const tokenPerSubTask = Math.min(Math.floor(args.tokens / subTasks.length), 1000); + const tokenPerSubTask = Math.min( + Math.floor(args.tokens / subTasks.length), + 1000, + ); let response = `# ${libraryConfig.name} Complex Task Solution\n\n`; response += `**Question**: ${args.query}\n`; @@ -43,25 +71,34 @@ async function handleComplexTask( const subTaskPromises = subTasks.map(async (subTask, index) => { try { - logger.info(`Processing subtask ${index + 1}/${subTasks.length}: ${subTask.topic}`); - const { documentation, error } = await fetchLibraryDocumentation(libraryId, subTask.topic, tokenPerSubTask); + logger.info( + `Processing subtask ${index + 1}/${subTasks.length}: ${subTask.topic}`, + ); + const { documentation, error } = await fetchLibraryDocumentation( + libraryId, + subTask.topic, + tokenPerSubTask, + ); return { task: subTask, documentation, error }; } catch (error) { logger.error(`Failed to process subtask ${index + 1}:`, error); return { task: subTask, documentation: null, - error: error instanceof Error ? error.message : String(error) + error: error instanceof Error ? error.message : String(error), }; } }); const results = await Promise.all(subTaskPromises); - const hasDocumentation = results.some(r => r.documentation !== null && r.documentation.trim() !== ''); + const hasDocumentation = results.some( + (r) => r.documentation !== null && r.documentation.trim() !== '', + ); // Generate subtask responses for (const [index, result] of results.entries()) { response += `## 📋 Subtask ${index + 1}: ${result.task.query}\n\n`; + response += `**Subtask Topic**: ${result.task.topic}\n\n`; if (result.documentation) { response += `${result.documentation}\n\n`; } else { @@ -74,7 +111,7 @@ async function handleComplexTask( } // Add integration summary - const successCount = results.filter(r => r.documentation).length; + const successCount = results.filter((r) => r.documentation).length; response += `## 🎯 Integration Summary\n\n`; if (successCount === results.length) { @@ -98,23 +135,30 @@ async function handleComplexTask( return { response, hasDocumentation }; } -function generateSimpleResponse(args: QueryAntVDocumentArgs, documentation: string | null, error?: string): string { +function generateSimpleResponse( + args: QueryAntVDocumentArgs, + documentation: string | null, + error?: string, +): string { const libraryConfig = getLibraryConfig(args.library); if (!documentation) { - return `# ${libraryConfig.name} Query Result\n\n` + - `**Question**: ${args.query}\n\n` + - `❌ **No Documentation Found**\n\n` + - `${error ? `Error: ${error}\n\n` : ''}` + - `**Suggestions**:\n` + - `- Try refining your search terms\n` + - `- Check the official ${libraryConfig.name} documentation\n` + - `- Ensure you're using the correct library for your use case\n\n` + - generateFollowUpNotice(); + return ( + `# ${libraryConfig.name} Query Result\n\n` + + `**Question**: ${args.query}\n\n` + + `❌ **No Documentation Found**\n\n` + + `${error ? `Error: ${error}\n\n` : ''}` + + `**Suggestions**:\n` + + `- Try refining your search terms\n` + + `- Check the official ${libraryConfig.name} documentation\n` + + `- Ensure you're using the correct library for your use case\n\n` + + generateFollowUpNotice() + ); } let response = `# ${libraryConfig.name} Solution\n\n`; - response += `**Question**: ${args.query}\n\n`; + response += `**User Question**: ${args.query}\n`; + response += `**Search Topic**: ${args.topic}\n`; response += `${documentation}\n\n`; response += generateImplementationGuidance(args.intent); response += generateFollowUpNotice(); @@ -125,40 +169,50 @@ function generateSimpleResponse(args: QueryAntVDocumentArgs, documentation: stri function generateImplementationGuidance(intent: string): string { switch (intent) { case 'learn': - return `## 💡 Learning Tips\n\n` + - `- Review the concepts and examples above\n` + - `- Try running the code examples in your development environment\n` + - `- Start with basic implementations before adding complexity\n\n`; + return ( + `## 💡 Learning Tips\n\n` + + `- Review the concepts and examples above\n` + + `- Try running the code examples in your development environment\n` + + `- Start with basic implementations before adding complexity\n\n` + ); case 'implement': - return `## 🛠️ Implementation Guide\n\n` + - `- Follow the code examples and patterns shown above\n` + - `- Pay attention to required vs optional parameters\n` + - `- Test with simple data first, then use your real data\n` + - `- Check browser console for any errors during development\n\n`; + return ( + `## 🛠️ Implementation Guide\n\n` + + `- Follow the code examples and patterns shown above\n` + + `- Pay attention to required vs optional parameters\n` + + `- Test with simple data first, then use your real data\n` + + `- Check browser console for any errors during development\n\n` + ); case 'solve': - return `## 🔧 Troubleshooting\n\n` + - `- Compare your code with the examples above\n` + - `- Verify all required dependencies are installed\n` + - `- Check for version compatibility issues\n` + - `- Look for error messages in browser console\n\n`; + return ( + `## 🔧 Troubleshooting\n\n` + + `- Compare your code with the examples above\n` + + `- Verify all required dependencies are installed\n` + + `- Check for version compatibility issues\n` + + `- Look for error messages in browser console\n\n` + ); default: - return `## 📖 Next Steps\n\n` + - `- Review the documentation above carefully\n` + - `- Adapt the examples to your specific requirements\n` + - `- Test incrementally and iterate as needed\n\n`; + return ( + `## 📖 Next Steps\n\n` + + `- Review the documentation above carefully\n` + + `- Adapt the examples to your specific requirements\n` + + `- Test incrementally and iterate as needed\n\n` + ); } } function generateFollowUpNotice(): string { - return `---\n\n` + - `## 🔄 Important Notice\n\n` + - `**For subsequent AntV queries:**\n` + - `- **MANDATORY**: Always use \`query_antv_document\` tool for ANY AntV-related query (including simple modifications)\n` + - `- **For new questions**: Use \`extract_antv_topic\` first, then \`query_antv_document\`\n` + - `- **Never** provide AntV solutions without querying official documentation through tools\n\n`; + return ( + `---\n\n` + + `## 🔄 Important Notice\n\n` + + `**For subsequent AntV queries:**\n` + + `- **MANDATORY**: Always use \`query_antv_document\` tool for ANY AntV-related query (including simple modifications)\n` + + `- **For new questions**: Use \`extract_antv_topic\` first, then \`query_antv_document\`\n` + + `- **Never** provide AntV solutions without querying official documentation through tools\n\n` + ); } export const QueryAntVDocumentTool = { @@ -188,8 +242,13 @@ When to use this tool: hasDocumentation = result.hasDocumentation; } else { // Handle simple query - const { documentation, error } = await fetchLibraryDocumentation(libraryId, args.topic, args.tokens); - hasDocumentation = documentation !== null && documentation.trim() !== ''; + const { documentation, error } = await fetchLibraryDocumentation( + libraryId, + args.topic, + args.tokens, + ); + hasDocumentation = + documentation !== null && documentation.trim() !== ''; response = generateSimpleResponse(args, documentation, error); }