MCP SDK 2.3.0 ออกพร้อมกันทั้ง Python และ TypeScript — Server.connect() ไม่ยอมให้ใช้ instance ซ้ำแล้ว, redirect ข้าม origin ถูกบล็อก, tool ที่ header ผิดพังตั้งแต่ตอนลงทะเบียน แต่ Skills (SEP-2640) ยังไม่เข้า
2 ต.ค. 2026 (ตามเวลา UTC) ทีม Model Context Protocol ปล่อย SDK อ้างอิงสองภาษาในวันเดียวกัน ได้แก่ TypeScript SDK v2.3.0 (17:55 UTC) พร้อม 1.32.0 สำหรับคนที่ยังอยู่สาย v1 (17:28 UTC) และ Python SDK v2.3.0 (22:02 UTC ซึ่งตรงกับเช้า 3 ต.ค. เวลาไทย) ส่วนใหญ่เป็นงานแก้บั๊ก แต่ทั้งสองฝั่งมี “behaviour changes” หลายข้อที่อาจทำให้โค้ดเดิมพังหรือเปลี่ยนพฤติกรรมได้ โดยเฉพาะกับคนที่เขียน MCP server แบบ stateless บน HTTP
บทความนี้สรุปเป็นโน้ตอัปเกรดสำหรับคนเขียน MCP server และเช็กสถานะของ Skills Extension ที่หลายคนรออยู่ด้วย ซึ่งยังไม่มีใน release นี้
TypeScript v2.3.0: หนึ่ง request ต่อหนึ่ง server
ข้อที่กระทบมากที่สุดคือ “One server per request” (#2918) ตอนนี้ Server.connect() จะ reject ถ้า instance นั้นเชื่อมต่ออยู่แล้ว และ stateless Streamable HTTP transport จะรับได้แค่ request เดียว release notes แนะนำให้สร้าง McpServer และ transport ข้างใน request handler (หรือใน factory ของ createMcpHandler) แทนการแชร์ instance เดียวข้ามหลาย request โดยบอกว่าการสร้าง server ตอนนี้ต้นทุนต่ำแล้ว เพราะ #2889 ทำให้ registerTool ไม่แปลง schema ของ tool ล่วงหน้าทุกครั้งอีกต่อไป
ข้ออื่นที่ต้องรู้:
- Redirect ต้องอยู่ใน origin เดิม (#2901) HTTP client transport จะตาม redirect เฉพาะเมื่อ scheme, host และ port เหมือนเดิม (อนุญาตแค่ http ไป https บน host เดียวกัน) ถ้า endpoint ของคุณ redirect ไป host หรือ port อื่น ให้ตั้ง URL ปลายทางตรง ๆ หรือตั้ง
redirectPolicy: 'follow'บน transport ส่วนในเบราว์เซอร์ request ที่ถูก redirect จะ fail เลยถ้าไม่ได้ตั้งค่านี้ - ตัวเลือกใหม่ด้านความปลอดภัย (ปิดไว้เป็นค่าเริ่มต้น)
maxToolInputElementsบนMcpServerใช้จำกัดจำนวน element ของ array และ member ของ object ใน argument ของ tool call ส่วนexpectedResourceบนrequireBearerAuth/verifyBearerTokenจะรับเฉพาะ token ที่ออกให้ server นี้ (เช็ก audience ของ token) ถ้าใช้ Express ต้องอัปเกรด@modelcontextprotocol/expressคู่กับ@modelcontextprotocol/serverด้วย prompts/getที่ไม่มีargumentsจะถูก validate เป็น{}เหมือนที่tools/callทำอยู่แล้ว ดังนั้น.optional()หรือ.default(...)ที่ครอบargsSchemaทั้งก้อนจะไม่เห็นค่าundefinedอีก- ฝั่ง client ต้องใช้
eventsource-parser3.0.8 ขึ้นไป ซึ่งช่วยเรื่องข้อความใหญ่ที่ส่งมาใน SSE event เดียวได้มาก
| การทดสอบของทีม SDK | ก่อน | หลัง 2.3.0 |
|---|---|---|
| tool result 100 MB ใน SSE event เดียว | ประมาณ 1 นาที, peak memory 1.7 GB | ไม่ถึง 1 วินาที, ประมาณ 0.5 GB |
| tool result 50 MB | ประมาณ 13 วินาที | ไม่ถึง 1 วินาที |
ของใหม่อื่น ๆ: allowedOrigins ของ helper Express/Fastify/Hono รับรูปแบบ <scheme>://* เช่น moz-extension://* ทำให้ server รับ MCP client ที่รันเป็น browser extension ได้, tasks/get และ tasks/cancel ใช้บนการเชื่อมต่อสเปก 2026-07-28 ได้แล้ว, SSEClientTransport จะ refresh แค่ครั้งเดียวหลังโดน 401 แทนการ retry ไม่รู้จบ และฟิลด์ license ใน package manifest ถูกแก้ให้เป็น Apache-2.0
สาย v1 (1.32.0) ได้ backport ไปสามเรื่อง คือ redirect เฉพาะ same-origin, maxToolInputElements และ expectedResource บน requireBearerAuth แต่ไม่มีเรื่อง “one server per request”
Python v2.3.0: ผิดตรงไหนให้พังตั้งแต่ตอนลงทะเบียน
ฝั่ง Python ระบุ behaviour changes ไว้ชัดเจนเช่นกัน:
- tool ที่มี annotation
x-mcp-headerไม่ถูกต้องจะ fail ตั้งแต่ตอนลงทะเบียน (#3620)@mcp.tool(),add_toolและTool.from_functionจะ raiseInvalidSignatureพร้อมบอกชื่อ tool และสาเหตุ ก่อนหน้านี้ server สตาร์ตได้ตามปกติ แต่ client ที่ใช้สเปก 2026-07-28 จะทิ้ง tool นั้นออกจากรายการเงียบ ๆ ค่าที่ไม่ผ่านคืออะไรก็ตามที่ไม่ใช่ parameter แบบstr,intหรือboolล้วน ๆ (รวมถึงstr | None,float, list และ enum), ชื่อ header ที่ไม่ใช่ token ที่ถูกต้อง และสองชื่อที่ต่างกันแค่ตัวพิมพ์เล็กใหญ่ ถ้าต้องการ header ที่เป็น optional ให้กำหนด schema เอง
Annotated[str | None, WithJsonSchema({"type": "string", "x-mcp-header": "Region"})] = None
- ไม่ส่ง
_metaและparamsที่ว่างอีกแล้ว (#3628) บนการเชื่อมต่อสเปก 2025-11-25 หรือเก่ากว่า SDK 2.x เคยส่ง"_meta": {}ไปกับทุก request ซึ่ง server บางตัวปฏิเสธ ตอนนี้เลิกส่งแล้วเหมือนใน v1 ผลที่ตามมาฝั่งรับคือctx.metaจะเป็นNoneแทน{}และ middleware จะเห็นctx.paramsเป็นNoneสำหรับ request ที่ไม่มี params ส่วนการเชื่อมต่อแบบ 2026-07-28 ไม่เปลี่ยน initializeไม่ส่งexperimentalถ้าไม่ได้ตั้งค่า (#3614) โค้ดฝั่ง client ที่อ่านcapabilities.experimentalบนการเชื่อมต่อแบบเก่าต้องรองรับค่าNone- ต้องใช้
httpx2>=2.10.0(เดิม>=2.5.0) เพราะตัวเลือกใหม่max_sse_event_sizeต้องใช้ ถ้าไม่ได้ pinhttpx2ต่ำกว่า 2.10 ก็ไม่ต้องทำอะไร - การ validate
Mcp-Param-*จะหา tool จากชื่อโดยตรง (#3630) แทนการรันtools/listทุกครั้งที่มีtools/callดังนั้น middleware ที่กรองหรือเขียนtools/listใหม่จะไม่มีผลกับการ validate อีก - การล็อกอิน OAuth แบบ interactive ไม่ถูกนับรวมใน request timeout (#3635) แก้ปัญหา
Client(mode="auto")ที่ไปตกลงใช้สเปก2025-11-25เมื่อผู้ใช้ล็อกอินนานเกิน 10 วินาที
ของใหม่ฝั่ง Python มี max_sse_event_size= (ค่าเริ่มต้นยังเป็น 1 MiB ต่อ SSE event ปรับขึ้นหรือส่ง None ได้ถ้า tool result ใหญ่), MCPServer(subscriptions=False) และ Client.call_tool ที่จะดึงรายการ tool ใหม่แล้ว retry หนึ่งครั้งเมื่อโดน HeaderMismatch (-32020)
เช็กลิสต์ก่อนอัปเกรด
- TS: มีโค้ดที่สร้าง
McpServerครั้งเดียวแล้วเรียกconnect()ซ้ำในแต่ละ request หรือไม่ ถ้ามี ให้ย้ายไปสร้างใน handler - TS: endpoint ของ MCP server ที่คุณเรียกมี redirect ข้าม host/port หรือไม่ (เช่น ผ่าน load balancer หรือ auth proxy) ถ้ามี ให้ใช้ URL ปลายทาง หรือตั้ง
redirectPolicy: 'follow'อย่างรู้ตัว - TS: ถ้าใช้ bearer auth ควรเปิด
expectedResourceเพื่อกันไม่ให้ token ที่ออกให้ server อื่นใช้ได้ และอัปเกรด adapter ของ Express ไปพร้อมกัน - TS: prompt ที่ใช้
.optional()/.default()ครอบargsSchemaทั้งก้อน ต้องเช็กว่ายังทำงานตามที่ตั้งใจเมื่อได้รับ{} - Python: ลองรัน server ดูหลังอัปเกรด ถ้ามี tool ใช้
x-mcp-headerกับ type ที่ไม่ใช่str/int/boolจะเจอInvalidSignatureทันที (ซึ่งดีกว่าให้ tool หายไปเงียบ ๆ) - Python: middleware หรือ handler ที่อ่าน
ctx.meta,ctx.paramsหรือcapabilities.experimentalต้องรองรับNone - Python: เช็กว่าไม่ได้ pin
httpx2ต่ำกว่า 2.10.0
Skills (SEP-2640) ยังไม่มาใน release นี้
บล็อกนี้เคยเขียนถึง SEP-2640 Skills Extension ที่ขึ้นสถานะ Final เมื่อกลางเดือน ก.ย. ซึ่งตอนนั้น SDK อ้างอิงยังไม่มีตัวไหน merge การรองรับเข้าไป จากการเช็ก GitHub API วันที่ 3 ต.ค. สถานะยังเหมือนเดิม: Python #3485 (อัปเดตล่าสุด 30 ก.ย.), TypeScript #2818 (ระบุว่าเป็น “phase 1”), รวมถึง PR ของ Go, Java, Rust และ C# ยังเปิดค้างอยู่ทั้งหมด และ release notes ของ 2.3.0 ทั้งสองภาษาไม่มีเรื่อง skills เลย ใครจะเสิร์ฟสกิลผ่าน skills/list ตามสเปกด้วย SDK ทางการตอนนี้จึงยังต้องรอ
มุมมอง AI Curator
ภาพรวมของ 2.3.0 คือ SDK กำลังเปลี่ยนจาก “ยอมให้ผ่านไปก่อน” เป็น “ผิดให้รู้ตั้งแต่เนิ่น ๆ” ทั้ง Server.connect() ที่ไม่ยอมให้ใช้ instance ซ้ำ, redirect ที่ถูกจำกัด origin และ tool ที่ header ผิดซึ่งพังตั้งแต่ตอนลงทะเบียน บั๊กแบบ “tool หายไปจากรายการเงียบ ๆ เฉพาะใน client รุ่นใหม่” เป็นบั๊กที่ debug ยากที่สุดแบบหนึ่ง เพราะฝั่ง server ไม่มี error อะไรเลย การย้ายมาพังตอน import จึงเป็นการเปลี่ยนที่ถูกต้อง แม้จะทำให้ CI แดงในวันอัปเกรดก็ตาม ส่วน expectedResource แม้จะปิดไว้เป็นค่าเริ่มต้น แต่ควรมองเป็นค่าที่ต้องเปิดสำหรับ remote MCP server ทุกตัวที่ใช้ OAuth เพราะการไม่เช็ก audience ของ token เป็นช่องโหว่คลาสสิกที่ token ของบริการหนึ่งถูกเอาไปใช้กับอีกบริการหนึ่ง
อีกเรื่องที่น่าคิดคือความ “เปิด” ของ MCP ในทางปฏิบัติ เมื่อ 30 ก.ย. David Soria Parra ผู้ร่วมสร้าง MCP ทวีตถึง Figma ว่า “please fix this” และทีม Figma ตอบว่า “our remote MCP server only accepts clients on our supported list, and Pi isn’t on it yet” พร้อมชี้ไปที่ MCP catalog และฟอร์มขอเข้ารายชื่อ แปลว่าแม้โปรโตคอลจะเปิด แต่ remote server ของผู้ให้บริการรายใหญ่สามารถเลือกได้ว่าจะคุยกับ client ตัวไหน งานด้านความปลอดภัยใน SDK อย่างการผูก audience ของ token หรือการจำกัด origin เป็นสิ่งที่ดี แต่ไม่ได้แก้ปัญหาเชิงนโยบายแบบนี้ สำหรับทีมไทยที่สร้าง agent harness หรือ client ของตัวเอง ควรเผื่อไว้เลยว่า remote MCP ของ SaaS บางเจ้าอาจใช้ไม่ได้จนกว่าจะได้อยู่ใน allowlist และควรออกแบบให้ fallback ไปใช้ REST API ตรงได้
ในฝั่ง Skills การที่สเปก Final มาเกือบสามสัปดาห์แต่ยังไม่มี SDK ไหน merge เลย ยืนยันสิ่งที่บล็อกนี้เคยเตือนไว้ว่า “สเปก Final” ยังไม่เท่ากับ “ใช้งานได้” ถ้าทีมของคุณกำลังวางแผนแจกจ่ายสกิลภายในองค์กรผ่าน MCP ตอนนี้ควรใช้วิธีที่มีอยู่แล้วไปก่อน และรอ release note ของ SDK ที่ระบุว่ามี skills จริง ๆ ค่อยย้ายมาใช้
แหล่งข่าว
อ่านเพิ่มในหมวด AI Skills
Anthropic แนะ “ยุบ subagent กลับเข้า agent loop เดียว” พร้อมปล่อย single-agent-loop-kit เป็น skill ของ Claude Code ที่ช่วย audit ระบบ multi-agent แล้วพับทีละตัวโดยวัดด้วย eval ก่อน-หลัง
บทความ 22 ต.ค. จากทีม Applied AI ของ Anthropic บอกว่า agent ตัวเดียวที่โหลด skill และ tool เมื่อจำเป็น มักให้คุณภาพดีกว่า ถูกกว่า และเร็วกว่าการแตก subagent ตามผังองค์กร ลูกค้ารายหนึ่งเร็วขึ้นราว 2 เท่า พร้อมปล่อย single-agent-loop-kit (Apache-2.0) เป็น skill ที่ audit ระบบเดิมแล้วพับ subagent ทีละตัว และเก็บไว้เฉพาะตัวที่ eval บอกว่ายังจำเป็น
MCP TypeScript SDK 2.4.0 เป็น SDK ทางการตัวแรกที่ปล่อย Skills over MCP (SEP-2640) ใน release จริง — loadSkills() เสิร์ฟทั้งโฟลเดอร์ SKILL.md, SkillsClient ตรวจ digest ทุกไฟล์ ส่วน Python/C# merge แล้วแต่ยังไม่ออก release
23 ต.ค. 2026 MCP TypeScript SDK 2.4.0 ปล่อยการรองรับ Skills extension (SEP-2640) ทั้งฝั่ง server และ client เป็น SDK อ้างอิงตัวแรกที่เอาฟีเจอร์นี้ขึ้น release จริง หลังสเปกขึ้นสถานะ Final มาตั้งแต่ 13 ก.ย. ทำงานได้ทั้งโปรโตคอล 2025-11-25 และ 2026-07-28 แต่ attach() ยังเป็น experimental
Anthropic ยก Agent Skills (มาตรฐาน SKILL.md) ให้ Agentic AI Foundation ใต้ Linux Foundation ต่อจาก MCP — 70+ แพลตฟอร์มรองรับแล้ว ทั้ง ChatGPT, Cursor, Copilot และ VS Code
เมื่อ 22 ต.ค. 2026 Anthropic มอบมาตรฐาน Agent Skills ให้ Agentic AI Foundation (AAIF) ใต้ Linux Foundation พร้อมชื่อ โลโก้ GitHub org และโดเมน agentskills.io มาตรฐานจะมี Technical Steering Committee จากหลายบริษัทดูแล และมี maintainer จาก Anthropic, Google, OpenAI ที่ทำงานในนามบุคคล roadmap แรกที่เสนอคือ versioned release, กระบวนการ proposal และแนวทาง security สำหรับคนเขียนและติดตั้ง skill