@kynver-app/runtime 0.1.0 → 0.1.2

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/README.md CHANGED
@@ -26,7 +26,18 @@ login | setup | daemon
26
26
 
27
27
  ## Worker providers
28
28
 
29
- Default provider: `claude` (`workerProvider` in `~/.kynver/config.json`). Provider interface lives in `src/providers/`.
29
+ Set once in `kynver setup --provider claude|cursor` (stored in `~/.kynver/config.json` as `workerProvider`).
30
+
31
+ | Provider | CLI | Auth |
32
+ | --- | --- | --- |
33
+ | `claude` (default) | `claude` on PATH | `claude login` (OAuth). `ANTHROPIC_API_KEY` is stripped from worker env so OAuth wins. |
34
+ | `cursor` | `agent` on PATH ([Cursor Agent CLI](https://cursor.com/docs/cli/headless)) | `agent login` (OAuth) **or** `CURSOR_API_KEY` for headless runners. |
35
+
36
+ Override per invocation: `kynver worker start ... --provider cursor`
37
+
38
+ Install Cursor CLI (Windows PowerShell): `irm 'https://cursor.com/install?win32=true' | iex`
39
+
40
+ Default Cursor model: `composer-2.5`. Override with `--model` on dispatch/worker start.
30
41
 
31
42
  ## Tests
32
43
 
package/dist/cli.js CHANGED
@@ -698,9 +698,58 @@ var claudeProvider = {
698
698
  }
699
699
  };
700
700
 
701
+ // src/providers/cursor.ts
702
+ import { closeSync as closeSync2, openSync as openSync2 } from "node:fs";
703
+ import { spawn as spawn2 } from "node:child_process";
704
+ var DEFAULT_CURSOR_MODEL = "composer-2.5";
705
+ function resolveAgentBin() {
706
+ return process.env.KYNVER_CURSOR_AGENT_BIN?.trim() || process.env.CURSOR_AGENT_BIN?.trim() || "agent";
707
+ }
708
+ var cursorProvider = {
709
+ name: "cursor",
710
+ start(opts) {
711
+ const model = opts.model || DEFAULT_CURSOR_MODEL;
712
+ const stdoutFd = openSync2(opts.stdoutPath, "a");
713
+ const stderrFd = openSync2(opts.stderrPath, "a");
714
+ const agentBin = resolveAgentBin();
715
+ const child = spawn2(
716
+ agentBin,
717
+ [
718
+ "-p",
719
+ "--force",
720
+ "--trust",
721
+ "--workspace",
722
+ opts.worktreePath,
723
+ "--output-format",
724
+ "stream-json",
725
+ "--stream-partial-output",
726
+ "--model",
727
+ model,
728
+ opts.prompt
729
+ ],
730
+ {
731
+ cwd: opts.worktreePath,
732
+ detached: true,
733
+ stdio: ["ignore", stdoutFd, stderrFd],
734
+ env: process.env
735
+ }
736
+ );
737
+ closeSync2(stdoutFd);
738
+ closeSync2(stderrFd);
739
+ if (!child.pid) {
740
+ throw new Error(
741
+ `failed to spawn Cursor agent worker (is \`${agentBin}\` on PATH? run \`agent login\` or set CURSOR_API_KEY)`
742
+ );
743
+ }
744
+ child.unref();
745
+ return { pid: child.pid, model };
746
+ }
747
+ };
748
+
701
749
  // src/providers/registry.ts
702
750
  var BUILTIN = {
703
- claude: claudeProvider
751
+ claude: claudeProvider,
752
+ cursor: cursorProvider
704
753
  };
705
754
  var overrideProvider = null;
706
755
  function resolveWorkerProvider(name) {
@@ -1414,14 +1463,14 @@ function usage(code = 0) {
1414
1463
  [
1415
1464
  "Usage:",
1416
1465
  " kynver login --api-key KEY",
1417
- " kynver setup [--api-base-url URL] [--agent-os-id ID] [--agent-os-slug SLUG] [--repo PATH] [--max-workers N]",
1466
+ " kynver setup [--api-base-url URL] [--agent-os-id ID] [--agent-os-slug SLUG] [--repo PATH] [--max-workers N] [--provider claude|cursor]",
1418
1467
  " kynver daemon --run RUN_ID --agent-os-id AOS_ID [--execute] [--interval-ms MS]",
1419
1468
  " kynver run create --repo /path/repo [--name name] [--base origin/main]",
1420
1469
  " kynver run list",
1421
1470
  " kynver run status --run RUN_ID",
1422
1471
  " kynver run dispatch --run RUN_ID --agent-os-id AOS_ID [--base-url URL] [--secret SECRET] [--execute] [--lane any|implementation|review|landing] [--max-starts 1] [--lease-ms MS] [--owned path[,path]] [--model claude-opus-4-7] [--disk-path /]",
1423
1472
  " kynver run sweep --run RUN_ID --agent-os-id AOS_ID [--base-url URL] [--secret SECRET] [--grace-ms MS]",
1424
- ' kynver worker start --run RUN_ID --name worker --task "..." [--owned path[,path]] [--model claude-opus-4-7] [--agent-os-id AOS_ID] [--task-id TASK_ID]',
1473
+ ' kynver worker start --run RUN_ID --name worker --task "..." [--owned path[,path]] [--model MODEL] [--provider claude|cursor] [--agent-os-id AOS_ID] [--task-id TASK_ID]',
1425
1474
  " kynver worker status --run RUN_ID --name worker",
1426
1475
  " kynver worker tail --run RUN_ID --name worker [--lines 40] [--raw]",
1427
1476
  " kynver worker stop --run RUN_ID --name worker",
@@ -1433,8 +1482,15 @@ function usage(code = 0) {
1433
1482
  async function main(argv = process.argv.slice(2)) {
1434
1483
  if (argv.length === 0 || isHelpFlag(argv[0])) return usage(0);
1435
1484
  const scope = argv.shift();
1436
- const action = argv.shift();
1437
- const args = parseArgs(argv);
1485
+ let action;
1486
+ let rest;
1487
+ if (scope === "run" || scope === "worker") {
1488
+ action = argv.shift();
1489
+ rest = argv;
1490
+ } else {
1491
+ rest = argv;
1492
+ }
1493
+ const args = parseArgs(rest);
1438
1494
  const { runsDir, worktreesDir } = getPaths();
1439
1495
  mkdirSync5(runsDir, { recursive: true });
1440
1496
  mkdirSync5(worktreesDir, { recursive: true });