@cursor/july 0.1.99 → 0.1.100
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/AGENTS.md +4 -2
- package/dist/channels/github/defaults.d.ts.map +1 -1
- package/dist/channels/github/defaults.js +28 -3
- package/dist/channels/github/progress.d.ts +7 -0
- package/dist/channels/github/progress.d.ts.map +1 -1
- package/dist/channels/slack/api.d.ts +16 -7
- package/dist/channels/slack/api.d.ts.map +1 -1
- package/dist/channels/slack/api.js +29 -13
- package/dist/channels/slack/constants.d.ts +6 -0
- package/dist/channels/slack/constants.d.ts.map +1 -1
- package/dist/channels/slack/constants.js +6 -0
- package/dist/channels/slack/defaults.d.ts +9 -4
- package/dist/channels/slack/defaults.d.ts.map +1 -1
- package/dist/channels/slack/defaults.js +154 -76
- package/dist/channels/slack/dispatch.d.ts.map +1 -1
- package/dist/channels/slack/dispatch.js +3 -3
- package/dist/channels/slack/inbound.d.ts +9 -0
- package/dist/channels/slack/inbound.d.ts.map +1 -1
- package/dist/channels/slack/inbound.js +14 -0
- package/dist/channels/slack/index.d.ts +1 -0
- package/dist/channels/slack/index.d.ts.map +1 -1
- package/dist/channels/slack/index.js +1 -0
- package/dist/channels/slack/live-delivery.d.ts +5 -0
- package/dist/channels/slack/live-delivery.d.ts.map +1 -1
- package/dist/channels/slack/live-delivery.js +107 -19
- package/dist/channels/slack/reasoning-card.d.ts +38 -0
- package/dist/channels/slack/reasoning-card.d.ts.map +1 -0
- package/dist/channels/slack/reasoning-card.js +104 -0
- package/dist/channels/slack/redact.d.ts +2 -0
- package/dist/channels/slack/redact.d.ts.map +1 -0
- package/dist/channels/slack/redact.js +5 -0
- package/dist/channels/slack/reply-options.d.ts +40 -0
- package/dist/channels/slack/reply-options.d.ts.map +1 -0
- package/dist/channels/slack/reply-options.js +150 -0
- package/dist/channels/slack/slack-channel.d.ts.map +1 -1
- package/dist/channels/slack/slack-channel.js +8 -4
- package/dist/channels/slack/stream.d.ts +22 -10
- package/dist/channels/slack/stream.d.ts.map +1 -1
- package/dist/channels/slack/stream.js +9 -16
- package/dist/channels/slack/tool-cards.d.ts +22 -0
- package/dist/channels/slack/tool-cards.d.ts.map +1 -0
- package/dist/channels/slack/tool-cards.js +178 -0
- package/dist/channels/slack/types.d.ts +145 -6
- package/dist/channels/slack/types.d.ts.map +1 -1
- package/dist/docs/404.html +2 -2
- package/dist/docs/ab.html +6 -6
- package/dist/docs/ab.md +1 -1
- package/dist/docs/assets/{ab.md.DJo5r4R-.js → ab.md.mlVgqvSk.js} +1 -1
- package/dist/docs/assets/{app.BplEAZ3S.js → app.DZ1e0Ycq.js} +1 -1
- package/dist/docs/assets/{building-with-agents.md.DI4mEzlt.js → building-with-agents.md.CUSWxlP_.js} +2 -2
- package/dist/docs/assets/chunks/@localSearchIndexroot.j70vvPL4.js +1 -0
- package/dist/docs/assets/chunks/{VPLocalSearchBox.CHXyv4wP.js → VPLocalSearchBox.l8omwc6D.js} +1 -1
- package/dist/docs/assets/chunks/{theme.BTcsZmjQ.js → theme.JVcD6gel.js} +2 -2
- package/dist/docs/assets/{evals.md.lfJoEVc8.js → evals.md.CPzDAwoH.js} +1 -1
- package/dist/docs/assets/{guides_github.md.Cnh2mL4a.js → guides_github.md.BtPr9GaP.js} +1 -1
- package/dist/docs/assets/{guides_mcp-oauth.md.CN-6YmTJ.js → guides_mcp-oauth.md.Dp6cDP7f.js} +1 -1
- package/dist/docs/assets/{guides_opentelemetry.md.bmPmkvJu.js → guides_opentelemetry.md.BVTXDCRg.js} +2 -2
- package/dist/docs/assets/{guides_slack.md.VDXQV3ja.js → guides_slack.md.9oHPye9o.js} +19 -3
- package/dist/docs/assets/{guides_slack.md.VDXQV3ja.lean.js → guides_slack.md.9oHPye9o.lean.js} +1 -1
- package/dist/docs/assets/hillclimbing.md.CpTGTCle.js +4 -0
- package/dist/docs/assets/{index.md.CVeRUOeZ.js → index.md.Bb4k8kUm.js} +1 -1
- package/dist/docs/assets/{quickstart.md.Nj_LjW_a.js → quickstart.md.DdQOF7Y8.js} +1 -1
- package/dist/docs/assets/{reference_connections.md.DxldvyIB.js → reference_connections.md.BiGoBAk2.js} +1 -1
- package/dist/docs/assets/scaffolding-agents.md.em43xlY1.js +1 -0
- package/dist/docs/assets/skills_ab.md.CsFNatVx.js +26 -0
- package/dist/docs/assets/skills_ab.md.CsFNatVx.lean.js +1 -0
- package/dist/docs/assets/skills_create-agent.md.BVoWPcan.js +8 -0
- package/dist/docs/assets/skills_create-agent.md.BVoWPcan.lean.js +1 -0
- package/dist/docs/assets/skills_debug.md.CDbPhHfg.js +1 -0
- package/dist/docs/assets/skills_debug.md.CDbPhHfg.lean.js +1 -0
- package/dist/docs/assets/skills_evals.md.723kpUmA.js +25 -0
- package/dist/docs/assets/skills_evals.md.723kpUmA.lean.js +1 -0
- package/dist/docs/assets/skills_framework-map.md.BTi817yv.js +1 -0
- package/dist/docs/assets/skills_framework-map.md.BTi817yv.lean.js +1 -0
- package/dist/docs/assets/skills_github.md.D0JahM8c.js +16 -0
- package/dist/docs/assets/skills_github.md.D0JahM8c.lean.js +1 -0
- package/dist/docs/assets/skills_hillclimb.md.B_zJerxA.js +7 -0
- package/dist/docs/assets/skills_hillclimb.md.B_zJerxA.lean.js +1 -0
- package/dist/docs/assets/skills_index.md.DKwIxzGg.js +1 -0
- package/dist/docs/assets/skills_index.md.DKwIxzGg.lean.js +1 -0
- package/dist/docs/assets/skills_mcp-auth.md.DGvFP3HE.js +18 -0
- package/dist/docs/assets/skills_mcp-auth.md.DGvFP3HE.lean.js +1 -0
- package/dist/docs/assets/skills_otel.md.CgiZryR3.js +8 -0
- package/dist/docs/assets/skills_otel.md.CgiZryR3.lean.js +1 -0
- package/dist/docs/assets/skills_setup-slack.md.BBgx8lUz.js +20 -0
- package/dist/docs/assets/skills_setup-slack.md.BBgx8lUz.lean.js +1 -0
- package/dist/docs/assets/{troubleshooting.md.DCiPBhYs.js → troubleshooting.md.Cus_YZga.js} +1 -1
- package/dist/docs/building-with-agents.html +6 -6
- package/dist/docs/building-with-agents.md +14 -11
- package/dist/docs/concepts.html +4 -4
- package/dist/docs/deployment.html +4 -4
- package/dist/docs/evals.html +6 -6
- package/dist/docs/evals.md +1 -1
- package/dist/docs/guides/agent-to-agent.html +4 -4
- package/dist/docs/guides/cloud-runtime.html +4 -4
- package/dist/docs/guides/convert-automation.html +4 -4
- package/dist/docs/guides/github.html +5 -5
- package/dist/docs/guides/github.md +1 -1
- package/dist/docs/guides/human-in-the-loop.html +4 -4
- package/dist/docs/guides/mcp-oauth.html +5 -5
- package/dist/docs/guides/mcp-oauth.md +1 -1
- package/dist/docs/guides/opentelemetry.html +7 -7
- package/dist/docs/guides/opentelemetry.md +2 -2
- package/dist/docs/guides/slack.html +22 -6
- package/dist/docs/guides/slack.md +80 -1
- package/dist/docs/guides/webhooks.html +5 -5
- package/dist/docs/hashmap.json +1 -1
- package/dist/docs/hillclimbing.html +6 -6
- package/dist/docs/hillclimbing.md +5 -5
- package/dist/docs/index.html +6 -6
- package/dist/docs/index.md +1 -1
- package/dist/docs/llms-full.txt +1041 -30
- package/dist/docs/llms.txt +14 -0
- package/dist/docs/quickstart.html +5 -5
- package/dist/docs/quickstart.md +1 -1
- package/dist/docs/reference/agent-config.html +4 -4
- package/dist/docs/reference/artifacts.html +4 -4
- package/dist/docs/reference/channels.html +4 -4
- package/dist/docs/reference/cli.html +4 -4
- package/dist/docs/reference/connections.html +6 -6
- package/dist/docs/reference/connections.md +1 -1
- package/dist/docs/reference/hooks.html +4 -4
- package/dist/docs/reference/http-api.html +4 -4
- package/dist/docs/reference/instructions.html +4 -4
- package/dist/docs/reference/playground.html +4 -4
- package/dist/docs/reference/project-layout.html +4 -4
- package/dist/docs/reference/prompt.html +4 -4
- package/dist/docs/reference/schedules.html +4 -4
- package/dist/docs/reference/sessions.html +4 -4
- package/dist/docs/reference/skills.html +4 -4
- package/dist/docs/reference/subagents.html +4 -4
- package/dist/docs/reference/tools.html +4 -4
- package/dist/docs/scaffolding-agents.html +5 -5
- package/dist/docs/scaffolding-agents.md +3 -3
- package/dist/docs/skills/ab.html +52 -0
- package/dist/docs/skills/ab.md +50 -0
- package/dist/docs/skills/create-agent.html +34 -0
- package/dist/docs/skills/create-agent.md +160 -0
- package/dist/docs/skills/debug.html +27 -0
- package/dist/docs/skills/debug.md +36 -0
- package/dist/docs/skills/evals.html +51 -0
- package/dist/docs/skills/evals.md +99 -0
- package/dist/docs/skills/framework-map.html +27 -0
- package/dist/docs/skills/framework-map.md +95 -0
- package/dist/docs/skills/github.html +42 -0
- package/dist/docs/skills/github.md +93 -0
- package/dist/docs/skills/hillclimb.html +33 -0
- package/dist/docs/skills/hillclimb.md +55 -0
- package/dist/docs/skills/index.html +27 -0
- package/dist/docs/skills/index.md +21 -0
- package/dist/docs/skills/mcp-auth.html +44 -0
- package/dist/docs/skills/mcp-auth.md +76 -0
- package/dist/docs/skills/otel.html +34 -0
- package/dist/docs/skills/otel.md +48 -0
- package/dist/docs/skills/setup-slack.html +46 -0
- package/dist/docs/skills/setup-slack.md +141 -0
- package/dist/docs/storage.html +4 -4
- package/dist/docs/templates/agentic-owners.html +4 -4
- package/dist/docs/templates/agents-md.html +4 -4
- package/dist/docs/templates/code-wiki.html +4 -4
- package/dist/docs/templates/demo.html +4 -4
- package/dist/docs/templates/pr-autofixer.html +4 -4
- package/dist/docs/templates/security-help.html +4 -4
- package/dist/docs/templates/security-reviewer.html +4 -4
- package/dist/docs/templates/triage.html +4 -4
- package/dist/docs/troubleshooting.html +5 -5
- package/dist/docs/troubleshooting.md +1 -1
- package/dist/files-backends/cursor-hosted.d.ts +6 -0
- package/dist/files-backends/cursor-hosted.d.ts.map +1 -1
- package/dist/files-backends/cursor-hosted.js +6 -9
- package/dist/internal/cli-deploy.js +2 -2
- package/dist/internal/conversation-mirror.d.ts.map +1 -1
- package/dist/internal/conversation-mirror.js +3 -4
- package/dist/internal/cursor/hosted-store-secrets.d.ts +15 -0
- package/dist/internal/cursor/hosted-store-secrets.d.ts.map +1 -0
- package/dist/internal/cursor/hosted-store-secrets.js +48 -0
- package/dist/internal/deploy-client.d.ts +6 -6
- package/dist/internal/deploy-client.js +7 -7
- package/dist/internal/discovery.d.ts.map +1 -1
- package/dist/internal/discovery.js +11 -1
- package/dist/internal/framework-file-storage.d.ts +12 -5
- package/dist/internal/framework-file-storage.d.ts.map +1 -1
- package/dist/internal/framework-file-storage.js +36 -5
- package/dist/internal/framework-storage-selection.d.ts +12 -12
- package/dist/internal/framework-storage-selection.d.ts.map +1 -1
- package/dist/internal/framework-storage-selection.js +33 -39
- package/dist/internal/session-run-log.d.ts +3 -3
- package/dist/internal/session-run-log.d.ts.map +1 -1
- package/dist/internal/session-run-log.js +6 -7
- package/dist/internal/storage-coordinator.d.ts +0 -6
- package/dist/internal/storage-coordinator.d.ts.map +1 -1
- package/dist/internal/storage-coordinator.js +1 -9
- package/dist/playground/assets/index-BszoQDc6.css +1 -0
- package/dist/playground/assets/{index-jzNbJENa.js → index-DVs98vPL.js} +1 -1
- package/dist/playground/index.html +2 -2
- package/dist/storage-backends/cursor-hosted-v2.d.ts +83 -0
- package/dist/storage-backends/cursor-hosted-v2.d.ts.map +1 -0
- package/dist/storage-backends/cursor-hosted-v2.js +164 -0
- package/dist/storage-backends/cursor-hosted.d.ts +6 -0
- package/dist/storage-backends/cursor-hosted.d.ts.map +1 -1
- package/dist/storage-backends/cursor-hosted.js +6 -1
- package/dist/types.d.ts +5 -0
- package/dist/types.d.ts.map +1 -1
- package/docs/README.md +1 -1
- package/docs/ab.md +1 -1
- package/docs/building-with-agents.md +14 -11
- package/docs/evals.md +1 -1
- package/docs/guides/github.md +1 -1
- package/docs/guides/mcp-oauth.md +1 -1
- package/docs/guides/opentelemetry.md +2 -2
- package/docs/guides/slack.md +80 -1
- package/docs/hillclimbing.md +5 -5
- package/docs/quickstart.md +1 -1
- package/docs/reference/connections.md +1 -1
- package/docs/scaffolding-agents.md +3 -3
- package/docs/skills/index.md +26 -0
- package/docs/troubleshooting.md +1 -1
- package/package.json +1 -1
- package/src/channels/github/defaults.ts +36 -3
- package/src/channels/github/progress.ts +7 -0
- package/src/channels/slack/api.ts +35 -17
- package/src/channels/slack/constants.ts +6 -0
- package/src/channels/slack/defaults.ts +173 -92
- package/src/channels/slack/dispatch.ts +8 -1
- package/src/channels/slack/inbound.ts +17 -0
- package/src/channels/slack/index.ts +1 -0
- package/src/channels/slack/live-delivery.ts +131 -20
- package/src/channels/slack/reasoning-card.ts +140 -0
- package/src/channels/slack/redact.ts +6 -0
- package/src/channels/slack/reply-options.ts +229 -0
- package/src/channels/slack/slack-channel.ts +7 -2
- package/src/channels/slack/stream.ts +31 -24
- package/src/channels/slack/tool-cards.ts +221 -0
- package/src/channels/slack/types.ts +159 -6
- package/src/files-backends/cursor-hosted.ts +15 -5
- package/src/internal/cli-deploy.ts +2 -2
- package/src/internal/conversation-mirror.ts +3 -8
- package/src/internal/cursor/hosted-store-secrets.ts +72 -0
- package/src/internal/deploy-client.ts +10 -10
- package/src/internal/discovery.ts +9 -1
- package/src/internal/framework-file-storage.ts +41 -5
- package/src/internal/framework-storage-selection.ts +31 -44
- package/src/internal/session-run-log.ts +6 -11
- package/src/internal/storage-coordinator.ts +1 -11
- package/src/storage-backends/cursor-hosted-v2.ts +219 -0
- package/src/storage-backends/cursor-hosted.ts +6 -1
- package/src/types.ts +5 -0
- package/dist/docs/assets/chunks/@localSearchIndexroot.DpuI4i7Z.js +0 -1
- package/dist/docs/assets/hillclimbing.md.DhESf3OO.js +0 -4
- package/dist/docs/assets/scaffolding-agents.md.D7UUkWw0.js +0 -1
- package/dist/internal/null-kv-storage.d.ts +0 -48
- package/dist/internal/null-kv-storage.d.ts.map +0 -1
- package/dist/internal/null-kv-storage.js +0 -58
- package/dist/playground/assets/index-D7rGZNjy.css +0 -1
- package/src/internal/null-kv-storage.ts +0 -74
- /package/dist/docs/assets/{ab.md.DJo5r4R-.lean.js → ab.md.mlVgqvSk.lean.js} +0 -0
- /package/dist/docs/assets/{building-with-agents.md.DI4mEzlt.lean.js → building-with-agents.md.CUSWxlP_.lean.js} +0 -0
- /package/dist/docs/assets/{evals.md.lfJoEVc8.lean.js → evals.md.CPzDAwoH.lean.js} +0 -0
- /package/dist/docs/assets/{guides_github.md.Cnh2mL4a.lean.js → guides_github.md.BtPr9GaP.lean.js} +0 -0
- /package/dist/docs/assets/{guides_mcp-oauth.md.CN-6YmTJ.lean.js → guides_mcp-oauth.md.Dp6cDP7f.lean.js} +0 -0
- /package/dist/docs/assets/{guides_opentelemetry.md.bmPmkvJu.lean.js → guides_opentelemetry.md.BVTXDCRg.lean.js} +0 -0
- /package/dist/docs/assets/{hillclimbing.md.DhESf3OO.lean.js → hillclimbing.md.CpTGTCle.lean.js} +0 -0
- /package/dist/docs/assets/{index.md.CVeRUOeZ.lean.js → index.md.Bb4k8kUm.lean.js} +0 -0
- /package/dist/docs/assets/{quickstart.md.Nj_LjW_a.lean.js → quickstart.md.DdQOF7Y8.lean.js} +0 -0
- /package/dist/docs/assets/{reference_connections.md.DxldvyIB.lean.js → reference_connections.md.BiGoBAk2.lean.js} +0 -0
- /package/dist/docs/assets/{scaffolding-agents.md.D7UUkWw0.lean.js → scaffolding-agents.md.em43xlY1.lean.js} +0 -0
- /package/dist/docs/assets/{troubleshooting.md.DCiPBhYs.lean.js → troubleshooting.md.Cus_YZga.lean.js} +0 -0
package/dist/docs/llms-full.txt
CHANGED
|
@@ -336,7 +336,7 @@ Continue with these pages:
|
|
|
336
336
|
`ab.assigned` event and durable log
|
|
337
337
|
- [Playground](/docs/reference/playground.md): the A/Bs tab
|
|
338
338
|
- [HTTP API](/docs/reference/http-api.md): `GET /v1/abs`
|
|
339
|
-
- [Live A/B metrics skill](
|
|
339
|
+
- [Live A/B metrics skill](/docs/skills/ab.md): have a coding agent
|
|
340
340
|
wire an experiment
|
|
341
341
|
|
|
342
342
|
---
|
|
@@ -367,7 +367,7 @@ and verify the result without reading terminal prose.
|
|
|
367
367
|
## How do I create an agent with the built-in skill?
|
|
368
368
|
|
|
369
369
|
Have the coding agent read
|
|
370
|
-
[`skills/create-agent/SKILL.md`](
|
|
370
|
+
[`skills/create-agent/SKILL.md`](/docs/skills/create-agent.md) and
|
|
371
371
|
follow it.
|
|
372
372
|
|
|
373
373
|
The skill asks about your agent's purpose, runtime, model, channels, MCP
|
|
@@ -386,18 +386,20 @@ the first end-to-end turn works.
|
|
|
386
386
|
|
|
387
387
|
## Which built-in skill should I use?
|
|
388
388
|
|
|
389
|
-
The package ships task-specific guides under [`skills/`](
|
|
389
|
+
The package ships task-specific guides under [`skills/`](/docs/skills/index.md):
|
|
390
390
|
|
|
391
391
|
| What you want to do | Skill |
|
|
392
392
|
| --- | --- |
|
|
393
|
-
| Understand the project layout and runtimes | [`framework-map`](
|
|
394
|
-
| Create and verify a new agent | [`create-agent`](
|
|
395
|
-
| Write fixtures and regression checks | [`evals`](
|
|
396
|
-
| Live A/B metrics on traffic (`defineAB`) | [`ab`](
|
|
397
|
-
|
|
|
398
|
-
|
|
|
399
|
-
|
|
|
400
|
-
|
|
|
393
|
+
| Understand the project layout and runtimes | [`framework-map`](/docs/skills/framework-map.md) |
|
|
394
|
+
| Create and verify a new agent | [`create-agent`](/docs/skills/create-agent.md) |
|
|
395
|
+
| Write fixtures and regression checks | [`evals`](/docs/skills/evals.md) |
|
|
396
|
+
| Live A/B metrics on traffic (`defineAB`) | [`ab`](/docs/skills/ab.md) |
|
|
397
|
+
| Export OpenTelemetry traces | [`otel`](/docs/skills/otel.md) |
|
|
398
|
+
| Improve an agent against fixed inputs | [`hillclimb`](/docs/skills/hillclimb.md) |
|
|
399
|
+
| Add GitHub webhooks and replay events | [`github`](/docs/skills/github.md) |
|
|
400
|
+
| Connect an agent to Slack | [`setup-slack`](/docs/skills/setup-slack.md) |
|
|
401
|
+
| Authorize host MCP OAuth | [`mcp-auth`](/docs/skills/mcp-auth.md) |
|
|
402
|
+
| Diagnose a local run | [`debug`](/docs/skills/debug.md) |
|
|
401
403
|
|
|
402
404
|
Point your coding agent at the matching `SKILL.md`. The guide contains
|
|
403
405
|
the workflow, commands, and common mistakes for that task.
|
|
@@ -450,7 +452,7 @@ smoke turn passes, give the hillclimb skill:
|
|
|
450
452
|
evals that must stay unchanged
|
|
451
453
|
|
|
452
454
|
Have the coding agent read
|
|
453
|
-
[`skills/hillclimb/SKILL.md`](
|
|
455
|
+
[`skills/hillclimb/SKILL.md`](/docs/skills/hillclimb.md). It measures
|
|
454
456
|
the current run, proposes one change, remeasures the same fixtures, and
|
|
455
457
|
adds an eval for each kept improvement.
|
|
456
458
|
|
|
@@ -458,6 +460,7 @@ adds an eval for each kept improvement.
|
|
|
458
460
|
|
|
459
461
|
- [Create your first agent](/docs/quickstart.md)
|
|
460
462
|
- [Scaffold an agent with Cursor](/docs/scaffolding-agents.md)
|
|
463
|
+
- [Coding-agent skills](/docs/skills/index.md)
|
|
461
464
|
- [Evals](/docs/evals.md)
|
|
462
465
|
- [Hillclimbing](/docs/hillclimbing.md)
|
|
463
466
|
- [CLI reference](/docs/reference/cli.md)
|
|
@@ -3277,7 +3280,7 @@ resolution for other file formats).
|
|
|
3277
3280
|
`maxConcurrency` limits parallel datapoints. It does not limit model or
|
|
3278
3281
|
API fan-out inside one datapoint. Materialized fixtures prevent a large
|
|
3279
3282
|
suite from exhausting provider and GitHub rate limits. The
|
|
3280
|
-
[evals skill](
|
|
3283
|
+
[evals skill](/docs/skills/evals.md) has the full fixture workflow.
|
|
3281
3284
|
|
|
3282
3285
|
## Keep improvements with regression evals
|
|
3283
3286
|
|
|
@@ -3739,7 +3742,7 @@ event stream for repos you've connected to Cursor. You still declare a
|
|
|
3739
3742
|
`githubChannel` so hooks decide what each event does.
|
|
3740
3743
|
|
|
3741
3744
|
The companion skill for coding agents is
|
|
3742
|
-
[`skills/github/SKILL.md`](
|
|
3745
|
+
[`skills/github/SKILL.md`](/docs/skills/github.md).
|
|
3743
3746
|
|
|
3744
3747
|
## Pull events from Cursor
|
|
3745
3748
|
|
|
@@ -4152,7 +4155,7 @@ deployment as secrets so prod can reconnect after a redeploy. Hosted
|
|
|
4152
4155
|
Connect lets the current process retry.
|
|
4153
4156
|
|
|
4154
4157
|
The companion skill is
|
|
4155
|
-
[`skills/mcp-auth/SKILL.md`](
|
|
4158
|
+
[`skills/mcp-auth/SKILL.md`](/docs/skills/mcp-auth.md).
|
|
4156
4159
|
|
|
4157
4160
|
## What can host MCP OAuth do?
|
|
4158
4161
|
|
|
@@ -4404,7 +4407,7 @@ You can also pass the same object to `serve(dir, { otel })`. Precedence
|
|
|
4404
4407
|
is `serve({ otel })` over `agent/otel.ts` over env. An empty
|
|
4405
4408
|
`defineOtel()` still enables export when `OTEL_EXPORTER_OTLP_*` is set.
|
|
4406
4409
|
|
|
4407
|
-
The companion skill is [`skills/otel/SKILL.md`](
|
|
4410
|
+
The companion skill is [`skills/otel/SKILL.md`](/docs/skills/otel.md).
|
|
4408
4411
|
|
|
4409
4412
|
## What spans does a session produce?
|
|
4410
4413
|
|
|
@@ -4519,7 +4522,7 @@ through `serve({ otel })` or env.
|
|
|
4519
4522
|
|
|
4520
4523
|
## What's next
|
|
4521
4524
|
|
|
4522
|
-
- [`skills/otel/SKILL.md`](
|
|
4525
|
+
- [`skills/otel/SKILL.md`](/docs/skills/otel.md): compact
|
|
4523
4526
|
`defineOtel` reference for coding agents
|
|
4524
4527
|
- [Hooks](/docs/reference/hooks.md): observe the same session event stream
|
|
4525
4528
|
in-process
|
|
@@ -4539,7 +4542,7 @@ Replies stream there, with thinking steps and suggested prompts.
|
|
|
4539
4542
|
Use `agent-sdk slack create` when Cursor should own the Slack app. Use
|
|
4540
4543
|
`agent-sdk slack init --manual` when you own it. Commands and flags live
|
|
4541
4544
|
in the [CLI reference](/docs/reference/cli.md#slack). Coding agents should
|
|
4542
|
-
follow [`skills/setup-slack/SKILL.md`](
|
|
4545
|
+
follow [`skills/setup-slack/SKILL.md`](/docs/skills/setup-slack.md).
|
|
4543
4546
|
|
|
4544
4547
|
## Define the channel
|
|
4545
4548
|
|
|
@@ -4582,6 +4585,85 @@ export default slackChannel({
|
|
|
4582
4585
|
});
|
|
4583
4586
|
```
|
|
4584
4587
|
|
|
4588
|
+
## Choose how the reply arrives
|
|
4589
|
+
|
|
4590
|
+
Slack gives an agent two places to show progress while a turn runs: the
|
|
4591
|
+
status chip under the thread ("Running grep…") and the reply message
|
|
4592
|
+
itself. It won't fill both at once. While a message is streaming, Slack
|
|
4593
|
+
shows its own "is working…" chip and hides any status text you set. Cards
|
|
4594
|
+
only exist inside a streamed message. `reply.mode` picks which one you get.
|
|
4595
|
+
|
|
4596
|
+
### `post` (default): status chip, then one message
|
|
4597
|
+
|
|
4598
|
+
Tool calls and the first line of each reasoning block show in the chip as
|
|
4599
|
+
they happen. The answer lands as a single message when the turn finishes.
|
|
4600
|
+
|
|
4601
|
+
```ts
|
|
4602
|
+
export default slackChannel({
|
|
4603
|
+
reply: {
|
|
4604
|
+
mode: "post",
|
|
4605
|
+
status: {
|
|
4606
|
+
reasoning: true,
|
|
4607
|
+
tools: true,
|
|
4608
|
+
idle: ["Checking the monorepo…", "Poking Datadog…"],
|
|
4609
|
+
},
|
|
4610
|
+
},
|
|
4611
|
+
});
|
|
4612
|
+
```
|
|
4613
|
+
|
|
4614
|
+
`idle` is the rotation Slack cycles through when nothing more specific is
|
|
4615
|
+
known, up to 5 lines of 50 characters. Pass a function to `tools` to write
|
|
4616
|
+
your own line from the calls in flight.
|
|
4617
|
+
|
|
4618
|
+
### `stream`: live text, with cards
|
|
4619
|
+
|
|
4620
|
+
The answer streams into one message as the model writes it. Slack owns the
|
|
4621
|
+
chip for the duration, so live feedback inside the message comes from
|
|
4622
|
+
cards. Both are off unless you turn them on.
|
|
4623
|
+
|
|
4624
|
+
```ts
|
|
4625
|
+
export default slackChannel({
|
|
4626
|
+
reply: {
|
|
4627
|
+
mode: "stream",
|
|
4628
|
+
reasoningCard: true,
|
|
4629
|
+
toolCards: { group: "per-tool" },
|
|
4630
|
+
},
|
|
4631
|
+
toolLabels: { grep: "Searching code", read: "Reading files" },
|
|
4632
|
+
});
|
|
4633
|
+
```
|
|
4634
|
+
|
|
4635
|
+
The reasoning card is one task card, titled "Thinking", that receives the
|
|
4636
|
+
model's reasoning as it streams and completes when the answer text starts.
|
|
4637
|
+
`maxChars` (default 1500) caps how much it collects. Slack caps a streamed
|
|
4638
|
+
message near 12k characters including cards; when an answer outgrows that,
|
|
4639
|
+
the streamed message closes where it stands and the rest continues in a
|
|
4640
|
+
new message.
|
|
4641
|
+
|
|
4642
|
+
Tool cards default to one card per tool name with a call count in the title
|
|
4643
|
+
(`grep ×3`), updated in place as calls finish. `group: "per-call"` shows one
|
|
4644
|
+
card per call instead.
|
|
4645
|
+
|
|
4646
|
+
Cards are collapsible by default: each call adds one line under the title,
|
|
4647
|
+
the same summary the playground shows in a tool's header (the grep pattern,
|
|
4648
|
+
the file path, the shell command), and the group expands the same way the
|
|
4649
|
+
reasoning card does. `collapsible: false` keeps cards to their titles. On a
|
|
4650
|
+
collapsible card, `details(call)` returns the line to add when a call starts
|
|
4651
|
+
and `output(result)` the text to add when it finishes.
|
|
4652
|
+
|
|
4653
|
+
`toolLabels` renames tools everywhere they appear: the chip, card titles,
|
|
4654
|
+
and the default `Running …` line.
|
|
4655
|
+
|
|
4656
|
+
### Migrating from `streaming` and `thinkingSteps`
|
|
4657
|
+
|
|
4658
|
+
`streaming: false` is `reply: { mode: "post" }`. `streaming: true` is
|
|
4659
|
+
`reply: { mode: "stream", toolCards: { group: "per-call", collapsible:
|
|
4660
|
+
false } }`, the title-only cards it used to show. `loadingMessages` moves
|
|
4661
|
+
to `reply.status.idle`. The old options still work and `agent-sdk validate`
|
|
4662
|
+
prints the rewrite for each one.
|
|
4663
|
+
|
|
4664
|
+
A channel that set none of these used to stream. It now posts. Set
|
|
4665
|
+
`reply: { mode: "stream" }` to keep streaming.
|
|
4666
|
+
|
|
4585
4667
|
## Set it up
|
|
4586
4668
|
|
|
4587
4669
|
`slack create` opens the Cursor dashboard wizard. Finish Slack consent
|
|
@@ -5213,7 +5295,7 @@ flowchart LR
|
|
|
5213
5295
|
|
|
5214
5296
|
## How do I hillclimb an agent with a coding agent?
|
|
5215
5297
|
|
|
5216
|
-
Have Cursor read [`skills/hillclimb/SKILL.md`](
|
|
5298
|
+
Have Cursor read [`skills/hillclimb/SKILL.md`](/docs/skills/hillclimb.md).
|
|
5217
5299
|
|
|
5218
5300
|
Tell it:
|
|
5219
5301
|
|
|
@@ -5227,10 +5309,10 @@ Other skills cover the edges:
|
|
|
5227
5309
|
|
|
5228
5310
|
| When you need… | Skill |
|
|
5229
5311
|
| --- | --- |
|
|
5230
|
-
| The measured improvement loop | [`skills/hillclimb/SKILL.md`](
|
|
5231
|
-
| An eval that locks a kept win | [`skills/evals/SKILL.md`](
|
|
5232
|
-
| Repeatable GitHub webhook inputs | [`skills/github/SKILL.md`](
|
|
5233
|
-
| A run that misbehaves | [`skills/debug/SKILL.md`](
|
|
5312
|
+
| The measured improvement loop | [`skills/hillclimb/SKILL.md`](/docs/skills/hillclimb.md) |
|
|
5313
|
+
| An eval that locks a kept win | [`skills/evals/SKILL.md`](/docs/skills/evals.md) |
|
|
5314
|
+
| Repeatable GitHub webhook inputs | [`skills/github/SKILL.md`](/docs/skills/github.md) |
|
|
5315
|
+
| A run that misbehaves | [`skills/debug/SKILL.md`](/docs/skills/debug.md) |
|
|
5234
5316
|
|
|
5235
5317
|
See [Building agents with agents](/docs/building-with-agents.md) for every framework skill and a good first prompt.
|
|
5236
5318
|
|
|
@@ -5435,7 +5517,7 @@ Confirm `agent-sdk whoami` shows the expected account.
|
|
|
5435
5517
|
## Related documentation
|
|
5436
5518
|
|
|
5437
5519
|
- Package reference: [`README.md`](https://github.com/cursor/cursor/blob/main/packages/agent-serve/README.md)
|
|
5438
|
-
- Coding-agent workflows: [`skills/`](
|
|
5520
|
+
- Coding-agent workflows: [`skills/`](/docs/skills/index.md)
|
|
5439
5521
|
|
|
5440
5522
|
---
|
|
5441
5523
|
|
|
@@ -5451,7 +5533,7 @@ review. Add GitHub event handling so pull requests can trigger reviews.
|
|
|
5451
5533
|
|
|
5452
5534
|
- **Get started with an agent in Cursor:** follow
|
|
5453
5535
|
[Scaffold an agent with Cursor](/docs/scaffolding-agents.md) and ask Cursor
|
|
5454
|
-
to read [`skills/create-agent/SKILL.md`](
|
|
5536
|
+
to read [`skills/create-agent/SKILL.md`](/docs/skills/create-agent.md).
|
|
5455
5537
|
- **Get started in the CLI:** continue below.
|
|
5456
5538
|
|
|
5457
5539
|
## Prerequisites
|
|
@@ -7454,7 +7536,7 @@ agent-sdk mcp oauth inventory --store # also upsert deployment secrets
|
|
|
7454
7536
|
```
|
|
7455
7537
|
|
|
7456
7538
|
Full walkthrough: [Host MCP OAuth](/docs/guides/mcp-oauth.md). Companion
|
|
7457
|
-
skill: [`skills/mcp-auth/SKILL.md`](
|
|
7539
|
+
skill: [`skills/mcp-auth/SKILL.md`](/docs/skills/mcp-auth.md).
|
|
7458
7540
|
|
|
7459
7541
|
Account MCP (`cursorAccount: true`) is the right choice for connectors
|
|
7460
7542
|
already linked in the Cursor dashboard. Omit `servers` (or pass `"*"`)
|
|
@@ -9249,7 +9331,7 @@ decision.
|
|
|
9249
9331
|
## What does the create-agent skill do?
|
|
9250
9332
|
|
|
9251
9333
|
The bundled
|
|
9252
|
-
[`create-agent` skill](
|
|
9334
|
+
[`create-agent` skill](/docs/skills/create-agent.md) turns your goal
|
|
9253
9335
|
into a small working project. Have Cursor read that file and follow it.
|
|
9254
9336
|
|
|
9255
9337
|
Where to find the file depends on how you got the package:
|
|
@@ -9264,7 +9346,7 @@ Where to find the file depends on how you got the package:
|
|
|
9264
9346
|
- Installed `@cursor/july` as a dependency? The skill also ships inside
|
|
9265
9347
|
the package at `node_modules/@cursor/july/skills/create-agent/SKILL.md`.
|
|
9266
9348
|
- Working from this package's source? The skill is at
|
|
9267
|
-
[`skills/create-agent/SKILL.md`](
|
|
9349
|
+
[`skills/create-agent/SKILL.md`](/docs/skills/create-agent.md). Run
|
|
9268
9350
|
`agent-sdk install-skills` if you want the same copies in
|
|
9269
9351
|
`~/.cursor/skills/agentsdk/` (the package postinstall skips the
|
|
9270
9352
|
source checkout).
|
|
@@ -9357,7 +9439,7 @@ without a Cursor credential. Model turns and evals need
|
|
|
9357
9439
|
|
|
9358
9440
|
Choose one to three fixed inputs, define what should improve, and name
|
|
9359
9441
|
what must stay unchanged. Then have Cursor follow
|
|
9360
|
-
[`skills/hillclimb/SKILL.md`](
|
|
9442
|
+
[`skills/hillclimb/SKILL.md`](/docs/skills/hillclimb.md).
|
|
9361
9443
|
|
|
9362
9444
|
The hillclimb skill measures a baseline, changes one lever, runs the same
|
|
9363
9445
|
inputs again, and adds an eval for each improvement you keep.
|
|
@@ -9373,6 +9455,935 @@ inputs again, and adds an eval for each improvement you keep.
|
|
|
9373
9455
|
|
|
9374
9456
|
---
|
|
9375
9457
|
|
|
9458
|
+
Source: /docs/skills/ab.md
|
|
9459
|
+
|
|
9460
|
+
# Agent SDK A/B metrics (`defineAB`)
|
|
9461
|
+
|
|
9462
|
+
Live metrics plug-in. No `agent-sdk ab` CLI. No assertion API.
|
|
9463
|
+
Reference: `docs/ab.md`.
|
|
9464
|
+
|
|
9465
|
+
| | `defineEval` | `defineAB` |
|
|
9466
|
+
| --- | --- | --- |
|
|
9467
|
+
| Job | Gates on frozen fixtures | Metrics on live runs |
|
|
9468
|
+
| Location | `evals/**/*.eval.ts` | `agent/ab.ts` or `agent/ab/<name>.ts` |
|
|
9469
|
+
| How it runs | `agent-sdk eval` | Under `serve` / `run` |
|
|
9470
|
+
|
|
9471
|
+
```ts
|
|
9472
|
+
import { defineAB, splitBySessionHash } from "@cursor/july/ab";
|
|
9473
|
+
|
|
9474
|
+
export default defineAB({
|
|
9475
|
+
name: "concise-instructions",
|
|
9476
|
+
variants: {
|
|
9477
|
+
control: { label: "Baseline" },
|
|
9478
|
+
treatment: {
|
|
9479
|
+
label: "Shorter",
|
|
9480
|
+
instructions: "Keep replies to one short paragraph.",
|
|
9481
|
+
},
|
|
9482
|
+
},
|
|
9483
|
+
split: splitBySessionHash({ holdout: 0.1 }),
|
|
9484
|
+
derive: {
|
|
9485
|
+
weatherCalls: (event) =>
|
|
9486
|
+
event.type === "action.result" && event.data.toolName === "get_weather"
|
|
9487
|
+
? 1
|
|
9488
|
+
: null,
|
|
9489
|
+
},
|
|
9490
|
+
onSample(sample) {
|
|
9491
|
+
console.log(sample.variant, sample.metrics.toolCalls, sample.metrics.wallTimeMs);
|
|
9492
|
+
},
|
|
9493
|
+
});
|
|
9494
|
+
```
|
|
9495
|
+
|
|
9496
|
+
```ts
|
|
9497
|
+
async execute(input, ctx) {
|
|
9498
|
+
if (ctx.session.abs?.["concise-instructions"] === "treatment") {
|
|
9499
|
+
// treatment-specific behavior
|
|
9500
|
+
}
|
|
9501
|
+
}
|
|
9502
|
+
```
|
|
9503
|
+
|
|
9504
|
+
Enrollment is at session creation. Eval sessions skip it. Do not
|
|
9505
|
+
use `splitIf` to filter evals. Split helpers and `onSample`
|
|
9506
|
+
fields: `docs/ab.md`.
|
|
9507
|
+
|
|
9508
|
+
Pick a name, arm labels, a split, and a real `onSample` sink. Do
|
|
9509
|
+
not invent credentials.
|
|
9510
|
+
|
|
9511
|
+
---
|
|
9512
|
+
|
|
9513
|
+
Source: /docs/skills/create-agent.md
|
|
9514
|
+
|
|
9515
|
+
# Create an Agent SDK agent
|
|
9516
|
+
|
|
9517
|
+
1. **Interview.** Two `AskQuestion` rounds, then a plan gate.
|
|
9518
|
+
2. **Scaffold.** `agent-sdk init`, then shape the files.
|
|
9519
|
+
3. **Verify.** `validate` / `info` / `call`, then a model turn.
|
|
9520
|
+
4. **Channels.** Slack, GitHub, webhook, or schedule as chosen.
|
|
9521
|
+
5. **Hillclimb.** `skills/hillclimb/SKILL.md`.
|
|
9522
|
+
|
|
9523
|
+
Read `skills/framework-map/SKILL.md` if you have not. CLI is
|
|
9524
|
+
`agent-sdk`. Public docs:
|
|
9525
|
+
`node_modules/@cursor/july/dist/docs/llms.txt` or `/docs/llms.txt`
|
|
9526
|
+
on a running host.
|
|
9527
|
+
|
|
9528
|
+
## Interview
|
|
9529
|
+
|
|
9530
|
+
`AskQuestion`: batched, recommended option first and labeled
|
|
9531
|
+
`(recommended)`.
|
|
9532
|
+
|
|
9533
|
+
- Mine the invoking message. Target: two rounds, then files.
|
|
9534
|
+
- Round 1 is identity. Round 2 is the surface, tailored by round 1.
|
|
9535
|
+
- Multi-select for channels, MCP, capabilities. Other where a
|
|
9536
|
+
custom answer is plausible.
|
|
9537
|
+
- Ask decisions, not how to build it. File layout, tool names,
|
|
9538
|
+
env prefix, and eval shape are yours.
|
|
9539
|
+
- If `AskQuestion` is missing or the user skips, state defaults
|
|
9540
|
+
in one list and proceed.
|
|
9541
|
+
|
|
9542
|
+
### Round 1: identity
|
|
9543
|
+
|
|
9544
|
+
| Question | Options |
|
|
9545
|
+
| --- | --- |
|
|
9546
|
+
| **Purpose** | chat assistant · PR / repo automation · domain assistant over APIs/tools · scheduled reporter · Other |
|
|
9547
|
+
| **Name** | 2–3 slugs from the purpose + Other. Directory: `[A-Za-z0-9][A-Za-z0-9_-]*`, not `v1`/`playground`/`docs` |
|
|
9548
|
+
| **Location** | `./<slug>` (default) · another directory |
|
|
9549
|
+
|
|
9550
|
+
### Round 2: surface
|
|
9551
|
+
|
|
9552
|
+
| Question | Options | Guidance |
|
|
9553
|
+
| --- | --- | --- |
|
|
9554
|
+
| **Runtime** | `local` (default) · `cloud` | Cloud needs `cloud.repos`. Approvals and sandbox seeds are local only. Recommend local unless the job needs a cloud checkout. |
|
|
9555
|
+
| **Model** | `grok-4.5` + `effort=high`, `fast=true` · Other id | Params, not id suffixes: `{ id: "grok-4.5", params: [{ id: "effort", value: "high" }, { id: "fast", value: "true" }] }` |
|
|
9556
|
+
| **Channels** (multi) | playground + HTTP (always on) · Slack · GitHub · custom webhook · schedule | Slack: `skills/setup-slack/SKILL.md`. GitHub: `skills/github/SKILL.md`. No Discord/Teams pack; offer custom webhook. |
|
|
9557
|
+
| **MCP** (multi) | none · remote URL · local stdio · Cursor account connectors · Other | One file under `agent/mcp-connections/`. Account file is `account.ts`, never `cursor.ts`. Named local tools need `advertiseTools: true`. Privileged servers go in `agent/host-connections/`. |
|
|
9558
|
+
| **Capabilities** (multi) | server tools · agent tools · skills · subagents · hooks · sandbox seeds · approvals · evals (recommend) | Always recommend one smoke eval. |
|
|
9559
|
+
|
|
9560
|
+
Close with the plan and file tree, then "Scaffold it" / "Adjust
|
|
9561
|
+
something". Write files only after approval.
|
|
9562
|
+
|
|
9563
|
+
## Fill the blanks
|
|
9564
|
+
|
|
9565
|
+
| Purpose | Shape |
|
|
9566
|
+
| --- | --- |
|
|
9567
|
+
| Slack chat | `slackChannel({ envPrefix })` + suggested prompts. `agent-sdk slack create` mints the bot. Prefix: `skills/setup-slack/SKILL.md` |
|
|
9568
|
+
| PR review with host prep | Channel `callTool` into a trimmed workspace `pr/` tree |
|
|
9569
|
+
| GitHub automation | `githubChannel()` hooks, replay fixtures |
|
|
9570
|
+
| Domain assistant | Server tools + one MCP connection + a skill |
|
|
9571
|
+
| Wrap an existing pipeline | GitHub `{ task }` over a thin `agent/lib/` loop |
|
|
9572
|
+
|
|
9573
|
+
Defaults:
|
|
9574
|
+
|
|
9575
|
+
- Instructions + 1–2 tools + chosen channels + one smoke eval.
|
|
9576
|
+
- `local.cwd` stays outside a monorepo checkout (default: a cache
|
|
9577
|
+
directory under `~/.cache`) unless the agent must inherit that
|
|
9578
|
+
tree.
|
|
9579
|
+
- `agent/instructions.md`: identity, when to use which tool,
|
|
9580
|
+
output shape.
|
|
9581
|
+
- One tool per file. Prefer `execution: "server"` + zod
|
|
9582
|
+
`inputSchema`. Gate side effects with `needsApproval: true`.
|
|
9583
|
+
- Long prompts: `prompt\`…\`` / `prompt.lines\`…\`` from
|
|
9584
|
+
`@cursor/july`.
|
|
9585
|
+
- Host prep is for evidence (`callTool`, `workspaceFiles`), not
|
|
9586
|
+
judgment, formatting, or replies.
|
|
9587
|
+
|
|
9588
|
+
### Deterministic-path budget
|
|
9589
|
+
|
|
9590
|
+
Default to instructions and skills. Promote to TypeScript only
|
|
9591
|
+
when it earns the left column:
|
|
9592
|
+
|
|
9593
|
+
| Code owns | Model owns |
|
|
9594
|
+
| --- | --- |
|
|
9595
|
+
| Side-effect gates (approve, deploy, post) | Human-facing output to a stated shape |
|
|
9596
|
+
| Dedupe of external writes | Summarizing, classifying, wording |
|
|
9597
|
+
| Auth and signature checks | What to do next from ground truth |
|
|
9598
|
+
| Evidence seeding | Soft-failure retries |
|
|
9599
|
+
| Hard API caps | Formatting under those caps |
|
|
9600
|
+
|
|
9601
|
+
Smells: prose builders in `.ts` (write `.md`); `agent/lib/` +
|
|
9602
|
+
`tools/` dwarfing instructions + skills on a first cut.
|
|
9603
|
+
|
|
9604
|
+
## Scaffold
|
|
9605
|
+
|
|
9606
|
+
```bash
|
|
9607
|
+
agent-sdk init ./<slug>
|
|
9608
|
+
```
|
|
9609
|
+
|
|
9610
|
+
`init` writes the project, runs `npm install`, and may wait on
|
|
9611
|
+
`login`. Then shape it:
|
|
9612
|
+
|
|
9613
|
+
1. `defineAgent` with the chosen model/runtime. Add
|
|
9614
|
+
`cloud: { repos: [...] }` for cloud.
|
|
9615
|
+
2. Real `instructions.md`. Replace `echo.ts`.
|
|
9616
|
+
3. Chosen `channels/`, `mcp-connections/`, `skills/`,
|
|
9617
|
+
`subagents/<id>/` (needs `description`), `schedules/`, `hooks/`.
|
|
9618
|
+
Slack: `agent-sdk slack create --dir ./<slug> --name "<Name>"`,
|
|
9619
|
+
not a hand-written channel. Manual Slack app:
|
|
9620
|
+
`agent-sdk slack init --manual` (Slack CLI, or paste at
|
|
9621
|
+
api.slack.com).
|
|
9622
|
+
4. `evals/evals.config.ts` with `maxConcurrency: 20` (required;
|
|
9623
|
+
cap 200) plus `evals/**/*.eval.ts`. Assert `t.succeeded()` +
|
|
9624
|
+
`t.calledTool(...)`. API: `skills/evals/SKILL.md`.
|
|
9625
|
+
|
|
9626
|
+
Stay on deps the Agent SDK already ships (`zod`,
|
|
9627
|
+
`@modelcontextprotocol/sdk`, `tsx`).
|
|
9628
|
+
|
|
9629
|
+
## Verify
|
|
9630
|
+
|
|
9631
|
+
```bash
|
|
9632
|
+
agent-sdk validate --dir ./<slug>
|
|
9633
|
+
agent-sdk info --dir ./<slug> --json
|
|
9634
|
+
agent-sdk call <tool> --dir ./<slug> --input '{…}'
|
|
9635
|
+
agent-sdk eval --dir ./<slug> --list
|
|
9636
|
+
npx tsc --noEmit -p ./<slug>
|
|
9637
|
+
```
|
|
9638
|
+
|
|
9639
|
+
tsx does not typecheck. Tool `execute` must return JSON-shaped
|
|
9640
|
+
values: object literals or `type` aliases, not `interface` types.
|
|
9641
|
+
|
|
9642
|
+
Model turns need `CURSOR_API_KEY`. Without one, finish the
|
|
9643
|
+
key-free checks, confirm `run` fails with only the API-key error,
|
|
9644
|
+
and hand these over:
|
|
9645
|
+
|
|
9646
|
+
```bash
|
|
9647
|
+
agent-sdk run --dir ./<slug> --message "<fixture prompt>"
|
|
9648
|
+
agent-sdk serve --dir ./<slug> --mode single --dev
|
|
9649
|
+
# http://127.0.0.1:3000/playground
|
|
9650
|
+
agent-sdk eval --dir ./<slug>
|
|
9651
|
+
```
|
|
9652
|
+
|
|
9653
|
+
Serve only this agent's directory. Session files land in the
|
|
9654
|
+
project state directory (`--state-root`). That is not harness cwd.
|
|
9655
|
+
|
|
9656
|
+
## Channel setup
|
|
9657
|
+
|
|
9658
|
+
- **Slack.** `skills/setup-slack/SKILL.md`
|
|
9659
|
+
- **GitHub.** `skills/github/SKILL.md`
|
|
9660
|
+
- **Custom webhook.** `POST /v1/channels/<id>/<route>`.
|
|
9661
|
+
Loopback-only until you add `bearerAuth(...)`.
|
|
9662
|
+
- **Schedules.** Never auto-fire under `--dev`.
|
|
9663
|
+
`POST /v1/dev/schedules/<id>`.
|
|
9664
|
+
|
|
9665
|
+
## Hillclimb handoff
|
|
9666
|
+
|
|
9667
|
+
Once a smoke turn passes, agree fixtures, success criteria, and a
|
|
9668
|
+
freeze line, then follow `skills/hillclimb/SKILL.md`. Seed from
|
|
9669
|
+
the smoke session under the project state directory. GitHub:
|
|
9670
|
+
snapshot `agent-sdk github replay ... --dry-run --out fixtures/github`.
|
|
9671
|
+
|
|
9672
|
+
Do not deploy or post to real Slack/GitHub beyond the smoke the
|
|
9673
|
+
user asked for. If the plan grows past ~10 files, cut scope.
|
|
9674
|
+
Re-check the budget at hand-off.
|
|
9675
|
+
|
|
9676
|
+
---
|
|
9677
|
+
|
|
9678
|
+
Source: /docs/skills/debug.md
|
|
9679
|
+
|
|
9680
|
+
# Debugging the Agent SDK locally
|
|
9681
|
+
|
|
9682
|
+
Local `agent-sdk serve`. Hosted start or health failures:
|
|
9683
|
+
`docs/troubleshooting.md` and `docs/deployment.md`.
|
|
9684
|
+
|
|
9685
|
+
1. **Validate.** `agent-sdk validate --dir <project>`
|
|
9686
|
+
2. **Info.** `curl -s http://127.0.0.1:3000/<slug>/v1/info | jq .`
|
|
9687
|
+
3. **Trace.** Session events under the project state directory.
|
|
9688
|
+
Then match the table.
|
|
9689
|
+
|
|
9690
|
+
| Symptom | Fix |
|
|
9691
|
+
| --- | --- |
|
|
9692
|
+
| Playground blank / "no agents" | Start `serve`. A built SPA with no backend serves nothing. |
|
|
9693
|
+
| Playground UI edits do not show | Open the URL `serve --dev` prints as `playground`, not `:3000`. |
|
|
9694
|
+
| Sessions on disk, empty playground list | List is the calling principal. `--dev` or `--allow-anonymous` shows all. Or `?sessionId=ses_...`. |
|
|
9695
|
+
| Built-in read/grep fail; retry loops | Bun. Rerun under Node. The tell is `NGHTTP2_FRAME_SIZE_ERROR`. |
|
|
9696
|
+
| `github forward` 401s; hook created | Blank `GITHUB_TOKEN`/`GH_TOKEN`. Relay uses `gh` login. |
|
|
9697
|
+
| `Hook already exists` | One forwarder per repo. `forward --dir <parent>`. |
|
|
9698
|
+
| Answers cite ancestor `AGENTS.md` | Nested checkout. Default `local.cwd` is a cache directory under `~/.cache`. |
|
|
9699
|
+
| Model lists IDE `cursor` tools, never MCP | `advertiseTools: true`. Check `GET /v1/info`. |
|
|
9700
|
+
| Port 3000 in use | `lsof -iTCP:3000 -sTCP:LISTEN` and kill that pid. |
|
|
9701
|
+
| Approval vanished after restart | Parked calls do not survive restart. Re-run. |
|
|
9702
|
+
| Schedule / reminder silent under `--dev` | Dev never auto-fires. `POST /<slug>/v1/dev/schedules/<id>`. |
|
|
9703
|
+
| `409` on follow-up | Stale `continuationToken`, busy session, or a task session. |
|
|
9704
|
+
| `409 session_busy` on `call --session` | Wait, or drop `--session`. |
|
|
9705
|
+
| `403` on stream | Wrong principal. Same auth as create; beyond loopback send `--bearer-token`. |
|
|
9706
|
+
| Works on loopback, blocked via tunnel | `localDevStrict()` rejects forwarded headers. Use `--bearer-token`. Never `--allow-anonymous` with account MCP. |
|
|
9707
|
+
| Slack `channel idle … missing credentials` | Expected. `slack doctor --prefix <PREFIX>`. |
|
|
9708
|
+
| Immediate API-key error | Model turns need `CURSOR_API_KEY`. |
|
|
9709
|
+
| Approvals or sandbox seeds missing | `runtime: "cloud"`. Those are local only. `validate` warns. |
|
|
9710
|
+
| `validate` clean, CI typecheck fails | tsx skipped types. JSON-shaped returns; `type` not `interface`. |
|
|
9711
|
+
|
|
9712
|
+
Count `action.result` by `toolName` before blaming latency.
|
|
9713
|
+
`turn.failed` + `"turn interrupted"` is a follow-up or stop, not a
|
|
9714
|
+
crash. `agent-sdk trajectory --events <file>` renders a saved
|
|
9715
|
+
trace.
|
|
9716
|
+
|
|
9717
|
+
---
|
|
9718
|
+
|
|
9719
|
+
Source: /docs/skills/evals.md
|
|
9720
|
+
|
|
9721
|
+
# Agent SDK evals
|
|
9722
|
+
|
|
9723
|
+
Fixed input, model turn, gates on the trajectory. Files live at
|
|
9724
|
+
project-root `evals/**/*.eval.ts`. `agent/evals/` is ignored.
|
|
9725
|
+
|
|
9726
|
+
Live traffic variants: `skills/ab/SKILL.md`. That is not a test
|
|
9727
|
+
runner.
|
|
9728
|
+
|
|
9729
|
+
```bash
|
|
9730
|
+
agent-sdk eval --dir . --list
|
|
9731
|
+
agent-sdk eval --dir . --json
|
|
9732
|
+
agent-sdk eval --dir . weather/nyc
|
|
9733
|
+
agent-sdk eval --dir . --tag smoke
|
|
9734
|
+
```
|
|
9735
|
+
|
|
9736
|
+
| Form | Case id |
|
|
9737
|
+
| --- | --- |
|
|
9738
|
+
| `evals/weather.eval.ts` + `test` | `weather` |
|
|
9739
|
+
| `evals/weather/nyc.eval.ts` + `test` | `weather/nyc` |
|
|
9740
|
+
| `evals/weather.eval.ts` + `{ id: "nyc" }` | `weather/nyc` |
|
|
9741
|
+
|
|
9742
|
+
`eval` boots an ephemeral server and a temp state root. `--url`
|
|
9743
|
+
points at a running agent. Model turns need `CURSOR_API_KEY`.
|
|
9744
|
+
|
|
9745
|
+
## Seeding
|
|
9746
|
+
|
|
9747
|
+
Creating or expanding cases: `AskQuestion` first.
|
|
9748
|
+
|
|
9749
|
+
| Question | Options |
|
|
9750
|
+
| --- | --- |
|
|
9751
|
+
| **How should we get eval samples?** | Generate test eval samples for me `(recommended)` · I will add / upload the data manually |
|
|
9752
|
+
|
|
9753
|
+
1. **Manual.** They provide files or paste. Show the shape below.
|
|
9754
|
+
Do not invent cases. Then `eval --list` and wire gates.
|
|
9755
|
+
API-backed pointers (PR URLs, SHAs, gold labels): materialize
|
|
9756
|
+
under `fixtures/` first.
|
|
9757
|
+
2. **Generated.** Ask count (`3` recommended). Append to an
|
|
9758
|
+
existing `cases` array when it fits. Never overwrite or weaken
|
|
9759
|
+
a datapoint. Create `evals/evals.config.ts` if missing
|
|
9760
|
+
(`maxConcurrency: 20`; cap 200).
|
|
9761
|
+
|
|
9762
|
+
## API
|
|
9763
|
+
|
|
9764
|
+
```ts
|
|
9765
|
+
import { defineEval, includes, satisfies } from "@cursor/july/evals";
|
|
9766
|
+
|
|
9767
|
+
export default defineEval({
|
|
9768
|
+
tags: ["smoke", "weather"],
|
|
9769
|
+
cases: [
|
|
9770
|
+
{
|
|
9771
|
+
id: "nyc",
|
|
9772
|
+
description: "NYC temperature.",
|
|
9773
|
+
async test(t) {
|
|
9774
|
+
await t.send("What's the temperature in NYC?");
|
|
9775
|
+
t.succeeded();
|
|
9776
|
+
t.calledTool("get_weather");
|
|
9777
|
+
t.notCalledTool("save_weather_note");
|
|
9778
|
+
t.check(t.reply, includes(/°|[FC]/));
|
|
9779
|
+
},
|
|
9780
|
+
},
|
|
9781
|
+
],
|
|
9782
|
+
});
|
|
9783
|
+
```
|
|
9784
|
+
|
|
9785
|
+
```ts
|
|
9786
|
+
import { defineEvalConfig } from "@cursor/july/evals";
|
|
9787
|
+
|
|
9788
|
+
export default defineEvalConfig({
|
|
9789
|
+
maxConcurrency: 20,
|
|
9790
|
+
});
|
|
9791
|
+
```
|
|
9792
|
+
|
|
9793
|
+
Either `test(t)` or `cases`, not both. `t.send` waits for park/fail.
|
|
9794
|
+
`workspaceFiles` seeds the first turn. Assert with `t.succeeded()`,
|
|
9795
|
+
`calledTool` / `notCalledTool`, `t.check(t.reply, …)`, `t.metric`.
|
|
9796
|
+
|
|
9797
|
+
## What to gate
|
|
9798
|
+
|
|
9799
|
+
Decisions and shape, not prose.
|
|
9800
|
+
|
|
9801
|
+
1. `t.succeeded()` first
|
|
9802
|
+
2. Intended tool + the tempting wrong one
|
|
9803
|
+
3. A shape regex or `satisfies` on parsed fields
|
|
9804
|
+
4. If formatting keeps failing, tighten instructions. Do not move
|
|
9805
|
+
rendering into a host tool.
|
|
9806
|
+
|
|
9807
|
+
Anti-patterns: exact phrasing; more than ~5 gates (split); live
|
|
9808
|
+
drifting inputs (pin them).
|
|
9809
|
+
|
|
9810
|
+
| Surface | Fixture |
|
|
9811
|
+
| --- | --- |
|
|
9812
|
+
| Chat | One frozen prompt |
|
|
9813
|
+
| Tool-heavy | `agent-sdk call` first, then the prompt |
|
|
9814
|
+
| GitHub | `github replay … --dry-run --out fixtures/github` |
|
|
9815
|
+
| Host-prep PR review | A team-owned PR; gate findings shape, not counts |
|
|
9816
|
+
| Workspace | `workspaceFiles` in `t.send` |
|
|
9817
|
+
|
|
9818
|
+
Every kept hillclimb change lands an eval that would have failed
|
|
9819
|
+
before it. Never weaken a gate to pass a round.
|
|
9820
|
+
|
|
9821
|
+
---
|
|
9822
|
+
|
|
9823
|
+
Source: /docs/skills/framework-map.md
|
|
9824
|
+
|
|
9825
|
+
# Agent SDK framework map
|
|
9826
|
+
|
|
9827
|
+
`@cursor/july` discovers files under `agent/` and serves the agent
|
|
9828
|
+
over HTTP, Slack, and GitHub. Markdown is prose. TypeScript is typed
|
|
9829
|
+
behavior. Ground truth: package `README.md` and `AGENTS.md`.
|
|
9830
|
+
|
|
9831
|
+
CLI is `agent-sdk` (Node, never Bun).
|
|
9832
|
+
|
|
9833
|
+
Public docs: `node_modules/@cursor/july/dist/docs/llms.txt` or
|
|
9834
|
+
`/docs/llms.txt` on a running host.
|
|
9835
|
+
|
|
9836
|
+
## Invariants
|
|
9837
|
+
|
|
9838
|
+
1. **Node 22.13+, never Bun.** Bun corrupts harness tool-result
|
|
9839
|
+
streams (`NGHTTP2_FRAME_SIZE_ERROR`).
|
|
9840
|
+
2. **Evals live at project-root `evals/`.** `agent/evals/` is ignored.
|
|
9841
|
+
3. **tsx does not typecheck.** Tool `execute` must return JSON-shaped
|
|
9842
|
+
values: object literals or `type` aliases, not `interface` types.
|
|
9843
|
+
4. **Nested git checkouts.** Discovery sets `local.cwd` to a
|
|
9844
|
+
per-project cache directory under `~/.cache`. Point cwd at a
|
|
9845
|
+
checkout only when the agent must inherit that tree.
|
|
9846
|
+
5. **Attached MCP is nameless** until `advertiseTools: true`.
|
|
9847
|
+
6. **Model turns need `CURSOR_API_KEY`.** `validate`, `info`, `call`,
|
|
9848
|
+
and `serve` bring-up do not.
|
|
9849
|
+
|
|
9850
|
+
## Folder structure
|
|
9851
|
+
|
|
9852
|
+
Path is identity. Full list: README "Folder structure".
|
|
9853
|
+
|
|
9854
|
+
| Path | Role |
|
|
9855
|
+
| --- | --- |
|
|
9856
|
+
| `agent/agent.ts` | `defineAgent({ model?, runtime?, cloud?, local? })` |
|
|
9857
|
+
| `agent/instructions.md` | Always-on system prompt (required) |
|
|
9858
|
+
| `agent/tools/<name>.ts` | One tool. `execution: "server"` or `"agent"` |
|
|
9859
|
+
| `agent/skills/*` | On-demand procedures |
|
|
9860
|
+
| `agent/mcp-connections/<name>.ts` | MCP. Never name an account file `cursor.ts`. `advertiseTools: true` for named local tools |
|
|
9861
|
+
| `agent/host-connections/<name>.ts` | Privileged MCP for `ctx.host.mcp` / `mcp oauth` |
|
|
9862
|
+
| `agent/subagents/<id>/` | Child agent (`description` required) |
|
|
9863
|
+
| `agent/channels/*.ts` | Slack / GitHub / custom HTTP |
|
|
9864
|
+
| `agent/hooks/*.ts` | Observe-only |
|
|
9865
|
+
| `agent/ab.ts` or `agent/ab/*.ts` | Live A/B (`defineAB`) |
|
|
9866
|
+
| `agent/otel.ts` | OpenTelemetry (`defineOtel`) |
|
|
9867
|
+
| `agent/schedules/*` | Cron. Never auto-fire under `--dev` |
|
|
9868
|
+
| `agent/sandbox/workspace/` | Session seed files (local only) |
|
|
9869
|
+
| `agent/lib/` | Import-only. Never discovered |
|
|
9870
|
+
| `evals/**/*.eval.ts` | Case id is the path under `evals/` |
|
|
9871
|
+
|
|
9872
|
+
## Local vs cloud
|
|
9873
|
+
|
|
9874
|
+
`runtime: "local"` (default) runs on the serve host.
|
|
9875
|
+
`runtime: "cloud"` needs `cloud: { repos: [...] }`.
|
|
9876
|
+
|
|
9877
|
+
| Capability | local | cloud |
|
|
9878
|
+
| --- | --- | --- |
|
|
9879
|
+
| Server tools | yes | yes on managed hosting; self-hosted needs `--public-url` |
|
|
9880
|
+
| Tool approvals | yes | no |
|
|
9881
|
+
| Agent tools / skills | yes | yes |
|
|
9882
|
+
| sandbox seeds | yes | no |
|
|
9883
|
+
| Checkout | you arrange it | the VM carries it |
|
|
9884
|
+
|
|
9885
|
+
Use cloud when the job needs a checkout at scale. `validate` warns
|
|
9886
|
+
when cloud is combined with local-only capabilities.
|
|
9887
|
+
|
|
9888
|
+
## Sessions
|
|
9889
|
+
|
|
9890
|
+
- **continuationToken** continues a conversation. HTTP follow-ups
|
|
9891
|
+
rotate it. Stale tokens return `409`.
|
|
9892
|
+
- **sessionId** is the inspect handle
|
|
9893
|
+
(`GET /v1/session/:id/stream?startIndex=N`).
|
|
9894
|
+
|
|
9895
|
+
A follow-up to a busy HTTP/MCP session interrupts the in-flight
|
|
9896
|
+
turn. Slack coalesces. Routes: `docs/reference/http-api.md`.
|
|
9897
|
+
Session files live under the project state directory
|
|
9898
|
+
(`--state-root`).
|
|
9899
|
+
|
|
9900
|
+
## Where logic belongs
|
|
9901
|
+
|
|
9902
|
+
Code: side-effect gates, write dedupe, auth, evidence seeding, hard
|
|
9903
|
+
API caps. Model: formatting, summarizing, classification, replies.
|
|
9904
|
+
Budget: `skills/create-agent/SKILL.md`.
|
|
9905
|
+
|
|
9906
|
+
Loop: `validate` / `info` / `call` / `run` / `eval` / `serve`. Serve
|
|
9907
|
+
only this agent's directory.
|
|
9908
|
+
|
|
9909
|
+
| Task | Skill |
|
|
9910
|
+
| --- | --- |
|
|
9911
|
+
| Scaffold | `skills/create-agent/SKILL.md` |
|
|
9912
|
+
| Evals | `skills/evals/SKILL.md` |
|
|
9913
|
+
| Live A/B | `skills/ab/SKILL.md` |
|
|
9914
|
+
| OpenTelemetry | `skills/otel/SKILL.md` |
|
|
9915
|
+
| GitHub | `skills/github/SKILL.md` |
|
|
9916
|
+
| Slack | `skills/setup-slack/SKILL.md` |
|
|
9917
|
+
| Host MCP OAuth | `skills/mcp-auth/SKILL.md` |
|
|
9918
|
+
| Local triage | `skills/debug/SKILL.md` |
|
|
9919
|
+
| Measured improvement | `skills/hillclimb/SKILL.md` |
|
|
9920
|
+
|
|
9921
|
+
---
|
|
9922
|
+
|
|
9923
|
+
Source: /docs/skills/github.md
|
|
9924
|
+
|
|
9925
|
+
# GitHub channels in the Agent SDK
|
|
9926
|
+
|
|
9927
|
+
Author `agent/channels/github.ts`. Production wakes:
|
|
9928
|
+
`cursorAccount` + `serve --cursor-events`. No public webhook URL.
|
|
9929
|
+
Use the HTTP route for fixtures, replay, and hosts that already
|
|
9930
|
+
terminate GitHub webhooks.
|
|
9931
|
+
|
|
9932
|
+
Guide: `docs/guides/github.md`.
|
|
9933
|
+
|
|
9934
|
+
```ts
|
|
9935
|
+
import { defaultGitHubAuth, githubChannel } from "@cursor/july/channels/github";
|
|
9936
|
+
|
|
9937
|
+
export default githubChannel({
|
|
9938
|
+
botName: "my-agent",
|
|
9939
|
+
cursorAccount: { repos: ["owner/repo"] }, // permissions?: "read" | "pr-write" | "contents-write"
|
|
9940
|
+
|
|
9941
|
+
onPullRequest: (ctx, pr) =>
|
|
9942
|
+
pr.action === "opened" ? { auth: defaultGitHubAuth(ctx) } : null,
|
|
9943
|
+
onCheckSuite: (ctx, suite) =>
|
|
9944
|
+
suite.conclusion === "failure" ? { task: () => triage(ctx) } : null,
|
|
9945
|
+
});
|
|
9946
|
+
```
|
|
9947
|
+
|
|
9948
|
+
Hooks: `onPullRequest`, `onComment`, `onIssue`, `onCheckSuite`,
|
|
9949
|
+
`onCheckRun`, `onWorkflowRun`, `onStatus`, plus `onEvent` and
|
|
9950
|
+
`onStart`/`onStop`.
|
|
9951
|
+
|
|
9952
|
+
| Return | Meaning |
|
|
9953
|
+
| --- | --- |
|
|
9954
|
+
| `{ auth }` | Model turn. Session shows in the playground. `workspaceFiles` can be a function. |
|
|
9955
|
+
| `{ task }` | Host work. No chat session. Use when the work can outlive a webhook timeout. |
|
|
9956
|
+
| `null` | Skip |
|
|
9957
|
+
|
|
9958
|
+
To keep repo scope in deploy config, use `cursorAccount: true`
|
|
9959
|
+
and pass `--repo owner/name` at serve / `--cursor-events-repo`
|
|
9960
|
+
at deploy. Repos must share one GitHub owner.
|
|
9961
|
+
|
|
9962
|
+
## Event sources
|
|
9963
|
+
|
|
9964
|
+
| Source | When |
|
|
9965
|
+
| --- | --- |
|
|
9966
|
+
| `cursorAccount` + `serve --cursor-events` | Preferred. Signed-in host (`agent-sdk login` / `CURSOR_API_KEY`). Repos from the channel and from repeatable `--repo owner/name`. Cap 20, one GitHub owner |
|
|
9967
|
+
| HTTP `POST /<slug>/v1/channels/github` with a webhook secret | `allowAll()` + `X-Hub-Signature-256` |
|
|
9968
|
+
| HTTP, no secret | Loopback only. `serve --dev` also admits unsigned loopback (fixtures / forward) |
|
|
9969
|
+
|
|
9970
|
+
`permissions`: `"read"` inspect; `"pr-write"` (default) comments /
|
|
9971
|
+
PR writes; `"contents-write"` push or merge-box checks.
|
|
9972
|
+
`progress.commitStatus` needs check-write; see the GitHub guide.
|
|
9973
|
+
Set `checks: true` when channel code posts its own Checks API
|
|
9974
|
+
runs through `ctx.github.createCheck`. The flag grants access.
|
|
9975
|
+
It does not post a check.
|
|
9976
|
+
|
|
9977
|
+
Without `cursorAccount`, outbound calls prefer App installation
|
|
9978
|
+
tokens (`GITHUB_APP_ID` + `GITHUB_APP_PRIVATE_KEY`). Local tests
|
|
9979
|
+
can use `GITHUB_TOKEN` / `gh auth login`.
|
|
9980
|
+
|
|
9981
|
+
The Cursor stream is metadata, not full webhook bodies. Re-read
|
|
9982
|
+
the PR from GitHub.
|
|
9983
|
+
|
|
9984
|
+
## Test locally
|
|
9985
|
+
|
|
9986
|
+
1. **Fixtures** (offline, `--dev`, no signature):
|
|
9987
|
+
|
|
9988
|
+
```bash
|
|
9989
|
+
curl -s -X POST http://127.0.0.1:3000/<slug>/v1/channels/github \
|
|
9990
|
+
-H 'content-type: application/json' \
|
|
9991
|
+
-H 'x-github-event: pull_request' \
|
|
9992
|
+
-d @fixtures/github/pull_request.synchronize.json
|
|
9993
|
+
```
|
|
9994
|
+
|
|
9995
|
+
2. **Replay** (hillclimb tier; pull access is enough):
|
|
9996
|
+
|
|
9997
|
+
```bash
|
|
9998
|
+
agent-sdk github replay owner/repo#123 --dir <project>
|
|
9999
|
+
agent-sdk github replay owner/repo#123 --dir <project> --events '*' --dry-run --out fixtures/github
|
|
10000
|
+
```
|
|
10001
|
+
|
|
10002
|
+
3. **Forward** (live; repo admin). One forwarder per repo. Blank
|
|
10003
|
+
`GITHUB_TOKEN`/`GH_TOKEN` or every delivery 401s:
|
|
10004
|
+
|
|
10005
|
+
```bash
|
|
10006
|
+
agent-sdk github doctor --install
|
|
10007
|
+
GITHUB_TOKEN= GH_TOKEN= agent-sdk github forward --dir <project>
|
|
10008
|
+
```
|
|
10009
|
+
|
|
10010
|
+
4. **Cursor pull** (same as production):
|
|
10011
|
+
|
|
10012
|
+
```bash
|
|
10013
|
+
agent-sdk serve --dir <project> --cursor-events --repo owner/repo
|
|
10014
|
+
```
|
|
10015
|
+
|
|
10016
|
+
Volume, debounce, and `progress.commitStatus` / `progress.banner`
|
|
10017
|
+
live in `docs/guides/github.md`. Do not preinstall them.
|
|
10018
|
+
|
|
10019
|
+
---
|
|
10020
|
+
|
|
10021
|
+
Source: /docs/skills/hillclimb.md
|
|
10022
|
+
|
|
10023
|
+
# Agent SDK hillclimb
|
|
10024
|
+
|
|
10025
|
+
Measure → change one lever → remeasure. One failure mode per round.
|
|
10026
|
+
|
|
10027
|
+
Siblings: `skills/evals/SKILL.md`, `skills/github/SKILL.md`,
|
|
10028
|
+
`skills/debug/SKILL.md`.
|
|
10029
|
+
|
|
10030
|
+
## Preconditions
|
|
10031
|
+
|
|
10032
|
+
From the user or the invoking message:
|
|
10033
|
+
|
|
10034
|
+
1. **Target.** Path or slug
|
|
10035
|
+
2. **Fixtures.** Fixed inputs
|
|
10036
|
+
3. **Success.** What better means this round
|
|
10037
|
+
4. **Freeze line.** What must not change
|
|
10038
|
+
|
|
10039
|
+
Ask before editing if any are missing. A moving fixture is noise.
|
|
10040
|
+
|
|
10041
|
+
| Surface | Pin it |
|
|
10042
|
+
| --- | --- |
|
|
10043
|
+
| GitHub | `agent-sdk github replay <pr> --dir <project>` (`--dry-run --out fixtures/github`) |
|
|
10044
|
+
| One tool | `agent-sdk call <tool> --dir <project> --input '{...}'` |
|
|
10045
|
+
| Chat | `agent-sdk run --dir <project> --message "<fixture>"` |
|
|
10046
|
+
|
|
10047
|
+
## Loop
|
|
10048
|
+
|
|
10049
|
+
1. **Serve.** `agent-sdk serve --dir <project> --mode single --dev`
|
|
10050
|
+
Playground: `http://127.0.0.1:3000/playground`.
|
|
10051
|
+
2. **Hit it.** Same path a user would. Record status, wall time,
|
|
10052
|
+
`sessionId`, output, and `action.result` counts by `toolName`.
|
|
10053
|
+
3. **Name the failure.** Score correctness, efficiency, harness
|
|
10054
|
+
fit. One dominant failure this round.
|
|
10055
|
+
4. **Change one lever.** Smallest first. Delete the code or prompt
|
|
10056
|
+
that caused it. Then instructions / skills, evidence shape,
|
|
10057
|
+
host prep (`workspaceFiles`, channel `callTool`) for wandering
|
|
10058
|
+
and latency (not formatting or judgment), remove or gate
|
|
10059
|
+
wandering tools, framework only if the agent cannot express
|
|
10060
|
+
the fix. Hypothesis: *If we X, metric Y should move because Z.*
|
|
10061
|
+
5. **Remeasure.** Same fixtures. Keep only if the target metric
|
|
10062
|
+
improves and the freeze line holds.
|
|
10063
|
+
6. **Lock.** A kept change gets an eval that would have failed
|
|
10064
|
+
before it (`skills/evals/SKILL.md`). Never weaken a gate to
|
|
10065
|
+
pass a round.
|
|
10066
|
+
|
|
10067
|
+
```markdown
|
|
10068
|
+
### Hillclimb round N. `<slug>`
|
|
10069
|
+
- Fixture(s): …
|
|
10070
|
+
- Hypothesis: …
|
|
10071
|
+
- Change: …
|
|
10072
|
+
- Before → after: tools …; wall …; quality …
|
|
10073
|
+
- Verdict: keep | revert | narrow
|
|
10074
|
+
- Next failure mode:
|
|
10075
|
+
```
|
|
10076
|
+
|
|
10077
|
+
Do not deploy or post real GitHub reviews unless asked.
|
|
10078
|
+
|
|
10079
|
+
---
|
|
10080
|
+
|
|
10081
|
+
Source: /docs/skills/index.md
|
|
10082
|
+
|
|
10083
|
+
# Coding-agent skills
|
|
10084
|
+
|
|
10085
|
+
Each skill is a procedure a coding agent can follow. Installing
|
|
10086
|
+
`@cursor/july` copies them into `~/.cursor/skills/agentsdk/`. This site
|
|
10087
|
+
publishes the same files.
|
|
10088
|
+
|
|
10089
|
+
See [Building agents with agents](/docs/building-with-agents.md) for when
|
|
10090
|
+
to use each one.
|
|
10091
|
+
|
|
10092
|
+
| Skill | Use it to |
|
|
10093
|
+
| --- | --- |
|
|
10094
|
+
| [framework-map](/docs/skills/framework-map.md) | Learn the project layout and runtimes |
|
|
10095
|
+
| [create-agent](/docs/skills/create-agent.md) | Scaffold and verify a new agent |
|
|
10096
|
+
| [evals](/docs/skills/evals.md) | Write fixtures and regression checks |
|
|
10097
|
+
| [ab](/docs/skills/ab.md) | Compare variants on live traffic |
|
|
10098
|
+
| [otel](/docs/skills/otel.md) | Export OpenTelemetry traces |
|
|
10099
|
+
| [hillclimb](/docs/skills/hillclimb.md) | Improve an agent against fixed inputs |
|
|
10100
|
+
| [github](/docs/skills/github.md) | Add GitHub webhooks and replay events |
|
|
10101
|
+
| [setup-slack](/docs/skills/setup-slack.md) | Connect an agent to Slack |
|
|
10102
|
+
| [mcp-auth](/docs/skills/mcp-auth.md) | Authorize host MCP OAuth |
|
|
10103
|
+
| [debug](/docs/skills/debug.md) | Diagnose a local run |
|
|
10104
|
+
|
|
10105
|
+
---
|
|
10106
|
+
|
|
10107
|
+
Source: /docs/skills/mcp-auth.md
|
|
10108
|
+
|
|
10109
|
+
# Host MCP OAuth
|
|
10110
|
+
|
|
10111
|
+
Guide: `docs/guides/mcp-oauth.md`.
|
|
10112
|
+
|
|
10113
|
+
| Need | Use |
|
|
10114
|
+
| --- | --- |
|
|
10115
|
+
| Connector already in the Cursor dashboard | `defineConnection({ cursorAccount: true })` or `servers: "*"` / `servers: […]` |
|
|
10116
|
+
| Remote URL that speaks OAuth; host holds tokens | `defineConnection({ url, oauth: true })` + this skill |
|
|
10117
|
+
| Static bearer / API key | `headers` / env on `{ url }` |
|
|
10118
|
+
|
|
10119
|
+
`advertiseTools: true` puts named tools on local turns. Host tools
|
|
10120
|
+
can still call `ctx.host.mcp`.
|
|
10121
|
+
|
|
10122
|
+
## Checklist
|
|
10123
|
+
|
|
10124
|
+
1. **Declare the connection.** `agent/mcp-connections/<name>.ts`
|
|
10125
|
+
with `url` + `oauth: true`. Use `agent/host-connections/` when
|
|
10126
|
+
the model must not see it.
|
|
10127
|
+
2. **Name the secrets** if you will `--store`:
|
|
10128
|
+
`hosting.secretNames` lists
|
|
10129
|
+
`MCP_OAUTH_<NAME>_{ACCESS_TOKEN,REFRESH_TOKEN,CLIENT_ID}`.
|
|
10130
|
+
3. **Allow egress** on hosted non-bootstrap hosts:
|
|
10131
|
+
`hosting.egressDomains`.
|
|
10132
|
+
4. **Authorize.** Local: `agent-sdk mcp oauth <name>`. Hosted:
|
|
10133
|
+
finish Connect so the current process can retry, then
|
|
10134
|
+
`agent-sdk mcp oauth <name> --store` and `agent-sdk deploy` so
|
|
10135
|
+
the next pod gets `MCP_OAUTH_*`. `secrets list` shows the names.
|
|
10136
|
+
Secrets are deployment-wide, not per caller. `cursorAccount: true`
|
|
10137
|
+
stays on the Cursor backend.
|
|
10138
|
+
|
|
10139
|
+
```ts
|
|
10140
|
+
// agent/mcp-connections/inventory.ts
|
|
10141
|
+
export default defineConnection({
|
|
10142
|
+
url: "https://mcp.example.com/inventory",
|
|
10143
|
+
oauth: true,
|
|
10144
|
+
});
|
|
10145
|
+
```
|
|
10146
|
+
|
|
10147
|
+
```ts
|
|
10148
|
+
// agent/agent.ts
|
|
10149
|
+
export default defineAgent({
|
|
10150
|
+
hosting: {
|
|
10151
|
+
secretNames: [
|
|
10152
|
+
"MCP_OAUTH_INVENTORY_ACCESS_TOKEN",
|
|
10153
|
+
"MCP_OAUTH_INVENTORY_REFRESH_TOKEN",
|
|
10154
|
+
"MCP_OAUTH_INVENTORY_CLIENT_ID",
|
|
10155
|
+
],
|
|
10156
|
+
egressDomains: ["mcp.example.com"],
|
|
10157
|
+
},
|
|
10158
|
+
});
|
|
10159
|
+
```
|
|
10160
|
+
|
|
10161
|
+
File `inventory.ts` → prefix `MCP_OAUTH_INVENTORY`. Do not put
|
|
10162
|
+
`CURSOR_*` names in `secretNames`.
|
|
10163
|
+
|
|
10164
|
+
```bash
|
|
10165
|
+
agent-sdk mcp oauth <connection>
|
|
10166
|
+
agent-sdk mcp oauth <connection> --store [--slug <slug>]
|
|
10167
|
+
agent-sdk secrets list <slug>
|
|
10168
|
+
agent-sdk deploy
|
|
10169
|
+
```
|
|
10170
|
+
|
|
10171
|
+
Browser callback: `http://127.0.0.1:8787/callback`. Tokens live in
|
|
10172
|
+
the CLI config directory (`mcp-auth.json` or
|
|
10173
|
+
`$AGENT_SERVE_CONFIG_DIR`). URL change drops the old entry; re-run.
|
|
10174
|
+
`--store` does not restart a running engine.
|
|
10175
|
+
|
|
10176
|
+
| Symptom | Fix |
|
|
10177
|
+
| --- | --- |
|
|
10178
|
+
| `must be defineConnection({ url, oauth: true })` | Wrong name or missing `oauth: true` |
|
|
10179
|
+
| `Unknown MCP connection` | Filename must match the CLI arg |
|
|
10180
|
+
| Callback hang | Free port 8787; finish the browser flow here |
|
|
10181
|
+
| Hosted 401 | `secrets list`; Connect or `--store`; redeploy |
|
|
10182
|
+
| Model invents `mcp_auth` / IDE MCP | `advertiseTools: true` on local turns |
|
|
10183
|
+
|
|
10184
|
+
No raw tokens in git.
|
|
10185
|
+
|
|
10186
|
+
---
|
|
10187
|
+
|
|
10188
|
+
Source: /docs/skills/otel.md
|
|
10189
|
+
|
|
10190
|
+
# Agent SDK OpenTelemetry (`defineOtel`)
|
|
10191
|
+
|
|
10192
|
+
Push traces and metrics from the serve process to an OTLP
|
|
10193
|
+
collector. Logs are off until you opt in.
|
|
10194
|
+
|
|
10195
|
+
Guide: `docs/guides/opentelemetry.md`.
|
|
10196
|
+
|
|
10197
|
+
## Enable
|
|
10198
|
+
|
|
10199
|
+
Any one of:
|
|
10200
|
+
|
|
10201
|
+
1. `OTEL_EXPORTER_OTLP_ENDPOINT` (optional
|
|
10202
|
+
`OTEL_SERVICE_NAME`, `OTEL_EXPORTER_OTLP_HEADERS`,
|
|
10203
|
+
`OTEL_EXPORTER_OTLP_PROTOCOL=http/protobuf|http/json`)
|
|
10204
|
+
2. `agent/otel.ts`:
|
|
10205
|
+
|
|
10206
|
+
```ts
|
|
10207
|
+
import { defineOtel } from "@cursor/july/otel";
|
|
10208
|
+
|
|
10209
|
+
export default defineOtel({
|
|
10210
|
+
serviceName: "cursor",
|
|
10211
|
+
exporters: [{ url: "https://otel.example.com", protocol: "http/protobuf" }],
|
|
10212
|
+
});
|
|
10213
|
+
```
|
|
10214
|
+
|
|
10215
|
+
3. `serve(dir, { otel: { … } })`. `otel: false` disables env and
|
|
10216
|
+
authored config.
|
|
10217
|
+
|
|
10218
|
+
| Signal | Default |
|
|
10219
|
+
| --- | --- |
|
|
10220
|
+
| Traces | on (`agent_sdk.http` → session → turn → tool / subagent) |
|
|
10221
|
+
| Metrics | on (`cursor.token.usage`, `cursor.tool.calls`, `cursor.cost.usage`) |
|
|
10222
|
+
| Logs | off (`logs: true` or `OTEL_LOGS_EXPORTER=otlp`) |
|
|
10223
|
+
|
|
10224
|
+
Prompt text and tool payloads stay off the wire unless you set
|
|
10225
|
+
`OTEL_LOG_USER_PROMPTS` / `OTEL_LOG_TOOL_CONTENT`.
|
|
10226
|
+
|
|
10227
|
+
## Custom metrics
|
|
10228
|
+
|
|
10229
|
+
```ts
|
|
10230
|
+
ctx.host.otel.setAttributes({ "abc.ticket_id": "INC-123" });
|
|
10231
|
+
ctx.host.otel.increment("abc.ticket.resolved");
|
|
10232
|
+
ctx.host.otel.record("abc.approval.duration_ms", 1420);
|
|
10233
|
+
```
|
|
10234
|
+
|
|
10235
|
+
Prefix names with team or agent. No custom spans. Join on
|
|
10236
|
+
`cursor.conversation.id` and `agent_sdk.agent`. Run `serve` as its
|
|
10237
|
+
own process when Agent SDK should own the destination.
|
|
10238
|
+
|
|
10239
|
+
---
|
|
10240
|
+
|
|
10241
|
+
Source: /docs/skills/setup-slack.md
|
|
10242
|
+
|
|
10243
|
+
# Setup Slack for the Agent SDK
|
|
10244
|
+
|
|
10245
|
+
Dedicated Socket Mode bot. `agent-sdk slack create` opens the
|
|
10246
|
+
signed-in dashboard wizard. Tokens land in `.env.local` and as
|
|
10247
|
+
deployment secrets. Never print token values.
|
|
10248
|
+
|
|
10249
|
+
Do not generate manifests or ask anyone to paste tokens unless
|
|
10250
|
+
they asked for `slack init --manual`.
|
|
10251
|
+
|
|
10252
|
+
Existing `<PREFIX>_SLACK_BOT_TOKEN` + `_SLACK_APP_TOKEN` in
|
|
10253
|
+
`.env.local` keep working. Do not force those onto the wizard.
|
|
10254
|
+
|
|
10255
|
+
Guide: `docs/guides/slack.md`.
|
|
10256
|
+
|
|
10257
|
+
## 1. Wizard (default)
|
|
10258
|
+
|
|
10259
|
+
```bash
|
|
10260
|
+
agent-sdk login
|
|
10261
|
+
agent-sdk slack create --dir .
|
|
10262
|
+
```
|
|
10263
|
+
|
|
10264
|
+
Same Cursor account in the browser. **Add Slack to this agent**,
|
|
10265
|
+
approve Slack, pick the bot name. CLI writes
|
|
10266
|
+
`<PREFIX>_SLACK_BOT_TOKEN` / `<PREFIX>_SLACK_APP_TOKEN` and runs
|
|
10267
|
+
`doctor`.
|
|
10268
|
+
|
|
10269
|
+
Prefix is the directory basename in upper snake (`jenny` →
|
|
10270
|
+
`JENNY`, `pr-approver` → `PR_APPROVER` → `PR_APPROVER_SLACK_*`).
|
|
10271
|
+
`--prefix` / `--no-prefix` override. Dev and prod are separate
|
|
10272
|
+
apps; `--prod` is the prod app. `--name` / `--icon` /
|
|
10273
|
+
`--channel-posts` / `--slack-team` prefill the wizard.
|
|
10274
|
+
|
|
10275
|
+
If Slack needs workspace-admin approval, keep the CLI running.
|
|
10276
|
+
Open the **Request approval** link it prints. Managed install
|
|
10277
|
+
does not file the request. After approval, **Retry** in the
|
|
10278
|
+
wizard.
|
|
10279
|
+
|
|
10280
|
+
`create` scaffolds `agent/channels/slack.ts` when missing:
|
|
10281
|
+
|
|
10282
|
+
```ts
|
|
10283
|
+
export default slackChannel({
|
|
10284
|
+
envPrefix: "JENNY",
|
|
10285
|
+
suggestedPrompts: [{ title: "Help", message: "How can you help me?" }],
|
|
10286
|
+
});
|
|
10287
|
+
```
|
|
10288
|
+
|
|
10289
|
+
Return from dispatch handlers. Do not await long work in the
|
|
10290
|
+
handler.
|
|
10291
|
+
|
|
10292
|
+
A second `slack create` for the same agent and env overwrites the
|
|
10293
|
+
app (same Slack app id, new manifest and tokens).
|
|
10294
|
+
`agent-sdk slack destroy` deletes it.
|
|
10295
|
+
|
|
10296
|
+
Local serve does not need a hosted engine. Next
|
|
10297
|
+
`agent-sdk deploy` injects the stored secrets.
|
|
10298
|
+
|
|
10299
|
+
## 2. Manual (`slack init --manual`)
|
|
10300
|
+
|
|
10301
|
+
Only when they own the app. Preferred: Slack CLI
|
|
10302
|
+
(`~/.slack/bin/slack`). Paste at api.slack.com if the CLI is
|
|
10303
|
+
missing. Never `slack deploy`; Agent SDK serve owns Socket Mode.
|
|
10304
|
+
|
|
10305
|
+
```bash
|
|
10306
|
+
agent-sdk slack init --manual --dir . --name "My Agent"
|
|
10307
|
+
# --slack-team T0123ABCD when several workspaces are logged in
|
|
10308
|
+
# --no-install to scaffold only
|
|
10309
|
+
```
|
|
10310
|
+
|
|
10311
|
+
Writes `agent/channels/slack.ts` (`envPrefix` from the directory),
|
|
10312
|
+
manifests, a `.slack/` project (`get-manifest` → those JSON files),
|
|
10313
|
+
and `env.example`. `--channel-posts` subscribes `message.channels`
|
|
10314
|
+
/ `message.groups`. If Slack CLI is logged in, this installs the
|
|
10315
|
+
app. `--install` fails when that cannot run.
|
|
10316
|
+
|
|
10317
|
+
Human gates, one at a time. Stop after each.
|
|
10318
|
+
|
|
10319
|
+
1. **Install the app.** If `next` starts with "Ask the user to
|
|
10320
|
+
install this Slack app", stop and prompt them. Slack CLI: they
|
|
10321
|
+
run `slack login --no-prompt`, send `/slackauthticket <ticket>`,
|
|
10322
|
+
then `slack login --ticket <ticket> --challenge <code>`, then
|
|
10323
|
+
`slack app install --environment local --team <T> --force`.
|
|
10324
|
+
Prod: `SLACK_ENV=deployed slack app install --environment
|
|
10325
|
+
deployed --team <T> --force`. Fallback: Create New App → From a
|
|
10326
|
+
manifest, start with `.slack/manifest.dev.json`.
|
|
10327
|
+
2. **Tokens.** Slack CLI leaves xoxb / xapp in that process only.
|
|
10328
|
+
Copy the bot token from the app's OAuth page. Mint an app-level
|
|
10329
|
+
token with `connections:write`. Put both in `.env.local` using
|
|
10330
|
+
`env.example` names. If Slack CLI wrote `SLACK_*` to `.env`,
|
|
10331
|
+
copy those values to the prefixed keys.
|
|
10332
|
+
3. **Doctor.**
|
|
10333
|
+
|
|
10334
|
+
## 3. Doctor and smoke
|
|
10335
|
+
|
|
10336
|
+
```bash
|
|
10337
|
+
agent-sdk slack doctor --prefix JENNY
|
|
10338
|
+
agent-sdk serve --dir . --dev
|
|
10339
|
+
```
|
|
10340
|
+
|
|
10341
|
+
Green: `app_token`, `connections_open`, `bot_token`, `auth_test`.
|
|
10342
|
+
Log: `[agent-sdk/slack] Socket Mode connected`. Missing tokens
|
|
10343
|
+
idle the channel; `serve` continues.
|
|
10344
|
+
|
|
10345
|
+
1. Invite the bot
|
|
10346
|
+
2. `@mention` or DM
|
|
10347
|
+
3. Thinking / Working, then a threaded reply
|
|
10348
|
+
4. Logs: `inbound kind=app_mention`, `session start`,
|
|
10349
|
+
`reply delivered via postMessage|stream`
|
|
10350
|
+
|
|
10351
|
+
## Watch channels (opt-in)
|
|
10352
|
+
|
|
10353
|
+
Default is mentions + DMs only. To wake on new posts:
|
|
10354
|
+
|
|
10355
|
+
```ts
|
|
10356
|
+
export default slackChannel({
|
|
10357
|
+
envPrefix: "JENNY",
|
|
10358
|
+
engagement: {
|
|
10359
|
+
channelPosts: {
|
|
10360
|
+
allow: ["#alerts"], // ["*"] for every joined channel
|
|
10361
|
+
posts: "top-level",
|
|
10362
|
+
},
|
|
10363
|
+
},
|
|
10364
|
+
onChannelPost: async (ctx, message) => ({}), // null = skip
|
|
10365
|
+
});
|
|
10366
|
+
```
|
|
10367
|
+
|
|
10368
|
+
Pass `--channel-posts` on `create` / `init --manual`. Invite the
|
|
10369
|
+
bot to each watched channel. Mentions stay on `app_mention`; a
|
|
10370
|
+
later mention continues the watch thread.
|
|
10371
|
+
|
|
10372
|
+
## Approvals (opt-in)
|
|
10373
|
+
|
|
10374
|
+
```ts
|
|
10375
|
+
export default slackChannel({
|
|
10376
|
+
envPrefix: "JENNY",
|
|
10377
|
+
toolApprovals: true,
|
|
10378
|
+
});
|
|
10379
|
+
```
|
|
10380
|
+
|
|
10381
|
+
Wizard enables interactivity when this is set. Server tools on
|
|
10382
|
+
`local` only. Parked calls die on host restart. Cards truncate
|
|
10383
|
+
args; execution uses the full input.
|
|
10384
|
+
|
|
10385
|
+
---
|
|
10386
|
+
|
|
9376
10387
|
Source: /docs/storage.md
|
|
9377
10388
|
|
|
9378
10389
|
# Storage
|
|
@@ -10399,7 +11410,7 @@ not on `PATH`, use `npx @cursor/july`.
|
|
|
10399
11410
|
| Model asks for `mcp_auth` or IDE MCP for a connector it already has | Attached MCP is behind meta-tools. Set `advertiseTools: true` for named tools on local turns, or call it from a host tool via `ctx.host.mcp`. |
|
|
10400
11411
|
|
|
10401
11412
|
See [Host MCP OAuth](/docs/guides/mcp-oauth.md) and
|
|
10402
|
-
[`skills/mcp-auth/SKILL.md`](
|
|
11413
|
+
[`skills/mcp-auth/SKILL.md`](/docs/skills/mcp-auth.md).
|
|
10403
11414
|
|
|
10404
11415
|
## What if a secret showed up in a terminal transcript?
|
|
10405
11416
|
|