egg-cluster
Advanced tools
Comparing version 1.19.1 to 1.20.0
1.20.0 / 2018-09-17 | ||
=================== | ||
* feat: kill agent after workers are killed (#76) | ||
* docs: fix typo (#77) | ||
1.19.1 / 2018-08-27 | ||
@@ -3,0 +9,0 @@ ================== |
@@ -15,2 +15,5 @@ 'use strict'; | ||
const semver = require('semver'); | ||
const awaitEvent = require('await-event'); | ||
const sleep = require('mz-modules/sleep'); | ||
const co = require('co'); | ||
@@ -288,17 +291,26 @@ const Manager = require('./utils/manager'); | ||
* make sure Agent Worker exit before master exit | ||
* | ||
* @param {number} timeout - kill agent timeout | ||
* @return {Promise} - | ||
*/ | ||
killAgentWorker() { | ||
killAgentWorker(timeout) { | ||
if (this.agentWorker) { | ||
this.log('[master] kill agent worker with signal SIGTERM'); | ||
this.agentWorker.removeAllListeners(); | ||
this.agentWorker.kill('SIGTERM'); | ||
} | ||
const self = this; | ||
return co(function* () { | ||
yield self._killSubProcess(self.agentWorker, timeout); | ||
}); | ||
} | ||
killAppWorkers() { | ||
for (const id in cluster.workers) { | ||
const worker = cluster.workers[id]; | ||
worker.disableRefork = true; | ||
worker.process.kill('SIGTERM'); | ||
} | ||
killAppWorkers(timeout) { | ||
const self = this; | ||
return co(function* () { | ||
yield Object.keys(cluster.workers).map(id => { | ||
const worker = cluster.workers[id]; | ||
worker.disableRefork = true; | ||
return self._killSubProcess(worker, timeout); | ||
}); | ||
}); | ||
} | ||
@@ -516,17 +528,13 @@ | ||
this.closed = true; | ||
// kill app workers | ||
// kill agent worker | ||
// exit itself | ||
this.killAppWorkers(); | ||
this.killAgentWorker(); | ||
// sleep to make sure SIGTERM send to the child processes | ||
const timeout = process.env.EGG_MASTER_CLOSE_TIMEOUT || 5000; | ||
this.log('[master] send kill SIGTERM to app workers and agent worker, will exit with code:0 after %sms', timeout); | ||
this.logger.info('[master] wait %sms', timeout); | ||
setTimeout(() => { | ||
this.log('[master] close done, exiting with code:0'); | ||
// FIXME: master should wait agent/app exit | ||
process.exit(0); | ||
}, timeout); | ||
const self = this; | ||
co(function* () { | ||
try { | ||
yield self._doClose(); | ||
self.log('[master] close done, exiting with code:0'); | ||
process.exit(0); | ||
} catch (e) /* istanbul ignore next */ { | ||
this.logger.error('[master] close with error: ', e); | ||
process.exit(1); | ||
} | ||
}); | ||
} | ||
@@ -541,2 +549,40 @@ | ||
} | ||
* _killSubProcess(subProcess, timeout) { | ||
subProcess.kill('SIGTERM'); | ||
yield Promise.race([ | ||
awaitEvent(subProcess, 'exit'), | ||
sleep(timeout), | ||
]); | ||
if (subProcess.killed) { | ||
return; | ||
} | ||
// SIGKILL: http://man7.org/linux/man-pages/man7/signal.7.html | ||
// worker: https://github.com/nodejs/node/blob/master/lib/internal/cluster/worker.js#L22 | ||
// subProcess.kill is wrapped to subProcess.destroy, it will wait to disconnected. | ||
(subProcess.process || subProcess).kill('SIGKILL'); | ||
} | ||
* _doClose() { | ||
// kill app workers | ||
// kill agent worker | ||
// exit itself | ||
const legacyTimeout = process.env.EGG_MASTER_CLOSE_TIMEOUT || 5000; | ||
const appTimeout = process.env.EGG_APP_CLOSE_TIMEOUT || legacyTimeout; | ||
const agentTimeout = process.env.EGG_AGENT_CLOSE_TIMEOUT || legacyTimeout; | ||
this.logger.info('[master] send kill SIGTERM to app workers, will exit with code:0 after %sms', appTimeout); | ||
this.logger.info('[master] wait %sms', appTimeout); | ||
try { | ||
yield this.killAppWorkers(appTimeout); | ||
} catch (e) /* istanbul ignore next */ { | ||
this.logger.error('[master] app workers exit error: ', e); | ||
} | ||
this.logger.info('[master] send kill SIGTERM to agent worker, will exit with code:0 after %sms', agentTimeout); | ||
this.logger.info('[master] wait %sms', agentTimeout); | ||
try { | ||
yield this.killAgentWorker(agentTimeout); | ||
} catch (e) /* istanbul ignore next */ { | ||
this.logger.error('[master] agent worker exit error: ', e); | ||
} | ||
} | ||
} | ||
@@ -543,0 +589,0 @@ |
{ | ||
"name": "egg-cluster", | ||
"version": "1.19.1", | ||
"version": "1.20.0", | ||
"description": "cluster manager for egg", | ||
@@ -35,4 +35,6 @@ "main": "index.js", | ||
"dependencies": { | ||
"await-event": "^2.1.0", | ||
"cfork": "^1.7.1", | ||
"cluster-reload": "^1.0.2", | ||
"co": "^4.6.0", | ||
"debug": "^3.1.0", | ||
@@ -46,2 +48,3 @@ "depd": "^1.1.2", | ||
"is-type-of": "^1.2.0", | ||
"mz-modules": "^2.1.0", | ||
"semver": "^5.5.0", | ||
@@ -54,3 +57,2 @@ "sendmessage": "^1.1.0", | ||
"autod": "^3.0.1", | ||
"await-event": "^2.1.0", | ||
"coffee": "^4.1.0", | ||
@@ -64,3 +66,2 @@ "egg": "^2.8.1", | ||
"mz": "^2.7.0", | ||
"mz-modules": "^2.1.0", | ||
"pedding": "^1.1.0", | ||
@@ -67,0 +68,0 @@ "supertest": "^3.1.0", |
@@ -63,6 +63,12 @@ # egg-cluster | ||
| typescript | `Boolean` | enable loader's typescript support | | ||
| require | `Array|String` | will inject into worker/agent process | | ||
| require | `Array\|String` | will inject into worker/agent process | | ||
## Env | ||
EGG_APP_CLOSE_TIMEOUT: app worker boot timeout value | ||
EGG_AGENT_CLOSE_TIMEOUT: agent worker boot timeout value | ||
## License | ||
[MIT](LICENSE) |
Environment variable access
Supply chain riskPackage accesses environment variables, which may be a sign of credential stuffing or data theft.
Found 2 instances in 1 package
46497
14
950
74
16
22
+ Addedawait-event@^2.1.0
+ Addedco@^4.6.0
+ Addedmz-modules@^2.1.0
+ Addedawait-event@2.1.0(transitive)
+ Addedbalanced-match@1.0.2(transitive)
+ Addedbrace-expansion@1.1.11(transitive)
+ Addedco@4.6.0(transitive)
+ Addedconcat-map@0.0.1(transitive)
+ Addedend-of-stream@1.4.4(transitive)
+ Addedfs.realpath@1.0.0(transitive)
+ Addedglob@7.2.3(transitive)
+ Addedinflight@1.0.6(transitive)
+ Addedinherits@2.0.4(transitive)
+ Addedko-sleep@1.1.4(transitive)
+ Addedminimatch@3.1.2(transitive)
+ Addedmz-modules@2.1.0(transitive)
+ Addedpath-is-absolute@1.0.1(transitive)
+ Addedpump@3.0.2(transitive)
+ Addedrimraf@2.7.1(transitive)