Computer >> บทช่วยสอนคอมพิวเตอร์ >  >> การเขียนโปรแกรม >> Redis

เร่งการพัฒนา MCP ด้วย Redis:โซลูชันที่รวดเร็วและคุ้มค่า

Model Context Protocol (MCP) กำลังกลายเป็นวิธีมาตรฐานในการเชื่อมต่อโมเดล AI กับเครื่องมือและแหล่งข้อมูลภายนอกอย่างรวดเร็ว เมื่อการนำ MCP ไปใช้เพิ่มมากขึ้น นักพัฒนาก็พบว่าการสร้างการใช้งาน MCP ที่แข็งแกร่งและพร้อมสำหรับการผลิตนั้นต้องการมากกว่าการปฏิบัติตามข้อกำหนด:ต้องมีโครงสร้างพื้นฐานที่เหมาะสม ในโพสต์นี้ เราจะสำรวจวิธีที่ Redis ขับเคลื่อนกรณีการใช้งาน MCP ที่แตกต่างกันสามกรณี:การประสานงานฟังก์ชันแบบไร้เซิร์ฟเวอร์แบบกระจายในการใช้งาน SSE ของ Vercel การเปิดใช้งานเหตุการณ์ที่กลับมาทำงานต่อสำหรับสตรีมที่รันระยะยาว และการจัดการโฟลว์ OAuth ที่ปลอดภัยกับพนักงาน

ทำความเข้าใจเกี่ยวกับการขนส่ง MCP

ก่อนที่จะเจาะลึกตัวอย่างของเรา เราจะมาสรุปสั้นๆ ว่า MCP จัดการกับการสื่อสารอย่างไร MCP รองรับการขนส่งสองแบบ:Stdio สำหรับเซิร์ฟเวอร์ภายในเครื่องและ HTTP ที่สตรีมได้ สำหรับเซิร์ฟเวอร์ระยะไกล ในอดีต ยังมีการขนส่ง SSE (เหตุการณ์ที่เซิร์ฟเวอร์ส่ง) สำหรับเซิร์ฟเวอร์ระยะไกลด้วย ซึ่งปัจจุบันเลิกใช้แล้ว

การเปลี่ยนจาก SSE เป็น HTTP แบบสตรีมได้แสดงถึงวิวัฒนาการในวิธีที่ MCP จัดการกับการสื่อสารแบบเรียลไทม์ แต่การใช้งานที่มีอยู่จำนวนมากยังคงใช้รูปแบบ SSE มาดูกันว่า Redis ช่วยแก้ปัญหาความท้าทายหลักประการหนึ่งในโมเดลนั้นได้อย่างไร

ใช้กรณีที่ 1:SSE กับ Redis Pub/Sub

เมื่อ Vercel CTO Malte สร้างเครื่องจัดการ MCP เขาเผชิญกับความท้าทายแบบไร้เซิร์ฟเวอร์แบบคลาสสิก:คุณจะประสานงานระหว่างปลายทางหลายจุดได้อย่างไร ในเมื่อแต่ละคำขออาจได้รับการจัดการโดยฟังก์ชันไร้เซิร์ฟเวอร์ที่แตกต่างกัน

ในโมเดลการขนส่ง SSE มีจุดสิ้นสุดที่สำคัญสองจุด:08 เพื่อรักษาการเชื่อมต่อและ 11 เพื่อรับข้อความจากลูกค้า ปัญหาคือ:ในสภาพแวดล้อมแบบไร้เซิร์ฟเวอร์เช่น Vercel ตำแหน่งข้อมูลเหล่านี้จะถูกแยกออกจากกันโดยสิ้นเชิง พวกเขาไม่แชร์หน่วยความจำและคำขอไปที่ 23 อาจถูกจัดการโดยอินสแตนซ์ฟังก์ชันที่แตกต่างไปจากอินสแตนซ์ที่จัดการ 39 โดยสิ้นเชิง .

วิธีแก้ปัญหา? เรดิสผับ/ซับ ดังที่ Malte อธิบายไว้ใน X:

เร่งการพัฒนา MCP ด้วย Redis:โซลูชันที่รวดเร็วและคุ้มค่า

การใช้งานใช้ช่องทาง Redis เพื่อประสานงานระหว่างตำแหน่งข้อมูล เมื่อลูกค้าส่งข้อความถึง 49 จุดสิ้นสุดนั้นจะเผยแพร่ไปยังช่องทาง Redis ที่ 57 ปลายทางสมัครเป็นสมาชิกแล้ว 64 จุดสิ้นสุดประมวลผลคำขอและเผยแพร่การตอบกลับผ่านช่องทางอื่นที่ 70 กำลังฟังอยู่

เร่งการพัฒนา MCP ด้วย Redis:โซลูชันที่รวดเร็วและคุ้มค่า

รูปแบบนี้เปลี่ยน Redis ให้เป็นบัสข้อความได้อย่างมีประสิทธิภาพซึ่งเชื่อมช่องว่างระหว่างฟังก์ชันไร้เซิร์ฟเวอร์ที่แยกออกมา ช่วยให้สามารถทำงานร่วมกันราวกับว่าเป็นส่วนหนึ่งของกระบวนการเดียวกัน แม้ว่า SSE จะเลิกใช้แล้วและหันไปใช้ Streamable HTTP แทน (หมายความว่าการใช้งาน MCP ใหม่ควรใช้การขนส่งสมัยใหม่) สิ่งนี้ยังคงเป็นตัวอย่างที่ดีเยี่ยมของการใช้ Redis สำหรับการประสานงานระหว่างฟังก์ชันไร้เซิร์ฟเวอร์ที่แยกออกมา

ใช้กรณีที่ 2:ที่เก็บกิจกรรมเพื่อการกลับมาทำงานต่อ

หนึ่งในคุณสมบัติที่ทรงพลังที่สุดของการขนส่ง HTTP แบบสตรีมได้ของ MCP คือการรองรับการทำงานต่อ คุณสมบัตินี้ช่วยให้ไคลเอนต์สามารถสตรีมต่อจากที่ค้างไว้ในกรณีที่ขาดการเชื่อมต่อ นี่เป็นสิ่งสำคัญสำหรับแอปพลิเคชันที่ใช้งานจริงซึ่งการหยุดชะงักของเครือข่ายเป็นสิ่งที่หลีกเลี่ยงไม่ได้

ทำความเข้าใจสตรีม MCP

เพื่อทำความเข้าใจว่าเหตุใดความสามารถในการกลับมาทำงานต่อจึงมีความสำคัญ เราต้องเข้าใจว่าสตรีม MCP ประกอบด้วยอะไร การดำเนินการบางอย่าง เช่น การเรียกใช้เครื่องมืออย่างง่าย ส่งคืนการตอบกลับครั้งเดียว แต่เครื่องมือยังสามารถส่งคืนหลายเหตุการณ์ระหว่างการดำเนินการโดยใช้วิธีการเช่น server.sendLoggingMessage การสตรีมแบบหลายเหตุการณ์เหล่านี้เป็นจุดที่ความสามารถในการกลับมาทำงานต่อเป็นสิ่งสำคัญ หากไคลเอนต์ยกเลิกการเชื่อมต่อกลางคัน ก็ควรจะสามารถดำเนินการต่อจากจุดที่ค้างไว้ แทนที่จะเริ่มต้นใหม่

การใช้งาน EventStore ด้วย Redis

MCP SDK กำหนดอินเทอร์เฟซ EventStore ที่ต้องใช้สองวิธี:84 สำหรับการเพิ่มเหตุการณ์และ 96 สำหรับการดึงข้อมูลเหตุการณ์ที่เริ่มต้นจากรหัสเหตุการณ์เฉพาะ SDK มีการใช้งานในหน่วยความจำ แต่สำหรับการใช้งานจริง คุณต้องมีพื้นที่เก็บข้อมูลถาวร

นี่คือการใช้งาน EventStore แบบอิง Redis:

import { Redis } from '@upstash/redis';
import { JSONRPCMessage } from '@modelcontextprotocol/sdk/types.js';
import { EventStore } from '@modelcontextprotocol/sdk/server/streamableHttp.js';
 
export class RedisEventStore implements EventStore {
 private redis: Redis;
 
 constructor(params: ConstructorParameters<typeof Redis>[0]) {
 this.redis = new Redis(params);
 }
 
 /**
 * Stores an event in a Redis Stream
 * Implements EventStore.storeEvent
 */
 async storeEvent(streamId: string, message: JSONRPCMessage): Promise<string> {
 const eventId = await this.redis.xadd(`stream:${streamId}`, '*', {
 message: JSON.stringify(message),
 });
 return eventId;
 }
 
 /**
 * Replays events that occurred after a specific event ID
 * Implements EventStore.replayEventsAfter
 */
 async replayEventsAfter(
 lastEventId: string,
 { send }: { send: (eventId: string, message: JSONRPCMessage) => Promise<void> }
 ): Promise<string> {
 if (!lastEventId) {
 return '';
 }
 
 // Extract the stream ID from the lastEventId
 const streamId = lastEventId.split('-')[0]; // Assuming the stream ID is part of the key
 if (!streamId) {
 return '';
 }
 
 let nextId = lastEventId;
 while (true) {
 // Fetch events from the stream starting AFTER the next ID (exclusive)
 const events = await this.redis.xrange(`stream:${streamId}`, `(${nextId}`, '+', 10);
 
 // Convert the returned object to an array of entries
 const eventEntries = Object.entries(events);
 
 if (eventEntries.length === 0) {
 break; // No more events to replay
 }
 
 for (const [eventId, fields] of eventEntries) {
 // Ensure fields.message exists and parse it
 if (fields && typeof fields === 'object' && 'message' in fields && typeof fields.message === 'string') {
 const message = JSON.parse(fields.message) as JSONRPCMessage;
 await send(eventId, message);
 nextId = eventId; // Update the next ID to the current event ID
 }
 }
 }
 
 return streamId;
 }
}

การใช้งานนี้ใช้ Redis Streams ซึ่งเหมาะสำหรับกรณีการใช้งานนี้

ข้อจำกัด

มีข้อแม้สำคัญประการหนึ่งที่ควรทราบ:เมื่อเครื่องมือส่งหลายเหตุการณ์ streamId จะถูกตั้งค่าเป็น 109 และค่าคงที่นี้จะยังคงเหมือนเดิมในสตรีมและผู้ใช้ที่แตกต่างกัน ซึ่งหมายความว่าหากผู้ใช้สองคนใช้เครื่องมือเดียวกันที่ส่งหลายเหตุการณ์พร้อมกัน กิจกรรมของพวกเขาอาจปะปนกันในสตรีมเดียวกันได้

ฉันได้เปิดประเด็นเกี่ยวกับเรื่องนี้ในพื้นที่เก็บข้อมูลอย่างเป็นทางการแล้ว เราอาจจำเป็นต้องปรับเปลี่ยนการใช้งาน และเราจะอัปเดตโพสต์นี้ตามความเหมาะสม หากจำเป็น

ใช้กรณีที่ 3:การใช้ MCP OAuth ของพนักงาน

ข้อกำหนด MCP รวมถึงการสนับสนุนการตรวจสอบสิทธิ์และการอนุญาต ทำให้เซิร์ฟเวอร์ MCP สามารถตรวจสอบสิทธิ์ไคลเอ็นต์ได้อย่างปลอดภัยและควบคุมการเข้าถึงทรัพยากร ข้อมูลจำเพาะรองรับรูปแบบการรับรองความถูกต้องหลายรูปแบบ รวมถึง OAuth 2.0 ซึ่งมีประโยชน์อย่างยิ่งสำหรับการผสานรวมกับผู้ให้บริการข้อมูลประจำตัวที่มีอยู่ และเปิดใช้งานการเข้าถึงเครื่องมือและข้อมูลตามขอบเขตผู้ใช้

เสมียนได้สร้างไคลเอนต์ OAuth ที่ครอบคลุมสำหรับ MCP โดยการใช้อินเทอร์เฟซ OAuthClientProvider จาก MCP SDK การใช้งานนี้แสดงให้เห็นถึงกรณีการใช้งานที่สำคัญอีกกรณีหนึ่งสำหรับ Redis ในแอปพลิเคชัน MCP หากคุณต้องการเริ่มต้นใช้งานเครื่องมือ MCP ลองดูพื้นที่เก็บข้อมูลสาธิตซึ่งเป็นจุดเริ่มต้นที่ดี

เหตุใดพื้นที่เก็บข้อมูลจึงมีความสำคัญสำหรับ OAuth

ดังที่เสมียนอธิบายไว้ใน 115 พื้นที่เก็บข้อมูล พื้นที่เก็บข้อมูลถาวรเป็นสิ่งจำเป็นสำหรับการใช้งาน MCP OAuth ด้วยเหตุผลสำคัญสองประการ:

  1. ขั้นตอน OAuth ครอบคลุมปลายทางหลายจุด - การเริ่มต้น, การโทรกลับ OAuth และคำขอ MCP ทั้งหมดสามารถจัดการได้โดยฟังก์ชันไร้เซิร์ฟเวอร์ที่แตกต่างกันโดยไม่ต้องใช้หน่วยความจำร่วมกัน
  2. การเชื่อมต่อ MCP ใช้เวลานาน - การใช้ที่เก็บข้อมูลในหน่วยความจำจะขยายความต้องการหน่วยความจำเมื่อแอปพลิเคชันปรับขนาด และการรีสตาร์ทเซิร์ฟเวอร์ใดๆ จะทำให้เซสชันทั้งหมดไม่ถูกต้อง

สิ่งที่ถูกเก็บไว้ใน Redis

ร้านค้า Redis ของเสมียนจัดการข้อมูลสามประเภท โดยแต่ละประเภทมีวัตถุประสงค์เฉพาะในโฟลว์ OAuth:

ผู้ตรวจสอบ PKCE (129 )สิ่งเหล่านี้จะถูกเก็บไว้เมื่อเริ่มต้นโฟลว์ OAuth และอ่านอีกครั้งหลังจากที่ผู้ใช้ให้สิทธิ์การเข้าถึง เป็นส่วนหนึ่งของโฟลว์ PKCE (Proof Key for Code Exchange) ซึ่งให้ความปลอดภัยเพิ่มเติมสำหรับ OAuth ในไคลเอ็นต์สาธารณะโดยทำให้แน่ใจว่าแอปพลิเคชันที่เริ่มโฟลว์นั้นเป็นแอปพลิเคชันเดียวกับที่ทำให้เสร็จสมบูรณ์ (ตามที่กำหนดไว้ใน RFC 7636)

{
 "value": "XoYQ...",
 "created_at": "2025-10-03T06:27:06.928Z",
 "updated_at": "2025-10-03T06:27:06.928Z"
}

ข้อมูลเซสชัน (136 )ซึ่งจะจัดเก็บการกำหนดค่าและสถานะทั้งหมดสำหรับเซสชัน MCP ในตอนแรก จะมีตำแหน่งข้อมูล MCP, การกำหนดค่า OAuth และข้อมูลรับรองไคลเอ็นต์ หลังจากที่ผู้ใช้ให้สิทธิ์การเข้าถึงแล้ว ระบบจะอัปเดตด้วยโทเค็นการเข้าถึงและรีเฟรช สุดท้าย 147 ธงจะถูกเพิ่มเมื่อโฟลว์เสร็จสิ้น

{
 "value": {
 "mcpEndpoint": "http://localhost:3001/mcp",
 "oauthRedirectUrl": "http://localhost:3000/oauth_callback",
 "oauthScopes": "openid profile email",
 "mcpClientName": "Clerk MCP Demo",
 "mcpClientVersion": "0.0.1",
 "oauthClientUri": "http://example.com",
 "oauthPublicClient": false,
 "clientId": "8Yb2...",
 "clientSecret": "64YG..."
 },
 "created_at": "2025-10-03T06:27:06.882Z",
 "updated_at": "2025-10-03T06:27:06.882Z"
}

พารามิเตอร์สถานะ (152 )จับคู่พารามิเตอร์สถานะ OAuth กับรหัสเซสชัน ทำให้สามารถรับข้อมูลเซสชันโดยใช้รหัสสถานะได้:

{
 "value": "dX61...",
 "created_at": "2025-10-03T06:27:03.585Z",
 "updated_at": "2025-10-03T06:27:03.585Z"
}

สถาปัตยกรรมนี้ช่วยให้โฟลว์ OAuth ทำงานได้อย่างราบรื่นในฟังก์ชันไร้เซิร์ฟเวอร์แบบกระจาย ในขณะที่ยังคงรักษาความปลอดภัยและความสมบูรณ์ของเซสชัน

เหตุใด Redis จึงสมบูรณ์แบบสำหรับ MCP

ในตัวอย่างทั้งสามนี้ เราเห็นรูปแบบทั่วไปที่ทำให้ Redis เป็นตัวเลือกที่เหมาะสมที่สุดสำหรับโครงสร้างพื้นฐาน MCP:

เวลาแฝงต่ำ :การดำเนินการ MCP มักจะต้องรวดเร็ว สถาปัตยกรรมในหน่วยความจำของ Redis มอบเวลาตอบสนองที่จำเป็นสำหรับการโต้ตอบของ AI แบบเรียลไทม์

ความสามารถ Pub/Sub :ดังที่เราเห็นในการใช้งานของ Vercel นั้น Redis Pub/Sub ช่วยให้สามารถประสานงานระหว่างส่วนประกอบที่กระจายได้อย่างสวยงาม โดยไม่ต้องซับซ้อนของคิวข้อความแบบเต็ม

โครงสร้างข้อมูลที่หลากหลาย :สตรีมสำหรับสตรีมเหตุการณ์ แฮชสำหรับข้อมูลเซสชัน และคู่คีย์-ค่าอย่างง่ายสำหรับสถานะ Redis มอบโครงสร้างข้อมูลที่เหมาะสมสำหรับกรณีการใช้งานแต่ละกรณี

การหมดอายุในตัว :การล้างข้อมูลอัตโนมัติผ่าน TTL โทเค็น OAuth สตรีมเหตุการณ์ และข้อมูลเซสชันทั้งหมดสามารถหมดอายุได้โดยอัตโนมัติโดยไม่ต้องรวบรวมขยะด้วยตนเอง

เป็นมิตรกับเซิร์ฟเวอร์ :ด้วยโซลูชันอย่าง Upstash Redis คุณจะได้รับ Redis ไร้เซิร์ฟเวอร์ที่มีการจัดการเต็มรูปแบบ ซึ่งจะปรับขนาดเป็นศูนย์เมื่อไม่ได้ใช้งาน เหมาะสำหรับการใช้งาน MCP ที่อาจมีปริมาณงานที่ไม่แน่นอน

เหนือกว่าคุณสมบัติเฉพาะของ MCP:Redis ในระบบนิเวศ AI ที่กว้างขึ้น

แม้ว่าเราจะมุ่งเน้นไปที่คุณสมบัติที่กำหนดไว้อย่างชัดเจนในข้อกำหนด MCP แต่ยูทิลิตี้ของ Redis ขยายไปไกลกว่ารูปแบบที่เราได้สำรวจเมื่อพูดถึงการขับเคลื่อน AI โพสต์ในบล็อกล่าสุดของเราแสดงรูปแบบต่างๆ เหล่านี้:

  • การบูรณาการ AI SDK - การใช้ Redis เพื่อปรับปรุง Vercel AI SDK
  • ประวัติการแชท - ประวัติการส่งข้อความคงอยู่

นอกเหนือจากตัวอย่างของเราแล้ว ชุมชนได้สร้างเครื่องมือที่ขับเคลื่อนด้วย Redis ที่น่าประทับใจสำหรับแอปพลิเคชัน AI ชุดเครื่องมือ ai-sdk-tools จาก Midday มีแพ็คเกจการแคชผลลัพธ์เครื่องมือที่ใช้ Redis เพื่อแคชผลลัพธ์เครื่องมือ AI SDK ดังที่แสดงในตัวอย่างนี้ ปรับปรุงประสิทธิภาพได้อย่างมากและลดต้นทุน:

เร่งการพัฒนา MCP ด้วย Redis:โซลูชันที่รวดเร็วและคุ้มค่า

ไม่ว่าคุณจะสร้างเซิร์ฟเวอร์ MCP, เอเจนต์ AI หรือแอปพลิเคชัน AI เต็มรูปแบบ Redis มอบเลเยอร์โครงสร้างพื้นฐานที่ทำให้ระบบของคุณพร้อมสำหรับการผลิต ปรับขนาดได้ และมีประสิทธิภาพ

บทสรุป

Model Context Protocol ยังใหม่อยู่ แต่กำลังกลายเป็นโครงสร้างพื้นฐานที่สำคัญสำหรับแอปพลิเคชัน AI อย่างรวดเร็ว ดังที่เราได้เห็นจากตัวอย่างทั้งสามนี้แล้ว Redis มีบทบาทสำคัญในการทำให้การใช้งาน MCP มีประสิทธิภาพและพร้อมสำหรับการผลิตผ่าน:

  • ความเร็วและความยืดหยุ่น :การผสมผสานระหว่างความเร็ว ความยืดหยุ่น และสถาปัตยกรรมที่เป็นมิตรต่อเซิร์ฟเวอร์
  • การลดต้นทุน :ความสามารถในการแคชที่ลดการเรียก API และการคำนวณที่มีราคาแพง

หากคุณกำลังสร้างด้วย MCP ไม่ว่าจะบนเซิร์ฟเวอร์หรือฝั่งไคลเอ็นต์ Redis ควรอยู่ในชุดเครื่องมือของคุณในฐานะคู่หูที่สมบูรณ์แบบสำหรับแอปพลิเคชัน AI ที่ขับเคลื่อนด้วย MCP ด้วย Upstash Redis คุณสามารถเริ่มต้นได้ภายในไม่กี่วินาทีวันนี้ด้วย Redis ไร้เซิร์ฟเวอร์ที่พร้อมใช้งานทั่วโลก ซึ่งจะปรับขนาดเป็นศูนย์เมื่อไม่ได้ใช้งาน