Only track hook states for running PIDs

Stop exposing and retaining hook state for PIDs that are not currently running. listProcesses() no longer returns orphaned states; live-pipe handling ignores PIDs not present in the current process list. When a process is not running its state is immediately torn down (tearDownClient called) and removed, and bridgeManager.onPidDisconnected is notified if the state was logged in. Also reorganized runningSet creation so it can be reused for these checks.
This commit is contained in:
手瓜一十雪
2026-05-09 19:38:52 +08:00
parent c39b3f5c4e
commit a7b3809a12
+6 -10
View File
@@ -76,9 +76,7 @@ export class HookManager {
async listProcesses(): Promise<HookProcessInfo[]> {
const processes = listHookProcesses();
const seen = new Set<number>();
for (const proc of processes) {
seen.add(proc.pid);
const state = this.ensureState(proc.pid);
state.name = proc.name || state.name;
state.path = proc.path || state.path;
@@ -87,11 +85,6 @@ export class HookManager {
for (const proc of processes) {
result.push(this.toPublicInfo(this.ensureState(proc.pid)));
}
for (const state of this.states.values()) {
if (!seen.has(state.pid) && (state.injected || state.client)) {
result.push(this.toPublicInfo(state));
}
}
return result.sort((a, b) => a.pid - b.pid);
}
@@ -316,6 +309,7 @@ export class HookManager {
try {
const livePipes = await QqHookClient.listLivePipes();
const processes = listHookProcesses();
const runningSet = new Set(processes.map(p => p.pid));
// Refresh metadata + ensure a state entry exists for each known PID.
for (const proc of processes) {
@@ -325,6 +319,7 @@ export class HookManager {
}
// Auto-detect hooks that survived a SnowLuma restart or failed unload.
for (const pid of livePipes) {
if (!runningSet.has(pid)) continue;
const state = this.ensureState(pid);
if (!state.injected) {
state.injected = true;
@@ -334,14 +329,15 @@ export class HookManager {
}
}
const runningSet = new Set(processes.map(p => p.pid));
const tasks: Promise<unknown>[] = [];
for (const state of [...this.states.values()]) {
const alivePipe = livePipes.has(state.pid);
const aliveProc = runningSet.has(state.pid);
// Reap stale state entries that have nothing left to do.
if (!aliveProc && !alivePipe && !state.injected && !state.client) {
if (!aliveProc) {
const wasLoggedIn = state.loggedIn;
this.tearDownClient(state);
if (wasLoggedIn) this.bridgeManager.onPidDisconnected(state.pid);
this.states.delete(state.pid);
continue;
}