/*
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *   http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing,
 * software distributed under the License is distributed on an
 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
 * KIND, either express or implied.  See the License for the
 * specific language governing permissions and limitations
 * under the License.
 *
*/

var fs = require('fs-extra');
var path = require('path');
var endent = require('endent');
var mungeutil = require('./ConfigChanges/munge-util');

function PlatformJson (filePath, platform, root) {
    this.filePath = filePath;
    this.platform = platform;
    this.root = fix_munge(root || {});
}

PlatformJson.load = function (plugins_dir, platform) {
    var filePath = path.join(plugins_dir, platform + '.json');
    var root = null;
    if (fs.existsSync(filePath)) {
        root = JSON.parse(fs.readFileSync(filePath, 'utf-8'));
    }
    return new PlatformJson(filePath, platform, root);
};

PlatformJson.prototype.save = function () {
    fs.outputJsonSync(this.filePath, this.root, { spaces: 2 });
};

/**
 * Indicates whether the specified plugin is installed as a top-level (not as
 *  dependency to others)
 * @method function
 * @param  {String} pluginId A plugin id to check for.
 * @return {Boolean} true if plugin installed as top-level, otherwise false.
 */
PlatformJson.prototype.isPluginTopLevel = function (pluginId) {
    return this.root.installed_plugins[pluginId];
};

/**
 * Indicates whether the specified plugin is installed as a dependency to other
 *  plugin.
 * @method function
 * @param  {String} pluginId A plugin id to check for.
 * @return {Boolean} true if plugin installed as a dependency, otherwise false.
 */
PlatformJson.prototype.isPluginDependent = function (pluginId) {
    return this.root.dependent_plugins[pluginId];
};

/**
 * Indicates whether plugin is installed either as top-level or as dependency.
 * @method function
 * @param  {String} pluginId A plugin id to check for.
 * @return {Boolean} true if plugin installed, otherwise false.
 */
PlatformJson.prototype.isPluginInstalled = function (pluginId) {
    return this.isPluginTopLevel(pluginId) ||
        this.isPluginDependent(pluginId);
};

PlatformJson.prototype.addPlugin = function (pluginId, variables, isTopLevel) {
    var pluginsList = isTopLevel
        ? this.root.installed_plugins
        : this.root.dependent_plugins;

    pluginsList[pluginId] = variables;

    return this;
};

/**
 * @chaining
 * Generates and adds metadata for provided plugin into associated <platform>.json file
 *
 * @param   {PluginInfo}  pluginInfo  A pluginInfo instance to add metadata from
 * @returns {this} Current PlatformJson instance to allow calls chaining
 */
PlatformJson.prototype.addPluginMetadata = function (pluginInfo) {
    var installedModules = this.root.modules || [];

    var installedPaths = installedModules.map(function (installedModule) {
        return installedModule.file;
    });

    var modulesToInstall = pluginInfo.getJsModules(this.platform)
        .map(function (module) {
            return new ModuleMetadata(pluginInfo.id, module);
        })
        .filter(function (metadata) {
            // Filter out modules which are already added to metadata
            return !installedPaths.includes(metadata.file);
        });

    this.root.modules = installedModules.concat(modulesToInstall);

    this.root.plugin_metadata = this.root.plugin_metadata || {};
    this.root.plugin_metadata[pluginInfo.id] = pluginInfo.version;

    return this;
};

PlatformJson.prototype.removePlugin = function (pluginId, isTopLevel) {
    var pluginsList = isTopLevel
        ? this.root.installed_plugins
        : this.root.dependent_plugins;

    delete pluginsList[pluginId];

    return this;
};

/**
 * @chaining
 * Removes metadata for provided plugin from associated file
 *
 * @param   {PluginInfo}  pluginInfo A PluginInfo instance to which modules' metadata
 *   we need to remove
 *
 * @returns {this} Current PlatformJson instance to allow calls chaining
 */
PlatformJson.prototype.removePluginMetadata = function (pluginInfo) {
    var modulesToRemove = pluginInfo.getJsModules(this.platform)
        .map(function (jsModule) {
            return ['plugins', pluginInfo.id, jsModule.src].join('/');
        });

    var installedModules = this.root.modules || [];
    this.root.modules = installedModules
        .filter(function (installedModule) {
            // Leave only those metadatas which 'file' is not in removed modules
            return !modulesToRemove.includes(installedModule.file);
        });

    if (this.root.plugin_metadata) {
        delete this.root.plugin_metadata[pluginInfo.id];
    }

    return this;
};

PlatformJson.prototype.addInstalledPluginToPrepareQueue = function (pluginDirName, vars, is_top_level, force) {
    this.root.prepare_queue.installed.push({ plugin: pluginDirName, vars: vars, topLevel: is_top_level, force: force });
};

PlatformJson.prototype.addUninstalledPluginToPrepareQueue = function (pluginId, is_top_level) {
    this.root.prepare_queue.uninstalled.push({ plugin: pluginId, id: pluginId, topLevel: is_top_level });
};

/**
 * Moves plugin, specified by id to top-level plugins. If plugin is top-level
 *  already, then does nothing.
 * @method function
 * @param  {String} pluginId A plugin id to make top-level.
 * @return {PlatformJson} PlatformJson instance.
 */
PlatformJson.prototype.makeTopLevel = function (pluginId) {
    var plugin = this.root.dependent_plugins[pluginId];
    if (plugin) {
        delete this.root.dependent_plugins[pluginId];
        this.root.installed_plugins[pluginId] = plugin;
    }
    return this;
};

/**
 * Generates a metadata for all installed plugins and js modules. The resultant
 *   string is ready to be written to 'cordova_plugins.js'
 *
 * @returns {String} cordova_plugins.js contents
 */
PlatformJson.prototype.generateMetadata = function () {
    const stringify = o => JSON.stringify(o, null, 2);
    return endent`
        cordova.define('cordova/plugin_list', function(require, exports, module) {
          module.exports = ${stringify(this.root.modules)};
          module.exports.metadata = ${stringify(this.root.plugin_metadata)};
        });
    `;
};

/**
 * @chaining
 * Generates and then saves metadata to specified file. Doesn't check if file exists.
 *
 * @param {String} destination  File metadata will be written to
 * @return {PlatformJson} PlatformJson instance
 */
PlatformJson.prototype.generateAndSaveMetadata = function (destination) {
    fs.outputFileSync(destination, this.generateMetadata());

    return this;
};

// convert a munge from the old format ([file][parent][xml] = count) to the current one
function fix_munge (root) {
    root.prepare_queue = root.prepare_queue || { installed: [], uninstalled: [] };
    root.config_munge = root.config_munge || { files: {} };
    root.installed_plugins = root.installed_plugins || {};
    root.dependent_plugins = root.dependent_plugins || {};

    var munge = root.config_munge;
    if (!munge.files) {
        var new_munge = { files: {} };
        for (var file in munge) {
            for (var selector in munge[file]) {
                for (var xml_child in munge[file][selector]) {
                    var val = parseInt(munge[file][selector][xml_child]);
                    for (var i = 0; i < val; i++) {
                        mungeutil.deep_add(new_munge, [file, selector, { xml: xml_child, count: val }]);
                    }
                }
            }
        }
        root.config_munge = new_munge;
    }

    return root;
}

/**
 * @constructor
 * @class ModuleMetadata
 *
 * Creates a ModuleMetadata object that represents module entry in 'cordova_plugins.js'
 *   file at run time
 *
 * @param {String}  pluginId  Plugin id where this module installed from
 * @param (JsModule|Object)  jsModule  A js-module entry from PluginInfo class to generate metadata for
 */
function ModuleMetadata (pluginId, jsModule) {
    if (!pluginId) throw new TypeError('pluginId argument must be a valid plugin id');
    if (!jsModule.src && !jsModule.name) throw new TypeError('jsModule argument must contain src or/and name properties');

    this.id = pluginId + '.' + (jsModule.name || jsModule.src.match(/([^/]+)\.js/)[1]);
    this.file = ['plugins', pluginId, jsModule.src].join('/');
    this.pluginId = pluginId;

    if (jsModule.clobbers && jsModule.clobbers.length > 0) {
        this.clobbers = jsModule.clobbers.map(function (o) { return o.target; });
    }
    if (jsModule.merges && jsModule.merges.length > 0) {
        this.merges = jsModule.merges.map(function (o) { return o.target; });
    }
    if (jsModule.runs) {
        this.runs = true;
    }
}

module.exports = PlatformJson;
