Commit 5bff61c2ca4ad1436e8b8324b85a382e3541d9b1

Authored by Igor Kulikov
1 parent da7da1ef

Improve JS Executor: add max active scripts parameter

... ... @@ -27,11 +27,13 @@ const config = require('config'),
27 27
28 28 const scriptBodyTraceFrequency = Number(config.get('script.script_body_trace_frequency'));
29 29 const useSandbox = config.get('script.use_sandbox') === 'true';
  30 +const maxActiveScripts = Number(config.get('script.max_active_scripts'));
30 31
31 32 function JsInvokeMessageProcessor(producer) {
32 33 this.producer = producer;
33 34 this.executor = new JsExecutor(useSandbox);
34 35 this.scriptMap = {};
  36 + this.scriptIds = [];
35 37 this.executedScriptsCounter = 0;
36 38 }
37 39
... ... @@ -70,7 +72,7 @@ JsInvokeMessageProcessor.prototype.processCompileRequest = function(requestId, r
70 72
71 73 this.executor.compileScript(compileRequest.scriptBody).then(
72 74 (script) => {
73   - this.scriptMap[scriptId] = script;
  75 + this.cacheScript(scriptId, script);
74 76 var compileResponse = createCompileResponse(scriptId, true);
75 77 logger.debug('[%s] Sending success compile response, scriptId: [%s]', requestId, scriptId);
76 78 this.sendResponse(requestId, responseTopic, scriptId, compileResponse);
... ... @@ -126,6 +128,10 @@ JsInvokeMessageProcessor.prototype.processReleaseRequest = function(requestId, r
126 128 var scriptId = getScriptId(releaseRequest);
127 129 logger.debug('[%s] Processing release request, scriptId: [%s]', requestId, scriptId);
128 130 if (this.scriptMap[scriptId]) {
  131 + var index = this.scriptIds.indexOf(scriptId);
  132 + if (index > -1) {
  133 + this.scriptIds.splice(index, 1);
  134 + }
129 135 delete this.scriptMap[scriptId];
130 136 }
131 137 var releaseResponse = createReleaseResponse(scriptId, true);
... ... @@ -165,7 +171,7 @@ JsInvokeMessageProcessor.prototype.getOrCompileScript = function(scriptId, scrip
165 171 } else {
166 172 self.executor.compileScript(scriptBody).then(
167 173 (script) => {
168   - self.scriptMap[scriptId] = script;
  174 + self.cacheScript(scriptId, script);
169 175 resolve(script);
170 176 },
171 177 (err) => {
... ... @@ -176,6 +182,19 @@ JsInvokeMessageProcessor.prototype.getOrCompileScript = function(scriptId, scrip
176 182 });
177 183 }
178 184
  185 +JsInvokeMessageProcessor.prototype.cacheScript = function(scriptId, script) {
  186 + if (!this.scriptMap[scriptId]) {
  187 + this.scriptIds.push(scriptId);
  188 + while (this.scriptIds.length > maxActiveScripts) {
  189 + logger.info('Active scripts count [%s] exceeds maximum limit [%s]', this.scriptIds.length, maxActiveScripts);
  190 + const prevScriptId = this.scriptIds.shift();
  191 + logger.info('Removing active script with id [%s]', prevScriptId);
  192 + delete this.scriptMap[prevScriptId];
  193 + }
  194 + }
  195 + this.scriptMap[scriptId] = script;
  196 +}
  197 +
179 198 function createRemoteResponse(requestId, compileResponse, invokeResponse, releaseResponse) {
180 199 const requestIdBits = Utils.UUIDToBits(requestId);
181 200 return {
... ...
... ... @@ -27,3 +27,4 @@ logger:
27 27 script:
28 28 use_sandbox: "SCRIPT_USE_SANDBOX"
29 29 script_body_trace_frequency: "SCRIPT_BODY_TRACE_FREQUENCY"
  30 + max_active_scripts: "MAX_ACTIVE_SCRIPTS"
... ...
... ... @@ -28,3 +28,4 @@ logger:
28 28 script:
29 29 use_sandbox: "true"
30 30 script_body_trace_frequency: "1000"
  31 + max_active_scripts: "1000"
... ...