@sideboard-ai/core 0.1.231 → 0.1.233

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 (42) hide show
  1. package/dist/agents/cursor-runner.cjs +167 -62
  2. package/dist/agents/cursor-runner.js +16 -9
  3. package/dist/{agents-ENAQHQRZ.js → agents-J2CUJHPC.js} +16 -6
  4. package/dist/{agents-TCTEAK6M.js → agents-LDYMFW6N.js} +17 -7
  5. package/dist/{chunk-TQBUXKIB.js → chunk-26T43LBM.js} +97 -11
  6. package/dist/{chunk-PO4M4JAJ.js → chunk-2P4XKWV2.js} +1 -1
  7. package/dist/{chunk-ABOBTSO6.js → chunk-2UG25RMK.js} +18 -5
  8. package/dist/{chunk-4CZ25DO2.js → chunk-4VFOJZPS.js} +2 -2
  9. package/dist/{chunk-N5TX66CD.js → chunk-7H2CVVLF.js} +2 -2
  10. package/dist/{chunk-HZLZ34FK.js → chunk-BGHDWCAV.js} +69 -30
  11. package/dist/{chunk-SZJZEFTY.js → chunk-DD67JWTN.js} +1 -1
  12. package/dist/{chunk-JJRRLCCS.js → chunk-NLETJP7Z.js} +64 -30
  13. package/dist/{chunk-FA4CPYCY.js → chunk-PZQNE5X4.js} +81 -41
  14. package/dist/{chunk-HVUVQXZ2.js → chunk-QVN2WOKJ.js} +18 -5
  15. package/dist/{chunk-HZFLKVGC.js → chunk-S2OEFXST.js} +1 -1
  16. package/dist/{chunk-SXFRXNBM.js → chunk-SPAMHHJH.js} +1 -1
  17. package/dist/{chunk-ZXJMAKEP.js → chunk-TNVJPFHM.js} +5 -5
  18. package/dist/{chunk-UNTOZA3C.js → chunk-TWXSZYR2.js} +1 -1
  19. package/dist/{chunk-6L25K7BE.js → chunk-TXMFBL3X.js} +195 -73
  20. package/dist/{connected-teams-PIBQTOJU.js → connected-teams-JUJAQZZE.js} +2 -2
  21. package/dist/{connected-teams-RVD3PFAG.js → connected-teams-KQUDU7LZ.js} +2 -2
  22. package/dist/{coordinator-prompt-YKLXQTWH.js → coordinator-prompt-CE7MN6QY.js} +4 -4
  23. package/dist/{coordinator-prompt-DFXYTM6D.js → coordinator-prompt-IGDMFKCD.js} +4 -4
  24. package/dist/{global-workspace-EYZKYHAO.js → global-workspace-7WH24UFO.js} +4 -4
  25. package/dist/{global-workspace-4SPANNJT.js → global-workspace-NCIC2Y2U.js} +4 -4
  26. package/dist/index.cjs +542 -337
  27. package/dist/index.d.cts +32 -4
  28. package/dist/index.d.ts +32 -4
  29. package/dist/index.js +31 -8
  30. package/dist/mcp/run-stdio.cjs +465 -315
  31. package/dist/mcp/run-stdio.js +7 -7
  32. package/dist/{orchestrator-ZT3SJVKF.js → orchestrator-BXALNM4M.js} +8 -8
  33. package/dist/{orchestrator-HMJPNUN5.js → orchestrator-NLZMHTLX.js} +7 -7
  34. package/dist/{run-UEQM4JMZ.js → run-PCX5QWR4.js} +1 -1
  35. package/dist/{run-QDZCTP4Y.js → run-TB7RBII2.js} +1 -1
  36. package/dist/{workspaces-73Y7IJY2.js → workspaces-H2TRFDE2.js} +4 -4
  37. package/dist/{workspaces-FQCSCTNH.js → workspaces-NSQZSDQD.js} +4 -4
  38. package/dist/{worktree-DOPRKG7K.js → worktree-FMIX4BRV.js} +3 -3
  39. package/dist/{worktree-36VEFUJN.js → worktree-W7BSI4GU.js} +3 -3
  40. package/dist/{worktree-exclude-K7QK4RI5.js → worktree-exclude-5N2KTYIT.js} +2 -2
  41. package/dist/{worktree-exclude-L32WEBX6.js → worktree-exclude-RXZPTCNH.js} +2 -2
  42. package/package.json +2 -2
@@ -2,13 +2,13 @@
2
2
 
3
3
  import {
4
4
  isOrchestratorThread
5
- } from "./chunk-UNTOZA3C.js";
5
+ } from "./chunk-TWXSZYR2.js";
6
6
  import {
7
7
  applyConnectedTeamToCli,
8
8
  brightsyMcpServerName,
9
9
  ensureCliTeamTracked,
10
10
  ensureConnectedBrightsyTeamTokens
11
- } from "./chunk-SXFRXNBM.js";
11
+ } from "./chunk-SPAMHHJH.js";
12
12
  import {
13
13
  loadBrightsyConfig
14
14
  } from "./chunk-P2BSMNHB.js";
@@ -20,14 +20,15 @@ import {
20
20
  mergeAgentGitAuthEnv,
21
21
  resolveAgentGitAuthEnv,
22
22
  resolveCodexGitWritableRoots
23
- } from "./chunk-4CZ25DO2.js";
23
+ } from "./chunk-4VFOJZPS.js";
24
24
  import {
25
25
  enrichPathWithNpmGlobalBin,
26
26
  isConductorBundledCli,
27
+ npmGlobalNodeModules,
27
28
  resolveCommandBinarySync,
28
29
  run,
29
30
  withExportedPath
30
- } from "./chunk-ABOBTSO6.js";
31
+ } from "./chunk-2UG25RMK.js";
31
32
  import {
32
33
  claudeChromeEnabled,
33
34
  fromInclusiveInputUsage,
@@ -2548,7 +2549,7 @@ var claudeAdapter = {
2548
2549
  );
2549
2550
  }
2550
2551
  const mode = permissionMode(thread);
2551
- const { isOrchestratorThread: isOrchestratorThread2 } = await import("./global-workspace-EYZKYHAO.js");
2552
+ const { isOrchestratorThread: isOrchestratorThread2 } = await import("./global-workspace-7WH24UFO.js");
2552
2553
  const isOrchestrator = isOrchestratorThread2(thread);
2553
2554
  const injectedServers = await buildInjectedMcpServers({
2554
2555
  includeSideboard: true,
@@ -3161,11 +3162,91 @@ var codexAdapter = {
3161
3162
  };
3162
3163
 
3163
3164
  // src/agents/cursor.ts
3164
- import { existsSync as existsSync11 } from "fs";
3165
- import { createRequire as createRequire3 } from "module";
3166
- import { dirname as dirname5, join as join9 } from "path";
3167
- import { fileURLToPath as fileURLToPath2 } from "url";
3168
- import { Cursor } from "@cursor/sdk";
3165
+ import { existsSync as existsSync12 } from "fs";
3166
+ import { createRequire as createRequire4 } from "module";
3167
+ import { dirname as dirname6, join as join10 } from "path";
3168
+ import { fileURLToPath as fileURLToPath3 } from "url";
3169
+
3170
+ // src/agents/cursor-sdk-resolve.ts
3171
+ import { existsSync as existsSync10, readFileSync as readFileSync5 } from "fs";
3172
+ import { createRequire as createRequire2 } from "module";
3173
+ import { basename, dirname as dirname4, join as join8 } from "path";
3174
+ import { fileURLToPath as fileURLToPath2, pathToFileURL } from "url";
3175
+ var CURSOR_SDK_INSTALL_HINT = "Cursor SDK is not installed. Settings \u2192 Agents \u2192 Cursor \u2192 Install (`npm i -g @cursor/sdk`). Sideboard does not ship the SDK \u2014 update it anytime without a new Sideboard build.";
3176
+ function thisModuleFile() {
3177
+ const cjsDir = typeof __dirname !== "undefined" ? __dirname : "";
3178
+ if (cjsDir) return join8(cjsDir, "cursor-sdk-resolve.js");
3179
+ try {
3180
+ return fileURLToPath2(import.meta.url);
3181
+ } catch {
3182
+ return join8(process.cwd(), "package.json");
3183
+ }
3184
+ }
3185
+ function packageRootLooksLikeSdk(dir) {
3186
+ try {
3187
+ const raw = readFileSync5(join8(dir, "package.json"), "utf8");
3188
+ const pkg = JSON.parse(raw);
3189
+ return pkg.name === "@cursor/sdk" && existsSync10(dir);
3190
+ } catch {
3191
+ return false;
3192
+ }
3193
+ }
3194
+ function resolvedPackageRoot(fromFile) {
3195
+ try {
3196
+ const req = createRequire2(fromFile);
3197
+ const pkgJson = req.resolve("@cursor/sdk/package.json");
3198
+ const root = dirname4(pkgJson);
3199
+ return packageRootLooksLikeSdk(root) ? root : null;
3200
+ } catch {
3201
+ return null;
3202
+ }
3203
+ }
3204
+ function resolveCursorSdkRoot(opts) {
3205
+ const env = opts?.env ?? process.env;
3206
+ const override = env.SIDEBOARD_CURSOR_SDK?.trim();
3207
+ if (override) {
3208
+ return packageRootLooksLikeSdk(override) ? override : null;
3209
+ }
3210
+ const globalNm = npmGlobalNodeModules(env);
3211
+ if (globalNm) {
3212
+ const globalRoot = join8(globalNm, "@cursor/sdk");
3213
+ if (packageRootLooksLikeSdk(globalRoot)) return globalRoot;
3214
+ }
3215
+ const cwdPkg = join8(process.cwd(), "package.json");
3216
+ return resolvedPackageRoot(thisModuleFile()) ?? resolvedPackageRoot(cwdPkg);
3217
+ }
3218
+ function isCursorSdkInstalled(opts) {
3219
+ return Boolean(resolveCursorSdkRoot(opts));
3220
+ }
3221
+ async function importCursorSdk(opts) {
3222
+ const root = resolveCursorSdkRoot(opts);
3223
+ if (!root) return null;
3224
+ try {
3225
+ const req = createRequire2(join8(root, "package.json"));
3226
+ const entry = req.resolve("@cursor/sdk");
3227
+ return await import(pathToFileURL(entry).href);
3228
+ } catch {
3229
+ return null;
3230
+ }
3231
+ }
3232
+ function cursorSdkPlatformRipgrepPackage() {
3233
+ return `@cursor/sdk-${process.platform}-${process.arch}`;
3234
+ }
3235
+ function nodeModulesDirForPackageRoot(packageRoot) {
3236
+ const parent = dirname4(packageRoot);
3237
+ return basename(parent).startsWith("@") ? dirname4(parent) : parent;
3238
+ }
3239
+ function cursorSdkRipgrepCandidate(opts) {
3240
+ const root = resolveCursorSdkRoot(opts);
3241
+ if (!root) return null;
3242
+ const nm = nodeModulesDirForPackageRoot(root);
3243
+ const pkg = cursorSdkPlatformRipgrepPackage();
3244
+ const bin = process.platform === "win32" ? "rg.exe" : "rg";
3245
+ const sibling = join8(nm, pkg, "bin", bin);
3246
+ if (existsSync10(sibling)) return sibling;
3247
+ const nested = join8(root, "node_modules", pkg, "bin", bin);
3248
+ return existsSync10(nested) ? nested : null;
3249
+ }
3169
3250
 
3170
3251
  // src/agents/cursor-events.ts
3171
3252
  function usageFromCursor(usage) {
@@ -3379,9 +3460,9 @@ function parseCursorRunnerLine(line) {
3379
3460
  }
3380
3461
 
3381
3462
  // src/agents/cursor-ripgrep.ts
3382
- import { existsSync as existsSync10 } from "fs";
3383
- import { createRequire as createRequire2 } from "module";
3384
- import { dirname as dirname4, isAbsolute, join as join8, parse, resolve as resolvePath } from "path";
3463
+ import { existsSync as existsSync11 } from "fs";
3464
+ import { createRequire as createRequire3 } from "module";
3465
+ import { dirname as dirname5, isAbsolute, join as join9, parse, resolve as resolvePath } from "path";
3385
3466
  var RIPGREP_ENV = "CURSOR_RIPGREP_PATH";
3386
3467
  function rgBinaryName() {
3387
3468
  return process.platform === "win32" ? "rg.exe" : "rg";
@@ -3393,19 +3474,19 @@ function usableRipgrepPath(candidate) {
3393
3474
  const raw = candidate?.trim();
3394
3475
  if (!raw || !isAbsolute(raw)) return null;
3395
3476
  const readable = nodeReadableScriptPath(raw);
3396
- if (!existsSync10(readable) || isAsarPath(readable)) return null;
3477
+ if (!existsSync11(readable) || isAsarPath(readable)) return null;
3397
3478
  return readable;
3398
3479
  }
3399
3480
  function walkForBundledRipgrep(startFile) {
3400
3481
  if (!startFile) return null;
3401
3482
  const pkg = platformRipgrepPackage();
3402
3483
  const name = rgBinaryName();
3403
- let dir = dirname4(resolvePath(startFile));
3484
+ let dir = dirname5(resolvePath(startFile));
3404
3485
  const root = parse(dir).root;
3405
3486
  while (dir !== root) {
3406
- const hit = usableRipgrepPath(join8(dir, "node_modules", pkg, "bin", name));
3487
+ const hit = usableRipgrepPath(join9(dir, "node_modules", pkg, "bin", name));
3407
3488
  if (hit) return hit;
3408
- const next = dirname4(dir);
3489
+ const next = dirname5(dir);
3409
3490
  if (next === dir) break;
3410
3491
  dir = next;
3411
3492
  }
@@ -3413,9 +3494,9 @@ function walkForBundledRipgrep(startFile) {
3413
3494
  }
3414
3495
  function requireResolveBundledRipgrep(fromFile) {
3415
3496
  try {
3416
- const req = createRequire2(fromFile);
3497
+ const req = createRequire3(fromFile);
3417
3498
  const pkgJson = req.resolve(`${platformRipgrepPackage()}/package.json`);
3418
- return usableRipgrepPath(join8(dirname4(pkgJson), "bin", rgBinaryName()));
3499
+ return usableRipgrepPath(join9(dirname5(pkgJson), "bin", rgBinaryName()));
3419
3500
  } catch {
3420
3501
  return null;
3421
3502
  }
@@ -3431,7 +3512,7 @@ function resolveCursorRipgrepPath(opts) {
3431
3512
  const start = opts?.startFile?.trim() || process.argv[1] || // CJS bundle only — ESM has no __filename; argv[1] is the running script.
3432
3513
  // eslint-disable-next-line camelcase
3433
3514
  (typeof __filename !== "undefined" ? __filename : "");
3434
- return walkForBundledRipgrep(start) ?? requireResolveBundledRipgrep(start);
3515
+ return walkForBundledRipgrep(start) ?? usableRipgrepPath(cursorSdkRipgrepCandidate({ env })) ?? requireResolveBundledRipgrep(start);
3435
3516
  }
3436
3517
  function cursorRipgrepEnv(opts) {
3437
3518
  const path = resolveCursorRipgrepPath(opts);
@@ -3469,8 +3550,10 @@ async function listCursorModels() {
3469
3550
  }
3470
3551
  const apiKey = resolveCursorApiKey();
3471
3552
  if (!apiKey) return FALLBACK_CURSOR_MODELS;
3553
+ const sdk = await importCursorSdk();
3554
+ if (!sdk) return FALLBACK_CURSOR_MODELS;
3472
3555
  try {
3473
- const listed = await Cursor.models.list({ apiKey });
3556
+ const listed = await sdk.Cursor.models.list({ apiKey });
3474
3557
  const models = listed.map((m) => ({
3475
3558
  id: m.id,
3476
3559
  displayName: m.displayName || m.id,
@@ -3487,11 +3570,11 @@ function entryDir() {
3487
3570
  const cjsDir = typeof __dirname !== "undefined" ? __dirname : "";
3488
3571
  if (cjsDir) return cjsDir;
3489
3572
  try {
3490
- return dirname5(fileURLToPath2(import.meta.url));
3573
+ return dirname6(fileURLToPath3(import.meta.url));
3491
3574
  } catch {
3492
3575
  try {
3493
- const req = createRequire3(process.cwd() + "/");
3494
- return dirname5(req.resolve("@sideboard-ai/core"));
3576
+ const req = createRequire4(process.cwd() + "/");
3577
+ return dirname6(req.resolve("@sideboard-ai/core"));
3495
3578
  } catch {
3496
3579
  return process.cwd();
3497
3580
  }
@@ -3502,23 +3585,33 @@ function cursorRunnerPath() {
3502
3585
  if (packaged) return packaged;
3503
3586
  const root = entryDir();
3504
3587
  const candidates = [
3505
- join9(root, "agents", "cursor-runner.js"),
3506
- join9(root, "agents", "cursor-runner.cjs"),
3588
+ join10(root, "agents", "cursor-runner.js"),
3589
+ join10(root, "agents", "cursor-runner.cjs"),
3507
3590
  // If somehow resolved from package root instead of dist/
3508
- join9(root, "dist", "agents", "cursor-runner.js"),
3509
- join9(root, "dist", "agents", "cursor-runner.cjs"),
3591
+ join10(root, "dist", "agents", "cursor-runner.js"),
3592
+ join10(root, "dist", "agents", "cursor-runner.cjs"),
3510
3593
  // Source tree (dev): packages/core/src/agents/cursor-runner.ts
3511
- join9(root, "cursor-runner.ts"),
3512
- join9(root, "src", "agents", "cursor-runner.ts")
3594
+ join10(root, "cursor-runner.ts"),
3595
+ join10(root, "src", "agents", "cursor-runner.ts")
3513
3596
  ];
3514
3597
  for (const candidate of candidates) {
3515
- if (existsSync11(candidate)) return candidate;
3598
+ if (existsSync12(candidate)) return candidate;
3516
3599
  }
3517
3600
  return candidates[0];
3518
3601
  }
3519
3602
  var cursorAdapter = {
3520
3603
  kind: "cursor",
3521
3604
  async detect() {
3605
+ if (!isCursorSdkInstalled()) {
3606
+ return {
3607
+ agent: "cursor",
3608
+ installed: false,
3609
+ authenticated: false,
3610
+ linearMcp: false,
3611
+ warnings: [],
3612
+ reason: CURSOR_SDK_INSTALL_HINT
3613
+ };
3614
+ }
3522
3615
  const apiKey = resolveCursorApiKey();
3523
3616
  if (!apiKey) {
3524
3617
  return {
@@ -3600,7 +3693,7 @@ var cursorAdapter = {
3600
3693
  };
3601
3694
 
3602
3695
  // src/agents/opencode.ts
3603
- import { existsSync as existsSync12 } from "fs";
3696
+ import { existsSync as existsSync13 } from "fs";
3604
3697
  var FALLBACK_OPENCODE_MODELS = [
3605
3698
  { id: "opencode/big-pickle", displayName: "opencode \xB7 big-pickle" },
3606
3699
  {
@@ -3659,7 +3752,7 @@ async function listOpencodeModels() {
3659
3752
  if (opencode === "opencode") {
3660
3753
  const which = await run("which", ["opencode"], { reject: false });
3661
3754
  if (which.exitCode !== 0) return FALLBACK_OPENCODE_MODELS;
3662
- } else if (!existsSync12(opencode)) {
3755
+ } else if (!existsSync13(opencode)) {
3663
3756
  return FALLBACK_OPENCODE_MODELS;
3664
3757
  }
3665
3758
  const listed = await run(opencode, ["models"], { reject: false });
@@ -3694,7 +3787,7 @@ var opencodeAdapter = {
3694
3787
  async detect() {
3695
3788
  const opencode = resolveAgentExecutable("opencode");
3696
3789
  if (opencode !== "opencode") {
3697
- if (!existsSync12(opencode)) {
3790
+ if (!existsSync13(opencode)) {
3698
3791
  return {
3699
3792
  agent: "opencode",
3700
3793
  installed: false,
@@ -4371,9 +4464,9 @@ function formatClaudeUsageOverLimitWait(windows, now = /* @__PURE__ */ new Date(
4371
4464
  }
4372
4465
 
4373
4466
  // src/agents/claude-usage-client.ts
4374
- import { existsSync as existsSync13, readFileSync as readFileSync5 } from "fs";
4467
+ import { existsSync as existsSync14, readFileSync as readFileSync6 } from "fs";
4375
4468
  import { homedir as homedir5 } from "os";
4376
- import { join as join10 } from "path";
4469
+ import { join as join11 } from "path";
4377
4470
  var CLAUDE_OAUTH_USAGE_URL = "https://api.anthropic.com/api/oauth/usage";
4378
4471
  var CLAUDE_USAGE_TTL_MS = 9e4;
4379
4472
  var CLAUDE_USAGE_ERROR_TTL_MS = 5 * 6e4;
@@ -4401,14 +4494,14 @@ function accessTokenFromCredentialsJson(raw) {
4401
4494
  }
4402
4495
  }
4403
4496
  function claudeCredentialsPath() {
4404
- const root = process.env.CLAUDE_CONFIG_DIR?.trim() || join10(homedir5(), ".claude");
4405
- return join10(root, ".credentials.json");
4497
+ const root = process.env.CLAUDE_CONFIG_DIR?.trim() || join11(homedir5(), ".claude");
4498
+ return join11(root, ".credentials.json");
4406
4499
  }
4407
4500
  async function readFileAccessToken() {
4408
4501
  const path = claudeCredentialsPath();
4409
- if (!existsSync13(path)) return null;
4502
+ if (!existsSync14(path)) return null;
4410
4503
  try {
4411
- return accessTokenFromCredentialsJson(readFileSync5(path, "utf8"));
4504
+ return accessTokenFromCredentialsJson(readFileSync6(path, "utf8"));
4412
4505
  } catch {
4413
4506
  return null;
4414
4507
  }
@@ -4514,6 +4607,7 @@ async function getClaudePlanUsage(opts = {}) {
4514
4607
  }
4515
4608
 
4516
4609
  // src/agents/install.ts
4610
+ import { existsSync as existsSync15 } from "fs";
4517
4611
  var SETUP = {
4518
4612
  claude: {
4519
4613
  agent: "claude",
@@ -4522,7 +4616,8 @@ var SETUP = {
4522
4616
  docsUrl: "https://code.claude.com/docs/en/install",
4523
4617
  installCommand: "npm install -g @anthropic-ai/claude-code",
4524
4618
  loginCommand: "claude auth login",
4525
- npmPackage: "@anthropic-ai/claude-code"
4619
+ npmPackage: "@anthropic-ai/claude-code",
4620
+ updateArgs: ["update"]
4526
4621
  },
4527
4622
  codex: {
4528
4623
  agent: "codex",
@@ -4531,7 +4626,8 @@ var SETUP = {
4531
4626
  docsUrl: "https://github.com/openai/codex",
4532
4627
  installCommand: "npm install -g @openai/codex",
4533
4628
  loginCommand: "codex login",
4534
- npmPackage: "@openai/codex"
4629
+ npmPackage: "@openai/codex",
4630
+ updateArgs: ["update"]
4535
4631
  },
4536
4632
  opencode: {
4537
4633
  agent: "opencode",
@@ -4541,20 +4637,22 @@ var SETUP = {
4541
4637
  // Prefer the official installer; npm package name is opencode-ai.
4542
4638
  installCommand: "curl -fsSL https://opencode.ai/install | bash",
4543
4639
  loginCommand: "opencode auth login",
4544
- npmPackage: "opencode-ai@latest"
4640
+ npmPackage: "opencode-ai@latest",
4641
+ updateArgs: ["upgrade"]
4545
4642
  },
4546
4643
  cursor: {
4547
4644
  agent: "cursor",
4548
- kind: "bundled-sdk",
4549
- summary: "No CLI install \u2014 Sideboard ships the Cursor SDK. Add a CURSOR_API_KEY from the Cursor dashboard.",
4550
- docsUrl: "https://cursor.com/dashboard/integrations",
4551
- installCommand: null,
4552
- loginCommand: null
4645
+ kind: "cli",
4646
+ summary: "Install (or update) @cursor/sdk with npm \u2014 Sideboard does not pin it in the app. Then add a CURSOR_API_KEY.",
4647
+ docsUrl: "https://www.npmjs.com/package/@cursor/sdk",
4648
+ installCommand: "npm install -g @cursor/sdk",
4649
+ loginCommand: null,
4650
+ npmPackage: "@cursor/sdk"
4553
4651
  },
4554
4652
  brightsy: {
4555
4653
  agent: "brightsy",
4556
4654
  kind: "cli",
4557
- summary: "Install the Brightsy CLI, then run `brightsy login`.",
4655
+ summary: "Install (or update) the Brightsy CLI with npm, then run `brightsy login`.",
4558
4656
  docsUrl: "https://www.npmjs.com/package/@brightsy/cli",
4559
4657
  installCommand: "npm install -g @brightsy/cli",
4560
4658
  loginCommand: "brightsy login",
@@ -4650,16 +4748,6 @@ async function whichOnPath(bin) {
4650
4748
  }
4651
4749
  async function installNpmGlobalPackage(opts) {
4652
4750
  enrichPathWithNpmGlobalBin();
4653
- if (opts.cliBin) {
4654
- const existing = await whichOnPath(opts.cliBin);
4655
- if (existing) {
4656
- return {
4657
- ok: true,
4658
- command: existing,
4659
- message: isConductorBundledCli(existing) ? `Using Conductor\u2019s ${opts.cliBin} at ${existing}. No extra install \u2014 Log in only if auth is missing.` : `Already on PATH: ${existing}`
4660
- };
4661
- }
4662
- }
4663
4751
  const result = await run("npm", ["install", "-g", opts.npmPackage], { reject: false });
4664
4752
  const ok = result.exitCode === 0;
4665
4753
  if (!ok) {
@@ -4696,6 +4784,33 @@ async function installNpmGlobalPackage(opts) {
4696
4784
  message: binPath ? `Installed ${opts.npmPackage} \u2192 ${binPath}` : `Installed ${opts.npmPackage} (CLI not yet on PATH)`
4697
4785
  };
4698
4786
  }
4787
+ async function resolveExistingCli(agent) {
4788
+ if (agent === "cursor") return null;
4789
+ const exe = resolveAgentExecutable(agent);
4790
+ if ((exe.includes("/") || exe.includes("\\")) && existsSync15(exe)) return exe;
4791
+ enrichPathWithNpmGlobalBin();
4792
+ return whichOnPath(CLI_BIN[agent]);
4793
+ }
4794
+ async function runVendorUpdate(existing, updateArgs) {
4795
+ const result = await run(existing, updateArgs, {
4796
+ reject: false,
4797
+ timeoutMs: 12e4
4798
+ });
4799
+ const command = `${existing} ${updateArgs.join(" ")}`;
4800
+ const ok = result.exitCode === 0;
4801
+ const detail = result.stdout.trim() || result.stderr.trim() || `exit ${result.exitCode}`;
4802
+ return {
4803
+ ok,
4804
+ command,
4805
+ exitCode: result.exitCode,
4806
+ stdout: result.stdout,
4807
+ stderr: result.stderr,
4808
+ message: ok ? isConductorBundledCli(existing) ? `Updated Conductor\u2019s CLI at ${existing}. ${detail}` : `Updated ${command}. ${detail}` : `Update failed (${command}): ${detail}`
4809
+ };
4810
+ }
4811
+ function isCurlInstaller(command) {
4812
+ return /curl\s| \|\s*bash/.test(command);
4813
+ }
4699
4814
  async function installAgent(agent) {
4700
4815
  const info = getAgentSetupInfo(agent);
4701
4816
  if (info.kind === "bundled-sdk" || info.kind === "api-key") {
@@ -4707,21 +4822,25 @@ async function installAgent(agent) {
4707
4822
  if (!info.installCommand) {
4708
4823
  return { ok: false, message: `No install command for ${agent}` };
4709
4824
  }
4710
- if (/curl\s| \|\s*bash/.test(info.installCommand) || !info.npmPackage) {
4711
- await openInSystemTerminal(info.installCommand);
4712
- return {
4713
- ok: true,
4714
- openedTerminal: true,
4715
- command: info.installCommand,
4716
- message: `Opened Terminal to run: ${info.installCommand}`
4717
- };
4825
+ const existing = await resolveExistingCli(agent);
4826
+ if (existing && info.updateArgs?.length) {
4827
+ return runVendorUpdate(existing, info.updateArgs);
4718
4828
  }
4719
- const cliBin = agent === "cursor" ? null : CLI_BIN[agent];
4720
- return installNpmGlobalPackage({
4721
- npmPackage: info.npmPackage,
4722
- installCommand: info.installCommand,
4723
- cliBin
4724
- });
4829
+ if (info.npmPackage && !isCurlInstaller(info.installCommand)) {
4830
+ const cliBin = agent === "cursor" ? null : CLI_BIN[agent];
4831
+ return installNpmGlobalPackage({
4832
+ npmPackage: info.npmPackage,
4833
+ installCommand: info.installCommand,
4834
+ cliBin
4835
+ });
4836
+ }
4837
+ await openInSystemTerminal(info.installCommand);
4838
+ return {
4839
+ ok: true,
4840
+ openedTerminal: true,
4841
+ command: info.installCommand,
4842
+ message: `Opened Terminal to run: ${info.installCommand}`
4843
+ };
4725
4844
  }
4726
4845
  async function loginAgent(agent) {
4727
4846
  const info = getAgentSetupInfo(agent);
@@ -4800,6 +4919,9 @@ export {
4800
4919
  claudeAdapter,
4801
4920
  listCodexModels,
4802
4921
  codexAdapter,
4922
+ CURSOR_SDK_INSTALL_HINT,
4923
+ resolveCursorSdkRoot,
4924
+ isCursorSdkInstalled,
4803
4925
  preferredCursorCostCents,
4804
4926
  turnCostUsdFromCursorUsage,
4805
4927
  cursorSdkMessageToEvents,
@@ -7,11 +7,11 @@ import {
7
7
  ensureConnectedBrightsyTeamTokens,
8
8
  getConnectedBrightsyTeamsRaw,
9
9
  listConnectedBrightsyTeams
10
- } from "./chunk-ZXJMAKEP.js";
10
+ } from "./chunk-TNVJPFHM.js";
11
11
  import "./chunk-ROPGQRPU.js";
12
12
  import "./chunk-N7WZ6NIN.js";
13
13
  import "./chunk-WFUDY6PC.js";
14
- import "./chunk-HVUVQXZ2.js";
14
+ import "./chunk-QVN2WOKJ.js";
15
15
  import "./chunk-4TR3HZFT.js";
16
16
  export {
17
17
  applyConnectedTeamToCli,
@@ -9,10 +9,10 @@ import {
9
9
  ensureConnectedBrightsyTeamTokens,
10
10
  getConnectedBrightsyTeamsRaw,
11
11
  listConnectedBrightsyTeams
12
- } from "./chunk-SXFRXNBM.js";
12
+ } from "./chunk-SPAMHHJH.js";
13
13
  import "./chunk-P2BSMNHB.js";
14
14
  import "./chunk-VKQGAWHY.js";
15
- import "./chunk-ABOBTSO6.js";
15
+ import "./chunk-2UG25RMK.js";
16
16
  import "./chunk-EQNRWDLN.js";
17
17
  import "./chunk-WWUABK6B.js";
18
18
  export {
@@ -9,13 +9,13 @@ import {
9
9
  enrichWorkspacesWithGithub,
10
10
  ensureGlobalCoordinatorCwd,
11
11
  formatWorkspaceInventory
12
- } from "./chunk-UNTOZA3C.js";
13
- import "./chunk-4CZ25DO2.js";
12
+ } from "./chunk-TWXSZYR2.js";
13
+ import "./chunk-4VFOJZPS.js";
14
14
  import "./chunk-D6JWYJ4P.js";
15
15
  import "./chunk-XJETIO4K.js";
16
16
  import "./chunk-X5B3OS5I.js";
17
- import "./chunk-SZJZEFTY.js";
18
- import "./chunk-ABOBTSO6.js";
17
+ import "./chunk-DD67JWTN.js";
18
+ import "./chunk-2UG25RMK.js";
19
19
  import "./chunk-RZTRWN2V.js";
20
20
  import "./chunk-NSTQ6QKD.js";
21
21
  import "./chunk-KGZBYWZ3.js";
@@ -7,10 +7,10 @@ import {
7
7
  enrichWorkspacesWithGithub,
8
8
  ensureGlobalCoordinatorCwd,
9
9
  formatWorkspaceInventory
10
- } from "./chunk-HZFLKVGC.js";
11
- import "./chunk-N5TX66CD.js";
10
+ } from "./chunk-S2OEFXST.js";
11
+ import "./chunk-7H2CVVLF.js";
12
12
  import "./chunk-6K64FJDD.js";
13
- import "./chunk-PO4M4JAJ.js";
13
+ import "./chunk-2P4XKWV2.js";
14
14
  import "./chunk-I5NC7DWO.js";
15
15
  import "./chunk-WDRMZKVB.js";
16
16
  import "./chunk-JT7R45JB.js";
@@ -18,7 +18,7 @@ import "./chunk-4VGCG2HV.js";
18
18
  import "./chunk-7J72QJOM.js";
19
19
  import "./chunk-77WWLBCI.js";
20
20
  import "./chunk-WFUDY6PC.js";
21
- import "./chunk-HVUVQXZ2.js";
21
+ import "./chunk-QVN2WOKJ.js";
22
22
  import "./chunk-4TR3HZFT.js";
23
23
  export {
24
24
  COORDINATOR_TOOL_PLAYBOOK,
@@ -17,13 +17,13 @@ import {
17
17
  orchestratorSessionPoisonedByBuiltins,
18
18
  slackCoordinatorSourceRef,
19
19
  takenTeamSlugsForOrchestration
20
- } from "./chunk-UNTOZA3C.js";
21
- import "./chunk-4CZ25DO2.js";
20
+ } from "./chunk-TWXSZYR2.js";
21
+ import "./chunk-4VFOJZPS.js";
22
22
  import "./chunk-D6JWYJ4P.js";
23
23
  import "./chunk-XJETIO4K.js";
24
24
  import "./chunk-X5B3OS5I.js";
25
- import "./chunk-SZJZEFTY.js";
26
- import "./chunk-ABOBTSO6.js";
25
+ import "./chunk-DD67JWTN.js";
26
+ import "./chunk-2UG25RMK.js";
27
27
  import "./chunk-RZTRWN2V.js";
28
28
  import "./chunk-NSTQ6QKD.js";
29
29
  import "./chunk-KGZBYWZ3.js";
@@ -15,10 +15,10 @@ import {
15
15
  orchestratorSessionPoisonedByBuiltins,
16
16
  slackCoordinatorSourceRef,
17
17
  takenTeamSlugsForOrchestration
18
- } from "./chunk-HZFLKVGC.js";
19
- import "./chunk-N5TX66CD.js";
18
+ } from "./chunk-S2OEFXST.js";
19
+ import "./chunk-7H2CVVLF.js";
20
20
  import "./chunk-6K64FJDD.js";
21
- import "./chunk-PO4M4JAJ.js";
21
+ import "./chunk-2P4XKWV2.js";
22
22
  import "./chunk-I5NC7DWO.js";
23
23
  import "./chunk-WDRMZKVB.js";
24
24
  import "./chunk-JT7R45JB.js";
@@ -28,7 +28,7 @@ import "./chunk-77WWLBCI.js";
28
28
  import {
29
29
  globalAgentCwd
30
30
  } from "./chunk-WFUDY6PC.js";
31
- import "./chunk-HVUVQXZ2.js";
31
+ import "./chunk-QVN2WOKJ.js";
32
32
  import "./chunk-4TR3HZFT.js";
33
33
  export {
34
34
  GLOBAL_WORKSPACE_ID,