"use strict";Object.defineProperty(exports, "__esModule", { value: true });exports.ActualCodeSandbox = void 0;var fs = _interopRequireWildcard(require("fs"));
var os = _interopRequireWildcard(require("os"));
var path = _interopRequireWildcard(require("path"));
var _util = require("util");function _interopRequireWildcard(obj) {if (obj && obj.__esModule) {return obj;} else {var newObj = {};if (obj != null) {for (var key in obj) {if (Object.prototype.hasOwnProperty.call(obj, key)) {var desc = Object.defineProperty && Object.getOwnPropertyDescriptor ? Object.getOwnPropertyDescriptor(obj, key) : {};if (desc.get || desc.set) {Object.defineProperty(newObj, key, desc);} else {newObj[key] = obj[key];}}}}newObj.default = obj;return newObj;}}function _defineProperty(obj, key, value) {if (key in obj) {Object.defineProperty(obj, key, { value: value, enumerable: true, configurable: true, writable: true });} else {obj[key] = value;}return obj;}

const mkdtemp = (0, _util.promisify)(fs.mkdtemp);
const writeFile = (0, _util.promisify)(fs.writeFile);























const mergeOption = (
opt1,
opt2) =>
{
  return {
    timeout: opt2.timeout || opt1.timeout,
    runMode: 'runMode' in opt2 ? opt2.runMode : opt1.runMode,
    browser: opt2.browser || opt1.browser,
    file: opt2.file };

};






class ActualCodeSandbox {






  constructor(actualCode, reporter) {_defineProperty(this, "_actualCode", void 0);_defineProperty(this, "_reporter", void 0);_defineProperty(this, "_boxes", []);_defineProperty(this, "_rootPath", void 0);_defineProperty(this, "_init", void 0);
    this._reporter = reporter;
    this._actualCode = actualCode;
    this._reporter.debug('create Sandbox');
    const init = async () => {
      this._rootPath = await mkdtemp(path.join(os.tmpdir(), 'actual-'));
      process.chdir(this._rootPath);
    };
    this._init = init();
  }

  async addPlugin(plugin) {
    await this._init;
    this._boxes.push((await plugin(this._reporter, this._rootPath)));
  }

  async run(codeBlock, opts) {
    await this._init;
    const { code, lang, meta, hash } = codeBlock;
    const opts2 = mergeOption(opts, meta);

    if (meta.plugin) {
      await this._actualCode.registerPlugin(code);
      return;
    }
    if (!opts2.runMode) {
      this._reporter.event('sandbox skip', { hash });
      return;
    }

    this._reporter.event('sandbox run', { hash });

    if (opts2.file) {
      await writeFile(opts2.file, code);
    }

    for (const box of this._boxes) {
      if (await box.run(code, hash, lang, opts2)) {
        break;
      }
    }
    this._reporter.event('sandbox end', { hash });
  }}exports.ActualCodeSandbox = ActualCodeSandbox;