@couralabs/claudin 0.1.2 → 0.1.4
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/claudin.js +1395 -145
- package/package.json +2 -2
package/claudin.js
CHANGED
|
@@ -6161,7 +6161,6 @@ var agentRequestSchemas = [
|
|
|
6161
6161
|
answers: record(string2(), string2())
|
|
6162
6162
|
}),
|
|
6163
6163
|
object({ type: literal("agent.model.set.requested"), agentSessionId, model: string2() }),
|
|
6164
|
-
object({ type: literal("agent.model.cycle.requested"), agentSessionId }),
|
|
6165
6164
|
object({
|
|
6166
6165
|
type: literal("agent.permission_mode.set.requested"),
|
|
6167
6166
|
agentSessionId,
|
|
@@ -6175,6 +6174,17 @@ var agentRequestSchemas = [
|
|
|
6175
6174
|
object({ type: literal("agent.commands.requested"), agentSessionId }),
|
|
6176
6175
|
object({ type: literal("agent.models.requested"), agentSessionId }),
|
|
6177
6176
|
object({ type: literal("agent.mcp.status.requested"), agentSessionId }),
|
|
6177
|
+
object({
|
|
6178
|
+
type: literal("agent.mcp.login.requested"),
|
|
6179
|
+
agentSessionId,
|
|
6180
|
+
serverName: string2()
|
|
6181
|
+
}),
|
|
6182
|
+
object({
|
|
6183
|
+
type: literal("agent.mcp.callback.submitted"),
|
|
6184
|
+
agentSessionId,
|
|
6185
|
+
serverName: string2(),
|
|
6186
|
+
callbackUrl: string2()
|
|
6187
|
+
}),
|
|
6178
6188
|
object({ type: literal("agent.usage.requested"), agentSessionId }),
|
|
6179
6189
|
object({ type: literal("agent.rate_limit.requested"), agentSessionId }),
|
|
6180
6190
|
object({ type: literal("agent.rate_limit.cached.requested") }),
|
|
@@ -6217,7 +6227,8 @@ var createSessionState = (sessionId) => ({
|
|
|
6217
6227
|
backgroundEditor: null,
|
|
6218
6228
|
question: null,
|
|
6219
6229
|
history: null,
|
|
6220
|
-
diffViewer: null
|
|
6230
|
+
diffViewer: null,
|
|
6231
|
+
toast: null
|
|
6221
6232
|
}
|
|
6222
6233
|
});
|
|
6223
6234
|
|
|
@@ -6632,7 +6643,7 @@ var applyLoadedBackground = (state, background = TRANSPARENT_BACKGROUND) => ({ .
|
|
|
6632
6643
|
var applySavedBackground = (state, color) => appendNotice(closeBackgroundEditor({ ...state, background: color }), "Background color saved");
|
|
6633
6644
|
|
|
6634
6645
|
// packages/events/src/reducers/reduceDiffViewer.ts
|
|
6635
|
-
var NO_DIFFS_NOTICE = "No changes
|
|
6646
|
+
var NO_DIFFS_NOTICE = "No git changes or session edits to show";
|
|
6636
6647
|
function openDiffViewer(state, files) {
|
|
6637
6648
|
if (files.length === 0)
|
|
6638
6649
|
return appendNotice(state, NO_DIFFS_NOTICE);
|
|
@@ -6651,7 +6662,10 @@ var closeDiffViewer = (state) => ({
|
|
|
6651
6662
|
});
|
|
6652
6663
|
|
|
6653
6664
|
// packages/events/src/reducers/reduceNotices.ts
|
|
6654
|
-
var
|
|
6665
|
+
var LOGIN_HINT = "needs-auth: sign in with /mcp login <name>";
|
|
6666
|
+
var describeServer = ({ name, status }) => `${name} (${status === "needs-auth" ? LOGIN_HINT.replace("<name>", name) : status})`;
|
|
6667
|
+
var describeServers = (servers) => servers.length === 0 ? "No MCP servers configured" : `MCP servers: ${servers.map(describeServer).join(", ")}`;
|
|
6668
|
+
var describeLoginStarted = (serverName, authUrl) => `Signing in to ${serverName}. If the browser did not open, visit: ${authUrl}`;
|
|
6655
6669
|
function reduceModelChanged(state, model) {
|
|
6656
6670
|
const changed = { ...state, model };
|
|
6657
6671
|
return appendNotice(changed, `Model set to ${readModelLabel(changed)}`);
|
|
@@ -6703,6 +6717,13 @@ function moveQuestionCursor(state, delta) {
|
|
|
6703
6717
|
return state;
|
|
6704
6718
|
return withDraft(state, { ...question, cursor: (question.cursor + delta + size) % size });
|
|
6705
6719
|
}
|
|
6720
|
+
function setQuestionCursor(state, cursor) {
|
|
6721
|
+
const { question } = state.ui;
|
|
6722
|
+
const current = question ? readCurrentQuestion(question) : undefined;
|
|
6723
|
+
if (!question || !current || cursor < 0 || cursor > current.options.length)
|
|
6724
|
+
return state;
|
|
6725
|
+
return withDraft(state, { ...question, cursor });
|
|
6726
|
+
}
|
|
6706
6727
|
function toggleQuestionPick(state) {
|
|
6707
6728
|
const { question } = state.ui;
|
|
6708
6729
|
const current = question ? readCurrentQuestion(question) : undefined;
|
|
@@ -6730,6 +6751,14 @@ function changeQuestionCustom(state, text) {
|
|
|
6730
6751
|
return question ? withDraft(state, { ...question, custom: text }) : state;
|
|
6731
6752
|
}
|
|
6732
6753
|
|
|
6754
|
+
// packages/events/src/reducers/reduceToast.ts
|
|
6755
|
+
var withToast = (state, toast) => ({
|
|
6756
|
+
...state,
|
|
6757
|
+
ui: { ...state.ui, toast }
|
|
6758
|
+
});
|
|
6759
|
+
var postToast = (state, toast) => withToast(state, { id: toast.id, text: toast.text });
|
|
6760
|
+
var dismissToast = (state, id) => state.ui.toast?.id === id ? withToast(state, null) : state;
|
|
6761
|
+
|
|
6733
6762
|
// packages/events/src/reducers/reduceUi.ts
|
|
6734
6763
|
var FOCUS_ORDER = ["input", "scrollback"];
|
|
6735
6764
|
function cycleFocus(state, direction) {
|
|
@@ -6817,6 +6846,8 @@ function reduceUi(state, event) {
|
|
|
6817
6846
|
return adjustBackgroundValue(state, event.delta);
|
|
6818
6847
|
case "ui.question.moved":
|
|
6819
6848
|
return moveQuestionCursor(state, event.delta);
|
|
6849
|
+
case "ui.question.cursor.set":
|
|
6850
|
+
return setQuestionCursor(state, event.cursor);
|
|
6820
6851
|
case "ui.question.toggled":
|
|
6821
6852
|
return toggleQuestionPick(state);
|
|
6822
6853
|
case "ui.question.custom.changed":
|
|
@@ -6827,6 +6858,10 @@ function reduceUi(state, event) {
|
|
|
6827
6858
|
return state;
|
|
6828
6859
|
case "ui.notice.posted":
|
|
6829
6860
|
return appendNotice(state, event.text);
|
|
6861
|
+
case "ui.toast.posted":
|
|
6862
|
+
return postToast(state, event);
|
|
6863
|
+
case "ui.toast.dismissed":
|
|
6864
|
+
return dismissToast(state, event.id);
|
|
6830
6865
|
case "ui.clock.ticked":
|
|
6831
6866
|
return { ...state, now: event.now };
|
|
6832
6867
|
}
|
|
@@ -6847,7 +6882,8 @@ function restoreSession(state, sessionId, stored, notice) {
|
|
|
6847
6882
|
return appendNotice({ ...adoptReplay(state, settled, sessionId), status: "idle", queuedTurns: 0 }, notice);
|
|
6848
6883
|
}
|
|
6849
6884
|
var syncSession = (state, sessionId, stored) => appendNotice(adoptReplay(state, replayEvents(sessionId, stored), sessionId), "Attached to the live session");
|
|
6850
|
-
function openModelPicker(state,
|
|
6885
|
+
function openModelPicker(state, allModels) {
|
|
6886
|
+
const models = allModels.filter((model) => model.value !== "default");
|
|
6851
6887
|
const current = models.findIndex((model) => model.value === state.model);
|
|
6852
6888
|
const picker = { kind: "model", selected: Math.max(current, 0) };
|
|
6853
6889
|
return { ...state, models, ui: { ...state.ui, picker } };
|
|
@@ -6937,6 +6973,8 @@ function reduceSessionState(state, event) {
|
|
|
6937
6973
|
return reduceModeChanged(state, event.mode);
|
|
6938
6974
|
case "agent.mcp.status.received":
|
|
6939
6975
|
return appendNotice(state, describeServers(event.servers));
|
|
6976
|
+
case "agent.mcp.login.started":
|
|
6977
|
+
return appendNotice(state, describeLoginStarted(event.serverName, event.authUrl));
|
|
6940
6978
|
case "workspace.info.received":
|
|
6941
6979
|
return { ...state, cwd: event.cwd, gitBranch: event.gitBranch, gitStats: event.gitStats };
|
|
6942
6980
|
case "options.loaded":
|
|
@@ -7059,6 +7097,11 @@ var agentResponseSchemas = [
|
|
|
7059
7097
|
type: literal("agent.mcp.status.received"),
|
|
7060
7098
|
servers: sdkValue()
|
|
7061
7099
|
}),
|
|
7100
|
+
object({
|
|
7101
|
+
type: literal("agent.mcp.login.started"),
|
|
7102
|
+
serverName: string2(),
|
|
7103
|
+
authUrl: string2()
|
|
7104
|
+
}),
|
|
7062
7105
|
object({
|
|
7063
7106
|
type: literal("agent.usage.received"),
|
|
7064
7107
|
usage: sdkValue()
|
|
@@ -7156,6 +7199,9 @@ var PRIVATE_TYPES = new Set([
|
|
|
7156
7199
|
"agent.commands.requested",
|
|
7157
7200
|
"agent.mcp.status.requested",
|
|
7158
7201
|
"agent.mcp.status.received",
|
|
7202
|
+
"agent.mcp.login.requested",
|
|
7203
|
+
"agent.mcp.callback.submitted",
|
|
7204
|
+
"agent.mcp.login.started",
|
|
7159
7205
|
"agent.usage.requested",
|
|
7160
7206
|
"agent.usage.received",
|
|
7161
7207
|
"agent.rate_limit.requested",
|
|
@@ -7396,12 +7442,41 @@ import {
|
|
|
7396
7442
|
getSessionMessages,
|
|
7397
7443
|
query
|
|
7398
7444
|
} from "@anthropic-ai/claude-agent-sdk";
|
|
7445
|
+
|
|
7446
|
+
// packages/agent/src/runtime/muteShadowedWarning.ts
|
|
7447
|
+
var SHADOWED_WARNING_CODE = "CLAUDE_SDK_CAN_USE_TOOL_SHADOWED";
|
|
7448
|
+
function readWarningCode(args) {
|
|
7449
|
+
const [first, second] = args;
|
|
7450
|
+
if (typeof first === "object" && first !== null)
|
|
7451
|
+
return first.code;
|
|
7452
|
+
return typeof first === "string" && typeof second === "string" ? second : undefined;
|
|
7453
|
+
}
|
|
7454
|
+
function muteShadowedWarning() {
|
|
7455
|
+
const original = process.emitWarning.bind(process);
|
|
7456
|
+
process.emitWarning = (warning, ...args) => {
|
|
7457
|
+
if (readWarningCode(args) === SHADOWED_WARNING_CODE)
|
|
7458
|
+
return;
|
|
7459
|
+
return original(warning, ...args);
|
|
7460
|
+
};
|
|
7461
|
+
}
|
|
7462
|
+
|
|
7463
|
+
// packages/agent/src/runtime/agentRuntime.ts
|
|
7464
|
+
muteShadowedWarning();
|
|
7399
7465
|
var sdkRuntime = {
|
|
7400
|
-
open: query,
|
|
7466
|
+
open: (params) => query(params),
|
|
7401
7467
|
getInfo: getSessionInfo,
|
|
7402
7468
|
getMessages: getSessionMessages,
|
|
7403
7469
|
fork: forkSession
|
|
7404
7470
|
};
|
|
7471
|
+
// packages/agent/src/runtime/buildUserMessage.ts
|
|
7472
|
+
var isSlashCommand = (content) => readPromptText(content).trimStart().startsWith("/");
|
|
7473
|
+
var buildUserMessage = (content, priority) => ({
|
|
7474
|
+
type: "user",
|
|
7475
|
+
message: { role: "user", content },
|
|
7476
|
+
parent_tool_use_id: null,
|
|
7477
|
+
priority,
|
|
7478
|
+
client_composed: isSlashCommand(content) ? undefined : true
|
|
7479
|
+
});
|
|
7405
7480
|
// node_modules/.bun/p-defer@4.0.1/node_modules/p-defer/index.js
|
|
7406
7481
|
function pDefer() {
|
|
7407
7482
|
const deferred = {};
|
|
@@ -7684,6 +7759,846 @@ function _pushable(getNext, options) {
|
|
|
7684
7759
|
};
|
|
7685
7760
|
return pushable;
|
|
7686
7761
|
}
|
|
7762
|
+
// packages/agent/src/mcp/waitForMcpLogin.ts
|
|
7763
|
+
var DEFAULT_LOGIN_WAIT = { intervalMs: 2000, timeoutMs: 180000 };
|
|
7764
|
+
async function waitForMcpLogin(fetchStatus, serverName, { intervalMs, timeoutMs } = DEFAULT_LOGIN_WAIT) {
|
|
7765
|
+
const deadline = Date.now() + timeoutMs;
|
|
7766
|
+
let servers = await fetchStatus();
|
|
7767
|
+
while (Date.now() < deadline && isAwaitingLogin(servers, serverName)) {
|
|
7768
|
+
await Bun.sleep(intervalMs);
|
|
7769
|
+
servers = await fetchStatus();
|
|
7770
|
+
}
|
|
7771
|
+
return servers;
|
|
7772
|
+
}
|
|
7773
|
+
var isAwaitingLogin = (servers, serverName) => servers.some((server) => server.name === serverName && server.status === "needs-auth");
|
|
7774
|
+
|
|
7775
|
+
// node_modules/.bun/open@11.0.4/node_modules/open/index.js
|
|
7776
|
+
import process9 from "process";
|
|
7777
|
+
import path2 from "path";
|
|
7778
|
+
import { fileURLToPath } from "url";
|
|
7779
|
+
import childProcess3 from "child_process";
|
|
7780
|
+
import fs5, { constants as fsConstants2 } from "fs/promises";
|
|
7781
|
+
|
|
7782
|
+
// node_modules/.bun/wsl-utils@1.0.1/node_modules/wsl-utils/index.js
|
|
7783
|
+
import path from "path";
|
|
7784
|
+
import { promisify as promisify2 } from "util";
|
|
7785
|
+
import childProcess2 from "child_process";
|
|
7786
|
+
import fs4, { constants as fsConstants } from "fs/promises";
|
|
7787
|
+
|
|
7788
|
+
// node_modules/.bun/is-wsl@3.1.1/node_modules/is-wsl/index.js
|
|
7789
|
+
import process2 from "process";
|
|
7790
|
+
import os from "os";
|
|
7791
|
+
import fs3 from "fs";
|
|
7792
|
+
|
|
7793
|
+
// node_modules/.bun/is-inside-container@1.0.0/node_modules/is-inside-container/index.js
|
|
7794
|
+
import fs2 from "fs";
|
|
7795
|
+
|
|
7796
|
+
// node_modules/.bun/is-docker@3.0.0/node_modules/is-docker/index.js
|
|
7797
|
+
import fs from "fs";
|
|
7798
|
+
var isDockerCached;
|
|
7799
|
+
function hasDockerEnv() {
|
|
7800
|
+
try {
|
|
7801
|
+
fs.statSync("/.dockerenv");
|
|
7802
|
+
return true;
|
|
7803
|
+
} catch {
|
|
7804
|
+
return false;
|
|
7805
|
+
}
|
|
7806
|
+
}
|
|
7807
|
+
function hasDockerCGroup() {
|
|
7808
|
+
try {
|
|
7809
|
+
return fs.readFileSync("/proc/self/cgroup", "utf8").includes("docker");
|
|
7810
|
+
} catch {
|
|
7811
|
+
return false;
|
|
7812
|
+
}
|
|
7813
|
+
}
|
|
7814
|
+
function isDocker() {
|
|
7815
|
+
if (isDockerCached === undefined) {
|
|
7816
|
+
isDockerCached = hasDockerEnv() || hasDockerCGroup();
|
|
7817
|
+
}
|
|
7818
|
+
return isDockerCached;
|
|
7819
|
+
}
|
|
7820
|
+
|
|
7821
|
+
// node_modules/.bun/is-inside-container@1.0.0/node_modules/is-inside-container/index.js
|
|
7822
|
+
var cachedResult;
|
|
7823
|
+
var hasContainerEnv = () => {
|
|
7824
|
+
try {
|
|
7825
|
+
fs2.statSync("/run/.containerenv");
|
|
7826
|
+
return true;
|
|
7827
|
+
} catch {
|
|
7828
|
+
return false;
|
|
7829
|
+
}
|
|
7830
|
+
};
|
|
7831
|
+
function isInsideContainer() {
|
|
7832
|
+
if (cachedResult === undefined) {
|
|
7833
|
+
cachedResult = hasContainerEnv() || isDocker();
|
|
7834
|
+
}
|
|
7835
|
+
return cachedResult;
|
|
7836
|
+
}
|
|
7837
|
+
|
|
7838
|
+
// node_modules/.bun/is-wsl@3.1.1/node_modules/is-wsl/index.js
|
|
7839
|
+
var isWsl = () => {
|
|
7840
|
+
if (process2.platform !== "linux") {
|
|
7841
|
+
return false;
|
|
7842
|
+
}
|
|
7843
|
+
if (os.release().toLowerCase().includes("microsoft")) {
|
|
7844
|
+
if (isInsideContainer()) {
|
|
7845
|
+
return false;
|
|
7846
|
+
}
|
|
7847
|
+
return true;
|
|
7848
|
+
}
|
|
7849
|
+
try {
|
|
7850
|
+
if (fs3.readFileSync("/proc/version", "utf8").toLowerCase().includes("microsoft")) {
|
|
7851
|
+
return !isInsideContainer();
|
|
7852
|
+
}
|
|
7853
|
+
} catch {}
|
|
7854
|
+
if (fs3.existsSync("/proc/sys/fs/binfmt_misc/WSLInterop") || fs3.existsSync("/run/WSL")) {
|
|
7855
|
+
return !isInsideContainer();
|
|
7856
|
+
}
|
|
7857
|
+
return false;
|
|
7858
|
+
};
|
|
7859
|
+
var is_wsl_default = process2.env.__IS_WSL_TEST__ ? isWsl : isWsl();
|
|
7860
|
+
|
|
7861
|
+
// node_modules/.bun/powershell-utils@0.2.1/node_modules/powershell-utils/index.js
|
|
7862
|
+
import process3 from "process";
|
|
7863
|
+
import { Buffer as Buffer2 } from "buffer";
|
|
7864
|
+
import { promisify } from "util";
|
|
7865
|
+
import childProcess from "child_process";
|
|
7866
|
+
var execFile = promisify(childProcess.execFile);
|
|
7867
|
+
var powerShellPath = () => `${process3.env.SYSTEMROOT || process3.env.windir || String.raw`C:\Windows`}\\System32\\WindowsPowerShell\\v1.0\\powershell.exe`;
|
|
7868
|
+
var argumentsPrefix = [
|
|
7869
|
+
"-NoProfile",
|
|
7870
|
+
"-NonInteractive",
|
|
7871
|
+
"-ExecutionPolicy",
|
|
7872
|
+
"Bypass",
|
|
7873
|
+
"-EncodedCommand"
|
|
7874
|
+
];
|
|
7875
|
+
var encodeCommand = (command) => Buffer2.from(command, "utf16le").toString("base64");
|
|
7876
|
+
var escapeArgument = (value) => `'${String(value).replaceAll(/['\u2018\u2019\u201A\u201B]/g, (match) => match + match)}'`;
|
|
7877
|
+
var createArguments = (command) => [...argumentsPrefix, encodeCommand(command)];
|
|
7878
|
+
var createExecFileOptions = (options) => ({
|
|
7879
|
+
encoding: "utf8",
|
|
7880
|
+
...options,
|
|
7881
|
+
shell: false
|
|
7882
|
+
});
|
|
7883
|
+
var executePowerShell = async (command, options = {}) => {
|
|
7884
|
+
const {
|
|
7885
|
+
powerShellPath: psPath,
|
|
7886
|
+
...execFileOptions
|
|
7887
|
+
} = options;
|
|
7888
|
+
return execFile(psPath ?? powerShellPath(), createArguments(command), createExecFileOptions(execFileOptions));
|
|
7889
|
+
};
|
|
7890
|
+
executePowerShell.argumentsPrefix = argumentsPrefix;
|
|
7891
|
+
executePowerShell.encodeCommand = encodeCommand;
|
|
7892
|
+
executePowerShell.escapeArgument = escapeArgument;
|
|
7893
|
+
executePowerShell.createArguments = createArguments;
|
|
7894
|
+
|
|
7895
|
+
// node_modules/.bun/wsl-utils@1.0.1/node_modules/wsl-utils/utilities.js
|
|
7896
|
+
function parseMountPointFromConfig(content) {
|
|
7897
|
+
for (const line of content.split(`
|
|
7898
|
+
`)) {
|
|
7899
|
+
if (/^\s*#/.test(line)) {
|
|
7900
|
+
continue;
|
|
7901
|
+
}
|
|
7902
|
+
const match = /^\s*root\s*=\s*(?<mountPoint>"[^"]*"|'[^']*'|[^#]*)/.exec(line);
|
|
7903
|
+
if (!match) {
|
|
7904
|
+
continue;
|
|
7905
|
+
}
|
|
7906
|
+
return match.groups.mountPoint.trim().replaceAll(/^["']|["']$/g, "");
|
|
7907
|
+
}
|
|
7908
|
+
}
|
|
7909
|
+
|
|
7910
|
+
// node_modules/.bun/wsl-utils@1.0.1/node_modules/wsl-utils/index.js
|
|
7911
|
+
var execFile2 = promisify2(childProcess2.execFile);
|
|
7912
|
+
var wslDrivesMountPoint = (() => {
|
|
7913
|
+
const defaultMountPoint = "/mnt/";
|
|
7914
|
+
let mountPoint;
|
|
7915
|
+
return async function() {
|
|
7916
|
+
if (mountPoint) {
|
|
7917
|
+
return mountPoint;
|
|
7918
|
+
}
|
|
7919
|
+
const configFilePath = "/etc/wsl.conf";
|
|
7920
|
+
let isConfigFileExists = false;
|
|
7921
|
+
try {
|
|
7922
|
+
await fs4.access(configFilePath, fsConstants.F_OK);
|
|
7923
|
+
isConfigFileExists = true;
|
|
7924
|
+
} catch {}
|
|
7925
|
+
if (!isConfigFileExists) {
|
|
7926
|
+
return defaultMountPoint;
|
|
7927
|
+
}
|
|
7928
|
+
const configContent = await fs4.readFile(configFilePath, { encoding: "utf8" });
|
|
7929
|
+
const parsedMountPoint = parseMountPointFromConfig(configContent);
|
|
7930
|
+
if (parsedMountPoint === undefined) {
|
|
7931
|
+
return defaultMountPoint;
|
|
7932
|
+
}
|
|
7933
|
+
mountPoint = parsedMountPoint;
|
|
7934
|
+
mountPoint = mountPoint.endsWith("/") ? mountPoint : `${mountPoint}/`;
|
|
7935
|
+
return mountPoint;
|
|
7936
|
+
};
|
|
7937
|
+
})();
|
|
7938
|
+
var powerShellPathFromWsl = async () => {
|
|
7939
|
+
const mountPoint = await wslDrivesMountPoint();
|
|
7940
|
+
return `${mountPoint}c/Windows/System32/WindowsPowerShell/v1.0/powershell.exe`;
|
|
7941
|
+
};
|
|
7942
|
+
var powerShellPath2 = is_wsl_default ? powerShellPathFromWsl : powerShellPath;
|
|
7943
|
+
var canAccessPowerShellPromise;
|
|
7944
|
+
var canAccessPowerShell = async () => {
|
|
7945
|
+
canAccessPowerShellPromise ??= (async () => {
|
|
7946
|
+
try {
|
|
7947
|
+
const psPath = await powerShellPath2();
|
|
7948
|
+
await fs4.access(psPath, fsConstants.X_OK);
|
|
7949
|
+
return true;
|
|
7950
|
+
} catch {
|
|
7951
|
+
return false;
|
|
7952
|
+
}
|
|
7953
|
+
})();
|
|
7954
|
+
return canAccessPowerShellPromise;
|
|
7955
|
+
};
|
|
7956
|
+
var wslDefaultBrowser = async () => {
|
|
7957
|
+
const psPath = await powerShellPath2();
|
|
7958
|
+
const command = String.raw`(Get-ItemProperty -Path "HKCU:\Software\Microsoft\Windows\Shell\Associations\UrlAssociations\http\UserChoice").ProgId`;
|
|
7959
|
+
const { stdout } = await executePowerShell(command, {
|
|
7960
|
+
powerShellPath: psPath,
|
|
7961
|
+
cwd: path.dirname(psPath)
|
|
7962
|
+
});
|
|
7963
|
+
return stdout.trim();
|
|
7964
|
+
};
|
|
7965
|
+
var isUrl = (path2) => /^[a-z]+:\/\//i.test(path2);
|
|
7966
|
+
var convertPath = async (flag, path2) => {
|
|
7967
|
+
const wslpathArguments = path2.startsWith("-") ? [flag, "--", path2] : [flag, path2];
|
|
7968
|
+
try {
|
|
7969
|
+
const { stdout } = await execFile2("wslpath", wslpathArguments, { encoding: "utf8" });
|
|
7970
|
+
return stdout.replace(/\r?\n$/, "") || path2;
|
|
7971
|
+
} catch {
|
|
7972
|
+
return path2;
|
|
7973
|
+
}
|
|
7974
|
+
};
|
|
7975
|
+
var convertWslPathToWindows = async (paths) => {
|
|
7976
|
+
const isBatch = Array.isArray(paths);
|
|
7977
|
+
const pathArray = isBatch ? paths : [paths];
|
|
7978
|
+
const results = await Promise.all(pathArray.map((path2) => isUrl(path2) ? path2 : convertPath("-aw", path2)));
|
|
7979
|
+
return isBatch ? results : results[0];
|
|
7980
|
+
};
|
|
7981
|
+
|
|
7982
|
+
// node_modules/.bun/define-lazy-prop@3.0.0/node_modules/define-lazy-prop/index.js
|
|
7983
|
+
function defineLazyProperty(object, propertyName, valueGetter) {
|
|
7984
|
+
const define = (value) => Object.defineProperty(object, propertyName, { value, enumerable: true, writable: true });
|
|
7985
|
+
Object.defineProperty(object, propertyName, {
|
|
7986
|
+
configurable: true,
|
|
7987
|
+
enumerable: true,
|
|
7988
|
+
get() {
|
|
7989
|
+
const result = valueGetter();
|
|
7990
|
+
define(result);
|
|
7991
|
+
return result;
|
|
7992
|
+
},
|
|
7993
|
+
set(value) {
|
|
7994
|
+
define(value);
|
|
7995
|
+
}
|
|
7996
|
+
});
|
|
7997
|
+
return object;
|
|
7998
|
+
}
|
|
7999
|
+
|
|
8000
|
+
// node_modules/.bun/default-browser@5.5.1/node_modules/default-browser/index.js
|
|
8001
|
+
import { promisify as promisify6 } from "util";
|
|
8002
|
+
import process7 from "process";
|
|
8003
|
+
import { execFile as execFile6 } from "child_process";
|
|
8004
|
+
|
|
8005
|
+
// node_modules/.bun/default-browser-id@5.0.1/node_modules/default-browser-id/index.js
|
|
8006
|
+
import { promisify as promisify3 } from "util";
|
|
8007
|
+
import process4 from "process";
|
|
8008
|
+
import { execFile as execFile3 } from "child_process";
|
|
8009
|
+
var execFileAsync = promisify3(execFile3);
|
|
8010
|
+
async function defaultBrowserId() {
|
|
8011
|
+
if (process4.platform !== "darwin") {
|
|
8012
|
+
throw new Error("macOS only");
|
|
8013
|
+
}
|
|
8014
|
+
const { stdout } = await execFileAsync("defaults", ["read", "com.apple.LaunchServices/com.apple.launchservices.secure", "LSHandlers"]);
|
|
8015
|
+
const match = /LSHandlerRoleAll = "(?!-)(?<id>[^"]+?)";\s+?LSHandlerURLScheme = (?:http|https);/.exec(stdout);
|
|
8016
|
+
const browserId = match?.groups.id ?? "com.apple.Safari";
|
|
8017
|
+
if (browserId === "com.apple.safari") {
|
|
8018
|
+
return "com.apple.Safari";
|
|
8019
|
+
}
|
|
8020
|
+
return browserId;
|
|
8021
|
+
}
|
|
8022
|
+
|
|
8023
|
+
// node_modules/.bun/run-applescript@7.1.0/node_modules/run-applescript/index.js
|
|
8024
|
+
import process5 from "process";
|
|
8025
|
+
import { promisify as promisify4 } from "util";
|
|
8026
|
+
import { execFile as execFile4, execFileSync } from "child_process";
|
|
8027
|
+
var execFileAsync2 = promisify4(execFile4);
|
|
8028
|
+
async function runAppleScript(script, { humanReadableOutput = true, signal } = {}) {
|
|
8029
|
+
if (process5.platform !== "darwin") {
|
|
8030
|
+
throw new Error("macOS only");
|
|
8031
|
+
}
|
|
8032
|
+
const outputArguments = humanReadableOutput ? [] : ["-ss"];
|
|
8033
|
+
const execOptions = {};
|
|
8034
|
+
if (signal) {
|
|
8035
|
+
execOptions.signal = signal;
|
|
8036
|
+
}
|
|
8037
|
+
const { stdout } = await execFileAsync2("osascript", ["-e", script, outputArguments], execOptions);
|
|
8038
|
+
return stdout.trim();
|
|
8039
|
+
}
|
|
8040
|
+
|
|
8041
|
+
// node_modules/.bun/bundle-name@4.1.1/node_modules/bundle-name/index.js
|
|
8042
|
+
var bundleIdentifierPattern = /^[^\n\r"\\]+$/u;
|
|
8043
|
+
async function bundleName(bundleId) {
|
|
8044
|
+
if (typeof bundleId !== "string") {
|
|
8045
|
+
throw new TypeError("Expected a string bundle identifier");
|
|
8046
|
+
}
|
|
8047
|
+
if (!bundleIdentifierPattern.test(bundleId)) {
|
|
8048
|
+
throw new TypeError(`Invalid bundle identifier: ${JSON.stringify(bundleId)}`);
|
|
8049
|
+
}
|
|
8050
|
+
return runAppleScript(`tell application "Finder" to set app_path to application file id "${bundleId}" as string
|
|
8051
|
+
tell application "System Events" to get value of property list item "CFBundleName" of property list file (app_path & ":Contents:Info.plist")`);
|
|
8052
|
+
}
|
|
8053
|
+
|
|
8054
|
+
// node_modules/.bun/default-browser@5.5.1/node_modules/default-browser/windows.js
|
|
8055
|
+
import process6 from "process";
|
|
8056
|
+
import { promisify as promisify5 } from "util";
|
|
8057
|
+
import { execFile as execFile5 } from "child_process";
|
|
8058
|
+
var execFileAsync3 = promisify5(execFile5);
|
|
8059
|
+
var windowsBrowserProgIds = {
|
|
8060
|
+
MSEdgeHTM: { name: "Edge", id: "com.microsoft.edge" },
|
|
8061
|
+
MSEdgeBHTML: { name: "Edge Beta", id: "com.microsoft.edge.beta" },
|
|
8062
|
+
MSEdgeDHTML: { name: "Edge Dev", id: "com.microsoft.edge.dev" },
|
|
8063
|
+
AppXq0fevzme2pys62n3e0fbqa7peapykr8v: { name: "Edge", id: "com.microsoft.edge.old" },
|
|
8064
|
+
ChromeHTML: { name: "Chrome", id: "com.google.chrome" },
|
|
8065
|
+
ChromeBHTML: { name: "Chrome Beta", id: "com.google.chrome.beta" },
|
|
8066
|
+
ChromeDHTML: { name: "Chrome Dev", id: "com.google.chrome.dev" },
|
|
8067
|
+
ChromiumHTM: { name: "Chromium", id: "org.chromium.Chromium" },
|
|
8068
|
+
BraveHTML: { name: "Brave", id: "com.brave.Browser" },
|
|
8069
|
+
BraveBHTML: { name: "Brave Beta", id: "com.brave.Browser.beta" },
|
|
8070
|
+
BraveDHTML: { name: "Brave Dev", id: "com.brave.Browser.dev" },
|
|
8071
|
+
BraveSSHTM: { name: "Brave Nightly", id: "com.brave.Browser.nightly" },
|
|
8072
|
+
FirefoxURL: { name: "Firefox", id: "org.mozilla.firefox" },
|
|
8073
|
+
OperaStable: { name: "Opera", id: "com.operasoftware.Opera" },
|
|
8074
|
+
VivaldiHTM: { name: "Vivaldi", id: "com.vivaldi.Vivaldi" },
|
|
8075
|
+
"IE.HTTP": { name: "Internet Explorer", id: "com.microsoft.ie" }
|
|
8076
|
+
};
|
|
8077
|
+
var _windowsBrowserProgIdMap = new Map(Object.entries(windowsBrowserProgIds));
|
|
8078
|
+
|
|
8079
|
+
class UnknownBrowserError extends Error {
|
|
8080
|
+
}
|
|
8081
|
+
async function defaultBrowser(_execFileAsync = execFileAsync3) {
|
|
8082
|
+
const regPath = `${process6.env.SYSTEMROOT ?? process6.env.windir ?? "C:\\Windows"}\\System32\\reg.exe`;
|
|
8083
|
+
const { stdout } = await _execFileAsync(regPath, [
|
|
8084
|
+
"QUERY",
|
|
8085
|
+
" HKEY_CURRENT_USER\\Software\\Microsoft\\Windows\\Shell\\Associations\\UrlAssociations\\http\\UserChoice",
|
|
8086
|
+
"/v",
|
|
8087
|
+
"ProgId"
|
|
8088
|
+
]);
|
|
8089
|
+
const match = /ProgId\s*REG_SZ\s*(?<id>\S+)/.exec(stdout);
|
|
8090
|
+
if (!match) {
|
|
8091
|
+
throw new UnknownBrowserError(`Cannot find Windows browser in stdout: ${JSON.stringify(stdout)}`);
|
|
8092
|
+
}
|
|
8093
|
+
const { id } = match.groups;
|
|
8094
|
+
const dotIndex = id.lastIndexOf(".");
|
|
8095
|
+
const hyphenIndex = id.lastIndexOf("-");
|
|
8096
|
+
const baseIdByDot = dotIndex === -1 ? undefined : id.slice(0, dotIndex);
|
|
8097
|
+
const baseIdByHyphen = hyphenIndex === -1 ? undefined : id.slice(0, hyphenIndex);
|
|
8098
|
+
return windowsBrowserProgIds[id] ?? windowsBrowserProgIds[baseIdByDot] ?? windowsBrowserProgIds[baseIdByHyphen] ?? { name: id, id };
|
|
8099
|
+
}
|
|
8100
|
+
|
|
8101
|
+
// node_modules/.bun/default-browser@5.5.1/node_modules/default-browser/index.js
|
|
8102
|
+
var execFileAsync4 = promisify6(execFile6);
|
|
8103
|
+
var titleize = (string) => string.toLowerCase().replaceAll(/(?:^|\s|-)\S/g, (x) => x.toUpperCase());
|
|
8104
|
+
async function defaultBrowser2() {
|
|
8105
|
+
if (process7.platform === "darwin") {
|
|
8106
|
+
const id = await defaultBrowserId();
|
|
8107
|
+
const name = await bundleName(id);
|
|
8108
|
+
return { name, id };
|
|
8109
|
+
}
|
|
8110
|
+
if (process7.platform === "linux") {
|
|
8111
|
+
const { stdout } = await execFileAsync4("xdg-mime", ["query", "default", "x-scheme-handler/http"]);
|
|
8112
|
+
const id = stdout.trim();
|
|
8113
|
+
const name = titleize(id.replace(/.desktop$/, "").replace("-", " "));
|
|
8114
|
+
return { name, id };
|
|
8115
|
+
}
|
|
8116
|
+
if (process7.platform === "win32") {
|
|
8117
|
+
return defaultBrowser();
|
|
8118
|
+
}
|
|
8119
|
+
throw new Error("Only macOS, Linux, and Windows are supported");
|
|
8120
|
+
}
|
|
8121
|
+
|
|
8122
|
+
// node_modules/.bun/is-in-ssh@1.0.0/node_modules/is-in-ssh/index.js
|
|
8123
|
+
import process8 from "process";
|
|
8124
|
+
var isInSsh = Boolean(process8.env.SSH_CONNECTION || process8.env.SSH_CLIENT || process8.env.SSH_TTY);
|
|
8125
|
+
var is_in_ssh_default = isInSsh;
|
|
8126
|
+
|
|
8127
|
+
// node_modules/.bun/open@11.0.4/node_modules/open/index.js
|
|
8128
|
+
var fallbackAttemptSymbol = Symbol("fallbackAttempt");
|
|
8129
|
+
var __dirname2 = import.meta.url ? path2.dirname(fileURLToPath(import.meta.url)) : "";
|
|
8130
|
+
var localXdgOpenPath = path2.join(__dirname2, "xdg-open");
|
|
8131
|
+
var { platform, arch } = process9;
|
|
8132
|
+
var tryEachApp = async (apps, opener) => {
|
|
8133
|
+
if (apps.length === 0) {
|
|
8134
|
+
return;
|
|
8135
|
+
}
|
|
8136
|
+
const errors = [];
|
|
8137
|
+
for (const app of apps) {
|
|
8138
|
+
try {
|
|
8139
|
+
return await opener(app);
|
|
8140
|
+
} catch (error) {
|
|
8141
|
+
errors.push(error);
|
|
8142
|
+
}
|
|
8143
|
+
}
|
|
8144
|
+
throw new AggregateError(errors, "Failed to open in all supported apps");
|
|
8145
|
+
};
|
|
8146
|
+
var baseOpen = async (options) => {
|
|
8147
|
+
options = {
|
|
8148
|
+
wait: false,
|
|
8149
|
+
background: false,
|
|
8150
|
+
newInstance: false,
|
|
8151
|
+
allowNonzeroExitCode: false,
|
|
8152
|
+
...options
|
|
8153
|
+
};
|
|
8154
|
+
const isFallbackAttempt = options[fallbackAttemptSymbol] === true;
|
|
8155
|
+
delete options[fallbackAttemptSymbol];
|
|
8156
|
+
if (Array.isArray(options.app)) {
|
|
8157
|
+
return tryEachApp(options.app, (singleApp) => baseOpen({
|
|
8158
|
+
...options,
|
|
8159
|
+
app: singleApp,
|
|
8160
|
+
[fallbackAttemptSymbol]: true
|
|
8161
|
+
}));
|
|
8162
|
+
}
|
|
8163
|
+
let { name: app, arguments: appArguments = [] } = options.app ?? {};
|
|
8164
|
+
appArguments = [...appArguments];
|
|
8165
|
+
if (Array.isArray(app)) {
|
|
8166
|
+
return tryEachApp(app, (appName) => baseOpen({
|
|
8167
|
+
...options,
|
|
8168
|
+
app: {
|
|
8169
|
+
name: appName,
|
|
8170
|
+
arguments: appArguments
|
|
8171
|
+
},
|
|
8172
|
+
[fallbackAttemptSymbol]: true
|
|
8173
|
+
}));
|
|
8174
|
+
}
|
|
8175
|
+
if (app === "browser" || app === "browserPrivate") {
|
|
8176
|
+
const ids = {
|
|
8177
|
+
"com.google.chrome": "chrome",
|
|
8178
|
+
"google-chrome.desktop": "chrome",
|
|
8179
|
+
"com.brave.browser": "brave",
|
|
8180
|
+
"org.mozilla.firefox": "firefox",
|
|
8181
|
+
"firefox.desktop": "firefox",
|
|
8182
|
+
"com.microsoft.msedge": "edge",
|
|
8183
|
+
"com.microsoft.edge": "edge",
|
|
8184
|
+
"com.microsoft.edgemac": "edge",
|
|
8185
|
+
"microsoft-edge.desktop": "edge",
|
|
8186
|
+
"com.apple.safari": "safari"
|
|
8187
|
+
};
|
|
8188
|
+
const flags = {
|
|
8189
|
+
chrome: "--incognito",
|
|
8190
|
+
brave: "--incognito",
|
|
8191
|
+
firefox: "--private-window",
|
|
8192
|
+
edge: "--inPrivate"
|
|
8193
|
+
};
|
|
8194
|
+
let browser;
|
|
8195
|
+
if (is_wsl_default) {
|
|
8196
|
+
const progId = await wslDefaultBrowser();
|
|
8197
|
+
const browserInfo = _windowsBrowserProgIdMap.get(progId);
|
|
8198
|
+
browser = browserInfo ?? {};
|
|
8199
|
+
} else {
|
|
8200
|
+
browser = await defaultBrowser2();
|
|
8201
|
+
}
|
|
8202
|
+
const browserId = browser.id?.toLowerCase();
|
|
8203
|
+
if (Object.hasOwn(ids, browserId)) {
|
|
8204
|
+
const browserName = ids[browserId];
|
|
8205
|
+
if (app === "browserPrivate") {
|
|
8206
|
+
if (browserName === "safari") {
|
|
8207
|
+
throw new Error("Safari doesn't support opening in private mode via command line");
|
|
8208
|
+
}
|
|
8209
|
+
appArguments.push(flags[browserName]);
|
|
8210
|
+
}
|
|
8211
|
+
return baseOpen({
|
|
8212
|
+
...options,
|
|
8213
|
+
app: {
|
|
8214
|
+
name: apps[browserName],
|
|
8215
|
+
arguments: appArguments
|
|
8216
|
+
}
|
|
8217
|
+
});
|
|
8218
|
+
}
|
|
8219
|
+
throw new Error(`${browser.name} is not supported as a default browser`);
|
|
8220
|
+
}
|
|
8221
|
+
let command;
|
|
8222
|
+
const cliArguments = [];
|
|
8223
|
+
const childProcessOptions = {};
|
|
8224
|
+
let shouldUseWindowsInWsl = false;
|
|
8225
|
+
if (is_wsl_default && !isInsideContainer() && !is_in_ssh_default && !app) {
|
|
8226
|
+
shouldUseWindowsInWsl = await canAccessPowerShell();
|
|
8227
|
+
}
|
|
8228
|
+
if (platform === "darwin") {
|
|
8229
|
+
command = "open";
|
|
8230
|
+
if (options.wait) {
|
|
8231
|
+
cliArguments.push("--wait-apps");
|
|
8232
|
+
}
|
|
8233
|
+
if (options.background) {
|
|
8234
|
+
cliArguments.push("--background");
|
|
8235
|
+
}
|
|
8236
|
+
if (options.newInstance) {
|
|
8237
|
+
cliArguments.push("--new");
|
|
8238
|
+
}
|
|
8239
|
+
if (app) {
|
|
8240
|
+
cliArguments.push("-a", app);
|
|
8241
|
+
}
|
|
8242
|
+
} else if (platform === "win32" || shouldUseWindowsInWsl) {
|
|
8243
|
+
command = await powerShellPath2();
|
|
8244
|
+
cliArguments.push(...executePowerShell.argumentsPrefix);
|
|
8245
|
+
if (!is_wsl_default) {
|
|
8246
|
+
childProcessOptions.windowsVerbatimArguments = true;
|
|
8247
|
+
}
|
|
8248
|
+
if (is_wsl_default && options.target) {
|
|
8249
|
+
options.target = await convertWslPathToWindows(options.target);
|
|
8250
|
+
}
|
|
8251
|
+
const encodedArguments = ["$ProgressPreference = 'SilentlyContinue';", "Start"];
|
|
8252
|
+
if (options.wait) {
|
|
8253
|
+
encodedArguments.push("-Wait");
|
|
8254
|
+
}
|
|
8255
|
+
if (app) {
|
|
8256
|
+
encodedArguments.push(executePowerShell.escapeArgument(app));
|
|
8257
|
+
if (options.target) {
|
|
8258
|
+
appArguments.push(options.target);
|
|
8259
|
+
}
|
|
8260
|
+
} else if (options.target) {
|
|
8261
|
+
encodedArguments.push(executePowerShell.escapeArgument(options.target));
|
|
8262
|
+
}
|
|
8263
|
+
if (appArguments.length > 0) {
|
|
8264
|
+
appArguments = appArguments.map((argument) => executePowerShell.escapeArgument(argument));
|
|
8265
|
+
encodedArguments.push("-ArgumentList", appArguments.join(","));
|
|
8266
|
+
}
|
|
8267
|
+
options.target = executePowerShell.encodeCommand(encodedArguments.join(" "));
|
|
8268
|
+
if (!options.wait) {
|
|
8269
|
+
childProcessOptions.stdio = "ignore";
|
|
8270
|
+
}
|
|
8271
|
+
if (is_wsl_default) {
|
|
8272
|
+
childProcessOptions.cwd = path2.dirname(command);
|
|
8273
|
+
}
|
|
8274
|
+
} else {
|
|
8275
|
+
if (app) {
|
|
8276
|
+
command = app;
|
|
8277
|
+
} else {
|
|
8278
|
+
const isBundled = !__dirname2 || __dirname2 === "/";
|
|
8279
|
+
let exeLocalXdgOpen = false;
|
|
8280
|
+
try {
|
|
8281
|
+
await fs5.access(localXdgOpenPath, fsConstants2.X_OK);
|
|
8282
|
+
exeLocalXdgOpen = true;
|
|
8283
|
+
} catch {}
|
|
8284
|
+
const useSystemXdgOpen = process9.versions.electron ?? (platform === "android" || isBundled || !exeLocalXdgOpen);
|
|
8285
|
+
command = useSystemXdgOpen ? "xdg-open" : localXdgOpenPath;
|
|
8286
|
+
}
|
|
8287
|
+
if (appArguments.length > 0) {
|
|
8288
|
+
cliArguments.push(...appArguments);
|
|
8289
|
+
}
|
|
8290
|
+
if (!options.wait) {
|
|
8291
|
+
childProcessOptions.stdio = "ignore";
|
|
8292
|
+
childProcessOptions.detached = true;
|
|
8293
|
+
}
|
|
8294
|
+
}
|
|
8295
|
+
if (platform === "darwin" && appArguments.length > 0) {
|
|
8296
|
+
cliArguments.push("--args", ...appArguments);
|
|
8297
|
+
}
|
|
8298
|
+
if (options.target) {
|
|
8299
|
+
cliArguments.push(options.target);
|
|
8300
|
+
}
|
|
8301
|
+
const subprocess = childProcess3.spawn(command, cliArguments, childProcessOptions);
|
|
8302
|
+
if (options.wait) {
|
|
8303
|
+
return new Promise((resolve, reject) => {
|
|
8304
|
+
subprocess.once("error", reject);
|
|
8305
|
+
subprocess.once("close", (exitCode) => {
|
|
8306
|
+
if (!options.allowNonzeroExitCode && exitCode !== 0) {
|
|
8307
|
+
reject(new Error(`Exited with code ${exitCode}`));
|
|
8308
|
+
return;
|
|
8309
|
+
}
|
|
8310
|
+
resolve(subprocess);
|
|
8311
|
+
});
|
|
8312
|
+
});
|
|
8313
|
+
}
|
|
8314
|
+
if (isFallbackAttempt || platform === "win32" || shouldUseWindowsInWsl) {
|
|
8315
|
+
return new Promise((resolve, reject) => {
|
|
8316
|
+
subprocess.once("error", reject);
|
|
8317
|
+
subprocess.once("spawn", () => {
|
|
8318
|
+
subprocess.once("close", (exitCode) => {
|
|
8319
|
+
subprocess.off("error", reject);
|
|
8320
|
+
if (isFallbackAttempt && exitCode !== 0) {
|
|
8321
|
+
reject(new Error(`Exited with code ${exitCode}`));
|
|
8322
|
+
return;
|
|
8323
|
+
}
|
|
8324
|
+
subprocess.unref();
|
|
8325
|
+
resolve(subprocess);
|
|
8326
|
+
});
|
|
8327
|
+
});
|
|
8328
|
+
});
|
|
8329
|
+
}
|
|
8330
|
+
subprocess.unref();
|
|
8331
|
+
return new Promise((resolve, reject) => {
|
|
8332
|
+
subprocess.once("error", reject);
|
|
8333
|
+
subprocess.once("spawn", () => {
|
|
8334
|
+
subprocess.off("error", reject);
|
|
8335
|
+
resolve(subprocess);
|
|
8336
|
+
});
|
|
8337
|
+
});
|
|
8338
|
+
};
|
|
8339
|
+
var open2 = (target, options) => {
|
|
8340
|
+
if (typeof target !== "string") {
|
|
8341
|
+
throw new TypeError("Expected a `target`");
|
|
8342
|
+
}
|
|
8343
|
+
return baseOpen({
|
|
8344
|
+
...options,
|
|
8345
|
+
target
|
|
8346
|
+
});
|
|
8347
|
+
};
|
|
8348
|
+
function detectArchBinary(binary) {
|
|
8349
|
+
if (typeof binary === "string" || Array.isArray(binary)) {
|
|
8350
|
+
return binary;
|
|
8351
|
+
}
|
|
8352
|
+
const { [arch]: archBinary } = binary;
|
|
8353
|
+
if (!archBinary) {
|
|
8354
|
+
throw new Error(`${arch} is not supported`);
|
|
8355
|
+
}
|
|
8356
|
+
return archBinary;
|
|
8357
|
+
}
|
|
8358
|
+
function detectPlatformBinary({ [platform]: platformBinary }, { wsl } = {}) {
|
|
8359
|
+
if (wsl && is_wsl_default) {
|
|
8360
|
+
return detectArchBinary(wsl);
|
|
8361
|
+
}
|
|
8362
|
+
if (!platformBinary) {
|
|
8363
|
+
throw new Error(`${platform} is not supported`);
|
|
8364
|
+
}
|
|
8365
|
+
return detectArchBinary(platformBinary);
|
|
8366
|
+
}
|
|
8367
|
+
var apps = {
|
|
8368
|
+
browser: "browser",
|
|
8369
|
+
browserPrivate: "browserPrivate"
|
|
8370
|
+
};
|
|
8371
|
+
defineLazyProperty(apps, "chrome", () => detectPlatformBinary({
|
|
8372
|
+
darwin: "google chrome",
|
|
8373
|
+
win32: "chrome",
|
|
8374
|
+
linux: ["google-chrome", "google-chrome-stable", "chromium", "chromium-browser"]
|
|
8375
|
+
}, {
|
|
8376
|
+
wsl: {
|
|
8377
|
+
ia32: "/mnt/c/Program Files (x86)/Google/Chrome/Application/chrome.exe",
|
|
8378
|
+
x64: ["/mnt/c/Program Files/Google/Chrome/Application/chrome.exe", "/mnt/c/Program Files (x86)/Google/Chrome/Application/chrome.exe"]
|
|
8379
|
+
}
|
|
8380
|
+
}));
|
|
8381
|
+
defineLazyProperty(apps, "brave", () => detectPlatformBinary({
|
|
8382
|
+
darwin: "brave browser",
|
|
8383
|
+
win32: "brave",
|
|
8384
|
+
linux: ["brave-browser", "brave"]
|
|
8385
|
+
}, {
|
|
8386
|
+
wsl: {
|
|
8387
|
+
ia32: "/mnt/c/Program Files (x86)/BraveSoftware/Brave-Browser/Application/brave.exe",
|
|
8388
|
+
x64: ["/mnt/c/Program Files/BraveSoftware/Brave-Browser/Application/brave.exe", "/mnt/c/Program Files (x86)/BraveSoftware/Brave-Browser/Application/brave.exe"]
|
|
8389
|
+
}
|
|
8390
|
+
}));
|
|
8391
|
+
defineLazyProperty(apps, "firefox", () => detectPlatformBinary({
|
|
8392
|
+
darwin: "firefox",
|
|
8393
|
+
win32: String.raw`C:\Program Files\Mozilla Firefox\firefox.exe`,
|
|
8394
|
+
linux: "firefox"
|
|
8395
|
+
}, {
|
|
8396
|
+
wsl: "/mnt/c/Program Files/Mozilla Firefox/firefox.exe"
|
|
8397
|
+
}));
|
|
8398
|
+
defineLazyProperty(apps, "edge", () => detectPlatformBinary({
|
|
8399
|
+
darwin: "microsoft edge",
|
|
8400
|
+
win32: "msedge",
|
|
8401
|
+
linux: ["microsoft-edge", "microsoft-edge-dev"]
|
|
8402
|
+
}, {
|
|
8403
|
+
wsl: "/mnt/c/Program Files (x86)/Microsoft/Edge/Application/msedge.exe"
|
|
8404
|
+
}));
|
|
8405
|
+
defineLazyProperty(apps, "safari", () => detectPlatformBinary({
|
|
8406
|
+
darwin: "Safari"
|
|
8407
|
+
}));
|
|
8408
|
+
var open_default = open2;
|
|
8409
|
+
|
|
8410
|
+
// packages/agent/src/system/openBrowser.ts
|
|
8411
|
+
var openBrowser = (url) => open_default(url).catch(() => {
|
|
8412
|
+
return;
|
|
8413
|
+
});
|
|
8414
|
+
|
|
8415
|
+
// packages/agent/src/permissions/sanitizeText.ts
|
|
8416
|
+
var isControlCode = (code) => code < 32 || code >= 127 && code <= 159;
|
|
8417
|
+
var sanitizeText = (text) => [...String(text ?? "")].map((char) => isControlCode(char.charCodeAt(0)) ? " " : char).join("");
|
|
8418
|
+
|
|
8419
|
+
// packages/agent/src/permissions/elicitationForm.ts
|
|
8420
|
+
var SKIP_LABEL = "Skip";
|
|
8421
|
+
var ACCEPT_LABEL = "Accept";
|
|
8422
|
+
var DECLINE_LABEL = "Decline";
|
|
8423
|
+
var YES_LABEL = "Yes";
|
|
8424
|
+
var NO_LABEL = "No";
|
|
8425
|
+
var isSchema = (value) => typeof value === "object" && value !== null && !Array.isArray(value);
|
|
8426
|
+
var readList = (value) => Array.isArray(value) ? value : [];
|
|
8427
|
+
var toChoice = (entry) => {
|
|
8428
|
+
if (typeof entry === "string")
|
|
8429
|
+
return { value: entry, label: sanitizeText(entry) };
|
|
8430
|
+
if (!isSchema(entry) || typeof entry.const !== "string")
|
|
8431
|
+
return;
|
|
8432
|
+
const label = typeof entry.title === "string" ? entry.title : entry.const;
|
|
8433
|
+
return { value: entry.const, label: sanitizeText(label) };
|
|
8434
|
+
};
|
|
8435
|
+
var readChoices = (field) => {
|
|
8436
|
+
const source = isSchema(field.items) ? field.items : field;
|
|
8437
|
+
const entries = [...readList(source.oneOf), ...readList(source.anyOf), ...readList(source.enum)];
|
|
8438
|
+
return entries.flatMap((entry) => toChoice(entry) ?? []);
|
|
8439
|
+
};
|
|
8440
|
+
var readKind = (field, choices) => {
|
|
8441
|
+
if (field.type === "array")
|
|
8442
|
+
return "multi";
|
|
8443
|
+
if (choices.length > 0)
|
|
8444
|
+
return "choice";
|
|
8445
|
+
if (field.type === "boolean")
|
|
8446
|
+
return "boolean";
|
|
8447
|
+
return field.type === "number" || field.type === "integer" ? "number" : "text";
|
|
8448
|
+
};
|
|
8449
|
+
var readOptions = (kind, choices) => {
|
|
8450
|
+
const labelled = (labels) => labels.map((label) => ({ label, description: "" }));
|
|
8451
|
+
if (kind === "boolean")
|
|
8452
|
+
return labelled([YES_LABEL, NO_LABEL]);
|
|
8453
|
+
return labelled(choices.length > 0 ? choices.map(({ label }) => label) : [SKIP_LABEL]);
|
|
8454
|
+
};
|
|
8455
|
+
var buildQuestionText = (key, field, message) => {
|
|
8456
|
+
const title = sanitizeText(typeof field.title === "string" ? field.title : key);
|
|
8457
|
+
const description = typeof field.description === "string" ? ` (${sanitizeText(field.description)})` : "";
|
|
8458
|
+
return `${message}${title}${description}`;
|
|
8459
|
+
};
|
|
8460
|
+
var buildConfirmForm = (header, message) => ({
|
|
8461
|
+
fields: [],
|
|
8462
|
+
questions: [
|
|
8463
|
+
{
|
|
8464
|
+
header,
|
|
8465
|
+
question: message,
|
|
8466
|
+
options: [
|
|
8467
|
+
{ label: ACCEPT_LABEL, description: "" },
|
|
8468
|
+
{ label: DECLINE_LABEL, description: "" }
|
|
8469
|
+
]
|
|
8470
|
+
}
|
|
8471
|
+
]
|
|
8472
|
+
});
|
|
8473
|
+
function buildElicitationForm(serverName, message, requestedSchema) {
|
|
8474
|
+
const header = sanitizeText(serverName);
|
|
8475
|
+
const properties = isSchema(requestedSchema?.properties) ? requestedSchema.properties : {};
|
|
8476
|
+
const entries = Object.entries(properties).filter((entry) => isSchema(entry[1]));
|
|
8477
|
+
if (entries.length === 0)
|
|
8478
|
+
return buildConfirmForm(header, sanitizeText(message));
|
|
8479
|
+
const fields = [];
|
|
8480
|
+
const questions = [];
|
|
8481
|
+
for (const [key, field] of entries) {
|
|
8482
|
+
const choices = readChoices(field);
|
|
8483
|
+
const kind = readKind(field, choices);
|
|
8484
|
+
const intro = fields.length === 0 ? `${sanitizeText(message)} \u2014 ` : "";
|
|
8485
|
+
const question = buildQuestionText(key, field, intro);
|
|
8486
|
+
fields.push({ key, question, kind, choices });
|
|
8487
|
+
questions.push({
|
|
8488
|
+
header,
|
|
8489
|
+
question,
|
|
8490
|
+
multiSelect: kind === "multi",
|
|
8491
|
+
options: readOptions(kind, choices)
|
|
8492
|
+
});
|
|
8493
|
+
}
|
|
8494
|
+
return { fields, questions };
|
|
8495
|
+
}
|
|
8496
|
+
var readChoiceValue = (choices, label) => choices.find((choice) => choice.label === label)?.value ?? label;
|
|
8497
|
+
var readFieldValue = ({ kind, choices }, answer) => {
|
|
8498
|
+
if (kind === "boolean")
|
|
8499
|
+
return answer === YES_LABEL;
|
|
8500
|
+
if (kind === "number")
|
|
8501
|
+
return Number.isFinite(Number(answer)) ? Number(answer) : undefined;
|
|
8502
|
+
if (kind === "choice")
|
|
8503
|
+
return readChoiceValue(choices, answer);
|
|
8504
|
+
if (kind === "multi")
|
|
8505
|
+
return answer.split(", ").map((label) => readChoiceValue(choices, label));
|
|
8506
|
+
return answer;
|
|
8507
|
+
};
|
|
8508
|
+
function buildElicitationContent(form, answers) {
|
|
8509
|
+
const content = {};
|
|
8510
|
+
for (const field of form.fields) {
|
|
8511
|
+
const answer = answers[field.question]?.trim();
|
|
8512
|
+
if (!answer || answer === SKIP_LABEL)
|
|
8513
|
+
continue;
|
|
8514
|
+
const value = readFieldValue(field, answer);
|
|
8515
|
+
if (value !== undefined)
|
|
8516
|
+
content[field.key] = value;
|
|
8517
|
+
}
|
|
8518
|
+
return content;
|
|
8519
|
+
}
|
|
8520
|
+
var isConfirmAccepted = (form, answers) => form.fields.length > 0 || Object.values(answers).includes(ACCEPT_LABEL);
|
|
8521
|
+
|
|
8522
|
+
// packages/agent/src/permissions/elicitationGate.ts
|
|
8523
|
+
var ELICITATION_PREFIX = "elicitation:";
|
|
8524
|
+
var OPEN_BROWSER_LABEL = "Open in browser";
|
|
8525
|
+
var DECLINED = { action: "decline" };
|
|
8526
|
+
var isWebUrl = (url) => {
|
|
8527
|
+
try {
|
|
8528
|
+
return url !== undefined && /^https?:$/.test(new URL(url).protocol);
|
|
8529
|
+
} catch {
|
|
8530
|
+
return false;
|
|
8531
|
+
}
|
|
8532
|
+
};
|
|
8533
|
+
var buildUrlQuestion = ({ serverName, message, url }) => ({
|
|
8534
|
+
header: sanitizeText(serverName),
|
|
8535
|
+
question: `${sanitizeText(message)} ${sanitizeText(url)}`,
|
|
8536
|
+
options: [
|
|
8537
|
+
{ label: OPEN_BROWSER_LABEL, description: "" },
|
|
8538
|
+
{ label: "Decline", description: "" }
|
|
8539
|
+
]
|
|
8540
|
+
});
|
|
8541
|
+
|
|
8542
|
+
class ElicitationGate {
|
|
8543
|
+
agentSessionId;
|
|
8544
|
+
openUrl;
|
|
8545
|
+
pending = new Map;
|
|
8546
|
+
emit = () => {};
|
|
8547
|
+
constructor(agentSessionId, openUrl = openBrowser) {
|
|
8548
|
+
this.agentSessionId = agentSessionId;
|
|
8549
|
+
this.openUrl = openUrl;
|
|
8550
|
+
}
|
|
8551
|
+
listen(emit) {
|
|
8552
|
+
this.emit = emit;
|
|
8553
|
+
}
|
|
8554
|
+
handle = async (request, { signal, requestId }) => {
|
|
8555
|
+
if (request.mode === "url") {
|
|
8556
|
+
if (!isWebUrl(request.url))
|
|
8557
|
+
return DECLINED;
|
|
8558
|
+
return this.open(requestId, signal, [buildUrlQuestion(request)], (answers) => this.acceptUrl(request.url, answers));
|
|
8559
|
+
}
|
|
8560
|
+
const form = buildElicitationForm(request.serverName, request.message, request.requestedSchema);
|
|
8561
|
+
return this.open(requestId, signal, form.questions, (answers) => this.acceptForm(form, answers));
|
|
8562
|
+
};
|
|
8563
|
+
answer(toolUseId, answers) {
|
|
8564
|
+
const pending = this.pending.get(toolUseId);
|
|
8565
|
+
if (!pending)
|
|
8566
|
+
return false;
|
|
8567
|
+
this.pending.delete(toolUseId);
|
|
8568
|
+
const answered = Object.keys(answers).length > 0;
|
|
8569
|
+
pending.settle(answered ? pending.accept(answers) : DECLINED);
|
|
8570
|
+
this.emit({ type: "agent.question.resolved", toolUseId, answered });
|
|
8571
|
+
return true;
|
|
8572
|
+
}
|
|
8573
|
+
rejectAll() {
|
|
8574
|
+
for (const id of [...this.pending.keys()])
|
|
8575
|
+
this.answer(id, {});
|
|
8576
|
+
}
|
|
8577
|
+
acceptUrl(url, answers) {
|
|
8578
|
+
if (!Object.values(answers).includes(OPEN_BROWSER_LABEL))
|
|
8579
|
+
return DECLINED;
|
|
8580
|
+
this.openUrl(url);
|
|
8581
|
+
return { action: "accept" };
|
|
8582
|
+
}
|
|
8583
|
+
acceptForm(form, answers) {
|
|
8584
|
+
if (!isConfirmAccepted(form, answers))
|
|
8585
|
+
return DECLINED;
|
|
8586
|
+
return { action: "accept", content: buildElicitationContent(form, answers) };
|
|
8587
|
+
}
|
|
8588
|
+
open(requestId, signal, questions, accept) {
|
|
8589
|
+
const toolUseId = `${ELICITATION_PREFIX}${requestId}`;
|
|
8590
|
+
return new Promise((settle) => {
|
|
8591
|
+
this.pending.set(toolUseId, { settle, accept });
|
|
8592
|
+
signal.addEventListener("abort", () => this.answer(toolUseId, {}), { once: true });
|
|
8593
|
+
this.emit({
|
|
8594
|
+
type: "agent.question.required",
|
|
8595
|
+
agentSessionId: this.agentSessionId,
|
|
8596
|
+
toolUseId,
|
|
8597
|
+
questions
|
|
8598
|
+
});
|
|
8599
|
+
});
|
|
8600
|
+
}
|
|
8601
|
+
}
|
|
7687
8602
|
|
|
7688
8603
|
// packages/agent/src/permissions/permissionResults.ts
|
|
7689
8604
|
var allowTool = (input) => ({
|
|
@@ -7800,7 +8715,87 @@ var ADHD_SYSTEM_PROMPT = `For the rest of this session, shape every response for
|
|
|
7800
8715
|
|
|
7801
8716
|
Break these rules only when: the reader asks you to "explain" or "walk through" (go as long as the topic needs, still no preamble/closer); a destructive action is ahead (confirm first; safety beats brevity); you are in a debug spiral (name the assumption that might be wrong, ask one diagnostic question); or the request is genuinely ambiguous (ask one short clarifying question); or the harness's own system prompt requires something these rules ban (the harness wins; keep the shape).`;
|
|
7802
8717
|
|
|
7803
|
-
// packages/agent/src/profile/
|
|
8718
|
+
// packages/agent/src/profile/codeReviewPrompt.ts
|
|
8719
|
+
var CODE_REVIEW_DESCRIPTION = "Reviews code changes since a commit, branch, or tag, or the uncommitted work, against the repo's coding standards and the originating spec. Use it to review a branch, a PR, or work in progress.";
|
|
8720
|
+
var CODE_REVIEW_PROMPT = `You are CodeReview. You review a diff along two separate axes and report them side by side. You are read-only: never edit files.
|
|
8721
|
+
|
|
8722
|
+
- Standards: does the code follow this repo's documented coding standards?
|
|
8723
|
+
- Spec: does the code match what the originating issue or spec asked for?
|
|
8724
|
+
|
|
8725
|
+
A change can pass one axis and fail the other. Never merge or rerank the two.
|
|
8726
|
+
|
|
8727
|
+
## 1. Pin the fixed point
|
|
8728
|
+
|
|
8729
|
+
Use the commit, branch, tag, or ref you were given. If none was given, review the uncommitted work with \`git diff HEAD\`.
|
|
8730
|
+
Verify the ref with \`git rev-parse <ref>\` and capture the diff once with \`git diff <ref>...HEAD\`, plus \`git log <ref>..HEAD --oneline\`. If the ref is bad or the diff is empty, say so and stop.
|
|
8731
|
+
|
|
8732
|
+
## 2. Find the spec
|
|
8733
|
+
|
|
8734
|
+
Look in this order:
|
|
8735
|
+
1. Issue references in commit messages (#123, Closes #45).
|
|
8736
|
+
2. A path you were given.
|
|
8737
|
+
3. A spec or issue file under docs/, specs/, or .scratch/ matching the branch name or feature.
|
|
8738
|
+
If there is none, skip the Spec axis and say "no spec available".
|
|
8739
|
+
|
|
8740
|
+
## 3. Find the standards
|
|
8741
|
+
|
|
8742
|
+
Collect every file that documents how code should be written: CLAUDE.md, CODING_STANDARDS.md, CONTRIBUTING.md, and similar. A documented repo standard always wins over the smell baseline.
|
|
8743
|
+
|
|
8744
|
+
Smell baseline, always a judgement call, never a hard violation (name it "possible <smell>"). Skip anything tooling already enforces.
|
|
8745
|
+
- Mysterious Name: a name that does not reveal what it does or holds.
|
|
8746
|
+
- Duplicated Code: the same logic shape in more than one hunk or file.
|
|
8747
|
+
- Feature Envy: a method that uses another object's data more than its own.
|
|
8748
|
+
- Data Clumps: the same few fields or params always travel together.
|
|
8749
|
+
- Primitive Obsession: a primitive standing in for a domain concept.
|
|
8750
|
+
- Repeated Switches: the same switch or if-cascade on one type recurs.
|
|
8751
|
+
- Shotgun Surgery: one logical change forces scattered edits across many files.
|
|
8752
|
+
- Divergent Change: one file is edited for several unrelated reasons.
|
|
8753
|
+
- Speculative Generality: abstraction or hooks for needs the spec does not have.
|
|
8754
|
+
- Message Chains: long a.b().c().d() navigation callers should not depend on.
|
|
8755
|
+
- Middle Man: a class or function that mostly delegates onward.
|
|
8756
|
+
- Refused Bequest: a subclass that ignores or overrides most of what it inherits.
|
|
8757
|
+
|
|
8758
|
+
## 4. Report
|
|
8759
|
+
|
|
8760
|
+
Under \`## Standards\`: every place the diff breaks a documented standard (cite the file and rule), then any baseline smell (name it, quote the hunk). Separate hard violations from judgement calls.
|
|
8761
|
+
Under \`## Spec\`: requirements that are missing or partial, behaviour that was not asked for, and requirements that look implemented but wrong. Quote the spec line for each.
|
|
8762
|
+
|
|
8763
|
+
Every finding names its file path and line range as <path>:<from>:<to>. Keep each axis under 400 words.
|
|
8764
|
+
End with one line: findings per axis and the worst issue within each axis. Do not pick a winner across axes.`;
|
|
8765
|
+
|
|
8766
|
+
// packages/agent/src/profile/scoutPrompt.ts
|
|
8767
|
+
var SCOUT_DESCRIPTION = "Scans the codebase for specific information and returns concise, useful findings with file paths and line ranges. Use it before reading or searching many files yourself.";
|
|
8768
|
+
var SCOUT_PROMPT = `You are Scout. You scan the codebase to answer one exploration request. You are read-only: never edit, write, or run state-changing commands.
|
|
8769
|
+
|
|
8770
|
+
1. Use Glob to find files, Grep to find content, Read to confirm. Read only the lines you need.
|
|
8771
|
+
2. Answer the request directly. Report only what the request needs.
|
|
8772
|
+
3. Every finding names its file path and line range as <path>:<from>:<to>, for example src/auth/login.ts:42:58. A single line is <path>:<line>:<line>.
|
|
8773
|
+
4. Keep it concise: one line per finding, the most relevant first, at most 10 findings.
|
|
8774
|
+
5. If nothing matches, say so and list what you searched.`;
|
|
8775
|
+
|
|
8776
|
+
// packages/agent/src/profile/subagents.ts
|
|
8777
|
+
var AGENT_SUBAGENTS = {
|
|
8778
|
+
Scout: {
|
|
8779
|
+
description: SCOUT_DESCRIPTION,
|
|
8780
|
+
prompt: SCOUT_PROMPT,
|
|
8781
|
+
tools: ["Glob", "Grep", "Read"],
|
|
8782
|
+
model: "haiku",
|
|
8783
|
+
effort: "medium"
|
|
8784
|
+
},
|
|
8785
|
+
CodeReview: {
|
|
8786
|
+
description: CODE_REVIEW_DESCRIPTION,
|
|
8787
|
+
prompt: CODE_REVIEW_PROMPT,
|
|
8788
|
+
tools: ["Bash", "Glob", "Grep", "Read"],
|
|
8789
|
+
model: "sonnet",
|
|
8790
|
+
effort: "medium"
|
|
8791
|
+
}
|
|
8792
|
+
};
|
|
8793
|
+
var SUBAGENT_GUIDANCE = `Prefer subagents over doing the work yourself. Use *Agent* with:
|
|
8794
|
+
- Scout: to scan the codebase for specific information. It returns file paths and line ranges (<path>:<from>:<to>). Use it before you search or read many files.
|
|
8795
|
+
- CodeReview: to review code changes against the repo's standards and spec.
|
|
8796
|
+
Run independent subagents in parallel.`;
|
|
8797
|
+
|
|
8798
|
+
// packages/agent/src/profile/agentTools.ts
|
|
7804
8799
|
var AGENT_TOOLS = [
|
|
7805
8800
|
"Bash",
|
|
7806
8801
|
"Read",
|
|
@@ -7821,16 +8816,70 @@ var AGENT_TOOLS = [
|
|
|
7821
8816
|
"Edit",
|
|
7822
8817
|
"NotebookEdit"
|
|
7823
8818
|
];
|
|
8819
|
+
var AGENT_DISALLOWED_TOOLS = [
|
|
8820
|
+
"Agent(Explore)",
|
|
8821
|
+
"Agent(Plan)",
|
|
8822
|
+
"Agent(statusline-setup)"
|
|
8823
|
+
];
|
|
8824
|
+
|
|
8825
|
+
// packages/agent/src/profile/toolGuidance.ts
|
|
8826
|
+
var TOOL_USAGE = {
|
|
8827
|
+
Bash: "run shell commands; never to read, search, or edit files",
|
|
8828
|
+
Read: "read files",
|
|
8829
|
+
Grep: "search file contents",
|
|
8830
|
+
Glob: "scan files by name pattern",
|
|
8831
|
+
WebSearch: "search the web",
|
|
8832
|
+
WebFetch: "fetch a URL",
|
|
8833
|
+
TaskStop: "stop a running background task",
|
|
8834
|
+
Agent: "delegate work to a subagent",
|
|
8835
|
+
TaskCreate: "create a task",
|
|
8836
|
+
TaskGet: "read one task",
|
|
8837
|
+
TaskList: "list tasks",
|
|
8838
|
+
TaskOutput: "read a background task's output",
|
|
8839
|
+
TaskUpdate: "update a task",
|
|
8840
|
+
TodoWrite: "track the steps of multi-step work",
|
|
8841
|
+
AskUserQuestion: "ask the user",
|
|
8842
|
+
Write: "create new files with content",
|
|
8843
|
+
Edit: "update files",
|
|
8844
|
+
NotebookEdit: "update notebook cells"
|
|
8845
|
+
};
|
|
8846
|
+
var TOOL_GUIDANCE = `Always use the dedicated tool, never a workaround:
|
|
8847
|
+
${AGENT_TOOLS.map((tool) => `- Use *${tool}* to ${TOOL_USAGE[tool]}`).join(`
|
|
8848
|
+
`)}`;
|
|
8849
|
+
|
|
8850
|
+
// packages/agent/src/profile/agentSystemPrompt.ts
|
|
8851
|
+
var AGENT_SYSTEM_PROMPT = [ADHD_SYSTEM_PROMPT, TOOL_GUIDANCE, SUBAGENT_GUIDANCE].join(`
|
|
8852
|
+
|
|
8853
|
+
`);
|
|
8854
|
+
|
|
8855
|
+
// packages/agent/src/profile/agentProfile.ts
|
|
7824
8856
|
var AGENT_PROFILE_OPTIONS = {
|
|
7825
8857
|
tools: AGENT_TOOLS,
|
|
7826
|
-
|
|
8858
|
+
disallowedTools: AGENT_DISALLOWED_TOOLS,
|
|
8859
|
+
systemPrompt: AGENT_SYSTEM_PROMPT,
|
|
8860
|
+
agents: AGENT_SUBAGENTS,
|
|
7827
8861
|
enableFileCheckpointing: true,
|
|
7828
8862
|
extraArgs: { "replay-user-messages": null },
|
|
7829
8863
|
permissionMode: DEFAULT_PERMISSION_MODE,
|
|
7830
8864
|
allowDangerouslySkipPermissions: true,
|
|
7831
8865
|
settings: {
|
|
8866
|
+
agentPushNotifEnabled: true,
|
|
8867
|
+
showMessageTimestamps: true,
|
|
8868
|
+
idleCompaction: false,
|
|
8869
|
+
autoCompactEnabled: true,
|
|
8870
|
+
showThinkingSummaries: true,
|
|
8871
|
+
autoMemoryEnabled: false,
|
|
8872
|
+
emojiCompletionEnabled: false,
|
|
8873
|
+
spinnerTipsEnabled: false,
|
|
8874
|
+
disableAgentView: true,
|
|
8875
|
+
allowAllClaudeAiMcps: false,
|
|
8876
|
+
includeGitInstructions: false,
|
|
8877
|
+
syncClaudeAiPlugins: false,
|
|
8878
|
+
syncClaudeAiSkills: false,
|
|
8879
|
+
enableAllProjectMcpServers: true,
|
|
7832
8880
|
promptCacheTtl: "1h",
|
|
7833
|
-
subagentPromptCacheTtl: "
|
|
8881
|
+
subagentPromptCacheTtl: "5m",
|
|
8882
|
+
viewMode: "verbose",
|
|
7834
8883
|
attribution: { commit: "", pr: "" }
|
|
7835
8884
|
},
|
|
7836
8885
|
settingSources: ["user", "project", "local"],
|
|
@@ -7840,19 +8889,6 @@ var AGENT_PROFILE_OPTIONS = {
|
|
|
7840
8889
|
includeHookEvents: true
|
|
7841
8890
|
};
|
|
7842
8891
|
|
|
7843
|
-
// packages/agent/src/runtime/buildUserMessage.ts
|
|
7844
|
-
var isSlashCommand = (content) => readPromptText(content).trimStart().startsWith("/");
|
|
7845
|
-
var buildUserMessage = (content, priority) => ({
|
|
7846
|
-
type: "user",
|
|
7847
|
-
message: { role: "user", content },
|
|
7848
|
-
parent_tool_use_id: null,
|
|
7849
|
-
priority,
|
|
7850
|
-
client_composed: isSlashCommand(content) ? undefined : true
|
|
7851
|
-
});
|
|
7852
|
-
|
|
7853
|
-
// packages/agent/src/session/pickNextModel.ts
|
|
7854
|
-
var pickNextModel = (models, current) => models[(models.findIndex((model) => model.value === current) + 1) % models.length]?.value;
|
|
7855
|
-
|
|
7856
8892
|
// packages/agent/src/session/agentSession.ts
|
|
7857
8893
|
function requireRewind(result) {
|
|
7858
8894
|
if (!result.canRewind)
|
|
@@ -7864,18 +8900,21 @@ class AgentSession {
|
|
|
7864
8900
|
baseOptions;
|
|
7865
8901
|
input = pushable({ objectMode: true });
|
|
7866
8902
|
gate;
|
|
8903
|
+
elicitations;
|
|
7867
8904
|
query;
|
|
7868
8905
|
pendingTurns = 0;
|
|
7869
8906
|
pumping = false;
|
|
7870
8907
|
constructor(agentSessionId, baseOptions, runtime) {
|
|
7871
8908
|
this.baseOptions = baseOptions;
|
|
7872
8909
|
this.gate = new PermissionGate(agentSessionId);
|
|
8910
|
+
this.elicitations = new ElicitationGate(agentSessionId);
|
|
7873
8911
|
this.query = runtime.open({
|
|
7874
8912
|
prompt: this.input,
|
|
7875
8913
|
options: {
|
|
7876
8914
|
...baseOptions,
|
|
7877
8915
|
...AGENT_PROFILE_OPTIONS,
|
|
7878
|
-
canUseTool: this.gate.canUseTool
|
|
8916
|
+
canUseTool: this.gate.canUseTool,
|
|
8917
|
+
onElicitation: this.elicitations.handle
|
|
7879
8918
|
}
|
|
7880
8919
|
});
|
|
7881
8920
|
}
|
|
@@ -7892,35 +8931,30 @@ class AgentSession {
|
|
|
7892
8931
|
return;
|
|
7893
8932
|
this.pumping = true;
|
|
7894
8933
|
const sink = pushable({ objectMode: true });
|
|
7895
|
-
this.
|
|
8934
|
+
this.listenGates((event) => sink.push(event));
|
|
7896
8935
|
this.pumpMessages(sink);
|
|
7897
8936
|
try {
|
|
7898
8937
|
yield* sink;
|
|
7899
8938
|
} finally {
|
|
7900
8939
|
this.pumping = false;
|
|
7901
|
-
this.
|
|
8940
|
+
this.listenGates(() => {});
|
|
7902
8941
|
}
|
|
7903
8942
|
}
|
|
7904
8943
|
answerApproval(toolUseId, decision) {
|
|
7905
8944
|
this.gate.answerApproval(toolUseId, decision);
|
|
7906
8945
|
}
|
|
7907
8946
|
answerQuestion(toolUseId, answers) {
|
|
7908
|
-
this.
|
|
8947
|
+
if (!this.elicitations.answer(toolUseId, answers))
|
|
8948
|
+
this.gate.answerQuestion(toolUseId, answers);
|
|
7909
8949
|
}
|
|
7910
8950
|
async cancel() {
|
|
7911
|
-
this.
|
|
8951
|
+
this.rejectAllPrompts();
|
|
7912
8952
|
await this.query.interrupt();
|
|
7913
8953
|
}
|
|
7914
8954
|
async setModel(model) {
|
|
7915
8955
|
await this.query.setModel(model);
|
|
7916
8956
|
this.baseOptions = { ...this.baseOptions, model };
|
|
7917
8957
|
}
|
|
7918
|
-
async cycleModel() {
|
|
7919
|
-
const next = pickNextModel(await this.fetchModels(), this.baseOptions.model);
|
|
7920
|
-
if (next)
|
|
7921
|
-
await this.setModel(next);
|
|
7922
|
-
return next;
|
|
7923
|
-
}
|
|
7924
8958
|
setPermissionMode(mode) {
|
|
7925
8959
|
return this.query.setPermissionMode(mode);
|
|
7926
8960
|
}
|
|
@@ -7930,6 +8964,27 @@ class AgentSession {
|
|
|
7930
8964
|
fetchMcpStatus() {
|
|
7931
8965
|
return this.query.mcpServerStatus();
|
|
7932
8966
|
}
|
|
8967
|
+
async startMcpLogin(serverName) {
|
|
8968
|
+
if (typeof this.query.mcpAuthenticate !== "function") {
|
|
8969
|
+
throw new Error("This Claude Agent SDK version does not support MCP login");
|
|
8970
|
+
}
|
|
8971
|
+
const { authUrl } = await this.query.mcpAuthenticate(serverName);
|
|
8972
|
+
if (!authUrl)
|
|
8973
|
+
throw new Error(`MCP server ${serverName} did not offer a login`);
|
|
8974
|
+
if (!/^https?:$/.test(new URL(authUrl).protocol)) {
|
|
8975
|
+
throw new Error(`MCP server ${serverName} offered an unsafe login link`);
|
|
8976
|
+
}
|
|
8977
|
+
return authUrl;
|
|
8978
|
+
}
|
|
8979
|
+
async submitMcpCallback(serverName, callbackUrl) {
|
|
8980
|
+
if (!/^https?:$/.test(new URL(callbackUrl).protocol)) {
|
|
8981
|
+
throw new Error("The callback must be an http(s) link");
|
|
8982
|
+
}
|
|
8983
|
+
await this.query.mcpSubmitOAuthCallbackUrl(serverName, callbackUrl);
|
|
8984
|
+
}
|
|
8985
|
+
awaitMcpLogin(serverName, wait) {
|
|
8986
|
+
return waitForMcpLogin(() => this.fetchMcpStatus(), serverName, wait);
|
|
8987
|
+
}
|
|
7933
8988
|
fetchModels() {
|
|
7934
8989
|
return this.query.supportedModels();
|
|
7935
8990
|
}
|
|
@@ -7947,10 +9002,18 @@ class AgentSession {
|
|
|
7947
9002
|
});
|
|
7948
9003
|
}
|
|
7949
9004
|
close() {
|
|
7950
|
-
this.
|
|
9005
|
+
this.rejectAllPrompts();
|
|
7951
9006
|
this.input.end();
|
|
7952
9007
|
this.query.close();
|
|
7953
9008
|
}
|
|
9009
|
+
listenGates(emit) {
|
|
9010
|
+
this.gate.listen(emit);
|
|
9011
|
+
this.elicitations.listen(emit);
|
|
9012
|
+
}
|
|
9013
|
+
rejectAllPrompts() {
|
|
9014
|
+
this.gate.rejectAll();
|
|
9015
|
+
this.elicitations.rejectAll();
|
|
9016
|
+
}
|
|
7954
9017
|
async pumpMessages(sink) {
|
|
7955
9018
|
try {
|
|
7956
9019
|
while (true) {
|
|
@@ -8023,13 +9086,13 @@ class AgentSessionManager {
|
|
|
8023
9086
|
import { homedir } from "os";
|
|
8024
9087
|
import { join as join2 } from "path";
|
|
8025
9088
|
var OPTIONS_PATH = join2(homedir(), ".claudin", "options.json");
|
|
8026
|
-
async function
|
|
9089
|
+
async function readOptions2(path) {
|
|
8027
9090
|
const stored = await Bun.file(path).json().catch(() => ({}));
|
|
8028
9091
|
const parsed = optionsFileSchema.safeParse(stored);
|
|
8029
9092
|
return parsed.success ? parsed.data : {};
|
|
8030
9093
|
}
|
|
8031
9094
|
async function saveBackground(path, background) {
|
|
8032
|
-
await Bun.write(path, JSON.stringify({ ...await
|
|
9095
|
+
await Bun.write(path, JSON.stringify({ ...await readOptions2(path), background }, null, 2));
|
|
8033
9096
|
}
|
|
8034
9097
|
|
|
8035
9098
|
// packages/daemon/src/workspace/resolvePath.ts
|
|
@@ -8249,11 +9312,6 @@ var agentHandlers = {
|
|
|
8249
9312
|
await agents.requireSession(request.agentSessionId).setModel(request.model);
|
|
8250
9313
|
yield { type: "agent.model.changed", model: request.model };
|
|
8251
9314
|
},
|
|
8252
|
-
async* "agent.model.cycle.requested"({ agents }, request) {
|
|
8253
|
-
const model = await agents.requireSession(request.agentSessionId).cycleModel();
|
|
8254
|
-
if (model)
|
|
8255
|
-
yield { type: "agent.model.changed", model };
|
|
8256
|
-
},
|
|
8257
9315
|
async* "agent.effort.set.requested"({ agents }, request) {
|
|
8258
9316
|
await agents.requireSession(request.agentSessionId).setEffort(request.effort);
|
|
8259
9317
|
yield { type: "agent.effort.changed", effort: request.effort };
|
|
@@ -8274,6 +9332,22 @@ var agentHandlers = {
|
|
|
8274
9332
|
const servers = await agents.requireSession(request.agentSessionId).fetchMcpStatus();
|
|
8275
9333
|
yield { type: "agent.mcp.status.received", servers };
|
|
8276
9334
|
},
|
|
9335
|
+
async* "agent.mcp.login.requested"({ agents }, request) {
|
|
9336
|
+
const { serverName } = request;
|
|
9337
|
+
const session = agents.requireSession(request.agentSessionId);
|
|
9338
|
+
const authUrl = await session.startMcpLogin(serverName);
|
|
9339
|
+
yield { type: "agent.mcp.login.started", serverName, authUrl };
|
|
9340
|
+
await openBrowser(authUrl);
|
|
9341
|
+
const servers = await session.awaitMcpLogin(serverName);
|
|
9342
|
+
yield { type: "agent.mcp.status.received", servers };
|
|
9343
|
+
},
|
|
9344
|
+
async* "agent.mcp.callback.submitted"({ agents }, request) {
|
|
9345
|
+
const { serverName, callbackUrl } = request;
|
|
9346
|
+
const session = agents.requireSession(request.agentSessionId);
|
|
9347
|
+
await session.submitMcpCallback(serverName, callbackUrl);
|
|
9348
|
+
const servers = await session.awaitMcpLogin(serverName, { intervalMs: 500, timeoutMs: 1e4 });
|
|
9349
|
+
yield { type: "agent.mcp.status.received", servers };
|
|
9350
|
+
},
|
|
8277
9351
|
async* "agent.usage.requested"({ agents }, request) {
|
|
8278
9352
|
const { session } = await agents.requireSession(request.agentSessionId).fetchUsage();
|
|
8279
9353
|
yield { type: "agent.usage.received", usage: session };
|
|
@@ -8304,7 +9378,7 @@ var agentHandlers = {
|
|
|
8304
9378
|
// packages/daemon/src/handlers/optionsHandlers.ts
|
|
8305
9379
|
var optionsHandlers = {
|
|
8306
9380
|
async* "options.load.requested"({ optionsPath }) {
|
|
8307
|
-
const { background } = await
|
|
9381
|
+
const { background } = await readOptions2(optionsPath);
|
|
8308
9382
|
yield { type: "options.loaded", background };
|
|
8309
9383
|
},
|
|
8310
9384
|
async* "options.background.save.requested"({ optionsPath }, request) {
|
|
@@ -8345,16 +9419,17 @@ var sessionHandlers = {
|
|
|
8345
9419
|
};
|
|
8346
9420
|
|
|
8347
9421
|
// packages/daemon/src/workspace/readFileDiffs.ts
|
|
8348
|
-
import { relative } from "path";
|
|
9422
|
+
import { relative, resolve as resolve2 } from "path";
|
|
8349
9423
|
var isTracked = async (cwd, path) => (await Bun.$`git ls-files --error-unmatch -- ${path}`.cwd(cwd).quiet().nothrow()).exitCode === 0;
|
|
8350
9424
|
async function readPatch(cwd, path) {
|
|
8351
9425
|
const command = await isTracked(cwd, path) ? Bun.$`git diff --no-color HEAD -- ${path}` : Bun.$`git diff --no-color --no-index -- /dev/null ${path}`;
|
|
8352
9426
|
return (await command.cwd(cwd).quiet().nothrow()).text();
|
|
8353
9427
|
}
|
|
8354
9428
|
async function readFileDiff(cwd, path) {
|
|
8355
|
-
const
|
|
9429
|
+
const absolute = resolve2(cwd, path);
|
|
9430
|
+
const patch = await readPatch(cwd, absolute);
|
|
8356
9431
|
return {
|
|
8357
|
-
path: relative(cwd,
|
|
9432
|
+
path: relative(cwd, absolute) || path,
|
|
8358
9433
|
patch,
|
|
8359
9434
|
additions: countPatchLines(patch, "+"),
|
|
8360
9435
|
deletions: countPatchLines(patch, "-")
|
|
@@ -8365,6 +9440,17 @@ async function readFileDiffs(cwd, paths) {
|
|
|
8365
9440
|
return diffs.filter(({ patch }) => patch.trim() !== "");
|
|
8366
9441
|
}
|
|
8367
9442
|
|
|
9443
|
+
// packages/daemon/src/workspace/readGitChangedPaths.ts
|
|
9444
|
+
var readLines = async (cwd, command) => (await command.cwd(cwd).quiet().nothrow()).text().split(`
|
|
9445
|
+
`).filter(Boolean);
|
|
9446
|
+
async function readGitChangedPaths(cwd) {
|
|
9447
|
+
const [tracked, untracked] = await Promise.all([
|
|
9448
|
+
readLines(cwd, Bun.$`git diff --name-only --relative HEAD`),
|
|
9449
|
+
readLines(cwd, Bun.$`git ls-files --others --exclude-standard`)
|
|
9450
|
+
]);
|
|
9451
|
+
return [...tracked, ...untracked];
|
|
9452
|
+
}
|
|
9453
|
+
|
|
8368
9454
|
// node_modules/.bun/fuzzysort@4.0.2/node_modules/fuzzysort/fuzzysort.js
|
|
8369
9455
|
function single(search, target) {
|
|
8370
9456
|
if (!search || !target)
|
|
@@ -9992,7 +11078,9 @@ var workspaceHandlers = {
|
|
|
9992
11078
|
yield { type: "workspace.cwd.changed", cwd, ...await readGitInfo(cwd) };
|
|
9993
11079
|
},
|
|
9994
11080
|
async* "workspace.diff.requested"({ cwd }, request) {
|
|
9995
|
-
|
|
11081
|
+
const changed = await readFileDiffs(cwd, await readGitChangedPaths(cwd));
|
|
11082
|
+
const files = changed.length > 0 ? changed : await readFileDiffs(cwd, request.paths);
|
|
11083
|
+
yield { type: "workspace.diff.received", files };
|
|
9996
11084
|
}
|
|
9997
11085
|
};
|
|
9998
11086
|
|
|
@@ -10045,7 +11133,11 @@ async function startDaemon(port = DEFAULT_PORT, context) {
|
|
|
10045
11133
|
return server;
|
|
10046
11134
|
}
|
|
10047
11135
|
// apps/tui/src/startTui.ts
|
|
10048
|
-
import {
|
|
11136
|
+
import {
|
|
11137
|
+
BoxRenderable as BoxRenderable16,
|
|
11138
|
+
createCliRenderer,
|
|
11139
|
+
createHostClipboard
|
|
11140
|
+
} from "@opentui/core";
|
|
10049
11141
|
|
|
10050
11142
|
// apps/tui/src/components/backgroundPanel.ts
|
|
10051
11143
|
import { BoxRenderable, StyledText, TextRenderable } from "@opentui/core";
|
|
@@ -17537,7 +18629,7 @@ var detectFiletype = (path) => FILETYPES[path.split(".").pop() ?? ""];
|
|
|
17537
18629
|
|
|
17538
18630
|
// apps/tui/src/format/diffViewerChunks.ts
|
|
17539
18631
|
import { bold as bold2, dim as dim2, fg as fg2 } from "@opentui/core";
|
|
17540
|
-
var VIEWER_TITLE = "
|
|
18632
|
+
var VIEWER_TITLE = "Diffs";
|
|
17541
18633
|
var VIEWER_HINT = "\u2190/\u2192 file \xB7 \u2191/\u2193 PgUp/PgDn scroll \xB7 Esc close";
|
|
17542
18634
|
var buildFileChunks = (file, selected) => [
|
|
17543
18635
|
selected ? bold2(fg2(Theme.fg.primary)(`\u276F ${file.path}`)) : fg2(Theme.fg.secondary)(file.path),
|
|
@@ -17787,7 +18879,9 @@ class ListPopover {
|
|
|
17787
18879
|
// apps/tui/src/components/promptInput.ts
|
|
17788
18880
|
import {
|
|
17789
18881
|
BoxRenderable as BoxRenderable5,
|
|
18882
|
+
decodePasteBytes as decodePasteBytes2,
|
|
17790
18883
|
SyntaxStyle,
|
|
18884
|
+
stripAnsiSequences,
|
|
17791
18885
|
TextareaRenderable,
|
|
17792
18886
|
TextRenderable as TextRenderable5
|
|
17793
18887
|
} from "@opentui/core";
|
|
@@ -17974,6 +19068,10 @@ class PromptInput {
|
|
|
17974
19068
|
event.preventDefault();
|
|
17975
19069
|
this.textarea.insertText(placeholder);
|
|
17976
19070
|
}
|
|
19071
|
+
insertPasted(content) {
|
|
19072
|
+
const placeholder = planPaste(content, this.attachments);
|
|
19073
|
+
this.textarea.insertText(placeholder ?? stripAnsiSequences(decodePasteBytes2(content.bytes)));
|
|
19074
|
+
}
|
|
17977
19075
|
clear() {
|
|
17978
19076
|
this.textarea.setText("");
|
|
17979
19077
|
this.attachments.reset();
|
|
@@ -18808,6 +19906,7 @@ class ApprovalPanel {
|
|
|
18808
19906
|
for (const { label, decision, color } of buildButtons()) {
|
|
18809
19907
|
buttons.add(new TextRenderable9(renderer, {
|
|
18810
19908
|
content: new StyledText8([bold4(fg9(color)(label))]),
|
|
19909
|
+
selectable: false,
|
|
18811
19910
|
onMouseDown: () => onDecision(decision)
|
|
18812
19911
|
}));
|
|
18813
19912
|
}
|
|
@@ -18832,44 +19931,64 @@ import {
|
|
|
18832
19931
|
var QUESTION_HINT = "\u2191/\u2193 select \xB7 Space toggle \xB7 Enter confirm \xB7 Esc dismiss";
|
|
18833
19932
|
var CUSTOM_PLACEHOLDER = "type your own answer";
|
|
18834
19933
|
var TEXT_CURSOR = "\u258F";
|
|
18835
|
-
var buildRowChunks = (draft) => {
|
|
18836
|
-
const
|
|
18837
|
-
|
|
18838
|
-
|
|
18839
|
-
const
|
|
18840
|
-
|
|
18841
|
-
|
|
19934
|
+
var buildRowChunks = (draft, multiSelect, { label, description, custom }, index) => {
|
|
19935
|
+
const focused = index === draft.cursor;
|
|
19936
|
+
const checked = custom ? draft.custom.trim() !== "" : draft.picks.includes(label);
|
|
19937
|
+
const marker = multiSelect ? checked ? QUESTION_GLYPHS.checked : QUESTION_GLYPHS.unchecked : "";
|
|
19938
|
+
const prefix = [focused ? QUESTION_GLYPHS.cursor : " ", marker].filter(Boolean).join(" ");
|
|
19939
|
+
const head = fg10(focused ? Theme.accent.brand : Theme.fg.primary)(`${prefix} ${label}`);
|
|
19940
|
+
if (!custom)
|
|
19941
|
+
return [head, fg10(Theme.fg.muted)(` ${description}`)];
|
|
19942
|
+
const typed = draft.custom ? [fg10(Theme.fg.primary)(draft.custom)] : focused ? [] : [fg10(Theme.fg.muted)(CUSTOM_PLACEHOLDER)];
|
|
19943
|
+
return [
|
|
19944
|
+
head,
|
|
19945
|
+
fg10(Theme.fg.muted)(": "),
|
|
19946
|
+
...typed,
|
|
19947
|
+
...focused ? [fg10(Theme.accent.brand)(TEXT_CURSOR)] : []
|
|
18842
19948
|
];
|
|
18843
|
-
|
|
18844
|
-
|
|
18845
|
-
|
|
18846
|
-
|
|
18847
|
-
const prefix = [focused ? QUESTION_GLYPHS.cursor : " ", marker].filter(Boolean).join(" ");
|
|
18848
|
-
const head = fg10(focused ? Theme.accent.brand : Theme.fg.primary)(`
|
|
18849
|
-
${prefix} ${label}`);
|
|
18850
|
-
if (!custom)
|
|
18851
|
-
return [head, fg10(Theme.fg.muted)(` ${description}`)];
|
|
18852
|
-
const typed = draft.custom ? fg10(Theme.fg.primary)(draft.custom) : fg10(Theme.fg.muted)(CUSTOM_PLACEHOLDER);
|
|
18853
|
-
return [
|
|
18854
|
-
head,
|
|
18855
|
-
fg10(Theme.fg.muted)(": "),
|
|
18856
|
-
typed,
|
|
18857
|
-
...focused ? [fg10(Theme.accent.brand)(TEXT_CURSOR)] : []
|
|
18858
|
-
];
|
|
18859
|
-
});
|
|
19949
|
+
};
|
|
19950
|
+
var listRows = (draft) => {
|
|
19951
|
+
const current = readCurrentQuestion(draft);
|
|
19952
|
+
return current ? [...current.options, { label: OTHER_LABEL, description: "", custom: true }] : [];
|
|
18860
19953
|
};
|
|
18861
19954
|
|
|
18862
19955
|
class QuestionPanel {
|
|
19956
|
+
renderer;
|
|
19957
|
+
onSelectRow;
|
|
18863
19958
|
renderable;
|
|
18864
19959
|
text;
|
|
18865
|
-
|
|
19960
|
+
rows;
|
|
19961
|
+
hint;
|
|
19962
|
+
rowViews = [];
|
|
19963
|
+
constructor(renderer, onSelectRow) {
|
|
19964
|
+
this.renderer = renderer;
|
|
19965
|
+
this.onSelectRow = onSelectRow;
|
|
18866
19966
|
this.renderable = new BoxRenderable9(renderer, {
|
|
18867
19967
|
flexDirection: "column",
|
|
18868
19968
|
marginTop: 1,
|
|
18869
19969
|
flexShrink: 0
|
|
18870
19970
|
});
|
|
18871
19971
|
this.text = new TextRenderable10(renderer, { content: "" });
|
|
19972
|
+
this.rows = new BoxRenderable9(renderer, { flexDirection: "column" });
|
|
19973
|
+
this.hint = new TextRenderable10(renderer, {
|
|
19974
|
+
content: new StyledText9([dim4(fg10(Theme.fg.muted)(QUESTION_HINT))])
|
|
19975
|
+
});
|
|
18872
19976
|
this.renderable.add(this.text);
|
|
19977
|
+
this.renderable.add(this.rows);
|
|
19978
|
+
this.renderable.add(this.hint);
|
|
19979
|
+
}
|
|
19980
|
+
readRowView(index) {
|
|
19981
|
+
const existing = this.rowViews[index];
|
|
19982
|
+
if (existing)
|
|
19983
|
+
return existing;
|
|
19984
|
+
const created = new TextRenderable10(this.renderer, {
|
|
19985
|
+
content: "",
|
|
19986
|
+
selectable: false,
|
|
19987
|
+
onMouseDown: () => this.onSelectRow(index)
|
|
19988
|
+
});
|
|
19989
|
+
this.rowViews.push(created);
|
|
19990
|
+
this.rows.add(created);
|
|
19991
|
+
return created;
|
|
18873
19992
|
}
|
|
18874
19993
|
update(draft) {
|
|
18875
19994
|
const current = readCurrentQuestion(draft);
|
|
@@ -18878,11 +19997,17 @@ class QuestionPanel {
|
|
|
18878
19997
|
const progress = draft.questions.length > 1 ? ` (${draft.index + 1}/${draft.questions.length})` : "";
|
|
18879
19998
|
this.text.content = new StyledText9([
|
|
18880
19999
|
bold5(fg10(Theme.status.warning)(`>>> ${current.header}${progress}: `)),
|
|
18881
|
-
bold5(fg10(Theme.fg.primary)(current.question))
|
|
18882
|
-
...buildRowChunks(draft),
|
|
18883
|
-
dim4(fg10(Theme.fg.muted)(`
|
|
18884
|
-
${QUESTION_HINT}`))
|
|
20000
|
+
bold5(fg10(Theme.fg.primary)(current.question))
|
|
18885
20001
|
]);
|
|
20002
|
+
const rows = listRows(draft);
|
|
20003
|
+
rows.forEach((row, index) => {
|
|
20004
|
+
const view = this.readRowView(index);
|
|
20005
|
+
view.visible = true;
|
|
20006
|
+
view.content = new StyledText9(buildRowChunks(draft, current.multiSelect === true, row, index));
|
|
20007
|
+
});
|
|
20008
|
+
this.rowViews.slice(rows.length).forEach((view) => {
|
|
20009
|
+
view.visible = false;
|
|
20010
|
+
});
|
|
18886
20011
|
}
|
|
18887
20012
|
}
|
|
18888
20013
|
|
|
@@ -18920,15 +20045,25 @@ class ToolCallView {
|
|
|
18920
20045
|
onMouseOver: () => this.setHovered(true),
|
|
18921
20046
|
onMouseOut: () => this.setHovered(false)
|
|
18922
20047
|
});
|
|
18923
|
-
this.title = new TextRenderable11(renderer, {
|
|
18924
|
-
|
|
20048
|
+
this.title = new TextRenderable11(renderer, {
|
|
20049
|
+
content: "",
|
|
20050
|
+
wrapMode: "none",
|
|
20051
|
+
flexShrink: 1,
|
|
20052
|
+
selectable: false
|
|
20053
|
+
});
|
|
20054
|
+
this.duration = new TextRenderable11(renderer, {
|
|
20055
|
+
content: "",
|
|
20056
|
+
flexShrink: 0,
|
|
20057
|
+
marginLeft: 2,
|
|
20058
|
+
selectable: false
|
|
20059
|
+
});
|
|
18925
20060
|
header.add(this.title);
|
|
18926
20061
|
header.add(this.duration);
|
|
18927
20062
|
this.body = new BoxRenderable10(renderer, { flexDirection: "column", paddingLeft: 2 });
|
|
18928
20063
|
this.command = new TextRenderable11(renderer, { content: "", fg: Theme.fg.secondary });
|
|
18929
20064
|
this.output = new TextRenderable11(renderer, { content: "" });
|
|
18930
20065
|
this.approval = new ApprovalPanel(renderer, (decision) => hooks.onDecision(decision, this.callId));
|
|
18931
|
-
this.question = new QuestionPanel(renderer);
|
|
20066
|
+
this.question = new QuestionPanel(renderer, (index) => hooks.onSelectRow(index));
|
|
18932
20067
|
this.body.add(this.command);
|
|
18933
20068
|
this.body.add(this.output);
|
|
18934
20069
|
this.renderable.add(header);
|
|
@@ -19198,8 +20333,8 @@ var buildWindowChunks = (label, window, now) => {
|
|
|
19198
20333
|
};
|
|
19199
20334
|
function buildRateLimitChunks(limits, now) {
|
|
19200
20335
|
const windows = [
|
|
19201
|
-
["\
|
|
19202
|
-
["\
|
|
20336
|
+
["\uD83E\uDFF5h", limits.fiveHour],
|
|
20337
|
+
["\uD83E\uDFF7d", limits.sevenDay]
|
|
19203
20338
|
];
|
|
19204
20339
|
return windows.flatMap(([label, window], index) => window ? [
|
|
19205
20340
|
...index > 0 ? [fg13(Theme.border.separator)(SEPARATOR)] : [],
|
|
@@ -19327,6 +20462,7 @@ class StatusLine {
|
|
|
19327
20462
|
content: "",
|
|
19328
20463
|
wrapMode: "none",
|
|
19329
20464
|
flexShrink: 0,
|
|
20465
|
+
selectable: false,
|
|
19330
20466
|
onMouseDown: onStop
|
|
19331
20467
|
});
|
|
19332
20468
|
this.renderable.add(this.label);
|
|
@@ -19354,6 +20490,44 @@ class StatusLine {
|
|
|
19354
20490
|
}
|
|
19355
20491
|
}
|
|
19356
20492
|
|
|
20493
|
+
// apps/tui/src/components/toastView.ts
|
|
20494
|
+
import { BoxRenderable as BoxRenderable15, fg as fg16, StyledText as StyledText14, TextRenderable as TextRenderable15 } from "@opentui/core";
|
|
20495
|
+
var TOAST_ICON = "\u25CF";
|
|
20496
|
+
|
|
20497
|
+
class ToastView {
|
|
20498
|
+
renderable;
|
|
20499
|
+
text;
|
|
20500
|
+
toastId;
|
|
20501
|
+
constructor(renderer) {
|
|
20502
|
+
this.renderable = new BoxRenderable15(renderer, {
|
|
20503
|
+
position: "absolute",
|
|
20504
|
+
top: 1,
|
|
20505
|
+
right: 2,
|
|
20506
|
+
zIndex: 100,
|
|
20507
|
+
paddingLeft: 1,
|
|
20508
|
+
paddingRight: 1,
|
|
20509
|
+
border: true,
|
|
20510
|
+
borderStyle: "rounded",
|
|
20511
|
+
visible: false
|
|
20512
|
+
});
|
|
20513
|
+
this.text = new TextRenderable15(renderer, { content: "", wrapMode: "none", selectable: false });
|
|
20514
|
+
this.renderable.add(this.text);
|
|
20515
|
+
}
|
|
20516
|
+
update({ ui }) {
|
|
20517
|
+
const { toast } = ui;
|
|
20518
|
+
this.renderable.visible = toast !== null;
|
|
20519
|
+
if (!toast || toast.id === this.toastId)
|
|
20520
|
+
return;
|
|
20521
|
+
this.toastId = toast.id;
|
|
20522
|
+
this.renderable.borderColor = Theme.border.focus;
|
|
20523
|
+
this.renderable.backgroundColor = Theme.bg.surface;
|
|
20524
|
+
this.text.content = new StyledText14([
|
|
20525
|
+
fg16(Theme.status.success)(`${TOAST_ICON} `),
|
|
20526
|
+
fg16(Theme.fg.primary)(toast.text)
|
|
20527
|
+
]);
|
|
20528
|
+
}
|
|
20529
|
+
}
|
|
20530
|
+
|
|
19357
20531
|
// apps/tui/src/input/agentBusy.ts
|
|
19358
20532
|
var isStatusBusy = (status) => status !== "idle" && status !== "error";
|
|
19359
20533
|
var isAgentBusy = (store) => isStatusBusy(store.state.status);
|
|
@@ -19395,13 +20569,10 @@ var WORKFLOW_COMMANDS = {
|
|
|
19395
20569
|
store.emit({ type: "ui.rewind.picker.opened" });
|
|
19396
20570
|
}
|
|
19397
20571
|
},
|
|
19398
|
-
"/
|
|
19399
|
-
description: "Review
|
|
20572
|
+
"/diffs": {
|
|
20573
|
+
description: "Review git changes, or this session's edits when there are none",
|
|
19400
20574
|
run(store) {
|
|
19401
|
-
|
|
19402
|
-
if (paths.length === 0)
|
|
19403
|
-
return postNotice(store, "This session has not edited any files");
|
|
19404
|
-
store.request({ type: "workspace.diff.requested", paths });
|
|
20575
|
+
store.request({ type: "workspace.diff.requested", paths: listEditedFiles(store.state) });
|
|
19405
20576
|
}
|
|
19406
20577
|
},
|
|
19407
20578
|
"/export": {
|
|
@@ -19421,13 +20592,30 @@ var WORKFLOW_COMMANDS = {
|
|
|
19421
20592
|
};
|
|
19422
20593
|
|
|
19423
20594
|
// apps/tui/src/input/localCommands.ts
|
|
19424
|
-
function
|
|
19425
|
-
requestAgent(store, { type: "agent.
|
|
20595
|
+
function openModelPicker2(store) {
|
|
20596
|
+
requestAgent(store, { type: "agent.models.requested" });
|
|
19426
20597
|
}
|
|
19427
20598
|
var QUIT_COMMAND = {
|
|
19428
20599
|
description: "Exit the app (also /exit, /q, /leave)",
|
|
19429
20600
|
run: (store) => store.emit({ type: "ui.exit.requested" })
|
|
19430
20601
|
};
|
|
20602
|
+
var MCP_USAGE = "Usage: /mcp | /mcp login <name> | /mcp callback <name> <url>";
|
|
20603
|
+
function runMcpCommand(store, argument) {
|
|
20604
|
+
const [action, serverName, callbackUrl] = argument.trim().split(/\s+/);
|
|
20605
|
+
if (!action)
|
|
20606
|
+
return void requestAgent(store, { type: "agent.mcp.status.requested" });
|
|
20607
|
+
if (action === "login" && serverName) {
|
|
20608
|
+
return void requestAgent(store, { type: "agent.mcp.login.requested", serverName });
|
|
20609
|
+
}
|
|
20610
|
+
if (action === "callback" && serverName && callbackUrl) {
|
|
20611
|
+
return void requestAgent(store, {
|
|
20612
|
+
type: "agent.mcp.callback.submitted",
|
|
20613
|
+
serverName,
|
|
20614
|
+
callbackUrl
|
|
20615
|
+
});
|
|
20616
|
+
}
|
|
20617
|
+
store.emit({ type: "ui.notice.posted", text: MCP_USAGE });
|
|
20618
|
+
}
|
|
19431
20619
|
var SLASH_ALIASES = {
|
|
19432
20620
|
"/exit": "/quit",
|
|
19433
20621
|
"/q": "/quit",
|
|
@@ -19453,7 +20641,7 @@ var SLASH_COMMANDS = {
|
|
|
19453
20641
|
run(store, model) {
|
|
19454
20642
|
if (model)
|
|
19455
20643
|
return void requestAgent(store, { type: "agent.model.set.requested", model });
|
|
19456
|
-
|
|
20644
|
+
openModelPicker2(store);
|
|
19457
20645
|
}
|
|
19458
20646
|
},
|
|
19459
20647
|
"/theme": {
|
|
@@ -19507,10 +20695,8 @@ var SLASH_COMMANDS = {
|
|
|
19507
20695
|
}
|
|
19508
20696
|
},
|
|
19509
20697
|
"/mcp": {
|
|
19510
|
-
description: "List MCP servers",
|
|
19511
|
-
run
|
|
19512
|
-
requestAgent(store, { type: "agent.mcp.status.requested" });
|
|
19513
|
-
}
|
|
20698
|
+
description: "List MCP servers, sign in with /mcp login <name>, or /mcp callback <name> <url>",
|
|
20699
|
+
run: runMcpCommand
|
|
19514
20700
|
},
|
|
19515
20701
|
"/clear": {
|
|
19516
20702
|
description: "Start a fresh session",
|
|
@@ -19704,6 +20890,46 @@ function routeAutocompleteKey(key, store, accept) {
|
|
|
19704
20890
|
return true;
|
|
19705
20891
|
}
|
|
19706
20892
|
|
|
20893
|
+
// apps/tui/src/prompt/clipboardPaste.ts
|
|
20894
|
+
var PREFERRED_TYPES = ["image/png", "text/plain"];
|
|
20895
|
+
async function readClipboardPaste(clipboard) {
|
|
20896
|
+
const result = await clipboard.read({ preferredTypes: PREFERRED_TYPES });
|
|
20897
|
+
if (result.status !== "read")
|
|
20898
|
+
return;
|
|
20899
|
+
const { mimeType, bytes } = result.representation;
|
|
20900
|
+
if (bytes.length === 0)
|
|
20901
|
+
return;
|
|
20902
|
+
return { bytes, metadata: { mimeType, kind: mimeType.startsWith("text/") ? "text" : "binary" } };
|
|
20903
|
+
}
|
|
20904
|
+
|
|
20905
|
+
// apps/tui/src/input/toastActions.ts
|
|
20906
|
+
var TOAST_DURATION_MS = 2500;
|
|
20907
|
+
function showToast(store, text) {
|
|
20908
|
+
const id = crypto.randomUUID();
|
|
20909
|
+
store.emit({ type: "ui.toast.posted", id, text });
|
|
20910
|
+
setTimeout(() => store.emit({ type: "ui.toast.dismissed", id }), TOAST_DURATION_MS).unref();
|
|
20911
|
+
}
|
|
20912
|
+
|
|
20913
|
+
// apps/tui/src/input/clipboardActions.ts
|
|
20914
|
+
var UNAVAILABLE_NOTICE = "Clipboard unavailable, use your terminal's paste shortcut";
|
|
20915
|
+
var COPIED_TOAST = "Copied to clipboard";
|
|
20916
|
+
var COPY_FAILED_TOAST = "Could not copy to clipboard";
|
|
20917
|
+
async function pasteFromClipboard(store, input, clipboard) {
|
|
20918
|
+
const content = await readClipboardPaste(clipboard);
|
|
20919
|
+
if (content)
|
|
20920
|
+
input.insertPasted(content);
|
|
20921
|
+
else
|
|
20922
|
+
showToast(store, UNAVAILABLE_NOTICE);
|
|
20923
|
+
}
|
|
20924
|
+
async function copySelection(store, renderer, clipboard, selection) {
|
|
20925
|
+
const text = selection.getSelectedText();
|
|
20926
|
+
if (!text)
|
|
20927
|
+
return;
|
|
20928
|
+
const written = (await clipboard.writeText(text)).status === "written";
|
|
20929
|
+
const copied = written || renderer.copyToClipboardOSC52(text);
|
|
20930
|
+
showToast(store, copied ? COPIED_TOAST : COPY_FAILED_TOAST);
|
|
20931
|
+
}
|
|
20932
|
+
|
|
19707
20933
|
// apps/tui/src/input/slashCommands.ts
|
|
19708
20934
|
var parseSlashLine = (line) => {
|
|
19709
20935
|
const [name = "", ...rest] = line.trim().split(/\s+/);
|
|
@@ -19883,7 +21109,7 @@ var routeExit = (key, { store, presses, exit }) => {
|
|
|
19883
21109
|
return true;
|
|
19884
21110
|
}
|
|
19885
21111
|
presses.ctrlCAt = pressedAt;
|
|
19886
|
-
store
|
|
21112
|
+
showToast(store, EXIT_NOTICE);
|
|
19887
21113
|
return true;
|
|
19888
21114
|
};
|
|
19889
21115
|
var routeDoubleEscape = (key, { store, presses }) => {
|
|
@@ -19911,10 +21137,11 @@ var QUESTION_ACTIONS = {
|
|
|
19911
21137
|
return: confirmQuestion,
|
|
19912
21138
|
escape: dismissQuestion
|
|
19913
21139
|
};
|
|
21140
|
+
var DELETE_CHARACTER = "\x7F";
|
|
19914
21141
|
var readTypedText = (key) => {
|
|
19915
21142
|
if (key.ctrl || key.meta)
|
|
19916
21143
|
return;
|
|
19917
|
-
return key.sequence.length === 1 && key.sequence >= " " ? key.sequence : undefined;
|
|
21144
|
+
return key.sequence.length === 1 && key.sequence >= " " && key.sequence !== DELETE_CHARACTER ? key.sequence : undefined;
|
|
19918
21145
|
};
|
|
19919
21146
|
function typeCustomAnswer(key, store) {
|
|
19920
21147
|
const { question } = store.state.ui;
|
|
@@ -19999,10 +21226,10 @@ var routePicker = (key, { store }) => {
|
|
|
19999
21226
|
}
|
|
20000
21227
|
return true;
|
|
20001
21228
|
};
|
|
20002
|
-
var
|
|
21229
|
+
var routeModelPicker = (key, { store }) => {
|
|
20003
21230
|
if (key.name !== "tab" || !key.shift)
|
|
20004
21231
|
return false;
|
|
20005
|
-
|
|
21232
|
+
openModelPicker2(store);
|
|
20006
21233
|
return true;
|
|
20007
21234
|
};
|
|
20008
21235
|
var routeDelivery = (key, { store, submitInput }) => {
|
|
@@ -20012,6 +21239,14 @@ var routeDelivery = (key, { store, submitInput }) => {
|
|
|
20012
21239
|
submitInput(delivery);
|
|
20013
21240
|
return true;
|
|
20014
21241
|
};
|
|
21242
|
+
var routePaste = (key, { store, pasteClipboard }) => {
|
|
21243
|
+
if (key.name !== "v" || !(key.ctrl || key.super))
|
|
21244
|
+
return false;
|
|
21245
|
+
if (store.state.ui.focus !== "input")
|
|
21246
|
+
return false;
|
|
21247
|
+
pasteClipboard();
|
|
21248
|
+
return true;
|
|
21249
|
+
};
|
|
20015
21250
|
var ROUTES = [
|
|
20016
21251
|
routeExit,
|
|
20017
21252
|
routeApproval,
|
|
@@ -20019,8 +21254,9 @@ var ROUTES = [
|
|
|
20019
21254
|
routeDiffViewer,
|
|
20020
21255
|
routeBackgroundEditor,
|
|
20021
21256
|
routePicker,
|
|
20022
|
-
|
|
21257
|
+
routeModelPicker,
|
|
20023
21258
|
routeDelivery,
|
|
21259
|
+
routePaste,
|
|
20024
21260
|
routeHistorySearch,
|
|
20025
21261
|
routeCompletion,
|
|
20026
21262
|
routeDoubleEscape,
|
|
@@ -20164,6 +21400,7 @@ class AppStore {
|
|
|
20164
21400
|
machine = new EventMachine(createSessionState(""), reduceTimedEvent);
|
|
20165
21401
|
peerEvents = new WeakSet;
|
|
20166
21402
|
stopListening;
|
|
21403
|
+
closed = false;
|
|
20167
21404
|
constructor(client) {
|
|
20168
21405
|
this.client = client;
|
|
20169
21406
|
this.stopListening = client.subscribe((event, peer) => this.receive(event, peer));
|
|
@@ -20181,7 +21418,8 @@ class AppStore {
|
|
|
20181
21418
|
this.client.send(event);
|
|
20182
21419
|
}
|
|
20183
21420
|
emit(event) {
|
|
20184
|
-
this.
|
|
21421
|
+
if (!this.closed)
|
|
21422
|
+
this.machine.send(event);
|
|
20185
21423
|
}
|
|
20186
21424
|
subscribe(listener) {
|
|
20187
21425
|
return this.machine.subscribe(() => listener(this.machine.state));
|
|
@@ -20193,6 +21431,7 @@ class AppStore {
|
|
|
20193
21431
|
});
|
|
20194
21432
|
}
|
|
20195
21433
|
close() {
|
|
21434
|
+
this.closed = true;
|
|
20196
21435
|
this.stopListening();
|
|
20197
21436
|
this.client.close();
|
|
20198
21437
|
}
|
|
@@ -20224,7 +21463,9 @@ var readShownTheme = ({ theme, ui }) => (ui.picker?.kind === "theme" ? THEME_NAM
|
|
|
20224
21463
|
var readShownBackground = ({ background, ui }) => ui.backgroundEditor?.color ?? background;
|
|
20225
21464
|
async function startTui(client, options = {}) {
|
|
20226
21465
|
const activeRenderer = options.renderer ?? await createCliRenderer({ exitOnCtrlC: false, useMouse: true });
|
|
21466
|
+
activeRenderer.setTerminalTitle("Claudin");
|
|
20227
21467
|
const store = new AppStore(client);
|
|
21468
|
+
const clipboard = options.clipboard ?? createHostClipboard();
|
|
20228
21469
|
let syntaxStyle = createSyntaxStyle(activeRenderer);
|
|
20229
21470
|
let appliedTheme = readShownTheme(store.state);
|
|
20230
21471
|
let appliedBackground = readShownBackground(store.state);
|
|
@@ -20232,13 +21473,15 @@ async function startTui(client, options = {}) {
|
|
|
20232
21473
|
const infoBar = new SessionInfoBar(activeRenderer);
|
|
20233
21474
|
const popover = new ListPopover(activeRenderer);
|
|
20234
21475
|
const backgroundPanel = new BackgroundPanel(activeRenderer);
|
|
21476
|
+
const toastView = new ToastView(activeRenderer);
|
|
20235
21477
|
const statusLine = new StatusLine(activeRenderer, () => cancelTurn(store));
|
|
20236
21478
|
const scrollback = new ScrollbackView(activeRenderer, {
|
|
20237
21479
|
syntaxStyle,
|
|
20238
21480
|
hooks: {
|
|
20239
21481
|
syntaxStyle,
|
|
20240
21482
|
onDecision: (decision, id) => answerApproval(store, decision, id),
|
|
20241
|
-
onToggle: (callId) => store.emit({ type: "ui.tool.toggled", callId })
|
|
21483
|
+
onToggle: (callId) => store.emit({ type: "ui.tool.toggled", callId }),
|
|
21484
|
+
onSelectRow: (cursor) => store.emit({ type: "ui.question.cursor.set", cursor })
|
|
20242
21485
|
}
|
|
20243
21486
|
});
|
|
20244
21487
|
const diffViewer = new DiffViewerPanel(activeRenderer, syntaxStyle);
|
|
@@ -20266,7 +21509,7 @@ async function startTui(client, options = {}) {
|
|
|
20266
21509
|
saveDraft(text);
|
|
20267
21510
|
}
|
|
20268
21511
|
});
|
|
20269
|
-
const root = new
|
|
21512
|
+
const root = new BoxRenderable16(activeRenderer, {
|
|
20270
21513
|
width: "100%",
|
|
20271
21514
|
height: "100%",
|
|
20272
21515
|
flexDirection: "column",
|
|
@@ -20285,6 +21528,10 @@ async function startTui(client, options = {}) {
|
|
|
20285
21528
|
for (const part of parts)
|
|
20286
21529
|
root.add(part.renderable);
|
|
20287
21530
|
activeRenderer.root.add(root);
|
|
21531
|
+
activeRenderer.root.add(toastView.renderable);
|
|
21532
|
+
activeRenderer.on("selection", (selection) => {
|
|
21533
|
+
copySelection(store, activeRenderer, clipboard, selection);
|
|
21534
|
+
});
|
|
20288
21535
|
for (const part of [header, statusLine, popover, backgroundPanel, input, infoBar]) {
|
|
20289
21536
|
part.renderable.onMouseScroll = ({ scroll }) => {
|
|
20290
21537
|
if (scroll?.direction === "up")
|
|
@@ -20317,6 +21564,7 @@ async function startTui(client, options = {}) {
|
|
|
20317
21564
|
syncTheme(state);
|
|
20318
21565
|
header.update(state);
|
|
20319
21566
|
statusLine.update(state);
|
|
21567
|
+
toastView.update(state);
|
|
20320
21568
|
infoBar.update(state);
|
|
20321
21569
|
scrollback.update(state);
|
|
20322
21570
|
scrollback.renderable.visible = state.ui.diffViewer === null;
|
|
@@ -20355,6 +21603,7 @@ async function startTui(client, options = {}) {
|
|
|
20355
21603
|
diffViewer,
|
|
20356
21604
|
editor,
|
|
20357
21605
|
acceptCompletion: () => acceptAutocomplete(store, input),
|
|
21606
|
+
pasteClipboard: () => void pasteFromClipboard(store, input, clipboard),
|
|
20358
21607
|
submitInput,
|
|
20359
21608
|
exit: () => activeRenderer.destroy()
|
|
20360
21609
|
};
|
|
@@ -20380,6 +21629,7 @@ async function startTui(client, options = {}) {
|
|
|
20380
21629
|
clearInterval(rateLimitPoll);
|
|
20381
21630
|
destroyed = true;
|
|
20382
21631
|
historySaver.flush();
|
|
21632
|
+
clipboard.dispose();
|
|
20383
21633
|
options.onExit?.(store.state.sessionId);
|
|
20384
21634
|
store.close();
|
|
20385
21635
|
});
|
|
@@ -20491,10 +21741,10 @@ function humanReadableArgName(arg) {
|
|
|
20491
21741
|
|
|
20492
21742
|
// node_modules/.bun/commander@15.0.0/node_modules/commander/lib/command.js
|
|
20493
21743
|
import { EventEmitter } from "events";
|
|
20494
|
-
import
|
|
20495
|
-
import
|
|
20496
|
-
import
|
|
20497
|
-
import
|
|
21744
|
+
import childProcess4 from "child_process";
|
|
21745
|
+
import path3 from "path";
|
|
21746
|
+
import fs6 from "fs";
|
|
21747
|
+
import process10 from "process";
|
|
20498
21748
|
import { stripVTControlCharacters as stripVTControlCharacters2 } from "util";
|
|
20499
21749
|
|
|
20500
21750
|
// node_modules/.bun/commander@15.0.0/node_modules/commander/lib/help.js
|
|
@@ -21131,13 +22381,13 @@ class Command extends EventEmitter {
|
|
|
21131
22381
|
this._showSuggestionAfterError = true;
|
|
21132
22382
|
this._savedState = null;
|
|
21133
22383
|
this._outputConfiguration = {
|
|
21134
|
-
writeOut: (str) =>
|
|
21135
|
-
writeErr: (str) =>
|
|
22384
|
+
writeOut: (str) => process10.stdout.write(str),
|
|
22385
|
+
writeErr: (str) => process10.stderr.write(str),
|
|
21136
22386
|
outputError: (str, write) => write(str),
|
|
21137
|
-
getOutHelpWidth: () =>
|
|
21138
|
-
getErrHelpWidth: () =>
|
|
21139
|
-
getOutHasColors: () => useColor() ?? (
|
|
21140
|
-
getErrHasColors: () => useColor() ?? (
|
|
22387
|
+
getOutHelpWidth: () => process10.stdout.isTTY ? process10.stdout.columns : undefined,
|
|
22388
|
+
getErrHelpWidth: () => process10.stderr.isTTY ? process10.stderr.columns : undefined,
|
|
22389
|
+
getOutHasColors: () => useColor() ?? (process10.stdout.isTTY && process10.stdout.hasColors?.()),
|
|
22390
|
+
getErrHasColors: () => useColor() ?? (process10.stderr.isTTY && process10.stderr.hasColors?.()),
|
|
21141
22391
|
stripColor: (str) => stripVTControlCharacters2(str)
|
|
21142
22392
|
};
|
|
21143
22393
|
this._hidden = false;
|
|
@@ -21345,7 +22595,7 @@ Expecting one of '${allowedValues.join("', '")}'`);
|
|
|
21345
22595
|
if (this._exitCallback) {
|
|
21346
22596
|
this._exitCallback(new CommanderError(exitCode, code, message));
|
|
21347
22597
|
}
|
|
21348
|
-
|
|
22598
|
+
process10.exit(exitCode);
|
|
21349
22599
|
}
|
|
21350
22600
|
action(fn) {
|
|
21351
22601
|
const listener = (args) => {
|
|
@@ -21537,16 +22787,16 @@ Expecting one of '${allowedValues.join("', '")}'`);
|
|
|
21537
22787
|
}
|
|
21538
22788
|
parseOptions = parseOptions || {};
|
|
21539
22789
|
if (argv === undefined && parseOptions.from === undefined) {
|
|
21540
|
-
if (
|
|
22790
|
+
if (process10.versions?.electron) {
|
|
21541
22791
|
parseOptions.from = "electron";
|
|
21542
22792
|
}
|
|
21543
|
-
const execArgv =
|
|
22793
|
+
const execArgv = process10.execArgv ?? [];
|
|
21544
22794
|
if (execArgv.includes("-e") || execArgv.includes("--eval") || execArgv.includes("-p") || execArgv.includes("--print")) {
|
|
21545
22795
|
parseOptions.from = "eval";
|
|
21546
22796
|
}
|
|
21547
22797
|
}
|
|
21548
22798
|
if (argv === undefined) {
|
|
21549
|
-
argv =
|
|
22799
|
+
argv = process10.argv;
|
|
21550
22800
|
}
|
|
21551
22801
|
this.rawArgs = argv.slice();
|
|
21552
22802
|
let userArgs;
|
|
@@ -21557,7 +22807,7 @@ Expecting one of '${allowedValues.join("', '")}'`);
|
|
|
21557
22807
|
userArgs = argv.slice(2);
|
|
21558
22808
|
break;
|
|
21559
22809
|
case "electron":
|
|
21560
|
-
if (
|
|
22810
|
+
if (process10.defaultApp) {
|
|
21561
22811
|
this._scriptPath = argv[1];
|
|
21562
22812
|
userArgs = argv.slice(2);
|
|
21563
22813
|
} else {
|
|
@@ -21623,7 +22873,7 @@ Expecting one of '${allowedValues.join("', '")}'`);
|
|
|
21623
22873
|
this.processedArgs = [];
|
|
21624
22874
|
}
|
|
21625
22875
|
_checkForMissingExecutable(executableFile, executableDir, subcommandName) {
|
|
21626
|
-
if (
|
|
22876
|
+
if (fs6.existsSync(executableFile))
|
|
21627
22877
|
return;
|
|
21628
22878
|
const executableDirMessage = executableDir ? `searched for local subcommand relative to directory '${executableDir}'` : "no directory for search for local subcommand, use .executableDir() to supply a custom directory";
|
|
21629
22879
|
const executableMissing = `'${executableFile}' does not exist
|
|
@@ -21636,12 +22886,12 @@ Expecting one of '${allowedValues.join("', '")}'`);
|
|
|
21636
22886
|
args = args.slice();
|
|
21637
22887
|
const sourceExt = [".js", ".ts", ".tsx", ".mjs", ".cjs"];
|
|
21638
22888
|
function findFile(baseDir, baseName) {
|
|
21639
|
-
const localBin =
|
|
21640
|
-
if (
|
|
22889
|
+
const localBin = path3.resolve(baseDir, baseName);
|
|
22890
|
+
if (fs6.existsSync(localBin))
|
|
21641
22891
|
return localBin;
|
|
21642
|
-
if (sourceExt.includes(
|
|
22892
|
+
if (sourceExt.includes(path3.extname(baseName)))
|
|
21643
22893
|
return;
|
|
21644
|
-
const foundExt = sourceExt.find((ext) =>
|
|
22894
|
+
const foundExt = sourceExt.find((ext) => fs6.existsSync(`${localBin}${ext}`));
|
|
21645
22895
|
if (foundExt)
|
|
21646
22896
|
return `${localBin}${foundExt}`;
|
|
21647
22897
|
return;
|
|
@@ -21653,42 +22903,42 @@ Expecting one of '${allowedValues.join("', '")}'`);
|
|
|
21653
22903
|
if (this._scriptPath) {
|
|
21654
22904
|
let resolvedScriptPath;
|
|
21655
22905
|
try {
|
|
21656
|
-
resolvedScriptPath =
|
|
22906
|
+
resolvedScriptPath = fs6.realpathSync(this._scriptPath);
|
|
21657
22907
|
} catch {
|
|
21658
22908
|
resolvedScriptPath = this._scriptPath;
|
|
21659
22909
|
}
|
|
21660
|
-
executableDir =
|
|
22910
|
+
executableDir = path3.resolve(path3.dirname(resolvedScriptPath), executableDir);
|
|
21661
22911
|
}
|
|
21662
22912
|
if (executableDir) {
|
|
21663
22913
|
let localFile = findFile(executableDir, executableFile);
|
|
21664
22914
|
if (!localFile && !subcommand._executableFile && this._scriptPath) {
|
|
21665
|
-
const legacyName =
|
|
22915
|
+
const legacyName = path3.basename(this._scriptPath, path3.extname(this._scriptPath));
|
|
21666
22916
|
if (legacyName !== this._name) {
|
|
21667
22917
|
localFile = findFile(executableDir, `${legacyName}-${subcommand._name}`);
|
|
21668
22918
|
}
|
|
21669
22919
|
}
|
|
21670
22920
|
executableFile = localFile || executableFile;
|
|
21671
22921
|
}
|
|
21672
|
-
const launchWithNode = sourceExt.includes(
|
|
22922
|
+
const launchWithNode = sourceExt.includes(path3.extname(executableFile));
|
|
21673
22923
|
let proc;
|
|
21674
|
-
if (
|
|
22924
|
+
if (process10.platform !== "win32") {
|
|
21675
22925
|
if (launchWithNode) {
|
|
21676
22926
|
args.unshift(executableFile);
|
|
21677
|
-
args = incrementNodeInspectorPort(
|
|
21678
|
-
proc =
|
|
22927
|
+
args = incrementNodeInspectorPort(process10.execArgv).concat(args);
|
|
22928
|
+
proc = childProcess4.spawn(process10.argv[0], args, { stdio: "inherit" });
|
|
21679
22929
|
} else {
|
|
21680
|
-
proc =
|
|
22930
|
+
proc = childProcess4.spawn(executableFile, args, { stdio: "inherit" });
|
|
21681
22931
|
}
|
|
21682
22932
|
} else {
|
|
21683
22933
|
this._checkForMissingExecutable(executableFile, executableDir, subcommand._name);
|
|
21684
22934
|
args.unshift(executableFile);
|
|
21685
|
-
args = incrementNodeInspectorPort(
|
|
21686
|
-
proc =
|
|
22935
|
+
args = incrementNodeInspectorPort(process10.execArgv).concat(args);
|
|
22936
|
+
proc = childProcess4.spawn(process10.execPath, args, { stdio: "inherit" });
|
|
21687
22937
|
}
|
|
21688
22938
|
if (!proc.killed) {
|
|
21689
22939
|
const signals = ["SIGUSR1", "SIGUSR2", "SIGTERM", "SIGINT", "SIGHUP"];
|
|
21690
22940
|
signals.forEach((signal) => {
|
|
21691
|
-
|
|
22941
|
+
process10.on(signal, () => {
|
|
21692
22942
|
if (proc.killed === false && proc.exitCode === null) {
|
|
21693
22943
|
proc.kill(signal);
|
|
21694
22944
|
}
|
|
@@ -21699,7 +22949,7 @@ Expecting one of '${allowedValues.join("', '")}'`);
|
|
|
21699
22949
|
proc.on("close", (code) => {
|
|
21700
22950
|
code = code ?? 1;
|
|
21701
22951
|
if (!exitCallback) {
|
|
21702
|
-
|
|
22952
|
+
process10.exit(code);
|
|
21703
22953
|
} else {
|
|
21704
22954
|
exitCallback(new CommanderError(code, "commander.executeSubCommandAsync", "(close)"));
|
|
21705
22955
|
}
|
|
@@ -21711,7 +22961,7 @@ Expecting one of '${allowedValues.join("', '")}'`);
|
|
|
21711
22961
|
throw new Error(`'${executableFile}' not executable`);
|
|
21712
22962
|
}
|
|
21713
22963
|
if (!exitCallback) {
|
|
21714
|
-
|
|
22964
|
+
process10.exit(1);
|
|
21715
22965
|
} else {
|
|
21716
22966
|
const wrappedError = new CommanderError(1, "commander.executeSubCommandAsync", "(error)");
|
|
21717
22967
|
wrappedError.nestedError = err;
|
|
@@ -22060,11 +23310,11 @@ Expecting one of '${allowedValues.join("', '")}'`);
|
|
|
22060
23310
|
}
|
|
22061
23311
|
_parseOptionsEnv() {
|
|
22062
23312
|
this.options.forEach((option) => {
|
|
22063
|
-
if (option.envVar && option.envVar in
|
|
23313
|
+
if (option.envVar && option.envVar in process10.env) {
|
|
22064
23314
|
const optionKey = option.attributeName();
|
|
22065
23315
|
if (this.getOptionValue(optionKey) === undefined || ["default", "config", "env"].includes(this.getOptionValueSource(optionKey))) {
|
|
22066
23316
|
if (option.required || option.optional) {
|
|
22067
|
-
this.emit(`optionEnv:${option.name()}`,
|
|
23317
|
+
this.emit(`optionEnv:${option.name()}`, process10.env[option.envVar]);
|
|
22068
23318
|
} else {
|
|
22069
23319
|
this.emit(`optionEnv:${option.name()}`);
|
|
22070
23320
|
}
|
|
@@ -22260,13 +23510,13 @@ Expecting one of '${allowedValues.join("', '")}'`);
|
|
|
22260
23510
|
cmd.helpGroup(this._defaultCommandGroup);
|
|
22261
23511
|
}
|
|
22262
23512
|
nameFromFilename(filename) {
|
|
22263
|
-
this._name =
|
|
23513
|
+
this._name = path3.basename(filename, path3.extname(filename));
|
|
22264
23514
|
return this;
|
|
22265
23515
|
}
|
|
22266
|
-
executableDir(
|
|
22267
|
-
if (
|
|
23516
|
+
executableDir(path) {
|
|
23517
|
+
if (path === undefined)
|
|
22268
23518
|
return this._executableDir;
|
|
22269
|
-
this._executableDir =
|
|
23519
|
+
this._executableDir = path;
|
|
22270
23520
|
return this;
|
|
22271
23521
|
}
|
|
22272
23522
|
helpInformation(contextOptions) {
|
|
@@ -22363,7 +23613,7 @@ Expecting one of '${allowedValues.join("', '")}'`);
|
|
|
22363
23613
|
}
|
|
22364
23614
|
help(contextOptions) {
|
|
22365
23615
|
this.outputHelp(contextOptions);
|
|
22366
|
-
let exitCode = Number(
|
|
23616
|
+
let exitCode = Number(process10.exitCode ?? 0);
|
|
22367
23617
|
if (exitCode === 0 && contextOptions && typeof contextOptions !== "function" && contextOptions.error) {
|
|
22368
23618
|
exitCode = 1;
|
|
22369
23619
|
}
|
|
@@ -22429,9 +23679,9 @@ function incrementNodeInspectorPort(args) {
|
|
|
22429
23679
|
});
|
|
22430
23680
|
}
|
|
22431
23681
|
function useColor() {
|
|
22432
|
-
if (
|
|
23682
|
+
if (process10.env.NO_COLOR || process10.env.FORCE_COLOR === "0" || process10.env.FORCE_COLOR === "false")
|
|
22433
23683
|
return false;
|
|
22434
|
-
if (
|
|
23684
|
+
if (process10.env.FORCE_COLOR || process10.env.CLICOLOR_FORCE !== undefined)
|
|
22435
23685
|
return true;
|
|
22436
23686
|
return;
|
|
22437
23687
|
}
|