File: //home/arjun/.pm2/modules/pm2-logrotate/node_modules/deep-metrics/probes/mqlight-probe.js
/*******************************************************************************
* Copyright 2015 IBM Corp.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*******************************************************************************/
'use strict';
var Probe = require('../lib/probe.js');
var aspect = require('../lib/aspect.js');
var request = require('../lib/request.js');
var util = require('util');
var am = require('../');
/**
* Probe to instrument the MQLight npm client
*/
function MQLightProbe() {
Probe.call(this, 'mqlight');
}
util.inherits(MQLightProbe, Probe);
MQLightProbe.prototype.attach = function(name, target) {
var that = this;
if (name != 'mqlight') return target;
if (target.__probeAttached__) return;
target.__probeAttached__ = true;
// After 'createClient'
aspect.after(target, 'createClient', {}, function(target, methodName, createClientArgs, context, rc) {
var thisClient = rc; // the MQLight client that was created
// Just monitor 'send' for now as not sure what else will be useful
var methods = 'send';
// Before one of the above methods is called on the client
aspect.around(
thisClient,
methods,
function(target, methodName, args, probeData) {
// Start the monitoring for the method
that.metricsProbeStart(probeData, methodName, args);
that.requestProbeStart(probeData, methodName, args);
// Advise the callback for the method. Will do nothing if no callback is registered
aspect.aroundCallback(args, probeData, function(target, callbackArgs, probeData) {
// method has completed and the callback has been called, so end the monitoring
var callbackPosition = aspect.findCallbackArg(args);
that.metricsProbeEnd(probeData, methodName, args, thisClient);
that.requestProbeEnd(probeData, methodName, args, thisClient);
});
},
function(target, methodName, args, probeData, rc) {
// If no callback used then end the monitoring after returning from the method instead
if (aspect.findCallbackArg(args) == undefined) {
that.metricsProbeEnd(probeData, methodName, args, thisClient);
that.requestProbeEnd(probeData, methodName, args, thisClient);
}
return rc;
}
);
// Advise the callback code that is called when a message is received
aspect.before(thisClient, 'on', function(target, methodName, args, probeData) {
// only care about 'message' events
if (args[0] == 'message') {
// Must be a callback so no need to check for it
aspect.aroundCallback(
args,
{},
function(obj, callbackArgs, probeData) {
that.metricsProbeStart(probeData, 'message', callbackArgs);
that.requestProbeStart(probeData, 'message', callbackArgs);
},
function(target, callbackArgs, probeData, ret) {
// method has completed and the callback has been called, so end the monitoring
that.metricsProbeEnd(probeData, 'message', callbackArgs, thisClient);
that.requestProbeEnd(probeData, 'message', callbackArgs, thisClient);
return ret;
}
);
}
});
return rc;
});
return target;
};
/*
* Lightweight metrics probe end for MQLight messages
*/
MQLightProbe.prototype.metricsEnd = function(probeData, method, methodArgs, client) {
if (probeData && probeData.timer) {
probeData.timer.stop();
/* eslint no-redeclare:0 */
if (method == 'message') {
var data = methodArgs[0];
if (data.length > 25) {
data = data.substring(0, 22) + '...';
}
var topic = methodArgs[1].message.topic;
am.emit('mqlight', {
time: probeData.timer.startTimeMillis,
clientid: client.id,
data: data,
method: method,
topic: topic,
duration: probeData.timer.timeDelta,
});
} else if (method == 'send') {
var data = methodArgs[1];
if (data.length > 25) {
data = data.substring(0, 22) + '...';
}
var qos;
var options; // options are optional - check number of arguments.
if (methodArgs.length > 3) {
options = methodArgs[2];
qos = options[0];
}
am.emit('mqlight', {
time: probeData.timer.startTimeMillis,
clientid: client.id,
data: data,
method: method,
topic: methodArgs[0],
qos: qos,
duration: probeData.timer.timeDelta,
});
}
}
};
/*
* Heavyweight request probes for MQLight messages
*/
MQLightProbe.prototype.requestStart = function(probeData, method, methodArgs) {
if (method == 'message') {
probeData.req = request.startRequest('mqlight', method, true, probeData.timer);
} else {
probeData.req = request.startRequest('mqlight', method, false, probeData.timer);
}
};
MQLightProbe.prototype.requestEnd = function(probeData, method, methodArgs, client) {
if (probeData && probeData.req) {
if (method == 'message') {
var data = methodArgs[0];
if (data.length > 25) {
data = data.substring(0, 22) + '...';
}
probeData.req.stop({
clientid: client.id,
data: data,
method: method,
topic: methodArgs[0],
});
} else if (method == 'send') {
var data = methodArgs[1];
if (data.length > 25) {
data = data.substring(0, 22) + '...';
}
var qos;
var options; // options are optional - check number of arguments.
if (methodArgs.length > 3) {
options = methodArgs[2];
qos = options[0];
}
probeData.req.stop({
clientid: client.id,
data: data,
method: method,
topic: methodArgs[0],
qos: qos,
});
}
}
};
module.exports = MQLightProbe;