const fs = require('fs');
const path = require('path');
const xml2js = require('xml2js');
const log = require('loglevel');

class PosServ {
    constructor () {
        this.axios = global.axiosInstances.axiosAfcInstance;
    }

    heartbeat = async (heartbeat) => {
        try {
            const xmlBuilder = new xml2js.Builder({xmldec: {version: '1.0', encoding: 'UTF-8'} });
            const xml = await xmlBuilder.buildObject(heartbeat);
            const res = await this.axios.post('device_comm/v1/' + process.env.CLIENT_DEVICE_MNEMONIC + '/heartbeat', xml, {headers: {'Content-Type': 'application/xml'}});
            if (typeof res === 'undefined' || res.status >= 400) { return {head: null}; }
            return await xml2js.parseStringPromise(res, { explicitRoot: false, explicitArray: false });
        } catch (err) {
            log.error(err);
        }
    }

    distributionDownload = async (version) => {
        try {
            let res = await this.axios.get(process.env.CLIENT_APIURL + '/media/distributions/DISTRIBUTION_' + process.env.CLIENT_DEVICE_MNEMONIC + '_' + version + '.zip', {responseType: 'arraybuffer'});
            if (typeof res === 'undefined' || res.status >= 400) { return {head: null}; }
            return res;
        } catch (err) {
            log.error(err);
        }
    }

    actionList = async (device, version) => {
        try {
            const xmlBuilder = new xml2js.Builder({xmldec: {version: '1.0', encoding: 'UTF-8'} });
            const xml = await xmlBuilder.buildObject(device);
            const res = await this.axios.post('device_comm/v1/' + process.env.CLIENT_DEVICE_MNEMONIC + '/actionlist/' + version, xml, {headers: {'Content-Type': 'application/xml'}, responseType: 'arraybuffer'});
            if (typeof res === 'undefined' || res.status >= 400) { return {head: null}; }
            return res;
        } catch (err) {
            log.error(err);
        }
    }

    distributionStatus = async (reportDistributionStatus) => {
        try {
            const xmlBuilder = new xml2js.Builder({xmldec: {version: '1.0', encoding: 'UTF-8'} });
            const xml = await xmlBuilder.buildObject(reportDistributionStatus);
            const res = await this.axios.post('device_comm/v1/' + process.env.CLIENT_DEVICE_MNEMONIC + '/distribution/status', xml, {headers: {'Content-Type': 'application/xml'}});
            if (typeof res === 'undefined' || res.status >= 400) { return {head: null}; }
            return await xml2js.parseStringPromise(res, { explicitRoot: false, explicitArray: false });
        } catch (err) {
            log.error(err);
        }
    }

    assignments = async (deviceAssignments) => {
        try {
            const xmlBuilder = new xml2js.Builder({xmldec: {version: '1.0', encoding: 'UTF-8'} });
            const xml = await xmlBuilder.buildObject(deviceAssignments);
            const res = await this.axios.post('device_comm/v1/' + process.env.CLIENT_DEVICE_MNEMONIC + '/assignments', xml, {headers: {'Content-Type': 'application/xml'}});
            if (typeof res === 'undefined' || res.status >= 400) { return {head: null}; }
            return await xml2js.parseStringPromise(res, { explicitRoot: false, explicitArray: false });
        } catch (err) {
            log.error(err);
        }
    }

    getLastTransactionCounter = async (deviceId) => {
        try {
            const res = await this.axios.get('device_comm/v1/' + process.env.CLIENT_DEVICE_MNEMONIC + '/'+deviceId+'/last-transaction-counter');
            if (typeof res === 'undefined' || res.status >= 400) { return null; }
            return res;
        } catch (err) {
            log.error(err);
        }
    }

    getCommands = async (deviceId) => {
        try {
            const res = await this.axios.get('device_comm/v1/' + process.env.CLIENT_DEVICE_MNEMONIC + '/'+deviceId+'/commands');
            if (typeof res === 'undefined' || res.status >= 400) { return null; }
            return res;
        } catch (err) {
            log.error(err);
        }
    }

    markCommandReceived = async (deviceId, commandId, receivedTimestamp) => {
        try {
            const res = await this.axios.put('device_comm/v1/' + process.env.CLIENT_DEVICE_MNEMONIC + '/'+deviceId+'/commands/'+commandId+'/received', receivedTimestamp);
            if (typeof res === 'undefined' || res.status >= 400) { return false; }
            return true;
        } catch (err) {
            log.error(err);
        }
    }

    markCommandExecuted = async (deviceId, commandId, executedTimestamp) => {
        try {
            const res = await this.axios.put('device_comm/v1/' + process.env.CLIENT_DEVICE_MNEMONIC + '/'+deviceId+'/commands/'+commandId+'/executed', executedTimestamp);
            if (typeof res === 'undefined' || res.status >= 400) { return false; }
            return true;
        } catch (err) {
            log.error(err);
        }
    }

    getOrganizations = async () => {
        try {
            const res = await this.axios.get('organization/v2');
            if (typeof res === 'undefined' || res.status >= 400) { return null; }
            return res;
        } catch (err) {
            log.error(err);
        }
    }

}

module.exports = PosServ;
