Model Context Protocol (MCP)

MCP بر روی HTTP: پل ارتباطی بین مدل‌های هوش مصنوعی و سیستم‌های محلی با یک پروتکل استاندارد

پروتکل زمینه مدل (MCP) به سرعت به عنوان «USB-C برای هوش مصنوعی» ظهور کرده و راهی استاندارد برای اتصال مدل‌های زبانی بزرگ (LLM) به منابع داده و ابزارهای خارجی فراهم می‌کند. در حالی که پیاده‌سازی‌های اولیه اغلب برای سادگی به ورودی/خروجی استاندارد محلی (stdio) تکیه می‌کردند، گذار به حمل‌ونقل HTTP یک تکامل حیاتی برای محیط‌های تولید، سیستم‌های توزیع‌شده و معماری‌های چندپاجه (multi-tenant) است.

این راهنما مکانیک‌های MCP بر روی HTTP را بررسی می‌کند و ساختار JSON-RPC زیربنایی، پیامدهای امنیتی و نمونه‌های کد برای پیاده‌سازی هر دو سمت کلاینت و سرور را تشریح می‌نماید.

چرا باید فراتر از Stdio برویم؟

حمل‌ونقل استاندارد stdio برای توسعه محلی و ابزارهای CLI تک‌کاربر ایده‌آل است. با این حال، در سناریوهای مقیاس‌پذیر با محدودیت‌های قابل توجهی مواجه است:

  • عزلت (Isolation): Stdio نیاز دارد که مدل و ابزار روی یک ماشین و درخت فرآیند واحد اجرا شوند.
  • مقیاس‌پذیری (Scalability): به صورت بومی از تعادل بار (load balancing) یا مقیاس‌بندی افقی پشتیبانی نمی‌کند.
  • امنیت (Security): ایجاد مستقیم فرآیند (process spawning) ایمنی کمتری نسبت به سرویس‌های شبکه‌ای با لایه‌های احراز هویت مناسب دارد.

HTTP (به ویژه HTTP/1.1 یا HTTP/2) ارتباط بدون حالت (stateless)، پشتیبانی قوی از میانی‌افزارها (middleware) و دسترسی جهانی را ارائه می‌دهد که آن را به انتخاب طبیعی برای آشکار کردن سرورهای MCP به نمونه‌های LLM از راه دور تبدیل می‌کند.

معماری: JSON-RPC بر روی HTTP

MCP فقط یک لایه حمل‌ونقل نیست؛ بلکه یک پروتکل معنایی (semantic) است. هنگام استقرار بر روی HTTP، MCP از JSON-RPC 2.0 به عنوان فرمت پیام استفاده می‌کند. هر تعامل از یک شیء JSON شامل یک روش (method)، پارامترها و یک شناسه (ID) تشکیل شده است.

روش‌های کلیدی

قابلیت‌های اصلی که توسط یک سرور MCP ارائه می‌شود عبارتند از:

  • tools/list: کشف ابزارهای در دسترس.
  • tools/call: فراخوانی یک ابزار خاص با آرگومان‌ها.
  • resources/list: دسترسی به منابع داده در دسترس.

نمونه‌های پیاده‌سازی

۱. مدیریت سمت سرور (نمونه Node.js/Express)

در زیر یک نمونه حداقلی از نحوه مدیریت یک درخواست HTTP POST ورودی توسط یک سرور MCP آورده شده است. توجه داشته باشید که MCP بر روی HTTP معمولاً از یک نقطه پایانی واحد (مثلاً /mcp) استفاده می‌کند که بر اساس فیلد method در بدنه JSON مسیریابی می‌شود.

const express = require('express');
const app = express();
app.use(express.json());

app.post('/mcp', (req, res) => {
    const { method, params, id } = req.body;

    // مسیریابی پایه بر اساس روش‌های MCP
    switch (method) {
        case 'tools/list':
            res.json({
                jsonrpc: '2.0',
                id,
                result: {
                    tools: [
                        {
                            name: 'get_weather',
                            description: 'Get current weather data',
                            inputSchema: {
                                type: 'object',
                                properties: {
                                    city: { type: 'string' }
                                },
                                required: ['city']
                            }
                        }
                    ]
                }
            });
            break;
            
        case 'tools/call':
            // منطق ابزار خود را اینجا پیاده‌سازی کنید
            const cityName = params.arguments.city;
            res.json({
                jsonrpc: '2.0',
                id,
                result: {
                    content: [{ type: 'text', text: `Sunny in ${cityName}, 75°F` }]
                }
            });
            break;

        default:
            res.json({
                jsonrpc: '2.0',
                id,
                error: { code: -32601, message: 'Method not found' }
            });
    }
});

app.listen(3000, () => console.log('MCP Server running on port 3000'));

۲. درخواست سمت کلاینت

اپلیکیشن LLM (یا میانی‌افزار آن) به عنوان کلاینت MCP عمل می‌کند. این کلاینت یک درخواست POST با بار JSON-RPC ارسال می‌کند. مدیریت صحیح زمان‌های انتظار (timeouts) و پاسخ‌های ناهمگام (async) حیاتی است، زیرا فراخوانی ابزارها می‌تواند طولانی باشد.

const fetch = require('node-fetch');

async function callMCPTool(toolName, args) {
    const response = await fetch('http://localhost:3000/mcp', {
        method: 'POST',
        headers: { 'Content-Type': 'application/json' },
        body: JSON.stringify({
            jsonrpc: '2.0',
            method: 'tools/call',
            params: {
                name: toolName,
                arguments: args
            },
            id: '12345'
        })
    });

    const data = await response.json();
    if (data.error) {
        throw new Error(data.error.message);
    }
    return data.result;
}

// استفاده
callMCPTool('get_weather', { city: 'New York' }).then(console.log);

ملاحظات امنیتی

آشکار کردن ابزارهای MCP بر روی HTTP سطح‌های حمله‌ای را معرفی می‌کند که در محیط‌های stdio محلی وجود ندارند. توسعه‌دهندگان باید کنترل‌های امنیتی سخت‌گیرانه را پیاده‌سازی کنند:

  1. احراز هویت (Authentication): همیشه کلیدهای API، توکن‌های OAuth 2.0 یا mTLS را الزامی کنید. هرگز سرور MCP را بدون احراز هویت در اینترنت عمومی آشکار نکنید.
  2. مجوزدهی (Authorization): اطمینان حاصل کنید که زمینه LLM امکان ارتقای امتیاز (privilege escalation) را فراهم نمی‌کند. سرور باید تأیید کند که کاربر درخواست‌کننده مجوز فراخوانی ابزارهای خاص را دارد.
  3. اعتبارسنجی ورودی (Input Validation): تمام آرگومان‌های ارسالی به ابزارها را به دقت اعتبارسنجی کنید. از آنجا که LLM ورودی را تولید می‌کند، ممکن است JSON نادرست یا مخرب تولید کند. از اعتبارسنجی اسکیمای (schema) (مثلاً Zod، Joi) در سمت سرور استفاده کنید.
  4. محدودسازی نرخ (Rate Limiting): محدودیت‌های نرخ را پیاده‌سازی کنید تا از سوءاستفاده یا افزایش هزینه‌های مرتبط با فراخوانی‌های API خارجی انجام شده توسط ابزارها جلوگیری شود.

بهترین روش‌ها برای محیط تولید

  • استفاده از HTTPS: همیشه ترافیک در حال انتقال را رمزگذاری کنید.
  • بدون حالت (Statelessness): سرور MCP خود را جایی که امکان دارد بدون حالت طراحی کنید تا مقیاس‌بندی افقی آسان باشد.
  • لاگ‌نویسی (Logging): تمام فراخوانی‌های ابزار را برای اهداف ممیزی ثبت کنید. ردیابی کنید که کدام نمونه LLM با چه پارامترهایی کدام ابزار را فراخوانی کرده است.
  • نسخه‌بندی (Versioning): نسخه‌بندی را در URL یا هدرها (مثلاً /mcp/v1) گنجانید تا تغییرات شکست‌دهنده (breaking changes) در اسکیمای ابزارها مدیریت شوند.

نتیجه‌گیری

گذار MCP از stdio به HTTP یک گام ضروری برای ساخت اپلیکیشن‌های هوش مصنوعی محکم و مقیاس‌پذیر است. با بهره‌گیری از فرمت استاندارد JSON-RPC 2.0 بر روی نقاط پایانی HTTP امن، توسعه‌دهندگان می‌توانند اکوسیستم‌های ابزار ماژولار و قابل استفاده مجدد ایجاد کنند که می‌توانند در میان ارائه‌دهندگان مختلف LLM و محیط‌های استقرار مختلف به اشتراک گذاشته شوند. با بالغ شدن اکوسیستم MCP، انتظار می‌رود ویژگی‌های غنی‌تری مانند پاسخ‌های پخش زنده (streaming) و پیوند پیچیده منابع به عنوان استاندارد بر روی حمل‌ونقل HTTP دیده شوند.

Share: