const signalRClient = {
    // SINGLETON object

    enabled: true,

    connection: null,

    connected: function connected() {
        if (!this.enabled)
            return false;

        if (signalRClient.connection === null)
            return false;

        return true;
    },

    sendMsg: function sendMsg(msg) {
        const flag = this.connected();

        if (!flag)
            return;

        // first call to invoke takes 1ms
        // after than, less than 1ms
        //const tmrSend = tmrUtils.newTimer("send").start();

        signalRClient.connection.invoke('Send', 'adam', 'Info', '23b3b85b-3315-4e3f-9438-1c2aea158d50', 'fbcaff80-393d-444d-8051-41bac42f0403', '59d0ee31-5af6-4e73-8d05-e55868254532', msg).catch(function (err) {
            return console.error(err.toString());
        });

        //tmrSend.stop();
        //logTime('signalRClient.sendMsg: TIME: ' + tmrSend);
    },

    initializeAsync: async function initializeAsync(userName, password) {
        const logHeader = 'signalRClient.initializeAsync: ';
        log(logHeader + 'enter');

        var success = false;

        signalRClient.connection = null;

        var xhr = new XMLHttpRequest();

        xhr.onerror = function (e) {
            console.error(xhr.statusText);
            // write error to console instead of calling log function
        };

        xhr.onload = function () {
            // called when the POST to request a JWT is complete

            if (xhr.readyState === 4) {
                // if the operation is complete

                if (xhr.status === 200) {
                    // if the operation is successful

                    const response = xhr.response;

                    const responseObj = JSON.parse(response);

                    token = responseObj.token;

                    var allocateConnection = () => {

                        // LogLevel enum
                        //  Trace
                        //  Debug
                        //  Information
                        //  Warning
                        //  Error
                        //  Critical
                        //  None

                        signalRClient.connection = new signalR.HubConnectionBuilder()
                            .withUrl("https://mmsignalr.azurewebsites.net/signalr", { accessTokenFactory: () => { return token; } })
                            .withAutomaticReconnect()
                            .configureLogging(signalR.LogLevel.Information)
                            .build();
                        // allocate a hub connection
                    };

                    allocateConnection();

                    signalRClient.connection.on('ReceiveMessage', (userName, msgType, subscriberGuid, msgGuid, requestGuid, message) => {
                        //console.log('userName=' + userName);
                        //console.log('msgType=' + msgType);
                        //console.log('subscriberGuid=' + subscriberGuid);
                        //console.log('msgGuid=' + msgGuid);
                        //console.log('requestGuid=' + requestGuid);
                        //console.log('message=' + message);
                    });

                    // do we need to await the following call?

                    signalRClient.connection.start()
                        .catch(err => console.log(err.toString()));

                    success = true;
                }
                else {
                    console.error(xhr.statusText);
                }
            }
        };

        const serverURI = 'https://mmsignalr.azurewebsites.net/token/requesttoken';

        xhr.open('POST', serverURI, true);
        // last parameter is: async

        xhr.setRequestHeader('Access-Control-Allow-Headers', 'Origin, X-Requested-With, Content-Type, Accept');
        xhr.setRequestHeader('Accept', 'application/json,text/plain,*/*');
        xhr.setRequestHeader('Content-Type', 'application/x-www-form-urlencoded');
        xhr.setRequestHeader('Cache-Control', 'no-cache');

        xhr.send('UserName=' + userName + '&Password=' + password);

        log(logHeader + 'leave');

        return success;
    }
};