Skip to main content
Glama
jakedx6
by jakedx6

search_documents

Search project documents by content with filtering by project, document type, and result limits to find specific information efficiently.

Instructions

Search documents by content with advanced filtering and ranking

Input Schema

TableJSON Schema
NameRequiredDescriptionDefault
queryYesSearch query to find in document titles and content
project_idNoLimit search to specific project
document_typesNoFilter by document types
limitNoMaximum number of results to return
include_contentNoWhether to include full document content in results

Implementation Reference

  • Primary execution handler for the search_documents tool. Parses input arguments using Zod, queries Supabase for matching documents based on search term and filters, ranks results by relevance (title match, content similarity, recency), and returns paginated results with metadata.
    export const searchDocuments = requireAuth(async (args: any) => { const { query, project_id, document_types, limit, include_content } = SearchDocumentsSchema.parse(args) logger.info('Searching documents', { query, project_id, document_types, limit }) // Get all matching documents const allDocuments = await supabaseService.getDocuments( { project_id, search: query }, { limit: limit * 2 }, // Get more for better ranking { field: 'updated_at', order: 'desc' } ) // Filter by document types if specified let filteredDocuments = allDocuments if (document_types && document_types.length > 0) { filteredDocuments = allDocuments.filter(doc => document_types.includes(doc.document_type)) } // Rank results by relevance const rankedResults = rankSearchResults(filteredDocuments, query, include_content) // Limit results const finalResults = rankedResults.slice(0, limit) return { results: finalResults, total_found: rankedResults.length, search_metadata: { query, filters: { project_id, document_types }, ranking_factors: ['title_match', 'content_relevance', 'document_freshness', 'ai_readiness'] } } })
  • Zod schema for input validation used within the search_documents handler to parse and validate tool arguments.
    const SearchDocumentsSchema = z.object({ query: z.string().min(1), project_id: z.string().uuid().optional(), document_types: z.array(z.string()).optional(), limit: z.number().int().positive().max(50).default(20), include_content: z.boolean().default(false) })
  • Registration object mapping tool names to their handler functions for all document-related tools, including 'search_documents' mapped to the searchDocuments handler.
    export const documentHandlers = { list_documents: listDocuments, create_document: createDocument, get_document: getDocument, update_document: updateDocument, search_documents: searchDocuments, get_document_context: getDocumentContext, add_document_collaborator: addDocumentCollaborator, analyze_document_content: analyzeDocumentContent, get_document_collaboration: getDocumentCollaboration, generate_document_template: generateDocumentTemplate, bulk_document_operations: bulkDocumentOperations
  • src/index.ts:143-155 (registration)
    Central registration in the MCP server where documentHandlers (including search_documents) is spread into the allHandlers object used to dispatch tool calls: this.allHandlers[name](args).
    this.allHandlers = { ...projectHandlers, ...taskHandlers, ...documentHandlers, ...conversationHandlers, ...contextAggregationHandlers, ...workflowAutomationHandlers, ...intelligentSearchHandlers, ...analyticsInsightsHandlers, ...initiativeHandlers, ...promptToProjectTools.reduce((acc, tool) => ({ ...acc, [tool.name]: tool.handler }), {}), ...debugHandlers, }
  • Key helper function used by the handler to compute relevance scores for search results based on title matching, content keyword frequency, recency, and document type, then sorts and returns ranked list.
    function rankSearchResults(documents: any[], query: string, includeContent: boolean): any[] { const queryLower = query.toLowerCase() return documents .map(doc => { let score = 0 // Title match (highest weight) if (doc.title.toLowerCase().includes(queryLower)) { score += 50 if (doc.title.toLowerCase().startsWith(queryLower)) score += 25 } // Content relevance const contentLower = doc.content.toLowerCase() const queryMatches = (contentLower.match(new RegExp(queryLower, 'g')) || []).length score += Math.min(30, queryMatches * 5) // Document freshness const daysSinceUpdate = (Date.now() - new Date(doc.updated_at).getTime()) / (1000 * 60 * 60 * 24) if (daysSinceUpdate < 7) score += 10 else if (daysSinceUpdate < 30) score += 5 // AI readiness // Removed metadata check as it doesn't exist in the database schema // Document type relevance if (['readme', 'api_docs'].includes(doc.document_type)) score += 10 return { ...doc, content: includeContent ? doc.content : undefined, search_score: score, query_matches: queryMatches } }) .sort((a, b) => b.search_score - a.search_score) }

Latest Blog Posts

MCP directory API

We provide all the information about MCP servers via our MCP API.

curl -X GET 'https://glama.ai/api/mcp/v1/servers/jakedx6/helios9-MCP-Server'

If you have feedback or need assistance with the MCP directory API, please join our Discord server