"use strict";

var _interopRequireDefault = require("@babel/runtime/helpers/interopRequireDefault");

Object.defineProperty(exports, "__esModule", {
  value: true
});
exports.default = void 0;

var _objectSpread2 = _interopRequireDefault(require("@babel/runtime/helpers/objectSpread"));

var _defineProperty2 = _interopRequireDefault(require("@babel/runtime/helpers/defineProperty"));

var _immutable = require("immutable");

var _constants = require("@instructure/quiz-common/lib/constants");

var _immutableHelpers = require("../util/immutableHelpers");

var _Stimulus = _interopRequireDefault(require("../records/Stimulus"));

var defaultObjMods = function defaultObjMods(objId) {
  var keyAttr = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : 'id';
  return (0, _immutable.Map)((0, _defineProperty2.default)({}, keyAttr, objId));
};

var mergeMods = function mergeMods(initialMods, modificationsMap) {
  return initialMods.merge((0, _immutable.fromJS)(modificationsMap));
};

var mergeModsDeep = function mergeModsDeep(initialMods, modificationsMap) {
  return initialMods.mergeWith(_immutableHelpers.mergeDeepOnlyMaps, (0, _immutable.fromJS)(modificationsMap));
};

var updateObjectOfType = function updateObjectOfType(state, key, modifications, objType) {
  var _ref = arguments.length > 4 && arguments[4] !== undefined ? arguments[4] : {},
      _ref$keyAttr = _ref.keyAttr,
      keyAttr = _ref$keyAttr === void 0 ? 'id' : _ref$keyAttr,
      _ref$mergeFunc = _ref.mergeFunc,
      mergeFunc = _ref$mergeFunc === void 0 ? mergeMods : _ref$mergeFunc;

  return state.updateIn([objType, key], defaultObjMods(key, keyAttr), function (obj) {
    return mergeFunc(obj, modifications);
  });
};

var clearObject = function clearObject(state, action) {
  return state.deleteIn([action.payload.objectType, action.payload.objectId].concat(action.payload.deepKeys));
};

var clearTemporaryEntry = function clearTemporaryEntry(state, action, type, id) {
  return state.setIn(['quizzes', action.payload.quizId, 'quizEntries'], []).deleteIn(['quizEntries', _constants.TEMPORARY_QUIZ_ENTRY_ID]).deleteIn([type, id]);
};

var clearTemporaryBankEntry = function clearTemporaryBankEntry(state, action, type, id) {
  return state.setIn(['banks', action.payload.bankId, 'bankEntries'], []).deleteIn(['bankEntries', _constants.TEMPORARY_BANK_ENTRY_ID]).deleteIn([type, id]);
};

var _default = function _default() {
  var state = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : (0, _immutable.fromJS)({
    banks: {},
    items: {},
    quizEntries: {},
    quizzes: {},
    sessionItemResults: {}
  });
  var action = arguments.length > 1 ? arguments[1] : undefined;

  switch (action.type) {
    case _constants.BANK_MODIFICATION:
      return updateObjectOfType(state, action.payload.id, action.payload.modifications, 'banks');

    case _constants.QUIZ_MODIFICATION:
      return updateObjectOfType(state, action.payload.id, action.payload.modifications, 'quizzes');

    case _constants.ITEM_MODIFICATION:
      return updateObjectOfType(state, action.payload.id, action.payload.modifications, 'items');

    case _constants.QUIZ_ENTRIES_MODIFICATION:
      return updateObjectOfType(state, action.payload.id, action.payload.modifications, 'quizEntries', {
        mergeFunc: mergeModsDeep
      });

    case _constants.SET_NEXT_QUIZ_ENTRY:
      return state.set('nextQuizEntry', action.payload);

    case _constants.QUIZ_SESSION_RESULT_MODIFICATION:
      return updateObjectOfType(state, action.payload.id, action.payload.modifications, 'quizSessionResults');

    case _constants.SESSION_ITEM_RESULTS_MODIFICATION:
      return updateObjectOfType(state, action.payload.id, action.payload.modifications, 'sessionItemResults', {
        keyAttr: 'id'
      });

    case _constants.CREATE_TEMPORARY_BANK:
      return updateObjectOfType(state, _constants.TEMPORARY_BANK_ID, (0, _objectSpread2.default)({
        title: ''
      }, action.payload), 'banks');

    case _constants.STIMULUS_MODIFICATION:
      return updateObjectOfType(state, action.payload.stimulus.id, action.payload.stimulus, 'stimuli');

    case _constants.CREATE_TEMPORARY_STIMULUS:
      return function () {
        var stimulusQuizMods = {
          quizEntries: [_constants.TEMPORARY_QUIZ_ENTRY_ID]
        };
        var stateWithStimulusQuizMods = updateObjectOfType(state, action.payload.quizId, stimulusQuizMods, 'quizzes');
        var tempStimulus = new _Stimulus.default({
          id: _constants.TEMPORARY_STIMULUS_ID
        }).toJS();
        var stateWithStimulusMods = updateObjectOfType(stateWithStimulusQuizMods, _constants.TEMPORARY_STIMULUS_ID, tempStimulus, 'stimuli');
        var stimulusPosition = action.payload.position === 0 ? 0.9 : action.payload.position - 0.1;
        var stimulusQuizEntryMods = {
          position: stimulusPosition,
          entry: _constants.TEMPORARY_STIMULUS_ID,
          entryType: 'Stimulus'
        };
        return updateObjectOfType(stateWithStimulusMods, _constants.TEMPORARY_QUIZ_ENTRY_ID, stimulusQuizEntryMods, 'quizEntries');
      }();

    case _constants.CREATE_TEMPORARY_ITEM:
      return function () {
        var quizMods = {
          quizEntries: [_constants.TEMPORARY_QUIZ_ENTRY_ID]
        };
        var stateWithQuizMods = updateObjectOfType(state, action.payload.quizId, quizMods, 'quizzes');
        var position = action.payload.position === 0 ? 0.9 : action.payload.position - 0.1;
        var quizEntryMods = {
          position: position,
          entry: _constants.TEMPORARY_ITEM_ID,
          entryType: 'Item',
          stimulusQuizEntryId: action.payload.parentEntryId
        };
        var stateWithQuizEntryMods = updateObjectOfType(stateWithQuizMods, _constants.TEMPORARY_QUIZ_ENTRY_ID, quizEntryMods, 'quizEntries');
        var itemMods = {
          interactionData: action.payload.interactionTypeData.interactionData,
          interactionType: action.payload.interactionTypeData.id,
          itemBody: action.payload.interactionTypeData.itemBody,
          properties: action.payload.interactionTypeData.properties,
          scoringData: action.payload.interactionTypeData.scoringData,
          title: null,
          stimulusId: action.payload.stimulusId
        };
        var stateWithAllMods = updateObjectOfType(stateWithQuizEntryMods, _constants.TEMPORARY_ITEM_ID, itemMods, 'items');
        return stateWithAllMods;
      }();

    case _constants.CREATE_TEMPORARY_BANK_ITEM:
      return function () {
        var bankMods = {
          bankEntries: [_constants.TEMPORARY_BANK_ENTRY_ID]
        };
        var stateWithBankMods = updateObjectOfType(state, action.payload.bankId, bankMods, 'banks');
        var tempId = action.payload.bankEntryType === 'Item' ? _constants.TEMPORARY_ITEM_ID : _constants.TEMPORARY_STIMULUS_ID;
        var bankEntryMods = {
          entry: tempId,
          entryType: action.payload.bankEntryType
        };
        var stateWithBankEntryMods = updateObjectOfType(stateWithBankMods, _constants.TEMPORARY_BANK_ENTRY_ID, bankEntryMods, 'bankEntries');
        var bankItemMods = action.payload.bankEntryType === 'Item' ? {
          interactionData: action.payload.interactionTypeData.interactionData,
          interactionType: action.payload.interactionTypeData.id,
          itemBody: action.payload.interactionTypeData.itemBody,
          properties: action.payload.interactionTypeData.properties,
          scoringData: action.payload.interactionTypeData.scoringData,
          title: null
        } : {
          title: ''
        };
        var collection = action.payload.bankEntryType === 'Item' ? 'items' : 'stimuli';
        var stateWithMods = updateObjectOfType(stateWithBankEntryMods, tempId, bankItemMods, collection);
        return stateWithMods;
      }();

    case _constants.CLEAR_NEXT_QUIZ_ENTRY:
      return state.delete('nextQuizEntry');

    case _constants.CLEAR_TEMPORARY_STIMULUS:
      return clearTemporaryEntry(state, action, 'stimuli', _constants.TEMPORARY_STIMULUS_ID);

    case _constants.CLEAR_TEMPORARY_ITEM:
      return clearTemporaryEntry(state, action, 'items', _constants.TEMPORARY_ITEM_ID);

    case _constants.CLEAR_TEMPORARY_BANK_ITEM:
      return clearTemporaryBankEntry(state, action, 'items', _constants.TEMPORARY_ITEM_ID);

    case _constants.CLEAR_MODIFICATIONS:
      return clearObject(state, action);

    case _constants.MOVE_TEMPORARY_ITEM:
      return function () {
        var oldPosition = state.getIn(['quizEntries', _constants.TEMPORARY_QUIZ_ENTRY_ID, 'position']);
        var newPosition;

        if (action.payload.direction) {
          newPosition = action.payload.direction === 'up' ? oldPosition - 1 : oldPosition + 1;
        } else {
          var offset = action.payload.movingDown ? 0.9 : -0.1;
          newPosition = action.payload.position + offset;
        }

        var qeMods = {
          position: newPosition,
          stimulusQuizEntryId: action.payload.stimulusQuizEntryId
        };
        return updateObjectOfType(state, _constants.TEMPORARY_QUIZ_ENTRY_ID, qeMods, 'quizEntries');
      }();

    default:
      return state;
  }
};

exports.default = _default;