From 9e136671fd5629171a71cd5b5103e5c4dc5b6cf3 Mon Sep 17 00:00:00 2001 From: Serbay Arslanhan Date: Fri, 25 Mar 2016 20:49:42 +0200 Subject: [PATCH 1/2] Add editorconfig configuration --- .editorconfig | 8 ++++++++ 1 file changed, 8 insertions(+) create mode 100644 .editorconfig diff --git a/.editorconfig b/.editorconfig new file mode 100644 index 0000000..a4b824b --- /dev/null +++ b/.editorconfig @@ -0,0 +1,8 @@ +root = true + +[*] +charset = utf-8 +end_of_line = lf +insert_final_newline = true +indent_style = space +indent_size = 2 From 08b69ef79bc675e476b2c93ce6431e61fb110df4 Mon Sep 17 00:00:00 2001 From: Serbay Arslanhan Date: Fri, 25 Mar 2016 20:50:44 +0200 Subject: [PATCH 2/2] Use `timequeue` package for rate limiting Since each api call on embedly has its own rate limit, they are defined using an `Object` rather than a single `Number`. --- README.rst | 15 +++++++++++++++ index.js | 19 ++++++++++++++++++- package.json | 5 +++-- 3 files changed, 36 insertions(+), 3 deletions(-) diff --git a/README.rst b/README.rst index df47792..34f987b 100644 --- a/README.rst +++ b/README.rst @@ -95,6 +95,21 @@ Here are some examples *hint* replace xxxxxxxxxxx with real key:: }); }); + new embedly({key: EMBEDLY_KEY, rateLimits: { extract: 10 }}, function(err, api) { + var url = ('http://www.guardian.co.uk/media/2011/jan' + + '/21/andy-coulson-phone-hacking-statement'); + api.extract({url: url}, function(err, objs) { + if (!!err) { + console.error('request #3 failed'); + console.error(err.stack, objs); + return; + } + console.log('---------------------------------------------------------'); + console.log('4. '); + console.log(util.inspect(objs[0])); + }); + }); + Authentication ^^^^^^^^^^^^^^ diff --git a/index.js b/index.js index b27553a..adf26b4 100644 --- a/index.js +++ b/index.js @@ -5,6 +5,8 @@ var bb = require('batbelt'), hashish = require('hashish'), querystring = require('querystring'); +var TimeQueue = require('timequeue'); + function defaultLogger() { try { var winston = require('winston') @@ -36,6 +38,10 @@ function defaultLogger() { // // **secure** _Boolean_ Enables ssl // +// **rateLimits** _Object_ An object that is used to provide rate limits for +// each api call. Possible keys are objectify, oembed, preview, +// and extract. By default they are set to _Infinity_. +// // **logger** _Object_ An object that has debug, warn and error functions that // except a single _String_ parameter. The `log` module is used by // default. @@ -53,6 +59,7 @@ function embedly(opts, callback) { preview: 1, extract: 1 }, + rateLimits: {}, timeout: 200000, protocol: false, logger: null, @@ -65,11 +72,21 @@ function embedly(opts, callback) { var self = this; hashish(this.config.apiVersion).forEach(function(version, action) { + var rateLimit = self.config.rateLimits[action]; + + var q = new TimeQueue(function () { + embedly.prototype.apiCall.apply(self, arguments); + }, { + concurrency: rateLimit || Infinity, + every: 1000 + }); + self[action] = function() { var args = Array.prototype.slice.call(arguments, 0); args.unshift(version); args.unshift(action); - return embedly.prototype.apiCall.apply(self, args); + + return q.push.apply(q, args); }; }); diff --git a/package.json b/package.json index ab3724c..7030e25 100644 --- a/package.json +++ b/package.json @@ -19,9 +19,10 @@ }, "dependencies": { "batbelt": "0.0.2", - "superagent": "0.21.0", + "hashish": "0.0.4", "sprintf": "0.1.1", - "hashish": "0.0.4" + "superagent": "0.21.0", + "timequeue": "^0.2.2" }, "devDependencies": { "mocha": "1.8.2",