ai-project-manage-cli 8.0.4 → 8.0.5

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.
Files changed (2) hide show
  1. package/dist/index.js +118 -1
  2. package/package.json +1 -1
package/dist/index.js CHANGED
@@ -1119,6 +1119,21 @@ function validateCancel(o) {
1119
1119
  data: { type: "cancel", messageId: o.messageId.trim() }
1120
1120
  };
1121
1121
  }
1122
+ function validateWebIdeStopTerminals(o) {
1123
+ if (o.type !== "webide-stop-terminals") {
1124
+ return { ok: false, reason: "\u671F\u671B webide-stop-terminals" };
1125
+ }
1126
+ if (!nonEmptyString(o.taskId)) {
1127
+ return { ok: false, reason: "webide-stop-terminals \u7F3A\u5C11 taskId" };
1128
+ }
1129
+ return {
1130
+ ok: true,
1131
+ data: {
1132
+ type: "webide-stop-terminals",
1133
+ taskId: o.taskId.trim()
1134
+ }
1135
+ };
1136
+ }
1122
1137
  function validateWebIdeStartProjectPush(o) {
1123
1138
  if (o.type !== "webide-start-project") {
1124
1139
  return { ok: false, reason: "\u671F\u671B webide-start-project" };
@@ -1169,7 +1184,7 @@ function validateAgentWsMessage(value, kind) {
1169
1184
  }
1170
1185
  const o = value;
1171
1186
  const type = o.type;
1172
- if (type !== "heartbeat" && type !== "webide-message" && type !== "cancel" && type !== "webide-start-project") {
1187
+ if (type !== "heartbeat" && type !== "webide-message" && type !== "cancel" && type !== "webide-start-project" && type !== "webide-stop-terminals") {
1173
1188
  return { ok: false, reason: `\u672A\u77E5 type: ${String(type)}` };
1174
1189
  }
1175
1190
  if (kind === "heartbeat" || type === "heartbeat") {
@@ -1181,6 +1196,9 @@ function validateAgentWsMessage(value, kind) {
1181
1196
  if (type === "webide-start-project") {
1182
1197
  return validateWebIdeStartProjectPush(o);
1183
1198
  }
1199
+ if (type === "webide-stop-terminals") {
1200
+ return validateWebIdeStopTerminals(o);
1201
+ }
1184
1202
  return validateWebIdeMessagePush(o);
1185
1203
  }
1186
1204
 
@@ -1382,6 +1400,102 @@ function handleStartProjectAction(payload, ctx) {
1382
1400
  trackActionTask(ctx, task);
1383
1401
  }
1384
1402
 
1403
+ // src/commands/connect/pty-session-mcp.ts
1404
+ init_config();
1405
+ var DEFAULT_PTY_SESSION_PORT = "7788";
1406
+ function resolvePtySessionBaseUrl(env = process.env) {
1407
+ const explicit = env.LOCAL_TERMINAL_URL?.trim();
1408
+ if (explicit) return explicit.replace(/\/+$/, "");
1409
+ const port = env.LOCAL_TERMINAL_PORT?.trim() || DEFAULT_PTY_SESSION_PORT;
1410
+ return `http://127.0.0.1:${port}`;
1411
+ }
1412
+ function asSessionList(data) {
1413
+ if (Array.isArray(data)) return data;
1414
+ if (data && typeof data === "object") {
1415
+ const sessions = data.sessions;
1416
+ if (Array.isArray(sessions)) return sessions;
1417
+ }
1418
+ return [];
1419
+ }
1420
+ async function requestPtyJson(url, token, init) {
1421
+ const res = await fetch(url, {
1422
+ ...init,
1423
+ headers: {
1424
+ Authorization: `Bearer ${token}`,
1425
+ ...init?.headers ?? {}
1426
+ }
1427
+ });
1428
+ if (!res.ok) {
1429
+ throw new Error(`pty-session HTTP ${res.status}`);
1430
+ }
1431
+ try {
1432
+ return await res.json();
1433
+ } catch {
1434
+ return null;
1435
+ }
1436
+ }
1437
+ async function killAllPtySessions(cfg) {
1438
+ const token = resolveApiKey(cfg);
1439
+ if (!token) return 0;
1440
+ const baseUrl = resolvePtySessionBaseUrl();
1441
+ let body;
1442
+ try {
1443
+ body = await requestPtyJson(`${baseUrl}/sessions`, token);
1444
+ } catch (err) {
1445
+ console.warn(
1446
+ "[apm] \u5217\u51FA PTY \u4F1A\u8BDD\u5931\u8D25:",
1447
+ err instanceof Error ? err.message : err
1448
+ );
1449
+ return 0;
1450
+ }
1451
+ const payload = body;
1452
+ if (payload && typeof payload === "object" && payload.ok === false) {
1453
+ return 0;
1454
+ }
1455
+ const data = payload && typeof payload === "object" && "data" in payload ? payload.data : body;
1456
+ const sessions = asSessionList(data);
1457
+ let killed = 0;
1458
+ for (const session of sessions) {
1459
+ const id = session.id?.trim();
1460
+ if (!id) continue;
1461
+ if (session.running === false) continue;
1462
+ try {
1463
+ await requestPtyJson(
1464
+ `${baseUrl}/sessions/${encodeURIComponent(id)}`,
1465
+ token,
1466
+ {
1467
+ method: "DELETE"
1468
+ }
1469
+ );
1470
+ killed += 1;
1471
+ } catch (err) {
1472
+ console.warn(
1473
+ `[apm] \u7ED3\u675F PTY \u4F1A\u8BDD\u5931\u8D25 id=${id}:`,
1474
+ err instanceof Error ? err.message : err
1475
+ );
1476
+ }
1477
+ }
1478
+ return killed;
1479
+ }
1480
+
1481
+ // src/commands/connect/actions/stop-terminals.ts
1482
+ function handleStopTerminalsAction(payload, ctx) {
1483
+ const task = (async () => {
1484
+ try {
1485
+ const killed = await killAllPtySessions(ctx.cfg);
1486
+ console.log(
1487
+ `[apm] webide-stop-terminals taskId=${payload.taskId} killed=${killed}`
1488
+ );
1489
+ } catch (err) {
1490
+ console.warn(
1491
+ `[apm] webide-stop-terminals \u5931\u8D25 taskId=${payload.taskId}:`,
1492
+ err instanceof Error ? err.message : err
1493
+ );
1494
+ }
1495
+ })();
1496
+ trackActionTask(ctx, task);
1497
+ }
1498
+
1385
1499
  // src/commands/connect/actions/index.ts
1386
1500
  function dispatchConnectAction(payload, ctx) {
1387
1501
  switch (payload.type) {
@@ -1396,6 +1510,9 @@ function dispatchConnectAction(payload, ctx) {
1396
1510
  case "webide-start-project":
1397
1511
  handleStartProjectAction(payload, ctx);
1398
1512
  return;
1513
+ case "webide-stop-terminals":
1514
+ handleStopTerminalsAction(payload, ctx);
1515
+ return;
1399
1516
  }
1400
1517
  }
1401
1518
 
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "ai-project-manage-cli",
3
- "version": "8.0.4",
3
+ "version": "8.0.5",
4
4
  "description": "命令行工具:后续用于调用平台后端 API 完成运维与自动化操作",
5
5
  "type": "module",
6
6
  "private": false,