get_clustered_expression
Retrieve clustered gene expression data from the GTEx Portal for visualizing patterns across human tissues using GENCODE gene IDs.
Instructions
Get clustered gene expression data for visualization
Input Schema
TableJSON Schema
| Name | Required | Description | Default |
|---|---|---|---|
| datasetId | No | GTEx dataset ID (default: gtex_v8) | gtex_v8 |
| gencodeIds | Yes | Array of GENCODE gene IDs |
Implementation Reference
- Main handler function implementing get_clustered_expression tool logic. Fetches median gene expression data using GTExApiClient, organizes by gene and tissue, computes statistics, and formats output suitable for clustering visualization.async getClusteredExpression(args: any) { if (!args.geneIds || !Array.isArray(args.geneIds) || args.geneIds.length === 0) { throw new Error('geneIds parameter is required and must be a non-empty array of gene IDs'); } if (args.geneIds.length > 20) { return { content: [{ type: "text", text: "Maximum 20 genes can be processed for clustering analysis." }] }; } // Get median expression for all genes const result = await this.apiClient.getMedianGeneExpression( args.geneIds, args.datasetId || 'gtex_v8' ); if (result.error) { return { content: [{ type: "text", text: `Error retrieving clustered expression data: ${result.error}` }], isError: true }; } const expressions = result.data || []; if (expressions.length === 0) { return { content: [{ type: "text", text: "No expression data found for clustering analysis." }] }; } // Organize data for clustering visualization const geneGroups: { [key: string]: any[] } = {}; expressions.forEach(expr => { const key = `${expr.geneSymbol} (${expr.gencodeId})`; if (!geneGroups[key]) { geneGroups[key] = []; } geneGroups[key].push(expr); }); let output = `**Clustered Gene Expression Analysis**\n`; output += `Genes: ${Object.keys(geneGroups).length}\n`; output += `Dataset: ${expressions[0]?.datasetId}\n`; output += `Format: Median expression values for clustering\n\n`; // Create expression matrix summary output += `**Expression Matrix Summary:**\n`; Object.entries(geneGroups).forEach(([geneKey, geneExpressions]) => { const sortedExpr = geneExpressions.sort((a, b) => b.median - a.median); const stats = { max: Math.max(...sortedExpr.map(e => e.median)), min: Math.min(...sortedExpr.map(e => e.median)), tissues: sortedExpr.length }; output += `• **${geneKey}**:\n`; output += ` - Tissues: ${stats.tissues}\n`; output += ` - Range: ${stats.min.toFixed(3)} - ${stats.max.toFixed(3)} TPM\n`; output += ` - Top tissue: ${this.getTissueDisplayName(sortedExpr[0].tissueSiteDetailId)} (${sortedExpr[0].median.toFixed(3)})\n`; }); output += `\n**Clustering Notes:**\n`; output += `- Expression values are median TPM across samples\n`; output += `- Data suitable for hierarchical clustering or PCA analysis\n`; output += `- Consider log-transformation for clustering algorithms\n`; return { content: [{ type: "text", text: output }] }; }
- src/index.ts:153-170 (schema)Tool schema definition including input schema for validating parameters: required array of gencodeIds and optional datasetId.name: "get_clustered_expression", description: "Get clustered gene expression data for visualization", inputSchema: { type: "object", properties: { gencodeIds: { type: "array", items: { type: "string" }, description: "Array of GENCODE gene IDs" }, datasetId: { type: "string", description: "GTEx dataset ID (default: gtex_v8)", default: "gtex_v8" } }, required: ["gencodeIds"] }
- src/index.ts:651-656 (registration)Registration and dispatch logic in the main CallToolRequest handler that maps tool name to the expressionHandlers.getClusteredExpression method, adapting input arguments.if (name === "get_clustered_expression") { return await expressionHandlers.getClusteredExpression({ gencodeIds: args?.gencodeIds || [], datasetId: args?.datasetId }); }