Skip to content

Commit ed65950

Browse files
support for proxy.nonDefaultWorkerIdleTime. Proxy crash under load
1 parent 4699cd1 commit ed65950

File tree

5 files changed

+70
-11
lines changed

5 files changed

+70
-11
lines changed

examples/proxy/proxy.json

+1-1
Original file line numberDiff line numberDiff line change
@@ -15,5 +15,5 @@
1515
}
1616
],
1717
"nonDefaultWorkerCount": 1,
18-
"nonDefaultWorkerIdleTime": 3600
18+
"nonDefaultWorkerIdleTime": 20
1919
}

lib/new-worker.js

+9-2
Original file line numberDiff line numberDiff line change
@@ -50,6 +50,7 @@ function newWorker(options, cb) {
5050
version = {
5151
name: options.version,
5252
port: options.PROXY_PORT,
53+
lastAccess: Date.now(),
5354
online: false
5455
};
5556
cservice.locals.proxy.versions[options.version] = version;
@@ -72,11 +73,11 @@ function onMessageFromWorker(msg) {
7273
return; // ignore invalid cluster-service messages
7374
}
7475

75-
var args;
76+
var args, version;
7677

7778
switch (msg.cservice.cmd) {
7879
case "workerReady":
79-
var version = cservice.locals.proxy.versions[worker.cservice.version];
80+
version = cservice.locals.proxy.versions[worker.cservice.version];
8081
if (version) {
8182
// if version detected within worker, flag as online
8283
version.online = true;
@@ -107,5 +108,11 @@ function onMessageFromWorker(msg) {
107108
cservice.trigger.apply(cservice, args);
108109
}
109110
break;
111+
case "versionUpdateLastAccess":
112+
version = cservice.locals.proxy.versions[msg.cservice.version];
113+
if (version) { // update freshness
114+
version.lastAccess = Date.now();
115+
}
116+
break;
110117
}
111118
}

lib/proxy-worker.js

+16-1
Original file line numberDiff line numberDiff line change
@@ -67,6 +67,7 @@ proxyServer.listen(bindingInfo.port, cservice.workerReady);
6767
function getProxyVersion(versionStr, cb) {
6868
var version = cservice.locals.proxy.versions[versionStr];
6969
if (version) {
70+
updateVersionLastAccess(version);
7071
return waitForVersionToComeOnline(versionStr, cb);
7172
}
7273

@@ -90,7 +91,8 @@ function waitForVersionToComeOnline(versionStr, cb) {
9091
// try waiting
9192
var timer, attempts = 0;
9293
timer = setInterval(function() {
93-
if (version.online === true) {
94+
version = cservice.locals.proxy.versions[versionStr];
95+
if (version && version.online === true) {
9496
clearInterval(timer);
9597
return cb(null, version);
9698
}
@@ -122,3 +124,16 @@ function onMessageFromMaster(msg) {
122124
break;
123125
}
124126
}
127+
128+
function updateVersionLastAccess(version) {
129+
var now = Date.now();
130+
var diff = now - version.lastAccess;
131+
if (diff >= 0 && diff < 5000) {
132+
return; // if less than 5 seconds since last access, don't bother updating master
133+
}
134+
version.lastAccess = now;
135+
var msg = cservice.msgBus.createMessage("versionUpdateLastAccess", {
136+
version: version.name
137+
});
138+
process.send(msg);
139+
}

lib/proxy.js

+43-6
Original file line numberDiff line numberDiff line change
@@ -81,6 +81,9 @@ function start(options, cb) {
8181
};
8282
});
8383

84+
cservice.locals.proxy.refreshnessTimer = setInterval(checkVersionsForFreshness, 10000);
85+
cservice.locals.proxy.refreshnessTimer.unref();
86+
8487
cservice.locals.proxy.enabled = true;
8588

8689
async.parallel(proxyWorkerTasks, function (err) {
@@ -133,6 +136,9 @@ function stop(cb) {
133136
return cb && cb("Proxy not running");
134137
}
135138

139+
clearInterval(cservice.locals.proxy.refreshnessTimer);
140+
cservice.locals.proxy.refreshnessTimer = null;
141+
136142
// now lets trigger a shutdown
137143
cservice.trigger("shutdown", function(err, result) {
138144
cservice.locals.proxy.enabled = false;
@@ -147,7 +153,7 @@ function version(versionStr, options, cb) {
147153
}
148154

149155
options = options || {};
150-
if (!options.workerCount) {
156+
if (isNaN(options.workerCount) === true) {
151157
options.workerCount =
152158
(versionStr === cservice.locals.proxy.options.defaultVersion)
153159
? cservice.locals.options.workerCount
@@ -161,6 +167,14 @@ function version(versionStr, options, cb) {
161167
// determine worker delta from desired count and actual count
162168
var workerCountDelta = options.workerCount - currentVersionWorkers.length;
163169

170+
// get existing version listing
171+
var v = cservice.locals.proxy.versions[versionStr];
172+
173+
if (v) {
174+
// update version lastAccess
175+
v.lastAccess = Date.now();
176+
}
177+
164178
// if version worker count is already current, nothing more to do
165179
if (workerCountDelta === 0) {
166180
return cb && cb();
@@ -194,8 +208,6 @@ function version(versionStr, options, cb) {
194208
versionStr, cservice.locals.proxy.workerFilename
195209
);
196210

197-
// get existing version listing
198-
var v = cservice.locals.proxy.versions[versionStr];
199211
// use existing port if available, otherwise allocate a new one
200212
var versionPort = (v && v.port) || getNextAvailablePort();
201213

@@ -338,18 +350,20 @@ function info(cb) {
338350
return cb && cb("Proxy cannot invoke 'info' from worker");
339351
}
340352

353+
var now = Date.now();
341354
var proxyWorkers = getProxyWorkers().map(function(worker) {
342355
var bindingInfo = JSON.parse(worker.cservice.bindingInfo);
343356
return {
344357
port: bindingInfo.port,
345-
ssl: typeof bindingInfo.tlsOptions === "object",
346-
358+
ssl: typeof bindingInfo.tlsOptions === "object"
347359
};
348360
});
349361
var versionWorkers = getVersionWorkers().map(function(worker) {
362+
var versionInfo = cservice.locals.proxy.versions[worker.cservice.version];
350363
return {
351364
worker: worker.cservice.worker,
352-
version: worker.cservice.version
365+
version: worker.cservice.version,
366+
lastAccess: versionInfo ? Math.round((now - versionInfo.lastAccess) / 1000) : "?"
353367
};
354368
});
355369

@@ -395,3 +409,26 @@ function isVersionRunning(versionStr, cb) {
395409

396410
return false; // no workers running desired version
397411
}
412+
413+
function checkVersionsForFreshness() {
414+
var now = Date.now();
415+
for (var k in cservice.locals.proxy.versions) {
416+
if (
417+
// live version is exempt
418+
k === cservice.locals.proxy.options.defaultVersion ||
419+
// verify a valid version
420+
!cservice.locals.proxy.versions.hasOwnProperty(k)) {
421+
continue; // skip
422+
}
423+
var v = cservice.locals.proxy.versions[k];
424+
var diff_s = (now - v.lastAccess) / 1000; // seconds
425+
if (diff_s < cservice.locals.proxy.options.nonDefaultWorkerIdleTime) {
426+
continue; // all OK
427+
}
428+
429+
cservice.log("Proxy version ".warn + k.info + " shutting down due to inactivity".warn);
430+
431+
// kill all the things
432+
version(k, { workerCount: 0 });
433+
}
434+
}

package.json

+1-1
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
{
22
"name": "cluster-service",
3-
"version": "2.0.0-alpha1",
3+
"version": "2.0.0-alpha2",
44
"author": {
55
"name": "Aaron Silvas",
66
"email": "[email protected]"

0 commit comments

Comments
 (0)