@paradow/ledge 0.34.0 → 0.35.0
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/dist/cli/index.js +39003 -39
- package/dist/cli/{chunk-IWY7DSSO.js → reduceWorker.js} +749 -1188
- package/package.json +4 -1
- package/dist/cli/action-K42H5BDA.js +0 -27
- package/dist/cli/attach-KEE4A5YP.js +0 -87
- package/dist/cli/bridge-X327AZY4.js +0 -70
- package/dist/cli/chunk-25RVT5MR.js +0 -623
- package/dist/cli/chunk-3OJCWJAA.js +0 -144
- package/dist/cli/chunk-4OYVM4MT.js +0 -49
- package/dist/cli/chunk-4TCSADFR.js +0 -252
- package/dist/cli/chunk-53ISXX2R.js +0 -39
- package/dist/cli/chunk-54KF5RBY.js +0 -17
- package/dist/cli/chunk-7NHQGP6J.js +0 -95
- package/dist/cli/chunk-G7XPEVCG.js +0 -118
- package/dist/cli/chunk-KPDTYX7F.js +0 -60
- package/dist/cli/chunk-OLLQBK6N.js +0 -41
- package/dist/cli/chunk-RPH773TY.js +0 -6
- package/dist/cli/chunk-RX5CJ7YH.js +0 -43
- package/dist/cli/chunk-T547FLQN.js +0 -128
- package/dist/cli/chunk-U67V476Y.js +0 -35
- package/dist/cli/chunk-UJ2WBGLW.js +0 -305
- package/dist/cli/chunk-ULOMKEB6.js +0 -85
- package/dist/cli/chunk-V4XKKL6K.js +0 -205
- package/dist/cli/daemon-RO43S3S5.js +0 -11449
- package/dist/cli/decide-KZFYL3HY.js +0 -59
- package/dist/cli/handover-BWNMI2RA.js +0 -17
- package/dist/cli/hook-ZLWXI5EQ.js +0 -473
- package/dist/cli/launch-GCX7TXOH.js +0 -28
- package/dist/cli/send-SXZAPVRH.js +0 -19
- package/dist/cli/setup-TJ32FMVJ.js +0 -38
- package/dist/cli/status-YDVRES4E.js +0 -28
- package/dist/cli/task-TUSOVJK7.js +0 -19
- package/dist/cli/tui-TCVIRZCQ.js +0 -19348
- package/dist/cli/uninstall-QO7YMSLA.js +0 -162
- package/dist/cli/version-BAYSYWFP.js +0 -7
- package/dist/cli/who-6AZYSP7T.js +0 -12
|
@@ -1,118 +0,0 @@
|
|
|
1
|
-
import {
|
|
2
|
-
CODEX_HOOK_VAR
|
|
3
|
-
} from "./chunk-4TCSADFR.js";
|
|
4
|
-
import {
|
|
5
|
-
connect
|
|
6
|
-
} from "./chunk-7NHQGP6J.js";
|
|
7
|
-
import {
|
|
8
|
-
LEDGE_GIVER,
|
|
9
|
-
TASK_TEXT_MAX,
|
|
10
|
-
TASK_TITLE_MAX
|
|
11
|
-
} from "./chunk-IWY7DSSO.js";
|
|
12
|
-
|
|
13
|
-
// src/cli/task.ts
|
|
14
|
-
import { randomUUID } from "crypto";
|
|
15
|
-
var TASK_USAGE = `ledge task give <nom> "<titre>" ["<d\xE9tail>"] confier un travail \xE0 une session
|
|
16
|
-
ledge task give ledge "<question>" "<options, recommandation>" une d\xE9cision pour l'utilisateur ; sa r\xE9ponse te r\xE9veille
|
|
17
|
-
ledge task list [--all] tes t\xE2ches (tenues ou confi\xE9es), ouvertes ; --all : closes aussi
|
|
18
|
-
ledge task show <id> une t\xE2che, son d\xE9tail et son historique
|
|
19
|
-
ledge task take <id> la prendre
|
|
20
|
-
ledge task done <id> "<r\xE9sultat>" la terminer, avec ce qui en est sorti (la session qui l'a confi\xE9e est pr\xE9venue)
|
|
21
|
-
ledge task refuse <id> "<raison>" la refuser, ou l'annuler si tu l'as confi\xE9e
|
|
22
|
-
ledge task pass <id> <nom> ["<note>"] la passer \xE0 une autre session`;
|
|
23
|
-
var TASK_MS = 4e3;
|
|
24
|
-
var ID = /^t[0-9a-f]{6}$/;
|
|
25
|
-
function taskArgs(args) {
|
|
26
|
-
const [op, ...rest] = args;
|
|
27
|
-
const id = rest[0] && ID.test(rest[0]) ? rest[0] : void 0;
|
|
28
|
-
const fits = (min, max) => rest.length >= min && rest.length <= max && rest.slice(0, min).every((a) => a.trim() !== "");
|
|
29
|
-
switch (op) {
|
|
30
|
-
case "give":
|
|
31
|
-
return fits(2, 3) && rest[1].length <= TASK_TITLE_MAX && (rest[2]?.length ?? 0) <= TASK_TEXT_MAX ? { op, to: rest[0], title: rest[1], ...rest[2] ? { text: rest[2] } : {} } : void 0;
|
|
32
|
-
case "list":
|
|
33
|
-
return rest.length === 0 ? { op } : rest.length === 1 && rest[0] === "--all" ? { op, all: true } : void 0;
|
|
34
|
-
case "show":
|
|
35
|
-
case "take":
|
|
36
|
-
return fits(1, 1) && id ? { op, task: id } : void 0;
|
|
37
|
-
case "done":
|
|
38
|
-
return fits(2, 2) && id && rest[1].length <= TASK_TEXT_MAX ? { op, task: id, text: rest[1] } : void 0;
|
|
39
|
-
case "refuse":
|
|
40
|
-
return fits(2, 2) && id && rest[1].length <= TASK_TEXT_MAX ? { op, task: id, text: rest[1] } : void 0;
|
|
41
|
-
case "pass":
|
|
42
|
-
return fits(2, 3) && id && (rest[2]?.length ?? 0) <= TASK_TEXT_MAX ? { op, task: id, to: rest[1], ...rest[2] ? { text: rest[2] } : {} } : void 0;
|
|
43
|
-
default:
|
|
44
|
-
return void 0;
|
|
45
|
-
}
|
|
46
|
-
}
|
|
47
|
-
var STATE = { open: "\xE0 prendre", taken: "prise", done: "termin\xE9e", refused: "refus\xE9e", dropped: "abandonn\xE9e" };
|
|
48
|
-
var time = (iso) => iso.slice(0, 16).replace("T", " ");
|
|
49
|
-
function formatTask(t) {
|
|
50
|
-
return [
|
|
51
|
-
`${t.id} \xB7 ${STATE[t.state]} \xB7 de ${t.giverName} \xE0 ${t.ownerName} \xB7 ${time(t.at)}`,
|
|
52
|
-
t.title,
|
|
53
|
-
...t.text ? ["", t.text] : [],
|
|
54
|
-
...t.result ? ["", `${t.state === "done" ? "R\xE9sultat" : "Raison"} : ${t.result}`] : [],
|
|
55
|
-
"",
|
|
56
|
-
"Historique :",
|
|
57
|
-
...t.log.map((l) => ` ${time(l.at)} ${l.by} : ${l.what}`)
|
|
58
|
-
].join("\n");
|
|
59
|
-
}
|
|
60
|
-
async function taskOnClient(client, args, by, ms) {
|
|
61
|
-
const op = taskArgs(args);
|
|
62
|
-
if (!op) return { line: TASK_USAGE, code: 1 };
|
|
63
|
-
if (by === LEDGE_GIVER) return { line: "refus\xE9 : seul Ledge confie une t\xE2che en son nom", code: 1 };
|
|
64
|
-
try {
|
|
65
|
-
client.send({ type: "task.cmd", rid: randomUUID(), by, ...op });
|
|
66
|
-
const r = await client.next("task.result", ms);
|
|
67
|
-
if (r.reason !== void 0) return { line: `refus\xE9 : ${r.reason}`, code: 1 };
|
|
68
|
-
if (op.op === "list") {
|
|
69
|
-
const list = r.tasks ?? [];
|
|
70
|
-
if (!list.length) return { line: op.all ? "aucune t\xE2che" : "aucune t\xE2che ouverte", code: 0 };
|
|
71
|
-
return { line: list.map((t2) => `${t2.id} ${STATE[t2.state].padEnd(10)} ${t2.giverName} \u2192 ${t2.ownerName} ${t2.title}`).join("\n"), code: 0 };
|
|
72
|
-
}
|
|
73
|
-
const t = r.task;
|
|
74
|
-
switch (op.op) {
|
|
75
|
-
case "give":
|
|
76
|
-
return { line: t.owner === LEDGE_GIVER ? `d\xE9cision ${t.id} pos\xE9e \xE0 l'utilisateur (ledge decide) : sa r\xE9ponse t'arrivera comme une t\xE2che termin\xE9e` : `t\xE2che ${t.id} confi\xE9e \xE0 ${t.ownerName} : elle lui arrive \xE0 son prochain moment libre`, code: 0 };
|
|
77
|
-
case "take":
|
|
78
|
-
return { line: `t\xE2che ${t.id} prise`, code: 0 };
|
|
79
|
-
case "done":
|
|
80
|
-
return { line: `t\xE2che ${t.id} termin\xE9e ; Ledge pr\xE9vient ${t.giverName}`, code: 0 };
|
|
81
|
-
case "refuse":
|
|
82
|
-
return { line: t.giver === by ? `t\xE2che ${t.id} annul\xE9e ; Ledge pr\xE9vient ${t.ownerName}` : `t\xE2che ${t.id} refus\xE9e ; Ledge pr\xE9vient ${t.giverName}`, code: 0 };
|
|
83
|
-
case "pass":
|
|
84
|
-
return { line: `t\xE2che ${t.id} pass\xE9e \xE0 ${t.ownerName}`, code: 0 };
|
|
85
|
-
default:
|
|
86
|
-
return { line: formatTask(t), code: 0 };
|
|
87
|
-
}
|
|
88
|
-
} catch (e) {
|
|
89
|
-
return { line: `pas de r\xE9ponse de Ledge : ${e.message}`, code: 1 };
|
|
90
|
-
}
|
|
91
|
-
}
|
|
92
|
-
async function runTask(args, opts = {}) {
|
|
93
|
-
if (!taskArgs(args)) return { line: TASK_USAGE, code: args.length ? 1 : 0 };
|
|
94
|
-
const env = opts.env ?? process.env;
|
|
95
|
-
const by = env[CODEX_HOOK_VAR] || env.LEDGE_SESSION;
|
|
96
|
-
if (!by) return { line: "ledge task ne marche que dans une session lanc\xE9e par Ledge", code: 1 };
|
|
97
|
-
const deadline = Date.now() + (opts.timeoutMs ?? TASK_MS);
|
|
98
|
-
const left = () => Math.max(0, deadline - Date.now());
|
|
99
|
-
let client;
|
|
100
|
-
try {
|
|
101
|
-
client = await connect({ port: opts.port, timeoutMs: left() });
|
|
102
|
-
} catch {
|
|
103
|
-
return { line: "daemon not running (start a session with `ledge claude`, or run `ledge daemon`)", code: 1 };
|
|
104
|
-
}
|
|
105
|
-
try {
|
|
106
|
-
return await taskOnClient(client, args, by, left());
|
|
107
|
-
} finally {
|
|
108
|
-
await client.close();
|
|
109
|
-
}
|
|
110
|
-
}
|
|
111
|
-
|
|
112
|
-
export {
|
|
113
|
-
TASK_USAGE,
|
|
114
|
-
taskArgs,
|
|
115
|
-
formatTask,
|
|
116
|
-
taskOnClient,
|
|
117
|
-
runTask
|
|
118
|
-
};
|
|
@@ -1,60 +0,0 @@
|
|
|
1
|
-
import {
|
|
2
|
-
CODEX_HOOK_VAR
|
|
3
|
-
} from "./chunk-4TCSADFR.js";
|
|
4
|
-
import {
|
|
5
|
-
connect
|
|
6
|
-
} from "./chunk-7NHQGP6J.js";
|
|
7
|
-
import {
|
|
8
|
-
BRIEF_MAX
|
|
9
|
-
} from "./chunk-IWY7DSSO.js";
|
|
10
|
-
|
|
11
|
-
// src/cli/handover.ts
|
|
12
|
-
import { randomUUID } from "crypto";
|
|
13
|
-
var HANDOVER_USAGE = `ledge handover "<bilan>" ton bilan de rel\xE8ve, quand Ledge te le demande (fait, en cours, suite, pi\xE8ges, fichiers cl\xE9s)
|
|
14
|
-
ledge handover show relire le bilan de la session dont tu as pris la rel\xE8ve`;
|
|
15
|
-
var HANDOVER_MS = 4e3;
|
|
16
|
-
function handoverArgs(args) {
|
|
17
|
-
if (args.length === 1 && args[0] === "show") return { op: "show" };
|
|
18
|
-
const text = args.join(" ").trim();
|
|
19
|
-
if (!args.length || !text || text.length > BRIEF_MAX) return void 0;
|
|
20
|
-
return { op: "brief", text };
|
|
21
|
-
}
|
|
22
|
-
async function handoverOnClient(client, args, by, ms) {
|
|
23
|
-
const op = handoverArgs(args);
|
|
24
|
-
if (!op) return { line: HANDOVER_USAGE, code: 1 };
|
|
25
|
-
try {
|
|
26
|
-
const rid = randomUUID();
|
|
27
|
-
client.send(op.op === "show" ? { type: "handover.show", rid, by } : { type: "handover.brief", rid, by, text: op.text });
|
|
28
|
-
const r = await client.next("handover.result", ms);
|
|
29
|
-
if (r.reason !== void 0) return { line: `refus\xE9 : ${r.reason}`, code: 1 };
|
|
30
|
-
return op.op === "show" ? { line: r.text ?? "", code: 0 } : { line: "bilan re\xE7u : Ledge lance la session qui prend ta rel\xE8ve et lui passe tes t\xE2ches. Arr\xEAte-toi l\xE0.", code: 0 };
|
|
31
|
-
} catch (e) {
|
|
32
|
-
return { line: `pas de r\xE9ponse de Ledge : ${e.message}`, code: 1 };
|
|
33
|
-
}
|
|
34
|
-
}
|
|
35
|
-
async function runHandover(args, opts = {}) {
|
|
36
|
-
if (!handoverArgs(args)) return { line: HANDOVER_USAGE, code: args.length ? 1 : 0 };
|
|
37
|
-
const env = opts.env ?? process.env;
|
|
38
|
-
const by = env[CODEX_HOOK_VAR] || env.LEDGE_SESSION;
|
|
39
|
-
if (!by) return { line: "ledge handover ne marche que dans une session lanc\xE9e par Ledge", code: 1 };
|
|
40
|
-
const deadline = Date.now() + (opts.timeoutMs ?? HANDOVER_MS);
|
|
41
|
-
const left = () => Math.max(0, deadline - Date.now());
|
|
42
|
-
let client;
|
|
43
|
-
try {
|
|
44
|
-
client = await connect({ port: opts.port, timeoutMs: left() });
|
|
45
|
-
} catch {
|
|
46
|
-
return { line: "daemon not running (start a session with `ledge claude`, or run `ledge daemon`)", code: 1 };
|
|
47
|
-
}
|
|
48
|
-
try {
|
|
49
|
-
return await handoverOnClient(client, args, by, left());
|
|
50
|
-
} finally {
|
|
51
|
-
await client.close();
|
|
52
|
-
}
|
|
53
|
-
}
|
|
54
|
-
|
|
55
|
-
export {
|
|
56
|
-
HANDOVER_USAGE,
|
|
57
|
-
handoverArgs,
|
|
58
|
-
handoverOnClient,
|
|
59
|
-
runHandover
|
|
60
|
-
};
|
|
@@ -1,41 +0,0 @@
|
|
|
1
|
-
// src/transport/frames.ts
|
|
2
|
-
var MAX_FRAME = 4 * 1024 * 1024;
|
|
3
|
-
function readFrames(input, frame, fail) {
|
|
4
|
-
let buffer = "", stopped = false;
|
|
5
|
-
input.setEncoding("utf8");
|
|
6
|
-
const data = (chunk) => {
|
|
7
|
-
if (stopped) return;
|
|
8
|
-
buffer += chunk;
|
|
9
|
-
try {
|
|
10
|
-
let i;
|
|
11
|
-
while ((i = buffer.indexOf("\n")) >= 0) {
|
|
12
|
-
const line = buffer.slice(0, i);
|
|
13
|
-
buffer = buffer.slice(i + 1);
|
|
14
|
-
if (Buffer.byteLength(line) > MAX_FRAME) throw new Error("Ledge frame too large");
|
|
15
|
-
if (line.trim()) frame(JSON.parse(line));
|
|
16
|
-
}
|
|
17
|
-
if (Buffer.byteLength(buffer) > MAX_FRAME) throw new Error("Ledge frame too large");
|
|
18
|
-
} catch (e) {
|
|
19
|
-
stopped = true;
|
|
20
|
-
fail(e instanceof Error ? e : new Error(String(e)));
|
|
21
|
-
}
|
|
22
|
-
};
|
|
23
|
-
const end = () => {
|
|
24
|
-
if (!stopped && buffer.trim()) {
|
|
25
|
-
stopped = true;
|
|
26
|
-
fail(new Error("Incomplete Ledge frame"));
|
|
27
|
-
}
|
|
28
|
-
};
|
|
29
|
-
input.on("data", data);
|
|
30
|
-
input.on("end", end);
|
|
31
|
-
return () => {
|
|
32
|
-
stopped = true;
|
|
33
|
-
input.off("data", data);
|
|
34
|
-
input.off("end", end);
|
|
35
|
-
};
|
|
36
|
-
}
|
|
37
|
-
|
|
38
|
-
export {
|
|
39
|
-
MAX_FRAME,
|
|
40
|
-
readFrames
|
|
41
|
-
};
|
|
@@ -1,43 +0,0 @@
|
|
|
1
|
-
import {
|
|
2
|
-
connect
|
|
3
|
-
} from "./chunk-7NHQGP6J.js";
|
|
4
|
-
import {
|
|
5
|
-
isArchived
|
|
6
|
-
} from "./chunk-IWY7DSSO.js";
|
|
7
|
-
|
|
8
|
-
// src/cli/who.ts
|
|
9
|
-
import { basename } from "path";
|
|
10
|
-
function formatWho(sessions, self) {
|
|
11
|
-
const live = sessions.filter((s) => s.state !== "exited" && !isArchived(s));
|
|
12
|
-
if (live.length === 0) return "aucune autre session";
|
|
13
|
-
const rows = live.map((s) => [
|
|
14
|
-
s.id === self ? "*" : " ",
|
|
15
|
-
s.name,
|
|
16
|
-
s.tool,
|
|
17
|
-
s.state,
|
|
18
|
-
`${s.repo ?? s.project}${s.worktree ? ` (${basename(s.cwd)})` : ""}`,
|
|
19
|
-
s.branch ?? "-",
|
|
20
|
-
`${s.topic ?? "-"}${s.source === "hook_only" ? " \xB7 lecture seule" : ""}`
|
|
21
|
-
]);
|
|
22
|
-
const head = [" ", "NOM", "OUTIL", "\xC9TAT", "PROJET", "BRANCHE", "SUJET"];
|
|
23
|
-
const widths = head.map((h, i) => Math.max(h.length, ...rows.map((r) => r[i].length)));
|
|
24
|
-
return [head, ...rows].map((r) => r.map((c, i) => i === r.length - 1 ? c : c.padEnd(widths[i])).join(" ")).join("\n");
|
|
25
|
-
}
|
|
26
|
-
async function printWho(opts = {}) {
|
|
27
|
-
let client;
|
|
28
|
-
try {
|
|
29
|
-
client = await connect({ port: opts.port, timeoutMs: 800 });
|
|
30
|
-
} catch {
|
|
31
|
-
return "daemon not running (start a session with `ledge claude`, or run `ledge daemon`)";
|
|
32
|
-
}
|
|
33
|
-
try {
|
|
34
|
-
return formatWho((await client.next("snapshot")).sessions, opts.self ?? process.env.LEDGE_SESSION);
|
|
35
|
-
} finally {
|
|
36
|
-
await client.close();
|
|
37
|
-
}
|
|
38
|
-
}
|
|
39
|
-
|
|
40
|
-
export {
|
|
41
|
-
formatWho,
|
|
42
|
-
printWho
|
|
43
|
-
};
|
|
@@ -1,128 +0,0 @@
|
|
|
1
|
-
import {
|
|
2
|
-
log
|
|
3
|
-
} from "./chunk-54KF5RBY.js";
|
|
4
|
-
import {
|
|
5
|
-
paths
|
|
6
|
-
} from "./chunk-53ISXX2R.js";
|
|
7
|
-
|
|
8
|
-
// src/tmux.ts
|
|
9
|
-
import { execFile } from "child_process";
|
|
10
|
-
import { existsSync } from "fs";
|
|
11
|
-
import { join } from "path";
|
|
12
|
-
function runFile(file, args, env, opts) {
|
|
13
|
-
return new Promise((resolve) => {
|
|
14
|
-
execFile(file, args, { maxBuffer: 4 * 1024 * 1024, env, ...opts?.timeoutMs ? { timeout: opts.timeoutMs, killSignal: "SIGTERM" } : {} }, (err, stdout, stderr) => {
|
|
15
|
-
const code = err && opts?.timeoutMs && err.killed ? 124 : err && typeof err.code === "number" ? err.code : err ? 1 : 0;
|
|
16
|
-
resolve({ code, stdout: String(stdout), stderr: String(stderr) });
|
|
17
|
-
});
|
|
18
|
-
});
|
|
19
|
-
}
|
|
20
|
-
var run = (args, env) => runFile("tmux", args, env);
|
|
21
|
-
function systemdAvailable(env = process.env, exists = existsSync) {
|
|
22
|
-
return !!env.XDG_RUNTIME_DIR && exists(join(env.XDG_RUNTIME_DIR, "systemd", "private"));
|
|
23
|
-
}
|
|
24
|
-
function newSessionCommand(tmuxArgs, scoped, unit) {
|
|
25
|
-
if (!scoped) return { file: "tmux", args: tmuxArgs };
|
|
26
|
-
return { file: "systemd-run", args: ["--user", "--scope", "--quiet", "--collect", `--unit=${unit}`, "--", "tmux", ...tmuxArgs] };
|
|
27
|
-
}
|
|
28
|
-
function realTmux(socket = "ledge", opts = {}) {
|
|
29
|
-
const scope = opts.scope ?? (async () => systemdAvailable());
|
|
30
|
-
const base = () => socket === null ? [] : ["-L", socket, "-f", paths().tmuxConf];
|
|
31
|
-
const t = (args, env) => run([...base(), ...args], env);
|
|
32
|
-
return {
|
|
33
|
-
async newSession({ name, cwd, env, unset = [], command }) {
|
|
34
|
-
const envArgs = Object.entries(env).flatMap(([k, v]) => ["-e", `${k}=${v}`]);
|
|
35
|
-
if (unset.length) command = ["env", ...unset.flatMap((v) => ["-u", v]), ...command];
|
|
36
|
-
const clientEnv = env.PATH === void 0 ? void 0 : { ...process.env, PATH: env.PATH };
|
|
37
|
-
const args = [...base(), "new-session", "-d", "-s", name, "-c", cwd, "-x", "200", "-y", "50", ...envArgs, "--", ...command];
|
|
38
|
-
const serverUp = (await t(["list-sessions"])).code === 0;
|
|
39
|
-
const scoped = !serverUp && await scope();
|
|
40
|
-
const { file, args: argv } = newSessionCommand(args, scoped, `ledge-tmux-${Date.now()}`);
|
|
41
|
-
let r = await runFile(file, argv, clientEnv);
|
|
42
|
-
if (r.code !== 0 && scoped) {
|
|
43
|
-
log(`tmux: scoped start failed (${r.stderr.trim()}), starting unscoped`);
|
|
44
|
-
r = await runFile("tmux", args, clientEnv);
|
|
45
|
-
}
|
|
46
|
-
if (r.code !== 0) throw new Error(`tmux new-session failed: ${r.stderr.trim()}`);
|
|
47
|
-
},
|
|
48
|
-
async sendText(name, text) {
|
|
49
|
-
if (/[\r\n]/.test(text)) throw new Error("sendText: text must not contain newlines; flatten it first");
|
|
50
|
-
const arg = text.endsWith(";") ? `${text.slice(0, -1)}\\;` : text;
|
|
51
|
-
const r = await t(["send-keys", "-t", `=${name}:`, "-l", "--", arg]);
|
|
52
|
-
if (r.code !== 0) throw new Error(`tmux send-keys failed: ${r.stderr.trim()}`);
|
|
53
|
-
},
|
|
54
|
-
async sendKeys(name, keys) {
|
|
55
|
-
const r = await t(["send-keys", "-t", `=${name}:`, ...keys]);
|
|
56
|
-
if (r.code !== 0) throw new Error(`tmux send-keys failed: ${r.stderr.trim()}`);
|
|
57
|
-
},
|
|
58
|
-
async capture(name, lines) {
|
|
59
|
-
const r = await t(["capture-pane", "-p", "-J", "-t", `=${name}:`, "-S", String(-lines)]);
|
|
60
|
-
if (r.code !== 0) return null;
|
|
61
|
-
return r.stdout.replace(/\s+$/g, "").split("\n").slice(-lines).join("\n");
|
|
62
|
-
},
|
|
63
|
-
async width(name) {
|
|
64
|
-
const r = await t(["display-message", "-p", "-t", `=${name}:`, "#{pane_width}"]);
|
|
65
|
-
const n = Number(r.stdout.trim());
|
|
66
|
-
return r.code === 0 && Number.isInteger(n) && n > 0 ? n : null;
|
|
67
|
-
},
|
|
68
|
-
async hasSession(name) {
|
|
69
|
-
return (await t(["has-session", "-t", `=${name}`])).code === 0;
|
|
70
|
-
},
|
|
71
|
-
async paneCwd(name) {
|
|
72
|
-
const r = await t(["display-message", "-p", "-t", `=${name}:`, "#{pane_current_path}"]);
|
|
73
|
-
const p = r.stdout.trim();
|
|
74
|
-
return r.code === 0 && p.startsWith("/") ? p : null;
|
|
75
|
-
},
|
|
76
|
-
async listSessions() {
|
|
77
|
-
const r = await t(["list-sessions", "-F", "#{session_name}"]);
|
|
78
|
-
if (r.code === 0) return r.stdout.split("\n").map((s) => s.trim()).filter(Boolean);
|
|
79
|
-
if (/no server running|error connecting to/i.test(r.stderr)) return [];
|
|
80
|
-
throw new Error(`tmux list-sessions failed: ${r.stderr.trim()}`);
|
|
81
|
-
},
|
|
82
|
-
async setOption(name, option, value) {
|
|
83
|
-
const r = await t(["set-option", "-t", `=${name}:`, option, value]);
|
|
84
|
-
if (r.code !== 0) throw new Error(`tmux set-option failed: ${r.stderr.trim()}`);
|
|
85
|
-
},
|
|
86
|
-
async killSession(name) {
|
|
87
|
-
await t(["kill-session", "-t", `=${name}`]);
|
|
88
|
-
},
|
|
89
|
-
attachArgs(name, opts2) {
|
|
90
|
-
return [...base(), "attach-session", ...opts2?.readOnly ? ["-r"] : [], "-t", `=${name}`];
|
|
91
|
-
}
|
|
92
|
-
};
|
|
93
|
-
}
|
|
94
|
-
var isSeatSession = (name) => name.includes("@");
|
|
95
|
-
function routedTmux(own, seats) {
|
|
96
|
-
const of = (name) => isSeatSession(name) ? seats : own;
|
|
97
|
-
return {
|
|
98
|
-
newSession: (o) => own.newSession(o),
|
|
99
|
-
sendText: (n, text) => of(n).sendText(n, text),
|
|
100
|
-
sendKeys: (n, keys) => of(n).sendKeys(n, keys),
|
|
101
|
-
capture: (n, lines) => of(n).capture(n, lines),
|
|
102
|
-
width: async (n) => {
|
|
103
|
-
const t = of(n);
|
|
104
|
-
return t.width ? t.width(n) : null;
|
|
105
|
-
},
|
|
106
|
-
paneCwd: async (n) => {
|
|
107
|
-
const t = of(n);
|
|
108
|
-
return t.paneCwd ? t.paneCwd(n) : null;
|
|
109
|
-
},
|
|
110
|
-
hasSession: (n) => of(n).hasSession(n),
|
|
111
|
-
async listSessions() {
|
|
112
|
-
const mine = await own.listSessions();
|
|
113
|
-
const theirs = await seats.listSessions().catch(() => []);
|
|
114
|
-
return [...mine, ...theirs.filter(isSeatSession)];
|
|
115
|
-
},
|
|
116
|
-
killSession: (n) => of(n).killSession(n),
|
|
117
|
-
setOption: (n, option, value) => of(n).setOption(n, option, value),
|
|
118
|
-
attachArgs: (n, opts) => of(n).attachArgs(n, opts)
|
|
119
|
-
};
|
|
120
|
-
}
|
|
121
|
-
|
|
122
|
-
export {
|
|
123
|
-
runFile,
|
|
124
|
-
run,
|
|
125
|
-
realTmux,
|
|
126
|
-
isSeatSession,
|
|
127
|
-
routedTmux
|
|
128
|
-
};
|
|
@@ -1,35 +0,0 @@
|
|
|
1
|
-
var __create = Object.create;
|
|
2
|
-
var __defProp = Object.defineProperty;
|
|
3
|
-
var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
|
|
4
|
-
var __getOwnPropNames = Object.getOwnPropertyNames;
|
|
5
|
-
var __getProtoOf = Object.getPrototypeOf;
|
|
6
|
-
var __hasOwnProp = Object.prototype.hasOwnProperty;
|
|
7
|
-
var __commonJS = (cb, mod) => function __require() {
|
|
8
|
-
return mod || (0, cb[__getOwnPropNames(cb)[0]])((mod = { exports: {} }).exports, mod), mod.exports;
|
|
9
|
-
};
|
|
10
|
-
var __export = (target, all) => {
|
|
11
|
-
for (var name in all)
|
|
12
|
-
__defProp(target, name, { get: all[name], enumerable: true });
|
|
13
|
-
};
|
|
14
|
-
var __copyProps = (to, from, except, desc) => {
|
|
15
|
-
if (from && typeof from === "object" || typeof from === "function") {
|
|
16
|
-
for (let key of __getOwnPropNames(from))
|
|
17
|
-
if (!__hasOwnProp.call(to, key) && key !== except)
|
|
18
|
-
__defProp(to, key, { get: () => from[key], enumerable: !(desc = __getOwnPropDesc(from, key)) || desc.enumerable });
|
|
19
|
-
}
|
|
20
|
-
return to;
|
|
21
|
-
};
|
|
22
|
-
var __toESM = (mod, isNodeMode, target) => (target = mod != null ? __create(__getProtoOf(mod)) : {}, __copyProps(
|
|
23
|
-
// If the importer is in node compatibility mode or this is not an ESM
|
|
24
|
-
// file that has been converted to a CommonJS file using a Babel-
|
|
25
|
-
// compatible transform (i.e. "__esModule" has not been set), then set
|
|
26
|
-
// "default" to the CommonJS "module.exports" for node compatibility.
|
|
27
|
-
isNodeMode || !mod || !mod.__esModule ? __defProp(target, "default", { value: mod, enumerable: true }) : target,
|
|
28
|
-
mod
|
|
29
|
-
));
|
|
30
|
-
|
|
31
|
-
export {
|
|
32
|
-
__commonJS,
|
|
33
|
-
__export,
|
|
34
|
-
__toESM
|
|
35
|
-
};
|