module.exports = function exportStaticProvider() { if (!PROVIDER) { PROVIDER = dtrace.createDTraceProvider('restify'); PROVIDER._rstfy_probes = {}; Object.keys(PROBES).forEach(function (p) { var args = PROBES[p].splice(0); args.unshift(p); var probe = PROVIDER.addProbe.apply(PROVIDER, args); PROVIDER._rstfy_probes[p] = probe; }); PROVIDER.enable(); PROVIDER.nextId = function nextId() { if (++ID >= MAX_INT) ID = 1; return (ID); }; } return (PROVIDER); }();
module.exports = (id, ...probes) => { const dtp = d.createDTraceProvider(id); each(probes, p => dtp.addProbe(...p)); return dtp; };
(function main() { const muskie = 'muskie'; // Parent object for client connection objects. var clients = {}; // DTrace probe setup var dtp = dtrace.createDTraceProvider(muskie); var client_close = dtp.addProbe('client_close', 'json'); var socket_timeout = dtp.addProbe('socket_timeout', 'json'); client_close.dtp = dtp; socket_timeout.dtp = dtp; dtp.enable(); const dtProbes = { client_close: client_close, socket_timeout: socket_timeout }; const opts = parseOptions(); const cfg = app.configure(muskie, opts, dtProbes); /* * Create a barrier to ensure client connections that are established * asynchronously and are required for muskie to serve a minimal subset of * requests are ready prior to starting up the restify servers. */ var barrier = vasync.barrier(); barrier.on('drain', clientsConnected.bind(null, muskie, cfg, clients)); /* * Establish minimal set of client connections required to begin * successfully servicing non-jobs read requests. */ clients.agent = new cueball.HttpAgent(cfg.cueballHttpAgent); clients.mahi = createAuthCacheClient(cfg.auth, clients.agent); barrier.start('createMorayClient'); createMorayClient(cfg.moray, onMorayConnect.bind(null, clients, barrier)); barrier.start('createPickerClient'); createPickerClient(cfg.storage, cfg.log, onPickerConnect.bind(null, clients, barrier)); // Establish other client connections needed for writes and jobs requests. createMarlinClient(cfg.marlin, onMarlinConnect.bind(null, clients)); createMedusaConnector(cfg.medusa, onMedusaConnect.bind(null, clients)); clients.sharkAgent = createCueballSharkAgent(cfg.sharkConfig); clients.keyapi = createKeyAPIClient(cfg); // Create monitoring server createMonitoringServer(cfg); process.on('SIGHUP', process.exit.bind(process, 0)); })();
module.exports = function(nt) { // trying to initialize dtrace provider var dtp = undefined; try { var d = require("dtrace-provider"); dtp = d.createDTraceProvider("nodetime"); dtp.addProbe("api-call-start", "int", "char *", "char *"); dtp.addProbe("api-call-done", "int", "char *", "char *"); dtp.enable(); } catch(err) { this.error(err) } // firing dtrace events on calls if(dtp) { nt.on('call', function(point, time) { try { var scope = time.scope.replace(/\s/g, '-').toLowerCase(); var command = time.command.replace(/\s/g, '-').toLowerCase(); dtp.fire('api-call-' + point, function() { return [time.id, scope, command]; }); } catch(err) { nt.error(err) } }); } };
function getDTraceProvider(options) { if (options.dtrace) return options.dtrace; if (!DTRACE) DTRACE = d.createDTraceProvider(options.name || 'restify'); return DTRACE; }
/** * @private * create dtrace object for unit test * @returns {Object} dtrace object */ function getDtrace() { var dtp; try { var d = require('dtrace-provider'); dtp = d.createDTraceProvider('nqBootstrapUnitTest'); } catch (e) { dtp = null; } return (dtp); }
module.exports = (function exportStaticProvider() { if (!PROVIDER) { try { var dtrace = require('dtrace-provider'); PROVIDER = dtrace.createDTraceProvider('restify'); } catch (e) { PROVIDER = { fire: function () { }, enable: function () { }, addProbe: function () { var p = { fire: function () { } }; return (p); }, removeProbe: function () { }, disable: function () { } }; } PROVIDER._rstfy_probes = {}; Object.keys(PROBES).forEach(function (p) { var args = PROBES[p].splice(0); args.unshift(p); var probe = PROVIDER.addProbe.apply(PROVIDER, args); PROVIDER._rstfy_probes[p] = probe; }); PROVIDER.enable(); PROVIDER.nextId = function nextId() { if (++ID >= MAX_INT) { ID = 1; } return (ID); }; } return (PROVIDER); }());
// Shamelessly copied from https://github.com/mcavage/node-restify function createDTrace(name) { // see https://github.com/mcavage/node-restify/issues/80 and // https://github.com/mcavage/node-restify/issues/100 if (!DTRACE) { try { var d = require('dtrace-provider'); DTRACE = d.createDTraceProvider(name); } catch (e) { DTRACE = { addProbe: function addProbe() {}, enable: function enable() {}, fire: function fire() {} }; } } return (DTRACE); }
module.exports = function () { if (!SERVER_PROVIDER) { try { var dtrace = require('dtrace-provider'); SERVER_PROVIDER = dtrace.createDTraceProvider('ldapjs'); Object.keys(SERVER_PROBES).forEach(function (p) { var args = SERVER_PROBES[p].splice(0); args.unshift(p); dtrace.DTraceProvider.prototype.addProbe.apply(SERVER_PROVIDER, args); }); } catch (e) { SERVER_PROVIDER = { fire: function () { }, enable: function () { }, addProbe: function () { var p = { fire: function () { } }; return (p); }, removeProbe: function () { }, disable: function () { } }; } SERVER_PROVIDER.enable(); SERVER_PROVIDER._nextId = function () { if (DTRACE_ID === MAX_INT) DTRACE_ID = 0; return ++DTRACE_ID; }; } return SERVER_PROVIDER; }();
module.exports = function exportStaticProvider() { if (!PROVIDER) { PROVIDER = dtrace.createDTraceProvider('fast'); PROVIDER._fast_probes = {}; Object.keys(PROBES).forEach(function (p) { var args = PROBES[p].splice(0); args.unshift(p); var probe = PROVIDER.addProbe.apply(PROVIDER, args); PROVIDER._fast_probes[p] = probe; }); PROVIDER.enable(); } return (PROVIDER); }();
function createDTraceProbes(name) { assert.string(name, 'name'); if (DTPS[name]) { return (DTPS[name]); } var dtp = dtrace.createDTraceProvider(name); var probes = { // these are all object_id, state release: dtp.addProbe('release', 'int', 'json'), remove: dtp.addProbe('remove', 'int', 'json'), kill: dtp.addProbe('kill', 'int', 'json'), create: dtp.addProbe('create', 'int', 'json'), // additionally create_time of object acquire: dtp.addProbe('acquire', 'int', 'json', 'char *'), // additionally "ok" assert: dtp.addProbe('assert', 'int', 'json', 'int'), // just num_items to check and state check: dtp.addProbe('check', 'int', 'json'), // arg0 is the current number of checked out connections shutdown: dtp.addProbe('shutdown', 'int', 'json'), // just the current state (ignore arg0) queue: dtp.addProbe('queue', 'int', 'json'), _provider: dtp }; DTPS[name] = probes; dtp.enable(); return (DTPS[name]); }
module.exports = function() { if (!SERVER_PROVIDER) { SERVER_PROVIDER = dtrace.createDTraceProvider('ldapjs'); Object.keys(SERVER_PROBES).forEach(function(p) { var args = SERVER_PROBES[p].splice(0); args.unshift(p); dtrace.DTraceProvider.prototype.addProbe.apply(SERVER_PROVIDER, args); }); SERVER_PROVIDER.enable(); SERVER_PROVIDER._nextId = function() { if (DTRACE_ID === MAX_INT) DTRACE_ID = 0; return ++DTRACE_ID; }; } return SERVER_PROVIDER; }();
var Logger = require('bunyan'); var test = require('tap').test; var uuid = require('node-uuid'); var HttpError = require('../lib/errors').HttpError; var RestError = require('../lib/errors').RestError; var Request = require('../lib/request'); var Response = require('../lib/response'); var Server = require('../lib/server'); var restify = require('../lib'); ///--- Globals var DTRACE = d.createDTraceProvider('restifyUnitTest'); var LOGGER = new Logger({name: 'restify/test/server'}); var PORT = process.env.UNIT_TEST_PORT || 12345; ///--- Tests test('throws on missing options', function (t) { t.throws(function () { return new Server(); }, new TypeError('options (Object) required')); t.end(); }); test('throws on missing dtrace', function (t) { t.throws(function () {
var dnsd = require('dnsd') var dtrace = require('dtrace-provider') var provider = dtrace.createDTraceProvider("dnsd") var probe = provider.addProbe("onrequest", "char *") provider.enable() dnsd.createServer(function handle(req, res) { provider.fire("onrequest", function(p) {}) res.end('1.2.3.4') }).listen(5354, '127.0.0.1') console.log('Server running on 5354') // dig @localhost -p 5354 foo.example A
}; tester.call(self, t); }); }; }, getLog: function (name, stream, level) { return (bunyan.createLogger({ level: (process.env.LOG_LEVEL || level || 'fatal'), name: name || process.argv[1], stream: stream || process.stdout, src: true, serializers: restify.bunyan.serializers })); }, get dtrace() { var dtp; try { var d = require('dtrace-provider'); dtp = d.createDTraceProvider('restifyUnitTest'); } catch (e) { dtp = null; } return (dtp); } };
var d = require('dtrace-provider'); var dtp = d.createDTraceProvider("nodeapp"); var p1 = dtp.addProbe("probe1", "int", "int"); var p2 = dtp.addProbe("probe2", "char *"); dtp.enable(); dtp.fire("probe1", function(p) { return [1, 2]; }); dtp.fire("probe2", function(p) { return ["hello, dtrace via provider", "foo"]; }); p1.fire(function(p) { return [1, 2, 3, 4, 5, 6]; }); p2.fire(function(p) { return ["hello, dtrace via probe", "foo"]; });
//---- Logger class /** * Create a Logger instance. * * @param options {Object} See documentation for full details. At minimum * this must include a 'name' string key. Configuration keys: * - `streams`: specify the logger output streams. This is an array of * objects with these fields: * - `type`: The stream type. See README.md for full details. * Often this is implied by the other fields. Examples are * 'file', 'stream' and "raw". * - `level`: Defaults to 'info'. * - `path` or `stream`: The specify the file path or writeable * stream to which log records are written. E.g. * `stream: process.stdout`. * - `closeOnExit` (boolean): Optional. Default is true for a * 'file' stream when `path` is given, false otherwise. * See README.md for full details. * - `level`: set the level for a single output stream (cannot be used * with `streams`) * - `stream`: the output stream for a logger with just one, e.g. * `process.stdout` (cannot be used with `streams`) * - `serializers`: object mapping log record field names to * serializing functions. See README.md for details. * - `src`: Boolean (default false). Set true to enable 'src' automatic * field with log call source info. * All other keys are log record fields. * * An alternative *internal* call signature is used for creating a child: * new Logger(<parent logger>, <child options>[, <child opts are simple>]); * * @param _childSimple (Boolean) An assertion that the given `_childOptions` * (a) only add fields (no config) and (b) no serialization handling is * required for them. IOW, this is a fast path for frequent child * creation. */ function Logger(options, _childOptions, _childSimple) { xxx('Logger start:', options) if (! this instanceof Logger) { return new Logger(options, _childOptions); } // Input arg validation. var parent; if (_childOptions !== undefined) { parent = options; options = _childOptions; if (! parent instanceof Logger) { throw new TypeError( 'invalid Logger creation: do not pass a second arg'); } } if (!options) { throw new TypeError('options (object) is required'); } if (!parent) { if (!options.name) { throw new TypeError('options.name (string) is required'); } } else { if (options.name) { throw new TypeError( 'invalid options.name: child cannot set logger name'); } } if (options.stream && options.streams) { throw new TypeError('cannot mix "streams" and "stream" options'); } if (options.streams && !Array.isArray(options.streams)) { throw new TypeError('invalid options.streams: must be an array') } if (options.serializers && (typeof (options.serializers) !== 'object' || Array.isArray(options.serializers))) { throw new TypeError('invalid options.serializers: must be an object') } EventEmitter.call(this); // Fast path for simple child creation. if (parent && _childSimple) { // `_isSimpleChild` is a signal to stream close handling that this child // owns none of its streams. this._isSimpleChild = true; this._level = parent._level; this.streams = parent.streams; this.serializers = parent.serializers; this.src = parent.src; var fields = this.fields = {}; var parentFieldNames = Object.keys(parent.fields); for (var i = 0; i < parentFieldNames.length; i++) { var name = parentFieldNames[i]; fields[name] = parent.fields[name]; } var names = Object.keys(options); for (var i = 0; i < names.length; i++) { var name = names[i]; fields[name] = options[name]; } return; } // Null values. var self = this; if (parent) { this._level = parent._level; this.streams = []; for (var i = 0; i < parent.streams.length; i++) { var s = objCopy(parent.streams[i]); s.closeOnExit = false; // Don't own parent stream. this.streams.push(s); } this.serializers = objCopy(parent.serializers); this.src = parent.src; this.fields = objCopy(parent.fields); if (options.level) { this.level(options.level); } } else { this._level = Number.POSITIVE_INFINITY; this.streams = []; this.serializers = null; this.src = false; this.fields = {}; } if (!dtp && dtrace) { dtp = dtrace.createDTraceProvider('bunyan'); for (var level in levelFromName) { var probe; probes[levelFromName[level]] = probe = dtp.addProbe('log-' + level, 'char *'); // Explicitly add a reference to dtp to prevent it from being GC'd probe.dtp = dtp; } dtp.enable(); } // Helpers function addStream(s) { s = objCopy(s); // Implicit 'type' from other args. var type = s.type; if (!s.type) { if (s.stream) { s.type = 'stream'; } else if (s.path) { s.type = 'file' } } s.raw = (s.type === 'raw'); // PERF: Allow for faster check in `_emit`. if (s.level) { s.level = resolveLevel(s.level); } else if (options.level) { s.level = resolveLevel(options.level); } else { s.level = INFO; } if (s.level < self._level) { self._level = s.level; } switch (s.type) { case 'stream': if (!s.closeOnExit) { s.closeOnExit = false; } break; case 'file': if (!s.stream) { s.stream = fs.createWriteStream(s.path, {flags: 'a', encoding: 'utf8'}); s.stream.on('error', function (err) { self.emit('error', err, s); }); if (!s.closeOnExit) { s.closeOnExit = true; } } else { if (!s.closeOnExit) { s.closeOnExit = false; } } break; case 'rotating-file': assert.ok(!s.stream, '"rotating-file" stream should not give a "stream"'); assert.ok(s.path); assert.ok(mv, '"rotating-file" stream type is not supported: ' + 'missing "mv" module'); s.stream = new RotatingFileStream(s); if (!s.closeOnExit) { s.closeOnExit = true; } break; case 'raw': if (!s.closeOnExit) { s.closeOnExit = false; } break; default: throw new TypeError('unknown stream type "' + s.type + '"'); } self.streams.push(s); } function addSerializers(serializers) { if (!self.serializers) { self.serializers = {}; } Object.keys(serializers).forEach(function (field) { var serializer = serializers[field]; if (typeof (serializer) !== 'function') { throw new TypeError(format( 'invalid serializer for "%s" field: must be a function', field)); } else { self.serializers[field] = serializer; } }); } // Handle *config* options (i.e. options that are not just plain data // for log records). if (options.stream) { addStream({ type: 'stream', stream: options.stream, closeOnExit: false, level: (options.level ? resolveLevel(options.level) : INFO) }); } else if (options.streams) { options.streams.forEach(addStream); } else if (parent && options.level) { this.level(options.level); } else if (!parent) { addStream({ type: 'stream', stream: process.stdout, closeOnExit: false, level: (options.level ? resolveLevel(options.level) : INFO) }); } if (options.serializers) { addSerializers(options.serializers); } if (options.src) { this.src = true; } xxx('Logger: ', self) // Fields. // These are the default fields for log records (minus the attributes // removed in this constructor). To allow storing raw log records // (unrendered), `this.fields` must never be mutated. Create a copy for // any changes. var fields = objCopy(options); delete fields.stream; delete fields.level; delete fields.streams; delete fields.serializers; delete fields.src; if (this.serializers) { this._applySerializers(fields); } if (!fields.hostname) { fields.hostname = os.hostname(); } if (!fields.pid) { fields.pid = process.pid; } Object.keys(fields).forEach(function (k) { self.fields[k] = fields[k]; }); }
test: function test(name, tester) { module.parent.exports[name] = function _(t) { var _done = false; t.end = function end() { if (!_done) { _done = true; t.done(); } }; t.notOk = function notOk(ok, message) { return (t.ok(!ok, message)); }; return (tester(t)); }; }, getLog: function (name, stream, level) { return (bunyan.createLogger({ level: (process.env.LOG_LEVEL || level || 'info'), name: name || process.argv[1], stream: stream || process.stdout, src: true, serializers: restify.bunyan.serializers })); }, dtrace: d.createDTraceProvider('restifyUnitTest') };
new Error().stack; var restify = require('restify'); var fs = require('fs'); var d = require('dtrace-provider'); var dtp = d.createDTraceProvider('echofile'); dtp.addProbe('fs-read-start', 'char *'); dtp.addProbe('fs-read-done', 'char *', 'char *', 'int'); console.log(dtp); var server = restify.createServer({ name: 'myapp', version: '1.0.0' }); server.use(restify.acceptParser(server.acceptable)); server.use(restify.queryParser()); server.use(restify.bodyParser()); server.get(/^\/(.*)/, function (req, res, next) { dtp.fire('fs-read-start', function() { return [req.params[0]]; }); fs.readFile(req.params[0], 'utf8', function(e, data) { var payload; dtp.fire('fs-read-done', function() { return [req.params[0], e && e.code ? e.code : null, data ? data.length : 0]; });