"use strict"; Object.defineProperty(exports, "__esModule", { value: true }); const EventEmitter = require('events').EventEmitter; class RequestTimgingsMeasurer extends EventEmitter { constructor(options) { super(); this.e = null; this.timings = { // start: 0, // lookup: -1, // connect: -1, // ready: -1, // waiting: -1, // download: -1, // end: -1 }; this.e = null; this.enable = options.enable === true; this.timerStarted = false; this.intervalId = null; this.timeoutId = null; this.waitingTime = options.waitingTime || 1000; this.interval = options.interval || 200; } static new(options) { return new RequestTimgingsMeasurer(options); } /* istanbul ignore next */ measure(clientRequest) { if (!this.enable) { return; } this.startTimer(); const timings = this.timings; timings.start = Date.now(); clientRequest .once('response', message => { timings.response = Date.now(); timings.waiting = Date.now() - timings.start; message.once('end', () => { timings.socket = timings.socket || 0; // timings.lookup = timings.lookup || timings.socket // timings.connect = timings.connect || timings.lookup timings.download = Date.now() - timings.response; timings.end = Date.now() - timings.start; this.stopTimer('end'); }); }) .once('socket', socket => { timings.socket = Date.now() - timings.start; const onlookup = () => { this.timings.lookup = Date.now() - this.timings.start; }; const onconnect = () => { this.timings.connect = Date.now() - this.timings.start; }; const onready = () => { this.timings.ready = Date.now() - this.timings.start; }; if (socket.connecting) { socket.once('lookup', onlookup); socket.once('connect', onconnect); socket.once('ready', onready); socket.once('error', e => { socket.off('lookup', onlookup); socket.off('connect', onconnect); socket.off('ready', onready); this.e = e; this.timings.error = Date.now() - this.timings.start; this.stopTimer(`ee:${e.message}`); }); } else { this.timings.lookup = -1; this.timings.connect = -1; this.timings.ready = -1; } // socket.once('data', () => {}) // socket.once('drain', () => {}) // socket.once('end', () => { // this.stopTimer('end') // }) // socket.once('timeout', () => { // this.timings.timeout = Date.now() - this.timings.start // }) }) .on('error', (e) => { this.stopTimer(`ee:${e.message}`); }); } /* istanbul ignore next */ startTimer() { if (!this.enable) { return; } if (this.timerStarted) { return; } this.timerStarted = true; this.intervalId = null; this.timeoutId = setTimeout(() => { this.process('inprogress'); this.intervalId = setInterval(() => { this.process('inprogress'); }, this.interval); }, this.waitingTime); } /* istanbul ignore next */ stopTimer(reason) { // if (!this.enable) { // return // } // if (!this.timerStarted) { // return // } this.timerStarted = false; clearTimeout(this.timeoutId); clearInterval(this.intervalId); this.process(reason); } /* istanbul ignore next */ process(reason) { this.emit('progress', Object.assign({}, this.timings), reason); } } exports.RequestTimgingsMeasurer = RequestTimgingsMeasurer;