1. Redis内部实现
1.1. 独立功能实现
1.1.1. 发布和订阅
(1)启动redis-cli,订阅new.*消息
redis 127.0.0.1:6379> psubscribe news.*
Reading messages... (press Ctrl-C to quit)
1) "psubscribe"
2) "news.*"
3) (integer) 1
(2)启动另一个redis-cli用来发布两条消息:
redis 127.0.0.1:6379> publish news.share "share a link http://www.google.com"
(integer) 2
redis 127.0.0.1:6379> publish news.blog "I post a blog"
(integer) 2
(3)此时之前订阅的client会打印:
1) "pmessage"
2) "news.*"
3) "news.share"
4) "share a link http://www.google.com"
1) "pmessage"
2) "news.*"
3) "news.blog"
4) "I post a blog"
1.1.2. 事务:
将多个命令打包,一次性执行多条命令。
127.0.0.1:6379> multi //开始对下面命令进行打包
OK
127.0.0.1:6379> SET “name” “Practical Common Lisp”
QUEUED
127.0.0.1:6379> GET “name”
QUEUED
127.0.0.1:6379> SET “author” “Peter Seibel”
QUEUED
127.0.0.1:6379> GET “author”
QUEUED
127.0.0.1:6379> EXEC //执行命令包
1)OK
2) “Practical Common Lisp”
3)OK
4)“Peter Seibel”
Watch的乐观锁的作用:
127.0.0.1:6379> watch “name” //watch下的name在事务将被拒绝执行
1.1.3. Lua脚本
通过redis.call('hexists', KEYS[3], KEYS[4])调用代替,redisCommand(context,format),使更灵活。
抢红包案例:http://blog.youkuaiyun.com/hengyunabc/article/details/19433779
/*- 函数:尝试获得红包,如果成功,则返回json字符串,如果不成功,则返回空
*-- 参数:红包队列名, 已消费的队列名,去重的Map名,用户ID
*-- 返回值:nil 或者 json字符串,包含用户ID:userId,红包ID:id,红包金额:money
*/
//-- 如果用户已抢过红包,则返回nil
if redis.call('hexists', KEYS[3], KEYS[4]) ~= 0 then
return nil
else
//-- 先取出一个小红包
local hongBao = redis.call('rpop', KEYS[1]);
if hongBao then
local x = cjson.decode(hongBao);
//-- 加入用户ID信息
x['userId'] = KEYS[4];
local re = cjson.encode(x);
//-- 把用户ID放到去重的set里
redis.call('hset', KEYS[3], KEYS[4], KEYS[4]);
// -- 把红包放到已消费队列里
redis.call('lpush', KEYS[2], re);
return re;
end
end
return nil
1.1.4. 排序
对象:set,score-set,list这三种。
(1)SORT <key> ASC升序排序,同SORT <key>也是升序
(2)SORT <key> DESC降序排序
(3)SORT <key> ALPHA可对字符串值进行排序,否则(1)(2)只能是数值.
(4)SORT <key> BY *-price
SORT <key> BY *-price
1)”banana”
2)”cherry”
3)”apple”
依据“元素+price”的权重键值做来排序,如
SADD fruite “apple” “banana” “cherry”
MSET apple-price 8 banana-price 5.5 cherry-price 7
SORT fruits BY *-price执行过程:
(a) 将fruits元素拼接-price,组成如apple-price作为权重键,查的对应权重键值8.
(b) 根据每个元素的权重键值作为排序依据
(5) SORT <key> BY *-id ALPHA可对字符串值作为权重值进行排序,如下依据“id-8”,“id-5.5”,“id-7”字符串值排序。
SADD fruite “apple” “banana” “cherry”
MSET apple-id id-8 banana-id id-5.5 cherry-id id-7
(6) SORT <key> LIMIT <offset><count>排序结果显示数量控制
(7) 127.0.0.1:6379> SORT studentALPHA
127.0.0.1:6379> SORT studentALPHA
1) "jack"
2) "peter"
3) "tom"
127.0.0.1:6379> SET peter-name "Peterwhite"
OK
127.0.0.1:6379> set jack-name "JackSnow"
OK
127.0.0.1:6379> set tom-name "TomSmith"
OK
127.0.0.1:6379> SORT student ALPHA GET *-name
1) "Jack Snow"
2) "Peter white"
3) "Tom Smith"
依据“元素+name”作为程序返回键,并向客户端返回对应键值。
GET可以是多个,如:
127.0.0.1:6379> SET peter-birth 1995-6-7
OK
127.0.0.1:6379> SET tom-birth 1995-8-7
OK
127.0.0.1:6379> SET jack-birth 1995-9-7
OK
127.0.0.1:6379> SORT student ALPHA GET *-name GET*-birth
1) "Jack Snow"
2) "1995-9-7"
3) "Peter white"
4) "1995-6-7"
5) "Tom Smith"
6) "1995-8-7"
(8) SORT <key> ALPHA STORE<key> STORE参数可以用于将排序结果保存为另一个key
127.0.0.1:6379> SORT students ALPHA STORE sorted_students
1.1.5. 二进制
可存二进制数值,并支持& ,|等位运算。
1.1.6. 慢查询日志
127.0.0.1:6379> CONFIG SET slowlog-log-slower-then 0 //记录执行时间超过多少微秒的命令,0表示所有命令都记录
127.0.0.1:6379> CONFIG SET slowlog-max-len 5 //最多保存多少条慢查询日志
127.0.0.1:6379> SLOWLOG GET
1.1.7. 监视器
127.0.0.1:6379> MONITOR
通过设置监视模式,客户端可以查看每个客户端发向服务器侧的命令