Skip to content

Commit ea9a183

Browse files
Merge pull request #57 from ServerlessLife/do-not-kill-node-worker-if-working
fix: Do not kill node worker if working
2 parents 8244950 + b55c0ff commit ea9a183

File tree

1 file changed

+46
-8
lines changed

1 file changed

+46
-8
lines changed

src/nodeWorker.ts

Lines changed: 46 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,14 @@ import { Configuration } from './configuration.js';
55
import { getModuleDirname, getProjectDirname } from './getDirname.js';
66
import { Logger } from './logger.js';
77

8-
const workers = new Map<string, Worker>();
8+
interface MyWorker extends Worker {
9+
used?: boolean;
10+
toKill?: boolean;
11+
onMessage?: (msg: any) => void;
12+
onError?: (err: any) => void;
13+
}
14+
15+
const workers = new Map<string, MyWorker>();
916

1017
/**
1118
* Run the function in a Node.js Worker Thread
@@ -22,7 +29,9 @@ async function runInWorker(input: {
2229
const func = await Configuration.getLambda(input.fuctionRequest.functionId);
2330

2431
return new Promise<void>((resolve, reject) => {
25-
let worker = workers.get(input.fuctionRequest.workerId);
32+
let worker: MyWorker | undefined = workers.get(
33+
input.fuctionRequest.workerId,
34+
);
2635

2736
if (!worker) {
2837
worker = startWorker({
@@ -33,31 +42,41 @@ async function runInWorker(input: {
3342
environment: input.environment,
3443
verbose: Configuration.config.verbose,
3544
});
45+
worker.used = false;
46+
worker.toKill = false;
3647
} else {
3748
Logger.verbose(
3849
`[Function ${input.fuctionRequest.functionId}] [Worker ${input.fuctionRequest.workerId}] Reusing worker`,
3950
);
4051
}
4152

42-
worker.on('message', (msg) => {
53+
worker.onMessage = (msg) => {
4354
Logger.verbose(
4455
`[Function ${input.fuctionRequest.functionId}] [Worker ${input.fuctionRequest.workerId}] Worker message`,
4556
JSON.stringify(msg),
4657
);
58+
59+
worker.used = false;
4760
if (msg?.errorType) {
4861
reject(msg);
4962
} else {
5063
resolve(msg);
5164
}
52-
});
53-
worker.on('error', (err) => {
65+
66+
if (worker.toKill) {
67+
worker.toKill = false;
68+
void worker.terminate();
69+
}
70+
};
71+
worker.onError = (err) => {
5472
Logger.error(
5573
`[Function ${input.fuctionRequest.functionId}] [Worker ${input.fuctionRequest.workerId}] Error`,
5674
err,
5775
);
5876
reject(err);
59-
});
77+
};
6078

79+
worker.used = true;
6180
worker.postMessage({
6281
env: input.fuctionRequest.env,
6382
event: input.fuctionRequest.event,
@@ -89,7 +108,7 @@ function startWorker(input: WorkerRequest) {
89108

90109
const localProjectDir = getProjectDirname();
91110

92-
const worker = new Worker(
111+
const worker: MyWorker = new Worker(
93112
path.resolve(path.join(getModuleDirname(), `./nodeWorkerRunner.mjs`)),
94113
{
95114
env: {
@@ -118,8 +137,16 @@ function startWorker(input: WorkerRequest) {
118137
);
119138
workers.delete(input.workerId);
120139
});
140+
121141
workers.set(input.workerId, worker);
122142

143+
worker.on('message', (msg) => {
144+
worker?.onMessage?.(msg);
145+
});
146+
worker.on('error', (err) => {
147+
worker?.onError?.(err);
148+
});
149+
123150
return worker;
124151
}
125152

@@ -130,7 +157,18 @@ async function stopAllWorkers() {
130157
Logger.verbose('Stopping all workers');
131158
const promises: Promise<any>[] = [];
132159
for (const worker of workers.values()) {
133-
promises.push(worker.terminate());
160+
if (worker.used) {
161+
worker.toKill = true;
162+
// set timout for 5 minutes and kill the worker if it is still running
163+
setTimeout(() => {
164+
if (worker.toKill) {
165+
worker.toKill = false;
166+
void worker.terminate();
167+
}
168+
}, 300000);
169+
} else {
170+
promises.push(worker.terminate());
171+
}
134172
}
135173
workers.clear();
136174
await Promise.all(promises);

0 commit comments

Comments
 (0)