UNPKG

redux-ab-test

Version:

A/B testing React components with Redux and debug tools. Isomorphic with a simple, universal interface. Well documented and lightweight. Tested in popular browsers and Node.js. Includes helpers for React, Redux, and Segment.io

215 lines (182 loc) 8.91 kB
'use strict'; var _keys = require('babel-runtime/core-js/object/keys'); var _keys2 = _interopRequireDefault(_keys); var _stringify = require('babel-runtime/core-js/json/stringify'); var _stringify2 = _interopRequireDefault(_stringify); var _immutable = require('immutable'); var _immutable2 = _interopRequireDefault(_immutable); var _randomVariation = require('./random-variation'); var _randomVariation2 = _interopRequireDefault(_randomVariation); function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { 'default': obj }; } describe('utils/random-variation.js', function () { describe('toWeight', function () { it('exists', function () { expect(_randomVariation.toWeight).not.toBeUndefined; }); it('has the correct weight', function () { expect((0, _randomVariation.toWeight)(_immutable2['default'].Map({ weight: 100 }))).toEqual(100); expect((0, _randomVariation.toWeight)(_immutable2['default'].Map({ weight: -100 }))).toEqual(-100); }); it('has the default weight', function () { expect((0, _randomVariation.toWeight)(_immutable2['default'].Map({}))).toEqual(0); expect((0, _randomVariation.toWeight)(_immutable2['default'].Map({ weight: undefined }))).toEqual(0); }); }); describe('toTotal', function () { it('exists', function () { expect(_randomVariation.toTotal).not.toBeUndefined; }); it('has the correct total', function () { expect((0, _randomVariation.toTotal)(_immutable2['default'].fromJS([{ weight: 100 }]))).toEqual(100); expect((0, _randomVariation.toTotal)(_immutable2['default'].fromJS([{ weight: 100 }, { weight: 200 }]))).toEqual(300); expect((0, _randomVariation.toTotal)(_immutable2['default'].fromJS([{ weight: 100 }, { weight: 200 }, { weight: 300 }]))).toEqual(600); }); it('has the default total', function () { expect((0, _randomVariation.toTotal)(_immutable2['default'].fromJS([]))).toEqual(0); }); }); describe('toRange', function () { it('exists', function () { expect(_randomVariation.toRange).not.toBeUndefined; }); it('has the correct range[0]', function () { var list = _immutable2['default'].List([]); list = (0, _randomVariation.toRange)(list, 5000); expect(list).not.toBeUndefined; expect(list.count()).toEqual(1); var range = list.last(); expect(range.first()).toEqual(0); expect(range.last()).toEqual(4999); }); it('has the correct range[1]', function () { var list = _immutable2['default'].List([_immutable2['default'].Range(0, 5000)]); list = (0, _randomVariation.toRange)(list, 5000); expect(list).not.toBeUndefined; expect(list.count()).toEqual(2); var range = list.last(); expect(range.first()).toEqual(5000); expect(range.last()).toEqual(9999); }); it('has the correct range[2]', function () { var list = _immutable2['default'].List([_immutable2['default'].Range(0, 5000), _immutable2['default'].Range(5000, 10000)]); list = (0, _randomVariation.toRange)(list, 10000); expect(list).not.toBeUndefined; expect(list.count()).toEqual(3); var range = list.last(); expect(range.first()).toEqual(10000); expect(range.last()).toEqual(19999); }); it('has the correct range[3]', function () { var list = _immutable2['default'].List([_immutable2['default'].Range(0, 5000), _immutable2['default'].Range(5000, 10000), _immutable2['default'].Range(10000, 20000)]); list = (0, _randomVariation.toRange)(list, 0); expect(list).not.toBeUndefined; expect(list.count()).toEqual(4); var range = list.last(); expect(range.first()).toBeUndefined; expect(range.last()).toBeUndefined; }); }); describe('toRanges', function () { it('exists', function () { expect(_randomVariation.toRanges).not.toBeUndefined; }); it('has the correct ranges', function () { var weights = _immutable2['default'].fromJS([{ weight: 5000 }, { weight: 5000 }, { weight: 10000 }, { weight: 0 }]); var ranges = (0, _randomVariation.toRanges)(weights); expect(ranges).not.toBeUndefined; expect(ranges.count()).toEqual(4); expect((0, _stringify2['default'])(ranges.map(function (i) { return i.first() + '/' + i.last(); }))).toEqual('["0/4999","5000/9999","10000/19999","undefined/undefined"]'); expect(ranges.get(0).first()).toEqual(0); expect(ranges.get(0).last()).toEqual(4999); expect(ranges.get(1).first()).toEqual(5000); expect(ranges.get(1).last()).toEqual(9999); expect(ranges.get(2).first()).toEqual(10000); expect(ranges.get(2).last()).toEqual(19999); expect(ranges.get(3).first()).toBeUndefined; expect(ranges.get(3).last()).toBeUndefined; }); it('has the correct ranges', function () { var weights = _immutable2['default'].fromJS([{ weight: 5000 }, { weight: 5000 }, { weight: 10000 }, { weight: 0 }, { weight: 0 }, { weight: 0 }]); var ranges = (0, _randomVariation.toRanges)(weights); expect(ranges).not.toBeUndefined; expect(ranges.count()).toEqual(6); expect((0, _stringify2['default'])(ranges.map(function (i) { return i.first() + '/' + i.last(); }))).toEqual('["0/4999","5000/9999","10000/19999","undefined/undefined","undefined/undefined","undefined/undefined"]'); expect(ranges.get(0).first()).toEqual(0); expect(ranges.get(0).last()).toEqual(4999); expect(ranges.get(1).first()).toEqual(5000); expect(ranges.get(1).last()).toEqual(9999); expect(ranges.get(2).first()).toEqual(10000); expect(ranges.get(2).last()).toEqual(19999); expect(ranges.get(3).first()).toBeUndefined; expect(ranges.get(3).last()).toBeUndefined; expect(ranges.get(4).first()).toBeUndefined; expect(ranges.get(4).last()).toBeUndefined; expect(ranges.get(5).first()).toBeUndefined; expect(ranges.get(5).last()).toBeUndefined; }); it('has the default ranges', function () { var weights = _immutable2['default'].fromJS([]); var ranges = (0, _randomVariation.toRanges)(weights); expect(ranges.count()).toEqual(0); }); }); describe('randomVariation', function () { var experiment = _immutable2['default'].fromJS({ variations: [{ name: 'Variation A', weight: 5000 }, { name: 'Variation B', weight: 5000 }, { name: 'Original', weight: 10000 }, { name: 'Variation Disabled', weight: 0 }] }); it('exists', function () { expect(_randomVariation2['default']).not.toBeUndefined; }); it('sorts the variations by weight descending', function () { var output = experiment.get('variations').sortBy(_randomVariation.toWeight).reverse(); expect(output).not.toBeUndefined; expect(_immutable2['default'].List.isList(output)).toBeTruthy; expect(output.get(0).get('name')).toEqual('Original'); expect(output.get(1).get('name')).toEqual('Variation B'); expect(output.get(2).get('name')).toEqual('Variation A'); expect(output.get(3).get('name')).toEqual('Variation Disabled'); }); it('returns an Immutable.Map', function () { var output = (0, _randomVariation2['default'])(experiment); expect(output).not.toBeUndefined; expect(_immutable2['default'].Map.isMap(output)).toBeTruthy; expect((0, _keys2['default'])(output.toJS())).toEqual(['name', 'weight']); }); var sharedContext = function () { function sharedContext(i, variationName) { it('returns the expected variation for i=' + i, function () { var random = function () { function random() { return i; } return random; }(); var output = (0, _randomVariation2['default'])(experiment, random); expect(output).not.toBeUndefined; expect(_immutable2['default'].Map.isMap(output)).toBeTruthy; expect((0, _keys2['default'])(output.toJS())).toEqual(['name', 'weight']); expect(output.get('name')).toEqual(variationName); }); } return sharedContext; }(); // Returns the variations with weight!=0 when Math.random is within the expected range [0, 1) _immutable2['default'].Range(0.0, 0.50, 0.05).forEach(function (i) { return sharedContext(i, 'Original'); }); _immutable2['default'].Range(0.50, 0.75, 0.01).forEach(function (i) { return sharedContext(i, 'Variation B'); }); _immutable2['default'].Range(0.75, 1.00, 0.01).forEach(function (i) { return sharedContext(i, 'Variation A'); }); // Returns the variation with weight=0 when Math.random is outside of the expected range [0,1) _immutable2['default'].Range(1.00, 1.01, 0.01).forEach(function (i) { return sharedContext(i, 'Variation Disabled'); }); }); });