estimate_operation_cost
Calculate computational costs for Clarity smart contract operations using SIP-012 cost functions to optimize contract performance and resource planning.
Instructions
Estimate the computational cost of specific Clarity operations based on SIP-012 cost functions. Useful for planning contract optimization.
Input Schema
TableJSON Schema
| Name | Required | Description | Default |
|---|---|---|---|
| dataSize | Yes | Size of data being processed (e.g., list length, string length) | |
| iterations | No | Number of iterations for batch operations | |
| operation | Yes | Type of operation to estimate |
Implementation Reference
- The complete tool definition including name, description, parameters schema reference, and execute handler function that implements the core logic for estimating operation costs using SIP-012 cost functions.export const estimateOperationCostTool: Tool<undefined, typeof CostEstimationScheme> = { name: "estimate_operation_cost", description: "Estimate the computational cost of specific Clarity operations based on SIP-012 cost functions. Useful for planning contract optimization.", parameters: CostEstimationScheme, execute: async (args, context) => { try { await recordTelemetry({ action: "estimate_operation_cost" }, context); const costs = calculateOperationCost(args.operation, args.dataSize, args.iterations || 1); const blockUtilization = calculateBlockUtilization(costs); return `# Operation Cost Estimation ## Operation Details - **Type**: ${args.operation} - **Data Size**: ${args.dataSize.toLocaleString()} - **Iterations**: ${args.iterations || 1} ## Estimated Costs (SIP-012) ### Resource Consumption \`\`\` Runtime Cost: ${costs.runtime.toLocaleString()} units Read Count: ${costs.readCount} operations Write Count: ${costs.writeCount} operations Read Length: ${costs.readLength.toLocaleString()} bytes Write Length: ${costs.writeLength.toLocaleString()} bytes \`\`\` ### Block Utilization - **Runtime**: ${blockUtilization.runtime.toFixed(4)}% (${costs.runtime.toLocaleString()}/${SIP012_COSTS.limits.runtime.toLocaleString()}) - **Read Count**: ${blockUtilization.readCount.toFixed(4)}% (${costs.readCount}/${SIP012_COSTS.limits.readCount}) - **Write Count**: ${blockUtilization.writeCount.toFixed(4)}% (${costs.writeCount}/${SIP012_COSTS.limits.writeCount}) - **Read Length**: ${blockUtilization.readLength.toFixed(4)}% (${costs.readLength.toLocaleString()}/${SIP012_COSTS.limits.readLength.toLocaleString()}) - **Write Length**: ${blockUtilization.writeLength.toFixed(4)}% (${costs.writeLength.toLocaleString()}/${SIP012_COSTS.limits.writeLength.toLocaleString()}) ### Performance Analysis ${blockUtilization.runtime > 50 ? '⚠️ **High Runtime Usage**: Consider optimization' : '✅ **Runtime**: Within reasonable bounds'} ${blockUtilization.readCount > 50 ? '⚠️ **High Read Count**: Consider batching or caching' : '✅ **Read Count**: Efficient database usage'} ${blockUtilization.writeCount > 50 ? '⚠️ **High Write Count**: Consider data structure optimization' : '✅ **Write Count**: Efficient storage usage'} ## Optimization Suggestions ${getOptimizationSuggestions(args.operation, costs, blockUtilization)} ## Batch Operation Analysis ${args.iterations && args.iterations > 1 ? ` **Single Operation Cost**: ${Math.round(costs.runtime / args.iterations).toLocaleString()} runtime units **Batch Efficiency**: ${(args.iterations > 10 ? 'High' : args.iterations > 5 ? 'Medium' : 'Low')} efficiency gain **Recommended Batch Size**: ${getRecommendedBatchSize(args.operation, costs)} ` : 'Single operation - consider batching for multiple operations'} ## SIP-012 Improvements ✅ **Enhanced Limits**: 2x more database operations available ✅ **Better Costing**: More accurate runtime cost estimation ✅ **Dynamic Storage**: List storage based on actual size ✅ **Improved Throughput**: Better block space utilization`; } catch (error) { return `❌ Failed to estimate operation cost: ${error}`; } }, };
- Zod schema defining the input parameters for the estimate_operation_cost tool: operation type, dataSize, and optional iterations.const CostEstimationScheme = z.object({ operation: z.enum([ "map-read", "map-write", "list-append", "list-filter", "string-concat", "arithmetic", "contract-call", "token-transfer", "batch-operation" ]).describe("Type of operation to estimate"), dataSize: z.number().describe("Size of data being processed (e.g., list length, string length)"), iterations: z.number().optional().describe("Number of iterations for batch operations"), });
- src/tools/index.ts:68-68 (registration)Registration of the estimateOperationCostTool in the FastMCP server.server.addTool(estimateOperationCostTool);
- SIP-012 cost constants and block limits used throughout the cost estimation logic.const SIP012_COSTS = { // Runtime costs (in units) runtime: { mapGet: 64, mapSet: 64, mapDelete: 64, listAppend: 32, listFilter: 64, listMap: 64, listFold: 64, stringConcat: 32, arithmetic: 1, contractCall: 1000, tokenTransfer: 50000, }, // Storage costs (per byte) storage: { read: 1, write: 10, }, // Block limits (post SIP-012) limits: { runtime: 5000000000, readCount: 15000, readLength: 100000000, writeCount: 15000, writeLength: 15000000, } };
- Core helper function that calculates detailed costs for different operations based on SIP-012 metrics, called directly from the tool handler.function calculateOperationCost(operation: string, dataSize: number, iterations: number) { const baseCosts = SIP012_COSTS.runtime; let costs = { runtime: 0, readCount: 0, writeCount: 0, readLength: 0, writeLength: 0 }; switch (operation) { case "map-read": costs.runtime = baseCosts.mapGet * iterations; costs.readCount = iterations; costs.readLength = dataSize * 40 * iterations; break; case "map-write": costs.runtime = baseCosts.mapSet * iterations; costs.writeCount = iterations; costs.writeLength = dataSize * 40 * iterations; break; case "list-append": costs.runtime = baseCosts.listAppend * iterations * Math.log2(dataSize); costs.writeCount = iterations; costs.writeLength = dataSize * 8 * iterations; break; case "token-transfer": costs.runtime = baseCosts.tokenTransfer * iterations; costs.readCount = iterations; costs.writeCount = iterations * 2; costs.readLength = 40 * iterations; costs.writeLength = 80 * iterations; break; case "batch-operation": const batchEfficiency = Math.min(0.8, Math.log10(iterations) / 2); costs.runtime = baseCosts.mapSet * iterations * (1 - batchEfficiency); costs.readCount = Math.ceil(iterations / 2); costs.writeCount = iterations; costs.writeLength = dataSize * iterations; break; default: costs.runtime = 1000 * iterations; } return costs; }