Skip to content

Commit 09eb9e4

Browse files
authored
Merge pull request #475 from Brikaa/fix-websockets
Clear hanging timeouts and parent processes writables
2 parents c7bcc7f + e177832 commit 09eb9e4

1 file changed

Lines changed: 34 additions & 13 deletions

File tree

api/src/job.js

Lines changed: 34 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -28,6 +28,9 @@ setInterval(() => {
2828
}, 10);
2929

3030
class Job {
31+
#active_timeouts;
32+
#active_parent_processes;
33+
3134
constructor({ runtime, files, args, stdin, timeouts, memory_limits }) {
3235
this.uuid = uuidv4();
3336

@@ -49,6 +52,9 @@ class Job {
4952
this.stdin += '\n';
5053
}
5154

55+
this.#active_timeouts = [];
56+
this.#active_parent_processes = [];
57+
5258
this.timeouts = timeouts;
5359
this.memory_limits = memory_limits;
5460

@@ -113,6 +119,28 @@ class Job {
113119
this.logger.debug('Primed job');
114120
}
115121

122+
exit_cleanup() {
123+
for (const timeout of this.#active_timeouts) {
124+
clear_timeout(timeout);
125+
}
126+
this.#active_timeouts = [];
127+
this.logger.debug('Cleared the active timeouts');
128+
129+
for (const proc of this.#active_parent_processes) {
130+
proc.stderr.destroy();
131+
if (!proc.stdin.destroyed) {
132+
proc.stdin.end();
133+
proc.stdin.destroy();
134+
}
135+
proc.stdout.destroy();
136+
}
137+
this.#active_parent_processes = [];
138+
this.logger.debug('Destroyed parent processes writables');
139+
140+
this.cleanup_processes();
141+
this.logger.debug(`Finished exit cleanup`);
142+
}
143+
116144
async safe_call(file, args, timeout, memory_limit, eventBus = null) {
117145
return new Promise((resolve, reject) => {
118146
const nonetwork = config.disable_networking ? ['nosocket'] : [];
@@ -149,6 +177,8 @@ class Job {
149177
detached: true, //give this process its own process group
150178
});
151179

180+
this.#active_parent_processes.push(proc);
181+
152182
if (eventBus === null) {
153183
proc.stdin.write(this.stdin);
154184
proc.stdin.end();
@@ -170,6 +200,7 @@ class Job {
170200
process.kill(proc.pid, 'SIGKILL');
171201
}, timeout)) ||
172202
null;
203+
this.#active_timeouts.push(kill_timeout);
173204

174205
proc.stderr.on('data', async data => {
175206
if (eventBus !== null) {
@@ -195,24 +226,14 @@ class Job {
195226
}
196227
});
197228

198-
const exit_cleanup = () => {
199-
clear_timeout(kill_timeout);
200-
201-
proc.stderr.destroy();
202-
proc.stdout.destroy();
203-
204-
this.cleanup_processes();
205-
this.logger.debug(`Finished exit cleanup`);
206-
};
207-
208229
proc.on('exit', (code, signal) => {
209-
exit_cleanup();
230+
this.exit_cleanup();
210231

211232
resolve({ stdout, stderr, code, signal, output });
212233
});
213234

214235
proc.on('error', err => {
215-
exit_cleanup();
236+
this.exit_cleanup();
216237

217238
reject({ error: err, stdout, stderr, output });
218239
});
@@ -431,7 +452,7 @@ class Job {
431452
async cleanup() {
432453
this.logger.info(`Cleaning up job`);
433454

434-
this.cleanup_processes(); // Run process janitor, just incase there are any residual processes somehow
455+
this.exit_cleanup(); // Run process janitor, just incase there are any residual processes somehow
435456
await this.cleanup_filesystem();
436457

437458
remaining_job_spaces++;

0 commit comments

Comments
 (0)