/**
* To work out which environment the site is on (dev/staging/live)
* @module
*/
import axios from 'axios';
import axiosCancel from 'axios-cancel';
axiosCancel(axios, {
debug: false, // default
});
/**
* @private
* @param {number} channel_id
* @param {string} hash_path String to the remote cfc to call CORE pluto.hash
* @returns {object} JS api struct with headers
*/
async function getParams(skv_config) {
// var channel_id = skv_config.channel_id;
const { hash_path } = skv_config;
let call_params = '';
try {
const response = await axios({
url: hash_path,
params: {
skv_params: skv_config.data,
channel_id: skv_config.channel_id,
method: 'getHash',
returnFormat: 'json',
},
});
call_params = response;
} catch (e) {
console.error(e);
}
return call_params;
}
/**
* work out whether the returned data is a cancelled ajax request
* @private
* @param {string} msg
* @returns {boolean}
*/
function isCancelRequest(msg) {
const regex = /cancelRequest\(.*\)/g;
const search_num = msg.search(regex);
if (search_num === -1) {
return false;
}
return true;
}
/**
* Generic ajax call
* @param {struct} config
* @returns {struct} Data returned from call
*/
const call = async (config) => {
const skv_config = config;
skv_config.data.returnFormat = 'json';
// cancel any other calculations to stop stacking
axios.cancel(config.request_id);
// when calling pluto we need to call a small cfc to get a hash for
// authentication. the hash is made up of key, secret, time and nonce
// that will then be decoded by the api
let is_hash_provided = false;
// to be populated and passed in to axios if we are calling the api
let headers = {};
// see if we're calling pluto/api
if (Object.prototype.hasOwnProperty.call(config, 'hash_path')) {
is_hash_provided = true;
}
try {
// if we're calling pluto/api we need to get a hash to authenticate
// the call with
if (is_hash_provided) {
const rst_hash_response = await getParams(skv_config);
const hash_data = rst_hash_response.data;
if (
hash_data.success
&& hash_data.data.length
) {
headers = {
key: hash_data.data[0].api_key,
hash: hash_data.data[0].hash,
nonce: hash_data.data[0].nonce,
time: hash_data.data[0].time,
};
} else {
throw new Error(`API is being called but no headers were retrieved: ${rst_hash_response.data.msg}`);
}
}
const skv_axios_call_cfg = {
url: skv_config.url,
requestId: config.request_id,
// params are the URL parameters to be sent with the request
// use config for POST
params: skv_config.data,
};
// if we're using the api we'll have headers to add to the axios call
if (Object.keys(headers).length) {
skv_axios_call_cfg.headers = headers;
}
const response = await axios(skv_axios_call_cfg);
// only return the data if the call worked
const { data } = response;
// default the internal_status_code to failure if there is no entry
// for one otherwise we'll have it as part of the data object
if (
!Object.prototype.hasOwnProperty.call(data, 'internal_status_code')
|| data.internal_status_code === ''
) {
data.internal_status_code = 'FAILURE';
}
// we should always be returning a minimum of jsapi keys (there'll likely
// be more for pluto calls)
if (
!Object.prototype.hasOwnProperty.call(data, 'data')
|| !Object.prototype.hasOwnProperty.call(data, 'msg')
|| !Object.prototype.hasOwnProperty.call(data, 'success')
) {
data.internal_status_code = 'FAIL_MISSING_KEYS_IN_RETURNED_DATA';
console.error(`Internal status code: ${data.internal_status_code} // Message: One of data, msg or success has not been included in the returned data struct`);
}
if (data.success) {
data.internal_status_code = 'SUCCESS';
} else {
// check to see if we are cancelling an ajax call based on the
// message provided by AxiosCancel
if (isCancelRequest(data.msg)) {
data.internal_status_code = 'AJAX_CANCEL';
}
console.error(`Internal status code: ${data.internal_status_code} // Message: ${data.msg}`);
}
// return whats hopefully a jsapi structured return data
return data;
} catch (err) {
let internal_status_code = 'FAILURE';
// if theres no cancelRequest(...) in the message record as an warning
// rather than an error
if (isCancelRequest(err.message)) {
internal_status_code = 'AJAX_CANCEL';
console.warn('Warning in service: ', err);
} else {
console.error('Error in service: ', err);
}
return {
msg: err.message,
data: [],
success: false,
internal_status_code,
};
}
};
export {
call,
};