├── index.js ├── .gitignore ├── package.json ├── README.md ├── LICENSE └── lib └── index.js /index.js: -------------------------------------------------------------------------------- 1 | module.exports = require("./lib"); 2 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | node_modules 2 | npm-debug.log 3 | 4 | .DS_Store 5 | *.swp 6 | *~ 7 | 8 | .idea/ 9 | -------------------------------------------------------------------------------- /package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "@tesglobal/connect-datadog", 3 | "version": "0.1.0", 4 | "description": "Datadog middleware for Connect JS / Express", 5 | "main": "index.js", 6 | "repository": { 7 | "type": "git", 8 | "url": "git://github.com/tes/node-connect-datadog.git" 9 | }, 10 | "keywords": [ 11 | "datadog", 12 | "middleware" 13 | ], 14 | "author": "Tes Global", 15 | "license": "MIT", 16 | "readmeFilename": "README.md", 17 | "dependencies": { 18 | "node-dogstatsd": "0.0.6" 19 | } 20 | } 21 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # node-connect-datadog 2 | 3 | Datadog middleware for Connect JS / Express 4 | 5 | 6 | ## Usage 7 | 8 | Add middleware immediately before your router. 9 | 10 | app.use(require("connect-datadog")({})); 11 | app.use(app.router); 12 | 13 | ## Options 14 | 15 | All options are optional. 16 | 17 | * `dogstatsd` node-dogstatsd client. `default = new (require("node-dogstatsd")).StatsD()` 18 | * `stat` *string* name for the stat. `default = "node.express.router"` 19 | * `tags` *array* of tags to be added to the histogram. `default = []` 20 | * `path` *boolean* include path tag. `default = false` 21 | * `method` *boolean* include http method tag. `default = false` 22 | * `protocol` *boolean* include protocol tag. `default = false` 23 | * `response_code` *boolean* include http response codes. `default = false` 24 | 25 | ## Published fork 26 | Tes Global has published this fork for use via npm, as [the original repo](https://github.com/tes/node-connect-datadog) has not merged PRs or published a new version for some time. 27 | 28 | ## License 29 | 30 | View the [LICENSE](https://github.com/tes/node-connect-datadog/blob/master/LICENSE) file. 31 | 32 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | (The MIT License) 2 | 3 | Copyright (c) 2013 App Press LLC 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining 6 | a copy of this software and associated documentation files (the 7 | 'Software'), to deal in the Software without restriction, including 8 | without limitation the rights to use, copy, modify, merge, publish, 9 | distribute, sublicense, and/or sell copies of the Software, and to 10 | permit persons to whom the Software is furnished to do so, subject to 11 | the following conditions: 12 | 13 | The above copyright notice and this permission notice shall be 14 | included in all copies or substantial portions of the Software. 15 | 16 | THE SOFTWARE IS PROVIDED 'AS IS', WITHOUT WARRANTY OF ANY KIND, 17 | EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF 18 | MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. 19 | IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY 20 | CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, 21 | TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE 22 | SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 23 | -------------------------------------------------------------------------------- /lib/index.js: -------------------------------------------------------------------------------- 1 | var DD = require('node-dogstatsd').StatsD; 2 | 3 | module.exports = function (options) { 4 | var datadog = options.dogstatsd || new DD(); 5 | var stat = options.stat || 'node.express.router'; 6 | var tags = options.tags || []; 7 | var response_code = options.response_code || false; 8 | 9 | return function (req, res, next) { 10 | if (!req._startTime) { 11 | req._startTime = new Date(); 12 | } 13 | 14 | var end = res.end; 15 | res.end = function (chunk, encoding) { 16 | res.end = end; 17 | res.end(chunk, encoding); 18 | 19 | var route; 20 | 21 | if (req.__route) { 22 | route = req.__route; 23 | } else { 24 | var apiPath = (req.route && req.route.path) || (req.swagger && req.swagger.apiPath); 25 | if (!apiPath) { 26 | return; 27 | } 28 | var baseUrl = req.baseUrl; 29 | route = baseUrl + apiPath; 30 | } 31 | 32 | var statTags = [].concat(tags); 33 | 34 | statTags.push('route:' + route); 35 | 36 | statTags.push('method:' + req.method.toLowerCase()); 37 | 38 | statTags.push('protocol:' + req.protocol); 39 | 40 | if (options.headers && options.headers.length > 0) { 41 | options.headers.forEach(function (header) { 42 | if (req.headers[header]) { 43 | statTags.push(header + ':' + req.headers[header]); 44 | } 45 | }); 46 | } 47 | 48 | if (response_code) { 49 | statTags.push('response_code:' + res.statusCode); 50 | datadog.increment(stat + '.response_code.' + res.statusCode, 1, statTags); 51 | datadog.increment(stat + '.response_code.all', 1, statTags); 52 | } 53 | 54 | datadog.histogram(stat + '.response_time', (new Date() - req._startTime), 1, statTags); 55 | }; 56 | 57 | next(); 58 | }; 59 | }; 60 | --------------------------------------------------------------------------------