Skip to main content
Glama

find_related_conversations

Discover conversations related to a specific discussion by analyzing shared files, folders, programming languages, size, or timing. Use this tool to identify similar problem-solving sessions, trace idea evolution, or find discussions about the same codebase.

Instructions

Find conversations related to a reference conversation based on shared files, folders, programming languages, similar size, or temporal proximity. Use this to discover related discussions, find conversations about the same codebase/project, identify similar problem-solving sessions, or trace the evolution of ideas across multiple conversations.

Input Schema

TableJSON Schema
NameRequiredDescriptionDefault
referenceConversationIdYesID of the conversation to find related conversations for
relationshipTypesNoTypes of relationships to consider when finding related conversations
maxResultsNoMaximum number of related conversations to return (1-50)
minScoreNoMinimum similarity score threshold (0.0-1.0)
includeScoreBreakdownNoInclude detailed breakdown of how similarity scores were calculated
outputModeNoOutput format: "json" for formatted JSON (default), "compact-json" for minified JSONjson

Implementation Reference

  • src/server.ts:266-295 (registration)
    MCP server registration of the 'find_related_conversations' tool, including input schema validation and thin wrapper handler that formats the response.
    server.tool( 'find_related_conversations', 'Find conversations related to a reference conversation based on shared files, folders, programming languages, similar size, or temporal proximity. Use this to discover related discussions, find conversations about the same codebase/project, identify similar problem-solving sessions, or trace the evolution of ideas across multiple conversations.', { referenceConversationId: z.string().min(1).describe('ID of the conversation to find related conversations for'), relationshipTypes: z.array(z.enum(['files', 'folders', 'languages', 'size', 'temporal'])).optional().default(['files']).describe('Types of relationships to consider when finding related conversations'), maxResults: z.number().min(1).max(50).optional().default(10).describe('Maximum number of related conversations to return (1-50)'), minScore: z.number().min(0).max(1).optional().default(0.1).describe('Minimum similarity score threshold (0.0-1.0)'), includeScoreBreakdown: z.boolean().optional().default(false).describe('Include detailed breakdown of how similarity scores were calculated'), outputMode: z.enum(['json', 'compact-json']).optional().default('json').describe('Output format: "json" for formatted JSON (default), "compact-json" for minified JSON') }, async (input) => { try { const result = await findRelatedConversations(input); return { content: [{ type: 'text', text: formatResponse(result, input.outputMode) }] }; } catch (error) { return { content: [{ type: 'text', text: `Error: ${error instanceof Error ? error.message : 'Unknown error occurred'}` }] }; } } );
  • Primary handler function that connects to the database, retrieves summaries for the reference conversation and all others, extracts languages if needed, and delegates relationship computation to the utility function.
    export async function findRelatedConversations( input: FindRelatedConversationsInput ): Promise<RelatedConversationsResult> { const reader = new CursorDatabaseReader(); try { await reader.connect(); // Get reference conversation summary const referenceSummary = await reader.getConversationSummary(input.referenceConversationId, { includeFirstMessage: true, includeCodeBlockCount: true, includeFileList: true, includeAttachedFolders: true, maxFirstMessageLength: 150 }); if (!referenceSummary) { throw new DatabaseError(`Reference conversation ${input.referenceConversationId} not found`); } // Get all conversation IDs for comparison const allConversationIds = await reader.getConversationIds({ format: 'both', minLength: 100 }); // Get summaries for all conversations const allSummaries = await reader.getConversationSummariesForAnalytics(allConversationIds); // Extract languages from reference conversation if needed let referenceLanguages: string[] = []; if (input.relationshipTypes.includes('languages')) { const conversationsWithCode = await reader.getConversationsWithCodeBlocks([input.referenceConversationId]); if (conversationsWithCode.length > 0) { referenceLanguages = extractLanguagesFromCodeBlocks(conversationsWithCode[0].codeBlocks); } } // Find related conversations const related = findRelatedConversationsUtil( referenceSummary, allSummaries, allConversationIds, { relationshipTypes: input.relationshipTypes, maxResults: input.maxResults, minScore: input.minScore, includeScoreBreakdown: input.includeScoreBreakdown } ); return { reference: { composerId: referenceSummary.composerId, files: referenceSummary.relevantFiles, folders: referenceSummary.attachedFolders, languages: referenceLanguages, messageCount: referenceSummary.messageCount, size: referenceSummary.conversationSize }, related }; } catch (error) { throw new DatabaseError(`Failed to find related conversations: ${error instanceof Error ? error.message : 'Unknown error'}`); } finally { reader.close(); } }
  • Zod schema definition for input validation of the findRelatedConversations tool (used for TypeScript typing).
    export const findRelatedConversationsSchema = z.object({ referenceConversationId: z.string().min(1), relationshipTypes: z.array(z.enum(['files', 'folders', 'languages', 'size', 'temporal'])).optional().default(['files']), maxResults: z.number().min(1).max(50).optional().default(10), minScore: z.number().min(0).max(1).optional().default(0.1), includeScoreBreakdown: z.boolean().optional().default(false) });
  • Core utility function (aliased as findRelatedConversationsUtil) that iterates over all conversation summaries, computes relationship scores (files, folders, etc.), and returns top related conversations sorted by composite score.
    export function findRelatedConversations( referenceSummary: ConversationSummary, allSummaries: ConversationSummary[], conversationIds: string[], options: RelationshipOptions ): RelatedConversation[] { const related: RelatedConversation[] = []; // Get reference conversation index for temporal calculations const referenceIndex = conversationIds.indexOf(referenceSummary.composerId); for (const summary of allSummaries) { // Skip the reference conversation itself if (summary.composerId === referenceSummary.composerId) { continue; } const relationships = calculateRelationships( referenceSummary, summary, conversationIds, referenceIndex, options.relationshipTypes ); const score = calculateCompositeScore(relationships, options.relationshipTypes); if (score >= options.minScore) { related.push({ composerId: summary.composerId, relationshipScore: score, relationships, summary: summary.firstMessage || 'No preview available', scoreBreakdown: options.includeScoreBreakdown ? calculateScoreBreakdown(relationships, options.relationshipTypes) : undefined }); } } // Sort by score and limit results return related .sort((a, b) => b.relationshipScore - a.relationshipScore) .slice(0, options.maxResults); }

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/vltansky/cursor-conversations-mcp'

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