Git Product home page Git Product logo

mock_redis's Introduction

Personal web site, powered by Jekyll.

mock_redis's People

Contributors

cander avatar ecoffey avatar empact avatar hieuk09 avatar jmthomas avatar jrmhaig avatar jughead avatar kcdragon avatar mattly avatar mjonuschat avatar numbata avatar okhwaja avatar olleolleolle avatar orien avatar polpak avatar rkotov93 avatar rvashurin avatar ryansch avatar saverio-kantox avatar sds avatar sinclairtarget avatar smerritt avatar snmgian avatar stupidcodefactory avatar ted-hanson avatar tomasv avatar vhiairrassary avatar viralpraxis avatar wincent avatar yaauie avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

mock_redis's Issues

Set/Get Bit Weirdness

I'm getting inconsistent results on getting a set bit.

Here is a spec that fails:

  it "sets and retrieves bits" do
    @redises.setbit(@key, 22, 1)
    @redises.getbit(@key, 22).should == 1
    @redises.setbit(@key, 23, 0)
    @redises.getbit(@key, 23).should == 0
  end

When setting a bit to 0, it does not return the zero. When doing the same operation in Redis, it does work.

127.0.0.1:6379> setbit "features" 5 0
(integer) 0
127.0.0.1:6379> getbit "features" 5
(integer) 0
127.0.0.1:6379> setbit "features" 15 1
(integer) 0
127.0.0.1:6379> getbit "features" 15
(integer) 1
127.0.0.1:6379> getbit "features" 25
(integer) 0

Am I missing something?

"zrem" discrepancy

Hi,

I've run into a small discrepancy between how MockRedis and Redis function.

When calling Redis::Client#zrem with an empty Array as the second argument, the method raises a Redis::CommandError. MockRedis#zrem doesn't raise this error.

redis

irb(main):003:0> redis.zrem('foo', [])
Redis::CommandError: ERR wrong number of arguments for 'zrem' command
    from /Users/rasmus/.gem/ruby/2.3.1/gems/redis-3.3.1/lib/redis/client.rb:121:in `call'
    from /Users/rasmus/.gem/ruby/2.3.1/gems/redis-3.3.1/lib/redis.rb:1571:in `block in zrem'
    from /Users/rasmus/.gem/ruby/2.3.1/gems/redis-3.3.1/lib/redis.rb:58:in `block in synchronize'
    from /Users/rasmus/.rubies/ruby-2.3.1/lib/ruby/2.3.0/monitor.rb:214:in `mon_synchronize'
    from /Users/rasmus/.gem/ruby/2.3.1/gems/redis-3.3.1/lib/redis.rb:58:in `synchronize'
    from /Users/rasmus/.gem/ruby/2.3.1/gems/redis-3.3.1/lib/redis.rb:1570:in `zrem'
    from (irb):3
    from /Users/rasmus/.rubies/ruby-2.3.1/bin/irb:11:in `<main>'
irb(main):004:0>

redis-mock

irb(main):003:0> mock_redis.zrem('foo', [])
=> 0
irb(main):004:0>

ZRange behavior does not match Redis when using a negative STOP argument

Using redis-cli:

127.0.0.1:6379> ZADD myzset 10 10
(integer) 1
127.0.0.1:6379> ZADD myzset 20 20
(integer) 1
127.0.0.1:6379> ZADD myzset 30 30
(integer) 1
127.0.0.1:6379> ZRANGE myzset 0 -4
(empty list or set)

Using redis-rb:

irb(main):001:0> redis = Redis.new
=> #<Redis client v3.3.3 for redis://127.0.0.1:6379/0>
irb(main):002:0> redis.zadd('myzset', 10, 10)
=> true
irb(main):003:0> redis.zadd('myzset', 20, 20)
=> true
irb(main):004:0> redis.zadd('myzset', 30, 30)
=> true
irb(main):005:0> redis.zrange('myzset', 0, -4)
=> []

Using mock_redis, version 0.17.2:

irb(main):001:0> redis = MockRedis.new
=> #<MockRedis:0x007fb63b8e94c0 @options={:scheme=>"redis", :host=>"127.0.0.1", :port=>6379, :path=>nil, :timeout=>5.0, :password=>nil, :db=>0, :time_class=>Time}, @db=#<MockRedis::PipelinedWrapper:0x007fb63b8e9150 @db=#<MockRedis::TransactionWrapper:0x007fb63b8e91a0 @db=#<MockRedis::ExpireWrapper:0x007fb63b8e91f0 @db=#<MockRedis::MultiDbWrapper:0x007fb63b8e9380 @db_index=0, @prototype_db=#<MockRedis::Database:0x007fb63b8e9330 @base=#<MockRedis:0x007fb63b8e94c0 ...>, @data={}, @expire_times=[]>, @databases={0=>#<MockRedis::Database:0x007fb63b8e9420 @base=#<MockRedis:0x007fb63b8e94c0 ...>, @data={}, @expire_times=[]>}>>, @transaction_futures=[], @in_multi=false, @multi_block_given=false>, @pipelined_futures=[], @in_pipeline=false>>
irb(main):002:0> redis.zadd('myzset', 10, 10)
=> true
irb(main):003:0> redis.zadd('myzset', 20, 20)
=> true
irb(main):004:0> redis.zadd('myzset', 30, 30)
=> true
irb(main):005:0> redis.zrange('myzset', 0, -4)
=> ["10"]

It looks like #128 introduced the problem.

hset command does not give proper return values

The command hset from redis-rb returns a different value than mock_redis. Redis returns a 1 when the key is new in the hash, or 0 if the key exists and was changed. The redis client gem converts these return values to true and false respectively, mock_redis universally returns true.

Below is an irb session that demonstrates the issue.

irb(main):003:0> r = Redis.new
irb(main):004:0> mr = MockRedis.new
irb(main):005:0> r.hset('myhash', 'key', 'first')
=> true
irb(main):006:0> mr.hset('myhash', 'key', 'first')
=> true
irb(main):007:0> r.hset('myhash', 'key', 'second')
=> false
irb(main):008:0> mr.hset('myhash', 'key', 'second')
=> true

#multi does not act the same as Redis gem

This bit me hard in our test suite. MockRedis#multi doesn't act the same as the official Redis gem. I'm unsure if I should start work on making MockRedis behave the same, because I'm unsure of the goal of the project; if it's to make a working implementation of Redis, or to emulate the official Redis gem.

The issue is any return of data inside of a multi block in the official Redis gem returns a Redis::Future object. This makes sense because the value is not going to be immediately available, because we are in a multi transaction. Ultimately you never even want to try and do any data requests in a multi block, but in our case we started a multi block up much higher in the stack.

In detail:

$redis.multi do
  x = $redis.get('1')
  #here x is a Redis::Future that is a subclass of BasicObject that looks like <Redis::Future [:get, "1"]>:Redis::Future
end

r = MockRedis.new
r.set '1', 1
r.multi do
  x = r.get '1'
  #x is '1', very different than expected and can cause false positives
end  

Point here is that we should make MockRedis do something different regardless of what it's trying to emulate. Fetching a value inside of a multi block should never immediately return the value, Redis does not work like that. For example, by using redis-cli

redis 127.0.0.1:6379> multi
OK
redis 127.0.0.1:6379> get '1'
QUEUED
redis 127.0.0.1:6379> exec
1) "1"

The question here is should MockRedis just emulate the normal redis-rb behavior, or something else?

setex performance degrades exponentially with keys count

require 'mock_redis'
mr = MockRedis.new

puts 'setex', (Benchmark.realtime do
    1000.times do |i|
        key = "some_key:#{i}"
        mr.setex(key, 3000, 'some value')
    end
end)

puts 'set', (Benchmark.realtime do
    1000.times do |i|
        key = "some_key:#{i}"
        mr.set(key, 'some value')
    end
end)
setex
1.039400445
set
0.010056671

With 10000 keys:

setex
107.453612374
set
0.106323161

Simulating behavior when redis unreachable?

Hi guys!

Is there a recommended way to test behavior when redis is unavailable/unreachable? (Basically, asking mock_redis to raise Redis::ConnectionErrors in response to any call?)

I'd love to be able to simulate downtime situations using this gem!

inconsistent behavior between `Redis#hdel`, `MockRedis#hdel`

See the following examples:

Redis

redis = Redis.new

redis.hset('test_key', 'test_field1', 'test_value1')
# => true

redis.hset('test_key', 'test_field2', 'test_value2')
# => true

[redis.hget('test_key', 'test_field1'), redis.hget('test_key', 'test_field2')]
# => ["test_value1", "test_value2"]

redis.hdel('test_key', ['test_field1', 'test_field2'])
# => 2

[redis.hget('test_key', 'test_field1'), redis.hget('test_key', 'test_field2')]
# => [nil, nil]

MockRedis

redis = MockRedis.new

redis.hset('test_key', 'test_field1', 'test_value1')
# => true

redis.hset('test_key', 'test_field2', 'test_value2')
# => true

[redis.hget('test_key', 'test_field1'), redis.hget('test_key', 'test_field2')]
# => ["test_value1", "test_value2"]

redis.hdel('test_key', ['test_field1', 'test_field2'])
# => 0

[redis.hget('test_key', 'test_field1'), redis.hget('test_key', 'test_field2')]
# => ["test_value1", "test_value2"]

Sorted Set input discrepencies

mock-redis

$mock_redis.zadd 'test_set', DateTime.now, "foo"
=> true

$mock_redis.zrevrangebyscore('test_set', DateTime.now, "-inf")
=> ["foo"]

redis-rb

$redis.zadd 'test_set', DateTime.now, "foo"
=> Redis::CommandError: ERR value is not a valid float

$redis.zrevrangebyscore('test_set', DateTime.now, "-inf")
=> Redis::CommandError: ERR min or max is not a float

issue

redis-rb requires floats for scores on sorted sets, whereas mock-redis does not. Proper implementation of the above sample code would require DateTime.now.to_i to be called to use redis-rb.

Keys are not converted to strings

Redis converts keys to strings, whereas MockRedis does not.

Example:

> r = Redis.new
=> #<Redis client v2.2.2 connected to redis://127.0.0.1:6379/0 (Redis v2.4.10)>
> r.set :x, 1
=> "OK"
> r.get 'x'
=> "1"

> r = MockRedis.new
=> #<MockRedis:0x0000000b0c6ec0...>
> r.set :x, 1
=> "OK"
> r.get 'x'
=> nil

Supporting pubsub commands

Hi, one of my tests expect the publish command to work (or at least not fail.) If I modify so it "supports" publish and subscribe, in the sense that publish is a no-op and subscribe raises MockRedis::WouldBlock, would you entertain the pull request?

Doesn't work with jRuby

There are failing tests when running them on jRuby 1.6.7 under both 1.8 mode and even more on 1.9 mode.

Does not support Redis EVAL?

The current implementation is tested against Redis 2.8.17.

Does this not include Redis EVAL/EVALSHA? According to the Redis docs EVAL was available starting with 2.6.

Adding Sorted Set with array of [score, member] throws "ERR syntax error"

I'm trying to use zadd with multiple score/member pairs inside an array.

For example:
redis.zadd("zset", [[32.0, "a"], [64.0, "b"]])

This is a perfectly valid command in Redis and works fine. When using mock_redis, however, this command generates the "ERR syntax error" on /lib/mock_redis/zset_methods.rb:19

Investigating further, it seems the splat (*args) wraps a new array around the passed array and therefore the conditionals don't work as expected. Perhaps, it is necessary to use flatten(1) before checking if the pairs are all valid on line 18:

unless args.flatten(1).all? {|pair| pair.size == 2 }

hmset raises CommandError when passed an actual array

Where $redis is a MockRedis, this works:

$redis.hmset("woot", "boo", "bar")

... but this causes assert_has_args to raise an error:

$redis.hmset(["woot", "boo", "bar"])

The official redis/redis-rb allows me to do either.

Streams support

Is there a plan to support Redis Streams (see https://redis.io/topics/streams-intro)? This feature will only become available with Redis 5.0 and as this is currently in beta I can understand that there is no reason it should be available. However, with a server running 4.9.101 (the release candidate) I can use (for example):

require 'redis'
redis.xadd 'mystream', '*', 'sensor-id', 1234, 'temperature', 19.8
# => entry ID returned as a string

I am currently evaluating Redis Streams and, if I go ahead with using them, I may try to create a wrapper gem. mock_redis would be very helpful for unit tests.

TIME command does not respond as expected

For example:

[1] pry(main)> require 'redis'
=> true
[2] pry(main)> require 'mock_redis'
=> true
[3] pry(main)> Redis.new.time
=> [1485530757, 588428]
[4] pry(main)> MockRedis.new.time
=> 2017-01-27 15:26:02 +0000

The expected behaviour of the TIME command is for it to return and array of two integers - the unix timestamp and the microseconds elapsed in the current second.

This is comparing the gems mock_redis version 0.17.1 and redis version 3.3.3 against a Redis server running version 3.2.6.

Using integer keys causes get/set to not work as expected

Hi,

I'm running into an issue when using a SET followed by a GET with integer keys. My productionredis-rb client handles this case.

[1] pry(main)> r = Redis.new;
[2] pry(main)> r.set(123, 'yo')
  Redis (3.30ms) SET 123 yo
=> "OK"
[3] pry(main)> r.get(123)
  Redis (0.65ms) GET 123
=> "yo"
[4] pry(main)> m = MockRedis.new;
[5] pry(main)> m.set(123, 'yo')
=> "OK"
[6] pry(main)> m.get(123)
=> nil

The key is converted into a string in the SET method, but not in the GET method

I'd be happy to submit a PR to change this behavior. Please let me know

Supporting eval

Any interest in adding support for eval (and possibly evalsha) using embedded LUA? I'm looking at the rufus-lua gem and it seems as though it wouldn't be difficult to wire up, but would require additional dependencies. If there is interest, how would you prefer that was tied in?

Mock for Ohm gem have a bug

Ohm (1.20 version) , if set index or unique attributes , when do model save operator , it will failed, and report error 'Wrong number args for ...'

I think the problem is Ohm generate a watch command that mock_redis is not supported ( Maybe redis version problem )

----------- I use below method to avoid this problem -----------
$redis = MockRedis.new
Redis.stubs(:connect).returns($redis)
$redis.stubs(:watch).returns(nil) # fix watch command bug

zrange can't handle string arguments

1.9.3p125 :017 > real_redis.zrange 'zset', '0', '-1', :withscores => true
 => ["a", "1"]
1.9.3p125 :021 > mock_redis.zrange 'zset', '0', '-1', :withscores => true
TypeError: can't convert String into Integer
    from /Users/betelgeuse/.rvm/gems/ruby-1.9.3-p125/gems/mock_redis-0.4.1/lib/mock_redis/zset_methods.rb:53:in `[]'
    from /Users/betelgeuse/.rvm/gems/ruby-1.9.3-p125/gems/mock_redis-0.4.1/lib/mock_redis/zset_methods.rb:53:in `block in zrange'
    from /Users/betelgeuse/.rvm/gems/ruby-1.9.3-p125/gems/mock_redis-0.4.1/lib/mock_redis/utility_methods.rb:10:in `with_thing_at'
    from /Users/betelgeuse/.rvm/gems/ruby-1.9.3-p125/gems/mock_redis-0.4.1/lib/mock_redis/zset_methods.rb:172:in `with_zset_at'
    from /Users/betelgeuse/.rvm/gems/ruby-1.9.3-p125/gems/mock_redis-0.4.1/lib/mock_redis/zset_methods.rb:52:in `zrange'
    from /Users/betelgeuse/.rvm/gems/ruby-1.9.3-p125/gems/mock_redis-0.4.1/lib/mock_redis/multi_db_wrapper.rb:21:in `method_missing'
    from /Users/betelgeuse/.rvm/gems/ruby-1.9.3-p125/gems/mock_redis-0.4.1/lib/mock_redis/expire_wrapper.rb:17:in `method_missing'
    from /Users/betelgeuse/.rvm/gems/ruby-1.9.3-p125/gems/mock_redis-0.4.1/lib/mock_redis/transaction_wrapper.rb:23:in `method_missing'
    from /Users/betelgeuse/.rvm/gems/ruby-1.9.3-p125/gems/mock_redis-0.4.1/lib/mock_redis.rb:26:in `method_missing'
    from (irb):21
    from /Users/betelgeuse/.rvm/gems/ruby-1.9.3-p125/gems/railties-3.1.4/lib/rails/commands/console.rb:45:in `start'
    from /Users/betelgeuse/.rvm/gems/ruby-1.9.3-p125/gems/railties-3.1.4/lib/rails/commands/console.rb:8:in `start'
    from /Users/betelgeuse/.rvm/gems/ruby-1.9.3-p125/gems/railties-3.1.4/lib/rails/commands.rb:40:in `<top (required)>'
    from ./script/rails:25:in `require'
    from ./script/rails:25:in `<main>'

License missing from gemspec

RubyGems.org doesn't report a license for your gem. This is because it is not specified in the gemspec of your last release.

via e.g.

spec.license = 'MIT'
# or
spec.licenses = ['MIT', 'GPL-2']

Including a license in your gemspec is an easy way for rubygems.org and other tools to check how your gem is licensed. As you can image, scanning your repository for a LICENSE file or parsing the README, and then attempting to identify the license or licenses is much more difficult and more error prone. So, even for projects that already specify a license, including a license in your gemspec is a good practice. See, for example, how rubygems.org uses the gemspec to display the rails gem license.

There is even a License Finder gem to help companies/individuals ensure all gems they use meet their licensing needs. This tool depends on license information being available in the gemspec. This is an important enough issue that even Bundler now generates gems with a default 'MIT' license.

I hope you'll consider specifying a license in your gemspec. If not, please just close the issue with a nice message. In either case, I'll follow up. Thanks for your time!

Appendix:

If you need help choosing a license (sorry, I haven't checked your readme or looked for a license file), GitHub has created a license picker tool. Code without a license specified defaults to 'All rights reserved'-- denying others all rights to use of the code.
Here's a list of the license names I've found and their frequencies

p.s. In case you're wondering how I found you and why I made this issue, it's because I'm collecting stats on gems (I was originally looking for download data) and decided to collect license metadata,too, and make issues for gemspecs not specifying a license as a public service :). See the previous link or my blog post about this project for more information.

Simulating max memory allocation

Hi

Are there any plans to simulate when the Mock Redis runs into its maximum allocated memory capacity so that it can return an error like the analogous Redis::CommandError (ERR command not allowed when used memory > 'maxmemory') for Redis?

Support hmset with an array

 require 'mock_redis'
 => true

REDIS1 = MockRedis.new
 => #<MockRedis:0x007feccd959e28 @options={:scheme=>"redis", :host=>"127.0.0.1", :port=>6379, :path=>nil, :timeout=>5.0, :password=>nil, :db=>0, :time_class=>Time}, @db=#<MockRedis::PipelinedWrapper:0x007feccd951ed0 @db=#<MockRedis::TransactionWrapper:0x007feccd9523d0 @db=#<MockRedis::ExpireWrapper:0x007feccd952448 @db=#<MockRedis::MultiDbWrapper:0x007feccd958c80 @db_index=0, @prototype_db=#<MockRedis::Database:0x007feccd958870 @base=#<MockRedis:0x007feccd959e28 ...>, @data={}, @expire_times=[]>, @databases={0=>#<MockRedis::Database:0x007feccd959360 @base=#<MockRedis:0x007feccd959e28 ...>, @data={}, @expire_times=[]>}>>, @transaction_futures=[], @in_multi=false, @multi_block_given=false>, @pipelined_futures=[], @in_pipeline=false>>

a = {1 => 2, 3=>4}.to_a.flatten
 => [1, 2, 3, 4]

 REDIS1.hmset('b',a)
Redis::CommandError: ERR wrong number of arguments for HMSET
	from /Users/vjain/.rvm/gems/ruby-2.2.3@subject_data_integration/gems/mock_redis-0.16.0/lib/mock_redis/hash_methods.rb:93:in `hmset'
	from /Users/vjain/.rvm/gems/ruby-2.2.3@subject_data_integration/gems/mock_redis-0.16.0/lib/mock_redis/multi_db_wrapper.rb:21:in `method_missing'
	from /Users/vjain/.rvm/gems/ruby-2.2.3@subject_data_integration/gems/mock_redis-0.16.0/lib/mock_redis/expire_wrapper.rb:17:in `method_missing'
	from /Users/vjain/.rvm/gems/ruby-2.2.3@subject_data_integration/gems/mock_redis-0.16.0/lib/mock_redis/transaction_wrapper.rb:30:in `method_missing'
	from /Users/vjain/.rvm/gems/ruby-2.2.3@subject_data_integration/gems/mock_redis-0.16.0/lib/mock_redis/pipelined_wrapper.rb:27:in `method_missing'
	from /Users/vjain/.rvm/gems/ruby-2.2.3@subject_data_integration/gems/mock_redis-0.16.0/lib/mock_redis.rb:89:in `method_missing'
	from (irb):4
	from /Users/vjain/.rvm/gems/ruby-2.2.3@subject_data_integration/gems/railties-4.2.5.2/lib/rails/commands/console.rb:110:in `start'
	from /Users/vjain/.rvm/gems/ruby-2.2.3@subject_data_integration/gems/railties-4.2.5.2/lib/rails/commands/console.rb:9:in `start'
	from /Users/vjain/.rvm/gems/ruby-2.2.3@subject_data_integration/gems/railties-4.2.5.2/lib/rails/commands/commands_tasks.rb:68:in `console'
	from /Users/vjain/.rvm/gems/ruby-2.2.3@subject_data_integration/gems/railties-4.2.5.2/lib/rails/commands/commands_tasks.rb:39:in `run_command!'
	from /Users/vjain/.rvm/gems/ruby-2.2.3@subject_data_integration/gems/railties-4.2.5.2/lib/rails/commands.rb:17:in `<top (required)>'
	from bin/rails:4:in `require'
	from bin/rails:4:in `<main>'


REDIS2 = Redis.new(url: 'redis://localhost:6379')
 => #<Redis client v3.2.1 for redis://localhost:6379/0>
 REDIS2.hmset('b',a)
 => "OK"

#<ArgumentError: tried to create Proc object without a block>

I am using redis but I have problem to test it.
I have a global variable $redis and in specs MockRedis is used:

   before :all do
     @redis = $redis
     $redis = MockRedis.new
   end
    
   after :all do
     $redis = @redis
   end

In index action I have:

      $redis.set("payment_transaction_searched_ids",@ids.join(","))

and in other action I have:

      ids = $redis.get("payment_transaction_searched_ids")

I have begin and rescue on both callings to redis and 'set' passes but when I call 'get' I get this exception:

     ArgumentError: tried to create Proc object without a block

"del" discrepency

redis

irb(main):001:0> $redis.set 'a','a'
=> "OK"
irb(main):002:0> $redis.set 'b','b'
=> "OK"
irb(main):003:0> $redis.del ['a','b']
=> 2

mock-redis

irb(main):001:0> $mock_redis.set 'a','a'
=> "OK"
irb(main):002:0> $mock_redis.set 'b','b'
=> "OK"
irb(main):003:0> $mock_redis.del ['a','b']
=> 0

issue

mock-redis requires the splat operator on arrays, whereas redis does not:

irb(main):004:0> $mock_redis.del *['a','b']
=> 2

Calling flushdb to clear the database between tests?

This is partly a question/discussion, but I believe that when using MockRedis in tests flushdb should be called between each test to clear the database. If that's correct, should that be mentioned in the readme? (I'm happy to make a pull request for that, but I wanted to make sure that my understanding is correct first)

Nested multi throws <Redis::CommandError: ERR MULTI calls can not be nested>

While this would indeed be an error on redis-cli, the official redis-rb gem supports it.

 pry(main)> r = Redis.new
=> #<Redis client v4.0.2 for redis://127.0.0.1:6379/0
 pry(main)> r.multi do
 pry(main)*   r.set('foo', 'bar')
 pry(main)*   r.multi do
 pry(main)*     r.set('foo', 'baz')
 pry(main)*   end
 pry(main)* end
=> ["OK", "OK"]
 pry(main)> r.get('foo')
=> "baz"

Version 0.3.0 needs to be published

Can we push 0.3.0 to rubygems? I've got a large pull request in the making for another project and the tests rely on my changes to mock_redis on master. I'd rather not use my fork of mock_redis since the changes have already been accepted.

smembers returns members in the wrong order

It seems like mock_redis returns a reversed array vs. Redis.

Redis returns the members in the order they were inserted (last is last) but mock_redis returns this [last, first].

The result when passing an array of integer to srem is not as expected

Hi,
When I pass an array of integer to srem, the members could not be deleted as expeced.
But in redis gem, it works.

r = Redis.new;
r.sadd('k', [1]);
r.srem('k', [1])
=> 1

m = MockRedis.new;
m.sadd('k', [1]);
m.srem('k', [1])
=> 0

Environment

ruby 2.5.5
redis 4.1.0
mock_redis 0.20.0

REDIS.dbsize errors when there is no data in MockRedis

REDIS_APP_JOIN = Redis::Namespace.new(:appjoin, redis: MockRedis.new )
#
it 'invalid test' do
  # run the actual test
  expect(REDIS_APP_JOIN.dbsize).to eq 0
end
#
expected: 0
got: #<MockRedis::Future:0x00000001e8f660 @command=[:dbsize], @result_set=false>

The test is part of a gem I recently created https://github.com/dmitrypol/redis_app_join/blob/master/spec/redis_app_join_spec.rb#L37

Here is Gemfile.lock https://github.com/dmitrypol/redis_app_join/blob/master/Gemfile.lock

It works when there is data in Redis. Has anyone experienced this?

Add support for BITCOUNT command

bitcount key [start] [end] counts the number of set bits aka population count of a string and has been available since 2.6.0. Is there any sort of plan to implement this?

Multi block within pipelined block

MR gets stuck in multi mode if multi block is called like so:

mr.pipelined do
  mr.multi do
    mr.set('abc', 'abv')
  end
end

results in:

[9] pry(main)> mr
=> #<MockRedis:0x0000000664bd78
 @db=
  #<MockRedis::PipelinedWrapper:0x0000000664b940
   @db=
    #<MockRedis::TransactionWrapper:0x0000000664b990
     @db=
      #<MockRedis::ExpireWrapper:0x0000000664b9b8
       @db=
        #<MockRedis::MultiDbWrapper:0x0000000664bbe8
         @databases={0=>#<MockRedis::Database:0x0000000664bcd8 @base=#<MockRedis:0x0000000664bd78 ...>, @data={"abc"=>"abv"}, @expire_times=[]>},
         @db_index=0,
         @prototype_db=#<MockRedis::Database:0x0000000664bb70 @base=#<MockRedis:0x0000000664bd78 ...>, @data={}, @expire_times=[]>>>,
     @in_multi=true,
     @multi_block_given=false,
     @transaction_futures=[]>,
   @in_pipeline=false,
   @pipelined_futures=[]>,
 @options={:scheme=>"redis", :host=>"127.0.0.1", :port=>6379, :path=>nil, :timeout=>5.0, :password=>nil, :db=>0, :time_class=>Time}>
 
[10] pry(main)> mr.get('abc')
=> "QUEUED"

Explicit exec does finish transaction though.
This does not occur if multi is used with explicit exec in the first place, or blocks are nested other way around - pipelined within multi.

Discrepancy in return value for SADD

Using redis-rb:

[0] pry(main)> Redis.new.sadd "temp", ["123"]
=> 1
[1] pry(main)> Redis.new.sadd "temp", "12"
=> true

Using mock_redis:

[0] pry(main)> MockRedis.new.sadd "temp", ["123"]
=> true
[1] pry(main)> MockRedis.new.sadd "temp", "12"
=> true

This is probably because of here:
https://github.com/brigade/mock_redis/blob/master/lib/mock_redis/set_methods.rb#L10

I guess this is also an issue with redis-rb. Since the return value of SADD should always be an integer.

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    ๐Ÿ–– Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. ๐Ÿ“Š๐Ÿ“ˆ๐ŸŽ‰

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google โค๏ธ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.