'use strict';

Object.defineProperty(exports, "__esModule", {
  value: true
});
var timeoutIDs = [];

var renderIf = exports.renderIf = function renderIf(condition) {
  return function (component) {
    return condition && component;
  };
};

var limitEval = exports.limitEval = function limitEval(code, fnOnStop) {
  var opt_timeoutInMS = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : 1000;

  // Chris West http://cwestblog.com/2016/03/16/javascript-detecting-infinite-loops/

  function clearTimeouts() {
    timeoutIDs.forEach(function (id) {
      clearTimeout(id);
    });
    timeoutIDs = [];
  }

  var id = Math.random() + 1;
  var blob = new Blob(['onmessage = function (message){\n        const data = message.data;\n\n        // increment id and send message back to parent process\n        // before executing code. This will start the setTimeout\n        postMessage({ id: data.id + 1 });\n\n        // if data.code evaluates in time,\n        // a new message is sent with the original ID\n        // If not, the setTimeout callback will kill the worker\n        // TODO: check for syntax errors in data.code\n        postMessage({ returnedVal: eval.call(this, data.code) , id:data.id });\n      };'], { type: 'text/javascript' });
  var myWorker = new Worker(URL.createObjectURL(blob));

  // eslint-disable-next-line no-unused-vars
  function onDone(success) {
    clearTimeouts();
    URL.revokeObjectURL(blob);
    fnOnStop.apply(this, arguments);
  }

  myWorker.onmessage = function (message) {
    var data = message.data;
    if (data) {
      if (data.id === id) {
        id = 0;
        onDone(true, data.returnedVal);
      } else if (data.id === id + 1) {
        var timeoutID = setTimeout(function killWorker() {
          // if the code successfully ran, id === 0
          if (id) {
            myWorker.terminate();
            onDone(false);
          }
        }, opt_timeoutInMS);
        timeoutIDs.push(timeoutID);
      }
    }
  };

  myWorker.postMessage({ code: code, id: id });
};