Skip to main content
Glama

suggest_mana_base

Generate optimal mana base compositions and land recommendations for Magic: The Gathering decks based on color requirements, deck size, strategy, budget, and special needs.

Instructions

Suggest optimal mana base composition and land recommendations for a deck

Input Schema

TableJSON Schema
NameRequiredDescriptionDefault
average_cmcNoAverage converted mana cost of non-land cards
budgetNoBudget constraint for land recommendationsmoderate
color_intensityNoColor intensity requirements (1-10 scale)
color_requirementsYesColor requirements (e.g., "WU", "RBG", "WUBRG")
deck_sizeNoTotal deck size
formatNoFormat to suggest lands for
special_requirementsNoSpecial mana base requirements
strategyNoDeck strategy archetypemidrange

Implementation Reference

  • Main handler function that orchestrates validation, calculations, recommendation generation, and response formatting for the suggest_mana_base tool.
    async execute(args: unknown) { try { const params = this.validateParams(args); // Calculate land count const landCount = this.calculateLandCount(params); // Calculate color distribution const colorDistribution = this.calculateColorDistribution(params, landCount); // Generate land recommendations const landRecommendations = await this.generateLandRecommendations(params, colorDistribution); // Format response const responseText = this.formatManaBaseResponse(params, landCount, colorDistribution, landRecommendations); return { content: [{ type: 'text', text: responseText }] }; } catch (error) { if (error instanceof ValidationError) { return { content: [{ type: 'text', text: `Validation error: ${error.message}` }], isError: true }; } return { content: [{ type: 'text', text: `Unexpected error: ${error instanceof Error ? error.message : 'Unknown error occurred'}` }], isError: true }; } }
  • Input schema defining the parameters for the suggest_mana_base tool, including color requirements, deck size, format, strategy, and more.
    readonly inputSchema = { type: 'object' as const, properties: { color_requirements: { type: 'string', description: 'Color requirements (e.g., "WU", "RBG", "WUBRG")' }, deck_size: { type: 'number', default: 60, minimum: 40, maximum: 250, description: 'Total deck size' }, format: { type: 'string', enum: ['standard', 'modern', 'legacy', 'vintage', 'commander', 'pioneer', 'brawl', 'standardbrawl'], description: 'Format to suggest lands for' }, strategy: { type: 'string', enum: ['aggro', 'midrange', 'control', 'combo', 'ramp'], default: 'midrange', description: 'Deck strategy archetype' }, average_cmc: { type: 'number', minimum: 0, maximum: 10, description: 'Average converted mana cost of non-land cards' }, budget: { type: 'string', enum: ['budget', 'moderate', 'expensive', 'no_limit'], default: 'moderate', description: 'Budget constraint for land recommendations' }, color_intensity: { type: 'object', properties: { W: { type: 'number', minimum: 0, maximum: 10 }, U: { type: 'number', minimum: 0, maximum: 10 }, B: { type: 'number', minimum: 0, maximum: 10 }, R: { type: 'number', minimum: 0, maximum: 10 }, G: { type: 'number', minimum: 0, maximum: 10 } }, description: 'Color intensity requirements (1-10 scale)' }, special_requirements: { type: 'array', items: { type: 'string', enum: ['enters_untapped', 'basic_types', 'nonbasic_hate_protection', 'utility_lands', 'combo_lands'] }, description: 'Special mana base requirements' } }, required: ['color_requirements'] };
  • src/server.ts:79-79 (registration)
    Registration of the SuggestManaBaseTool instance in the MCP server's tools map under the name 'suggest_mana_base'.
    this.tools.set("suggest_mana_base", new SuggestManaBaseTool(this.scryfallClient));
  • Helper function to calculate the optimal number of lands based on deck size, strategy, average CMC, and format.
    private calculateLandCount(params: any): number { const { deck_size, strategy, average_cmc } = params; // Base land count ratios by strategy const baseRatios = { aggro: 0.35, // 35% lands midrange: 0.40, // 40% lands control: 0.42, // 42% lands combo: 0.38, // 38% lands ramp: 0.45 // 45% lands }; let baseCount = Math.round(deck_size * baseRatios[strategy as keyof typeof baseRatios]); // Adjust for average CMC if (average_cmc !== undefined) { if (average_cmc > 4) { baseCount += Math.round((average_cmc - 4) * 2); } else if (average_cmc < 2.5) { baseCount -= Math.round((2.5 - average_cmc) * 2); } } // Format-specific adjustments if (params.format === 'commander') { baseCount = Math.max(36, Math.min(40, baseCount)); } else if (params.format === 'brawl') { baseCount = Math.max(22, Math.min(26, baseCount)); } return Math.max(Math.round(deck_size * 0.30), Math.min(Math.round(deck_size * 0.50), baseCount)); }
  • Helper function to format the final mana base suggestion response in a readable markdown format.
    private formatManaBaseResponse(params: any, landCount: number, colorDistribution: Record<string, number>, recommendations: any): string { let response = `**Mana Base Suggestion**\n\n`; // Overview response += `🎯 **Overview:**\n`; response += `• Colors: ${params.color_requirements}\n`; response += `• Strategy: ${params.strategy}\n`; response += `• Total Lands: ${landCount}/${params.deck_size}\n`; if (params.format) { response += `• Format: ${params.format}\n`; } response += `• Budget: ${params.budget}\n\n`; // Land count breakdown response += `📊 **Land Distribution:**\n`; for (const [color, count] of Object.entries(colorDistribution)) { if (count > 0 && color !== 'dual' && color !== 'utility') { const colorName = { W: 'White', U: 'Blue', B: 'Black', R: 'Red', G: 'Green' }[color as keyof typeof colorDistribution] || color; response += `• ${colorName}: ${count} lands\n`; } } if (colorDistribution.dual) { response += `• Dual/Fixing: ${colorDistribution.dual} lands\n`; } if (colorDistribution.utility) { response += `• Utility: ${colorDistribution.utility} lands\n`; } response += '\n'; // Basic lands if (recommendations.basics.length > 0) { response += `🏔️ **Basic Lands:**\n`; for (const basic of recommendations.basics) { response += `• ${basic.count}x ${basic.name}\n`; } response += '\n'; } // Dual lands if (recommendations.duals.length > 0) { response += `🌈 **Dual Lands:**\n`; for (const dual of recommendations.duals) { response += `• ${dual.count}x ${dual.name}\n`; response += ` 💡 *${dual.reason}*\n`; if (dual.example) { response += ` 📝 Example: ${dual.example}\n`; } } response += '\n'; } // Utility lands if (recommendations.utility.length > 0) { response += `🛠️ **Utility Lands:**\n`; for (const utility of recommendations.utility) { response += `• ${utility.count}x ${utility.name}\n`; response += ` 💡 *${utility.reason}*\n`; if (utility.example) { response += ` 📝 Example: ${utility.example}\n`; } } response += '\n'; } // Budget alternatives if (recommendations.budget_alternatives.length > 0) { response += `💰 **Budget Alternatives:**\n`; for (const alt of recommendations.budget_alternatives) { response += `• ${alt.count}x ${alt.name}\n`; response += ` 💡 *${alt.reason}*\n`; if (alt.example) { response += ` 📝 Example: ${alt.example}\n`; } } response += '\n'; } // Additional recommendations response += `💡 **Additional Tips:**\n`; if (params.strategy === 'aggro') { response += `• Prioritize lands that enter untapped\n`; response += `• Consider fewer utility lands for speed\n`; } else if (params.strategy === 'control') { response += `• Include more utility lands for late game\n`; response += `• Consider lands with card selection\n`; } else if (params.strategy === 'combo') { response += `• Focus on consistency over speed\n`; response += `• Include tutoring lands if available\n`; } if (params.color_requirements.length > 2) { response += `• Three+ color decks need excellent mana fixing\n`; response += `• Consider green ramp spells for color fixing\n`; } return response; }

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/bmurdock/scryfall-mcp'

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