"use strict";

Object.defineProperty(exports, "__esModule", {
  value: true
});

var _selectn = require("selectn");

var _selectn2 = _interopRequireDefault(_selectn);

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

function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }

/* global encounterTemplateV2User, encounterTemplateV2EncounterInfo */

var ApplicationName = "EHR";
var URL = "/PMV2API/billing/authentication/AuthenticateExternalUser";
var SESSION_STORAGE_IMO_AUTH = "RxNT_IMO_SESSION_STORAGE_AUTH";

function credentials() {
  var ExternalDoctorCompanyId = "" + encounterTemplateV2User.DoctorCompanyId;
  var ExternalAppLoginId = "" + encounterTemplateV2EncounterInfo.LoggedInUserId;
  return {
    ApplicationName: ApplicationName,
    ExternalDoctorCompanyId: ExternalDoctorCompanyId,
    ExternalAppLoginId: ExternalAppLoginId
  };
}

function parseAuthObject(jsonData) {
  var authObj = {
    Token: jsonData.Login.AppLoginTokens[0].Token,
    Signature: jsonData.Login.AppLoginInfoes[0].Signature,
    DoctorCompanyId: jsonData.Login.DoctorCompanyId
  };
  return authObj;
}

function doAuth() {
  var authReqBody = credentials();
  var req = new Request(URL, {
    method: "POST",
    headers: {
      RequestInfo: "####",
      "Content-Type": "application/json"
    },
    body: JSON.stringify(authReqBody)
  });
  return fetch(req).then(function (res) {
    return res.json();
  }).then(parseAuthObject);
}

function auth() {
  if (sessionStorage && sessionStorage.getItem(SESSION_STORAGE_IMO_AUTH)) {
    var authObj = JSON.parse(sessionStorage.getItem(SESSION_STORAGE_IMO_AUTH));
    return Promise.resolve(authObj);
  }
  return doAuth().then(function (authObj) {
    sessionStorage.setItem(SESSION_STORAGE_IMO_AUTH, JSON.stringify(authObj));
    return authObj;
  });
}

var IMOAPI = function IMOAPI() {
  var _this = this;

  _classCallCheck(this, IMOAPI);

  this.parseOption = function (json, root, mapping) {
    var isSelectable = function isSelectable(option) {
      return option["POST_COORD_LEX_FLAG"] === "3";
    };

    var options = (0, _selectn2.default)(root, json);
    var mappedOptions = options.map(function (option) {
      var mappedOption = Object.keys(mapping).reduce(function (agg, field) {
        var respKey = mapping[field];
        agg[field] = option[respKey];
        return agg;
      }, {});
      mappedOption.selectable = isSelectable(option);
      mappedOption.modifiers = option.Modifiers ? option.Modifiers.split(",").map(function (m) {
        return m.trim();
      }) : [];
      return mappedOption;
    });
    return mappedOptions;
  };

  this.parseModifiers = function (json) {
    var modifiers = json.ModifierTypeList.map(function (modifier) {
      var name = modifier.tITLEField;
      var options = modifier.mODIFIERSField.map(function (option) {
        var code = option.mODIFIER_CODEField;
        var title = option.mODIFIER_TITLEField;
        return { code: code, title: title };
      });
      return { name: name, options: options };
    });
    return modifiers;
  };

  this.singAndFetch = function (url, queryObj) {
    return _this.auth.then(function (authObj) {
      var body = Object.assign({}, authObj, queryObj);
      return fetch(url, {
        method: "POST",
        headers: {
          RequestInfo: "TestUser#TestPass#" + authObj.DoctorCompanyId + "#" + authObj.Signature + "#" + authObj.Token,
          "Content-Type": "application/json"
        },
        body: JSON.stringify(body)
      });
    });
  };

  this.search = function (query, _ref) {
    var url = _ref.url,
        root = _ref.root,
        mapping = _ref.mapping;

    return _this.singAndFetch(url, { SearchQuery: query }).then(function (resp) {
      return resp.json();
    }).then(function (json) {
      return _this.parseOption(json, root, mapping);
    });
  };

  this.searchDetails = function (code, _ref2) {
    var url = _ref2.url,
        root = _ref2.root,
        mapping = _ref2.mapping;

    return _this.singAndFetch(url, { LexicalItemCode: code }).then(function (resp) {
      return resp.json();
    }).then(function (json) {
      var options = _this.parseOption(json, root, mapping);
      var modifiers = _this.parseModifiers(json);
      return { options: options, modifiers: modifiers };
    });
  };

  this.auth = auth();
};

exports.default = IMOAPI;