@cursor/july 0.1.95 → 0.1.97

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.
Files changed (424) hide show
  1. package/AGENTS.md +3 -4
  2. package/README.md +3 -2
  3. package/dist/bin/agent-serve.js +14 -3
  4. package/dist/channels/deployments/types.d.ts +1 -1
  5. package/dist/channels/deployments/types.d.ts.map +1 -1
  6. package/dist/channels/deployments/types.js +1 -0
  7. package/dist/channels/origin/api.d.ts +72 -15
  8. package/dist/channels/origin/api.d.ts.map +1 -1
  9. package/dist/channels/origin/api.js +185 -28
  10. package/dist/channels/origin/binding.d.ts +13 -2
  11. package/dist/channels/origin/binding.d.ts.map +1 -1
  12. package/dist/channels/origin/binding.js +41 -25
  13. package/dist/channels/origin/checks.d.ts +6 -6
  14. package/dist/channels/origin/checks.js +6 -6
  15. package/dist/channels/origin/cursor-account.d.ts +5 -3
  16. package/dist/channels/origin/cursor-account.d.ts.map +1 -1
  17. package/dist/channels/origin/cursor-account.js +5 -3
  18. package/dist/channels/origin/index.d.ts +1 -0
  19. package/dist/channels/origin/index.d.ts.map +1 -1
  20. package/dist/channels/origin/index.js +1 -0
  21. package/dist/channels/origin/origin-channel.d.ts.map +1 -1
  22. package/dist/channels/origin/origin-channel.js +3 -0
  23. package/dist/channels/origin/reactions.d.ts +56 -0
  24. package/dist/channels/origin/reactions.d.ts.map +1 -0
  25. package/dist/channels/origin/reactions.js +67 -0
  26. package/dist/channels/origin/types.d.ts +11 -0
  27. package/dist/channels/origin/types.d.ts.map +1 -1
  28. package/dist/channels/slack/api.d.ts +9 -0
  29. package/dist/channels/slack/api.d.ts.map +1 -1
  30. package/dist/channels/slack/api.js +36 -5
  31. package/dist/channels/slack/approvals.d.ts +16 -0
  32. package/dist/channels/slack/approvals.d.ts.map +1 -1
  33. package/dist/channels/slack/approvals.js +86 -0
  34. package/dist/channels/slack/cli-project.d.ts +19 -0
  35. package/dist/channels/slack/cli-project.d.ts.map +1 -0
  36. package/dist/channels/slack/cli-project.js +234 -0
  37. package/dist/channels/slack/defaults.d.ts.map +1 -1
  38. package/dist/channels/slack/defaults.js +110 -81
  39. package/dist/channels/slack/dispatch.d.ts +7 -1
  40. package/dist/channels/slack/dispatch.d.ts.map +1 -1
  41. package/dist/channels/slack/dispatch.js +47 -23
  42. package/dist/channels/slack/inbound.d.ts +8 -0
  43. package/dist/channels/slack/inbound.d.ts.map +1 -1
  44. package/dist/channels/slack/inbound.js +32 -0
  45. package/dist/channels/slack/init.d.ts +3 -2
  46. package/dist/channels/slack/init.d.ts.map +1 -1
  47. package/dist/channels/slack/init.js +5 -5
  48. package/dist/channels/slack/interactive.d.ts +2 -1
  49. package/dist/channels/slack/interactive.d.ts.map +1 -1
  50. package/dist/channels/slack/interactive.js +15 -4
  51. package/dist/channels/slack/live-delivery.d.ts +26 -29
  52. package/dist/channels/slack/live-delivery.d.ts.map +1 -1
  53. package/dist/channels/slack/live-delivery.js +172 -73
  54. package/dist/channels/slack/manifest.d.ts +1 -1
  55. package/dist/channels/slack/manifest.d.ts.map +1 -1
  56. package/dist/channels/slack/manifest.js +6 -2
  57. package/dist/channels/slack/nudge-carrier.d.ts +2 -0
  58. package/dist/channels/slack/nudge-carrier.d.ts.map +1 -1
  59. package/dist/channels/slack/nudge-carrier.js +48 -1
  60. package/dist/channels/slack/setup.d.ts +1 -1
  61. package/dist/channels/slack/setup.d.ts.map +1 -1
  62. package/dist/channels/slack/setup.js +10 -6
  63. package/dist/channels/slack/slack-channel.d.ts.map +1 -1
  64. package/dist/channels/slack/slack-channel.js +3 -2
  65. package/dist/channels/slack/tool-approval-events.d.ts.map +1 -1
  66. package/dist/channels/slack/tool-approval-events.js +91 -1
  67. package/dist/docs/404.html +2 -2
  68. package/dist/docs/ab.html +4 -4
  69. package/dist/docs/assets/{app.BBj0klBO.js → app.B3rWNYE1.js} +1 -1
  70. package/dist/docs/assets/chunks/@localSearchIndexroot.BU9nHdnQ.js +1 -0
  71. package/dist/docs/assets/chunks/{VPLocalSearchBox.CUEXpL78.js → VPLocalSearchBox.C1lhqJJR.js} +1 -1
  72. package/dist/docs/assets/chunks/{theme.DabmQnia.js → theme.B40_SXuv.js} +2 -2
  73. package/dist/docs/assets/{deployment.md.D9msOFOW.js → deployment.md.MFPKqsqI.js} +2 -2
  74. package/dist/docs/assets/{guides_mcp-oauth.md.DPYmBCbV.js → guides_mcp-oauth.md.CN-6YmTJ.js} +4 -4
  75. package/dist/docs/assets/{guides_mcp-oauth.md.DPYmBCbV.lean.js → guides_mcp-oauth.md.CN-6YmTJ.lean.js} +1 -1
  76. package/dist/docs/assets/guides_slack.md.VDXQV3ja.js +22 -0
  77. package/dist/docs/assets/guides_slack.md.VDXQV3ja.lean.js +1 -0
  78. package/dist/docs/assets/index.md.CVeRUOeZ.js +5 -0
  79. package/dist/docs/assets/{index.md.BoHaMdeZ.lean.js → index.md.CVeRUOeZ.lean.js} +1 -1
  80. package/dist/docs/assets/{reference_agent-config.md.Cp_x38Nl.js → reference_agent-config.md.BHeYMgme.js} +1 -1
  81. package/dist/docs/assets/{reference_cli.md.BsMOxDvh.js → reference_cli.md.RyZf5OTE.js} +10 -6
  82. package/dist/docs/assets/{reference_cli.md.BsMOxDvh.lean.js → reference_cli.md.RyZf5OTE.lean.js} +1 -1
  83. package/dist/docs/assets/{reference_connections.md.BH8Oc0D0.js → reference_connections.md.DxldvyIB.js} +4 -3
  84. package/dist/docs/assets/{reference_http-api.md.D89k1mdm.js → reference_http-api.md.5zOAbV86.js} +1 -1
  85. package/dist/docs/assets/reference_sessions.md.NxFP_CAC.js +1 -0
  86. package/dist/docs/assets/{reference_tools.md.BHeXn2id.js → reference_tools.md.B84gw9Ii.js} +1 -1
  87. package/dist/docs/assets/templates_agents-md.md.CXSMZljE.js +2 -0
  88. package/dist/docs/assets/templates_agents-md.md.CXSMZljE.lean.js +1 -0
  89. package/dist/docs/assets/templates_code-wiki.md.CDYZIBFN.js +2 -0
  90. package/dist/docs/assets/templates_code-wiki.md.CDYZIBFN.lean.js +1 -0
  91. package/dist/docs/assets/troubleshooting.md.DCiPBhYs.js +1 -0
  92. package/dist/docs/building-with-agents.html +4 -4
  93. package/dist/docs/concepts.html +4 -4
  94. package/dist/docs/deployment.html +7 -7
  95. package/dist/docs/deployment.md +5 -4
  96. package/dist/docs/evals.html +4 -4
  97. package/dist/docs/guides/agent-to-agent.html +4 -4
  98. package/dist/docs/guides/cloud-runtime.html +4 -4
  99. package/dist/docs/guides/convert-automation.html +4 -4
  100. package/dist/docs/guides/github.html +4 -4
  101. package/dist/docs/guides/human-in-the-loop.html +4 -4
  102. package/dist/docs/guides/mcp-oauth.html +8 -8
  103. package/dist/docs/guides/mcp-oauth.md +26 -8
  104. package/dist/docs/guides/opentelemetry.html +4 -4
  105. package/dist/docs/guides/slack.html +17 -33
  106. package/dist/docs/guides/slack.md +92 -201
  107. package/dist/docs/guides/webhooks.html +4 -4
  108. package/dist/docs/hashmap.json +1 -1
  109. package/dist/docs/hillclimbing.html +4 -4
  110. package/dist/docs/index.html +6 -6
  111. package/dist/docs/index.md +7 -3
  112. package/dist/docs/llms-full.txt +398 -653
  113. package/dist/docs/llms.txt +3 -2
  114. package/dist/docs/quickstart.html +4 -4
  115. package/dist/docs/reference/agent-config.html +6 -6
  116. package/dist/docs/reference/agent-config.md +2 -2
  117. package/dist/docs/reference/artifacts.html +4 -4
  118. package/dist/docs/reference/channels.html +4 -4
  119. package/dist/docs/reference/cli.html +14 -10
  120. package/dist/docs/reference/cli.md +39 -16
  121. package/dist/docs/reference/connections.html +9 -8
  122. package/dist/docs/reference/connections.md +6 -3
  123. package/dist/docs/reference/hooks.html +4 -4
  124. package/dist/docs/reference/http-api.html +6 -6
  125. package/dist/docs/reference/http-api.md +2 -1
  126. package/dist/docs/reference/instructions.html +4 -4
  127. package/dist/docs/reference/playground.html +4 -4
  128. package/dist/docs/reference/project-layout.html +4 -4
  129. package/dist/docs/reference/prompt.html +4 -4
  130. package/dist/docs/reference/schedules.html +4 -4
  131. package/dist/docs/reference/sessions.html +5 -5
  132. package/dist/docs/reference/sessions.md +4 -2
  133. package/dist/docs/reference/skills.html +4 -4
  134. package/dist/docs/reference/subagents.html +4 -4
  135. package/dist/docs/reference/tools.html +6 -6
  136. package/dist/docs/reference/tools.md +9 -2
  137. package/dist/docs/scaffolding-agents.html +4 -4
  138. package/dist/docs/storage.html +4 -4
  139. package/dist/docs/templates/agentic-owners.html +4 -4
  140. package/dist/docs/templates/agents-md.html +28 -0
  141. package/dist/docs/templates/agents-md.md +105 -0
  142. package/dist/docs/templates/code-wiki.html +28 -0
  143. package/dist/docs/templates/code-wiki.md +91 -0
  144. package/dist/docs/templates/demo.html +5 -5
  145. package/dist/docs/templates/pr-autofixer.html +4 -4
  146. package/dist/docs/templates/security-help.html +4 -4
  147. package/dist/docs/templates/security-reviewer.html +5 -5
  148. package/dist/docs/templates/triage.html +4 -4
  149. package/dist/docs/troubleshooting.html +5 -5
  150. package/dist/docs/troubleshooting.md +2 -2
  151. package/dist/evals/run-facts.d.ts.map +1 -1
  152. package/dist/evals/run-facts.js +27 -0
  153. package/dist/files-backends/cursor-hosted.d.ts +26 -4
  154. package/dist/files-backends/cursor-hosted.d.ts.map +1 -1
  155. package/dist/files-backends/cursor-hosted.js +32 -4
  156. package/dist/internal/advertise-tools.d.ts +2 -0
  157. package/dist/internal/advertise-tools.d.ts.map +1 -1
  158. package/dist/internal/advertise-tools.js +30 -10
  159. package/dist/internal/approval-gate.d.ts +12 -13
  160. package/dist/internal/approval-gate.d.ts.map +1 -1
  161. package/dist/internal/approval-gate.js +16 -21
  162. package/dist/internal/bounded.d.ts +7 -0
  163. package/dist/internal/bounded.d.ts.map +1 -0
  164. package/dist/internal/bounded.js +32 -0
  165. package/dist/internal/chat-client.js +10 -0
  166. package/dist/internal/cli-deploy.d.ts +5 -0
  167. package/dist/internal/cli-deploy.d.ts.map +1 -1
  168. package/dist/internal/cli-deploy.js +57 -18
  169. package/dist/internal/cli-mcp-oauth.js +8 -18
  170. package/dist/internal/cli-slack-manual.d.ts +24 -2
  171. package/dist/internal/cli-slack-manual.d.ts.map +1 -1
  172. package/dist/internal/cli-slack-manual.js +251 -20
  173. package/dist/internal/cli-slack.d.ts +9 -2
  174. package/dist/internal/cli-slack.d.ts.map +1 -1
  175. package/dist/internal/cli-slack.js +29 -82
  176. package/dist/internal/conversation-mirror.d.ts +11 -8
  177. package/dist/internal/conversation-mirror.d.ts.map +1 -1
  178. package/dist/internal/conversation-mirror.js +116 -55
  179. package/dist/internal/cursor/account-mcp.d.ts +1 -0
  180. package/dist/internal/cursor/account-mcp.d.ts.map +1 -1
  181. package/dist/internal/cursor/account-mcp.js +17 -0
  182. package/dist/internal/cursor/backend-client.d.ts.map +1 -1
  183. package/dist/internal/cursor/backend-client.js +22 -48
  184. package/dist/internal/cursor/session-token.d.ts +45 -0
  185. package/dist/internal/cursor/session-token.d.ts.map +1 -0
  186. package/dist/internal/cursor/session-token.js +99 -0
  187. package/dist/internal/cursor-agent-template.d.ts +1 -1
  188. package/dist/internal/cursor-agent-template.d.ts.map +1 -1
  189. package/dist/internal/cursor-agent-template.js +2 -0
  190. package/dist/internal/deploy-client.d.ts +17 -0
  191. package/dist/internal/deploy-client.d.ts.map +1 -1
  192. package/dist/internal/deploy-client.js +31 -10
  193. package/dist/internal/env-file.d.ts +19 -0
  194. package/dist/internal/env-file.d.ts.map +1 -0
  195. package/dist/internal/env-file.js +90 -0
  196. package/dist/internal/framework-file-storage.d.ts +61 -0
  197. package/dist/internal/framework-file-storage.d.ts.map +1 -0
  198. package/dist/internal/framework-file-storage.js +210 -0
  199. package/dist/internal/framework-storage-selection.d.ts +11 -5
  200. package/dist/internal/framework-storage-selection.d.ts.map +1 -1
  201. package/dist/internal/framework-storage-selection.js +38 -11
  202. package/dist/internal/hosted-delivery-protocol.d.ts +7 -0
  203. package/dist/internal/hosted-delivery-protocol.d.ts.map +1 -1
  204. package/dist/internal/hosted-delivery-protocol.js +7 -0
  205. package/dist/internal/hosted-delivery.d.ts +13 -0
  206. package/dist/internal/hosted-delivery.d.ts.map +1 -1
  207. package/dist/internal/hosted-delivery.js +64 -19
  208. package/dist/internal/hosted-execution-diag.d.ts +48 -0
  209. package/dist/internal/hosted-execution-diag.d.ts.map +1 -0
  210. package/dist/internal/hosted-execution-diag.js +150 -0
  211. package/dist/internal/http-channel.d.ts.map +1 -1
  212. package/dist/internal/http-channel.js +81 -1
  213. package/dist/internal/init-project.d.ts.map +1 -1
  214. package/dist/internal/init-project.js +4 -0
  215. package/dist/internal/install-cursor-skills.d.ts.map +1 -1
  216. package/dist/internal/install-cursor-skills.js +1 -3
  217. package/dist/internal/logs-client.d.ts +5 -0
  218. package/dist/internal/logs-client.d.ts.map +1 -1
  219. package/dist/internal/logs-client.js +5 -0
  220. package/dist/internal/managed-delivery.d.ts +80 -0
  221. package/dist/internal/managed-delivery.d.ts.map +1 -0
  222. package/dist/internal/managed-delivery.js +86 -0
  223. package/dist/internal/mcp-endpoint.js +2 -3
  224. package/dist/internal/mcp-host.d.ts +10 -0
  225. package/dist/internal/mcp-host.d.ts.map +1 -1
  226. package/dist/internal/mcp-host.js +57 -8
  227. package/dist/internal/mcp-oauth-on-demand.d.ts +68 -0
  228. package/dist/internal/mcp-oauth-on-demand.d.ts.map +1 -0
  229. package/dist/internal/mcp-oauth-on-demand.js +287 -0
  230. package/dist/internal/mcp-oauth-persist.d.ts +42 -0
  231. package/dist/internal/mcp-oauth-persist.d.ts.map +1 -0
  232. package/dist/internal/mcp-oauth-persist.js +92 -0
  233. package/dist/internal/mcp-oauth.d.ts +1 -0
  234. package/dist/internal/mcp-oauth.d.ts.map +1 -1
  235. package/dist/internal/mcp-oauth.js +10 -2
  236. package/dist/internal/otel/collector.d.ts.map +1 -1
  237. package/dist/internal/otel/collector.js +22 -9
  238. package/dist/internal/runtime-dispatch-runner.d.ts +5 -1
  239. package/dist/internal/runtime-dispatch-runner.d.ts.map +1 -1
  240. package/dist/internal/runtime-dispatch-runner.js +7 -0
  241. package/dist/internal/sdk-runner.d.ts +11 -0
  242. package/dist/internal/sdk-runner.d.ts.map +1 -1
  243. package/dist/internal/sdk-runner.js +39 -8
  244. package/dist/internal/server.d.ts +3 -0
  245. package/dist/internal/server.d.ts.map +1 -1
  246. package/dist/internal/server.js +49 -21
  247. package/dist/internal/session-engine.d.ts +101 -3
  248. package/dist/internal/session-engine.d.ts.map +1 -1
  249. package/dist/internal/session-engine.js +577 -46
  250. package/dist/internal/sessions-client.d.ts +9 -7
  251. package/dist/internal/sessions-client.d.ts.map +1 -1
  252. package/dist/internal/sessions-client.js +3 -1
  253. package/dist/internal/steering.d.ts +15 -0
  254. package/dist/internal/steering.d.ts.map +1 -0
  255. package/dist/internal/steering.js +18 -0
  256. package/dist/internal/storage-coordinator.d.ts +7 -0
  257. package/dist/internal/storage-coordinator.d.ts.map +1 -1
  258. package/dist/internal/storage-coordinator.js +28 -5
  259. package/dist/internal/storage-roles.d.ts +5 -0
  260. package/dist/internal/storage-roles.d.ts.map +1 -1
  261. package/dist/internal/stream-progress.d.ts.map +1 -1
  262. package/dist/internal/stream-progress.js +10 -0
  263. package/dist/internal/tool-policy.d.ts +9 -1
  264. package/dist/internal/tool-policy.d.ts.map +1 -1
  265. package/dist/internal/tool-policy.js +13 -0
  266. package/dist/internal/trajectory.d.ts.map +1 -1
  267. package/dist/internal/trajectory.js +10 -0
  268. package/dist/internal/turn-outbox.d.ts +24 -0
  269. package/dist/internal/turn-outbox.d.ts.map +1 -0
  270. package/dist/internal/turn-outbox.js +80 -0
  271. package/dist/playground/assets/{index-CZA1uEWA.js → index-DrkI6y5O.js} +51 -51
  272. package/dist/playground/assets/index-DzNGwm7q.css +1 -0
  273. package/dist/playground/index.html +2 -2
  274. package/dist/storage-backends/cursor-hosted.d.ts +9 -6
  275. package/dist/storage-backends/cursor-hosted.d.ts.map +1 -1
  276. package/dist/storage-backends/cursor-hosted.js +16 -3
  277. package/dist/storage.d.ts +8 -0
  278. package/dist/storage.d.ts.map +1 -1
  279. package/dist/types.d.ts +65 -8
  280. package/dist/types.d.ts.map +1 -1
  281. package/docs/README.md +7 -3
  282. package/docs/deployment.md +5 -4
  283. package/docs/guides/mcp-oauth.md +26 -8
  284. package/docs/guides/slack.md +93 -202
  285. package/docs/reference/agent-config.md +2 -2
  286. package/docs/reference/cli.md +39 -16
  287. package/docs/reference/connections.md +6 -3
  288. package/docs/reference/http-api.md +2 -1
  289. package/docs/reference/sessions.md +4 -2
  290. package/docs/reference/tools.md +9 -2
  291. package/docs/templates/agents-md.md +110 -0
  292. package/docs/templates/code-wiki.md +96 -0
  293. package/docs/troubleshooting.md +2 -2
  294. package/package.json +2 -2
  295. package/skills/ab/SKILL.md +13 -97
  296. package/skills/create-agent/SKILL.md +124 -223
  297. package/skills/debug/SKILL.md +34 -68
  298. package/skills/evals/SKILL.md +55 -180
  299. package/skills/framework-map/SKILL.md +83 -145
  300. package/skills/github/SKILL.md +53 -111
  301. package/skills/hillclimb/SKILL.md +40 -163
  302. package/skills/mcp-auth/SKILL.md +51 -107
  303. package/skills/otel/SKILL.md +22 -68
  304. package/skills/setup-slack/SKILL.md +91 -212
  305. package/src/bin/agent-serve.ts +13 -1
  306. package/src/channels/deployments/types.ts +1 -0
  307. package/src/channels/origin/api.ts +264 -33
  308. package/src/channels/origin/binding.ts +57 -28
  309. package/src/channels/origin/checks.ts +6 -6
  310. package/src/channels/origin/cursor-account.ts +5 -3
  311. package/src/channels/origin/index.ts +1 -0
  312. package/src/channels/origin/origin-channel.ts +4 -0
  313. package/src/channels/origin/reactions.ts +82 -0
  314. package/src/channels/origin/types.ts +11 -0
  315. package/src/channels/slack/api.ts +41 -5
  316. package/src/channels/slack/approvals.ts +105 -0
  317. package/src/channels/slack/cli-project.ts +267 -0
  318. package/src/channels/slack/defaults.ts +122 -93
  319. package/src/channels/slack/dispatch.ts +56 -22
  320. package/src/channels/slack/inbound.ts +43 -0
  321. package/src/channels/slack/init.ts +10 -5
  322. package/src/channels/slack/interactive.ts +35 -9
  323. package/src/channels/slack/live-delivery.ts +235 -114
  324. package/src/channels/slack/manifest.ts +6 -2
  325. package/src/channels/slack/nudge-carrier.ts +48 -1
  326. package/src/channels/slack/setup.ts +10 -6
  327. package/src/channels/slack/slack-channel.ts +3 -0
  328. package/src/channels/slack/tool-approval-events.ts +93 -0
  329. package/src/evals/run-facts.ts +32 -0
  330. package/src/files-backends/cursor-hosted.ts +40 -7
  331. package/src/internal/advertise-tools.ts +49 -12
  332. package/src/internal/approval-gate.ts +20 -29
  333. package/src/internal/bounded.ts +28 -0
  334. package/src/internal/chat-client.ts +19 -0
  335. package/src/internal/cli-deploy.ts +91 -9
  336. package/src/internal/cli-mcp-oauth.ts +7 -21
  337. package/src/internal/cli-slack-manual.ts +350 -18
  338. package/src/internal/cli-slack.ts +40 -84
  339. package/src/internal/conversation-mirror.ts +145 -69
  340. package/src/internal/cursor/account-mcp.ts +21 -0
  341. package/src/internal/cursor/backend-client.ts +34 -58
  342. package/src/internal/cursor/session-token.ts +115 -0
  343. package/src/internal/cursor-agent-template.ts +2 -0
  344. package/src/internal/deploy-client.ts +43 -0
  345. package/src/internal/env-file.ts +84 -0
  346. package/src/internal/framework-file-storage.ts +228 -0
  347. package/src/internal/framework-storage-selection.ts +51 -11
  348. package/src/internal/hosted-delivery-protocol.ts +7 -0
  349. package/src/internal/hosted-delivery.ts +107 -24
  350. package/src/internal/hosted-execution-diag.ts +207 -0
  351. package/src/internal/http-channel.ts +99 -0
  352. package/src/internal/init-project.ts +4 -0
  353. package/src/internal/install-cursor-skills.ts +1 -4
  354. package/src/internal/logs-client.ts +5 -0
  355. package/src/internal/managed-delivery.ts +125 -0
  356. package/src/internal/mcp-endpoint.ts +13 -4
  357. package/src/internal/mcp-host.ts +77 -11
  358. package/src/internal/mcp-oauth-on-demand.ts +352 -0
  359. package/src/internal/mcp-oauth-persist.ts +127 -0
  360. package/src/internal/mcp-oauth.ts +17 -1
  361. package/src/internal/otel/collector.ts +30 -0
  362. package/src/internal/runtime-dispatch-runner.ts +10 -0
  363. package/src/internal/sdk-runner.ts +56 -8
  364. package/src/internal/server.ts +61 -9
  365. package/src/internal/session-engine.ts +723 -60
  366. package/src/internal/sessions-client.ts +17 -8
  367. package/src/internal/steering.ts +17 -0
  368. package/src/internal/storage-coordinator.ts +38 -8
  369. package/src/internal/storage-roles.ts +7 -0
  370. package/src/internal/stream-progress.ts +19 -0
  371. package/src/internal/tool-policy.ts +18 -0
  372. package/src/internal/trajectory.ts +10 -0
  373. package/src/internal/turn-outbox.ts +85 -0
  374. package/src/storage-backends/cursor-hosted.ts +22 -8
  375. package/src/storage.ts +12 -0
  376. package/src/types.ts +70 -9
  377. package/templates/agents-md/README.md +39 -0
  378. package/templates/agents-md/agent/agent.ts +8 -0
  379. package/templates/agents-md/agent/channels/github.ts +10 -0
  380. package/templates/agents-md/agent/channels/queue.ts +28 -0
  381. package/templates/agents-md/agent/channels/slack.ts +9 -0
  382. package/templates/agents-md/agent/instructions.md +39 -0
  383. package/templates/agents-md/agent/lib/collect.ts +439 -0
  384. package/templates/agents-md/agent/lib/config.ts +8 -0
  385. package/templates/agents-md/agent/lib/paths.ts +51 -0
  386. package/templates/agents-md/agent/schedules/weekly.ts +17 -0
  387. package/templates/agents-md/agent/tools/apply_agents.ts +226 -0
  388. package/templates/agents-md/evals/agents.eval.ts +135 -0
  389. package/templates/agents-md/evals/evals.config.ts +5 -0
  390. package/templates/agents-md/init.json +38 -0
  391. package/templates/agents-md/package.json +18 -0
  392. package/templates/agents-md/tsconfig.json +12 -0
  393. package/templates/code-wiki/README.md +34 -0
  394. package/templates/code-wiki/agent/agent.ts +8 -0
  395. package/templates/code-wiki/agent/channels/github.ts +144 -0
  396. package/templates/code-wiki/agent/instructions.md +39 -0
  397. package/templates/code-wiki/agent/lib/repos.ts +5 -0
  398. package/templates/code-wiki/agent/lib/wiki.ts +22 -0
  399. package/templates/code-wiki/agent/tools/apply_wiki.ts +219 -0
  400. package/templates/code-wiki/evals/evals.config.ts +5 -0
  401. package/templates/code-wiki/evals/wiki.eval.ts +132 -0
  402. package/templates/code-wiki/init.json +25 -0
  403. package/templates/code-wiki/package.json +18 -0
  404. package/templates/code-wiki/tsconfig.json +12 -0
  405. package/dist/docs/assets/chunks/@localSearchIndexroot.oqPawjiD.js +0 -1
  406. package/dist/docs/assets/guides_slack.md.C32HsdKk.js +0 -38
  407. package/dist/docs/assets/guides_slack.md.C32HsdKk.lean.js +0 -1
  408. package/dist/docs/assets/index.md.BoHaMdeZ.js +0 -5
  409. package/dist/docs/assets/reference_sessions.md.D0mIh4KK.js +0 -1
  410. package/dist/docs/assets/troubleshooting.md.Ctv3T8C2.js +0 -1
  411. package/dist/docs/design/agsh.md +0 -406
  412. package/dist/internal/deployment-scm-event-stream.d.ts +0 -116
  413. package/dist/internal/deployment-scm-event-stream.d.ts.map +0 -1
  414. package/dist/internal/deployment-scm-event-stream.js +0 -474
  415. package/dist/playground/assets/index-CF7hUDnQ.css +0 -1
  416. package/docs/design/agsh.md +0 -406
  417. package/src/internal/deployment-scm-event-stream.ts +0 -593
  418. /package/dist/docs/assets/{deployment.md.D9msOFOW.lean.js → deployment.md.MFPKqsqI.lean.js} +0 -0
  419. /package/dist/docs/assets/{reference_agent-config.md.Cp_x38Nl.lean.js → reference_agent-config.md.BHeYMgme.lean.js} +0 -0
  420. /package/dist/docs/assets/{reference_connections.md.BH8Oc0D0.lean.js → reference_connections.md.DxldvyIB.lean.js} +0 -0
  421. /package/dist/docs/assets/{reference_http-api.md.D89k1mdm.lean.js → reference_http-api.md.5zOAbV86.lean.js} +0 -0
  422. /package/dist/docs/assets/{reference_sessions.md.D0mIh4KK.lean.js → reference_sessions.md.NxFP_CAC.lean.js} +0 -0
  423. /package/dist/docs/assets/{reference_tools.md.BHeXn2id.lean.js → reference_tools.md.B84gw9Ii.lean.js} +0 -0
  424. /package/dist/docs/assets/{troubleshooting.md.Ctv3T8C2.lean.js → troubleshooting.md.DCiPBhYs.lean.js} +0 -0
package/AGENTS.md CHANGED
@@ -33,9 +33,9 @@ built-in read/grep fail and sends models into retry loops.
33
33
  Before scaffolding, wiring channels, writing evals, or deploying, **read the
34
34
  matching skill under `skills/<task>/SKILL.md`** (paths
35
35
  below are relative to this package). Those files ship with `@cursor/july`.
36
- Cloud agents get the same published skills (except `operate`) via
37
- `GetManagedSkills`, which reads these files. Open them directly there
38
- are no `.cursor/skills/` stubs for authoring.
36
+ Cloud agents get the same published skills via `GetManagedSkills`,
37
+ which reads these files. Open them directly. There are no
38
+ `.cursor/skills/` stubs for authoring.
39
39
 
40
40
  | Skill | Read it when |
41
41
  | --- | --- |
@@ -49,7 +49,6 @@ are no `.cursor/skills/` stubs for authoring.
49
49
  | `skills/setup-slack/SKILL.md` | Slack wiring and Slack tool approvals |
50
50
  | `skills/mcp-auth/SKILL.md` | Host MCP OAuth (`mcp oauth`, `--store`, `advertiseTools`, `host-connections/`) |
51
51
  | `skills/debug/SKILL.md` | Something misbehaving locally (symptom → cause) |
52
- | `skills/operate/SKILL.md` | Dogfood host, corp ECS, hosted-platform map |
53
52
 
54
53
  Hosted-platform debug (stopped / slow start / health-fail, Datadog
55
54
  `cursor.agent_serve.*`) is the monorepo skill
package/README.md CHANGED
@@ -620,8 +620,9 @@ info and materialized workspace, and the call is recorded on the
620
620
  session's event stream as `actions.requested` / `action.result` under a
621
621
  per-call `turnId`. That call is visible in the playground, NDJSON
622
622
  trace, and trajectories like any model-initiated call. Session-bound
623
- calls are serialized with model turns: while a turn is running the call
624
- is rejected with `409 session_busy`.
623
+ writes are serialized with model turns: while a turn is running a
624
+ write-effect call is rejected with `409 session_busy`, while a
625
+ read-effect call runs alongside the turn.
625
626
 
626
627
  Unknown tools are rejected with the available tool names, `execution:
627
628
  "agent"` tools cannot be called on the host (400), schema-invalid input is a
@@ -104,7 +104,7 @@ Usage:
104
104
  ${CLI} deploy [--dir <path>] [--slug <slug> | --all] [--team <id>] [--json]
105
105
  [--no-wait] [--repo <url>] [--ref <ref>]
106
106
  [--path <agentPath>] [--cursor-events-repo <owner/name>]...
107
- [--allow-domain <domain>]...
107
+ [--allow-domain <domain>]... [--multi-tenant]
108
108
  ${CLI} manifest [--dir <path>] [--json]
109
109
  ${CLI} deployments [--team <id>] [--json]
110
110
  ${CLI} deployment <slug> [--team <id>] [--json]
@@ -232,6 +232,8 @@ Commands:
232
232
  (flags always win). When --dir is a multi-agent parent,
233
233
  pick one interactively, or pass --slug / --all. First deploy
234
234
  of a slug prints the alias token exactly once — save it.
235
+ --multi-tenant adds a release to an existing Cursor-managed
236
+ product (v2 only); it cannot create a new multi-tenant app.
235
237
  deployments List the team's deployments (slug, status, generation, kind).
236
238
  deployment Show one deployment in full (status, lastError, engine info).
237
239
  stop Stop a deployment and wait until it reports stopped.
@@ -394,6 +396,9 @@ Options:
394
396
  --allow-domain deploy: egress domain the engine pod may reach
395
397
  (repeatable; unioned with hosting.egressDomains from the
396
398
  agent manifest). Repo-backed deploys only.
399
+ --multi-tenant deploy: add a release to an existing Cursor-managed
400
+ (multi-tenant) product. architecture v2 only. Cannot
401
+ create a new multi-tenant application.
397
402
  --from-argv secrets set: allow NAME=VALUE on argv (leaks into shell
398
403
  history and agent-captured terminals). Default is names
399
404
  only with a hidden prompt or piped stdin.
@@ -403,6 +408,8 @@ Options:
403
408
  GITHUB_WEBHOOK_SECRET). github: --events overrides the
404
409
  derived webhook event list.
405
410
  --install github: install the cli/gh-webhook extension if missing.
411
+ slack init --manual: require Slack CLI app install.
412
+ --no-install slack init --manual: skip Slack CLI app install.
406
413
  --action github replay: event action (e.g. opened, synchronize).
407
414
  --conclusion github replay: CI conclusion (check_run/suite/status).
408
415
  --comment github replay: comment body for comment events.
@@ -517,6 +524,7 @@ function main(argv) {
517
524
  secret: { type: "string" },
518
525
  channel: { type: "string", multiple: true },
519
526
  install: { type: "boolean", default: false },
527
+ "no-install": { type: "boolean", default: false },
520
528
  action: { type: "string" },
521
529
  conclusion: { type: "string" },
522
530
  context: { type: "string" },
@@ -530,6 +538,7 @@ function main(argv) {
530
538
  all: { type: "boolean", default: false },
531
539
  "cursor-events-repo": { type: "string", multiple: true },
532
540
  "allow-domain": { type: "string", multiple: true },
541
+ "multi-tenant": { type: "boolean", default: false },
533
542
  "from-argv": { type: "boolean", default: false },
534
543
  strict: { type: "boolean", default: false },
535
544
  junit: { type: "string" },
@@ -577,6 +586,8 @@ function main(argv) {
577
586
  icon: values.icon,
578
587
  force: values.force,
579
588
  manual: values.manual,
589
+ install: values.install,
590
+ noInstall: values["no-install"],
580
591
  iconSource: positionals[0] === "icon" ? positionals[1] : undefined,
581
592
  });
582
593
  }
@@ -684,11 +695,11 @@ function main(argv) {
684
695
  // `--repo` is repeatable for `serve --cursor-events`; deploy targets a
685
696
  // single source repo, so the last one wins.
686
697
  const repo = (_c = values.repo) === null || _c === void 0 ? void 0 : _c.at(-1);
687
- return cmdDeploy(Object.assign(Object.assign(Object.assign(Object.assign(Object.assign(Object.assign(Object.assign(Object.assign(Object.assign({}, deployOptionsFromValues(values)), { dir }), (values.slug === undefined ? {} : { slug: values.slug })), { all: values.all === true }), (repo === undefined ? {} : { repo })), (values.ref === undefined ? {} : { ref: values.ref })), (values.path === undefined ? {} : { path: values.path })), (values["cursor-events-repo"] === undefined
698
+ return cmdDeploy(Object.assign(Object.assign(Object.assign(Object.assign(Object.assign(Object.assign(Object.assign(Object.assign(Object.assign(Object.assign({}, deployOptionsFromValues(values)), { dir }), (values.slug === undefined ? {} : { slug: values.slug })), { all: values.all === true }), (repo === undefined ? {} : { repo })), (values.ref === undefined ? {} : { ref: values.ref })), (values.path === undefined ? {} : { path: values.path })), (values["cursor-events-repo"] === undefined
688
699
  ? {}
689
700
  : { cursorEventsRepos: values["cursor-events-repo"] })), (values["allow-domain"] === undefined
690
701
  ? {}
691
- : { allowDomains: values["allow-domain"] })));
702
+ : { allowDomains: values["allow-domain"] })), { multiTenant: values["multi-tenant"] === true }));
692
703
  }
693
704
  case "manifest": {
694
705
  // Offline extraction of deploy metadata (events, egress, routes,
@@ -2,7 +2,7 @@ import type { ContinuationIdentity } from "../../continuation.js";
2
2
  import type { ChannelDefinition, ChannelHandlerArgs } from "../../types.js";
3
3
  /** {@link ChannelMeta.kind} value used by {@link deploymentsChannel}. */
4
4
  export declare const DEPLOYMENTS_CHANNEL_KIND = "deployments";
5
- export declare const DEPLOYMENT_EVENT_TYPES: readonly ["deployment.created", "deployment.succeeded"];
5
+ export declare const DEPLOYMENT_EVENT_TYPES: readonly ["deployment.created", "deployment.succeeded", "deployment.failed"];
6
6
  export type DeploymentEventType = (typeof DEPLOYMENT_EVENT_TYPES)[number];
7
7
  export type DeploymentStatus = "pending" | "in_progress" | "success" | "failed";
8
8
  /** One deployment event, as the control plane records it. */
@@ -1 +1 @@
1
- {"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../../../src/channels/deployments/types.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,oBAAoB,EAAE,MAAM,uBAAuB,CAAC;AAClE,OAAO,KAAK,EAAE,iBAAiB,EAAE,kBAAkB,EAAE,MAAM,gBAAgB,CAAC;AAE5E,yEAAyE;AACzE,eAAO,MAAM,wBAAwB,gBAAgB,CAAC;AAEtD,eAAO,MAAM,sBAAsB,YACjC,oBAAoB,EACpB,sBAAsB,CACd,CAAC;AACX,MAAM,MAAM,mBAAmB,GAAG,CAAC,OAAO,sBAAsB,CAAC,CAAC,MAAM,CAAC,CAAC;AAE1E,MAAM,MAAM,gBAAgB,GAAG,SAAS,GAAG,aAAa,GAAG,SAAS,GAAG,QAAQ,CAAC;AAEhF,6DAA6D;AAC7D,MAAM,WAAW,eAAe;IAC9B,SAAS,EAAE,mBAAmB,CAAC;IAC/B,mEAAmE;IACnE,OAAO,EAAE,MAAM,CAAC;IAChB,0BAA0B;IAC1B,MAAM,EAAE,MAAM,CAAC;IACf,8DAA8D;IAC9D,eAAe,EAAE,MAAM,CAAC;IACxB,YAAY,EAAE,MAAM,CAAC;IACrB,qCAAqC;IACrC,WAAW,EAAE,MAAM,CAAC;IACpB,qDAAqD;IACrD,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB,aAAa,EAAE,MAAM,CAAC;IACtB,MAAM,EAAE,gBAAgB,CAAC;IACzB,YAAY,EAAE,MAAM,CAAC;CACtB;AAED,kDAAkD;AAClD,MAAM,WAAW,sBAAsB;IACrC;;;OAGG;IACH,eAAe,EAAE,MAAM,CAAC;IACxB,iDAAiD;IACjD,YAAY,CAAC,EAAE,SAAS,MAAM,EAAE,CAAC;IACjC,0CAA0C;IAC1C,MAAM,CAAC,EAAE,SAAS,mBAAmB,EAAE,CAAC;CACzC;AAED,MAAM,WAAW,yBAAyB;IACxC;;;;;;;;;;;OAWG;IACH,gBAAgB,EAAE,SAAS,CAAC,MAAM,GAAG,sBAAsB,CAAC,EAAE,CAAC;IAC/D;;;OAGG;IACH,YAAY,CAAC,EAAE,SAAS,MAAM,EAAE,CAAC;IACjC;;;OAGG;IACH,MAAM,CAAC,EAAE,SAAS,mBAAmB,EAAE,CAAC;IACxC,6EAA6E;IAC7E,OAAO,EAAE,CACP,KAAK,EAAE,eAAe,EACtB,IAAI,EAAE,kBAAkB,KACrB,OAAO,CAAC,OAAO,CAAC,GAAG,OAAO,CAAC;IAChC,6DAA6D;IAC7D,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,IAAI,CAAC,EAAE,iBAAiB,CAAC,MAAM,CAAC,CAAC;IACjC,OAAO,CAAC,EAAE,iBAAiB,CAAC,SAAS,CAAC,CAAC;IACvC,MAAM,CAAC,EAAE,iBAAiB,CAAC,QAAQ,CAAC,CAAC;IACrC;;;;;OAKG;IACH,YAAY,CAAC,EAAE,oBAAoB,CAAC;CACrC"}
1
+ {"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../../../src/channels/deployments/types.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,oBAAoB,EAAE,MAAM,uBAAuB,CAAC;AAClE,OAAO,KAAK,EAAE,iBAAiB,EAAE,kBAAkB,EAAE,MAAM,gBAAgB,CAAC;AAE5E,yEAAyE;AACzE,eAAO,MAAM,wBAAwB,gBAAgB,CAAC;AAEtD,eAAO,MAAM,sBAAsB,YACjC,oBAAoB,EACpB,sBAAsB,EACtB,mBAAmB,CACX,CAAC;AACX,MAAM,MAAM,mBAAmB,GAAG,CAAC,OAAO,sBAAsB,CAAC,CAAC,MAAM,CAAC,CAAC;AAE1E,MAAM,MAAM,gBAAgB,GAAG,SAAS,GAAG,aAAa,GAAG,SAAS,GAAG,QAAQ,CAAC;AAEhF,6DAA6D;AAC7D,MAAM,WAAW,eAAe;IAC9B,SAAS,EAAE,mBAAmB,CAAC;IAC/B,mEAAmE;IACnE,OAAO,EAAE,MAAM,CAAC;IAChB,0BAA0B;IAC1B,MAAM,EAAE,MAAM,CAAC;IACf,8DAA8D;IAC9D,eAAe,EAAE,MAAM,CAAC;IACxB,YAAY,EAAE,MAAM,CAAC;IACrB,qCAAqC;IACrC,WAAW,EAAE,MAAM,CAAC;IACpB,qDAAqD;IACrD,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB,aAAa,EAAE,MAAM,CAAC;IACtB,MAAM,EAAE,gBAAgB,CAAC;IACzB,YAAY,EAAE,MAAM,CAAC;CACtB;AAED,kDAAkD;AAClD,MAAM,WAAW,sBAAsB;IACrC;;;OAGG;IACH,eAAe,EAAE,MAAM,CAAC;IACxB,iDAAiD;IACjD,YAAY,CAAC,EAAE,SAAS,MAAM,EAAE,CAAC;IACjC,0CAA0C;IAC1C,MAAM,CAAC,EAAE,SAAS,mBAAmB,EAAE,CAAC;CACzC;AAED,MAAM,WAAW,yBAAyB;IACxC;;;;;;;;;;;OAWG;IACH,gBAAgB,EAAE,SAAS,CAAC,MAAM,GAAG,sBAAsB,CAAC,EAAE,CAAC;IAC/D;;;OAGG;IACH,YAAY,CAAC,EAAE,SAAS,MAAM,EAAE,CAAC;IACjC;;;OAGG;IACH,MAAM,CAAC,EAAE,SAAS,mBAAmB,EAAE,CAAC;IACxC,6EAA6E;IAC7E,OAAO,EAAE,CACP,KAAK,EAAE,eAAe,EACtB,IAAI,EAAE,kBAAkB,KACrB,OAAO,CAAC,OAAO,CAAC,GAAG,OAAO,CAAC;IAChC,6DAA6D;IAC7D,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,IAAI,CAAC,EAAE,iBAAiB,CAAC,MAAM,CAAC,CAAC;IACjC,OAAO,CAAC,EAAE,iBAAiB,CAAC,SAAS,CAAC,CAAC;IACvC,MAAM,CAAC,EAAE,iBAAiB,CAAC,QAAQ,CAAC,CAAC;IACrC;;;;;OAKG;IACH,YAAY,CAAC,EAAE,oBAAoB,CAAC;CACrC"}
@@ -3,4 +3,5 @@ export const DEPLOYMENTS_CHANNEL_KIND = "deployments";
3
3
  export const DEPLOYMENT_EVENT_TYPES = [
4
4
  "deployment.created",
5
5
  "deployment.succeeded",
6
+ "deployment.failed",
6
7
  ];
@@ -1,18 +1,24 @@
1
1
  /**
2
2
  * Origin public REST helpers (`https://api.cursor.com/v1/origin/...`).
3
3
  *
4
- * Origin writes such as CI check runs are installation-only: they need an
5
- * `oit_…` installation token minted from Origin app credentials (EdDSA app
6
- * JWT → `/v1/origin/app/installations/{id}/access_tokens`). This module
7
- * consolidates that flow so agents configure credentials once and call
8
- * {@link createOriginClient} — the GitHub-channel analogue of
4
+ * This module consolidates Origin auth so agents configure credentials once
5
+ * and call {@link createOriginClient} the GitHub-channel analogue of
9
6
  * `createGitHubOctokit`.
10
7
  *
11
- * Credentials resolve from options first, then the environment:
12
- * `ORIGIN_APP_ID` (or `AGENT_SERVE_ORIGIN_APP_ID`),
13
- * `ORIGIN_APP_INSTALLATION_ID`, `ORIGIN_APP_PRIVATE_KEY` (PKCS8 PEM for the
14
- * app's Ed25519 key; literal `\n` sequences are normalized), and
15
- * `ORIGIN_API_BASE_URL` for the public REST base.
8
+ * Self-configured channels with their own Origin app resolve credentials
9
+ * from options first, then the environment: `ORIGIN_APP_ID` (or
10
+ * `AGENT_SERVE_ORIGIN_APP_ID`), `ORIGIN_APP_INSTALLATION_ID`,
11
+ * `ORIGIN_APP_PRIVATE_KEY` (PKCS8 PEM for the app's Ed25519 key; literal
12
+ * `\n` sequences are normalized), `ORIGIN_API_BASE_URL` for the public REST
13
+ * base, and `ORIGIN_RPC_BASE_URL` for the first-party ConnectRPC base.
14
+ *
15
+ * Hosted v2 forks configure none of that: their only credential is the
16
+ * deployment service account's `CURSOR_API_KEY`, exchanged for a Cursor
17
+ * session ({@link cursorSessionTokenProvider}, `POST
18
+ * /auth/exchange_user_api_key`) and sent as the Origin bearer. Reads and
19
+ * writes both run as the deployment **service-account principal**; Origin's
20
+ * `agent-serve` allowlist grants team-namespace read/write, so there is no
21
+ * app-installation token exchange for managed deployments.
16
22
  */
17
23
  /**
18
24
  * Public Origin REST base (check runs, installation tokens). Distinct from
@@ -20,6 +26,14 @@
20
26
  * `origin-webhook.ts`).
21
27
  */
22
28
  export declare const DEFAULT_ORIGIN_PUBLIC_API_BASE_URL = "https://api.cursor.com";
29
+ /**
30
+ * Origin's first-party ConnectRPC host (`origin.v1.OriginService`). Separate
31
+ * deployment from {@link DEFAULT_ORIGIN_PUBLIC_API_BASE_URL}: a handful of
32
+ * workflow operations — comment reactions among them — have no
33
+ * `/v1/origin/...` REST binding yet and are only reachable as Connect unary
34
+ * JSON here.
35
+ */
36
+ export declare const DEFAULT_ORIGIN_RPC_BASE_URL = "https://api.origin.cursor.com";
23
37
  export type OriginApiMethod = "DELETE" | "GET" | "PATCH" | "POST" | "PUT";
24
38
  /** Normalized Origin REST failure — the `GitHubApiError` analogue. */
25
39
  export declare class OriginApiError extends Error {
@@ -34,7 +48,10 @@ export declare class OriginApiError extends Error {
34
48
  status: number;
35
49
  });
36
50
  }
37
- /** Yields a bearer for Origin REST calls (usually a short-lived `oit_…`). */
51
+ /**
52
+ * Yields a bearer for Origin REST calls (a short-lived `oit_…` for app
53
+ * channels, or a Cursor session token for service-account access).
54
+ */
38
55
  export type OriginTokenProvider = () => Promise<string>;
39
56
  export interface OriginAppCredentials {
40
57
  /** Origin app id (`app_<typeid>`). */
@@ -54,6 +71,32 @@ export declare function resolveOriginAppCredentialParts(env?: NodeJS.ProcessEnv)
54
71
  export declare function resolveOriginAppCredentials(env?: NodeJS.ProcessEnv): OriginAppCredentials | undefined;
55
72
  /** Public Origin REST base. Trailing slashes are stripped for path joins. */
56
73
  export declare function originPublicApiBaseUrl(env?: NodeJS.ProcessEnv): string;
74
+ /** Origin ConnectRPC base. Trailing slashes are stripped for path joins. */
75
+ export declare function originRpcBaseUrl(env?: NodeJS.ProcessEnv): string;
76
+ /**
77
+ * Exchange endpoint for Cursor-account session tokens. Override with
78
+ * `AGENT_SERVE_CURSOR_SESSION_EXCHANGE_URL`; defaults to the Cursor backend.
79
+ */
80
+ export declare function resolveCursorSessionExchangeUrl(): string;
81
+ /**
82
+ * A session-backed Origin token provider: {@link OriginTokenProvider} plus
83
+ * an `invalidate` hook `createOriginClient` calls when Origin rejects the
84
+ * bearer (401), so the next mint re-exchanges instead of serving the
85
+ * rejected session until its local renewal deadline.
86
+ */
87
+ export type CursorSessionTokenProvider = OriginTokenProvider & {
88
+ invalidate: (token: string) => void;
89
+ };
90
+ /** Test-only: drop the process-wide exchanged-session cache. */
91
+ export declare function _clearCursorSessionTokenCacheForTesting(): void;
92
+ export declare function cursorSessionTokenProvider(input?: {
93
+ /** Cursor API key source. Defaults to the standard host resolution. */
94
+ getApiKey?: () => string | undefined;
95
+ /** Exchange endpoint. Defaults to {@link resolveCursorSessionExchangeUrl}. */
96
+ exchangeUrl?: string;
97
+ fetch?: typeof fetch;
98
+ now?: () => number;
99
+ }): CursorSessionTokenProvider;
57
100
  /**
58
101
  * A cached per-use token provider for one set of app credentials. Every call
59
102
  * inside the reuse window returns the same `oit_…`; the first call after it
@@ -70,13 +113,24 @@ export interface OriginClientOptions {
70
113
  token?: string | OriginTokenProvider;
71
114
  /**
72
115
  * App credentials to mint installation tokens from. Defaults to the
73
- * environment ({@link resolveOriginAppCredentials}).
116
+ * environment ({@link resolveOriginAppCredentials}). Pass `false` to
117
+ * disable app credential lookup and force the Cursor-account exchange.
74
118
  */
75
- credentials?: OriginAppCredentials;
119
+ credentials?: OriginAppCredentials | false;
76
120
  /** Public Origin REST base. Defaults to `ORIGIN_API_BASE_URL` / prod. */
77
121
  apiBaseUrl?: string;
78
122
  /** Injectable fetch for tests. */
79
123
  fetch?: typeof fetch;
124
+ /**
125
+ * Cursor-account session exchange fallback (hosted v2 deployment SAs and
126
+ * local personal keys). `true` (default) engages when no explicit token
127
+ * or app credentials resolve and a Cursor credential is present; `false`
128
+ * disables it; an object injects the key source / endpoint.
129
+ */
130
+ cursorAccountExchange?: boolean | {
131
+ getApiKey?: () => string | undefined;
132
+ exchangeUrl?: string;
133
+ };
80
134
  }
81
135
  /** Minimal authenticated Origin REST client (the `Octokit` analogue). */
82
136
  export interface OriginClient {
@@ -93,8 +147,11 @@ export interface OriginClient {
93
147
  }
94
148
  /**
95
149
  * Build an authenticated Origin REST client. Auth resolution: explicit
96
- * token/provider, then app credentials (options or environment). Missing
97
- * auth fails at the first request with a clear message.
150
+ * token/provider, then app credentials (options or environment, for
151
+ * channels with their own Origin app), then the Cursor-account session
152
+ * exchange (hosted v2 deployment SAs — reads and writes both run as the
153
+ * deployment service-account principal). Missing auth fails at the first
154
+ * request with a clear message.
98
155
  */
99
156
  export declare function createOriginClient(options?: OriginClientOptions): OriginClient;
100
157
  //# sourceMappingURL=api.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"api.d.ts","sourceRoot":"","sources":["../../../src/channels/origin/api.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;GAeG;AAKH;;;;GAIG;AACH,eAAO,MAAM,kCAAkC,2BAA2B,CAAC;AAS3E,MAAM,MAAM,eAAe,GAAG,QAAQ,GAAG,KAAK,GAAG,OAAO,GAAG,MAAM,GAAG,KAAK,CAAC;AAE1E,sEAAsE;AACtE,qBAAa,cAAe,SAAQ,KAAK;IACvC,QAAQ,CAAC,IAAI,EAAE,OAAO,CAAC;IACvB,QAAQ,CAAC,MAAM,EAAE,MAAM,CAAC;IACxB,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAC;IACtB,QAAQ,CAAC,MAAM,EAAE,MAAM,CAAC;IAExB,YAAY,KAAK,EAAE;QACjB,IAAI,EAAE,OAAO,CAAC;QACd,MAAM,EAAE,MAAM,CAAC;QACf,IAAI,EAAE,MAAM,CAAC;QACb,MAAM,EAAE,MAAM,CAAC;KAChB,EASA;CACF;AAED,6EAA6E;AAC7E,MAAM,MAAM,mBAAmB,GAAG,MAAM,OAAO,CAAC,MAAM,CAAC,CAAC;AAExD,MAAM,WAAW,oBAAoB;IACnC,sCAAsC;IACtC,KAAK,EAAE,MAAM,CAAC;IACd,4CAA4C;IAC5C,cAAc,EAAE,MAAM,CAAC;IACvB,2DAA2D;IAC3D,UAAU,EAAE,MAAM,CAAC;CACpB;AAaD,2EAA2E;AAC3E,wBAAgB,+BAA+B,CAC7C,GAAG,GAAE,MAAM,CAAC,UAAwB,GACnC,OAAO,CAAC,oBAAoB,CAAC,CAO/B;AAED;;;;GAIG;AACH,wBAAgB,2BAA2B,CACzC,GAAG,GAAE,MAAM,CAAC,UAAwB,GACnC,oBAAoB,GAAG,SAAS,CAWlC;AAED,6EAA6E;AAC7E,wBAAgB,sBAAsB,CACpC,GAAG,GAAE,MAAM,CAAC,UAAwB,GACnC,MAAM,CAGR;AA8DD;;;;GAIG;AACH,wBAAgB,sBAAsB,CAAC,KAAK,EAAE;IAC5C,WAAW,EAAE,oBAAoB,CAAC;IAClC,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,KAAK,CAAC,EAAE,OAAO,KAAK,CAAC;IACrB,GAAG,CAAC,EAAE,MAAM,MAAM,CAAC;CACpB,GAAG,mBAAmB,CAmBtB;AAED,MAAM,WAAW,mBAAmB;IAClC,0EAA0E;IAC1E,KAAK,CAAC,EAAE,MAAM,GAAG,mBAAmB,CAAC;IACrC;;;OAGG;IACH,WAAW,CAAC,EAAE,oBAAoB,CAAC;IACnC,yEAAyE;IACzE,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,kCAAkC;IAClC,KAAK,CAAC,EAAE,OAAO,KAAK,CAAC;CACtB;AAED,yEAAyE;AACzE,MAAM,WAAW,YAAY;IAC3B,QAAQ,CAAC,UAAU,EAAE,MAAM,CAAC;IAC5B;;;OAGG;IACH,OAAO,CAAC,CAAC,GAAG,OAAO,EAAE,KAAK,EAAE;QAC1B,MAAM,EAAE,eAAe,CAAC;QACxB,IAAI,EAAE,MAAM,CAAC;QACb,IAAI,CAAC,EAAE,OAAO,CAAC;KAChB,GAAG,OAAO,CAAC,CAAC,CAAC,CAAC;CAChB;AAED;;;;GAIG;AACH,wBAAgB,kBAAkB,CAChC,OAAO,GAAE,mBAAwB,GAChC,YAAY,CAoEd"}
1
+ {"version":3,"file":"api.d.ts","sourceRoot":"","sources":["../../../src/channels/origin/api.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;GAqBG;AAcH;;;;GAIG;AACH,eAAO,MAAM,kCAAkC,2BAA2B,CAAC;AAE3E;;;;;;GAMG;AACH,eAAO,MAAM,2BAA2B,kCAAkC,CAAC;AAS3E,MAAM,MAAM,eAAe,GAAG,QAAQ,GAAG,KAAK,GAAG,OAAO,GAAG,MAAM,GAAG,KAAK,CAAC;AAE1E,sEAAsE;AACtE,qBAAa,cAAe,SAAQ,KAAK;IACvC,QAAQ,CAAC,IAAI,EAAE,OAAO,CAAC;IACvB,QAAQ,CAAC,MAAM,EAAE,MAAM,CAAC;IACxB,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAC;IACtB,QAAQ,CAAC,MAAM,EAAE,MAAM,CAAC;IAExB,YAAY,KAAK,EAAE;QACjB,IAAI,EAAE,OAAO,CAAC;QACd,MAAM,EAAE,MAAM,CAAC;QACf,IAAI,EAAE,MAAM,CAAC;QACb,MAAM,EAAE,MAAM,CAAC;KAChB,EASA;CACF;AAED;;;GAGG;AACH,MAAM,MAAM,mBAAmB,GAAG,MAAM,OAAO,CAAC,MAAM,CAAC,CAAC;AAExD,MAAM,WAAW,oBAAoB;IACnC,sCAAsC;IACtC,KAAK,EAAE,MAAM,CAAC;IACd,4CAA4C;IAC5C,cAAc,EAAE,MAAM,CAAC;IACvB,2DAA2D;IAC3D,UAAU,EAAE,MAAM,CAAC;CACpB;AAaD,2EAA2E;AAC3E,wBAAgB,+BAA+B,CAC7C,GAAG,GAAE,MAAM,CAAC,UAAwB,GACnC,OAAO,CAAC,oBAAoB,CAAC,CAO/B;AAED;;;;GAIG;AACH,wBAAgB,2BAA2B,CACzC,GAAG,GAAE,MAAM,CAAC,UAAwB,GACnC,oBAAoB,GAAG,SAAS,CAWlC;AAED,6EAA6E;AAC7E,wBAAgB,sBAAsB,CACpC,GAAG,GAAE,MAAM,CAAC,UAAwB,GACnC,MAAM,CAGR;AAED,4EAA4E;AAC5E,wBAAgB,gBAAgB,CAAC,GAAG,GAAE,MAAM,CAAC,UAAwB,GAAG,MAAM,CAG7E;AA8DD;;;GAGG;AACH,wBAAgB,+BAA+B,IAAI,MAAM,CAMxD;AAED;;;;;GAKG;AACH,MAAM,MAAM,0BAA0B,GAAG,mBAAmB,GAAG;IAC7D,UAAU,EAAE,CAAC,KAAK,EAAE,MAAM,KAAK,IAAI,CAAC;CACrC,CAAC;AA4BF,gEAAgE;AAChE,wBAAgB,uCAAuC,IAAI,IAAI,CAG9D;AAED,wBAAgB,0BAA0B,CAAC,KAAK,CAAC,EAAE;IACjD,uEAAuE;IACvE,SAAS,CAAC,EAAE,MAAM,MAAM,GAAG,SAAS,CAAC;IACrC,8EAA8E;IAC9E,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,KAAK,CAAC,EAAE,OAAO,KAAK,CAAC;IACrB,GAAG,CAAC,EAAE,MAAM,MAAM,CAAC;CACpB,GAAG,0BAA0B,CA8E7B;AAED;;;;GAIG;AACH,wBAAgB,sBAAsB,CAAC,KAAK,EAAE;IAC5C,WAAW,EAAE,oBAAoB,CAAC;IAClC,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,KAAK,CAAC,EAAE,OAAO,KAAK,CAAC;IACrB,GAAG,CAAC,EAAE,MAAM,MAAM,CAAC;CACpB,GAAG,mBAAmB,CAmBtB;AAED,MAAM,WAAW,mBAAmB;IAClC,0EAA0E;IAC1E,KAAK,CAAC,EAAE,MAAM,GAAG,mBAAmB,CAAC;IACrC;;;;OAIG;IACH,WAAW,CAAC,EAAE,oBAAoB,GAAG,KAAK,CAAC;IAC3C,yEAAyE;IACzE,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,kCAAkC;IAClC,KAAK,CAAC,EAAE,OAAO,KAAK,CAAC;IACrB;;;;;OAKG;IACH,qBAAqB,CAAC,EAClB,OAAO,GACP;QACE,SAAS,CAAC,EAAE,MAAM,MAAM,GAAG,SAAS,CAAC;QACrC,WAAW,CAAC,EAAE,MAAM,CAAC;KACtB,CAAC;CACP;AAED,yEAAyE;AACzE,MAAM,WAAW,YAAY;IAC3B,QAAQ,CAAC,UAAU,EAAE,MAAM,CAAC;IAC5B;;;OAGG;IACH,OAAO,CAAC,CAAC,GAAG,OAAO,EAAE,KAAK,EAAE;QAC1B,MAAM,EAAE,eAAe,CAAC;QACxB,IAAI,EAAE,MAAM,CAAC;QACb,IAAI,CAAC,EAAE,OAAO,CAAC;KAChB,GAAG,OAAO,CAAC,CAAC,CAAC,CAAC;CAChB;AAED;;;;;;;GAOG;AACH,wBAAgB,kBAAkB,CAChC,OAAO,GAAE,mBAAwB,GAChC,YAAY,CA6Gd"}
@@ -1,18 +1,24 @@
1
1
  /**
2
2
  * Origin public REST helpers (`https://api.cursor.com/v1/origin/...`).
3
3
  *
4
- * Origin writes such as CI check runs are installation-only: they need an
5
- * `oit_…` installation token minted from Origin app credentials (EdDSA app
6
- * JWT → `/v1/origin/app/installations/{id}/access_tokens`). This module
7
- * consolidates that flow so agents configure credentials once and call
8
- * {@link createOriginClient} — the GitHub-channel analogue of
4
+ * This module consolidates Origin auth so agents configure credentials once
5
+ * and call {@link createOriginClient} the GitHub-channel analogue of
9
6
  * `createGitHubOctokit`.
10
7
  *
11
- * Credentials resolve from options first, then the environment:
12
- * `ORIGIN_APP_ID` (or `AGENT_SERVE_ORIGIN_APP_ID`),
13
- * `ORIGIN_APP_INSTALLATION_ID`, `ORIGIN_APP_PRIVATE_KEY` (PKCS8 PEM for the
14
- * app's Ed25519 key; literal `\n` sequences are normalized), and
15
- * `ORIGIN_API_BASE_URL` for the public REST base.
8
+ * Self-configured channels with their own Origin app resolve credentials
9
+ * from options first, then the environment: `ORIGIN_APP_ID` (or
10
+ * `AGENT_SERVE_ORIGIN_APP_ID`), `ORIGIN_APP_INSTALLATION_ID`,
11
+ * `ORIGIN_APP_PRIVATE_KEY` (PKCS8 PEM for the app's Ed25519 key; literal
12
+ * `\n` sequences are normalized), `ORIGIN_API_BASE_URL` for the public REST
13
+ * base, and `ORIGIN_RPC_BASE_URL` for the first-party ConnectRPC base.
14
+ *
15
+ * Hosted v2 forks configure none of that: their only credential is the
16
+ * deployment service account's `CURSOR_API_KEY`, exchanged for a Cursor
17
+ * session ({@link cursorSessionTokenProvider}, `POST
18
+ * /auth/exchange_user_api_key`) and sent as the Origin bearer. Reads and
19
+ * writes both run as the deployment **service-account principal**; Origin's
20
+ * `agent-serve` allowlist grants team-namespace read/write, so there is no
21
+ * app-installation token exchange for managed deployments.
16
22
  */
17
23
  var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
18
24
  function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
@@ -25,12 +31,22 @@ var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, ge
25
31
  };
26
32
  import { Buffer } from "node:buffer";
27
33
  import { createPrivateKey, sign } from "node:crypto";
34
+ import { cursorBackendUrl, resolveApiKeySync, } from "../../internal/cursor/credentials.js";
35
+ import { CURSOR_SESSION_EXCHANGE_PATH, exchangeCursorApiKeyForSession, SESSION_TOKEN_EXPIRY_LEEWAY_MS, } from "../../internal/cursor/session-token.js";
28
36
  /**
29
37
  * Public Origin REST base (check runs, installation tokens). Distinct from
30
38
  * the webhook JWKS base (`DEFAULT_ORIGIN_API_BASE_URL` in
31
39
  * `origin-webhook.ts`).
32
40
  */
33
41
  export const DEFAULT_ORIGIN_PUBLIC_API_BASE_URL = "https://api.cursor.com";
42
+ /**
43
+ * Origin's first-party ConnectRPC host (`origin.v1.OriginService`). Separate
44
+ * deployment from {@link DEFAULT_ORIGIN_PUBLIC_API_BASE_URL}: a handful of
45
+ * workflow operations — comment reactions among them — have no
46
+ * `/v1/origin/...` REST binding yet and are only reachable as Connect unary
47
+ * JSON here.
48
+ */
49
+ export const DEFAULT_ORIGIN_RPC_BASE_URL = "https://api.origin.cursor.com";
34
50
  /** Fixed audience for Origin app JWTs (`APP_TOKEN_AUDIENCE` backend-side). */
35
51
  const ORIGIN_APP_TOKEN_AUDIENCE = "origin-apps";
36
52
  const APP_JWT_TTL_SECONDS = 5 * 60;
@@ -86,6 +102,12 @@ export function originPublicApiBaseUrl(env = process.env) {
86
102
  const fromEnv = (_a = envValue(env.ORIGIN_API_BASE_URL)) === null || _a === void 0 ? void 0 : _a.replace(/\/+$/, "");
87
103
  return fromEnv !== null && fromEnv !== void 0 ? fromEnv : DEFAULT_ORIGIN_PUBLIC_API_BASE_URL;
88
104
  }
105
+ /** Origin ConnectRPC base. Trailing slashes are stripped for path joins. */
106
+ export function originRpcBaseUrl(env = process.env) {
107
+ var _a;
108
+ const fromEnv = (_a = envValue(env.ORIGIN_RPC_BASE_URL)) === null || _a === void 0 ? void 0 : _a.replace(/\/+$/, "");
109
+ return fromEnv !== null && fromEnv !== void 0 ? fromEnv : DEFAULT_ORIGIN_RPC_BASE_URL;
110
+ }
89
111
  function base64UrlJson(value) {
90
112
  return Buffer.from(JSON.stringify(value)).toString("base64url");
91
113
  }
@@ -132,6 +154,109 @@ function mintOriginInstallationToken(input) {
132
154
  return token;
133
155
  });
134
156
  }
157
+ /**
158
+ * Exchange endpoint for Cursor-account session tokens. Override with
159
+ * `AGENT_SERVE_CURSOR_SESSION_EXCHANGE_URL`; defaults to the Cursor backend.
160
+ */
161
+ export function resolveCursorSessionExchangeUrl() {
162
+ const override = process.env.AGENT_SERVE_CURSOR_SESSION_EXCHANGE_URL;
163
+ if (override !== undefined && override.trim() !== "") {
164
+ return override.trim().replace(/\/+$/, "");
165
+ }
166
+ return `${cursorBackendUrl()}${CURSOR_SESSION_EXCHANGE_PATH}`;
167
+ }
168
+ /**
169
+ * Token provider backed by the shared Cursor session exchange
170
+ * (`exchangeCursorApiKeyForSession`, `POST /auth/exchange_user_api_key` —
171
+ * the same primitive `CursorBackendClient` mints through).
172
+ *
173
+ * Hosted v2 forks hold exactly one credential — the deployment service
174
+ * account's `CURSOR_API_KEY` — and Origin authenticates the exchanged
175
+ * session directly: reads and writes run as the deployment
176
+ * **service-account principal**, confined server-side to namespaces owned
177
+ * by the deployment's team (`agent-serve` allowlist). Local runs work the
178
+ * same way with a personal key: Origin authorizes the user principal.
179
+ *
180
+ * The API key is re-read on every mint so Bind can drop
181
+ * `CURSOR_API_KEY_FILE` onto a listening process; sessions are cached until
182
+ * shortly before their JWT expiry. The cache is **process-wide**, keyed by
183
+ * (endpoint, API key): hosted channels build a fresh `createOriginClient()`
184
+ * per event, so a per-provider cache would re-exchange on every read/write
185
+ * and concurrent first calls would race. In-flight exchanges are deduped
186
+ * for the same reason.
187
+ */
188
+ const cursorSessionTokenCache = new Map();
189
+ const cursorSessionTokenInFlight = new Map();
190
+ /** Test-only: drop the process-wide exchanged-session cache. */
191
+ export function _clearCursorSessionTokenCacheForTesting() {
192
+ cursorSessionTokenCache.clear();
193
+ cursorSessionTokenInFlight.clear();
194
+ }
195
+ export function cursorSessionTokenProvider(input) {
196
+ var _a, _b, _c;
197
+ const getApiKey = (_a = input === null || input === void 0 ? void 0 : input.getApiKey) !== null && _a !== void 0 ? _a : (() => { var _a; return (_a = resolveApiKeySync()) === null || _a === void 0 ? void 0 : _a.apiKey; });
198
+ const fetchImpl = (_b = input === null || input === void 0 ? void 0 : input.fetch) !== null && _b !== void 0 ? _b : fetch;
199
+ const now = (_c = input === null || input === void 0 ? void 0 : input.now) !== null && _c !== void 0 ? _c : Date.now;
200
+ const cacheKey = (url, apiKey) => `${url}\u0000${apiKey}`;
201
+ const resolveUrl = () => { var _a; return (_a = input === null || input === void 0 ? void 0 : input.exchangeUrl) !== null && _a !== void 0 ? _a : resolveCursorSessionExchangeUrl(); };
202
+ const mint = (url, apiKey) => __awaiter(this, void 0, void 0, function* () {
203
+ const nowMs = now();
204
+ let session;
205
+ try {
206
+ session = yield exchangeCursorApiKeyForSession({
207
+ exchangeUrl: url,
208
+ apiKey,
209
+ fetchImpl,
210
+ nowMs,
211
+ });
212
+ }
213
+ catch (error) {
214
+ throw new Error(`originClient: ${error instanceof Error ? error.message : String(error)} Check CURSOR_API_KEY / CURSOR_API_KEY_FILE, or pass an explicit token.`);
215
+ }
216
+ const renewAtMs = Math.max(nowMs + 1000, session.expiresAtMs - SESSION_TOKEN_EXPIRY_LEEWAY_MS);
217
+ cursorSessionTokenCache.set(cacheKey(url, apiKey), {
218
+ token: session.token,
219
+ renewAtMs,
220
+ });
221
+ return session.token;
222
+ });
223
+ const provider = () => __awaiter(this, void 0, void 0, function* () {
224
+ const apiKey = getApiKey();
225
+ if (apiKey === undefined || apiKey === "") {
226
+ throw new Error("originClient: no Cursor credential available for the session exchange (set CURSOR_API_KEY or CURSOR_API_KEY_FILE).");
227
+ }
228
+ const url = resolveUrl();
229
+ const key = cacheKey(url, apiKey);
230
+ const cached = cursorSessionTokenCache.get(key);
231
+ if (cached !== undefined && now() < cached.renewAtMs) {
232
+ return cached.token;
233
+ }
234
+ // Dedupe concurrent first calls: one exchange per (endpoint, key).
235
+ const inFlight = cursorSessionTokenInFlight.get(key);
236
+ if (inFlight !== undefined) {
237
+ return yield inFlight;
238
+ }
239
+ const pending = mint(url, apiKey).finally(() => {
240
+ cursorSessionTokenInFlight.delete(key);
241
+ });
242
+ cursorSessionTokenInFlight.set(key, pending);
243
+ return yield pending;
244
+ });
245
+ // Origin answered 401 for this bearer: drop it (unless a newer session
246
+ // already replaced it) so the next call re-exchanges immediately.
247
+ const invalidate = (token) => {
248
+ var _a;
249
+ const apiKey = getApiKey();
250
+ if (apiKey === undefined || apiKey === "") {
251
+ return;
252
+ }
253
+ const key = cacheKey(resolveUrl(), apiKey);
254
+ if (((_a = cursorSessionTokenCache.get(key)) === null || _a === void 0 ? void 0 : _a.token) === token) {
255
+ cursorSessionTokenCache.delete(key);
256
+ }
257
+ };
258
+ return Object.assign(provider, { invalidate });
259
+ }
135
260
  /**
136
261
  * A cached per-use token provider for one set of app credentials. Every call
137
262
  * inside the reuse window returns the same `oit_…`; the first call after it
@@ -160,16 +285,23 @@ export function originAppTokenProvider(input) {
160
285
  }
161
286
  /**
162
287
  * Build an authenticated Origin REST client. Auth resolution: explicit
163
- * token/provider, then app credentials (options or environment). Missing
164
- * auth fails at the first request with a clear message.
288
+ * token/provider, then app credentials (options or environment, for
289
+ * channels with their own Origin app), then the Cursor-account session
290
+ * exchange (hosted v2 deployment SAs — reads and writes both run as the
291
+ * deployment service-account principal). Missing auth fails at the first
292
+ * request with a clear message.
165
293
  */
166
294
  export function createOriginClient(options = {}) {
167
295
  var _a, _b;
168
296
  const apiBaseUrl = ((_a = options.apiBaseUrl) !== null && _a !== void 0 ? _a : originPublicApiBaseUrl()).replace(/\/+$/, "");
169
297
  const fetchImpl = (_b = options.fetch) !== null && _b !== void 0 ? _b : fetch;
170
298
  let tokenProvider;
299
+ // Set when the session-exchange fallback is engaged: a 401 from Origin
300
+ // invalidates the cached session and retries once with a fresh one, the
301
+ // `CursorBackendClient` re-exchange behavior.
302
+ let sessionProvider;
171
303
  const getToken = () => __awaiter(this, void 0, void 0, function* () {
172
- var _a;
304
+ var _a, _b, _c, _d;
173
305
  if (typeof options.token === "string") {
174
306
  return options.token;
175
307
  }
@@ -177,31 +309,56 @@ export function createOriginClient(options = {}) {
177
309
  return yield options.token();
178
310
  }
179
311
  if (tokenProvider === undefined) {
180
- const credentials = (_a = options.credentials) !== null && _a !== void 0 ? _a : resolveOriginAppCredentials();
181
- if (credentials === undefined) {
182
- throw new Error("originClient: no Origin credential available (pass token / credentials, or set ORIGIN_APP_ID + ORIGIN_APP_INSTALLATION_ID + ORIGIN_APP_PRIVATE_KEY).");
312
+ const credentials = options.credentials === false
313
+ ? undefined
314
+ : ((_a = options.credentials) !== null && _a !== void 0 ? _a : resolveOriginAppCredentials());
315
+ const exchange = (_b = options.cursorAccountExchange) !== null && _b !== void 0 ? _b : true;
316
+ const exchangeOptions = exchange === false ? undefined : exchange === true ? {} : exchange;
317
+ const getExchangeApiKey = (_c = exchangeOptions === null || exchangeOptions === void 0 ? void 0 : exchangeOptions.getApiKey) !== null && _c !== void 0 ? _c : (() => { var _a; return (_a = resolveApiKeySync()) === null || _a === void 0 ? void 0 : _a.apiKey; });
318
+ if (credentials !== undefined) {
319
+ tokenProvider = originAppTokenProvider({
320
+ credentials,
321
+ apiBaseUrl,
322
+ fetch: fetchImpl,
323
+ });
324
+ }
325
+ else if (exchangeOptions !== undefined &&
326
+ ((_d = getExchangeApiKey()) !== null && _d !== void 0 ? _d : "") !== "") {
327
+ sessionProvider = cursorSessionTokenProvider(Object.assign({ fetch: fetchImpl, getApiKey: getExchangeApiKey }, (exchangeOptions.exchangeUrl === undefined
328
+ ? {}
329
+ : { exchangeUrl: exchangeOptions.exchangeUrl })));
330
+ tokenProvider = sessionProvider;
331
+ }
332
+ else {
333
+ throw new Error("originClient: no Origin credential available (pass token / credentials, set ORIGIN_APP_ID + ORIGIN_APP_INSTALLATION_ID + ORIGIN_APP_PRIVATE_KEY, or sign in with a Cursor credential for the session exchange).");
183
334
  }
184
- tokenProvider = originAppTokenProvider({
185
- credentials,
186
- apiBaseUrl,
187
- fetch: fetchImpl,
188
- });
189
335
  }
190
336
  return yield tokenProvider();
191
337
  });
338
+ const send = (input, path, token) => __awaiter(this, void 0, void 0, function* () {
339
+ return yield fetchImpl(`${apiBaseUrl}${path}`, {
340
+ method: input.method,
341
+ headers: Object.assign({ authorization: `Bearer ${token}` }, (input.body === undefined
342
+ ? {}
343
+ : { "content-type": "application/json" })),
344
+ body: input.body === undefined ? undefined : JSON.stringify(input.body),
345
+ });
346
+ });
192
347
  return {
193
348
  apiBaseUrl,
194
349
  request(input) {
195
350
  return __awaiter(this, void 0, void 0, function* () {
196
351
  const path = input.path.startsWith("/") ? input.path : `/${input.path}`;
197
352
  const token = yield getToken();
198
- const response = yield fetchImpl(`${apiBaseUrl}${path}`, {
199
- method: input.method,
200
- headers: Object.assign({ authorization: `Bearer ${token}` }, (input.body === undefined
201
- ? {}
202
- : { "content-type": "application/json" })),
203
- body: input.body === undefined ? undefined : JSON.stringify(input.body),
204
- });
353
+ let response = yield send(input, path, token);
354
+ if (response.status === 401 && sessionProvider !== undefined) {
355
+ // The session aged out server-side. Drop it unless a concurrent
356
+ // retry already minted a newer one — and retry once.
357
+ yield response.text().catch(() => undefined);
358
+ sessionProvider.invalidate(token);
359
+ const retryToken = yield getToken();
360
+ response = yield send(input, path, retryToken);
361
+ }
205
362
  const text = yield response.text();
206
363
  let parsed;
207
364
  try {
@@ -10,6 +10,7 @@
10
10
  */
11
11
  import { type OriginApiMethod } from "./api.js";
12
12
  import { type OriginCheck, type OriginCheckCreateInput } from "./checks.js";
13
+ import { type OriginCommentReactionInput } from "./reactions.js";
13
14
  import type { OriginAppOptions, OriginRepositoryRef } from "./types.js";
14
15
  /** Origin operations exposed to hooks (`ctx.origin`). */
15
16
  export interface OriginHandle {
@@ -27,15 +28,25 @@ export interface OriginHandle {
27
28
  }): Promise<T>;
28
29
  /**
29
30
  * Open a CI check run on `sha` and get a handle for updating and
30
- * concluding it. Needs an app installation with
31
- * `repository:checks:write` Origin check writes are installation-only.
31
+ * concluding it. Needs `repository:checks:write` — via an app
32
+ * installation, or the deployment service account on hosted v2 forks.
32
33
  */
33
34
  createCheck(input: Omit<OriginCheckCreateInput, "origin" | "owner" | "repo">): Promise<OriginCheck>;
35
+ /**
36
+ * Add or remove one reaction on a PR comment — the Origin analogue of
37
+ * GitHub's `thread.react("eyes")`. Needs
38
+ * `repository:pull_requests:reviews:write`. Reactions have no REST
39
+ * binding, so this call goes to Origin's ConnectRPC host rather than the
40
+ * public API base {@link request} uses.
41
+ */
42
+ reactToComment(input: OriginCommentReactionInput): Promise<void>;
34
43
  }
35
44
  export declare function buildOriginBinding(input: {
36
45
  repository: OriginRepositoryRef;
37
46
  /** Installation id from the delivery envelope, when present. */
38
47
  installationId?: string;
48
+ /** Force the signed-in Cursor account / deployment SA credential path. */
49
+ cursorAccount?: boolean;
39
50
  /** Channel-authored outbound app credentials / API base. */
40
51
  app?: OriginAppOptions;
41
52
  /** Injectable fetch for tests. */
@@ -1 +1 @@
1
- {"version":3,"file":"binding.d.ts","sourceRoot":"","sources":["../../../src/channels/origin/binding.ts"],"names":[],"mappings":"AAAA;;;;;;;;;GASG;AAEH,OAAO,EAEL,KAAK,eAAe,EAGrB,MAAM,UAAU,CAAC;AAClB,OAAO,EAEL,KAAK,WAAW,EAChB,KAAK,sBAAsB,EAC5B,MAAM,aAAa,CAAC;AACrB,OAAO,KAAK,EAAE,gBAAgB,EAAE,mBAAmB,EAAE,MAAM,YAAY,CAAC;AAExE,yDAAyD;AACzD,MAAM,WAAW,YAAY;IAC3B,yEAAyE;IACzE,cAAc,EAAE,MAAM,GAAG,SAAS,CAAC;IACnC,UAAU,EAAE,mBAAmB,CAAC;IAChC;;;OAGG;IACH,OAAO,CAAC,CAAC,GAAG,OAAO,EAAE,KAAK,EAAE;QAC1B,MAAM,EAAE,eAAe,CAAC;QACxB,IAAI,EAAE,MAAM,CAAC;QACb,IAAI,CAAC,EAAE,OAAO,CAAC;KAChB,GAAG,OAAO,CAAC,CAAC,CAAC,CAAC;IACf;;;;OAIG;IACH,WAAW,CACT,KAAK,EAAE,IAAI,CAAC,sBAAsB,EAAE,QAAQ,GAAG,OAAO,GAAG,MAAM,CAAC,GAC/D,OAAO,CAAC,WAAW,CAAC,CAAC;CACzB;AAED,wBAAgB,kBAAkB,CAAC,KAAK,EAAE;IACxC,UAAU,EAAE,mBAAmB,CAAC;IAChC,gEAAgE;IAChE,cAAc,CAAC,EAAE,MAAM,CAAC;IACxB,4DAA4D;IAC5D,GAAG,CAAC,EAAE,gBAAgB,CAAC;IACvB,kCAAkC;IAClC,KAAK,CAAC,EAAE,OAAO,KAAK,CAAC;CACtB,GAAG,YAAY,CAuCf"}
1
+ {"version":3,"file":"binding.d.ts","sourceRoot":"","sources":["../../../src/channels/origin/binding.ts"],"names":[],"mappings":"AAAA;;;;;;;;;GASG;AAEH,OAAO,EAEL,KAAK,eAAe,EAIrB,MAAM,UAAU,CAAC;AAClB,OAAO,EAEL,KAAK,WAAW,EAChB,KAAK,sBAAsB,EAC5B,MAAM,aAAa,CAAC;AACrB,OAAO,EACL,KAAK,0BAA0B,EAEhC,MAAM,gBAAgB,CAAC;AACxB,OAAO,KAAK,EAAE,gBAAgB,EAAE,mBAAmB,EAAE,MAAM,YAAY,CAAC;AAExE,yDAAyD;AACzD,MAAM,WAAW,YAAY;IAC3B,yEAAyE;IACzE,cAAc,EAAE,MAAM,GAAG,SAAS,CAAC;IACnC,UAAU,EAAE,mBAAmB,CAAC;IAChC;;;OAGG;IACH,OAAO,CAAC,CAAC,GAAG,OAAO,EAAE,KAAK,EAAE;QAC1B,MAAM,EAAE,eAAe,CAAC;QACxB,IAAI,EAAE,MAAM,CAAC;QACb,IAAI,CAAC,EAAE,OAAO,CAAC;KAChB,GAAG,OAAO,CAAC,CAAC,CAAC,CAAC;IACf;;;;OAIG;IACH,WAAW,CACT,KAAK,EAAE,IAAI,CAAC,sBAAsB,EAAE,QAAQ,GAAG,OAAO,GAAG,MAAM,CAAC,GAC/D,OAAO,CAAC,WAAW,CAAC,CAAC;IACxB;;;;;;OAMG;IACH,cAAc,CAAC,KAAK,EAAE,0BAA0B,GAAG,OAAO,CAAC,IAAI,CAAC,CAAC;CAClE;AAED,wBAAgB,kBAAkB,CAAC,KAAK,EAAE;IACxC,UAAU,EAAE,mBAAmB,CAAC;IAChC,gEAAgE;IAChE,cAAc,CAAC,EAAE,MAAM,CAAC;IACxB,0EAA0E;IAC1E,aAAa,CAAC,EAAE,OAAO,CAAC;IACxB,4DAA4D;IAC5D,GAAG,CAAC,EAAE,gBAAgB,CAAC;IACvB,kCAAkC;IAClC,KAAK,CAAC,EAAE,OAAO,KAAK,CAAC;CACtB,GAAG,YAAY,CAqDf"}