@nothumanwork/cursor-agents-sdk
v0.7.0
Published
Typed Node-friendly utilities for driving the Cursor Agent CLI programmatically.
Readme
Cursor Agents SDK
Typed, Node-friendly helpers for driving the cursor-agent CLI in automation, CI, or custom developer tools. The SDK keeps parity with the documentation inside ./cursor-cli, exposing:
CursorAgent– spawns the CLI with safe defaults, structured JSON output, streaming NDJSON parsing, andAbortSignalcancellation.buildCursorAgentCommand– deterministic CLI argument construction (always pairs--print+--output-format).CursorStreamEventSchema/CursorJsonResultSchema– Zod validators aligned with Cursor's documented output, including tool call events.
Installation
npm install @nothumanlabs/cursor-agents-sdk
# or
pnpm add @nothumanlabs/cursor-agents-sdk
# or
bun add @nothumanlabs/cursor-agents-sdkThe install script downloads the latest published cursor-agent binary from
https://downloads.cursor.com/lab. The command is linked as the package
"bin", so npx cursor-agent, pnpm exec cursor-agent, or bunx cursor-agent
will launch the vendored CLI without additional setup.
Environment toggles:
| Variable | Description |
| --- | --- |
| CURSOR_AGENT_SDK_VERSION | Override the binary version tag (default: 2025.10.22-f894c20). |
| CURSOR_AGENT_SDK_BASE_URL | Override the download base URL. |
| CURSOR_AGENT_SDK_FORCE=1 | Force re-downloading the binary even if cached. |
| CURSOR_AGENT_SDK_SKIP=1 | Skip the download (useful for CI with cached vendor folders). |
| CURSOR_AGENT_SDK_STRICT=1 | Fail the install if checksum retrieval or verification fails. |
| CURSOR_AGENT_SDK_BIN_NAME | Customize the binary name written to the manifest. |
Manifest metadata is written to vendor/manifest.json. Programmatic consumers
can read the manifest or resolve the executable location with
resolveCursorAgentBinaryPath().
Usage
import {
CursorAgent,
type CursorAgentGenerateOptions,
parseCursorEventLine,
} from "cursor-agents-sdk";
const agent = new CursorAgent({
// apiKey defaults to process.env.CURSOR_API_KEY when omitted
defaultModel: "sonnet-4",
});
const result = await agent.generate({
prompt: "Summarize CONTRIBUTING.md",
chatId: "previous-session-id", // optional resume
});
console.log(result.result);
for await (const event of agent.stream({
prompt: "Review the staged diff for security issues",
streamPartialOutput: true,
})) {
if (event.type === "assistant") {
console.log(event.message.content[0]?.text);
}
}If you only need the CLI command, reuse the builder:
import { spawn } from "node:child_process";
import { buildCursorAgentCommand } from "cursor-agents-sdk";
const command = buildCursorAgentCommand(
{ forceWrites: true },
{ prompt: "apply the diff", outputFormat: "json" },
);
await new Promise<void>((resolve, reject) => {
const child = spawn(command[0], command.slice(1), { stdio: "inherit" });
child.once("error", reject);
child.once("close", (code) => {
if (code === 0) {
resolve();
} else {
reject(new Error(`cursor-agent exited with code ${code ?? "unknown"}`));
}
});
});To delegate to the binary directly, resolve the vendored path via the manifest:
import { spawn } from "node:child_process";
import { resolveCursorAgentBinaryPath } from "cursor-agents-sdk";
const cursorAgentPath = await resolveCursorAgentBinaryPath();
await new Promise<void>((resolve, reject) => {
const child = spawn(cursorAgentPath, ["status"], { stdio: "inherit" });
child.once("error", reject);
child.once("close", (code) => {
if (code === 0) {
resolve();
} else {
reject(new Error(`cursor-agent exited with code ${code ?? "unknown"}`));
}
});
});Development
| Task | Command |
| --- | --- |
| Install deps + generate dist | bun install |
| Type-check & emit types | bun run build:types |
| Bundle JS + declarations | bun run build |
| Lint / format | bun run lint / bun run format |
| Tests | bun test |
Git hooks (via simple-git-hooks) run bun run lint && bun test before each commit, keeping the publish artifact (dist/**) in sync with src/**.
The repo follows TDD by default: add or adjust tests (*.test.ts) before changing implementation, especially when reflecting new Cursor CLI behaviors documented in ./cursor-cli.
## Changelog ### 28/10/2025 - Migration to NodeJS compatibility The library was heavily reliant on Bun's Javascript runtime, causing some severe incompatibility issues with environments where Bun won't natively run (e.g. Cloudflare Workers, Vercel...)
Removed dependencies on Bun's native features (i.e. Bun.spawn, subprocess, env...). Migrating to using Node libraries.
examples/showcase.mjs- can be run usingnode examples/showcase.mjsand it uses the built (to target Node) version of the library indist/index.js
