Đi hết hướng dẫn này, bạn sẽ có một giao diện cho MCP server render ngay trong cửa sổ hội thoại ChatGPT: widget tương tác như bản đồ, biểu đồ động hay trình xem mô hình 3D, thay cho những dòng văn bản tĩnh.
Nền tảng là tiêu chuẩn MCP Apps. Nó dựng các thành phần giao diện trong một iframe bảo mật, cho phép người dùng thao tác thẳng trên dữ liệu thay vì chỉ nhận kết quả thô.
Trước khi bắt đầu, bạn cần Node.js 18 trở lên và đã quen với hai thành phần cơ bản Tools và Resources trong Model Context Protocol. Bạn cũng cần biết cách điều phối luồng dữ liệu giữa logic phía server và sandbox của host.
Mã nguồn hoàn chỉnh của dự án mẫu trong bài có sẵn trên GitHub: camnangai-public-sources/mcp-app-demo.

Bước 1 — Tạo dự án và cài gói MCP Apps
Kiến trúc MCP App tách bạch giữa logic xử lý dữ liệu và mã nguồn hiển thị: một bên là server Node.js/TypeScript, một bên là bundle giao diện chạy trong iframe. Cả hai nằm chung một dự án.
mkdir mcp-app-demo && cd mcp-app-demo
npm init -yMở package.json và thêm "type": "module" để dùng được cú pháp ES module.
Cài các gói phụ thuộc:
npm install @modelcontextprotocol/ext-apps @modelcontextprotocol/sdk express cors zod
npm install -D typescript tsx vite vite-plugin-singlefile @types/express @types/corsexpress và cors là phụ thuộc chạy thật — server import chúng lúc khởi động — nên chúng thuộc
dependencies, không phải devDependencies.
Thêm ba script vào package.json:
{
"scripts": {
"build": "vite build",
"serve": "tsx server.ts",
"dev": "INPUT=mcp-app.html npm run build && npm run serve"
}
}Đi hết hướng dẫn, cấu trúc dự án sẽ như sau:
mcp-app-demo/
├── package.json
├── tsconfig.json
├── vite.config.ts # gộp giao diện thành một file HTML duy nhất
├── server.ts # MCP server, đọc ./dist/mcp-app.html
├── mcp-app.html # entry point của giao diện
└── src/
└── mcp-app.ts # logic phía giao diệnThư viện ext-apps cung cấp các lớp cầu nối quản lý giao thức JSON-RPC qua postMessage, thiết
lập kênh liên lạc an toàn giữa iframe và host ChatGPT.
Bước 2 — Viết giao diện và nối với host bằng lớp App
Frontend dùng lớp App từ SDK để đăng ký listener và truyền tin với host.

- Tạo file
src/mcp-app.ts. - Khởi tạo kết nối và xử lý kết quả trả về từ tool:
import { App } from "@modelcontextprotocol/ext-apps";
const app = new App({ name: "My App", version: "1.0.0" });
app.connect();
// Xử lý dữ liệu từ thuộc tính structuredContent của kết quả tool
app.ontoolresult = (result) => {
const data = result.structuredContent;
if (data) {
renderUI(data); // Logic hiển thị tùy chỉnh
}
};- Dùng
app.callServerToolđể kích hoạt hành động phía server khi người dùng tương tác trên UI.
Lớp App đóng gói phần truyền tin JSON-RPC qua postMessage, đảm bảo UI giao tiếp an toàn với
host mà không vi phạm chính sách cùng nguồn gốc (Same-origin policy).