"use strict";

Object.defineProperty(exports, "__esModule", {
  value: true
});
exports.CustomAttributesPlugin = void 0;

var _htmlWebpackInjectAttributesPlugin = _interopRequireDefault(require("html-webpack-inject-attributes-plugin"));

var _webpack = require("webpack");

function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }

const pluginName = 'CustomAttributesPlugin';

function attributeSetTemplate(attributes, variableName) {
  const str = [];
  Object.keys(attributes).forEach(key => {
    const val = attributes[key];
    str.push(`${variableName}.setAttribute(${JSON.stringify(key)}, ${JSON.stringify(val)});`);
  });
  return str;
}

function writeCss(attributes, code) {
  const str = attributeSetTemplate(attributes, 'linkTag');
  return code.replace('document.head.appendChild(linkTag);', `${str.join('')}document.head.appendChild(linkTag);`);
}

function writeI18nJs(attributes, code) {
  const str = attributeSetTemplate(attributes, 'scripTag');
  return code.replace('document.head.appendChild(scriptTag);', `{${str.join('')} document.head.appendChild(scriptTag)};`);
}

function writeJs(attributes, code) {
  const str = attributeSetTemplate(attributes, 'script');
  return code.replace('needAttach && document.head.appendChild(script);', `if(needAttach) {${str.join('')} document.head.appendChild(script)};`);
}

class CustomAttributesPlugin {
  constructor(options) {
    this.options = {
      attributes: options.attributes,
      jsAttributes: options.jsAttributes || options.attributes || {},
      cssAttributes: options.cssAttributes || options.attributes || {},
      i18nAttributes: options.i18nAttributes || options.attributes || {}
    };
  }

  apply(compiler) {
    const {
      RawSource
    } = compiler.webpack.sources; // NOTE: we not using this, Reason currently this option is only need for EFC,
    // So it do not needed.

    const {
      attributes
    } = this.options;
    attributes && new _htmlWebpackInjectAttributesPlugin.default(attributes).apply(compiler);
    compiler.hooks.thisCompilation.tap(pluginName, compilation => {
      compilation.hooks.processAssets.tap({
        name: pluginName,
        stage: _webpack.Compilation.PROCESS_ASSETS_STAGE_DERIVED
      }, assets => {
        const asset = Object.keys(assets).filter(k => /runtime.*\.js$/g.test(k));
        asset.forEach(e => {
          const runtimeJS = assets[e];
          let code = runtimeJS.source();
          code = writeCss(this.options.cssAttributes, code);
          code = writeI18nJs(this.options.i18nAttributes, code);
          code = writeJs(this.options.jsAttributes, code);
          compilation.updateAsset(e, new RawSource(code));
        });
      });
    });
  }

}

exports.CustomAttributesPlugin = CustomAttributesPlugin;