tt-help-cli-ycl 1.4.66 → 1.4.67
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/package.json
CHANGED
package/src/watch/public/app.js
CHANGED
|
@@ -3562,7 +3562,17 @@ function renderOfflineCard(userId, cmds) {
|
|
|
3562
3562
|
"div",
|
|
3563
3563
|
"display:flex;gap:10px;align-items:center",
|
|
3564
3564
|
styled("span", "color:#f87171", "● 离线") +
|
|
3565
|
-
styled("span", "color:#555;font-size:10px", "—")
|
|
3565
|
+
styled("span", "color:#555;font-size:10px", "—") +
|
|
3566
|
+
tag(
|
|
3567
|
+
"button",
|
|
3568
|
+
{
|
|
3569
|
+
onclick: "wdDeleteClient('" + esc(userId) + "')",
|
|
3570
|
+
style:
|
|
3571
|
+
"padding:2px 8px;font-size:10px;background:#991b1b;color:#fff;border:none;border-radius:3px;cursor:pointer",
|
|
3572
|
+
title: "删除此客户端配置",
|
|
3573
|
+
},
|
|
3574
|
+
"删除",
|
|
3575
|
+
),
|
|
3566
3576
|
),
|
|
3567
3577
|
) +
|
|
3568
3578
|
styled(
|
|
@@ -3623,7 +3633,19 @@ function renderClientCard(c, clientCommands) {
|
|
|
3623
3633
|
"display:flex;gap:10px;align-items:center",
|
|
3624
3634
|
styled("span", "color:#888;font-size:11px", c.ip) +
|
|
3625
3635
|
onlineBadge +
|
|
3626
|
-
styled("span", "color:#666;font-size:10px", lastSeen)
|
|
3636
|
+
styled("span", "color:#666;font-size:10px", lastSeen) +
|
|
3637
|
+
(!c.online && userId
|
|
3638
|
+
? tag(
|
|
3639
|
+
"button",
|
|
3640
|
+
{
|
|
3641
|
+
onclick: "wdDeleteClient('" + esc(userId) + "')",
|
|
3642
|
+
style:
|
|
3643
|
+
"padding:2px 8px;font-size:10px;background:#991b1b;color:#fff;border:none;border-radius:3px;cursor:pointer;margin-left:6px",
|
|
3644
|
+
title: "删除此客户端配置",
|
|
3645
|
+
},
|
|
3646
|
+
"删除",
|
|
3647
|
+
)
|
|
3648
|
+
: ""),
|
|
3627
3649
|
),
|
|
3628
3650
|
);
|
|
3629
3651
|
|
|
@@ -3889,3 +3911,15 @@ async function wdSaveClientCmds(userId, commands) {
|
|
|
3889
3911
|
alert("保存失败: " + e.message);
|
|
3890
3912
|
}
|
|
3891
3913
|
}
|
|
3914
|
+
|
|
3915
|
+
function wdDeleteClient(userId) {
|
|
3916
|
+
if (
|
|
3917
|
+
!confirm(
|
|
3918
|
+
"确定删除 " +
|
|
3919
|
+
userId +
|
|
3920
|
+
" 的所有命令配置?\n\n删除后该客户端将不再出现在列表中。",
|
|
3921
|
+
)
|
|
3922
|
+
)
|
|
3923
|
+
return;
|
|
3924
|
+
wdSaveClientCmds(userId, []);
|
|
3925
|
+
}
|
|
@@ -44,19 +44,6 @@ function splitCommand(cmdLine) {
|
|
|
44
44
|
return parts;
|
|
45
45
|
}
|
|
46
46
|
|
|
47
|
-
// Windows: 从 cmd.exe 往下找真正的子进程 PID(跳过 conhost)
|
|
48
|
-
function getChildPid(parentPid) {
|
|
49
|
-
try {
|
|
50
|
-
const out = execSync(
|
|
51
|
-
`powershell -NoProfile -Command "Get-CimInstance Win32_Process -Filter 'ParentProcessId=${parentPid}' | Where-Object { $_.Name -ne 'conhost.exe' } | Select-Object -First 1 -ExpandProperty ProcessId"`,
|
|
52
|
-
{ encoding: "utf-8", timeout: 3000, stdio: ["ignore", "pipe", "ignore"] },
|
|
53
|
-
).trim();
|
|
54
|
-
return parseInt(out, 10) || 0;
|
|
55
|
-
} catch {
|
|
56
|
-
return 0;
|
|
57
|
-
}
|
|
58
|
-
}
|
|
59
|
-
|
|
60
47
|
function getProcessStats(pid) {
|
|
61
48
|
try {
|
|
62
49
|
const cmd = IS_WIN
|
|
@@ -119,36 +106,16 @@ export class ProcessManager extends EventEmitter {
|
|
|
119
106
|
let child;
|
|
120
107
|
const startTime = Date.now();
|
|
121
108
|
try {
|
|
122
|
-
// 拆分为 program + args
|
|
109
|
+
// 拆分为 program + args(引号感知)
|
|
123
110
|
if (args.length === 0) {
|
|
124
111
|
const parts = splitCommand(command);
|
|
125
112
|
command = parts[0] || command;
|
|
126
113
|
args = parts.slice(1);
|
|
127
114
|
}
|
|
128
|
-
|
|
129
|
-
|
|
130
|
-
|
|
131
|
-
|
|
132
|
-
detached: false,
|
|
133
|
-
shell: true,
|
|
134
|
-
})
|
|
135
|
-
: spawn(command, args, {
|
|
136
|
-
stdio: ["ignore", "pipe", "pipe"],
|
|
137
|
-
detached: false,
|
|
138
|
-
});
|
|
139
|
-
|
|
140
|
-
// Windows: cmd.exe 不是真实进程,延迟获取子进程 PID
|
|
141
|
-
if (IS_WIN) {
|
|
142
|
-
setTimeout(() => {
|
|
143
|
-
const realPid = getChildPid(child.pid);
|
|
144
|
-
if (realPid > 0) {
|
|
145
|
-
const info = this.processes.get(id);
|
|
146
|
-
if (info && info.child === child) {
|
|
147
|
-
info._realPid = realPid;
|
|
148
|
-
}
|
|
149
|
-
}
|
|
150
|
-
}, 2000);
|
|
151
|
-
}
|
|
115
|
+
child = spawn(command, args, {
|
|
116
|
+
stdio: ["ignore", "pipe", "pipe"],
|
|
117
|
+
detached: false,
|
|
118
|
+
});
|
|
152
119
|
} catch (e) {
|
|
153
120
|
console.error(`[watchdog] 启动命令 ${id} 失败: ${e.message}`);
|
|
154
121
|
this.processes.set(id, {
|
|
@@ -262,8 +229,7 @@ export class ProcessManager extends EventEmitter {
|
|
|
262
229
|
const result = [];
|
|
263
230
|
for (const [cmdId, info] of this.processes) {
|
|
264
231
|
if (info.stopped) continue;
|
|
265
|
-
|
|
266
|
-
const pid = info._realPid || info.child?.pid || 0;
|
|
232
|
+
const pid = info.child?.pid || 0;
|
|
267
233
|
const stats = pid ? getProcessStats(pid) : null;
|
|
268
234
|
const uptimeSeconds = Math.round((Date.now() - info.startTime) / 1000);
|
|
269
235
|
|
|
@@ -370,7 +336,7 @@ export class ProcessManager extends EventEmitter {
|
|
|
370
336
|
if (info.stopped || !info.child) continue;
|
|
371
337
|
const thresholds = info.thresholds || {};
|
|
372
338
|
const uptimeSeconds = Math.round((now - info.startTime) / 1000);
|
|
373
|
-
const pid = info.
|
|
339
|
+
const pid = info.child.pid;
|
|
374
340
|
|
|
375
341
|
let reason = "";
|
|
376
342
|
// 检查运行时长
|