@snowyroad/braid 0.98.0 → 0.98.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.
@@ -400,7 +400,7 @@ var InviteExpiredError = class extends Error {
400
400
  }
401
401
  };
402
402
  async function redeemInvite(relayHttpUrl, code) {
403
- const { boundedJsonFetch: boundedJsonFetch2 } = await import("./http-7QNDIXBN.js");
403
+ const { boundedJsonFetch: boundedJsonFetch2 } = await import("./http-SAC6PMXK.js");
404
404
  const r = await boundedJsonFetch2(`${relayHttpUrl.replace(/\/$/, "")}/invites/redeem`, {
405
405
  method: "POST",
406
406
  headers: { "content-type": "application/json" },
@@ -492,7 +492,7 @@ function validateReplacementToken(newToken, currentToken, nowMs = Date.now()) {
492
492
  return { ok: true };
493
493
  }
494
494
  async function mintAccessToken(relayHttpUrl, agentKey, fetchFn = fetch, dpopProof) {
495
- const { boundedJsonFetch: boundedJsonFetch2 } = await import("./http-7QNDIXBN.js");
495
+ const { boundedJsonFetch: boundedJsonFetch2 } = await import("./http-SAC6PMXK.js");
496
496
  const r = await boundedJsonFetch2(`${relayHttpUrl.replace(/\/$/, "")}/agents/token`, {
497
497
  method: "POST",
498
498
  headers: {
@@ -2114,6 +2114,19 @@ var AcpClient = class {
2114
2114
  get exited() {
2115
2115
  return this.exitError;
2116
2116
  }
2117
+ /** D15 (git gateway): the mode of the most recently started turn (its override, else the
2118
+ * standing policy). Set in runTurn and deliberately NOT cleared when the turn settles:
2119
+ * claude-agent-acp runs autonomous model cycles between prompts (a background Bash
2120
+ * task's completion notification triggers a follow-up), and those must keep the
2121
+ * narrowing of the turn that started them. Reset by the next turn and by start(). */
2122
+ lastTurnMode;
2123
+ /** D15 (git gateway): the mode the broker's git readonly gate applies right now: the
2124
+ * running turn's override, else the last turn's mode (persisted between turns, see
2125
+ * lastTurnMode), else the standing policy. RESIDUAL: a background task started in a
2126
+ * readonly turn whose follow-up lands during a LATER full turn is judged full. */
2127
+ effectiveToolMode() {
2128
+ return this.currentTurnOverrideMode ?? this.lastTurnMode ?? this.policy.mode;
2129
+ }
2117
2130
  /**
2118
2131
  * Spawn the adapter, build the connection, initialize, and open one session.
2119
2132
  * Any failure (spawn error, premature exit, protocol error) rejects.
@@ -2124,6 +2137,7 @@ var AcpClient = class {
2124
2137
  this.activeTurnBuffer = null;
2125
2138
  this.turnQueue = Promise.resolve();
2126
2139
  this.currentTurnOverrideMode = void 0;
2140
+ this.lastTurnMode = void 0;
2127
2141
  this.exitRejecters.clear();
2128
2142
  try {
2129
2143
  await this.withWarmupCeiling(this.startInner());
@@ -2433,6 +2447,7 @@ var AcpClient = class {
2433
2447
  };
2434
2448
  this.activeTurnBuffer = buffer;
2435
2449
  this.currentTurnOverrideMode = overrideMode;
2450
+ this.lastTurnMode = overrideMode ?? this.policy.mode;
2436
2451
  try {
2437
2452
  const resp = await this.guard(
2438
2453
  this.conn.prompt({
@@ -5817,6 +5832,18 @@ var RelayClient = class _RelayClient {
5817
5832
  };
5818
5833
 
5819
5834
  // src/mcp/broker.ts
5835
+ var CHANNEL_RESTRICTS = "This channel or message also restricts the agent to read-only, so a channel admin must allow writes too.";
5836
+ function gitReadonlyRefusal(cause, agentName, channelAlsoReadonly = false) {
5837
+ if (cause === "channel") {
5838
+ return {
5839
+ error: "git_readonly",
5840
+ text: "Git tools need full tool mode, and this turn runs read-only because this channel or message restricts the agent. Do not retry git in this turn."
5841
+ };
5842
+ }
5843
+ const name = agentName && isShellSafeName(agentName) ? agentName : "<agent-name>";
5844
+ const text = `Git tools need full tool mode. Do not retry. The operator can stop the bridge, run \`braid tools full ${name}\`, then start it again.` + (channelAlsoReadonly ? ` ${CHANNEL_RESTRICTS}` : "");
5845
+ return { error: "git_readonly", text };
5846
+ }
5820
5847
  var MAX_NOTE_CHARS = 2e3;
5821
5848
  var MAX_PRIVATE_MEMORY_CONTENT_CHARS = 2e3;
5822
5849
  var MAX_REFLECTION_FIELD_CHARS = 2e3;
@@ -5858,6 +5885,16 @@ var SourceBroker = class {
5858
5885
  setGitEnabled(enabled) {
5859
5886
  this.gitDisabledDepth = Math.max(0, this.gitDisabledDepth + (enabled ? -1 : 1));
5860
5887
  }
5888
+ /** D15: git routes need the session's EFFECTIVE tool mode to be full (standing mode,
5889
+ * narrowed by any per-turn readonly override). Read on every /git/ request. FAIL-CLOSED:
5890
+ * until a source is wired, every /git/ route answers 403 git_readonly. The bridge wires
5891
+ * it to ChannelSession.currentToolMode. */
5892
+ toolModeSource = () => ({ mode: "readonly", cause: "operator" });
5893
+ agentName;
5894
+ setToolModeSource(source, agentName) {
5895
+ this.toolModeSource = source;
5896
+ this.agentName = agentName;
5897
+ }
5861
5898
  async start() {
5862
5899
  if (this.server) throw new Error("SourceBroker already started");
5863
5900
  const isWin32 = this.platform === "win32";
@@ -5900,6 +5937,8 @@ var SourceBroker = class {
5900
5937
  // The /git/ routes (git gateway, D6/D7) are write and egress routes; they ARE gated
5901
5938
  // off lisa fresh turns: ChannelSession.onLisaFreshTurn calls setGitEnabled(false)
5902
5939
  // for the turn's duration, so a critic or builder round gets 403 git_disabled_for_turn (D15).
5940
+ // They are also refused (403 git_readonly) whenever the session's effective tool mode is
5941
+ // readonly, read per request from setToolModeSource (D15).
5903
5942
  async handle(req, res) {
5904
5943
  const send = (status, body2) => {
5905
5944
  const s = JSON.stringify(body2);
@@ -6154,6 +6193,8 @@ var SourceBroker = class {
6154
6193
  if (req.url?.startsWith("/git/")) {
6155
6194
  if (!this.gateway) return send(404, { error: "unknown route" });
6156
6195
  if (this.gitDisabledDepth > 0) return send(403, { error: "git_disabled_for_turn", text: "Git tools are unavailable during this turn." });
6196
+ const { mode, cause, channelAlsoReadonly } = this.toolModeSource();
6197
+ if (mode !== "full") return send(403, gitReadonlyRefusal(cause, this.agentName, channelAlsoReadonly));
6157
6198
  const str = (v) => typeof v === "string" ? v : void 0;
6158
6199
  const pathArg = str(body.path);
6159
6200
  if (req.url === "/git/pr/merge") {
@@ -6813,6 +6854,10 @@ var AcpAdapter = class {
6813
6854
  // --- Local session handoff (verified providers only; see interactiveResumeSpecFor) ---
6814
6855
  // liveSessionId is the ACP session id, which for claude IS the native `--resume` id.
6815
6856
  liveSessionId: () => this.client?.sessionId ?? null,
6857
+ // D15: the client's enforced mode (running turn's override, else the last turn's mode,
6858
+ // else standing), for the broker's git gate. Unconditional and fail-closed: a client
6859
+ // that cannot report its mode reads as readonly.
6860
+ effectiveToolMode: () => this.client?.effectiveToolMode?.() ?? "readonly",
6816
6861
  // Fully release the headless subprocess so an interactive `claude --resume` can own the
6817
6862
  // single-writer transcript. Set the guard FIRST so any in-flight/racing turn short-circuits.
6818
6863
  handoffPause: async () => {
@@ -7164,6 +7209,8 @@ var ClaudeAdapter = class {
7164
7209
  onTurn(cb) {
7165
7210
  turnCbs.push(cb);
7166
7211
  },
7212
+ // D15: same head-of-queue mode canUseTool applies (override ?? standing).
7213
+ effectiveToolMode: () => overrideQueue[0] ?? policy.mode,
7167
7214
  async stop() {
7168
7215
  input.end();
7169
7216
  try {
package/dist/cli.js CHANGED
@@ -88,7 +88,7 @@ import {
88
88
  validateRelayWsUrl,
89
89
  withAgentGitEnv,
90
90
  wsToHttp
91
- } from "./chunk-3SHZYLWH.js";
91
+ } from "./chunk-SAUKTY6P.js";
92
92
  import {
93
93
  clampUntrusted,
94
94
  externalSourceLabel,
@@ -821,6 +821,21 @@ Here is the recent discussion so far ` : `You just joined this Braid channel. He
821
821
  liveSessionId() {
822
822
  return this.session?.liveSessionId?.() ?? null;
823
823
  }
824
+ /** D15 (git gateway): the tool mode in force right now, for the broker's git readonly
825
+ * gate. Narrowest of the adapter's live mode (the running turn's per-turn override,
826
+ * else standing), the operator's standing mode, and the channel's last bound bundle
827
+ * mode, so it can only narrow. `cause` mirrors flowModeAndCause: "channel" when the
828
+ * operator granted full but this turn or channel is narrowed (BL-203: then
829
+ * `braid tools full` is the wrong remedy). `channelAlsoReadonly`: the operator is readonly
830
+ * AND the channel's bound bundle is readonly, so the refusal names both remedies. (A
831
+ * Slack-origin turn under a readonly operator enqueues no override, so it is not seen
832
+ * here; the operator remedy is still shown.) */
833
+ currentToolMode() {
834
+ const mode = narrowestMode(this.session?.effectiveToolMode?.(), this.toolMode, this.lastBundleMode);
835
+ const cause = mode === "readonly" && this.toolMode !== "readonly" ? "channel" : "operator";
836
+ const channelAlsoReadonly = this.toolMode === "readonly" && this.lastBundleMode === "readonly";
837
+ return { mode, cause, channelAlsoReadonly };
838
+ }
824
839
  /** True while a dispatched turn has not yet settled (its onTurn hasn't fired).
825
840
  * The take-control banner uses this to warn that taking over interrupts work
826
841
  * (which then re-runs via the hand-back catch-up). */
@@ -2613,6 +2628,17 @@ function oneLine(s, max = 300) {
2613
2628
  function errText(e) {
2614
2629
  return oneLine(e instanceof Error ? e.message : String(e));
2615
2630
  }
2631
+ var GH_OWNER_RE = /^[A-Za-z0-9-]{1,100}$/;
2632
+ var GH_REPO_RE = /^(?!\.\.?$)[A-Za-z0-9._-]{1,100}$/;
2633
+ function parseGitHubOrigin(url) {
2634
+ const s = url.trim();
2635
+ const m = /^https:\/\/(?:[^@/\s]+@)?github\.com\/(.+)$/i.exec(s) ?? /^ssh:\/\/(?:[^@/\s]+@)?github\.com(?::22)?\/(.+)$/i.exec(s) ?? /^(?:[^@/\s:]+@)?github\.com:(?!\/)(.+)$/i.exec(s);
2636
+ if (!m) return null;
2637
+ const parts = m[1].replace(/\/$/, "").replace(/\.git$/i, "").split("/");
2638
+ if (parts.length !== 2) return null;
2639
+ const [owner, name] = parts;
2640
+ return GH_OWNER_RE.test(owner) && GH_REPO_RE.test(name) ? { owner, name } : null;
2641
+ }
2616
2642
  function shellQuote(p) {
2617
2643
  return `'${p.replace(/'/g, `'\\''`)}'`;
2618
2644
  }
@@ -2625,6 +2651,9 @@ function safeSegment(s) {
2625
2651
  function logSafe(s) {
2626
2652
  return s.replace(/[^A-Za-z0-9._\/-]/g, "?").slice(0, 200) || "-";
2627
2653
  }
2654
+ function repoKey(g) {
2655
+ return `${g.repoOwner}/${g.repoName}`.toLowerCase();
2656
+ }
2628
2657
  function isAutonomous(g) {
2629
2658
  return g.mode === "autonomous";
2630
2659
  }
@@ -2677,7 +2706,7 @@ var GitGateway = class {
2677
2706
  async statusInner(channelId, args) {
2678
2707
  const gate = this.gateChecks(channelId);
2679
2708
  if (gate) return gate;
2680
- const grant = await this.singleGrant();
2709
+ const grant = await this.resolveGrant(channelId, args.path, true);
2681
2710
  if (!grant.ok) return grant;
2682
2711
  const g = grant.grant;
2683
2712
  const wt = this.worktree(channelId, args.path);
@@ -2717,12 +2746,12 @@ var GitGateway = class {
2717
2746
  `Worktree ${wt.path}: branch ${branch ?? "unknown"}, HEAD ${head ?? "none"}.`,
2718
2747
  tracking
2719
2748
  ];
2720
- return { ok: true, text: lines.join("\n"), data: { repo, mode, branch, head, ahead, behind } };
2749
+ return { ok: true, text: lines.join("\n"), data: { repo, mode, source: g.source, branch, head, ahead, behind } };
2721
2750
  }
2722
2751
  async fetchInner(channelId, args) {
2723
2752
  const gate = this.gateChecks(channelId);
2724
2753
  if (gate) return gate;
2725
- const grant = await this.singleGrant();
2754
+ const grant = await this.resolveGrant(channelId, args.path, true);
2726
2755
  if (!grant.ok) return grant;
2727
2756
  const g = grant.grant;
2728
2757
  const mirror = this.mirrorPath(g);
@@ -2767,7 +2796,7 @@ ${shown}${more}`,
2767
2796
  async pushInner(channelId, branch, args, out) {
2768
2797
  const gate = this.gateChecks(channelId);
2769
2798
  if (gate) return gate;
2770
- const grant = await this.singleGrant();
2799
+ const grant = await this.resolveGrant(channelId, args.path, true);
2771
2800
  if (!grant.ok) return grant;
2772
2801
  const listed = grant.grant;
2773
2802
  const repo = `${listed.repoOwner}/${listed.repoName}`;
@@ -2840,7 +2869,7 @@ Compare: https://github.com/${repo}/compare/${encodeURIComponent(branch)}`,
2840
2869
  async openPrInner(channelId, args) {
2841
2870
  const gate = this.gateChecks(channelId);
2842
2871
  if (gate) return gate;
2843
- const grant = await this.singleGrant();
2872
+ const grant = await this.resolveGrant(channelId, args.path, false);
2844
2873
  if (!grant.ok) return grant;
2845
2874
  const branch = String(args.branch ?? "");
2846
2875
  const badHead = await this.checkBranch(branch);
@@ -2876,7 +2905,7 @@ Compare: https://github.com/${repo}/compare/${encodeURIComponent(branch)}`,
2876
2905
  async mergePrInner(channelId, args) {
2877
2906
  const gate = this.gateChecks(channelId);
2878
2907
  if (gate) return gate;
2879
- const grant = await this.singleGrant();
2908
+ const grant = await this.resolveGrant(channelId, void 0, false);
2880
2909
  if (!grant.ok) return grant;
2881
2910
  const num = Number(args.number);
2882
2911
  if (!Number.isInteger(num) || num <= 0) return fail(400, "invalid_number", "Pass the pull request number as a positive integer.");
@@ -2963,17 +2992,70 @@ Compare: https://github.com/${repo}/compare/${encodeURIComponent(branch)}`,
2963
2992
  if (this.disabledDepth.has(channelId)) return fail(403, "git_disabled_for_turn", "Git tools are disabled for this turn. Describe the change in your reply instead, and a later turn can push it.");
2964
2993
  return null;
2965
2994
  }
2966
- /** D7: one grant per agent for now; the repo is never chosen by the model. */
2967
- async singleGrant() {
2995
+ /** D11 + R15: exactly one grant (server or PAT) is used as is, whatever the worktree's
2996
+ * origin (a fork origin keeps working, as in 0.98.0). When every grant is for the same
2997
+ * repo (case-insensitive owner/name, e.g. a server grant plus a local PAT), the repo is
2998
+ * unambiguous: no origin lookup, and grantForRepo picks the server grant over the PAT.
2999
+ * With grants for two or more distinct repos, "the repo" is the
3000
+ * worktree's GitHub origin and its grant is the server grant when one exists, else the
3001
+ * local PAT (resolver.grantForRepo); an origin matching no grant is no_grant_for_repo and
3002
+ * no usable origin is no_grant_for_worktree. The grant is still the only source of the
3003
+ * push/fetch target (D8.1): the origin only selects among grants the owner already made,
3004
+ * never names a destination. Ops that do not need a worktree (open/merge PR without a
3005
+ * path) treat an unusable cwd as "no origin". */
3006
+ async resolveGrant(channelId, path2, needWorktree) {
2968
3007
  let grants;
2969
3008
  try {
2970
3009
  grants = await this.deps.resolver.listGrants();
2971
3010
  } catch (e) {
2972
3011
  return fail(502, "grants_unavailable", `Could not load this agent's git grants (${errText(e)}). Try again in a minute.`);
2973
3012
  }
2974
- if (grants.length === 0) return fail(404, "no_grant", `No git grant for this agent. Your owner can add one under Agents > ${this.deps.agentName} > Git access.`);
2975
- if (grants.length > 1) return fail(409, "multiple_grants", `This agent has ${grants.length} git grants, and the gateway supports exactly one today. Ask the owner to keep one repository under Agents > ${this.deps.agentName} > Git access.`);
2976
- return { ok: true, grant: grants[0] };
3013
+ const where = `Agents > ${this.deps.agentName} > Git access`;
3014
+ if (grants.length === 0) return fail(404, "no_grant", `No git grant for this agent. Your owner can add one under ${where}.`);
3015
+ if (grants.length === 1) return { ok: true, grant: grants[0] };
3016
+ if (new Set(grants.map(repoKey)).size === 1) {
3017
+ const only = grants[0];
3018
+ let g2;
3019
+ try {
3020
+ g2 = await this.deps.resolver.grantForRepo(only.repoOwner, only.repoName);
3021
+ } catch (e) {
3022
+ return fail(502, "grants_unavailable", `Could not load this agent's git grants (${errText(e)}). Try again in a minute.`);
3023
+ }
3024
+ return { ok: true, grant: g2 ?? only };
3025
+ }
3026
+ const wt = this.worktree(channelId, path2);
3027
+ if (!wt.ok && (needWorktree || path2 !== void 0)) return wt;
3028
+ const origin = wt.ok ? await this.worktreeOrigin(wt) : null;
3029
+ if (origin && !origin.ok) return origin;
3030
+ const repo = origin?.repo ?? null;
3031
+ if (!repo) {
3032
+ const example = `${grants[0].repoOwner}/${grants[0].repoName}`;
3033
+ return fail(404, "no_grant_for_worktree", `This worktree has no GitHub origin remote and the agent has ${grants.length} git grants (${this.grantList(grants)}). Add the granted repository as origin (git remote add origin https://github.com/${example}.git, using the repository you are working on) so the gateway knows which grant applies.`);
3034
+ }
3035
+ let g;
3036
+ try {
3037
+ g = await this.deps.resolver.grantForRepo(repo.owner, repo.name);
3038
+ } catch (e) {
3039
+ return fail(502, "grants_unavailable", `Could not load this agent's git grants (${errText(e)}). Try again in a minute.`);
3040
+ }
3041
+ if (!g) return fail(404, "no_grant_for_repo", `This worktree's origin is ${repo.owner}/${repo.name}, and the agent has no git grant for that repository (its grants: ${this.grantList(grants)}). Your owner can add ${repo.owner}/${repo.name} under ${where}.`);
3042
+ return { ok: true, grant: g };
3043
+ }
3044
+ grantList(grants) {
3045
+ const byKey = /* @__PURE__ */ new Map();
3046
+ for (const x of grants) if (!byKey.has(repoKey(x))) byKey.set(repoKey(x), `${x.repoOwner}/${x.repoName}`);
3047
+ const names = [...byKey.values()];
3048
+ return names.slice(0, 10).join(", ") + (names.length > 10 ? `, and ${names.length - 10} more` : "");
3049
+ }
3050
+ /** R15: remote.origin.url of the validated worktree, read with the hardened runner while
3051
+ * the worktree identity is held; null repo = no usable (GitHub) origin. */
3052
+ async worktreeOrigin(wt) {
3053
+ const changed = fail(400, "invalid_path", "The worktree changed while its origin remote was being read (its .git was replaced or gained alternates or a config include). Make sure nothing else is modifying the repository, then try again.");
3054
+ const id = this.identity(wt);
3055
+ if (!id) return changed;
3056
+ const r = await this.git(["config", "--get", "remote.origin.url"], { gitDir: wt.gitDir, cwd: wt.path });
3057
+ if (!this.sameIdentity(wt, id)) return changed;
3058
+ return { ok: true, repo: r.code === 0 ? parseGitHubOrigin(r.stdout) : null };
2977
3059
  }
2978
3060
  /** Credential plus the effective policy. When the listed grant is LOOSER than the
2979
3061
  * policy the cached mint carries (the owner loosened the grant after the mint), the
@@ -3323,11 +3405,13 @@ var GrantResolver = class {
3323
3405
  }
3324
3406
  return out;
3325
3407
  }
3408
+ /** D11: a server (app) grant for the repo wins; otherwise the local PAT grant.
3409
+ * GitHub owner and repo names are case-insensitive. */
3326
3410
  async grantForRepo(owner, name) {
3327
3411
  const o = owner.toLowerCase();
3328
3412
  const n = name.toLowerCase();
3329
- const all = await this.listGrants();
3330
- return all.find((g) => g.repoOwner.toLowerCase() === o && g.repoName.toLowerCase() === n) ?? null;
3413
+ const matches = (await this.listGrants()).filter((g) => g.repoOwner.toLowerCase() === o && g.repoName.toLowerCase() === n);
3414
+ return matches.find((g) => g.source === "app") ?? matches.find((g) => g.source === "pat") ?? null;
3331
3415
  }
3332
3416
  async credentialFor(grant) {
3333
3417
  if (grant.source === "pat") {
@@ -3612,6 +3696,7 @@ async function startBridge(cfg, relay, deps) {
3612
3696
  broker.setGitEnabled(!active);
3613
3697
  gitGateway.setChannelGitEnabled(channelId, !active);
3614
3698
  };
3699
+ broker.setToolModeSource(() => session.currentToolMode(), cfg.agentName);
3615
3700
  const brokerInfo = await broker.start();
3616
3701
  const allowedReactions = await relay.fetchAllowedReactions?.().catch(() => []) ?? [];
3617
3702
  const mcpServers = [{
@@ -4,7 +4,7 @@ import {
4
4
  boundedJsonFetch,
5
5
  resetHttpMetricsForTest,
6
6
  snapshotHttpMetrics
7
- } from "./chunk-3SHZYLWH.js";
7
+ } from "./chunk-SAUKTY6P.js";
8
8
  import "./chunk-HQNAAXUM.js";
9
9
  export {
10
10
  assertHttpEndpoint,
@@ -971,7 +971,7 @@ async function main() {
971
971
  server.registerTool(
972
972
  "braid_git_status",
973
973
  {
974
- description: "Show the GitHub repository this agent may act on through Braid (granted by its owner), the autonomy mode, the current branch and HEAD, and how far it is from the remote. Read-only. Use before braid_git_push.",
974
+ description: "Show the GitHub repository this agent may act on through Braid (granted by its owner), the autonomy mode, the current branch and HEAD, and how far it is from the remote. Read-only. Use before braid_git_push. All Braid git tools (this one included) need full tool mode: in read-only mode every one is refused, so do not retry; tell the operator instead.",
975
975
  inputSchema: { path: gitPath }
976
976
  },
977
977
  async (args) => ({ content: [{ type: "text", text: await tools.braidGitStatus(args) }] })
@@ -979,7 +979,7 @@ async function main() {
979
979
  server.registerTool(
980
980
  "braid_git_fetch",
981
981
  {
982
- description: "Fetch the granted repository's branches into the current worktree under refs/remotes/braid/* (for example braid/main). Braid runs git outside the sandbox with a credential you never see.",
982
+ description: "Fetch the granted repository's branches into the current worktree under refs/remotes/braid/* (for example braid/main). Braid runs git outside the sandbox with a credential you never see. Needs full tool mode; in read-only mode it is refused, so do not retry.",
983
983
  inputSchema: { path: gitPath }
984
984
  },
985
985
  async (args) => ({ content: [{ type: "text", text: await tools.braidGitFetch(args) }] })
@@ -987,7 +987,7 @@ async function main() {
987
987
  server.registerTool(
988
988
  "braid_git_push",
989
989
  {
990
- description: "Push a local commit (default HEAD of the worktree) to a branch of the granted repository. Braid runs the push outside the sandbox with a credential you never see and enforces the owner's rules: fast-forward only, no deletes or tags; in pr-only mode only branches under braid/<agent>/ and never the default branch; .github/workflows changes only if the owner allowed them. On refusal the text tells you what to ask the owner for.",
990
+ description: "Push a local commit (default HEAD of the worktree) to a branch of the granted repository. Braid runs the push outside the sandbox with a credential you never see and enforces the owner's rules: fast-forward only, no deletes or tags; in pr-only mode only branches under braid/<agent>/ and never the default branch; .github/workflows changes only if the owner allowed them. On refusal the text tells you what to ask the owner for. Needs full tool mode; in read-only mode it is refused, so do not retry.",
991
991
  inputSchema: {
992
992
  path: gitPath,
993
993
  branch: z.string(),
@@ -999,7 +999,7 @@ async function main() {
999
999
  server.registerTool(
1000
1000
  "braid_open_pr",
1001
1001
  {
1002
- description: "Open a pull request from a branch you pushed to the granted repository (draft in pr-only mode). Returns the PR number and URL.",
1002
+ description: "Open a pull request from a branch you pushed to the granted repository (draft in pr-only mode). Returns the PR number and URL. Needs full tool mode; in read-only mode it is refused, so do not retry.",
1003
1003
  inputSchema: {
1004
1004
  path: gitPath,
1005
1005
  branch: z.string(),
@@ -1013,7 +1013,7 @@ async function main() {
1013
1013
  server.registerTool(
1014
1014
  "braid_merge_pr",
1015
1015
  {
1016
- description: "Merge a pull request in the granted repository. Allowed only when the owner set autonomous mode; in pr-only mode a human merges. method is squash (default), merge, or rebase.",
1016
+ description: "Merge a pull request in the granted repository. Allowed only when the owner set autonomous mode; in pr-only mode a human merges. method is squash (default), merge, or rebase. Needs full tool mode; in read-only mode it is refused, so do not retry.",
1017
1017
  inputSchema: {
1018
1018
  number: z.number().int(),
1019
1019
  method: z.enum(["merge", "squash", "rebase"]).optional()
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@snowyroad/braid",
3
- "version": "0.98.0",
3
+ "version": "0.98.2",
4
4
  "description": "Braid: connect your own coding agent (Claude Code, Codex, Gemini, Grok) to a Braid channel and collaborate with other agents and humans.",
5
5
  "license": "SEE LICENSE IN LICENSE.md",
6
6
  "author": "SnowyRoad",
@@ -1,12 +1,12 @@
1
1
  {
2
2
  "name": "@snowyroad/braid",
3
- "version": "0.98.0",
3
+ "version": "0.98.2",
4
4
  "lockfileVersion": 3,
5
5
  "requires": true,
6
6
  "packages": {
7
7
  "": {
8
8
  "name": "@snowyroad/braid",
9
- "version": "0.98.0",
9
+ "version": "0.98.2",
10
10
  "license": "SEE LICENSE IN LICENSE.md",
11
11
  "dependencies": {
12
12
  "@agentclientprotocol/sdk": "0.25.1",
@@ -247,9 +247,9 @@
247
247
  }
248
248
  },
249
249
  "node_modules/@babel/runtime": {
250
- "version": "7.29.7",
251
- "resolved": "https://registry.npmjs.org/@babel/runtime/-/runtime-7.29.7.tgz",
252
- "integrity": "sha512-Nq8OhGWiZIZGV6hLHoyAKLLcJihP/xFeBMGJoUrxTX2psI8dCifzLhZISFb+VWS3wFMRDmCGw5R+dOySCqPLhw==",
250
+ "version": "7.29.10",
251
+ "resolved": "https://registry.npmjs.org/@babel/runtime/-/runtime-7.29.10.tgz",
252
+ "integrity": "sha512-NpugTzbKgGrNe45Ui32cN8vCFFMxVtP/9rtfwv0nP5FRDAjvYBxJcLVpYA9mr1jxP6cnIT7x9LUzuDTbWYYNRA==",
253
253
  "license": "MIT",
254
254
  "engines": {
255
255
  "node": ">=6.9.0"
@@ -815,9 +815,9 @@
815
815
  "license": "MIT"
816
816
  },
817
817
  "node_modules/@rollup/rollup-android-arm-eabi": {
818
- "version": "4.64.0",
819
- "resolved": "https://registry.npmjs.org/@rollup/rollup-android-arm-eabi/-/rollup-android-arm-eabi-4.64.0.tgz",
820
- "integrity": "sha512-FLLpX941CD/7aBvX3GqLGBM9OvY5PGXTryPJkG5r5/OuBpZpV5k45Uo3RxAvqd35tsyc3hH1bhtz921IKzoIzg==",
818
+ "version": "4.64.1",
819
+ "resolved": "https://registry.npmjs.org/@rollup/rollup-android-arm-eabi/-/rollup-android-arm-eabi-4.64.1.tgz",
820
+ "integrity": "sha512-QRU7UpoS9hd8Ij5I6fCVBxZ0UpdfAbZ5y7BWG5STFGMoM9jGzUP464yYAa3CzZxvG+jBwq1kI8L07xx0ReAdGA==",
821
821
  "cpu": [
822
822
  "arm"
823
823
  ],
@@ -829,9 +829,9 @@
829
829
  ]
830
830
  },
831
831
  "node_modules/@rollup/rollup-android-arm64": {
832
- "version": "4.64.0",
833
- "resolved": "https://registry.npmjs.org/@rollup/rollup-android-arm64/-/rollup-android-arm64-4.64.0.tgz",
834
- "integrity": "sha512-iI32XM/jnDYJsvx5ai/za/7gWO9XoSeFFtU06/ZCaRgyilfJOjaopD3nOpk2WrTCGOyeDt4hleUiGOAnd5tHNg==",
832
+ "version": "4.64.1",
833
+ "resolved": "https://registry.npmjs.org/@rollup/rollup-android-arm64/-/rollup-android-arm64-4.64.1.tgz",
834
+ "integrity": "sha512-ttQF6Rp4MrNy9/2AOPmHmMXbNE8kIlNPYoGC3ksid9tonleMQALfrhTFJiQxobBvXYKG5Wcc8VGcHWTHR0ik8w==",
835
835
  "cpu": [
836
836
  "arm64"
837
837
  ],
@@ -843,9 +843,9 @@
843
843
  ]
844
844
  },
845
845
  "node_modules/@rollup/rollup-darwin-arm64": {
846
- "version": "4.64.0",
847
- "resolved": "https://registry.npmjs.org/@rollup/rollup-darwin-arm64/-/rollup-darwin-arm64-4.64.0.tgz",
848
- "integrity": "sha512-dRBZlbt2sEtF8Mn4MODThze9fIPdDoOhVSlXMAKy5dQbOYK9pOOoPY4Fat3OTtr0+8zbJo5TTZwlsfxY/kDNJg==",
846
+ "version": "4.64.1",
847
+ "resolved": "https://registry.npmjs.org/@rollup/rollup-darwin-arm64/-/rollup-darwin-arm64-4.64.1.tgz",
848
+ "integrity": "sha512-MvzZ+qbBi5jrafURHsASUF1qW/58tOJFt/gFVJo2znQWrKX4CSf/Lt/qGONtoA4yHsNL5QzgdXMuITZxAs62Vg==",
849
849
  "cpu": [
850
850
  "arm64"
851
851
  ],
@@ -857,9 +857,9 @@
857
857
  ]
858
858
  },
859
859
  "node_modules/@rollup/rollup-darwin-x64": {
860
- "version": "4.64.0",
861
- "resolved": "https://registry.npmjs.org/@rollup/rollup-darwin-x64/-/rollup-darwin-x64-4.64.0.tgz",
862
- "integrity": "sha512-Y3whrJOMucfkhgNkvcM93M6j8C53iEAMmPMYD99C6G1kUy4ELigLWk9ar2/4aCBSRgsql0zdlOemLgW2m5GZgQ==",
860
+ "version": "4.64.1",
861
+ "resolved": "https://registry.npmjs.org/@rollup/rollup-darwin-x64/-/rollup-darwin-x64-4.64.1.tgz",
862
+ "integrity": "sha512-9uj1VBuiPK5ij/+g0mCK17X+V/4SbErvRQMXIQjZAtbl4VcUhv63RhPZsFSWHrCRkTd3FKDtaVTrtT0+8bIhhQ==",
863
863
  "cpu": [
864
864
  "x64"
865
865
  ],
@@ -871,9 +871,9 @@
871
871
  ]
872
872
  },
873
873
  "node_modules/@rollup/rollup-freebsd-arm64": {
874
- "version": "4.64.0",
875
- "resolved": "https://registry.npmjs.org/@rollup/rollup-freebsd-arm64/-/rollup-freebsd-arm64-4.64.0.tgz",
876
- "integrity": "sha512-S6S1GEzPjFF6IONYJX3AKt/799+8RgBgCcwRnUo+Ep1IvBxUbw5M51iU0TDdK2NWWVnSvCQ8yi6Em0fGASMOng==",
874
+ "version": "4.64.1",
875
+ "resolved": "https://registry.npmjs.org/@rollup/rollup-freebsd-arm64/-/rollup-freebsd-arm64-4.64.1.tgz",
876
+ "integrity": "sha512-FCoXm836IqcXWhWPRkqlLx3Hjnv9S7c8tg5MFwsgHB3aFCz1JjUy6b1ssrxEjEbqaHpnvRmNjUUHxsXuU85NYA==",
877
877
  "cpu": [
878
878
  "arm64"
879
879
  ],
@@ -885,9 +885,9 @@
885
885
  ]
886
886
  },
887
887
  "node_modules/@rollup/rollup-freebsd-x64": {
888
- "version": "4.64.0",
889
- "resolved": "https://registry.npmjs.org/@rollup/rollup-freebsd-x64/-/rollup-freebsd-x64-4.64.0.tgz",
890
- "integrity": "sha512-Ed1DPoFENkXj4IGzSB12SesV40iP6LxCCrbTIkSGIQBpOOxpBM+0kj62lmaeIHfMWTDoddqTOtqc7s8LYfn+Pw==",
888
+ "version": "4.64.1",
889
+ "resolved": "https://registry.npmjs.org/@rollup/rollup-freebsd-x64/-/rollup-freebsd-x64-4.64.1.tgz",
890
+ "integrity": "sha512-Xa6Oxo86Ilx1hq1vNb69541NOuUyhGEH3Sc0g7eGkfsfRblWh4hAa4Lj2GWwZyfUVYL+Z4xK3TxhwIuZ3fNPLg==",
891
891
  "cpu": [
892
892
  "x64"
893
893
  ],
@@ -899,9 +899,9 @@
899
899
  ]
900
900
  },
901
901
  "node_modules/@rollup/rollup-linux-arm-gnueabihf": {
902
- "version": "4.64.0",
903
- "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm-gnueabihf/-/rollup-linux-arm-gnueabihf-4.64.0.tgz",
904
- "integrity": "sha512-J/6xhutJPtFyIkmHdf4olOdHHKH5kOJNumojdWn+Elv5ICEYTVOa362Vw27TxsK0BLzb1le3EDlO3UbvFK1lnQ==",
902
+ "version": "4.64.1",
903
+ "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm-gnueabihf/-/rollup-linux-arm-gnueabihf-4.64.1.tgz",
904
+ "integrity": "sha512-Nkw7cVMu1yrczpzr42Mh1BZ5Ai5A4Fsz2Je/frbwHmazpQTJzP+qo7pNjdxHrxVj56ivKTJihNoN90OD1hGxBA==",
905
905
  "cpu": [
906
906
  "arm"
907
907
  ],
@@ -916,9 +916,9 @@
916
916
  ]
917
917
  },
918
918
  "node_modules/@rollup/rollup-linux-arm-musleabihf": {
919
- "version": "4.64.0",
920
- "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm-musleabihf/-/rollup-linux-arm-musleabihf-4.64.0.tgz",
921
- "integrity": "sha512-G4L/Nnx59d2LvDoV/P4S5lZ7oVLT6hodOHMacqjiq2LL2gts86KbkEBTYL53+fBt0odhf7XPIbIATGoYiJctxg==",
919
+ "version": "4.64.1",
920
+ "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm-musleabihf/-/rollup-linux-arm-musleabihf-4.64.1.tgz",
921
+ "integrity": "sha512-JONaLM9mZPXbSetxMzYG3496qoJuWvG2ERCTrrVptfw/Fwe4UzrQoEx/mYEeZCRv/Xz0RldOLFeqDfqmH75/Zg==",
922
922
  "cpu": [
923
923
  "arm"
924
924
  ],
@@ -933,9 +933,9 @@
933
933
  ]
934
934
  },
935
935
  "node_modules/@rollup/rollup-linux-arm64-gnu": {
936
- "version": "4.64.0",
937
- "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm64-gnu/-/rollup-linux-arm64-gnu-4.64.0.tgz",
938
- "integrity": "sha512-zF16pvJDEUksGYRbfnXne7pdklAyj2XDmJeYKgP93oq0cUyX9Y8O7lUo1R+IY1GagP/YBvCEDCe7eEcAKpw//g==",
936
+ "version": "4.64.1",
937
+ "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm64-gnu/-/rollup-linux-arm64-gnu-4.64.1.tgz",
938
+ "integrity": "sha512-OfimHma+prmdoobHI3tfYud2enQ2LXYaMu+iMUQH7IjJkykJ6qUmAs1M/scdQaEKRWysiKwTctsDa2LXvaO0xw==",
939
939
  "cpu": [
940
940
  "arm64"
941
941
  ],
@@ -950,9 +950,9 @@
950
950
  ]
951
951
  },
952
952
  "node_modules/@rollup/rollup-linux-arm64-musl": {
953
- "version": "4.64.0",
954
- "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm64-musl/-/rollup-linux-arm64-musl-4.64.0.tgz",
955
- "integrity": "sha512-nIggWn8n+w12+R5lsV+PYYoUY8vuObxPAQqJI7WES+9v0qspYuAHoZMfYM0yLxlipasT5BY9ht5W8t5c/rSCkg==",
953
+ "version": "4.64.1",
954
+ "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm64-musl/-/rollup-linux-arm64-musl-4.64.1.tgz",
955
+ "integrity": "sha512-X5fwh2HM8EHbgfFwpf4m2x2pG/AHdQ2aPDPk+JCDwV4DPeM8yxYmKG1vvm123JSc9gBSu8tu9NECA99wHPztsw==",
956
956
  "cpu": [
957
957
  "arm64"
958
958
  ],
@@ -967,9 +967,9 @@
967
967
  ]
968
968
  },
969
969
  "node_modules/@rollup/rollup-linux-loong64-gnu": {
970
- "version": "4.64.0",
971
- "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-loong64-gnu/-/rollup-linux-loong64-gnu-4.64.0.tgz",
972
- "integrity": "sha512-WLOTiHPzszP0dxIMsHpFeDSOSB5I49Mj8K4+yKE3H1X/D0JRG5XZ5jrctJLMjnUc/LUzaKiwq6EHWNJ8pup8PA==",
970
+ "version": "4.64.1",
971
+ "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-loong64-gnu/-/rollup-linux-loong64-gnu-4.64.1.tgz",
972
+ "integrity": "sha512-8dp2TxKdjiX/4f7Da9gF7BR29hygxOQlHxKNa8qxJHoqZ13ytrogFTpMPhtVEFrgFu9MSOabAn006PeoygavjA==",
973
973
  "cpu": [
974
974
  "loong64"
975
975
  ],
@@ -984,9 +984,9 @@
984
984
  ]
985
985
  },
986
986
  "node_modules/@rollup/rollup-linux-loong64-musl": {
987
- "version": "4.64.0",
988
- "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-loong64-musl/-/rollup-linux-loong64-musl-4.64.0.tgz",
989
- "integrity": "sha512-35RK9aRhh7g7Pmeu5gQ01aCvrhXzj9LoBE6xtUcEH1ns+nyTaSzxSpADmBQINu4QiTDGvmQYwo1j5hlg1rRXFw==",
987
+ "version": "4.64.1",
988
+ "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-loong64-musl/-/rollup-linux-loong64-musl-4.64.1.tgz",
989
+ "integrity": "sha512-YuYDpRSZnU9qLf6sqyhiBdMRCw5ImECGLNqRjM2hZrJIEwAckameWkRJ3SUnn0oxSewZIib/4iLwyEXj40QqQQ==",
990
990
  "cpu": [
991
991
  "loong64"
992
992
  ],
@@ -1001,9 +1001,9 @@
1001
1001
  ]
1002
1002
  },
1003
1003
  "node_modules/@rollup/rollup-linux-ppc64-gnu": {
1004
- "version": "4.64.0",
1005
- "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-ppc64-gnu/-/rollup-linux-ppc64-gnu-4.64.0.tgz",
1006
- "integrity": "sha512-RqTfnpoTjuWfPAmqK5p2edt2AMCDJWm6oTn7sKfmyx+6tRga0ip05SJ977o6udTcIiDeF/CJMUfkaN4gtWt6Aw==",
1004
+ "version": "4.64.1",
1005
+ "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-ppc64-gnu/-/rollup-linux-ppc64-gnu-4.64.1.tgz",
1006
+ "integrity": "sha512-gGj3v7YYkysy7IbfclMI4PDtHaa6YX4nU1D5NR1fyvXAGqM4TDk28ZWvrpOkkK92eoQRryAludWz6jNjsm77Qg==",
1007
1007
  "cpu": [
1008
1008
  "ppc64"
1009
1009
  ],
@@ -1018,9 +1018,9 @@
1018
1018
  ]
1019
1019
  },
1020
1020
  "node_modules/@rollup/rollup-linux-ppc64-musl": {
1021
- "version": "4.64.0",
1022
- "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-ppc64-musl/-/rollup-linux-ppc64-musl-4.64.0.tgz",
1023
- "integrity": "sha512-RQjZPigjxFvFZDijG6rjlSXxhRaTf9zLYVpGK+lVcga64oMqP1GbgVqCb46eHTTceSIgp89Ja0y5aPe3GFBYHg==",
1021
+ "version": "4.64.1",
1022
+ "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-ppc64-musl/-/rollup-linux-ppc64-musl-4.64.1.tgz",
1023
+ "integrity": "sha512-DTZVwvS94FUYpP0CjCfz2iT0XTmBfQGc/arx9IdwUbDImpe9h8dWuMT/oPUvcGiwLKMQoNmuFBx3AVajm+FNjA==",
1024
1024
  "cpu": [
1025
1025
  "ppc64"
1026
1026
  ],
@@ -1035,9 +1035,9 @@
1035
1035
  ]
1036
1036
  },
1037
1037
  "node_modules/@rollup/rollup-linux-riscv64-gnu": {
1038
- "version": "4.64.0",
1039
- "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-riscv64-gnu/-/rollup-linux-riscv64-gnu-4.64.0.tgz",
1040
- "integrity": "sha512-tjL58mgQcTRnDRpeky+Sth1MKQeYi2Ct6r3Luq9E5aTSjnM/i/JbozqZkKqp9thM5+oDSZxo+05f9kdQedfTGA==",
1038
+ "version": "4.64.1",
1039
+ "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-riscv64-gnu/-/rollup-linux-riscv64-gnu-4.64.1.tgz",
1040
+ "integrity": "sha512-NWnyiq2moc8iEHGyTjIFadJTy8VCvCU/rUBfor+3l30JOQKAifpmKdxX4ZxRRPSPE/rLhFpLADdzNjS3Ldctdw==",
1041
1041
  "cpu": [
1042
1042
  "riscv64"
1043
1043
  ],
@@ -1052,9 +1052,9 @@
1052
1052
  ]
1053
1053
  },
1054
1054
  "node_modules/@rollup/rollup-linux-riscv64-musl": {
1055
- "version": "4.64.0",
1056
- "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-riscv64-musl/-/rollup-linux-riscv64-musl-4.64.0.tgz",
1057
- "integrity": "sha512-ictoRyVaoZ8C67myHef+8hhCa6IplXJJ/xUCkVCxziV4zxMZh+jvhkhGsPBLqj1S72fnqD0QH5zL4lcaa4X7DQ==",
1055
+ "version": "4.64.1",
1056
+ "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-riscv64-musl/-/rollup-linux-riscv64-musl-4.64.1.tgz",
1057
+ "integrity": "sha512-yIz+7L37g7bVOGLaUQmGqiYADH262krL4dtf5zU6QGldPgOairLEgW1FTs5pP0UFkHq5uf2qxDttOFsVAX6kxg==",
1058
1058
  "cpu": [
1059
1059
  "riscv64"
1060
1060
  ],
@@ -1069,9 +1069,9 @@
1069
1069
  ]
1070
1070
  },
1071
1071
  "node_modules/@rollup/rollup-linux-s390x-gnu": {
1072
- "version": "4.64.0",
1073
- "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-s390x-gnu/-/rollup-linux-s390x-gnu-4.64.0.tgz",
1074
- "integrity": "sha512-8aVvZ2hfr9RLFzBQkQNmYeHLDja8fLeQAmLt757zdKN/B+8L809KlLJKctQjS22wZotptV8G6o7fVPuAs8S1tQ==",
1072
+ "version": "4.64.1",
1073
+ "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-s390x-gnu/-/rollup-linux-s390x-gnu-4.64.1.tgz",
1074
+ "integrity": "sha512-sRK+GWovJZV6ijyV/k1Ft3FL5+4DscF5OYsJolTbhVTTLFxKOPVjS0wxUUHakvL0vRw/cbFxZNeZLfM/EzuQhA==",
1075
1075
  "cpu": [
1076
1076
  "s390x"
1077
1077
  ],
@@ -1086,9 +1086,9 @@
1086
1086
  ]
1087
1087
  },
1088
1088
  "node_modules/@rollup/rollup-linux-x64-gnu": {
1089
- "version": "4.64.0",
1090
- "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-x64-gnu/-/rollup-linux-x64-gnu-4.64.0.tgz",
1091
- "integrity": "sha512-2dEF8GAcDKwshUfydD+GhosppNyBzhVUHkdFF3CXd3FpOkzj/RZzF5aoEtzklujklT5qFVRU2GK/cFeLaTNKVg==",
1089
+ "version": "4.64.1",
1090
+ "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-x64-gnu/-/rollup-linux-x64-gnu-4.64.1.tgz",
1091
+ "integrity": "sha512-T2C0NXqqD063yJdm8UGdcoudBATDODdphEXWS7rEoh0jOITfoEBv7LHfRBYVsy+pI7wwxgScoZpkFiQOf40ryQ==",
1092
1092
  "cpu": [
1093
1093
  "x64"
1094
1094
  ],
@@ -1103,9 +1103,9 @@
1103
1103
  ]
1104
1104
  },
1105
1105
  "node_modules/@rollup/rollup-linux-x64-musl": {
1106
- "version": "4.64.0",
1107
- "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-x64-musl/-/rollup-linux-x64-musl-4.64.0.tgz",
1108
- "integrity": "sha512-3XHTvoo2hKkh0MiOfS7SkhHjMaaWF7P4F3drocZZaho/Z8w7h/jpnuBHm91BOQLfvrKHs1yR+zir4E8RI3XzTQ==",
1106
+ "version": "4.64.1",
1107
+ "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-x64-musl/-/rollup-linux-x64-musl-4.64.1.tgz",
1108
+ "integrity": "sha512-05wl8uRZMkcobB6YZrzskr2SiM0VOdzlFw3bAxOjKKTt3M6o3O0X/hE/8xk15u8oQY17xUCdTKcNMMg45ZAFog==",
1109
1109
  "cpu": [
1110
1110
  "x64"
1111
1111
  ],
@@ -1120,9 +1120,9 @@
1120
1120
  ]
1121
1121
  },
1122
1122
  "node_modules/@rollup/rollup-openbsd-x64": {
1123
- "version": "4.64.0",
1124
- "resolved": "https://registry.npmjs.org/@rollup/rollup-openbsd-x64/-/rollup-openbsd-x64-4.64.0.tgz",
1125
- "integrity": "sha512-HKtkzodL4a3KFWDXDoO61cRynAWTR3LnAE0oGtfG9lcNFpNuVYUFOByxDgNqEvic9rvaQbAj+SFwTEWDptRaIw==",
1123
+ "version": "4.64.1",
1124
+ "resolved": "https://registry.npmjs.org/@rollup/rollup-openbsd-x64/-/rollup-openbsd-x64-4.64.1.tgz",
1125
+ "integrity": "sha512-NoRZK1VclOgn9x3b9vPJ3sTxwvQ/F+Hf93xurRKSFJKiwNZyQZnLxVpqlCejhDvesMLMF8VNN+Y4jHTFddV/Xg==",
1126
1126
  "cpu": [
1127
1127
  "x64"
1128
1128
  ],
@@ -1134,9 +1134,9 @@
1134
1134
  ]
1135
1135
  },
1136
1136
  "node_modules/@rollup/rollup-openharmony-arm64": {
1137
- "version": "4.64.0",
1138
- "resolved": "https://registry.npmjs.org/@rollup/rollup-openharmony-arm64/-/rollup-openharmony-arm64-4.64.0.tgz",
1139
- "integrity": "sha512-JBsxqiY16uyyCujtoC3s7zL+SrYyNElptD7K4V+KUoJ2V8/XG3hPWpheK+SuPwNh1cikJvIZmIdsrYXvD6PLJw==",
1137
+ "version": "4.64.1",
1138
+ "resolved": "https://registry.npmjs.org/@rollup/rollup-openharmony-arm64/-/rollup-openharmony-arm64-4.64.1.tgz",
1139
+ "integrity": "sha512-SDkX4OkZBePUPf0/XsXVJLwS+O61CmkDKuIyk5CeWddK3vkE8AZjmWK+p1ILRez4wnbS5rTK+U9YmcbRyx2dHw==",
1140
1140
  "cpu": [
1141
1141
  "arm64"
1142
1142
  ],
@@ -1148,9 +1148,9 @@
1148
1148
  ]
1149
1149
  },
1150
1150
  "node_modules/@rollup/rollup-win32-arm64-msvc": {
1151
- "version": "4.64.0",
1152
- "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-arm64-msvc/-/rollup-win32-arm64-msvc-4.64.0.tgz",
1153
- "integrity": "sha512-S5Qrijh37qhnUYQ0ay8WN3LuWeKjow7wTUyCOPMZtnXiBXYXdsZETI6ZLfYnQAKovltckPLBFdNeD61P2rJc7g==",
1151
+ "version": "4.64.1",
1152
+ "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-arm64-msvc/-/rollup-win32-arm64-msvc-4.64.1.tgz",
1153
+ "integrity": "sha512-JQ7el/Plr3juYFxIVu9YXDPNl57XR2L8WIc87JX9wj0L3goV8fXQPQXb3DaHVXq61X/WCGWsTCQsQHo6/Mz5UQ==",
1154
1154
  "cpu": [
1155
1155
  "arm64"
1156
1156
  ],
@@ -1162,9 +1162,9 @@
1162
1162
  ]
1163
1163
  },
1164
1164
  "node_modules/@rollup/rollup-win32-ia32-msvc": {
1165
- "version": "4.64.0",
1166
- "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-ia32-msvc/-/rollup-win32-ia32-msvc-4.64.0.tgz",
1167
- "integrity": "sha512-zbZ6iMmLFEsCtTdc2/y1F/cDFVNNCPF7Ae8PCT/wdPE//hGwYp6r+MyCLMFX+kOeIe09Pz6ASfnnfpSTN1FJQQ==",
1165
+ "version": "4.64.1",
1166
+ "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-ia32-msvc/-/rollup-win32-ia32-msvc-4.64.1.tgz",
1167
+ "integrity": "sha512-oZSlQ2H3ZDOz3ce1jEyuOZKuD0tPY/D2cKGMcMl0jhHQauBvkHHKAGR1OeRiMluvu3itzLRU2xCTUZptLayObA==",
1168
1168
  "cpu": [
1169
1169
  "ia32"
1170
1170
  ],
@@ -1176,9 +1176,9 @@
1176
1176
  ]
1177
1177
  },
1178
1178
  "node_modules/@rollup/rollup-win32-x64-gnu": {
1179
- "version": "4.64.0",
1180
- "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-x64-gnu/-/rollup-win32-x64-gnu-4.64.0.tgz",
1181
- "integrity": "sha512-L6Hw69oNpuYaOr1zCG30v0/DqKYCSRwodPGwIcVZ/6f8SOzq9rxtL/xNVI5MO4wjli+Ko0ErK9uHJL3mNPt8wQ==",
1179
+ "version": "4.64.1",
1180
+ "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-x64-gnu/-/rollup-win32-x64-gnu-4.64.1.tgz",
1181
+ "integrity": "sha512-Do2m3jUeVAvUDpee/yVZYRqhO8Ecx4x5sX3EVGalqLx+OxecLDGx3sIwPEm1Nq+MFK2FV3pgdpwWP4624b85Og==",
1182
1182
  "cpu": [
1183
1183
  "x64"
1184
1184
  ],
@@ -1190,9 +1190,9 @@
1190
1190
  ]
1191
1191
  },
1192
1192
  "node_modules/@rollup/rollup-win32-x64-msvc": {
1193
- "version": "4.64.0",
1194
- "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-x64-msvc/-/rollup-win32-x64-msvc-4.64.0.tgz",
1195
- "integrity": "sha512-nl+CTWIgOGszQmUz/kanfgrfFZ4qiwxKIfT/ryl3N3Ewk5tqizmYtNXiqb7Bu/fDtNgu1kyxdFiAUJNur3iysg==",
1193
+ "version": "4.64.1",
1194
+ "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-x64-msvc/-/rollup-win32-x64-msvc-4.64.1.tgz",
1195
+ "integrity": "sha512-KpxCwRn1Qh3tmBHAqIAF4HtUCVKqZd0w57TsItWblx3QVeJLtXaSgeBFAj1WAvBSpBo+Mh9iZCjj6YW/HaBVMw==",
1196
1196
  "cpu": [
1197
1197
  "x64"
1198
1198
  ],
@@ -3174,9 +3174,9 @@
3174
3174
  }
3175
3175
  },
3176
3176
  "node_modules/rollup": {
3177
- "version": "4.64.0",
3178
- "resolved": "https://registry.npmjs.org/rollup/-/rollup-4.64.0.tgz",
3179
- "integrity": "sha512-gjA/kFeDfffII8COoPsvLPvE16hWDTEc1+0QKQNKUkuV8iJjqsC4xXs8/FzuL0v9EV39kuxTbAgcFoTRyy2TGQ==",
3177
+ "version": "4.64.1",
3178
+ "resolved": "https://registry.npmjs.org/rollup/-/rollup-4.64.1.tgz",
3179
+ "integrity": "sha512-7s4V+3J8ux75WNj9qwSJnrWmlCmZ2YHr2fojtHy5RiIMvhJv6DGe7HKKz7L6G1sq1Eg1fLC8SjYtAtDis1F4CQ==",
3180
3180
  "dev": true,
3181
3181
  "license": "MIT",
3182
3182
  "dependencies": {
@@ -3191,31 +3191,31 @@
3191
3191
  },
3192
3192
  "optionalDependencies": {
3193
3193
  "@napi-rs/lzma-linux-x64-gnu": "1.5.1",
3194
- "@rollup/rollup-android-arm-eabi": "4.64.0",
3195
- "@rollup/rollup-android-arm64": "4.64.0",
3196
- "@rollup/rollup-darwin-arm64": "4.64.0",
3197
- "@rollup/rollup-darwin-x64": "4.64.0",
3198
- "@rollup/rollup-freebsd-arm64": "4.64.0",
3199
- "@rollup/rollup-freebsd-x64": "4.64.0",
3200
- "@rollup/rollup-linux-arm-gnueabihf": "4.64.0",
3201
- "@rollup/rollup-linux-arm-musleabihf": "4.64.0",
3202
- "@rollup/rollup-linux-arm64-gnu": "4.64.0",
3203
- "@rollup/rollup-linux-arm64-musl": "4.64.0",
3204
- "@rollup/rollup-linux-loong64-gnu": "4.64.0",
3205
- "@rollup/rollup-linux-loong64-musl": "4.64.0",
3206
- "@rollup/rollup-linux-ppc64-gnu": "4.64.0",
3207
- "@rollup/rollup-linux-ppc64-musl": "4.64.0",
3208
- "@rollup/rollup-linux-riscv64-gnu": "4.64.0",
3209
- "@rollup/rollup-linux-riscv64-musl": "4.64.0",
3210
- "@rollup/rollup-linux-s390x-gnu": "4.64.0",
3211
- "@rollup/rollup-linux-x64-gnu": "4.64.0",
3212
- "@rollup/rollup-linux-x64-musl": "4.64.0",
3213
- "@rollup/rollup-openbsd-x64": "4.64.0",
3214
- "@rollup/rollup-openharmony-arm64": "4.64.0",
3215
- "@rollup/rollup-win32-arm64-msvc": "4.64.0",
3216
- "@rollup/rollup-win32-ia32-msvc": "4.64.0",
3217
- "@rollup/rollup-win32-x64-gnu": "4.64.0",
3218
- "@rollup/rollup-win32-x64-msvc": "4.64.0",
3194
+ "@rollup/rollup-android-arm-eabi": "4.64.1",
3195
+ "@rollup/rollup-android-arm64": "4.64.1",
3196
+ "@rollup/rollup-darwin-arm64": "4.64.1",
3197
+ "@rollup/rollup-darwin-x64": "4.64.1",
3198
+ "@rollup/rollup-freebsd-arm64": "4.64.1",
3199
+ "@rollup/rollup-freebsd-x64": "4.64.1",
3200
+ "@rollup/rollup-linux-arm-gnueabihf": "4.64.1",
3201
+ "@rollup/rollup-linux-arm-musleabihf": "4.64.1",
3202
+ "@rollup/rollup-linux-arm64-gnu": "4.64.1",
3203
+ "@rollup/rollup-linux-arm64-musl": "4.64.1",
3204
+ "@rollup/rollup-linux-loong64-gnu": "4.64.1",
3205
+ "@rollup/rollup-linux-loong64-musl": "4.64.1",
3206
+ "@rollup/rollup-linux-ppc64-gnu": "4.64.1",
3207
+ "@rollup/rollup-linux-ppc64-musl": "4.64.1",
3208
+ "@rollup/rollup-linux-riscv64-gnu": "4.64.1",
3209
+ "@rollup/rollup-linux-riscv64-musl": "4.64.1",
3210
+ "@rollup/rollup-linux-s390x-gnu": "4.64.1",
3211
+ "@rollup/rollup-linux-x64-gnu": "4.64.1",
3212
+ "@rollup/rollup-linux-x64-musl": "4.64.1",
3213
+ "@rollup/rollup-openbsd-x64": "4.64.1",
3214
+ "@rollup/rollup-openharmony-arm64": "4.64.1",
3215
+ "@rollup/rollup-win32-arm64-msvc": "4.64.1",
3216
+ "@rollup/rollup-win32-ia32-msvc": "4.64.1",
3217
+ "@rollup/rollup-win32-x64-gnu": "4.64.1",
3218
+ "@rollup/rollup-win32-x64-msvc": "4.64.1",
3219
3219
  "fsevents": "~2.3.2"
3220
3220
  }
3221
3221
  },