AI 开发实战:使用MCP 服务管理SKILL

从开发到部署上线,实现MCP服务,包括工具与技能的接入

AI 开发实战:使用MCP 服务管理SKILL封面图

基于AI开发实现MCP服务,可为 Agent 提供统一的工具接入能力,自动完成技能发现和安装。

项目链接

项目初始化

这里我们直接使用codex+gpt5.5模型进行初始化,输入提示词(使用prompt-optimizer可优化提示词),mcp服务类型选择时选择”stdio“本地开发先:

$prompt-optimize 在当前项目下创建一个node类型的mcp服务,要求:
- 内容仅包含基础信息与一个简单的加法演示,
- 使用tsdown打包
- 标准的git项目,具备基本git过滤
- 具备基础utils等文件架构,能复用的优先复用,能扩展的优先扩展,
- 具备基础的可配置的环境env文件控制
- 生成agents文件说明文件架构与开发基本规范

Snipaste_2026-06-15_12-27-54

优化下打包文件:

- 打包时不需要ts与map,统一输出index.js即可
- #!/usr/bin/env node通过tsdown的banner: '#!/usr/bin/env node'添加

打包运行以下命令测试:

npx @modelcontextprotocol/inspector node dist/index.js

界面运行测试下工具是否起作用即可: Snipaste_2026-06-15_14-24-46

Skill

建议使用plan模式先计划下开发:

$prompt-optimizer 根目录下创建skills文件夹并新增一个轻量级的“提示词增强”的测试skill,utils中新增skill的扫描函数,并新增注册skill的获取、安装工具方法

检查计划模式是否符合预期后同意执行:

# 添加本地 Skill 扫描与说明式安装工具

## Summary
在项目根目录新增 `skills/`,放入轻量级测试 skill:`prompt-enhancer`。服务新增本地 skill 扫描能力,并注册 `list/get/install` 三个 MCP 工具;`install_skill` 不接收 `targetDir`,只返回由调用方 AI 结合当前提示词和运行环境决定目标位置的安装说明,不实际复制文件。

## Key Changes
- 新增 `skills/prompt-enhancer/SKILL.md`,包含 `name`、`description` frontmatter,正文用中文简要说明提示词增强流程、改写原则和输出格式。
- 在 `src/utils/` 新增 skill 扫描模块:
  - 扫描项目根目录 `skills/*/SKILL.md`。
  - 解析 `name`、`description` 和正文内容。
  - 返回 skill 名称、描述、目录路径、`SKILL.md` 路径。
  - 列表扫描跳过无效项并报告 warnings;按名获取遇到无效项则返回错误。
- 在 `src/tools/` 新增 skill 工具:
  - `list_skills`:返回项目内可用 skill 列表。
  - `get_skill`:按 `name` 返回 skill 元数据和完整 `SKILL.md` 内容。
  - `install_skill`:输入仅 `{ name: string }`,返回源路径、推荐安装策略、可执行的手动安装步骤和注意事项。
- `install_skill` 的目标目录决策不放进参数:
  - 工具输出环境线索,例如 `CODEX_HOME`、`HOME`、`USERPROFILE` 是否存在。
  - 工具给出默认规则:优先 `$CODEX_HOME/skills`,否则 `~/.codex/skills`;若当前提示词要求项目内安装,则调用方 AI 可选择项目根目录 `skills/`。
  - 因工具不执行复制,覆盖策略只以说明形式呈现:如目标已存在,可由调用方 AI 根据用户意图决定是否覆盖。
- 在 `src/server/create-server.ts` 注册新增工具,保持现有 `add` 工具不变。
- 不新增运行时依赖;frontmatter 用轻量字符串解析实现。

## Public Interfaces
- `list_skills` 输入为空;输出 `{ skills, warnings }`。
- `get_skill` 输入 `{ name: string }`;输出 `{ skill }`。
- `install_skill` 输入 `{ name: string }`;输出 `{ name, sourceDir, recommendedTargets, selectedByAiPolicy, steps, note }`。

## Test Plan
- 运行 `pnpm run typecheck`。
- 运行 `pnpm run build`。
- 可选用 MCP Inspector 手动调用 `list_skills`、`get_skill`、`install_skill` 检查返回结构。

## Assumptions
- “安装”仍为说明式安装,不写入用户全局 skill 目录。
- `install_skill` 不提供 `targetDir` 参数,目标位置由调用方 AI 根据当前提示词和环境线索判断。
- 测试 skill 目录名使用 `prompt-enhancer`,正文使用中文。

开发完成后执行命令测试:

npx @modelcontextprotocol/inspector node dist/index.js

在运行界面下,执行下工具查看是否有效: Snipaste_2026-06-15_16-21-16

在Agent上使用MCP服务

最简单的安装方式就是在项目下直接告诉Agent进行安装

请将当前打包后的mcp服务安装到codex的全局mcp服务中

或者在codex ui 界面下手动配置

78cf4d53bb1b4ca48d15abbbf8de1726

之后重启下,测试: Snipaste_2026-06-16_09-39-51 Snipaste_2026-06-16_09-40-06

安装下mcp上的skill: Snipaste_2026-06-16_09-57-20

安装后再重启测试下: Snipaste_2026-06-16_09-58-41 Snipaste_2026-06-16_10-02-17

当然,这个skill还需要改进优化,这里能生效说明已经成功了,在本地创建mcp服务以及skill的管理基本就是这样,接下就是通过需要进行线上部署的相关开发。

Streamable HTTP模式

$prompt-optimizer 将当前的mcp服务拆分为stdio模式与http模式,stdio与http模式的边界必须尽可能区分,必要时可创建不同的文件进行拆分

同时兼容了两种模式: Snipaste_2026-06-16_16-56-45

先卸载之前安装的mcp后,先在本地运行:

pnpm start:http

添加到agent上的mcp服务器中

为codex添加mcp服务:gu-mcp,请求地址为http://127.0.0.1:3369/mcp

重启后测试下: Snipaste_2026-06-16_17-29-56 同时可以看到控制台会有日志连接的日志输出: Snipaste_2026-06-16_17-30-07 最后测试下skill,同样安装后需要重启: Snipaste_2026-06-16_17-33-54 Snipaste_2026-06-16_17-45-43

部署到服务器上

这里以部署到阿里云ESC为例,有关服务器环境准备等内容这里不做描述,可参考文章项目部署中的准备工作以及后端服务的部署内容。

生成pm2配置文件

根据当前项目结构内容,在当前项目的根目录生成ecosystem.configjs的pm2配置文件,包含日志处理方式
import { mkdirSync } from 'node:fs';
import { dirname, join } from 'node:path';
import { fileURLToPath } from 'node:url';

// rootDir 标记项目根目录,避免 PM2 从其他目录启动时路径漂移。
const rootDir = dirname(fileURLToPath(import.meta.url));

// logDir 集中保存 PM2 日志,配置加载时确保目录已存在。
const logDir = join(rootDir, 'logs', 'pm2');

mkdirSync(logDir, { recursive: true });

// apps 是 PM2 ecosystem 的应用列表;命名导出可兼容 type: module 项目中的 ecosystem.config.js。
export const apps = [
  {
    // HTTP 模式可由 PM2 常驻托管;stdio 模式需要 MCP 客户端直接接管标准输入输出。
    name: 'gu-mcp-http',
    cwd: rootDir,
    script: './dist/http.js',
    interpreter: 'node',
    exec_mode: 'fork',
    instances: 1,
    autorestart: true,
    watch: false,
    max_memory_restart: '256M',
    kill_timeout: 5000,

    // 项目运行日志写入 stderr;error_file 是主要应用日志,out_file 仅用于兜底异常 stdout。
    out_file: join(logDir, 'gu-mcp-http.out.log'),
    error_file: join(logDir, 'gu-mcp-http.error.log'),
    log_file: join(logDir, 'gu-mcp-http.combined.log'),
    merge_logs: true,
    log_date_format: 'YYYY-MM-DD HH:mm:ss.SSS Z',

    env: {
      NODE_ENV: 'production',
    },
  },
];

部署项目并启动

# 进入 opt 目录
cd /opt

# 克隆项目代码
git clone <您的项目仓库URL> gu-mcp

# 进入项目目录
cd gu-mcp

# 安装依赖
pnpm i

# 打包
pnpm build

# 启动
pm2 start ecosystem.config.js

nginx转发到域名地址

	server {
		listen 443 ssl;
		server_name www.gujianruchu.cn;
		# ...证书配置

		location = /mcp {
			proxy_pass http://127.0.0.1:3000;

			proxy_http_version 1.1;
			proxy_set_header Connection "";

			proxy_set_header Host $host;
			proxy_set_header X-Real-IP $remote_addr;
			proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
			proxy_set_header X-Forwarded-Proto $scheme;

			proxy_buffering off;
			proxy_cache off;
			proxy_read_timeout 3600s;
			proxy_send_timeout 3600s;
		}

		location = /mcp/ {
			return 308 /mcp;
		}
	}

启动nginx:

# 启动
systemctl start nginx
# 重启
systemctl restart nginx

安装到codex中测试下:

为codex添加mcp服务:gu-mcp,请求地址为https://www.gujianruchu.cn/mcp

Snipaste_2026-06-17_10-33-35 screenshot_2026-06-17_10-48-08