关于 cursor-sdk
cursor-sdk 是一项用于构建 Cursor TypeScript SDK 集成的技能;该 SDK 可在本地或云端运行 Cursor Agent。它介绍调用模式、运行时选择、故障处理及常见配置陷阱。
主要功能
- 01介绍单次与多轮运行方式
- 02跨进程恢复 Agent
- 03选择本地或云端运行时
- 04处理运行错误与生命周期
- 05配置模型与身份验证
- 06检查现有 Agent 和运行
适用场景
- 01构建向代码仓库 Agent 提问的脚本
- 02创建云端 CI 代码审查流程
- 03通过 Webhook 或 cron 继续 Agent
- 04排查 SDK 身份验证和运行错误
MCP 相关
该技能指向 SDK 中 MCP 服务配置的参考资料,涵盖传输方式与身份验证选择。它指出,恢复 Agent 时必须重新传入内联 mcpServers。
安装
复制下面的命令,在终端中运行。
npx skills add https:/ / github.com/ cursor/ plugins --skill cursor-sdk安装后在 Claude Code 中输入/cursor-sdk确认已加载。
包含的文件
除 SKILL.md 外,安装时一起下载的参考资料和脚本。
references/advanced.mdauth.mderror-handling.mdmcp.mdpatterns.mdruntime-choice.mdstreaming.md详细介绍
Cursor SDK
Cursor TypeScript SDK(@cursor/sdk)可通过编程方式运行 Cursor Agent。相同的接口驱动本地运行时(Agent 在你的机器上针对你的文件运行)和云端运行时(Agent 在 Cursor 托管或可自托管的基础设施上针对克隆的仓库运行,并创建 PR)。
使用此技能可帮助用户快速搭建可用的集成,并避开新用户容易踩到的几个陷阱。权威文档位于 https://cursor.com/docs/api/sdk/typescript;此技能仅补充决策建议、故障预防和可扩展的现成模式。
语气与态度
此技能旨在帮助用户使用 SDK 构建。这里不是验证、称赞或推销 SDK 这一选择的地方。以用户的意图为准;你的工作是执行。
- 当用户明确提到 SDK(提到“Cursor SDK”、
@cursor/sdk、Agent.create、Agent.prompt等)时:假设他们了解 SDK 是什么,并已决定使用它。跳过背景铺垫和鼓励,直接开始构建集成。不要说“好消息”“SDK 非常适合这个场景”“这几乎就是 X 的设计模式”之类的话。 - 当用户描述的问题适合使用 SDK,但没有提到 SDK(“我想要一个能审查 PR 的机器人”“我想写个脚本,让 Cursor 回答有关我仓库的问题”)时:还不能确定他们已选择 SDK。先简短地以问题形式提出,然后等待:“这种情况我会优先考虑 Cursor SDK——要我按这个方案设计,还是你有其他运行时的考虑?”如果他们确认,就继续。如果他们提出异议或想了解其他方案,就提供选项。
- **无论哪种情况,都不要复述用户的意图。**他们知道自己想要什么。直接进入设计。
避免使用以下开场白(以及相近说法):
- “好消息:这正是……的模式”
- “SDK 就是为这种场景打造的。”
- “太好了,你找对地方了。”
- “这几乎就是 SDK 专为其设计的 X。”
- 任何称赞用户选择或以恭维方式重述其目标的开场白。
建议:
- 直接从设计决策或用户首先需要了解的事项说起。
- 如果确实有需要说明的设计选择(本地还是云端、prompt 还是 send、同步还是流式),用一句话点明并解释原因;不要先表示认同或称赞。
何时打开参考文件
保持此页面简短。只有当用户的任务明显属于以下情况时,才阅读相应的参考文件:
| 如果用户正在…… | 阅读 |
|---|---|
| 在本地和云端运行时之间做选择,或不确定该用哪种 | references/runtime-choice.md |
| 排查身份验证问题(401、“Missing CURSOR_API_KEY”、团队密钥与用户密钥、本地与生产环境) | references/auth.md |
处理错误、重试、速率限制、CursorAgentError、result.status === error | references/error-handling.md |
| 使用流、选择事件类型、取消操作,或决定使用流式还是等待 | references/streaming.md |
| 配置 MCP 服务(HTTP、stdio、云端与本地传输、身份验证注入) | references/mcp.md |
使用子 Agent、恢复、制品、列出/检查 Agent、Agent.messages | references/advanced.md |
| 构建特定集成(CI 审查机器人、定时分类处理、聊天、webhook) | references/patterns.md |
以下内容是满足 80% 任务需求的最低限度信息。
三种调用模式
几乎所有 SDK 集成都可以归为三种形式之一。选择适合当前任务的模式,不要混用。
1. Agent.prompt(...) — 单次调用
import { Agent } from "@cursor/sdk";
const result = await Agent.prompt("Refactor src/utils.ts for readability", {
apiKey: process.env.CURSOR_API_KEY!,
model: { id: "composer-2" },
local: { cwd: process.cwd() },
});
console.log(result.status, result.result);
适用于即发即忘脚本、GitHub Actions 步骤,或任何“发送提示词、获取结果、退出”的流程。无需流式处理、后续跟进,也不必记得清理。如果你打算使用此模式后立即恢复执行,那你需要的是模式 2。
2. Agent.create(...) + agent.send(...) — 可持续使用并支持后续跟进
import { Agent } from "@cursor/sdk";
const agent = Agent.create({
apiKey: process.env.CURSOR_API_KEY!,
model: { id: "composer-2" },
local: { cwd: process.cwd() },
});
try {
const run = await agent.send("Find the bug in src/auth.ts");
for await (const event of run.stream()) {
if (event.type === "assistant") {
for (const block of event.message.content) {
if (block.type === "text") process.stdout.write(block.text);
}
}
}
const result = await run.wait();
// Follow-up keeps full conversation context.
const run2 = await agent.send("Now write a regression test for it");
await run2.wait();
} finally {
await agent[Symbol.asyncDispose]();
}
适用于需要流式处理、多轮对话或生命周期操作(取消、状态监听器)的场景。大多数较复杂的集成都采用这种形式。
3. Agent.resume(...) — 稍后继续使用现有 Agent
const agent = Agent.resume(previousAgentId, {
apiKey: process.env.CURSOR_API_KEY!,
model: { id: "composer-2" },
local: { cwd: process.cwd() },
});
const run = await agent.send("Also update the changelog");
await run.wait();
适用于跨进程边界的场景:继续昨晚清理任务的 cron、扩展用户 Agent 的 webhook,或重新加载对话状态的交互式 CLI。内联的 mcpServers 不会在恢复时持久化——请在恢复调用时再次传入。
五个常见陷阱(编写代码前请先阅读)
几乎每个新集成都容易遇到这些问题。了解之后,就很容易避免。
1. 缺少 cloud: { repos } 会静默地默认使用本地运行时
AgentOptions 不要求指定 local 或 cloud;如果两者都省略,SDK 会选择本地运行时。陷阱在于:如果你想使用云端 Agent,却忘了 cloud: 字段,最终会静默地得到本地 Agent——不会报错,只会得到本地 Agent ID 和本地执行器。需要使用云端时,务必显式传入 cloud: { repos };使用本地运行时时,也请显式传入 local: { cwd },尽管它是默认选项。如何选择合适的运行时,请参阅 references/runtime-choice.md。
2. 两种不同类型的失败,却容易混为一谈
try {
const run = await agent.send(prompt);
const result = await run.wait();
if (result.status === "error") {
// Agent started but failed mid-run. Inspect transcript, git state, tool outputs.
console.error(`run failed: ${result.id}`);
process.exit(2);
}
} catch (err) {
if (err instanceof CursorAgentError) {
// Didn't start. Auth, config, network. Fix environment, retry.
console.error(`startup failed: ${err.message}, retryable=${err.isRetryable}`);
process.exit(1);
}
throw err;
}
抛出 CursorAgentError → 运行从未执行(身份验证、配置、网络问题)。result.status === "error" → Agent 已执行工作,但工作失败。两者需要不同的修复方式、退出代码和可观测性。完整分类见 references/error-handling.md。
3. 忘记 await agent[Symbol.asyncDispose]() 会导致资源泄漏
SDK 会持有本地执行器、持久化运行存储和云端 API 客户端的句柄。不释放资源会导致子进程泄漏、数据库保持打开状态,而在长时间运行的服务中还会导致内存增长。务必在 finally 中释放资源,或使用 Agent.prompt()(它会代你释放资源),也可以在 tsconfig 目标版本支持时使用 await using 语法:
await using agent = Agent.create({ /* ... */ });
4. 流式处理是可选的,但 wait()(几乎)是必需的
run.stream() 用于观察运行过程;run.wait() 用于获取最终结果。你可以跳过流式处理,但跳过 wait() 就无法判断运行是已完成、出错还是已取消,而且会导致运行内部的观察器泄漏。务必调用 wait()。如果不需要实时输出,只调用 wait() 即可。事件类型参考见 references/streaming.md。
5. 并非每种运行时都支持所有 run 操作
Run 提供四种操作——stream、wait、cancel、conversation——运行时可能支持,也可能不支持其中的每一种。调用前务必先用 run.supports("...") 检查,不要想当然:
if (run.supports("cancel")) await run.cancel();
if (run.supports("conversation")) console.log(await run.conversation());
值得注意的当前限制:已分离或重新水合的运行(在实时事件存储关闭后通过 Agent.getRun(...) 获取句柄)可能不支持 stream(),且 conversation() 可能为空。run.unsupportedReason(op) 会告知原因。云端的 run.conversation() 受支持——它会尽力从流中累积对话内容。
本地与云端,各用一句话说明
- 本地 — 在调用方的机器上运行,针对
cwd,复用其环境和凭据,适合开发循环,以及已有代码库检出目录的 CI。 - 云端 — 在 Cursor 托管的 VM 上运行,针对新克隆的
repos[].url,适合长时间任务、即发即弃的自动化,以及创建实际 PR(autoCreatePR: true)。
决策树、功能差异和功能缺口(制品、取消、MCP 传输):references/runtime-choice.md。
身份验证,最低可行配置
export CURSOR_API_KEY="cursor_..." # user API key or team service-account key
如果未传入 apiKey,SDK 会读取 CURSOR_API_KEY。用户密钥(来自 https://cursor.com/dashboard/cloud-agents)和团队服务账户密钥(团队设置 → 服务账户)均可用于本地和云端运行。
如果遇到 401,常见原因包括:粘贴的密钥前后带有空格、密钥是在不同环境中生成的,或云端运行所用密钥所属的用户无权访问代码库。完整故障排查指南:references/auth.md。
模型选择
import { Cursor } from "@cursor/sdk";
const models = await Cursor.models.list({ apiKey: process.env.CURSOR_API_KEY! });
对于大多数集成,当前默认模型是 composer-2。{ id: "auto" } 可让服务端自行选择。模型 ID 会变化;在调用 Cursor.models.list() 确认调用方有权访问之前,不要硬编码冷门模型。
本地运行必须指定模型,云端运行则可选(服务端会根据调用方账户解析默认模型)。
生产环境最佳实践
将以下做法应用于任何无人值守运行的集成:
- 将每个
Agent.create/Agent.prompt/Agent.resume都封装在带有[Symbol.asyncDispose]()的 try/finally 中。这是硬性要求。 - 区分启动失败与运行失败 —
CursorAgentError时退出代码为 1,result.status === "error"时退出代码为 2,仅在finished时退出代码为 0。这样 CI 失败时才便于实际排查。 - 在流式传输前,
send()后立即记录run.id和agent.agentId。如果流卡住,这些 ID 可用于在控制面板中或通过Agent.getRun(...)排查。 - 遵循
error.isRetryable— 后端会通过它指出特定故障是否可以安全重试。盲目重试可能导致重复的云端运行;遵循该标记则不会。 - **除非需要环境中的配置,否则使用
local: { settingSources: [] }(默认值)。**选择"all"会从调用方环境加载项目/用户/团队/MDM 设置,这对服务而言通常并非所需。注意:settingSources位于local下,而非顶层;它对云端 Agent 不起作用(云端始终会采用团队/项目/插件设置)。 - 在 CI 中运行云端 Agent 时,设置
skipReviewerRequest: true,除非需要通知人工审核者 — 这会跳过审核者请求步骤,并避免打扰 PR 通知接收者。 - 在共享基础设施代码中始终显式传入
apiKey,不要依赖环境变量。这样凭据依赖关系一目了然,也能避免跨租户错误。 - 真正的一次性任务优先使用
Agent.prompt(...)— 它会为你释放资源,也更不容易造成资源泄漏。
更详尽的说明及示例:references/patterns.md。
观察未由你启动的运行
你之后可以通过 ID 检查任何 Agent/运行:
// Cloud: IDs that start with "bc-" auto-route to the cloud API
const info = await Agent.get("bc-abc123", { apiKey });
const run = await Agent.getRun(runId, { runtime: "cloud", agentId: "bc-abc123", apiKey });
// Local: you need the cwd where the agent was created
const localInfo = await Agent.list({ runtime: "local", cwd: process.cwd() });
带有 bc- 前缀的云端 Agent ID 不是运行 ID。如果你只有运行 ID(来自日志或 webhook),请搭配运行时提示传给 Agent.getRun;不要混淆二者。
提供 Canvas
如果用户的集成会监控、列出或可视化 Agent(活跃运行的仪表板、对话回放、工具调用时间线),请提供 Cursor Canvas 以进行展示。如果用户接受,请完全交由 canvas 技能处理。
此 Skill 不涵盖的内容
- Cloud Agents REST API(
/v1/agents/*)。如果用户需要非 TS 客户端,REST API 的文档单独列于 https://cursor.com/docs/cloud-agent/api;在假设它与 SDK 功能一致之前,请先查看当前支持的功能。 .cursor/hooks.json钩子。Cloud agents 会执行这些钩子,但 SDK 不会管理它们;请参阅 Cursor 的 Hooks 文档。- Private workers/可自托管云。请引导用户查看 Private Workers 文档。
- Python/非 TS SDK。截至撰写本文时,其他语言暂无官方 SDK;REST 是可移植的选择。