UNPKG

gpii-universal

Version:

Cross platform, core components of the GPII personalization infrastructure.

119 lines (104 loc) 6.35 kB
/*! GPII Exploding Settings Handler Copyright 2018 Raising the Floor - International Licensed under the New BSD license. You may not use this file except in compliance with this License. You may obtain a copy of the License at https://github.com/gpii/universal/LICENSE.txt */ "use strict"; var fluid = require("infusion"), gpii = fluid.registerNamespace("gpii"); fluid.registerNamespace("gpii.settingsHandlers.exploding"); /** The exploding settings handler is used in both automated and manual tests in order to verify that errors which occur * when reading or writing system settings are appropriately signalled to the user. To aid in doing this, it accepts * various material in its settings payload encoding the method to be used when failing, and special preference sets * have been drawn up to be used in manual testing which make use of these payloads */ /** * The payload type sent to some exploding settings handler methods. * @typedef {Object} {ExplodingPayload} * @property {String} operation - Either "get" or "set" depending on which settings handler method was requested * @property {String} explodeOn - Either "get" or "set" depending on which settings handler method was required to explode * @property {Object} errorPayload - [optional] An error payload (with member `isError: true`) which should be sent to either the * "reject" or "throw" operations if either of these was requested in `explodeMethod` * @property {String} explodeMethod - Either: * "reject", if the explosion should be signalled via returning a rejected promise * "fail", if the explosion should be signalled via calling `fluid.fail` * "throw", if the explosion should be signalled by throwing a bare execption */ /** The implementation for the exploding settings handler. * @param {String} operation - Either "get" or "set" * @param {ExplodingPayload} explodeSettings - Settings payload describing whether the settings handler should explode * @return {Promise|None} A rejected promise if the operation should explode and the payload requested that it should do so by returning a rejected promise */ gpii.settingsHandlers.exploding.explode = function (operation, explodeSettings) { var errorMessage = "Exploding settings handler has failed on " + operation + " method"; var errorPayload = explodeSettings.errorPayload || { isError: true, message: errorMessage }; if (explodeSettings.explodeMethod === "reject") { return fluid.promise().reject(errorPayload); } else if (explodeSettings.explodeMethod === "fail") { fluid.fail(errorMessage); } else if (explodeSettings.explodeMethod === "throw") { throw new Error(errorMessage); } }; /** Global store for mock solution running state **/ gpii.settingsHandlers.exploding.runningState = { running: false }; /** Return an explosion or settings, depending on whether the operation in progress matches the one designated to explode * @param {String} operation - Either "get", "set", "launch" or "stop" * @param {ExplodingPayload} explodeSettings - Settings payload describing whether the settings handler should explode * @param {Object} settings - Settings handler options which may include a member * {Boolean} options.launchHandler Set to `true` if this settings handler is being invoked as a launch handler * {Object} options.preferences The user's entire preference set (for tunnelling launch settings) * @return {Promise|Value} A rejected promise if an error should have been signalled, and should have been signalled by that method, or otherwise the * appropriate get/set settingsHandler payload. */ gpii.settingsHandlers.exploding.determineExplode = function (operation, explodeSettings, settings) { if (explodeSettings.explodeOn === operation) { return gpii.settingsHandlers.exploding.explode(operation, explodeSettings); } else { if (operation === "get") { return "running" in settings ? gpii.settingsHandlers.exploding.runningState : settings; } else { return "running" in settings ? {running: {newValue: settings.running, oldValue: !settings.running}} : fluid.transform(settings, function (value) { return {newValue: value}; }); } } }; /** Core implementation of the exploding settings handler. * @param {String} operation - Either "get" or "set" * @param {ExplodingPayload|Object} settings - Settings payload describing whether the settings handler should explode, or standard settings payload * @param {Object} options - Settings handler options which may include a member * {Boolean} options.launchHandler Set to `true` if this settings handler is being invoked as a launch handler * {Object} options.preferences The user's entire preference set (for tunnelling launch settings) * @return {Promise|Value} A rejected promise if an error should have been signalled, and should have been signalled by that method, or the * original input payload if no error should be signalled. */ // In the case of "launch"/"stop" interception we use hard-coded knowledge of the exact structure of the preference set as // being explodeLaunchHandlerXxxxx.json gpii.settingsHandlers.exploding.impl = function (operation, settings, options) { if (options && options.launchHandler && operation === "set") { gpii.settingsHandlers.exploding.runningState.running = settings.running; var launchOperation = settings.running ? "launch" : "stop"; var launchSettings = fluid.get(options, ["preferences", "contexts", "gpii-default", "preferences", "http://registry.gpii.net/applications/net.gpii.explode"]); return gpii.settingsHandlers.exploding.determineExplode(launchOperation, launchSettings, settings); } else { return gpii.settingsHandlers.exploding.determineExplode(operation, settings, settings); } }; // Top-level driver methods for SettingsHandler ["get", "set"].forEach(function (operation) { gpii.settingsHandlers.exploding[operation] = function (payload) { return gpii.settingsHandlers.invokeSettingsHandler(function (payload) { return gpii.settingsHandlers.exploding.impl(operation, payload.settings, payload.options); }, payload); }; });