يوفر هذا الفصل دليلاً شاملاً لتنفيذ بث آمن وقابل للتوسع وفي الوقت الحقيقي باستخدام بروتوكول سياق النموذج (MCP) عبر HTTPS. يغطي الدوافع وراء البث، وآليات النقل المتاحة، كيفية تنفيذ HTTP قابل للبث في MCP، أفضل ممارسات الأمان، الانتقال من SSE، وإرشادات عملية لبناء تطبيقات MCP للبث الخاصة بك.
يستعرض هذا القسم آليات النقل المختلفة المتاحة في MCP ودورها في تمكين قدرات البث للتواصل في الوقت الحقيقي بين العملاء والخوادم.
آلية النقل تحدد كيفية تبادل البيانات بين العميل والخادم. يدعم MCP عدة أنواع من النقل لتناسب بيئات ومتطلبات مختلفة:
- stdio: الإدخال/الإخراج القياسي، مناسب للأدوات المحلية وأدوات سطر الأوامر. بسيط لكنه غير مناسب للويب أو السحابة.
- SSE (Server-Sent Events): يسمح للخوادم بدفع تحديثات في الوقت الحقيقي إلى العملاء عبر HTTP. جيد لواجهات الويب، لكنه محدود من حيث التوسع والمرونة.
- Streamable HTTP: نقل بث حديث قائم على HTTP، يدعم الإشعارات وتوسع أفضل. يُنصح به لمعظم سيناريوهات الإنتاج والسحابة.
اطلع على جدول المقارنة أدناه لفهم الفروقات بين آليات النقل هذه:
| النقل | التحديثات في الوقت الحقيقي | البث | قابلية التوسع | حالة الاستخدام |
|---|---|---|---|---|
| stdio | لا | لا | منخفضة | أدوات CLI محلية |
| SSE | نعم | نعم | متوسطة | الويب، التحديثات الفورية |
| Streamable HTTP | نعم | نعم | عالية | السحابة، متعدد العملاء |
نصيحة: اختيار آلية النقل المناسبة يؤثر على الأداء، وقابلية التوسع، وتجربة المستخدم. يُنصح باستخدام Streamable HTTP للتطبيقات الحديثة والقابلة للتوسع والمهيأة للسحابة.
لاحظ آليات النقل stdio و SSE التي تم عرضها في الفصول السابقة وكيف أن Streamable HTTP هو النقل الذي يغطيه هذا الفصل.
فهم المفاهيم الأساسية والدوافع وراء البث ضروري لتنفيذ أنظمة تواصل فعالة في الوقت الحقيقي.
البث هو تقنية في برمجة الشبكات تسمح بإرسال واستقبال البيانات على شكل أجزاء صغيرة يمكن إدارتها أو كسلسلة من الأحداث، بدلاً من الانتظار حتى يكون الرد كاملاً. هذا مفيد بشكل خاص لـ:
- الملفات أو مجموعات البيانات الكبيرة.
- التحديثات في الوقت الحقيقي (مثل الدردشة، أشرطة التقدم).
- العمليات الحسابية طويلة الأمد حيث تريد إبقاء المستخدم على اطلاع.
إليك ما تحتاج لمعرفته على مستوى عالٍ عن البث:
- يتم تسليم البيانات تدريجياً، وليس دفعة واحدة.
- يمكن للعميل معالجة البيانات فور وصولها.
- يقلل من زمن الاستجابة الظاهر ويحسن تجربة المستخدم.
الأسباب لاستخدام البث هي:
- يحصل المستخدمون على ردود فعل فورية، وليس فقط في النهاية.
- يتيح تطبيقات في الوقت الحقيقي وواجهات مستخدم تفاعلية.
- استخدام أكثر كفاءة لموارد الشبكة والحوسبة.
إليك مثال بسيط لكيفية تنفيذ البث:
الخادم (Python، باستخدام FastAPI و StreamingResponse):
from fastapi import FastAPI
from fastapi.responses import StreamingResponse
import time
app = FastAPI()
async def event_stream():
for i in range(1, 6):
yield f"data: Message {i}\n\n"
time.sleep(1)
@app.get("/stream")
def stream():
return StreamingResponse(event_stream(), media_type="text/event-stream")العميل (Python، باستخدام requests):
import requests
with requests.get("http://localhost:8000/stream", stream=True) as r:
for line in r.iter_lines():
if line:
print(line.decode())يوضح هذا المثال خادمًا يرسل سلسلة من الرسائل إلى العميل بمجرد توفرها، بدلاً من الانتظار حتى تكون كل الرسائل جاهزة.
كيف يعمل:
- الخادم يولد كل رسالة بمجرد جاهزيتها.
- العميل يستقبل ويطبع كل جزء عند وصوله.
المتطلبات:
- يجب أن يستخدم الخادم استجابة بث (مثل
StreamingResponseفي FastAPI). - يجب أن يعالج العميل الاستجابة كبث (
stream=Trueفي requests). - نوع المحتوى عادةً
text/event-streamأوapplication/octet-stream.
الخادم (Java، باستخدام Spring Boot و Server-Sent Events):
@RestController
public class CalculatorController {
@GetMapping(value = "/calculate", produces = MediaType.TEXT_EVENT_STREAM_VALUE)
public Flux<ServerSentEvent<String>> calculate(@RequestParam double a,
@RequestParam double b,
@RequestParam String op) {
double result;
switch (op) {
case "add": result = a + b; break;
case "sub": result = a - b; break;
case "mul": result = a * b; break;
case "div": result = b != 0 ? a / b : Double.NaN; break;
default: result = Double.NaN;
}
return Flux.<ServerSentEvent<String>>just(
ServerSentEvent.<String>builder()
.event("info")
.data("Calculating: " + a + " " + op + " " + b)
.build(),
ServerSentEvent.<String>builder()
.event("result")
.data(String.valueOf(result))
.build()
)
.delayElements(Duration.ofSeconds(1));
}
}العميل (Java، باستخدام Spring WebFlux WebClient):
@SpringBootApplication
public class CalculatorClientApplication implements CommandLineRunner {
private final WebClient client = WebClient.builder()
.baseUrl("http://localhost:8080")
.build();
@Override
public void run(String... args) {
client.get()
.uri(uriBuilder -> uriBuilder
.path("/calculate")
.queryParam("a", 7)
.queryParam("b", 5)
.queryParam("op", "mul")
.build())
.accept(MediaType.TEXT_EVENT_STREAM)
.retrieve()
.bodyToFlux(String.class)
.doOnNext(System.out::println)
.blockLast();
}
}ملاحظات تنفيذ Java:
- يستخدم تكديس Spring Boot التفاعلي مع
Fluxللبث ServerSentEventيوفر بث أحداث منظم مع أنواع أحداثWebClientمعbodyToFlux()يمكّن استهلاك البث التفاعليdelayElements()يحاكي وقت المعالجة بين الأحداث- يمكن أن تحتوي الأحداث على أنواع (
info,result) لتحسين معالجة العميل
يمكن توضيح الفروقات بين كيفية عمل البث "الكلاسيكي" وكيفية عمله في MCP كما يلي:
| الميزة | البث الكلاسيكي عبر HTTP | بث MCP (الإشعارات) |
|---|---|---|
| الاستجابة الرئيسية | مقسمة إلى أجزاء | واحدة، في النهاية |
| تحديثات التقدم | تُرسل كقطع بيانات | تُرسل كإشعارات |
| متطلبات العميل | يجب معالجة البث | يجب تنفيذ معالج رسائل |
| حالة الاستخدام | ملفات كبيرة، تدفقات رموز AI | التقدم، السجلات، ردود فعل فورية |
إضافة إلى ذلك، هناك بعض الفروقات الرئيسية:
-
نمط الاتصال:
- البث الكلاسيكي عبر HTTP: يستخدم ترميز نقل مقسم بسيط لإرسال البيانات على شكل أجزاء
- بث MCP: يستخدم نظام إشعارات منظم مع بروتوكول JSON-RPC
-
صيغة الرسالة:
- HTTP الكلاسيكي: قطع نصية عادية مع فواصل أسطر
- MCP: كائنات LoggingMessageNotification منظمة مع بيانات وصفية
-
تنفيذ العميل:
- HTTP الكلاسيكي: عميل بسيط يعالج استجابات البث
- MCP: عميل أكثر تطوراً مع معالج رسائل لمعالجة أنواع مختلفة من الرسائل
-
تحديثات التقدم:
- HTTP الكلاسيكي: التقدم جزء من تدفق الاستجابة الرئيسي
- MCP: التقدم يُرسل عبر رسائل إشعار منفصلة بينما تأتي الاستجابة الرئيسية في النهاية
هناك بعض التوصيات عند الاختيار بين تنفيذ البث الكلاسيكي (كنقطة نهاية عرضناها أعلاه باستخدام /stream) مقابل اختيار البث عبر MCP.
- للحاجات البسيطة للبث: البث الكلاسيكي عبر HTTP أبسط في التنفيذ وكافٍ للاحتياجات الأساسية.
- للتطبيقات المعقدة والتفاعلية: بث MCP يوفر نهجًا أكثر تنظيماً مع بيانات وصفية أغنى وفصل بين الإشعارات والنتائج النهائية.
- لتطبيقات الذكاء الاصطناعي: نظام الإشعارات في MCP مفيد بشكل خاص للمهام الطويلة الأمد حيث تريد إبقاء المستخدمين على اطلاع بالتقدم.
حسنًا، لقد رأيت بعض التوصيات والمقارنات حتى الآن حول الفرق بين البث الكلاسيكي والبث في MCP. دعنا ندخل في التفاصيل حول كيفية الاستفادة من البث في MCP.
فهم كيفية عمل البث ضمن إطار MCP ضروري لبناء تطبيقات تفاعلية توفر ردود فعل في الوقت الحقيقي للمستخدمين أثناء العمليات طويلة الأمد.
في MCP، البث لا يعني إرسال الاستجابة الرئيسية على شكل أجزاء، بل إرسال إشعارات إلى العميل أثناء معالجة الأداة للطلب. يمكن أن تشمل هذه الإشعارات تحديثات التقدم، السجلات، أو أحداث أخرى.
النتيجة الرئيسية لا تزال تُرسل كرد واحد. ومع ذلك، يمكن إرسال الإشعارات كرسائل منفصلة أثناء المعالجة لتحديث العميل في الوقت الحقيقي. يجب أن يكون العميل قادرًا على التعامل مع هذه الإشعارات وعرضها.
قلنا "إشعار"، ماذا يعني ذلك في سياق MCP؟
الإشعار هو رسالة تُرسل من الخادم إلى العميل لإبلاغه بالتقدم، الحالة، أو أحداث أخرى أثناء عملية طويلة الأمد. الإشعارات تحسن الشفافية وتجربة المستخدم.
على سبيل المثال، من المفترض أن يرسل العميل إشعارًا بمجرد إتمام المصافحة الأولية مع الخادم.
يبدو الإشعار كرسالة JSON كما يلي:
{
jsonrpc: "2.0";
method: string;
params?: {
[key: string]: unknown;
};
}تنتمي الإشعارات إلى موضوع في MCP يُشار إليه باسم "Logging".
لجعل التسجيل يعمل، يحتاج الخادم إلى تمكينه كميزة/قدرة كما يلي:
{
"capabilities": {
"logging": {}
}
}Note
اعتمادًا على SDK المستخدم، قد يكون التسجيل مفعلاً افتراضيًا، أو قد تحتاج إلى تمكينه صراحة في تكوين الخادم.
هناك أنواع مختلفة من الإشعارات:
| المستوى | الوصف | مثال على الاستخدام |
|---|---|---|
| debug | معلومات تفصيلية للتصحيح | نقاط دخول/خروج الدوال |
| info | رسائل معلومات عامة | تحديثات تقدم العملية |
| notice | أحداث عادية لكنها مهمة | تغييرات التكوين |
| warning | حالات تحذيرية | استخدام ميزات مهجورة |
| error | حالات خطأ | فشل العمليات |
| critical | حالات حرجة | فشل مكونات النظام |
| alert | يجب اتخاذ إجراء فورًا | اكتشاف تلف في البيانات |
| emergency | النظام غير قابل للاستخدام | فشل النظام الكامل |
لتنفيذ الإشعارات في MCP، تحتاج إلى إعداد كل من جانب الخادم والعميل للتعامل مع التحديثات في الوقت الحقيقي. هذا يسمح لتطبيقك بتقديم ردود فعل فورية للمستخدمين أثناء العمليات طويلة الأمد.
لنبدأ بجانب الخادم. في MCP، تعرف الأدوات التي يمكنها إرسال إشعارات أثناء معالجة الطلبات. يستخدم الخادم كائن السياق (عادة ctx) لإرسال الرسائل إلى العميل.
@mcp.tool(description="A tool that sends progress notifications")
async def process_files(message: str, ctx: Context) -> TextContent:
await ctx.info("Processing file 1/3...")
await ctx.info("Processing file 2/3...")
await ctx.info("Processing file 3/3...")
return TextContent(type="text", text=f"Done: {message}")في المثال السابق، ترسل أداة process_files ثلاث إشعارات إلى العميل أثناء معالجة كل ملف. تُستخدم طريقة ctx.info() لإرسال رسائل معلوماتية.
بالإضافة إلى ذلك، لتمكين الإشعارات، تأكد من أن خادمك يستخدم نقل بث (مثل streamable-http) وأن عميلك ينفذ معالج رسائل لمعالجة الإشعارات. إليك كيفية إعداد الخادم لاستخدام نقل streamable-http:
mcp.run(transport="streamable-http")[Tool("A tool that sends progress notifications")]
public async Task<TextContent> ProcessFiles(string message, ToolContext ctx)
{
await ctx.Info("Processing file 1/3...");
await ctx.Info("Processing file 2/3...");
await ctx.Info("Processing file 3/3...");
return new TextContent
{
Type = "text",
Text = $"Done: {message}"
};
}في هذا المثال الخاص بـ .NET، تُزين أداة ProcessFiles بوسم Tool وترسل ثلاث إشعارات إلى العميل أثناء معالجة كل ملف. تُستخدم طريقة ctx.Info() لإرسال رسائل معلوماتية.
لتمكين الإشعارات في خادم MCP الخاص بك على .NET، تأكد من استخدام نقل بث:
var builder = McpBuilder.Create();
await builder
.UseStreamableHttp() // Enable streamable HTTP transport
.Build()
.RunAsync();يجب على العميل تنفيذ معالج رسائل لمعالجة وعرض الإشعارات عند وصولها.
async def message_handler(message):
if isinstance(message, types.ServerNotification):
print("NOTIFICATION:", message)
else:
print("SERVER MESSAGE:", message)
async with ClientSession(
read_stream,
write_stream,
logging_callback=logging_collector,
message_handler=message_handler,
) as session:في الكود السابق، تتحقق دالة message_handler مما إذا كانت الرسالة الواردة إشعارًا. إذا كانت كذلك، تطبع الإشعار؛ وإلا تعالجه كرسالة خادم عادية. لاحظ أيضًا كيف يتم تهيئة ClientSession مع message_handler للتعامل مع الإشعارات الواردة.
// Define a message handler
void MessageHandler(IJsonRpcMessage message)
{
if (message is ServerNotification notification)
{
Console.WriteLine($"NOTIFICATION: {notification}");
}
else
{
Console.WriteLine($"SERVER MESSAGE: {message}");
}
}
// Create and use a client session with the message handler
var clientOptions = new ClientSessionOptions
{
MessageHandler = MessageHandler,
LoggingCallback = (level, message) => Console.WriteLine($"[{level}] {message}")
};
using var client = new ClientSession(readStream, writeStream, clientOptions);
await client.InitializeAsync();
// Now the client will process notifications through the MessageHandlerفي هذا المثال الخاص بـ .NET، تتحقق دالة MessageHandler مما إذا كانت الرسالة الواردة إشعارًا. إذا كانت كذلك، تطبع الإشعار؛ وإلا تعالجه كرسالة خادم عادية. يتم تهيئة ClientSession مع معالج الرسائل عبر ClientSessionOptions.
لتمكين الإشعارات، تأكد من أن خادمك يستخدم نقل بث (مثل streamable-http) وأن عميلك ينفذ معالج رسائل لمعالجة الإشعارات.
يشرح هذا القسم مفهوم إشعارات التقدم في MCP، ولماذا هي مهمة، وكيفية تنفيذها باستخدام Streamable HTTP. ستجد أيضًا مهمة عملية لتعزيز فهمك.
إشعارات التقدم هي رسائل في الوقت الحقيقي تُرسل من الخادم إلى العميل أثناء العمليات طويلة الأمد. بدلاً من الانتظار حتى انتهاء العملية بالكامل، يبقي الخادم العميل محدثًا بالحالة الحالية. هذا يحسن الشفافية، تجربة المستخدم، ويسهل التصحيح.
مثال:
"Processing document 1/10"
"Processing document 2/10"
...
"Processing complete!"
إشعارات التقدم ضرورية لعدة أسباب:
- تحسين تجربة المستخدم: يرى المستخدمون التحديثات أثناء تقدم العمل، وليس فقط في النهاية.
- ردود فعل في الوقت الحقيقي: يمكن للعملاء عرض أشرطة تقدم أو سجلات، مما يجعل التطبيق يبدو تفاعليًا.
- تسهيل التصحيح والمراقبة: يمكن للمطورين والمستخدمين رؤية أين قد تكون العملية بطيئة أو متوقفة.
إليك كيفية تنفيذ إشعارات التقدم في MCP:
- على الخادم: استخدم
ctx.info()أوctx.log()لإرسال الإشعارات مع معالجة كل عنصر. هذا يرسل رسالة إلى العميل قبل أن تكون النتيجة الرئيسية جاهزة. - على العميل: نفذ معالج رسائل يستمع للإشعارات ويعرضها عند وصولها. يميز هذا المعالج بين الإشعارات والنتيجة النهائية.
مثال الخادم:
@mcp.tool(description="A tool that sends progress notifications")
async def process_files(message: str, ctx: Context) -> TextContent:
for i in range(1, 11):
await ctx.info(f"Processing document {i}/10")
await ctx.info("Processing complete!")
return TextContent(type="text", text=f"Done: {message}")مثال العميل:
async def message_handler(message):
if isinstance(message, types.ServerNotification):
print("NOTIFICATION:", message)
else:
print("SERVER MESSAGE:", message)عند تنفيذ خوادم MCP باستخدام نقل قائم على HTTP، يصبح الأمان أمرًا بالغ الأهمية يتطلب اهتمامًا دقيقًا بعدة نواحي للهجوم وآليات الحماية.
الأمان ضروري عند تعريض خوادم MCP عبر HTTP. يقدم Streamable HTTP أسطح هجوم جديدة ويتطلب تكوينًا دقيقًا.
- التحقق من رأس Origin: تحقق دائمًا من رأس
Originلمنع هجمات إعادة ربط DNS. - ربط localhost: للتطوير المحلي، اربط الخوادم بـ
localhostلتجنب تعريضها للإنترنت العام. - المصادقة: نفذ المصادقة (مثل مفاتيح API، OAuth) للنشر في الإنتاج.
- CORS: قم بتكوين سياسات مشاركة الموارد عبر الأصول (CORS) لتقييد الوصول.
- HTTPS: استخدم HTTPS في الإنتاج لتشفير الحركة.
- لا تثق أبدًا في الطلبات الواردة بدون تحقق.
- سجل وراقب كل الوصول والأخطاء.
- حدّث التبعيات بانتظام لسد ثغرات الأمان.
- موازنة الأمان مع سهولة التطوير
- ضمان التوافق مع بيئات العملاء المختلفة
بالنسبة للتطبيقات التي تستخدم حاليًا Server-Sent Events (SSE)، يوفر الانتقال إلى Streamable HTTP قدرات محسنة واستدامة أفضل على المدى الطويل لتطبيقات MCP الخاصة بك.
هناك سببان مقنعان للترقية من SSE إلى Streamable HTTP:
- يوفر Streamable HTTP قابلية توسع أفضل، وتوافق أكبر، ودعمًا أغنى للإشعارات مقارنةً بـ SSE.
- هو النقل الموصى به لتطبيقات MCP الجديدة.
إليك كيفية الترحيل من SSE إلى Streamable HTTP في تطبيقات MCP الخاصة بك:
- تحديث كود الخادم لاستخدام
transport="streamable-http"فيmcp.run(). - تحديث كود العميل لاستخدام
streamablehttp_clientبدلاً من عميل SSE. - تنفيذ معالج رسائل في العميل لمعالجة الإشعارات.
- اختبار التوافق مع الأدوات وسير العمل الحالية.
يوصى بالحفاظ على التوافق مع عملاء SSE الحاليين أثناء عملية الترحيل. فيما يلي بعض الاستراتيجيات:
- يمكنك دعم كل من SSE وStreamable HTTP بتشغيل كلا النقلين على نقاط نهاية مختلفة.
- ترحيل العملاء تدريجيًا إلى النقل الجديد.
تأكد من معالجة التحديات التالية أثناء الترحيل:
- ضمان تحديث جميع العملاء
- التعامل مع الاختلافات في تسليم الإشعارات
يجب أن تكون الأمان أولوية قصوى عند تنفيذ أي خادم، خاصة عند استخدام نقلات تعتمد على HTTP مثل Streamable HTTP في MCP.
عند تنفيذ خوادم MCP باستخدام نقلات تعتمد على HTTP، يصبح الأمان أمرًا بالغ الأهمية يتطلب اهتمامًا دقيقًا بعدة نواحي للهجوم وآليات الحماية.
الأمان أمر حاسم عند تعريض خوادم MCP عبر HTTP. يقدم Streamable HTTP أسطح هجوم جديدة ويتطلب إعدادًا دقيقًا.
فيما يلي بعض اعتبارات الأمان الرئيسية:
- التحقق من رأس Origin: تحقق دائمًا من رأس
Originلمنع هجمات إعادة ربط DNS. - ربط localhost: للتطوير المحلي، اربط الخوادم بـ
localhostلتجنب تعريضها للإنترنت العام. - المصادقة: نفذ المصادقة (مثل مفاتيح API، OAuth) للنشر في بيئات الإنتاج.
- CORS: قم بتكوين سياسات مشاركة الموارد عبر الأصول (CORS) لتقييد الوصول.
- HTTPS: استخدم HTTPS في بيئات الإنتاج لتشفير حركة المرور.
بالإضافة إلى ذلك، إليك بعض أفضل الممارسات التي يجب اتباعها عند تنفيذ الأمان في خادم MCP للبث:
- لا تثق أبدًا في الطلبات الواردة دون تحقق.
- سجل وراقب جميع عمليات الوصول والأخطاء.
- حدّث التبعيات بانتظام لسد ثغرات الأمان.
ستواجه بعض التحديات عند تنفيذ الأمان في خوادم MCP للبث:
- الموازنة بين الأمان وسهولة التطوير
- ضمان التوافق مع بيئات عملاء متنوعة
السيناريو: قم ببناء خادم وعميل MCP حيث يعالج الخادم قائمة من العناصر (مثل الملفات أو المستندات) ويرسل إشعارًا لكل عنصر تتم معالجته. يجب على العميل عرض كل إشعار فور وصوله.
الخطوات:
- نفذ أداة خادم تعالج قائمة وترسل إشعارات لكل عنصر.
- نفذ عميلًا مع معالج رسائل لعرض الإشعارات في الوقت الحقيقي.
- اختبر تنفيذك بتشغيل كل من الخادم والعميل، وراقب الإشعارات.
لمواصلة رحلتك مع بث MCP وتوسيع معرفتك، يوفر هذا القسم موارد إضافية وخطوات مقترحة لبناء تطبيقات أكثر تقدمًا.
- Microsoft: مقدمة في HTTP Streaming
- Microsoft: Server-Sent Events (SSE)
- Microsoft: CORS في ASP.NET Core
- Python requests: طلبات البث
- جرب بناء أدوات MCP أكثر تقدمًا تستخدم البث للتحليلات في الوقت الحقيقي، الدردشة، أو التحرير التعاوني.
- استكشف دمج بث MCP مع أُطُر الواجهة الأمامية (React، Vue، إلخ) لتحديثات واجهة المستخدم الحية.
- التالي: استخدام مجموعة أدوات AI لـ VSCode
إخلاء المسؤولية:
تمت ترجمة هذا المستند باستخدام خدمة الترجمة الآلية Co-op Translator. بينما نسعى لتحقيق الدقة، يرجى العلم أن الترجمات الآلية قد تحتوي على أخطاء أو عدم دقة. يجب اعتبار المستند الأصلي بلغته الأصلية المصدر الموثوق به. للمعلومات الهامة، يُنصح بالاعتماد على الترجمة البشرية المهنية. نحن غير مسؤولين عن أي سوء فهم أو تفسير ناتج عن استخدام هذه الترجمة.