wormclaude 1.0.130 → 1.0.132
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/inlinetools.js +20 -7
- package/dist/theme.js +1 -1
- package/dist/tools.js +66 -19
- package/package.json +1 -1
package/dist/inlinetools.js
CHANGED
|
@@ -206,16 +206,29 @@ export function recoverInlineToolCalls(text) {
|
|
|
206
206
|
}
|
|
207
207
|
}
|
|
208
208
|
// 4) AskUserQuestion'ı JSON yerine DÜZ-METİN (prose) yazan model (abliterated):
|
|
209
|
-
// AskUserQuestion question "X" with options [A · B · C]
|
|
209
|
+
// AskUserQuestion question "X" with options ["A","B"] | [A · B · C] → gerçek çağrıya çevir.
|
|
210
210
|
if (!out.length && /AskUserQuestion/i.test(t)) {
|
|
211
|
-
const m = t.match(/AskUserQuestion[\s\S]*?["“]([^"”]{3,}?)["”][\s\S]
|
|
211
|
+
const m = t.match(/AskUserQuestion[\s\S]*?["“]([^"”]{3,}?)["”][\s\S]*?(\[[\s\S]*?\])/i);
|
|
212
212
|
if (m) {
|
|
213
213
|
const question = m[1].trim();
|
|
214
|
-
|
|
215
|
-
|
|
216
|
-
|
|
217
|
-
|
|
218
|
-
|
|
214
|
+
let options = [];
|
|
215
|
+
// Önce gerçek JSON array dene (model çoğunlukla ["A","B/C","D"] yazıyor → "/" ile BÖLME).
|
|
216
|
+
const arr = safeJsonParse(m[2], null);
|
|
217
|
+
if (Array.isArray(arr)) {
|
|
218
|
+
options = arr
|
|
219
|
+
.map((x) => (typeof x === 'string' ? x.trim() : (x && (x.label || x.value || x.text) ? String(x.label || x.value || x.text).trim() : '')))
|
|
220
|
+
.filter(Boolean)
|
|
221
|
+
.map((label) => ({ label }));
|
|
222
|
+
}
|
|
223
|
+
// JSON değilse ayraçla böl ("·•|," ve 2+ boşluk — "/" YOK, "İşletme/Teknoloji" bölünmesin).
|
|
224
|
+
if (options.length < 2) {
|
|
225
|
+
options = m[2]
|
|
226
|
+
.replace(/^\[|\]$/g, '')
|
|
227
|
+
.split(/\s*[·•|,]\s*|\s{2,}/)
|
|
228
|
+
.map((s) => s.trim().replace(/^["'“]|["'”]$/g, ''))
|
|
229
|
+
.filter(Boolean)
|
|
230
|
+
.map((label) => ({ label }));
|
|
231
|
+
}
|
|
219
232
|
if (options.length >= 2)
|
|
220
233
|
push({ name: 'AskUserQuestion', arguments: { question, options } });
|
|
221
234
|
}
|
package/dist/theme.js
CHANGED
package/dist/tools.js
CHANGED
|
@@ -2,7 +2,7 @@
|
|
|
2
2
|
// OpenAI function şemaları + Node executor'ları. Açıklamalar ve davranışlar
|
|
3
3
|
// WormClaude'un gerçek prompt.ts/şemalarından alınmıştır; sadece marka adı ve
|
|
4
4
|
// WormClaude'da bulunmayan araç referansları (Agent tool, sandbox) uyarlandı.
|
|
5
|
-
import {
|
|
5
|
+
import { spawn } from 'node:child_process';
|
|
6
6
|
import * as fs from 'node:fs';
|
|
7
7
|
import * as os from 'node:os';
|
|
8
8
|
import * as path from 'node:path';
|
|
@@ -51,18 +51,47 @@ export function resolveWs(fp) {
|
|
|
51
51
|
const _webFetchCache = new Map();
|
|
52
52
|
// Komutu çalıştırır ve sonrasında cwd değişikliğini (cd) yakalayıp bashCwd'yi günceller.
|
|
53
53
|
// POSIX: pwd'yi temp dosyaya yazan, çıkış kodunu KORUYAN sarmalayıcı (hata propagasyonu bozulmaz).
|
|
54
|
+
// ── ASYNC shell çalıştırıcı — KRİTİK: event-loop'u BLOKLAMAZ ────────────────
|
|
55
|
+
// Eskiden spawnSync/execSync (SENKRON) kullanılıyordu → uzun komut (npm install vb.)
|
|
56
|
+
// boyunca tüm Node event-loop'u kilitleniyor, spinner+girdi DAHİL her şey donuyordu
|
|
57
|
+
// ("8 saattir donma" şikayetinin kök sebebi buydu). spawn (async) ile komut arkada
|
|
58
|
+
// çalışırken UI canlı kalır. stdout+stderr ayrı yakalanır (curl progress sızmaz).
|
|
59
|
+
const _SHELL_CAP = 10 * 1024 * 1024;
|
|
60
|
+
function _spawnAsync(command, timeout, spawnOpts) {
|
|
61
|
+
return new Promise((resolve, reject) => {
|
|
62
|
+
let child;
|
|
63
|
+
try {
|
|
64
|
+
child = spawn(command, spawnOpts);
|
|
65
|
+
}
|
|
66
|
+
catch (e) {
|
|
67
|
+
return reject(e);
|
|
68
|
+
}
|
|
69
|
+
let out = '';
|
|
70
|
+
let killed = false;
|
|
71
|
+
const to = setTimeout(() => { killed = true; try {
|
|
72
|
+
child.kill();
|
|
73
|
+
}
|
|
74
|
+
catch { /* */ } }, timeout);
|
|
75
|
+
const onData = (d) => { if (out.length < _SHELL_CAP)
|
|
76
|
+
out += d.toString(); };
|
|
77
|
+
child.stdout?.on('data', onData);
|
|
78
|
+
child.stderr?.on('data', onData);
|
|
79
|
+
child.on('error', (e) => { clearTimeout(to); reject(e); });
|
|
80
|
+
child.on('close', (code) => { clearTimeout(to); resolve({ out, code, killed }); });
|
|
81
|
+
});
|
|
82
|
+
}
|
|
83
|
+
function _timeoutErr(out, timeout) {
|
|
84
|
+
const e = new Error((out ? out + '\n' : '') +
|
|
85
|
+
`[Komut ${Math.round(timeout / 1000)}sn icinde bitmedi ve durduruldu — uzun sureli/sunucu komutuysa run_in_background ile arka planda calistir.]`);
|
|
86
|
+
e.stdout = out;
|
|
87
|
+
e.timedOut = true;
|
|
88
|
+
return e;
|
|
89
|
+
}
|
|
54
90
|
// Windows: komutu olduğu gibi çalıştır, sonra baştaki `cd <hedef>`'i regex ile yakala (best-effort).
|
|
55
|
-
function runBashCapturingCwd(command, timeout) {
|
|
91
|
+
async function runBashCapturingCwd(command, timeout) {
|
|
56
92
|
const cwd = getBashCwd();
|
|
57
|
-
const opts = { encoding: 'utf8', timeout, maxBuffer: 10 * 1024 * 1024, windowsHide: true, cwd };
|
|
58
93
|
if (process.platform === 'win32') {
|
|
59
|
-
|
|
60
|
-
// meter'ı terminale sızmaz. execSync stderr'i inherit ederdi; `2>&1` ise zincirli (A && B)
|
|
61
|
-
// komutlarda yalnız SON komutun stderr'ini yakalıyordu (ilkininki sızıyordu).
|
|
62
|
-
const r = spawnSync(command, { ...opts, shell: true });
|
|
63
|
-
if (r.error)
|
|
64
|
-
throw r.error;
|
|
65
|
-
const out = (r.stdout || '') + (r.stderr || '');
|
|
94
|
+
const { out, code, killed } = await _spawnAsync(command, timeout, { shell: true, windowsHide: true, cwd });
|
|
66
95
|
// best-effort: "cd <hedef>" / "cd /d <hedef>" (zincirsiz tek komut)
|
|
67
96
|
const m = /^\s*cd\s+(?:\/d\s+)?"?([^"&|<>]+?)"?\s*$/i.exec(command);
|
|
68
97
|
if (m) {
|
|
@@ -73,10 +102,12 @@ function runBashCapturingCwd(command, timeout) {
|
|
|
73
102
|
}
|
|
74
103
|
catch { /* yok say */ }
|
|
75
104
|
}
|
|
76
|
-
if (
|
|
77
|
-
|
|
105
|
+
if (killed)
|
|
106
|
+
throw _timeoutErr(out, timeout);
|
|
107
|
+
if (typeof code === 'number' && code !== 0) {
|
|
108
|
+
const e = new Error(out || `Command failed (exit ${code})`);
|
|
78
109
|
e.stdout = out;
|
|
79
|
-
e.status =
|
|
110
|
+
e.status = code;
|
|
80
111
|
throw e;
|
|
81
112
|
}
|
|
82
113
|
return out;
|
|
@@ -85,7 +116,16 @@ function runBashCapturingCwd(command, timeout) {
|
|
|
85
116
|
const pwdFile = path.join(os.tmpdir(), `wc_pwd_${process.pid}_${Date.now()}.tmp`);
|
|
86
117
|
const wrapped = `{ ${command}\n}; __wc=$?; pwd > '${pwdFile}' 2>/dev/null; exit $__wc`;
|
|
87
118
|
try {
|
|
88
|
-
|
|
119
|
+
const { out, code, killed } = await _spawnAsync(wrapped, timeout, { shell: '/bin/sh', cwd });
|
|
120
|
+
if (killed)
|
|
121
|
+
throw _timeoutErr(out, timeout);
|
|
122
|
+
if (typeof code === 'number' && code !== 0) {
|
|
123
|
+
const e = new Error(out || `Command failed (exit ${code})`);
|
|
124
|
+
e.stdout = out;
|
|
125
|
+
e.status = code;
|
|
126
|
+
throw e;
|
|
127
|
+
}
|
|
128
|
+
return out;
|
|
89
129
|
}
|
|
90
130
|
finally {
|
|
91
131
|
try {
|
|
@@ -998,7 +1038,7 @@ export async function executeTool(name, args) {
|
|
|
998
1038
|
let timeout = Number(args.timeout) || DEFAULT_BASH_TIMEOUT_MS;
|
|
999
1039
|
if (timeout > MAX_BASH_TIMEOUT_MS)
|
|
1000
1040
|
timeout = MAX_BASH_TIMEOUT_MS;
|
|
1001
|
-
const out = runBashCapturingCwd(String(args.command), timeout);
|
|
1041
|
+
const out = await runBashCapturingCwd(String(args.command), timeout);
|
|
1002
1042
|
return { ok: true, output: (out || '(no output)').slice(0, 20000) };
|
|
1003
1043
|
}
|
|
1004
1044
|
if (name === 'Agent') {
|
|
@@ -1349,9 +1389,12 @@ export async function executeTool(name, args) {
|
|
|
1349
1389
|
if (timeout > MAX_BASH_TIMEOUT_MS)
|
|
1350
1390
|
timeout = MAX_BASH_TIMEOUT_MS;
|
|
1351
1391
|
const cmd = String(args.command).replace(/"/g, '\\"');
|
|
1352
|
-
|
|
1353
|
-
|
|
1354
|
-
|
|
1392
|
+
// ASYNC — event-loop'u bloklamaz (eski execSync donmaya sebep oluyordu).
|
|
1393
|
+
const { out, code, killed } = await _spawnAsync(`powershell -NoProfile -NonInteractive -Command "${cmd}"`, timeout, { shell: true, windowsHide: true, cwd: getBashCwd() });
|
|
1394
|
+
if (killed)
|
|
1395
|
+
return { ok: false, output: _timeoutErr(out, timeout).message };
|
|
1396
|
+
if (typeof code === 'number' && code !== 0)
|
|
1397
|
+
return { ok: false, output: out || `PowerShell failed (exit ${code})` };
|
|
1355
1398
|
return { ok: true, output: (out || '(no output)').slice(0, 20000) };
|
|
1356
1399
|
}
|
|
1357
1400
|
if (name === 'NotebookEdit') {
|
|
@@ -1390,7 +1433,11 @@ export async function executeTool(name, args) {
|
|
|
1390
1433
|
fs.writeFileSync(tmp, String(args.code || ''));
|
|
1391
1434
|
try {
|
|
1392
1435
|
const cmd = lang === 'python' ? `python "${tmp}"` : `node "${tmp}"`;
|
|
1393
|
-
const out =
|
|
1436
|
+
const { out, code, killed } = await _spawnAsync(cmd, 60000, { shell: true, windowsHide: true, cwd: getBashCwd() });
|
|
1437
|
+
if (killed)
|
|
1438
|
+
return { ok: false, output: _timeoutErr(out, 60000).message };
|
|
1439
|
+
if (typeof code === 'number' && code !== 0)
|
|
1440
|
+
return { ok: false, output: (out || `exit ${code}`).slice(0, 15000) };
|
|
1394
1441
|
return { ok: true, output: (out || '(no output)').slice(0, 15000) };
|
|
1395
1442
|
}
|
|
1396
1443
|
catch (e) {
|