UNPKG

sententiaregum-flux-container

Version:

The flux implementation of the sententiaregum project based on facebook/flux

175 lines (145 loc) 6.61 kB
/* * This file is part of the Sententiaregum project. * * (c) Maximilian Bosch <maximilian.bosch.27@gmail.com> * (c) Ben Bieler <benjaminbieler2014@gmail.com> * * For the full copyright and license information, please view the LICENSE * file that was distributed with this source code. */ 'use strict'; Object.defineProperty(exports, "__esModule", { value: true }); var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }(); var _invariant = require('invariant'); var _invariant2 = _interopRequireDefault(_invariant); var _deepEqual = require('deep-equal'); var _deepEqual2 = _interopRequireDefault(_deepEqual); var _runAction = require('../runAction'); var _runAction2 = _interopRequireDefault(_runAction); var _Dispatcher = require('../dispatcher/Dispatcher'); var _Dispatcher2 = _interopRequireDefault(_Dispatcher); function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; } function _toConsumableArray(arr) { if (Array.isArray(arr)) { for (var i = 0, arr2 = Array(arr.length); i < arr.length; i++) { arr2[i] = arr[i]; } return arr2; } else { return Array.from(arr); } } 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; } function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } } /** * Builds an error message for failed assertions. * * @param {String} kind Which kind of data mismatched. * @param {*} expected Expected dataset. * @param {*} actual Actual dataset. * * @returns {String} The error message. */ function getErrorMessage(kind, expected, actual) { return 'Can\'t match the expected ' + kind + ' (' + JSON.stringify(expected) + ') with actual ' + kind + ' (' + JSON.stringify(actual) + ')!'; } /** * API for testing utility. * * @author Maximilian Bosch <maximilian.bosch.27@gmail.com> */ exports.default = new (function () { function _class() { _classCallCheck(this, _class); } _createClass(_class, [{ key: 'clear', /** * Clear. * * As the dispatcher is an internal API which is stateful, it needs to be ensured that everything will be * cleared properly before running tests. * * @returns {void} */ value: function clear() { _Dispatcher2.default.reset(); } /** * Executes an action and returns a function to match the payload. * This is helpful when unittesting the way how action creators should work. * * Example: * * describe('TestUtils', () => { * it('single test', () => { * TestUtils.executeAction(actionCreator, event, args)(expected); * }); * }); * * @param {Function} actionCreator The creator which should be tested. * @param {String} event The event of the action creator to be tested. * @param {Array.<*>} args The arguments used in that event. * * @returns {Function} The function used assert the result. */ }, { key: 'executeAction', value: function executeAction(actionCreator, event, args) { this.clear(); return function (expected) { var _actionCreator; var events = arguments.length <= 1 || arguments[1] === undefined ? [] : arguments[1]; var dispatched = arguments.length <= 2 || arguments[2] === undefined ? {} : arguments[2]; var list = {}; events.forEach(function (event) { return _Dispatcher2.default.addListener(event, function (payload) { return Object.assign(list, _defineProperty({}, event, payload)); }); }); (_actionCreator = actionCreator())[event].apply(_actionCreator, [function (payload) { return (0, _invariant2.default)((0, _deepEqual2.default)(payload, expected), getErrorMessage('payload', expected, payload)); }].concat(_toConsumableArray(args))); if (Object.keys(list).length > 0) { Object.keys(dispatched).forEach(function (event) { (0, _invariant2.default)(typeof list[event] !== 'undefined', 'Missing event "' + event + '"!'); (0, _invariant2.default)((0, _deepEqual2.default)(dispatched[event], list[event]), getErrorMessage('payload', dispatched[event], list[event])); }); } }; } /** * Uses the runAction API to check whether actions and stores interact correctly. * This sort of integrative tests is helpful when ensuring that the interaction between the components * behaves as expected. * * Example: * * describe('TestUtils', () => { * it('single test', () => { * TestUtils.executeAction(actionCreator, event, args)(expected, storeToValidate); * // or * TestUtils.executeAction(actionCreator, event, args)([expected1, expected2], [store1, store2]); * }); * }); * * @param actionCreator * @param event * @param args * @returns {function(*=, *)} */ }, { key: 'executeFullWorkflow', value: function executeFullWorkflow(actionCreator, event) { var args = arguments.length <= 2 || arguments[2] === undefined ? [] : arguments[2]; (0, _runAction2.default)(event, actionCreator, args); return function (expected, stores) { var compareWithState = function compareWithState(state, expected) { (0, _invariant2.default)((0, _deepEqual2.default)(expected, state), getErrorMessage('state', expected, state)); }; if (!Array.isArray(stores)) { compareWithState(stores.getState(), expected); return; } (0, _invariant2.default)(Array.isArray(expected), 'A list of expected values is needed when asserting against multiple stores!'); stores.forEach(function (store, i) { return compareWithState(store.getState(), expected[i]); }); }; } }]); return _class; }())();