redis 5.0.6 → 5.0.7
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.
- checksums.yaml +4 -4
- data/CHANGELOG.md +9 -0
- data/README.md +16 -10
- data/lib/redis/client.rb +22 -22
- data/lib/redis/commands/lists.rb +54 -0
- data/lib/redis/commands/sorted_sets.rb +66 -0
- data/lib/redis/distributed.rb +28 -0
- data/lib/redis/version.rb +1 -1
- data/lib/redis.rb +2 -0
- metadata +5 -5
checksums.yaml
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
---
|
|
2
2
|
SHA256:
|
|
3
|
-
metadata.gz:
|
|
4
|
-
data.tar.gz:
|
|
3
|
+
metadata.gz: 1dde5fad5c2d0c73c390528b059ab36b185dd61a2c32e4f9be9512bb4516977b
|
|
4
|
+
data.tar.gz: cda581f3f9b0b4238f15b4b3ddf7566fb6ca02b60ee7951b903e8e195bd395cd
|
|
5
5
|
SHA512:
|
|
6
|
-
metadata.gz:
|
|
7
|
-
data.tar.gz:
|
|
6
|
+
metadata.gz: 122fd647eda1a251370f32dfefb4711411b0ff9b0e9185cdb871c389c99d5b80a80d554a6b7787ed10e515291b1ebed6dceb2364f8c28021ce6fdedd3297d08e
|
|
7
|
+
data.tar.gz: 13aadc0709a9fc7779ad7ad1f64bb3d3b26da57eb44dd2ebd629d5ed2d34ea17c782337ce92e1047e7ae736df8b90eafb2e935e460f1b1af979621942dad772f
|
data/CHANGELOG.md
CHANGED
|
@@ -1,5 +1,9 @@
|
|
|
1
1
|
# Unreleased
|
|
2
2
|
|
|
3
|
+
# 5.0.7
|
|
4
|
+
|
|
5
|
+
- Fix compatibility with `redis-client 0.15.0` when using Redis Sentinel. Fix #1209.
|
|
6
|
+
|
|
3
7
|
# 5.0.6
|
|
4
8
|
|
|
5
9
|
- Wait for an extra `config.read_timeout` in blocking commands rather than an arbitrary 100ms. See #1175.
|
|
@@ -27,6 +31,7 @@
|
|
|
27
31
|
|
|
28
32
|
# 5.0.0
|
|
29
33
|
|
|
34
|
+
- Default client timeout decreased from 5 seconds to 1 second.
|
|
30
35
|
- Eagerly and strictly cast Integer and Float parameters.
|
|
31
36
|
- Allow to call `subscribe`, `unsubscribe`, `psubscribe` and `punsubscribe` from a subscribed client. See #1131.
|
|
32
37
|
- Use `MD5` for hashing server nodes in `Redis::Distributed`. This should improve keys distribution among servers. See #1089.
|
|
@@ -49,6 +54,10 @@
|
|
|
49
54
|
- Removed the `synchrony` driver.
|
|
50
55
|
- Removed `Redis.exists_returns_integer`, it's now always enabled.
|
|
51
56
|
|
|
57
|
+
# 4.8.1
|
|
58
|
+
|
|
59
|
+
* Automatically reconnect after fork regardless of `reconnect_attempts`
|
|
60
|
+
|
|
52
61
|
# 4.8.0
|
|
53
62
|
|
|
54
63
|
* Introduce `sadd?` and `srem?` as boolean returning versions of `sadd` and `srem`.
|
data/README.md
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
# redis-rb [![Build Status][gh-actions-image]][gh-actions-link] [![Inline docs][
|
|
1
|
+
# redis-rb [![Build Status][gh-actions-image]][gh-actions-link] [![Inline docs][rdoc-master-image]][rdoc-master-link]
|
|
2
2
|
|
|
3
3
|
A Ruby client that tries to match [Redis][redis-home]' API one-to-one, while still providing an idiomatic interface.
|
|
4
4
|
|
|
@@ -103,7 +103,7 @@ To connect using Sentinel, use:
|
|
|
103
103
|
SENTINELS = [{ host: "127.0.0.1", port: 26380 },
|
|
104
104
|
{ host: "127.0.0.1", port: 26381 }]
|
|
105
105
|
|
|
106
|
-
redis = Redis.new(
|
|
106
|
+
redis = Redis.new(name: "mymaster", sentinels: SENTINELS, role: :master)
|
|
107
107
|
```
|
|
108
108
|
|
|
109
109
|
* The master name identifies a group of Redis instances composed of a master
|
|
@@ -129,6 +129,12 @@ SENTINELS = [{ host: '127.0.0.1', port: 26380, password: 'mysecret' },
|
|
|
129
129
|
redis = Redis.new(name: 'mymaster', sentinels: SENTINELS, role: :master)
|
|
130
130
|
```
|
|
131
131
|
|
|
132
|
+
Also the name can be passed as an url:
|
|
133
|
+
|
|
134
|
+
```ruby
|
|
135
|
+
redis = Redis.new(name: "redis://mymaster", sentinels: SENTINELS, role: :master)
|
|
136
|
+
```
|
|
137
|
+
|
|
132
138
|
## Cluster support
|
|
133
139
|
|
|
134
140
|
[Clustering](https://redis.io/topics/cluster-spec). is supported via the [`redis-clustering` gem](cluster/).
|
|
@@ -394,11 +400,11 @@ client and evangelized Redis in Rubyland. Thank you, Ezra.
|
|
|
394
400
|
requests.
|
|
395
401
|
|
|
396
402
|
|
|
397
|
-
[
|
|
398
|
-
[
|
|
399
|
-
[redis-commands]:
|
|
400
|
-
[redis-home]:
|
|
401
|
-
[redis-url]:
|
|
402
|
-
[gh-actions-image]:
|
|
403
|
-
[gh-actions-link]:
|
|
404
|
-
[rubydoc]:
|
|
403
|
+
[rdoc-master-image]: https://img.shields.io/badge/docs-rdoc.info-blue.svg
|
|
404
|
+
[rdoc-master-link]: https://rubydoc.info/github/redis/redis-rb
|
|
405
|
+
[redis-commands]: https://redis.io/commands
|
|
406
|
+
[redis-home]: https://redis.io
|
|
407
|
+
[redis-url]: https://www.iana.org/assignments/uri-schemes/prov/redis
|
|
408
|
+
[gh-actions-image]: https://github.com/redis/redis-rb/workflows/Test/badge.svg
|
|
409
|
+
[gh-actions-link]: https://github.com/redis/redis-rb/actions
|
|
410
|
+
[rubydoc]: https://rubydoc.info/gems/redis
|
data/lib/redis/client.rb
CHANGED
|
@@ -24,7 +24,24 @@ class Redis
|
|
|
24
24
|
end
|
|
25
25
|
|
|
26
26
|
def sentinel(**kwargs)
|
|
27
|
-
super(protocol: 2, **kwargs)
|
|
27
|
+
super(protocol: 2, **kwargs, client_implementation: ::RedisClient)
|
|
28
|
+
end
|
|
29
|
+
|
|
30
|
+
def translate_error!(error)
|
|
31
|
+
redis_error = translate_error_class(error.class)
|
|
32
|
+
raise redis_error, error.message, error.backtrace
|
|
33
|
+
end
|
|
34
|
+
|
|
35
|
+
private
|
|
36
|
+
|
|
37
|
+
def translate_error_class(error_class)
|
|
38
|
+
ERROR_MAPPING.fetch(error_class)
|
|
39
|
+
rescue IndexError
|
|
40
|
+
if (client_error = error_class.ancestors.find { |a| ERROR_MAPPING[a] })
|
|
41
|
+
ERROR_MAPPING[error_class] = ERROR_MAPPING[client_error]
|
|
42
|
+
else
|
|
43
|
+
raise
|
|
44
|
+
end
|
|
28
45
|
end
|
|
29
46
|
end
|
|
30
47
|
|
|
@@ -72,7 +89,7 @@ class Redis
|
|
|
72
89
|
def call_v(command, &block)
|
|
73
90
|
super(command, &block)
|
|
74
91
|
rescue ::RedisClient::Error => error
|
|
75
|
-
translate_error!(error)
|
|
92
|
+
Client.translate_error!(error)
|
|
76
93
|
end
|
|
77
94
|
|
|
78
95
|
def blocking_call_v(timeout, command, &block)
|
|
@@ -85,19 +102,19 @@ class Redis
|
|
|
85
102
|
|
|
86
103
|
super(timeout, command, &block)
|
|
87
104
|
rescue ::RedisClient::Error => error
|
|
88
|
-
translate_error!(error)
|
|
105
|
+
Client.translate_error!(error)
|
|
89
106
|
end
|
|
90
107
|
|
|
91
108
|
def pipelined
|
|
92
109
|
super
|
|
93
110
|
rescue ::RedisClient::Error => error
|
|
94
|
-
translate_error!(error)
|
|
111
|
+
Client.translate_error!(error)
|
|
95
112
|
end
|
|
96
113
|
|
|
97
114
|
def multi
|
|
98
115
|
super
|
|
99
116
|
rescue ::RedisClient::Error => error
|
|
100
|
-
translate_error!(error)
|
|
117
|
+
Client.translate_error!(error)
|
|
101
118
|
end
|
|
102
119
|
|
|
103
120
|
def disable_reconnection(&block)
|
|
@@ -107,22 +124,5 @@ class Redis
|
|
|
107
124
|
def inherit_socket!
|
|
108
125
|
@inherit_socket = true
|
|
109
126
|
end
|
|
110
|
-
|
|
111
|
-
private
|
|
112
|
-
|
|
113
|
-
def translate_error!(error)
|
|
114
|
-
redis_error = translate_error_class(error.class)
|
|
115
|
-
raise redis_error, error.message, error.backtrace
|
|
116
|
-
end
|
|
117
|
-
|
|
118
|
-
def translate_error_class(error_class)
|
|
119
|
-
ERROR_MAPPING.fetch(error_class)
|
|
120
|
-
rescue IndexError
|
|
121
|
-
if (client_error = error_class.ancestors.find { |a| ERROR_MAPPING[a] })
|
|
122
|
-
ERROR_MAPPING[error_class] = ERROR_MAPPING[client_error]
|
|
123
|
-
else
|
|
124
|
-
raise
|
|
125
|
-
end
|
|
126
|
-
end
|
|
127
127
|
end
|
|
128
128
|
end
|
data/lib/redis/commands/lists.rb
CHANGED
|
@@ -183,6 +183,60 @@ class Redis
|
|
|
183
183
|
send_blocking_command(command, timeout)
|
|
184
184
|
end
|
|
185
185
|
|
|
186
|
+
# Pops one or more elements from the first non-empty list key from the list
|
|
187
|
+
# of provided key names. If lists are empty, blocks until timeout has passed.
|
|
188
|
+
#
|
|
189
|
+
# @example Popping a element
|
|
190
|
+
# redis.blmpop(1.0, 'list')
|
|
191
|
+
# #=> ['list', ['a']]
|
|
192
|
+
# @example With count option
|
|
193
|
+
# redis.blmpop(1.0, 'list', count: 2)
|
|
194
|
+
# #=> ['list', ['a', 'b']]
|
|
195
|
+
#
|
|
196
|
+
# @params timeout [Float] a float value specifying the maximum number of seconds to block) elapses.
|
|
197
|
+
# A timeout of zero can be used to block indefinitely.
|
|
198
|
+
# @params key [String, Array<String>] one or more keys with lists
|
|
199
|
+
# @params modifier [String]
|
|
200
|
+
# - when `"LEFT"` - the elements popped are those from the left of the list
|
|
201
|
+
# - when `"RIGHT"` - the elements popped are those from the right of the list
|
|
202
|
+
# @params count [Integer] a number of elements to pop
|
|
203
|
+
#
|
|
204
|
+
# @return [Array<String, Array<String, Float>>] list of popped elements or nil
|
|
205
|
+
def blmpop(timeout, *keys, modifier: "LEFT", count: nil)
|
|
206
|
+
raise ArgumentError, "Pick either LEFT or RIGHT" unless modifier == "LEFT" || modifier == "RIGHT"
|
|
207
|
+
|
|
208
|
+
args = [:lmpop, keys.size, *keys, modifier]
|
|
209
|
+
args << "COUNT" << Integer(count) if count
|
|
210
|
+
|
|
211
|
+
send_blocking_command(args, timeout)
|
|
212
|
+
end
|
|
213
|
+
|
|
214
|
+
# Pops one or more elements from the first non-empty list key from the list
|
|
215
|
+
# of provided key names.
|
|
216
|
+
#
|
|
217
|
+
# @example Popping a element
|
|
218
|
+
# redis.lmpop('list')
|
|
219
|
+
# #=> ['list', ['a']]
|
|
220
|
+
# @example With count option
|
|
221
|
+
# redis.lmpop('list', count: 2)
|
|
222
|
+
# #=> ['list', ['a', 'b']]
|
|
223
|
+
#
|
|
224
|
+
# @params key [String, Array<String>] one or more keys with lists
|
|
225
|
+
# @params modifier [String]
|
|
226
|
+
# - when `"LEFT"` - the elements popped are those from the left of the list
|
|
227
|
+
# - when `"RIGHT"` - the elements popped are those from the right of the list
|
|
228
|
+
# @params count [Integer] a number of elements to pop
|
|
229
|
+
#
|
|
230
|
+
# @return [Array<String, Array<String, Float>>] list of popped elements or nil
|
|
231
|
+
def lmpop(*keys, modifier: "LEFT", count: nil)
|
|
232
|
+
raise ArgumentError, "Pick either LEFT or RIGHT" unless modifier == "LEFT" || modifier == "RIGHT"
|
|
233
|
+
|
|
234
|
+
args = [:lmpop, keys.size, *keys, modifier]
|
|
235
|
+
args << "COUNT" << Integer(count) if count
|
|
236
|
+
|
|
237
|
+
send_command(args)
|
|
238
|
+
end
|
|
239
|
+
|
|
186
240
|
# Get an element from a list by its index.
|
|
187
241
|
#
|
|
188
242
|
# @param [String] key
|
|
@@ -167,6 +167,72 @@ class Redis
|
|
|
167
167
|
end
|
|
168
168
|
end
|
|
169
169
|
|
|
170
|
+
# Removes and returns up to count members with scores in the sorted set stored at key.
|
|
171
|
+
#
|
|
172
|
+
# @example Popping a member
|
|
173
|
+
# redis.bzmpop('zset')
|
|
174
|
+
# #=> ['zset', ['a', 1.0]]
|
|
175
|
+
# @example With count option
|
|
176
|
+
# redis.bzmpop('zset', count: 2)
|
|
177
|
+
# #=> ['zset', [['a', 1.0], ['b', 2.0]]
|
|
178
|
+
#
|
|
179
|
+
# @params timeout [Float] a float value specifying the maximum number of seconds to block) elapses.
|
|
180
|
+
# A timeout of zero can be used to block indefinitely.
|
|
181
|
+
# @params key [String, Array<String>] one or more keys with sorted sets
|
|
182
|
+
# @params modifier [String]
|
|
183
|
+
# - when `"MIN"` - the elements popped are those with lowest scores
|
|
184
|
+
# - when `"MAX"` - the elements popped are those with the highest scores
|
|
185
|
+
# @params count [Integer] a number of members to pop
|
|
186
|
+
#
|
|
187
|
+
# @return [Array<String, Array<String, Float>>] list of popped elements and scores
|
|
188
|
+
def bzmpop(timeout, *keys, modifier: "MIN", count: nil)
|
|
189
|
+
raise ArgumentError, "Pick either MIN or MAX" unless modifier == "MIN" || modifier == "MAX"
|
|
190
|
+
|
|
191
|
+
args = [:bzmpop, timeout, keys.size, *keys, modifier]
|
|
192
|
+
args << "COUNT" << Integer(count) if count
|
|
193
|
+
|
|
194
|
+
send_blocking_command(args, timeout) do |response|
|
|
195
|
+
response&.map do |entry|
|
|
196
|
+
case entry
|
|
197
|
+
when String then entry
|
|
198
|
+
when Array then entry.map { |pair| FloatifyPairs.call(pair) }.flatten(1)
|
|
199
|
+
end
|
|
200
|
+
end
|
|
201
|
+
end
|
|
202
|
+
end
|
|
203
|
+
|
|
204
|
+
# Removes and returns up to count members with scores in the sorted set stored at key.
|
|
205
|
+
#
|
|
206
|
+
# @example Popping a member
|
|
207
|
+
# redis.zmpop('zset')
|
|
208
|
+
# #=> ['zset', ['a', 1.0]]
|
|
209
|
+
# @example With count option
|
|
210
|
+
# redis.zmpop('zset', count: 2)
|
|
211
|
+
# #=> ['zset', [['a', 1.0], ['b', 2.0]]
|
|
212
|
+
#
|
|
213
|
+
# @params key [String, Array<String>] one or more keys with sorted sets
|
|
214
|
+
# @params modifier [String]
|
|
215
|
+
# - when `"MIN"` - the elements popped are those with lowest scores
|
|
216
|
+
# - when `"MAX"` - the elements popped are those with the highest scores
|
|
217
|
+
# @params count [Integer] a number of members to pop
|
|
218
|
+
#
|
|
219
|
+
# @return [Array<String, Array<String, Float>>] list of popped elements and scores
|
|
220
|
+
def zmpop(*keys, modifier: "MIN", count: nil)
|
|
221
|
+
raise ArgumentError, "Pick either MIN or MAX" unless modifier == "MIN" || modifier == "MAX"
|
|
222
|
+
|
|
223
|
+
args = [:zmpop, keys.size, *keys, modifier]
|
|
224
|
+
args << "COUNT" << Integer(count) if count
|
|
225
|
+
|
|
226
|
+
send_command(args) do |response|
|
|
227
|
+
response&.map do |entry|
|
|
228
|
+
case entry
|
|
229
|
+
when String then entry
|
|
230
|
+
when Array then entry.map { |pair| FloatifyPairs.call(pair) }.flatten(1)
|
|
231
|
+
end
|
|
232
|
+
end
|
|
233
|
+
end
|
|
234
|
+
end
|
|
235
|
+
|
|
170
236
|
# Removes and returns up to count members with the highest scores in the sorted set stored at keys,
|
|
171
237
|
# or block until one is available.
|
|
172
238
|
#
|
data/lib/redis/distributed.rb
CHANGED
|
@@ -542,6 +542,20 @@ class Redis
|
|
|
542
542
|
node_for(key).ltrim(key, start, stop)
|
|
543
543
|
end
|
|
544
544
|
|
|
545
|
+
# Iterate over keys, blocking and removing elements from the first non empty liist found.
|
|
546
|
+
def blmpop(timeout, *keys, modifier: "LEFT", count: nil)
|
|
547
|
+
ensure_same_node(:blmpop, keys) do |node|
|
|
548
|
+
node.blmpop(timeout, *keys, modifier: modifier, count: count)
|
|
549
|
+
end
|
|
550
|
+
end
|
|
551
|
+
|
|
552
|
+
# Iterate over keys, removing elements from the first non list found.
|
|
553
|
+
def lmpop(*keys, modifier: "LEFT", count: nil)
|
|
554
|
+
ensure_same_node(:lmpop, keys) do |node|
|
|
555
|
+
node.lmpop(*keys, modifier: modifier, count: count)
|
|
556
|
+
end
|
|
557
|
+
end
|
|
558
|
+
|
|
545
559
|
# Get the number of members in a set.
|
|
546
560
|
def scard(key)
|
|
547
561
|
node_for(key).scard(key)
|
|
@@ -694,6 +708,20 @@ class Redis
|
|
|
694
708
|
node_for(key).zmscore(key, *members)
|
|
695
709
|
end
|
|
696
710
|
|
|
711
|
+
# Iterate over keys, blocking and removing members from the first non empty sorted set found.
|
|
712
|
+
def bzmpop(timeout, *keys, modifier: "MIN", count: nil)
|
|
713
|
+
ensure_same_node(:bzmpop, keys) do |node|
|
|
714
|
+
node.bzmpop(timeout, *keys, modifier: modifier, count: count)
|
|
715
|
+
end
|
|
716
|
+
end
|
|
717
|
+
|
|
718
|
+
# Iterate over keys, removing members from the first non empty sorted set found.
|
|
719
|
+
def zmpop(*keys, modifier: "MIN", count: nil)
|
|
720
|
+
ensure_same_node(:zmpop, keys) do |node|
|
|
721
|
+
node.zmpop(*keys, modifier: modifier, count: count)
|
|
722
|
+
end
|
|
723
|
+
end
|
|
724
|
+
|
|
697
725
|
# Return a range of members in a sorted set, by index, score or lexicographical ordering.
|
|
698
726
|
def zrange(key, start, stop, **options)
|
|
699
727
|
node_for(key).zrange(key, start, stop, **options)
|
data/lib/redis/version.rb
CHANGED
data/lib/redis.rb
CHANGED
metadata
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
|
2
2
|
name: redis
|
|
3
3
|
version: !ruby/object:Gem::Version
|
|
4
|
-
version: 5.0.
|
|
4
|
+
version: 5.0.7
|
|
5
5
|
platform: ruby
|
|
6
6
|
authors:
|
|
7
7
|
- Ezra Zygmuntowicz
|
|
@@ -16,7 +16,7 @@ authors:
|
|
|
16
16
|
autorequire:
|
|
17
17
|
bindir: bin
|
|
18
18
|
cert_chain: []
|
|
19
|
-
date: 2023-
|
|
19
|
+
date: 2023-08-09 00:00:00.000000000 Z
|
|
20
20
|
dependencies:
|
|
21
21
|
- !ruby/object:Gem::Dependency
|
|
22
22
|
name: redis-client
|
|
@@ -75,9 +75,9 @@ licenses:
|
|
|
75
75
|
metadata:
|
|
76
76
|
bug_tracker_uri: https://github.com/redis/redis-rb/issues
|
|
77
77
|
changelog_uri: https://github.com/redis/redis-rb/blob/master/CHANGELOG.md
|
|
78
|
-
documentation_uri: https://www.rubydoc.info/gems/redis/5.0.
|
|
78
|
+
documentation_uri: https://www.rubydoc.info/gems/redis/5.0.7
|
|
79
79
|
homepage_uri: https://github.com/redis/redis-rb
|
|
80
|
-
source_code_uri: https://github.com/redis/redis-rb/tree/v5.0.
|
|
80
|
+
source_code_uri: https://github.com/redis/redis-rb/tree/v5.0.7
|
|
81
81
|
post_install_message:
|
|
82
82
|
rdoc_options: []
|
|
83
83
|
require_paths:
|
|
@@ -93,7 +93,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
|
93
93
|
- !ruby/object:Gem::Version
|
|
94
94
|
version: '0'
|
|
95
95
|
requirements: []
|
|
96
|
-
rubygems_version: 3.
|
|
96
|
+
rubygems_version: 3.3.7
|
|
97
97
|
signing_key:
|
|
98
98
|
specification_version: 4
|
|
99
99
|
summary: A Ruby client library for Redis
|