deskbuddy 0.2.0-beta.35 → 0.2.0-beta.37
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.js +150 -26
- package/hook/hook-debug.log +42 -0
- package/package.json +1 -1
package/dist/cli.js
CHANGED
|
@@ -2890,13 +2890,40 @@ function singleCursor(lines3, q) {
|
|
|
2890
2890
|
if (m) {
|
|
2891
2891
|
const k = Number(m[1]) - 1;
|
|
2892
2892
|
if (k >= 0 && k < n) return squash(m[2]).startsWith(squash(q.options[k].label).slice(0, 6)) ? k : -1;
|
|
2893
|
-
if (k === n) return /^Typesomething
|
|
2893
|
+
if (k === n) return /^(Typesomething)?$/.test(squash(m[2])) ? n : -1;
|
|
2894
2894
|
return -1;
|
|
2895
2895
|
}
|
|
2896
2896
|
if (new RegExp(`^\\s*${CURSOR}\\s*(Next|Submit)\\s*$`).test(l)) return n + 1;
|
|
2897
2897
|
}
|
|
2898
2898
|
return -1;
|
|
2899
2899
|
}
|
|
2900
|
+
function typeLine(lines3, n) {
|
|
2901
|
+
const start = questionStart(lines3);
|
|
2902
|
+
if (start < 0) return -1;
|
|
2903
|
+
for (let i = start; i < lines3.length; i++) {
|
|
2904
|
+
const m = lines3[i].match(/^\s*(?:[❯>›]\s*)?[☐☒]?\s*(\d+)\.(?:\s|$)/);
|
|
2905
|
+
if (m && Number(m[1]) === n + 1) return i;
|
|
2906
|
+
}
|
|
2907
|
+
return -1;
|
|
2908
|
+
}
|
|
2909
|
+
function typedText(lines3, n) {
|
|
2910
|
+
const ln = typeLine(lines3, n);
|
|
2911
|
+
if (ln < 0) return null;
|
|
2912
|
+
const parts = [lines3[ln].replace(/^\s*(?:[❯>›]\s*)?[☐☒]?\s*\d+\./, "")];
|
|
2913
|
+
for (let i = ln + 1; i < lines3.length; i++) {
|
|
2914
|
+
if (new RegExp(`^\\s*(?:${CURSOR}\\s*)?(Submit|Next)\\s*$`).test(lines3[i]) || /^\s*(?:[❯>›]\s*)?[☐☒]?\s*\d+\./.test(lines3[i])) break;
|
|
2915
|
+
parts.push(lines3[i]);
|
|
2916
|
+
}
|
|
2917
|
+
return squash(parts.join(""));
|
|
2918
|
+
}
|
|
2919
|
+
async function typeOther(io, q, text) {
|
|
2920
|
+
const n = q.options.length;
|
|
2921
|
+
const want = squash(text);
|
|
2922
|
+
if (!want) return "no_focus";
|
|
2923
|
+
if (!await waitUntil(io, (l) => onQuestion(l, q) && typedText(l, n) === "")) return "no_focus";
|
|
2924
|
+
io.write(text);
|
|
2925
|
+
return await waitUntil(io, (l) => typedText(l, n) === want) ? "typed" : "mismatch";
|
|
2926
|
+
}
|
|
2900
2927
|
async function move(io, delta) {
|
|
2901
2928
|
const key = delta > 0 ? KEY_DOWN : KEY_UP;
|
|
2902
2929
|
for (let i = 0; i < Math.abs(delta); i++) {
|
|
@@ -2904,12 +2931,16 @@ async function move(io, delta) {
|
|
|
2904
2931
|
await io.sleep(ARROW_GAP_MS);
|
|
2905
2932
|
}
|
|
2906
2933
|
}
|
|
2907
|
-
async function answerQuestions(io, questions, selections) {
|
|
2934
|
+
async function answerQuestions(io, questions, selections, others) {
|
|
2908
2935
|
if (questions.length === 0 || selections.length !== questions.length) return "not_waiting";
|
|
2936
|
+
if (others !== void 0 && others.length !== questions.length) return "not_waiting";
|
|
2909
2937
|
for (let qi = 0; qi < questions.length; qi++) {
|
|
2910
2938
|
const sel = selections[qi];
|
|
2911
2939
|
const q = questions[qi];
|
|
2912
|
-
|
|
2940
|
+
const n = q.options.length;
|
|
2941
|
+
const other = others?.[qi] ?? "";
|
|
2942
|
+
if (sel.length === 0 || sel.some((i) => !Number.isInteger(i) || i < 0 || i > n)) return "not_waiting";
|
|
2943
|
+
if (sel.includes(n) !== (squash(other) !== "")) return "not_waiting";
|
|
2913
2944
|
if (q.multiSelect !== true && sel.length !== 1) return "not_waiting";
|
|
2914
2945
|
}
|
|
2915
2946
|
if (!await settled(io, (l) => onQuestion(l, questions[0]))) return "not_waiting";
|
|
@@ -2930,6 +2961,14 @@ async function answerQuestions(io, questions, selections) {
|
|
|
2930
2961
|
for (const t of sel) {
|
|
2931
2962
|
await move(io, t - cur);
|
|
2932
2963
|
cur = t;
|
|
2964
|
+
if (t === n) {
|
|
2965
|
+
const ty = await typeOther(io, q, others?.[qi] ?? "");
|
|
2966
|
+
if (ty !== "no_focus") wrote = true;
|
|
2967
|
+
if (ty !== "typed") return fail();
|
|
2968
|
+
io.write(KEY_ENTER);
|
|
2969
|
+
if (!await waitUntil(io, (l) => checked(l, typeLine(l, n)))) return fail();
|
|
2970
|
+
continue;
|
|
2971
|
+
}
|
|
2933
2972
|
const onTarget = await waitUntil(io, (l) => {
|
|
2934
2973
|
const ln = optionLine(l, t + 1, q.options[t].label);
|
|
2935
2974
|
return ln >= 0 && io.cursorLine?.() === ln;
|
|
@@ -2948,7 +2987,11 @@ async function answerQuestions(io, questions, selections) {
|
|
|
2948
2987
|
const cur = singleCursor(io.screen(), q);
|
|
2949
2988
|
if (cur < 0) return fail();
|
|
2950
2989
|
await move(io, t - cur);
|
|
2951
|
-
if (
|
|
2990
|
+
if (t === n) {
|
|
2991
|
+
const ty = await typeOther(io, q, others?.[qi] ?? "");
|
|
2992
|
+
if (ty !== "no_focus") wrote = true;
|
|
2993
|
+
if (ty !== "typed") return fail();
|
|
2994
|
+
} else if (!await waitUntil(io, (l) => singleCursor(l, q) === t && optionLine(l, t + 1, q.options[t].label) >= 0)) return fail();
|
|
2952
2995
|
io.write(KEY_ENTER);
|
|
2953
2996
|
wrote = true;
|
|
2954
2997
|
}
|
|
@@ -7806,7 +7849,14 @@ ${PRELUDE3}
|
|
|
7806
7849
|
}
|
|
7807
7850
|
}
|
|
7808
7851
|
if (C && typeof C.currentId === 'string') return { mode: 'dom', locale: localeOf(), why };
|
|
7809
|
-
|
|
7852
|
+
// 没有 SDK 时列出页面上像接口的全局名(258 退回:WorkBuddy 5.1.7 没有 wb,日志里据此判断老版本把接口放在哪)
|
|
7853
|
+
let globals;
|
|
7854
|
+
if (why === 'no_wb') {
|
|
7855
|
+
try {
|
|
7856
|
+
globals = Object.getOwnPropertyNames(globalThis).filter((k) => /wb|work|buddy|genie|sdk|electron|bridge|ipc|conv|agent|app/i.test(k) && !/^on/.test(k) && k.length <= 40).sort().slice(0, 30);
|
|
7857
|
+
} catch (e) { globals = undefined; }
|
|
7858
|
+
}
|
|
7859
|
+
return { mode: 'none', locale: localeOf(), why, ...(globals ? { globals } : {}) };
|
|
7810
7860
|
})()`;
|
|
7811
7861
|
var IDLE_STATES = "['idle','completed','cancelled','canceled','done','failed','error','terminated','archived','deleted','']";
|
|
7812
7862
|
var SNAPSHOT2 = String.raw`(async () => {
|
|
@@ -8249,7 +8299,10 @@ var WorkbuddyAppWatch = class {
|
|
|
8249
8299
|
this.#nonSdkSince = first && kept && now - kept.at < NON_SDK_KEEP_MS ? kept.since : now;
|
|
8250
8300
|
this.#nonSdkKept = null;
|
|
8251
8301
|
}
|
|
8252
|
-
if (first || prev !== this.#mode || prevWhy !== this.#modeWhy)
|
|
8302
|
+
if (first || prev !== this.#mode || prevWhy !== this.#modeWhy) {
|
|
8303
|
+
const g = Array.isArray(r?.globals) ? r.globals.filter((x) => typeof x === "string").map((x) => x.slice(0, 40)).slice(0, 30) : null;
|
|
8304
|
+
this.#d.log(`WorkBuddy App \u6388\u6743\u6865\u6A21\u5F0F\uFF1A${this.#mode}${this.#modeWhy ? `\uFF08${modeWhyText(this.#modeWhy)}\uFF09` : ""}${g ? `\uFF1B\u9875\u9762\u5168\u5C40\u540D\uFF1A${g.join(",") || "\u65E0"}` : ""}`);
|
|
8305
|
+
}
|
|
8253
8306
|
const cands = this.#client?.target?.candidates ?? 1;
|
|
8254
8307
|
if (this.#mode !== "sdk" && this.#modeWhy === "no_wb" && cands > 1 && this.#nonSdkSince && now - this.#nonSdkSince >= NO_SDK_REPROBE_MS && now - this.#reprobeAt >= NO_SDK_REPROBE_MS) {
|
|
8255
8308
|
this.#reprobeAt = now;
|
|
@@ -8518,7 +8571,7 @@ function modeWhyText(why) {
|
|
|
8518
8571
|
const msg = rest.join(":");
|
|
8519
8572
|
switch (k) {
|
|
8520
8573
|
case "no_wb":
|
|
8521
|
-
return "\u9875\u9762\u91CC\u6CA1\u6709 WorkBuddy SDK\uFF08globalThis.wb\uFF09";
|
|
8574
|
+
return "\u9875\u9762\u91CC\u6CA1\u6709 WorkBuddy SDK\uFF08globalThis.wb\uFF09\uFF0CWorkBuddy \u7248\u672C\u53EF\u80FD\u592A\u65E7\uFF0C\u5347\u7EA7\u5230\u6700\u65B0\u7248\u540E\u4EFB\u52A1\u624D\u80FD\u76F4\u63A5\u8FDB App";
|
|
8522
8575
|
case "no_conversations":
|
|
8523
8576
|
return "\u9875\u9762\u91CC\u6CA1\u6709\u4F1A\u8BDD\u63A5\u53E3\uFF08wb.conversations\uFF09";
|
|
8524
8577
|
case "no_list_get":
|
|
@@ -10455,14 +10508,28 @@ function parseAnswer(m) {
|
|
|
10455
10508
|
const questions = parseQuestions(a.questions);
|
|
10456
10509
|
const sel = a.selections;
|
|
10457
10510
|
if (!questions || sel.length !== questions.length) return null;
|
|
10511
|
+
let others;
|
|
10512
|
+
if (a.others !== void 0) {
|
|
10513
|
+
if (!Array.isArray(a.others) || a.others.length !== questions.length) return null;
|
|
10514
|
+
others = [];
|
|
10515
|
+
for (const o of a.others) {
|
|
10516
|
+
if (typeof o !== "string" || o.length > OTHER_MAX_CHARS || /[\u0000-\u001f\u007f-\u009f\u200b-\u200f\u202a-\u202e\u2066-\u2069\ufeff]/.test(o)) return null;
|
|
10517
|
+
others.push(o);
|
|
10518
|
+
}
|
|
10519
|
+
}
|
|
10458
10520
|
const selections = [];
|
|
10459
10521
|
for (let i = 0; i < questions.length; i++) {
|
|
10460
10522
|
const s2 = sel[i];
|
|
10461
|
-
|
|
10523
|
+
const n = questions[i].options.length;
|
|
10524
|
+
const other = others?.[i] ?? "";
|
|
10525
|
+
if (!Array.isArray(s2) || s2.length === 0 || !s2.every((x) => Number.isInteger(x) && x >= 0 && x <= n)) return null;
|
|
10526
|
+
if (s2.includes(n) !== (other.trim() !== "")) return null;
|
|
10527
|
+
if (new Set(s2).size !== s2.length) return null;
|
|
10462
10528
|
selections.push(s2);
|
|
10463
10529
|
}
|
|
10464
|
-
return { instructionId, sessionId, expireAt, answer: { kind: "question", questions, selections } };
|
|
10530
|
+
return { instructionId, sessionId, expireAt, answer: { kind: "question", questions, selections, ...others ? { others } : {} } };
|
|
10465
10531
|
}
|
|
10532
|
+
var OTHER_MAX_CHARS = 500;
|
|
10466
10533
|
function parseQuestions(v) {
|
|
10467
10534
|
if (!Array.isArray(v)) return null;
|
|
10468
10535
|
const qs = v;
|
|
@@ -10828,20 +10895,31 @@ function pendingCall(text, toolName) {
|
|
|
10828
10895
|
function selectionsOf(input, lists) {
|
|
10829
10896
|
const qs = Array.isArray(input.questions) ? input.questions : null;
|
|
10830
10897
|
if (!qs || !Array.isArray(lists) || lists.length !== qs.length) return null;
|
|
10831
|
-
const
|
|
10898
|
+
const selections = [];
|
|
10899
|
+
const others = [];
|
|
10832
10900
|
for (let i = 0; i < qs.length; i++) {
|
|
10833
10901
|
const opts = Array.isArray(qs[i]?.options) ? qs[i].options : [];
|
|
10834
10902
|
const items = lists[i];
|
|
10835
10903
|
if (!Array.isArray(items) || items.length === 0) return null;
|
|
10836
10904
|
const idx = [];
|
|
10837
|
-
|
|
10905
|
+
let other = "";
|
|
10906
|
+
for (let j = 0; j < items.length; j++) {
|
|
10907
|
+
const label = items[j];
|
|
10838
10908
|
const k = opts.findIndex((o) => o?.label === label);
|
|
10839
|
-
if (k
|
|
10840
|
-
|
|
10909
|
+
if (k >= 0) {
|
|
10910
|
+
if (!idx.includes(k)) idx.push(k);
|
|
10911
|
+
continue;
|
|
10912
|
+
}
|
|
10913
|
+
if (j !== items.length - 1 || typeof label !== "string") return null;
|
|
10914
|
+
other = label.replace(/[\u0000-\u001f\u007f-\u009f\u200b-\u200f\u202a-\u202e\u2066-\u2069\ufeff]+/g, " ").replace(/\s+/g, " ").trim();
|
|
10915
|
+
if (!other) return null;
|
|
10841
10916
|
}
|
|
10842
|
-
|
|
10917
|
+
if (other) idx.push(opts.length);
|
|
10918
|
+
if (qs[i]?.multiSelect !== true && idx.length !== 1) return null;
|
|
10919
|
+
selections.push(idx);
|
|
10920
|
+
others.push(other);
|
|
10843
10921
|
}
|
|
10844
|
-
return
|
|
10922
|
+
return { selections, others };
|
|
10845
10923
|
}
|
|
10846
10924
|
var WorkbuddyBridge = class {
|
|
10847
10925
|
#d;
|
|
@@ -10979,10 +11057,16 @@ var WorkbuddyBridge = class {
|
|
|
10979
11057
|
if (reply.decision !== "allow") return;
|
|
10980
11058
|
const sel = selectionsOf(card.input, reply.answerLists);
|
|
10981
11059
|
if (!sel) {
|
|
10982
|
-
this.#d.log(`WorkBuddy\uFF1A\u4F1A\u8BDD ${card.sessionId.slice(0, 8)} \u7684\u8BBE\u5907\u7B54\u6848\u5BF9\u4E0D\u4E0A\u9009\u9879\
|
|
11060
|
+
this.#d.log(`WorkBuddy\uFF1A\u4F1A\u8BDD ${card.sessionId.slice(0, 8)} \u7684\u8BBE\u5907\u7B54\u6848\u5BF9\u4E0D\u4E0A\u9009\u9879\uFF0C\u6846\u7559\u7ED9\u7535\u8111`);
|
|
10983
11061
|
return;
|
|
10984
11062
|
}
|
|
10985
|
-
|
|
11063
|
+
const withOther = sel.others.some((o) => o !== "");
|
|
11064
|
+
spec = {
|
|
11065
|
+
kind: "question",
|
|
11066
|
+
questions: card.input.questions,
|
|
11067
|
+
selections: sel.selections,
|
|
11068
|
+
...withOther ? { others: sel.others } : {}
|
|
11069
|
+
};
|
|
10986
11070
|
} else if (reply.decision === "allow" || reply.decision === "deny") {
|
|
10987
11071
|
spec = { kind: "permission", toolName: card.toolName, fingerprint: card.fingerprint, decision: reply.decision };
|
|
10988
11072
|
} else return;
|
|
@@ -13768,6 +13852,7 @@ function removeCodexRemote() {
|
|
|
13768
13852
|
import { closeSync as closeSync8, openSync as openSync8, readdirSync as readdirSync9, readSync as readSync7, statSync as statSync11 } from "fs";
|
|
13769
13853
|
import { dirname as dirname6, join as join22 } from "path";
|
|
13770
13854
|
var INTERRUPT_TOOLS = ["claude_code", "qoder_cn", "qoder"];
|
|
13855
|
+
var CODEX_INTERRUPT_TOOL = "codex";
|
|
13771
13856
|
function transcriptHome(tool) {
|
|
13772
13857
|
if (tool === "claude_code") return claudeHome();
|
|
13773
13858
|
if (tool === "qoder_cn") return dirname6(qoderCnSettingsPath());
|
|
@@ -13890,14 +13975,53 @@ function claudeTranscriptFile(sessionId, cwd, home = claudeHome()) {
|
|
|
13890
13975
|
var INTERRUPT_SETTLE_MS = 2e3;
|
|
13891
13976
|
var INTERRUPT_TOLERANCE_MS = 5e3;
|
|
13892
13977
|
function shouldSettleInterrupt(st, markerAt, now) {
|
|
13893
|
-
|
|
13978
|
+
const codex = st.tool === CODEX_INTERRUPT_TOOL;
|
|
13979
|
+
if (markerAt === null || !INTERRUPT_TOOLS.includes(st.tool) && !codex) return false;
|
|
13894
13980
|
if (st.state !== "watch" && st.state !== "ask_approval") return false;
|
|
13895
|
-
if (st.interactive !== true && st.embedded !== true) return false;
|
|
13981
|
+
if (!codex && st.interactive !== true && st.embedded !== true) return false;
|
|
13896
13982
|
if (now - markerAt < INTERRUPT_SETTLE_MS) return false;
|
|
13897
13983
|
if (st.updatedAt > markerAt + INTERRUPT_TOLERANCE_MS) return false;
|
|
13898
13984
|
if ((st.recent ?? []).some((r) => r.e === "UserPromptSubmit" && r.at > markerAt)) return false;
|
|
13899
13985
|
return true;
|
|
13900
13986
|
}
|
|
13987
|
+
function codexInterruptedAt(file) {
|
|
13988
|
+
let fd;
|
|
13989
|
+
try {
|
|
13990
|
+
const st = statSync11(file);
|
|
13991
|
+
const len = Math.min(st.size, TAIL);
|
|
13992
|
+
const buf = Buffer.alloc(len);
|
|
13993
|
+
fd = openSync8(file, "r");
|
|
13994
|
+
readSync7(fd, buf, 0, len, st.size - len);
|
|
13995
|
+
const lines3 = buf.toString("utf8").split("\n");
|
|
13996
|
+
for (let i = lines3.length - 1; i >= 0; i--) {
|
|
13997
|
+
const line = lines3[i];
|
|
13998
|
+
if (line.indexOf('"event_msg"') === -1) continue;
|
|
13999
|
+
let o;
|
|
14000
|
+
try {
|
|
14001
|
+
o = JSON.parse(line);
|
|
14002
|
+
} catch {
|
|
14003
|
+
continue;
|
|
14004
|
+
}
|
|
14005
|
+
if (!o || o.type !== "event_msg" || !o.payload) continue;
|
|
14006
|
+
const t = o.payload.type;
|
|
14007
|
+
if (t === "turn_aborted") {
|
|
14008
|
+
const at = typeof o.timestamp === "string" ? Date.parse(o.timestamp) : NaN;
|
|
14009
|
+
return Number.isFinite(at) ? at : st.mtimeMs;
|
|
14010
|
+
}
|
|
14011
|
+
if (t === "task_complete" || t === "turn_complete" || t === "task_started" || t === "turn_started" || t === "user_message") return null;
|
|
14012
|
+
}
|
|
14013
|
+
return null;
|
|
14014
|
+
} catch {
|
|
14015
|
+
return null;
|
|
14016
|
+
} finally {
|
|
14017
|
+
if (fd !== void 0) {
|
|
14018
|
+
try {
|
|
14019
|
+
closeSync8(fd);
|
|
14020
|
+
} catch {
|
|
14021
|
+
}
|
|
14022
|
+
}
|
|
14023
|
+
}
|
|
14024
|
+
}
|
|
13901
14025
|
|
|
13902
14026
|
// src/daemon/qoderAppDb.ts
|
|
13903
14027
|
import { execFile as execFile4 } from "child_process";
|
|
@@ -15668,7 +15792,7 @@ var Daemon = class {
|
|
|
15668
15792
|
#settleInterrupted() {
|
|
15669
15793
|
if (this.#stopped) return;
|
|
15670
15794
|
const enabled = loadConfig().enabledTools;
|
|
15671
|
-
const tools = INTERRUPT_TOOLS.filter((t) => enabled.includes(t));
|
|
15795
|
+
const tools = [...INTERRUPT_TOOLS, CODEX_INTERRUPT_TOOL].filter((t) => enabled.includes(t));
|
|
15672
15796
|
if (tools.length === 0) return;
|
|
15673
15797
|
const now = this.#deps.now();
|
|
15674
15798
|
const alive = /* @__PURE__ */ new Set();
|
|
@@ -15676,7 +15800,7 @@ var Daemon = class {
|
|
|
15676
15800
|
let changed = false;
|
|
15677
15801
|
for (const st of this.#aliveStates(tool)) {
|
|
15678
15802
|
alive.add(st.sessionId);
|
|
15679
|
-
if (!BUSY_STATES3.has(st.state) || st.interactive !== true && st.embedded !== true) {
|
|
15803
|
+
if (!BUSY_STATES3.has(st.state) || tool !== CODEX_INTERRUPT_TOOL && st.interactive !== true && st.embedded !== true) {
|
|
15680
15804
|
this.#transcriptSeen.delete(st.sessionId);
|
|
15681
15805
|
continue;
|
|
15682
15806
|
}
|
|
@@ -15688,16 +15812,16 @@ var Daemon = class {
|
|
|
15688
15812
|
if (!file) continue;
|
|
15689
15813
|
const sig = transcriptSig(file);
|
|
15690
15814
|
if (sig && this.#transcriptSeen.get(st.sessionId) === sig) continue;
|
|
15691
|
-
const at = interruptedAt(file);
|
|
15815
|
+
const at = tool === CODEX_INTERRUPT_TOOL ? codexInterruptedAt(file) : interruptedAt(file);
|
|
15692
15816
|
if (sig && (at === null || now - at >= INTERRUPT_SETTLE_MS)) this.#transcriptSeen.set(st.sessionId, sig);
|
|
15693
15817
|
if (at === null || !shouldSettleInterrupt(st, at, now)) continue;
|
|
15694
|
-
if (this.#settleBusy(st.sessionId, tool, st.updatedAt,
|
|
15818
|
+
if (this.#settleBusy(st.sessionId, tool, st.updatedAt, `${tool === CODEX_INTERRUPT_TOOL ? "\u88AB\u7528\u6237\u505C\u6B62" : "\u5728\u7A97\u53E3\u91CC\u88AB\u6253\u65AD"}\uFF08${tool} \u4E0D\u53D1 Stop\uFF09`)) {
|
|
15695
15819
|
changed = true;
|
|
15696
15820
|
this.#idleWindowAfterInterrupt(st.sessionId, tool, at);
|
|
15697
15821
|
this.#coord.settleInterruptedWindows(st.sessionId, at);
|
|
15698
15822
|
}
|
|
15699
15823
|
}
|
|
15700
|
-
if (changed) void this.#reportTool(tool);
|
|
15824
|
+
if (changed) void (tool === CODEX_INTERRUPT_TOOL ? this.#reportCodex() : this.#reportTool(tool));
|
|
15701
15825
|
}
|
|
15702
15826
|
for (const m of [this.#transcripts, this.#transcriptMiss, this.#transcriptSeen]) for (const k of [...m.keys()]) if (!alive.has(k)) m.delete(k);
|
|
15703
15827
|
}
|
|
@@ -15718,7 +15842,7 @@ var Daemon = class {
|
|
|
15718
15842
|
const missAt = this.#transcriptMiss.get(st.sessionId);
|
|
15719
15843
|
if (missAt !== void 0 && now - missAt < TRANSCRIPT_MISS_TTL_MS) return null;
|
|
15720
15844
|
const home = transcriptHome(st.tool);
|
|
15721
|
-
const f = home ? claudeTranscriptFile(st.sessionId, st.cwd, home) : null;
|
|
15845
|
+
const f = st.tool === CODEX_INTERRUPT_TOOL ? findCodexRollout(codexHome(), st.sessionId, 7) : home ? claudeTranscriptFile(st.sessionId, st.cwd, home) : null;
|
|
15722
15846
|
if (f) {
|
|
15723
15847
|
this.#transcripts.set(st.sessionId, f);
|
|
15724
15848
|
this.#transcriptMiss.delete(st.sessionId);
|
|
@@ -19667,7 +19791,7 @@ async function applyAnswer(req, io, trust) {
|
|
|
19667
19791
|
} else if (a.kind === "trust" && a.prompt !== "hooks" && trust?.widens) r = "not_waiting";
|
|
19668
19792
|
else if (a.kind === "trust") r = await answerTrust(keys, trust?.tool ?? "", a.decision, trust?.forms ?? [], a.prompt ?? "trust");
|
|
19669
19793
|
else if (a.kind === "permission") r = await answerPermission(keys, a.toolName, a.fingerprint, a.decision);
|
|
19670
|
-
else r = await answerQuestions(keys, a.questions, a.selections);
|
|
19794
|
+
else r = await answerQuestions(keys, a.questions, a.selections, a.others);
|
|
19671
19795
|
} catch {
|
|
19672
19796
|
r = "partial";
|
|
19673
19797
|
}
|
package/hook/hook-debug.log
CHANGED
|
@@ -338,3 +338,45 @@
|
|
|
338
338
|
2026-10-12T07:48:57.673Z [opencode] opencode 版本 读不出:带说明的拒绝不走新路由
|
|
339
339
|
2026-10-12T07:48:57.673Z [opencode] opencode 版本不确定支持带说明的拒绝,设备上的反馈没有带给模型
|
|
340
340
|
2026-10-12T07:49:00.208Z [opencode] 后台任务里的提问 que_r2 没法在设备上回答(后台任务不能提问,请在电脑上继续),已拒绝
|
|
341
|
+
2026-10-12T08:43:33.911Z [opencode] 回填选择题失败:/question/{requestID}/reply status=404
|
|
342
|
+
2026-10-12T08:43:38.975Z [opencode] opencode 版本 1.4.3:带说明的拒绝不走新路由
|
|
343
|
+
2026-10-12T08:43:38.975Z [opencode] opencode 版本不确定支持带说明的拒绝,设备上的反馈没有带给模型
|
|
344
|
+
2026-10-12T08:43:39.078Z [opencode] opencode 版本 读不出:带说明的拒绝不走新路由
|
|
345
|
+
2026-10-12T08:43:39.078Z [opencode] opencode 版本不确定支持带说明的拒绝,设备上的反馈没有带给模型
|
|
346
|
+
2026-10-12T08:43:41.400Z [opencode] 后台任务里的提问 que_r2 没法在设备上回答(后台任务不能提问,请在电脑上继续),已拒绝
|
|
347
|
+
2026-10-12T08:45:36.004Z [opencode] 回填选择题失败:/question/{requestID}/reply status=404
|
|
348
|
+
2026-10-12T08:45:40.986Z [opencode] opencode 版本 1.4.3:带说明的拒绝不走新路由
|
|
349
|
+
2026-10-12T08:45:40.986Z [opencode] opencode 版本不确定支持带说明的拒绝,设备上的反馈没有带给模型
|
|
350
|
+
2026-10-12T08:45:41.084Z [opencode] opencode 版本 读不出:带说明的拒绝不走新路由
|
|
351
|
+
2026-10-12T08:45:41.084Z [opencode] opencode 版本不确定支持带说明的拒绝,设备上的反馈没有带给模型
|
|
352
|
+
2026-10-12T08:45:43.292Z [opencode] 后台任务里的提问 que_r2 没法在设备上回答(后台任务不能提问,请在电脑上继续),已拒绝
|
|
353
|
+
2026-10-12T08:51:55.878Z [opencode] 回填选择题失败:/question/{requestID}/reply status=404
|
|
354
|
+
2026-10-12T08:52:01.359Z [opencode] opencode 版本 1.4.3:带说明的拒绝不走新路由
|
|
355
|
+
2026-10-12T08:52:01.360Z [opencode] opencode 版本不确定支持带说明的拒绝,设备上的反馈没有带给模型
|
|
356
|
+
2026-10-12T08:52:01.517Z [opencode] opencode 版本 读不出:带说明的拒绝不走新路由
|
|
357
|
+
2026-10-12T08:52:01.517Z [opencode] opencode 版本不确定支持带说明的拒绝,设备上的反馈没有带给模型
|
|
358
|
+
2026-10-12T08:52:04.661Z [opencode] 后台任务里的提问 que_r2 没法在设备上回答(后台任务不能提问,请在电脑上继续),已拒绝
|
|
359
|
+
2026-10-12T09:01:07.164Z [opencode] 回填选择题失败:/question/{requestID}/reply status=404
|
|
360
|
+
2026-10-12T09:01:12.193Z [opencode] opencode 版本 1.4.3:带说明的拒绝不走新路由
|
|
361
|
+
2026-10-12T09:01:12.194Z [opencode] opencode 版本不确定支持带说明的拒绝,设备上的反馈没有带给模型
|
|
362
|
+
2026-10-12T09:01:12.293Z [opencode] opencode 版本 读不出:带说明的拒绝不走新路由
|
|
363
|
+
2026-10-12T09:01:12.293Z [opencode] opencode 版本不确定支持带说明的拒绝,设备上的反馈没有带给模型
|
|
364
|
+
2026-10-12T09:01:14.613Z [opencode] 后台任务里的提问 que_r2 没法在设备上回答(后台任务不能提问,请在电脑上继续),已拒绝
|
|
365
|
+
2026-10-12T10:52:32.632Z [opencode] 回填选择题失败:/question/{requestID}/reply status=404
|
|
366
|
+
2026-10-12T10:52:37.625Z [opencode] opencode 版本 1.4.3:带说明的拒绝不走新路由
|
|
367
|
+
2026-10-12T10:52:37.625Z [opencode] opencode 版本不确定支持带说明的拒绝,设备上的反馈没有带给模型
|
|
368
|
+
2026-10-12T10:52:37.718Z [opencode] opencode 版本 读不出:带说明的拒绝不走新路由
|
|
369
|
+
2026-10-12T10:52:37.719Z [opencode] opencode 版本不确定支持带说明的拒绝,设备上的反馈没有带给模型
|
|
370
|
+
2026-10-12T10:52:40.546Z [opencode] 后台任务里的提问 que_r2 没法在设备上回答(后台任务不能提问,请在电脑上继续),已拒绝
|
|
371
|
+
2026-10-12T10:56:52.376Z [opencode] 回填选择题失败:/question/{requestID}/reply status=404
|
|
372
|
+
2026-10-12T10:56:57.350Z [opencode] opencode 版本 1.4.3:带说明的拒绝不走新路由
|
|
373
|
+
2026-10-12T10:56:57.350Z [opencode] opencode 版本不确定支持带说明的拒绝,设备上的反馈没有带给模型
|
|
374
|
+
2026-10-12T10:56:57.454Z [opencode] opencode 版本 读不出:带说明的拒绝不走新路由
|
|
375
|
+
2026-10-12T10:56:57.454Z [opencode] opencode 版本不确定支持带说明的拒绝,设备上的反馈没有带给模型
|
|
376
|
+
2026-10-12T10:56:59.731Z [opencode] 后台任务里的提问 que_r2 没法在设备上回答(后台任务不能提问,请在电脑上继续),已拒绝
|
|
377
|
+
2026-10-12T11:00:08.567Z [opencode] 回填选择题失败:/question/{requestID}/reply status=404
|
|
378
|
+
2026-10-12T11:00:13.510Z [opencode] opencode 版本 1.4.3:带说明的拒绝不走新路由
|
|
379
|
+
2026-10-12T11:00:13.510Z [opencode] opencode 版本不确定支持带说明的拒绝,设备上的反馈没有带给模型
|
|
380
|
+
2026-10-12T11:00:13.614Z [opencode] opencode 版本 读不出:带说明的拒绝不走新路由
|
|
381
|
+
2026-10-12T11:00:13.614Z [opencode] opencode 版本不确定支持带说明的拒绝,设备上的反馈没有带给模型
|
|
382
|
+
2026-10-12T11:00:15.993Z [opencode] 后台任务里的提问 que_r2 没法在设备上回答(后台任务不能提问,请在电脑上继续),已拒绝
|