"use strict";

var _treeSelector = require("../tree-selector");

var _ramda = _interopRequireDefault(require("ramda"));

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

function _objectSpread(target) { for (var i = 1; i < arguments.length; i++) { var source = arguments[i] != null ? arguments[i] : {}; var ownKeys = Object.keys(source); if (typeof Object.getOwnPropertySymbols === 'function') { ownKeys = ownKeys.concat(Object.getOwnPropertySymbols(source).filter(function (sym) { return Object.getOwnPropertyDescriptor(source, sym).enumerable; })); } ownKeys.forEach(function (key) { _defineProperty(target, key, source[key]); }); } return target; }

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; }

var hierarchy = {
  root: {
    name: 'Root',
    children: ['a', 'b']
  },
  a: {
    name: 'A',
    parentId: 'root',
    children: ['a1', 'a2']
  },
  a1: {
    name: 'A1',
    parentId: 'a',
    children: ['a11']
  },
  a2: {
    name: 'A2',
    parentId: 'a',
    children: []
  },
  a11: {
    name: 'A11',
    parentId: 'a1',
    children: []
  },
  b: {
    name: 'B',
    parentId: 'root',
    children: ['b1', 'b2', 'b3']
  },
  b1: {
    name: 'B1',
    parentId: 'b',
    children: ['b11']
  },
  b2: {
    name: 'B2',
    parentId: 'b',
    children: []
  },
  b3: {
    name: 'B3',
    parentId: 'b',
    children: []
  },
  b11: {
    name: 'B11',
    parentId: 'b1',
    children: ['b111']
  },
  b111: {
    name: 'B111',
    parentId: 'b11',
    children: []
  }
};

var initialSelection = _ramda.default.map(_ramda.default.always(_treeSelector.SELECTION_FULL), hierarchy);

var treeSelector = new _treeSelector.TreeSelector({
  parent: function parent(nodeId, hierarchy) {
    return hierarchy[nodeId].parentId;
  },
  children: function children(nodeId, hierarchy) {
    return hierarchy[nodeId].children;
  },
  isChild: function isChild(nodeId, hierarchy) {
    return hierarchy[nodeId].children.length === 0;
  },
  all: function all(predicate, hierarchy) {
    return function* () {
      for (var id in hierarchy) {
        if (predicate(id)) yield id;
      }
    }();
  },
  rootId: function rootId(_) {
    return 'root';
  },
  name: function name(nodeId, hierarchy) {
    return hierarchy[nodeId].name;
  }
});

var toggle = function toggle(nodeId) {
  var selection = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : initialSelection;
  return treeSelector.toggle(nodeId, selection, hierarchy);
};

var select = function select(nodeId, state) {
  var selection = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : initialSelection;
  return treeSelector.select(nodeId, state, selection, hierarchy);
};

var forAll = function forAll() {
  return true;
};

var selectAllLeaves = function selectAllLeaves(predicate, newState) {
  var selection = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : initialSelection;
  return treeSelector.selectAllLeaves(predicate, newState, selection, hierarchy);
};

test('toggling selection of a leaf node works', function () {
  var actual1 = toggle('a2');
  expect(actual1).toEqual(_objectSpread({}, initialSelection, {
    a2: _treeSelector.SELECTION_EMPTY,
    a: _treeSelector.SELECTION_PARTIAL,
    root: _treeSelector.SELECTION_PARTIAL
  }));
  var actual2 = toggle('a2', actual1);
  expect(actual2).toEqual(initialSelection);
});
test('setting selection of a leaf node works', function () {
  var actual1 = select('a2', _treeSelector.SELECTION_EMPTY);
  expect(actual1).toEqual(_objectSpread({}, initialSelection, {
    a2: _treeSelector.SELECTION_EMPTY,
    a: _treeSelector.SELECTION_PARTIAL,
    root: _treeSelector.SELECTION_PARTIAL
  }));
  var actual2 = select('a2', _treeSelector.SELECTION_FULL, actual1);
  expect(actual2).toEqual(initialSelection);
});
test('setting selection of a leaf node is idempotent', function () {
  var actual1 = select('a2', _treeSelector.SELECTION_EMPTY, select('a2', _treeSelector.SELECTION_EMPTY));
  expect(actual1).toEqual(_objectSpread({}, initialSelection, {
    a2: _treeSelector.SELECTION_EMPTY,
    a: _treeSelector.SELECTION_PARTIAL,
    root: _treeSelector.SELECTION_PARTIAL
  }));
  var actual2 = select('a2', _treeSelector.SELECTION_FULL, select('a2', _treeSelector.SELECTION_FULL, actual1));
  expect(actual2).toEqual(initialSelection);
});
test('toggling selection of a non-leaf node works', function () {
  var actual1 = toggle('a');
  expect(actual1).toEqual(_objectSpread({}, initialSelection, {
    a: _treeSelector.SELECTION_EMPTY,
    a1: _treeSelector.SELECTION_EMPTY,
    a11: _treeSelector.SELECTION_EMPTY,
    a2: _treeSelector.SELECTION_EMPTY,
    root: _treeSelector.SELECTION_PARTIAL
  }));
  var actual2 = toggle('a', actual1);
  expect(actual2).toEqual(initialSelection);
});
test('setting selection of a non-leaf node works', function () {
  var actual1 = select('a', _treeSelector.SELECTION_EMPTY);
  expect(actual1).toEqual(_objectSpread({}, initialSelection, {
    a: _treeSelector.SELECTION_EMPTY,
    a1: _treeSelector.SELECTION_EMPTY,
    a11: _treeSelector.SELECTION_EMPTY,
    a2: _treeSelector.SELECTION_EMPTY,
    root: _treeSelector.SELECTION_PARTIAL
  }));
  var actual2 = select('a', _treeSelector.SELECTION_FULL, actual1);
  expect(actual2).toEqual(initialSelection);
});
test('setting selection of a non-leaf is idempotent', function () {
  var actual1 = select('a', _treeSelector.SELECTION_EMPTY, select('a', _treeSelector.SELECTION_EMPTY));
  expect(actual1).toEqual(_objectSpread({}, initialSelection, {
    a: _treeSelector.SELECTION_EMPTY,
    a1: _treeSelector.SELECTION_EMPTY,
    a11: _treeSelector.SELECTION_EMPTY,
    a2: _treeSelector.SELECTION_EMPTY,
    root: _treeSelector.SELECTION_PARTIAL
  }));
  var actual2 = select('a', _treeSelector.SELECTION_FULL, select('a', _treeSelector.SELECTION_FULL, actual1));
  expect(actual2).toEqual(initialSelection);
});
test('setting selection of all leaves works', function () {
  var actual1 = selectAllLeaves(forAll, _treeSelector.SELECTION_EMPTY);
  expect(actual1).toEqual({
    root: _treeSelector.SELECTION_EMPTY,
    a: _treeSelector.SELECTION_EMPTY,
    b: _treeSelector.SELECTION_EMPTY,
    a1: _treeSelector.SELECTION_EMPTY,
    a11: _treeSelector.SELECTION_EMPTY,
    a2: _treeSelector.SELECTION_EMPTY,
    b1: _treeSelector.SELECTION_EMPTY,
    b2: _treeSelector.SELECTION_EMPTY,
    b3: _treeSelector.SELECTION_EMPTY,
    b11: _treeSelector.SELECTION_EMPTY,
    b111: _treeSelector.SELECTION_EMPTY
  });
  var actual2 = selectAllLeaves(forAll, _treeSelector.SELECTION_FULL, actual1);
  expect(actual2).toEqual(initialSelection);
});
test('setting selection of all leaves is idempotent', function () {
  var actual1 = selectAllLeaves(forAll, _treeSelector.SELECTION_EMPTY, selectAllLeaves(forAll, _treeSelector.SELECTION_EMPTY));
  expect(actual1).toEqual({
    root: _treeSelector.SELECTION_EMPTY,
    a: _treeSelector.SELECTION_EMPTY,
    b: _treeSelector.SELECTION_EMPTY,
    a1: _treeSelector.SELECTION_EMPTY,
    a11: _treeSelector.SELECTION_EMPTY,
    a2: _treeSelector.SELECTION_EMPTY,
    b1: _treeSelector.SELECTION_EMPTY,
    b2: _treeSelector.SELECTION_EMPTY,
    b3: _treeSelector.SELECTION_EMPTY,
    b11: _treeSelector.SELECTION_EMPTY,
    b111: _treeSelector.SELECTION_EMPTY
  });
  var actual2 = selectAllLeaves(forAll, _treeSelector.SELECTION_FULL, selectAllLeaves(forAll, _treeSelector.SELECTION_FULL, actual1));
  expect(actual2).toEqual(initialSelection);
});
test('setting selection of a set of leaves works', function () {
  var predicate = function predicate(id) {
    return id === 'a2' || id === 'b3';
  };

  var actual1 = selectAllLeaves(predicate, _treeSelector.SELECTION_EMPTY);
  expect(actual1).toEqual({
    root: _treeSelector.SELECTION_PARTIAL,
    a: _treeSelector.SELECTION_PARTIAL,
    b: _treeSelector.SELECTION_PARTIAL,
    a1: _treeSelector.SELECTION_FULL,
    a11: _treeSelector.SELECTION_FULL,
    a2: _treeSelector.SELECTION_EMPTY,
    b1: _treeSelector.SELECTION_FULL,
    b2: _treeSelector.SELECTION_FULL,
    b3: _treeSelector.SELECTION_EMPTY,
    b11: _treeSelector.SELECTION_FULL,
    b111: _treeSelector.SELECTION_FULL
  });
  var actual2 = selectAllLeaves(predicate, _treeSelector.SELECTION_FULL, actual1);
  expect(actual2).toEqual(initialSelection);
});
test('setting selection of a set of leaves is idempotent', function () {
  var predicate = function predicate(id) {
    return id === 'a2' || id === 'b3';
  };

  var actual1 = selectAllLeaves(predicate, _treeSelector.SELECTION_EMPTY, selectAllLeaves(predicate, _treeSelector.SELECTION_EMPTY));
  expect(actual1).toEqual({
    root: _treeSelector.SELECTION_PARTIAL,
    a: _treeSelector.SELECTION_PARTIAL,
    b: _treeSelector.SELECTION_PARTIAL,
    a1: _treeSelector.SELECTION_FULL,
    a11: _treeSelector.SELECTION_FULL,
    a2: _treeSelector.SELECTION_EMPTY,
    b1: _treeSelector.SELECTION_FULL,
    b2: _treeSelector.SELECTION_FULL,
    b3: _treeSelector.SELECTION_EMPTY,
    b11: _treeSelector.SELECTION_FULL,
    b111: _treeSelector.SELECTION_FULL
  });
  var actual2 = selectAllLeaves(predicate, _treeSelector.SELECTION_FULL, selectAllLeaves(predicate, _treeSelector.SELECTION_FULL, actual1));
  expect(actual2).toEqual(initialSelection);
});
test('Pre-human description for everything and nothing works', function () {
  var actual1 = treeSelector.describe(initialSelection, hierarchy);
  expect(actual1).toEqual('Everything');
  var actual2 = treeSelector.describe({
    root: _treeSelector.SELECTION_EMPTY,
    a: _treeSelector.SELECTION_EMPTY,
    a1: _treeSelector.SELECTION_EMPTY,
    a11: _treeSelector.SELECTION_EMPTY,
    a2: _treeSelector.SELECTION_EMPTY,
    b: _treeSelector.SELECTION_EMPTY,
    b1: _treeSelector.SELECTION_EMPTY,
    b2: _treeSelector.SELECTION_EMPTY,
    b3: _treeSelector.SELECTION_EMPTY,
    b11: _treeSelector.SELECTION_EMPTY,
    b111: _treeSelector.SELECTION_EMPTY
  }, hierarchy);
  expect(actual2).toEqual('Nothing');
});
test('Pre-human description for deep selection works', function () {
  var actual1 = treeSelector.describe({
    root: _treeSelector.SELECTION_PARTIAL,
    a: _treeSelector.SELECTION_FULL,
    a1: _treeSelector.SELECTION_FULL,
    a11: _treeSelector.SELECTION_FULL,
    a2: _treeSelector.SELECTION_FULL,
    b: _treeSelector.SELECTION_PARTIAL,
    b1: _treeSelector.SELECTION_EMPTY,
    b11: _treeSelector.SELECTION_EMPTY,
    b111: _treeSelector.SELECTION_EMPTY,
    b2: _treeSelector.SELECTION_FULL,
    b3: _treeSelector.SELECTION_FULL
  }, hierarchy);
  expect(actual1).toEqual(['Everything', 'except', ['B1']]);
  var actual2 = treeSelector.describe({
    root: _treeSelector.SELECTION_PARTIAL,
    a: _treeSelector.SELECTION_FULL,
    a1: _treeSelector.SELECTION_FULL,
    a11: _treeSelector.SELECTION_FULL,
    a2: _treeSelector.SELECTION_FULL,
    b: _treeSelector.SELECTION_PARTIAL,
    b1: _treeSelector.SELECTION_EMPTY,
    b11: _treeSelector.SELECTION_EMPTY,
    b111: _treeSelector.SELECTION_EMPTY,
    b2: _treeSelector.SELECTION_EMPTY,
    b3: _treeSelector.SELECTION_FULL
  }, hierarchy);
  expect(actual2).toEqual(['Everything', 'except', ['B', 'except', ['B3']]]);
});
test('Retrieving selected IDs for everything and nothing works', function () {
  var actual1 = treeSelector.selectedIds(initialSelection, hierarchy);
  expect(actual1).toEqual([]);
  var actual2 = treeSelector.selectedIds({
    root: _treeSelector.SELECTION_EMPTY,
    a: _treeSelector.SELECTION_EMPTY,
    a1: _treeSelector.SELECTION_EMPTY,
    a11: _treeSelector.SELECTION_EMPTY,
    a2: _treeSelector.SELECTION_EMPTY,
    b: _treeSelector.SELECTION_EMPTY,
    b1: _treeSelector.SELECTION_EMPTY,
    b2: _treeSelector.SELECTION_EMPTY,
    b3: _treeSelector.SELECTION_EMPTY,
    b11: _treeSelector.SELECTION_EMPTY,
    b111: _treeSelector.SELECTION_EMPTY
  }, hierarchy);
  expect(actual2).toEqual(null);
});
test('Retrieving selected IDs for a mixed selection works', function () {
  var actual1 = treeSelector.selectedIds({
    root: _treeSelector.SELECTION_PARTIAL,
    a: _treeSelector.SELECTION_FULL,
    a1: _treeSelector.SELECTION_FULL,
    a11: _treeSelector.SELECTION_FULL,
    a2: _treeSelector.SELECTION_FULL,
    b: _treeSelector.SELECTION_PARTIAL,
    b1: _treeSelector.SELECTION_EMPTY,
    b11: _treeSelector.SELECTION_EMPTY,
    b111: _treeSelector.SELECTION_EMPTY,
    b2: _treeSelector.SELECTION_FULL,
    b3: _treeSelector.SELECTION_FULL
  }, hierarchy);
  expect(new Set(actual1)).toEqual(new Set(['a', 'b2', 'b3']));
  var actual2 = treeSelector.selectedIds({
    root: _treeSelector.SELECTION_PARTIAL,
    a: _treeSelector.SELECTION_FULL,
    a1: _treeSelector.SELECTION_FULL,
    a11: _treeSelector.SELECTION_FULL,
    a2: _treeSelector.SELECTION_FULL,
    b: _treeSelector.SELECTION_PARTIAL,
    b1: _treeSelector.SELECTION_EMPTY,
    b11: _treeSelector.SELECTION_EMPTY,
    b111: _treeSelector.SELECTION_EMPTY,
    b2: _treeSelector.SELECTION_EMPTY,
    b3: _treeSelector.SELECTION_FULL
  }, hierarchy);
  expect(new Set(actual2)).toEqual(new Set(['a', 'b3']));
});