Skip to content

Commit

Permalink
Merge commit 'ezmobius/master'
Browse files Browse the repository at this point in the history
Conflicts:
	lib/redis.rb
	spec/redis_spec.rb
  • Loading branch information
jeremy committed Mar 22, 2009
2 parents 2bee186 + e746b1f commit e8d087d
Show file tree
Hide file tree
Showing 4 changed files with 108 additions and 8 deletions.
2 changes: 1 addition & 1 deletion Rakefile
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@ require 'tasks/redis.tasks'


GEM = 'redis'
GEM_VERSION = '0.0.2'
GEM_VERSION = '0.0.3'
AUTHORS = ['Ezra Zygmuntowicz', 'Taylor Weibley']
EMAIL = "ez@engineyard.com"
HOMEPAGE = "http://github.com/ezmobius/redis-rb"
Expand Down
64 changes: 62 additions & 2 deletions lib/redis.rb
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
require 'socket'
#require File.join(File.dirname(__FILE__),'better_timeout')
require File.join(File.dirname(__FILE__),'better_timeout')
require 'set'

class RedisError < StandardError
Expand Down Expand Up @@ -55,7 +55,7 @@ def []=(key, val)
def set_unless_exists(key, val)
val = redis_marshal(val)
timeout_retry(3, 3){
OK == perform("SETNX #{key} #{val.size}\r\n#{val}\r\n")
1 == perform("SETNX #{key} #{val.size}\r\n#{val}\r\n")
}
end

Expand Down Expand Up @@ -390,6 +390,36 @@ def list_index(key, index)
}
end

# LREM key count value
#
# Time complexity: O(N) (with N being the length of the list)
#
# Remove the first count occurrences of the value element from the list.
# If count is zero all the elements are removed. If count is negative
# elements are removed from tail to head, instead to go from head to
# tail that is the normal behaviour. So for example LREM with count -2
# and hello as value to remove against the list (a,b,c,hello,x,hello,hello)
# will lave the list (a,b,c,hello,x). The number of removed elements is
# returned as an integer, see below for more information aboht the returned value.
# Return value
#
# Integer Reply, specifically:
#
# The number of removed elements if the operation succeeded
# -1 if the specified key does not exist
# -2 if the specified key does not hold a list value
def list_rm(key, count, value)
res = perform("LREM #{key} #{count} #{value.to_s.size}\r\n#{value}\r\n").to_i
case res
when -1
raise RedisError, "key: #{key} does not exist"
when -2
raise RedisError, "key: #{key} does not hold a list value"
else
res
end
end

# SADD key member
# Time complexity O(1)
# Add the specified member to the set value stored at key. If member is
Expand Down Expand Up @@ -681,6 +711,36 @@ def quit
}
end


def info
info = {}

x = timeout_retry(3, 3){
write "INFO\r\n"
read(read_proto.to_i.abs).split("\r\n")
}

x.each do |kv|
k,v = kv.split(':')[0], kv.split(':')[1]
info[k.to_sym] = v
end

info
end

def flush_db
timeout_retry(3, 3){
perform("FLUSHDB\r\n")
}
end


def last_save
timeout_retry(3, 3){
perform("LASTSAVE\r\n").to_i
}
end

def connect
@socket = TCPSocket.new(@opts[:host], @opts[:port])
@socket.sync = true
Expand Down
31 changes: 31 additions & 0 deletions spec/redis_spec.rb
Original file line number Diff line number Diff line change
Expand Up @@ -197,6 +197,16 @@ class MyFail; def fail; 'it will' end; end
@r.delete('list')
end

it "should be able to remove values from a list LREM" do
@r.push_tail "list", 'hello'
@r.push_tail "list", 'goodbye'
@r.type?('list').should == "list"
@r.list_length('list').should == 2
@r.list_rm('list', 1, 'hello').should == 1
@r.list_range('list', 0, -1).should == ['goodbye']
@r.delete('list')
end

it "should be able add members to a set" do
@r.set_add "set", 'key1'
@r.set_add "set", 'key2'
Expand Down Expand Up @@ -266,4 +276,25 @@ class MyFail; def fail; 'it will' end; end
@r.sort('dogs', :get => 'dog_*', :limit => [0,1]).should == ['louie']
@r.sort('dogs', :get => 'dog_*', :limit => [0,1], :order => 'desc alpha').should == ['taj']
end

it "should provide info" do
[:last_save_time, :redis_version, :total_connections_received, :connected_clients, :total_commands_processed, :connected_slaves, :uptime_in_seconds, :used_memory, :uptime_in_days, :changes_since_last_save].each do |x|
@r.info.keys.should include(x)
end
end

it "should be able to flush the database" do
@r['key1'] = 'keyone'
@r['key2'] = 'keytwo'
@r.keys('*').sort.should == ['foo', 'key1', 'key2'] #foo from before
@r.flush_db
@r.keys('*').should == []
end

it "should be able to provide the last save time" do
savetime = @r.last_save
Time.at(savetime).class.should == Time
Time.at(savetime).should <= Time.now
end

end
19 changes: 14 additions & 5 deletions tasks/redis.tasks.rb
Original file line number Diff line number Diff line change
Expand Up @@ -52,6 +52,12 @@ def self.stop
task :stop do
RedisRunner.stop
end

desc 'Restart redis'
task :restart do
RedisRunner.stop
RedisRunner.start
end

desc 'Attach to redis dtach socket'
task :attach do
Expand All @@ -60,9 +66,12 @@ def self.stop

desc 'Install the lastest redis from svn'
task :install => [:about, :download, :make] do
sh 'sudo cp /tmp/redis/redis-server /usr/bin/'
sh 'sudo cp /tmp/redis/redis-benchmark /usr/bin/'
puts 'Installed redis-server and redis-benchmark to /usr/bin/'
%w(redis-benchmark redis-cli redis-server).each do |bin|
sh "sudo cp /tmp/redis/#{bin} /usr/bin/"
end

puts "Installed redis-benchmark, redis-cli and redis-server to /usr/bin/"

unless File.exists?('/etc/redis.conf')
sh 'sudo cp /tmp/redis/redis.conf /etc/'
puts "Installed redis.conf to /etc/ \n You should look at this file!"
Expand All @@ -76,8 +85,8 @@ def self.stop

desc "Download package"
task :download do
system 'svn checkout http://redis.googlecode.com/svn/trunk /tmp/redis' unless File.exists?(RedisRunner.redisdir)
system 'svn up' if File.exists?("#{RedisRunner.redisdir}/.svn")
sh 'svn checkout http://redis.googlecode.com/svn/trunk /tmp/redis' unless File.exists?(RedisRunner.redisdir)
sh "cd #{RedisRunner.redisdir} && svn up" if File.exists?("#{RedisRunner.redisdir}/.svn")
end

end
Expand Down

0 comments on commit e8d087d

Please sign in to comment.