engine7 7.1.29 → 7.1.30
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.mjs
CHANGED
|
@@ -1,7 +1,12 @@
|
|
|
1
1
|
var __defProp = Object.defineProperty;
|
|
2
2
|
var __getOwnPropNames = Object.getOwnPropertyNames;
|
|
3
|
-
var __esm = (fn, res) => function __init() {
|
|
4
|
-
|
|
3
|
+
var __esm = (fn, res, err) => function __init() {
|
|
4
|
+
if (err) throw err[0];
|
|
5
|
+
try {
|
|
6
|
+
return fn && (res = (0, fn[__getOwnPropNames(fn)[0]])(fn = 0)), res;
|
|
7
|
+
} catch (e) {
|
|
8
|
+
throw err = [e], e;
|
|
9
|
+
}
|
|
5
10
|
};
|
|
6
11
|
var __export = (target, all) => {
|
|
7
12
|
for (var name in all)
|
|
@@ -1332,13 +1337,253 @@ engine7 start \u2014 \u542F\u52A8 Engine
|
|
|
1332
1337
|
} catch {
|
|
1333
1338
|
}
|
|
1334
1339
|
console.log("");
|
|
1340
|
+
const envForChild = { ...process.env };
|
|
1341
|
+
const secretsDir = path2.join(process.env.HOME || process.env.USERPROFILE || ".", ".engine7-secrets");
|
|
1342
|
+
const cfgBase = path2.basename(configPath2, ".json");
|
|
1343
|
+
const secretCandidates = [
|
|
1344
|
+
path2.join(secretsDir, `${cfgBase}.env`),
|
|
1345
|
+
path2.join(path2.dirname(configPath2), `.env.${cfgBase}`),
|
|
1346
|
+
path2.join(path2.dirname(configPath2), ".env")
|
|
1347
|
+
];
|
|
1348
|
+
for (const secretPath of secretCandidates) {
|
|
1349
|
+
if (fs2.existsSync(secretPath)) {
|
|
1350
|
+
const content = fs2.readFileSync(secretPath, "utf-8");
|
|
1351
|
+
for (const line of content.split("\n")) {
|
|
1352
|
+
const trimmed = line.trim();
|
|
1353
|
+
if (!trimmed || trimmed.startsWith("#")) continue;
|
|
1354
|
+
const eq = trimmed.indexOf("=");
|
|
1355
|
+
if (eq > 0) {
|
|
1356
|
+
const k = trimmed.slice(0, eq).trim();
|
|
1357
|
+
const v = trimmed.slice(eq + 1).trim();
|
|
1358
|
+
if (k && !(k in envForChild)) envForChild[k] = v;
|
|
1359
|
+
}
|
|
1360
|
+
}
|
|
1361
|
+
console.log(`[start] Loaded API keys from ${secretPath}`);
|
|
1362
|
+
break;
|
|
1363
|
+
}
|
|
1364
|
+
}
|
|
1335
1365
|
const child = spawn(process.execPath, [enginePath, "--engine-config", configPath2], {
|
|
1336
1366
|
stdio: "inherit",
|
|
1337
|
-
shell: false
|
|
1367
|
+
shell: false,
|
|
1368
|
+
env: envForChild
|
|
1338
1369
|
});
|
|
1339
1370
|
child.on("exit", (code) => process.exit(code ?? 1));
|
|
1340
1371
|
return;
|
|
1341
1372
|
}
|
|
1373
|
+
if (subcommand === "session") {
|
|
1374
|
+
const action = args[1];
|
|
1375
|
+
if (!action || action === "--help" || action === "-h") {
|
|
1376
|
+
console.log(`
|
|
1377
|
+
engine7 session \u2014 \u4F1A\u8BDD\u7BA1\u7406\u5DE5\u5177
|
|
1378
|
+
|
|
1379
|
+
\u7528\u6CD5:
|
|
1380
|
+
engine7 session reset --config <path> [--mode archive|drop-last|strip-images] [--n N] [--restart]
|
|
1381
|
+
|
|
1382
|
+
\u6A21\u5F0F:
|
|
1383
|
+
archive \u5F52\u6863\u6574\u4E2A\u4F1A\u8BDD\uFF0C\u91CD\u542F\u540E\u4ECE\u7A7A\u767D\u5F00\u59CB
|
|
1384
|
+
drop-last \u780D\u6700\u8FD1 N \u8F6E\u5BF9\u8BDD\uFF08\u9ED8\u8BA4 N=3\uFF09\uFF0C\u4FDD\u7559\u66F4\u65E9\u7684\u5386\u53F2
|
|
1385
|
+
strip-images \u53EA\u6458\u9664 image block / [\u56FE\u7247\xD7N] \u6807\u8BB0\uFF0C\u4FDD\u7559\u6587\u5B57\uFF08\u6025\u6551\u654F\u611F\u56FE\uFF09
|
|
1386
|
+
|
|
1387
|
+
\u9009\u9879:
|
|
1388
|
+
--config <path> config \u6587\u4EF6\u8DEF\u5F84\uFF08\u5FC5\u987B\u6307\u5B9A\uFF09
|
|
1389
|
+
--mode <mode> \u91CD\u7F6E\u6A21\u5F0F\uFF08\u9ED8\u8BA4: archive\uFF09
|
|
1390
|
+
--n <N> drop-last \u6A21\u5F0F\u780D\u51E0\u8F6E\uFF08\u9ED8\u8BA4: 3\uFF09
|
|
1391
|
+
--restart \u6539\u5B8C\u81EA\u52A8 kill + \u62C9\u8D77 engine
|
|
1392
|
+
-h, --help \u663E\u793A\u5E2E\u52A9
|
|
1393
|
+
`);
|
|
1394
|
+
process.exit(0);
|
|
1395
|
+
}
|
|
1396
|
+
if (action === "reset") {
|
|
1397
|
+
const { execSync: execSync2 } = await import("node:child_process");
|
|
1398
|
+
let configPath2 = "";
|
|
1399
|
+
let mode = "archive";
|
|
1400
|
+
let dropN = 3;
|
|
1401
|
+
let autoRestart = false;
|
|
1402
|
+
for (let i = 2; i < args.length; i++) {
|
|
1403
|
+
if (args[i] === "--config" && args[i + 1]) {
|
|
1404
|
+
configPath2 = args[++i];
|
|
1405
|
+
} else if (args[i] === "--mode" && args[i + 1]) {
|
|
1406
|
+
mode = args[++i];
|
|
1407
|
+
} else if (args[i] === "--n" && args[i + 1]) {
|
|
1408
|
+
dropN = parseInt(args[++i], 10);
|
|
1409
|
+
} else if (args[i] === "--restart") {
|
|
1410
|
+
autoRestart = true;
|
|
1411
|
+
} else if (args[i] === "-h" || args[i] === "--help") {
|
|
1412
|
+
console.log(`engine7 session reset --config <path> [--mode archive|drop-last|strip-images] [--n N] [--restart]`);
|
|
1413
|
+
process.exit(0);
|
|
1414
|
+
}
|
|
1415
|
+
}
|
|
1416
|
+
if (!configPath2) {
|
|
1417
|
+
console.error("\u274C \u5FC5\u987B\u6307\u5B9A --config <path>");
|
|
1418
|
+
process.exit(1);
|
|
1419
|
+
}
|
|
1420
|
+
if (!["archive", "drop-last", "strip-images"].includes(mode)) {
|
|
1421
|
+
console.error(`\u274C \u672A\u77E5\u6A21\u5F0F: ${mode}\uFF08\u53EF\u9009: archive / drop-last / strip-images\uFF09`);
|
|
1422
|
+
process.exit(1);
|
|
1423
|
+
}
|
|
1424
|
+
const configRaw = JSON.parse(fs2.readFileSync(configPath2, "utf-8"));
|
|
1425
|
+
const stateDir = configRaw.stateDir;
|
|
1426
|
+
if (!stateDir) {
|
|
1427
|
+
console.error("\u274C config \u91CC\u6CA1\u6709 stateDir");
|
|
1428
|
+
process.exit(1);
|
|
1429
|
+
}
|
|
1430
|
+
const sessionsDir = path2.join(stateDir, "agents", "main", "sessions");
|
|
1431
|
+
if (!fs2.existsSync(sessionsDir)) {
|
|
1432
|
+
console.error(`\u274C sessions \u76EE\u5F55\u4E0D\u5B58\u5728: ${sessionsDir}`);
|
|
1433
|
+
process.exit(1);
|
|
1434
|
+
}
|
|
1435
|
+
console.log(`\u{1F504} session reset`);
|
|
1436
|
+
console.log(` config: ${configPath2}`);
|
|
1437
|
+
console.log(` mode: ${mode}`);
|
|
1438
|
+
if (mode === "drop-last") console.log(` n: ${dropN}`);
|
|
1439
|
+
const platformMapPath = path2.join(sessionsDir, "platform-map.json");
|
|
1440
|
+
const indexPath = path2.join(sessionsDir, "session-index.json");
|
|
1441
|
+
let sessionFileUUID = null;
|
|
1442
|
+
if (fs2.existsSync(indexPath)) {
|
|
1443
|
+
const index = JSON.parse(fs2.readFileSync(indexPath, "utf-8"));
|
|
1444
|
+
const entries = Object.values(index);
|
|
1445
|
+
if (entries.length > 0) {
|
|
1446
|
+
const fileVal = entries[0].file || "";
|
|
1447
|
+
sessionFileUUID = path2.isAbsolute(fileVal) ? path2.basename(fileVal, ".jsonl") : fileVal.replace(".jsonl", "");
|
|
1448
|
+
}
|
|
1449
|
+
}
|
|
1450
|
+
if (!sessionFileUUID) {
|
|
1451
|
+
const jsonlFiles = fs2.readdirSync(sessionsDir).filter((f) => f.endsWith(".jsonl") && !f.includes(".archived.") && !f.includes(".compaction.")).map((f) => ({ name: f, mtime: fs2.statSync(path2.join(sessionsDir, f)).mtimeMs })).sort((a, b) => b.mtime - a.mtime);
|
|
1452
|
+
if (jsonlFiles.length === 0) {
|
|
1453
|
+
console.error("\u274C \u627E\u4E0D\u5230\u6D3B\u8DC3\u7684 session JSONL \u6587\u4EF6");
|
|
1454
|
+
process.exit(1);
|
|
1455
|
+
}
|
|
1456
|
+
sessionFileUUID = jsonlFiles[0].name.replace(".jsonl", "");
|
|
1457
|
+
}
|
|
1458
|
+
let jsonlPath = path2.join(sessionsDir, `${sessionFileUUID}.jsonl`);
|
|
1459
|
+
if (!fs2.existsSync(jsonlPath)) {
|
|
1460
|
+
const jsonlFiles = fs2.readdirSync(sessionsDir).filter((f) => f.endsWith(".jsonl") && !f.includes(".archived.") && !f.includes(".compaction.")).map((f) => ({ name: f, mtime: fs2.statSync(path2.join(sessionsDir, f)).mtimeMs })).sort((a, b) => b.mtime - a.mtime);
|
|
1461
|
+
if (jsonlFiles.length === 0) {
|
|
1462
|
+
console.error(`\u274C JSONL \u6587\u4EF6\u4E0D\u5B58\u5728: ${jsonlPath}`);
|
|
1463
|
+
process.exit(1);
|
|
1464
|
+
}
|
|
1465
|
+
sessionFileUUID = jsonlFiles[0].name.replace(".jsonl", "");
|
|
1466
|
+
jsonlPath = path2.join(sessionsDir, `${sessionFileUUID}.jsonl`);
|
|
1467
|
+
}
|
|
1468
|
+
console.log(` file: ${jsonlPath}`);
|
|
1469
|
+
const configName = path2.basename(configPath2);
|
|
1470
|
+
if (autoRestart) {
|
|
1471
|
+
try {
|
|
1472
|
+
const myPid = process.pid;
|
|
1473
|
+
const pids = execSync2(`pgrep -f "dist/main.mjs.*${configName}" 2>/dev/null || true`, { encoding: "utf-8" }).trim();
|
|
1474
|
+
const otherPids = pids.split("\n").filter((p) => p && p.trim() !== String(myPid)).join("\n").trim();
|
|
1475
|
+
if (otherPids) {
|
|
1476
|
+
console.log(`
|
|
1477
|
+
Killing engine (PID: ${otherPids})...`);
|
|
1478
|
+
execSync2(`echo "${otherPids}" | xargs kill -9 2>/dev/null || true`);
|
|
1479
|
+
await new Promise((r) => setTimeout(r, 2e3));
|
|
1480
|
+
}
|
|
1481
|
+
} catch {
|
|
1482
|
+
}
|
|
1483
|
+
}
|
|
1484
|
+
const timestamp = (/* @__PURE__ */ new Date()).toISOString().replace(/[:.]/g, "-");
|
|
1485
|
+
const { readFileSync: readFileSync3, writeFileSync: writeFileSync3, renameSync } = fs2;
|
|
1486
|
+
if (mode === "archive") {
|
|
1487
|
+
const archiveName = `${sessionFileUUID}.jsonl.archived.${timestamp}`;
|
|
1488
|
+
renameSync(jsonlPath, path2.join(sessionsDir, archiveName));
|
|
1489
|
+
console.log(`
|
|
1490
|
+
\u2705 \u5F52\u6863\u5B8C\u6210: ${archiveName}`);
|
|
1491
|
+
console.log(` \u91CD\u542F\u540E\u5C06\u4ECE\u7A7A\u767D\u4F1A\u8BDD\u5F00\u59CB`);
|
|
1492
|
+
} else if (mode === "drop-last") {
|
|
1493
|
+
const lines = readFileSync3(jsonlPath, "utf-8").trim().split("\n");
|
|
1494
|
+
const parsed = lines.map((l) => {
|
|
1495
|
+
try {
|
|
1496
|
+
return JSON.parse(l);
|
|
1497
|
+
} catch {
|
|
1498
|
+
return null;
|
|
1499
|
+
}
|
|
1500
|
+
}).filter(Boolean);
|
|
1501
|
+
let cutIndex = parsed.length;
|
|
1502
|
+
let userCount = 0;
|
|
1503
|
+
for (let i = parsed.length - 1; i >= 0; i--) {
|
|
1504
|
+
if (parsed[i].type === "message" && parsed[i].role === "user") {
|
|
1505
|
+
userCount++;
|
|
1506
|
+
cutIndex = i;
|
|
1507
|
+
if (userCount >= dropN) break;
|
|
1508
|
+
}
|
|
1509
|
+
}
|
|
1510
|
+
const kept = parsed.slice(0, cutIndex);
|
|
1511
|
+
const newContent = kept.map((p) => JSON.stringify(p)).join("\n") + "\n";
|
|
1512
|
+
writeFileSync3(jsonlPath, newContent);
|
|
1513
|
+
console.log(`
|
|
1514
|
+
\u2705 \u780D\u6389\u6700\u8FD1 ${parsed.length - cutIndex} \u884C\uFF08${dropN} \u8F6E\uFF09`);
|
|
1515
|
+
console.log(` \u4FDD\u7559 ${kept.length} \u884C`);
|
|
1516
|
+
} else if (mode === "strip-images") {
|
|
1517
|
+
const lines = readFileSync3(jsonlPath, "utf-8").trim().split("\n");
|
|
1518
|
+
let stripped = 0;
|
|
1519
|
+
const newLines = lines.map((line) => {
|
|
1520
|
+
try {
|
|
1521
|
+
const obj = JSON.parse(line);
|
|
1522
|
+
let changed = false;
|
|
1523
|
+
if (obj.type === "message") {
|
|
1524
|
+
const msg = obj.message || obj;
|
|
1525
|
+
if (typeof msg.content === "string") {
|
|
1526
|
+
const cleaned = msg.content.replace(/\n?\[图片×\d+\]/g, "").replace(/\n?\[图片来自[^\]]*\]/g, "");
|
|
1527
|
+
if (cleaned !== msg.content) {
|
|
1528
|
+
msg.content = cleaned;
|
|
1529
|
+
changed = true;
|
|
1530
|
+
}
|
|
1531
|
+
}
|
|
1532
|
+
if (Array.isArray(msg.content)) {
|
|
1533
|
+
msg.content = msg.content.map((block) => {
|
|
1534
|
+
if (block.type === "text" && typeof block.text === "string") {
|
|
1535
|
+
const cleaned = block.text.replace(/\n?\[图片×\d+\]/g, "").replace(/\n?\[图片来自[^\]]*\]/g, "");
|
|
1536
|
+
if (cleaned !== block.text) {
|
|
1537
|
+
changed = true;
|
|
1538
|
+
return { ...block, text: cleaned };
|
|
1539
|
+
}
|
|
1540
|
+
}
|
|
1541
|
+
if (block.type === "toolCall" && block.arguments?.image_path) {
|
|
1542
|
+
changed = true;
|
|
1543
|
+
return { ...block, arguments: { ...block.arguments, image_path: "[stripped]" } };
|
|
1544
|
+
}
|
|
1545
|
+
return block;
|
|
1546
|
+
});
|
|
1547
|
+
}
|
|
1548
|
+
}
|
|
1549
|
+
if (changed) {
|
|
1550
|
+
stripped++;
|
|
1551
|
+
return JSON.stringify(obj);
|
|
1552
|
+
}
|
|
1553
|
+
return line;
|
|
1554
|
+
} catch {
|
|
1555
|
+
return line;
|
|
1556
|
+
}
|
|
1557
|
+
});
|
|
1558
|
+
writeFileSync3(jsonlPath, newLines.join("\n") + "\n");
|
|
1559
|
+
console.log(`
|
|
1560
|
+
\u2705 \u6458\u9664 ${stripped} \u884C\u56FE\u7247\u76F8\u5173\u5185\u5BB9`);
|
|
1561
|
+
}
|
|
1562
|
+
if (autoRestart) {
|
|
1563
|
+
const realCliPath = fs2.realpathSync(process.argv[1]);
|
|
1564
|
+
const cliDir = path2.dirname(realCliPath);
|
|
1565
|
+
const pkgRoot = path2.resolve(cliDir, "..");
|
|
1566
|
+
let enginePath = path2.join(pkgRoot, "dist", "main.mjs");
|
|
1567
|
+
if (!fs2.existsSync(enginePath)) {
|
|
1568
|
+
enginePath = path2.join(cliDir, "main.mjs");
|
|
1569
|
+
}
|
|
1570
|
+
console.log(`
|
|
1571
|
+
\u{1F680} \u62C9\u8D77 engine...`);
|
|
1572
|
+
const { spawn } = await import("node:child_process");
|
|
1573
|
+
const child = spawn(process.execPath, [enginePath, "--engine-config", configPath2], {
|
|
1574
|
+
detached: true,
|
|
1575
|
+
stdio: "inherit"
|
|
1576
|
+
});
|
|
1577
|
+
child.on("exit", (code) => process.exit(code ?? 0));
|
|
1578
|
+
return;
|
|
1579
|
+
} else {
|
|
1580
|
+
console.log(`
|
|
1581
|
+
\u26A0\uFE0F \u8BF7\u624B\u52A8\u91CD\u542F engine \u4F7F\u6539\u52A8\u751F\u6548`);
|
|
1582
|
+
}
|
|
1583
|
+
process.exit(0);
|
|
1584
|
+
}
|
|
1585
|
+
process.exit(0);
|
|
1586
|
+
}
|
|
1342
1587
|
if (subcommand === "service") {
|
|
1343
1588
|
const action = args[1];
|
|
1344
1589
|
if (!action || action === "--help" || action === "-h") {
|