redis 2.6.1 → 2.6.5
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +32 -5
- package/changelog.md +27 -1
- package/index.js +16 -13
- package/lib/multi.js +1 -0
- package/lib/utils.js +5 -1
- package/package.json +4 -4
package/README.md
CHANGED
|
@@ -6,7 +6,7 @@ redis - a node.js redis client
|
|
|
6
6
|
[](https://ci.appveyor.com/project/BridgeAR/node-redis/branch/master)
|
|
7
7
|
[](https://gitter.im/NodeRedis/node_redis?utm_source=badge&utm_medium=badge&utm_campaign=pr-badge)
|
|
8
8
|
|
|
9
|
-
This is a complete and feature rich Redis client for node.js.
|
|
9
|
+
This is a complete and feature rich Redis client for node.js. __It supports all Redis commands__ and focuses on high performance.
|
|
10
10
|
|
|
11
11
|
Install with:
|
|
12
12
|
|
|
@@ -189,8 +189,8 @@ __Tip:__ If the Redis server runs on the same machine as the client consider usi
|
|
|
189
189
|
| socket_keepalive | true | If set to `true`, the keep-alive functionality is enabled on the underlying socket. |
|
|
190
190
|
| no_ready_check | false | When a connection is established to the Redis server, the server might still be loading the database from disk. While loading, the server will not respond to any commands. To work around this, `node_redis` has a "ready check" which sends the `INFO` command to the server. The response from the `INFO` command indicates whether the server is ready for more commands. When ready, `node_redis` emits a `ready` event. Setting `no_ready_check` to `true` will inhibit this check. |
|
|
191
191
|
| enable_offline_queue | true | By default, if there is no active connection to the Redis server, commands are added to a queue and are executed once the connection has been established. Setting `enable_offline_queue` to `false` will disable this feature and the callback will be executed immediately with an error, or an error will be emitted if no callback is specified. |
|
|
192
|
-
| retry_max_delay | null | By default, every time the client tries to connect and fails, the reconnection delay almost doubles. This delay normally grows infinitely, but setting `retry_max_delay` limits it to the maximum value provided in milliseconds. |
|
|
193
|
-
| connect_timeout | 3600000 | Setting `connect_timeout` limits the total time for the client to connect and reconnect. The value is provided in milliseconds and is counted from the moment a new client is created or from the time the connection is lost. The last retry is going to happen exactly at the timeout time. Default is to try connecting until the default system socket timeout has been exceeded and to try reconnecting until 1h has elapsed. |
|
|
192
|
+
| retry_max_delay | null | __Deprecated__ _Please use `retry_strategy` instead._ By default, every time the client tries to connect and fails, the reconnection delay almost doubles. This delay normally grows infinitely, but setting `retry_max_delay` limits it to the maximum value provided in milliseconds. |
|
|
193
|
+
| connect_timeout | 3600000 | __Deprecated__ _Please use `retry_strategy` instead._ Setting `connect_timeout` limits the total time for the client to connect and reconnect. The value is provided in milliseconds and is counted from the moment a new client is created or from the time the connection is lost. The last retry is going to happen exactly at the timeout time. Default is to try connecting until the default system socket timeout has been exceeded and to try reconnecting until 1h has elapsed. |
|
|
194
194
|
| max_attempts | 0 | __Deprecated__ _Please use `retry_strategy` instead._ By default, a client will try reconnecting until connected. Setting `max_attempts` limits total amount of connection attempts. Setting this to 1 will prevent any reconnect attempt. |
|
|
195
195
|
| retry_unfulfilled_commands | false | If set to `true`, all commands that were unfulfilled while the connection is lost will be retried after the connection has been reestablished. Use this with caution if you use state altering commands (e.g. `incr`). This is especially useful if you use blocking commands. |
|
|
196
196
|
| password | null | If set, client will run Redis auth command on connect. Alias `auth_pass` __Note__ `node_redis` < 2.5 must use `auth_pass` |
|
|
@@ -224,7 +224,7 @@ retry_strategy example
|
|
|
224
224
|
```js
|
|
225
225
|
var client = redis.createClient({
|
|
226
226
|
retry_strategy: function (options) {
|
|
227
|
-
if (options.error.code === 'ECONNREFUSED') {
|
|
227
|
+
if (options.error && options.error.code === 'ECONNREFUSED') {
|
|
228
228
|
// End reconnecting on a specific error and flush all commands with a individual error
|
|
229
229
|
return new Error('The server refused the connection');
|
|
230
230
|
}
|
|
@@ -237,7 +237,7 @@ var client = redis.createClient({
|
|
|
237
237
|
return undefined;
|
|
238
238
|
}
|
|
239
239
|
// reconnect after
|
|
240
|
-
return Math.
|
|
240
|
+
return Math.min(options.attempt * 100, 3000);
|
|
241
241
|
}
|
|
242
242
|
});
|
|
243
243
|
```
|
|
@@ -658,6 +658,33 @@ the second word as first parameter:
|
|
|
658
658
|
Duplicate all current options and return a new redisClient instance. All options passed to the duplicate function are going to replace the original option.
|
|
659
659
|
If you pass a callback, duplicate is going to wait until the client is ready and returns it in the callback. If an error occurs in the meanwhile, that is going to return an error instead in the callback.
|
|
660
660
|
|
|
661
|
+
One example of when to use duplicate() would be to accomodate the connection-
|
|
662
|
+
blocking redis commands BRPOP, BLPOP, and BRPOPLPUSH. If these commands
|
|
663
|
+
are used on the same redisClient instance as non-blocking commands, the
|
|
664
|
+
non-blocking ones may be queued up until after the blocking ones finish.
|
|
665
|
+
|
|
666
|
+
var Redis=require('redis');
|
|
667
|
+
var client = Redis.createClient();
|
|
668
|
+
var clientBlocking = client.duplicate();
|
|
669
|
+
|
|
670
|
+
var get = function() {
|
|
671
|
+
console.log("get called");
|
|
672
|
+
client.get("any_key",function() { console.log("get returned"); });
|
|
673
|
+
setTimeout( get, 1000 );
|
|
674
|
+
};
|
|
675
|
+
var brpop = function() {
|
|
676
|
+
console.log("brpop called");
|
|
677
|
+
clientBlocking.brpop("nonexistent", 5, function() {
|
|
678
|
+
console.log("brpop return");
|
|
679
|
+
setTimeout( brpop, 1000 );
|
|
680
|
+
});
|
|
681
|
+
};
|
|
682
|
+
get();
|
|
683
|
+
brpop();
|
|
684
|
+
|
|
685
|
+
Another reason to use duplicate() is when multiple DBs on the same server are
|
|
686
|
+
accessed via the redis SELECT command. Each DB could use its own connection.
|
|
687
|
+
|
|
661
688
|
## client.send_command(command_name[, [args][, callback]])
|
|
662
689
|
|
|
663
690
|
All Redis commands have been added to the `client` object. However, if new commands are introduced before this library is updated,
|
package/changelog.md
CHANGED
|
@@ -1,6 +1,32 @@
|
|
|
1
1
|
Changelog
|
|
2
2
|
=========
|
|
3
3
|
|
|
4
|
+
## v.2.6.5 - 15 Jan, 2017
|
|
5
|
+
|
|
6
|
+
Bugfixes
|
|
7
|
+
|
|
8
|
+
- Fixed parser not being reset in case the redis connection closed ASAP for overcoming of output buffer limits
|
|
9
|
+
- Fixed parser reset if (p)message_buffer listener is attached
|
|
10
|
+
|
|
11
|
+
## v.2.6.4 - 12 Jan, 2017
|
|
12
|
+
|
|
13
|
+
Bugfixes
|
|
14
|
+
|
|
15
|
+
- Fixed monitor mode not working in combination with IPv6, sockets or lua scripts (2.6.0 regression)
|
|
16
|
+
|
|
17
|
+
## v.2.6.3 - 31 Oct, 2016
|
|
18
|
+
|
|
19
|
+
Bugfixes
|
|
20
|
+
|
|
21
|
+
- Do not change the tls setting to camel_case
|
|
22
|
+
- Fix domain handling in combination with the offline queue (2.5.3 regression)
|
|
23
|
+
|
|
24
|
+
## v.2.6.2 - 16 Jun, 2016
|
|
25
|
+
|
|
26
|
+
Bugfixes
|
|
27
|
+
|
|
28
|
+
- Fixed individual callbacks of a transaction not being called (2.6.0 regression)
|
|
29
|
+
|
|
4
30
|
## v.2.6.1 - 02 Jun, 2016
|
|
5
31
|
|
|
6
32
|
Bugfixes
|
|
@@ -13,7 +39,7 @@ In addition to the pre-releases the following changes exist in v.2.6.0:
|
|
|
13
39
|
|
|
14
40
|
Features
|
|
15
41
|
|
|
16
|
-
- Updated [redis-parser](https://github.com/NodeRedis/redis-parser) dependency ([changelog](https://github.com/NodeRedis/redis-parser/releases/tag/v.2.0.0))
|
|
42
|
+
- Updated [redis-parser](https://github.com/NodeRedis/node-redis-parser) dependency ([changelog](https://github.com/NodeRedis/node-redis-parser/releases/tag/v.2.0.0))
|
|
17
43
|
- The JS parser is from now on the new default as it is a lot faster than the hiredis parser
|
|
18
44
|
- This is no BC as there is no changed behavior for the user at all but just a performance improvement. Explicitly requireing the Hiredis parser is still possible.
|
|
19
45
|
- Added name property to all Redis functions (Node.js >= 4.0)
|
package/index.js
CHANGED
|
@@ -156,8 +156,6 @@ function RedisClient (options, stream) {
|
|
|
156
156
|
this.buffers = options.return_buffers || options.detect_buffers;
|
|
157
157
|
this.options = options;
|
|
158
158
|
this.reply = 'ON'; // Returning replies is the default
|
|
159
|
-
// Init parser
|
|
160
|
-
this.reply_parser = create_parser(this);
|
|
161
159
|
this.create_stream();
|
|
162
160
|
// The listeners will not be attached right away, so let's print the deprecation message while the listener is attached
|
|
163
161
|
this.on('newListener', function (event) {
|
|
@@ -171,10 +169,16 @@ function RedisClient (options, stream) {
|
|
|
171
169
|
'The drain event listener is deprecated and will be removed in v.3.0.0.\n' +
|
|
172
170
|
'If you want to keep on listening to this event please listen to the stream drain event directly.'
|
|
173
171
|
);
|
|
174
|
-
} else if (event === 'message_buffer' || event === 'pmessage_buffer' || event === 'messageBuffer' || event === 'pmessageBuffer' && !this.buffers) {
|
|
172
|
+
} else if ((event === 'message_buffer' || event === 'pmessage_buffer' || event === 'messageBuffer' || event === 'pmessageBuffer') && !this.buffers && !this.message_buffers) {
|
|
173
|
+
if (this.reply_parser.name !== 'javascript') {
|
|
174
|
+
return this.warn(
|
|
175
|
+
'You attached the ' + event + ' without the hiredis parser without the returnBuffers option set to true.\n' +
|
|
176
|
+
'Please use the JavaScript parser or set the returnBuffers option to true to return buffers.'
|
|
177
|
+
);
|
|
178
|
+
}
|
|
179
|
+
this.reply_parser.optionReturnBuffers = true;
|
|
175
180
|
this.message_buffers = true;
|
|
176
181
|
this.handle_reply = handle_detect_buffers_reply;
|
|
177
|
-
this.reply_parser = create_parser(this);
|
|
178
182
|
}
|
|
179
183
|
});
|
|
180
184
|
}
|
|
@@ -224,6 +228,9 @@ function create_parser (self) {
|
|
|
224
228
|
RedisClient.prototype.create_stream = function () {
|
|
225
229
|
var self = this;
|
|
226
230
|
|
|
231
|
+
// Init parser
|
|
232
|
+
this.reply_parser = create_parser(this);
|
|
233
|
+
|
|
227
234
|
if (this.options.stream) {
|
|
228
235
|
// Only add the listeners once in case of a reconnect try (that won't work)
|
|
229
236
|
if (this.stream) {
|
|
@@ -791,9 +798,6 @@ function return_pub_sub (self, reply) {
|
|
|
791
798
|
}
|
|
792
799
|
|
|
793
800
|
RedisClient.prototype.return_reply = function (reply) {
|
|
794
|
-
// If in monitor mode, all normal commands are still working and we only want to emit the streamlined commands
|
|
795
|
-
// As this is not the average use case and monitor is expensive anyway, let's change the code here, to improve
|
|
796
|
-
// the average performance of all other commands in case of no monitor mode
|
|
797
801
|
if (this.monitoring) {
|
|
798
802
|
var replyStr;
|
|
799
803
|
if (this.buffers && Buffer.isBuffer(reply)) {
|
|
@@ -801,8 +805,7 @@ RedisClient.prototype.return_reply = function (reply) {
|
|
|
801
805
|
} else {
|
|
802
806
|
replyStr = reply;
|
|
803
807
|
}
|
|
804
|
-
//
|
|
805
|
-
// Therefore the monitor command has to finish before it catches further commands
|
|
808
|
+
// If in monitor mode, all normal commands are still working and we only want to emit the streamlined commands
|
|
806
809
|
if (typeof replyStr === 'string' && utils.monitor_regex.test(replyStr)) {
|
|
807
810
|
var timestamp = replyStr.slice(0, replyStr.indexOf(' '));
|
|
808
811
|
var args = replyStr.slice(replyStr.indexOf('"') + 1, -1).split('" "').map(function (elem) {
|
|
@@ -868,16 +871,16 @@ RedisClient.prototype.internal_send_command = function (command_obj) {
|
|
|
868
871
|
var big_data = false;
|
|
869
872
|
var args_copy = new Array(len);
|
|
870
873
|
|
|
874
|
+
if (process.domain && command_obj.callback) {
|
|
875
|
+
command_obj.callback = process.domain.bind(command_obj.callback);
|
|
876
|
+
}
|
|
877
|
+
|
|
871
878
|
if (this.ready === false || this.stream.writable === false) {
|
|
872
879
|
// Handle offline commands right away
|
|
873
880
|
handle_offline_command(this, command_obj);
|
|
874
881
|
return false; // Indicate buffering
|
|
875
882
|
}
|
|
876
883
|
|
|
877
|
-
if (process.domain && command_obj.callback) {
|
|
878
|
-
command_obj.callback = process.domain.bind(command_obj.callback);
|
|
879
|
-
}
|
|
880
|
-
|
|
881
884
|
for (i = 0; i < len; i += 1) {
|
|
882
885
|
if (typeof args[i] === 'string') {
|
|
883
886
|
// 30000 seemed to be a good value to switch to buffers after testing and checking the pros and cons
|
package/lib/multi.js
CHANGED
|
@@ -36,6 +36,7 @@ function pipeline_transaction_command (self, command_obj, index) {
|
|
|
36
36
|
// Keep track of who wants buffer responses:
|
|
37
37
|
// By the time the callback is called the command_obj got the buffer_args attribute attached
|
|
38
38
|
self.wants_buffers[index] = command_obj.buffer_args;
|
|
39
|
+
command_obj.callback = tmp;
|
|
39
40
|
};
|
|
40
41
|
self._client.internal_send_command(command_obj);
|
|
41
42
|
}
|
package/lib/utils.js
CHANGED
|
@@ -57,6 +57,10 @@ function clone (obj) {
|
|
|
57
57
|
var elems = Object.keys(obj);
|
|
58
58
|
var elem;
|
|
59
59
|
while (elem = elems.pop()) {
|
|
60
|
+
if (elem === 'tls') { // special handle tls
|
|
61
|
+
copy[elem] = obj[elem];
|
|
62
|
+
continue;
|
|
63
|
+
}
|
|
60
64
|
// Accept camelCase options and convert them to snake_case
|
|
61
65
|
var snake_case = elem.replace(/[A-Z][^A-Z]/g, '_$&').toLowerCase();
|
|
62
66
|
// If camelCase is detected, pass it to the client, so all variables are going to be camelCased
|
|
@@ -123,7 +127,7 @@ module.exports = {
|
|
|
123
127
|
reply_to_object: replyToObject,
|
|
124
128
|
print: print,
|
|
125
129
|
err_code: /^([A-Z]+)\s+(.+)$/,
|
|
126
|
-
monitor_regex: /^[0-9]{10,11}\.[0-9]+ \[[0-9]{1,3}
|
|
130
|
+
monitor_regex: /^[0-9]{10,11}\.[0-9]+ \[[0-9]{1,3} (.(?!\]))+.\]( ".+?")+$/,
|
|
127
131
|
clone: convenienceClone,
|
|
128
132
|
callback_or_emit: callbackOrEmit,
|
|
129
133
|
reply_in_order: replyInOrder
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "redis",
|
|
3
|
-
"version": "2.6.
|
|
3
|
+
"version": "2.6.5",
|
|
4
4
|
"description": "Redis client library",
|
|
5
5
|
"keywords": [
|
|
6
6
|
"database",
|
|
@@ -21,7 +21,7 @@
|
|
|
21
21
|
"coverage": "nyc report --reporter=html",
|
|
22
22
|
"benchmark": "node benchmarks/multi_bench.js",
|
|
23
23
|
"test": "nyc --cache mocha ./test/*.js ./test/commands/*.js --timeout=8000",
|
|
24
|
-
"
|
|
24
|
+
"lint": "eslint . --fix && npm run coverage",
|
|
25
25
|
"compare": "node benchmarks/diff_multi_bench_output.js beforeBench.txt afterBench.txt"
|
|
26
26
|
},
|
|
27
27
|
"dependencies": {
|
|
@@ -36,10 +36,10 @@
|
|
|
36
36
|
"bluebird": "^3.0.2",
|
|
37
37
|
"coveralls": "^2.11.2",
|
|
38
38
|
"intercept-stdout": "~0.1.2",
|
|
39
|
-
"eslint": "^
|
|
39
|
+
"eslint": "^3.5.0",
|
|
40
40
|
"metrics": "^0.1.9",
|
|
41
41
|
"mocha": "^2.3.2",
|
|
42
|
-
"nyc": "^
|
|
42
|
+
"nyc": "^8.3.0",
|
|
43
43
|
"tcp-port-used": "^0.1.2",
|
|
44
44
|
"uuid": "^2.0.1",
|
|
45
45
|
"win-spawn": "^2.0.0"
|