Redis起步
Linux安装
- 到官网下载tar.gz包
- 解压: tar -xzf redis-3.2.5.tar.gz
- 进入redis-3.2.5执行命令: make
- 安装: make install
- 复制配置文件: cp redis.conf /etc/
启动和关闭
- 在根目录下创建目录myredis,将目录redis-3.2.5里的redis.conf复制到此
- vim打开redis.conf,修改里面’daemonize no’改为’daemonize yes’
- 进入’usr/local/bin’,输入命令行’redis-server /myredis/redis.conf’启动服务
- 输入命令行’redis-cli -p 6379’进入客户端
- 进入后前缀会是’127.0.0.1:6379> ‘,输入’ping’,回应’PONG’则成功
- 输入’shutdown’关闭,再输入’exit’退出
使用Redis
测试
启动Redis后,在’usr/local/bin’下输入命令’redis-benchmark’可以测试redis读取性能等信息
选择库
Redis默认有16个库,可以用’select 4’选择,从0开始
创建键值对
Redis为KV数据库,数据以键值对形式保存
SET [key] [value]
//创建
SET kk HelloRedis
查询
查询时输入’键’查询
GET [key]
//获取
get kk
keys查询键
KEYS [pattern]
//获取所有键
KEYS *
//模糊匹配查询键
KEYS k?
查询键数量
DBSIZE
清除
清除当前库所有数据
FLUSHDB
清除所有库的数据
FLUSHALL
数据类型
五大数据类型
- String (字符串)
- Hash (哈希,类似Map)
- List (列表)
- Set (集合)
- ZSet (Sorted Set有序集合)
Redis键key
获取当前库的所有key
KEY *
判断某个key是否存在
EXIST k1
移动key到其他数据库
//移动k1到库2
MOVE k1 2
给key设置过期时间
//设置k1键10秒后过期
EXPIRE k1 10
查看过期时间
//查看k1还有多久过期,-1为不过期,-2为已过期,正数为剩余秒数
TTL k1
查看key是什么类型
TYPE k1
Redis字符串String
普通增删改查
SET/GET/DEL/APPEND/STRLEN(查询值的长度)
条件新增
//SETEX [key] [second] [value],新增定时过期key
//新增kex键10秒后过期
SETEX kex 10 aaa
//SETNX,数据库不存在此可以才新增,失败返回0
SETNX k1 aa
加减,只有数字类型才能进行加减
//INCR(自增)/DECR(自减)
INCR k1
//INCRBY/DECYBY
//增加2
INCRBY ki 2
截取字符串
//GETRANGE
//获取0-4的值
GETRANGE kk 0 4
//SETRANGE
//从下标5开始,将值换为aaaa,直到换完,剩余的保持不变
SETRANGE kk 5 aaaa
批量新增和获取
//MSET
//批量插入键值
MSET k1 v1 k2 v2
//MGET
//获取k1和k2
MGET k1 k2
//MSETNX
//当key不存在才插入,如果插入的键存在,则返回0
MSETNX k1 va k3 vb
Redis列表List
新建List和查看
//LPUSH [key] [value] [value]...,左边插入,
LPUSH list01 1 2 3 4 5
//LRANGE [key] [start] [stop],查看,[stop]为'-1'表示最后一位下标
LRANGE list01 0 -1
//结果为5 4 3 2 1
//RPUSH [key] [value] [value]...,右边插入
RPUSH list02 1 2 3 4 5
//LRANGE [key] [start] [stop],查看,[stop]为'-1'表示最后一位下标
LRANGE list02 0 -1
//结果为1 2 3 4 5
出栈(类比),即删除头尾值
//LPOP [key],左边出栈
LPOP list01
LRANGE list01 0 -1
//结果为4 3 2 1
//RPOP [key],右边出栈
RPOP list01
LRANGE list01 0 -1
//结果为4 3 2
根据下标获取值
//LINDEX [key] [index]
LINDEX list01 0
获取List长度
//LLEN [key]
LLEN list01
删除value
//LREM [key] [count] [value]
//删除3个value为2的数据
LREM list01 3 2
截取再赋值
//LTRIM [key] [start] [stop]
//截取下标0-2的value,再重新赋值给list01,此时list01只有3个value
LTRIM list01 0 2
取’源List’数据赋给’目标List’
//RPOPLPUSH [source] [destination]
//将list02右边出栈,将值在list01左边入栈
RPOPLPUSH list02 list01
插入
//LINSERT [key] BEFORE/AFTER [pivot] [value]
//在list01中,value为1的前面添加3
LINSERT list01 BEFORE 1 3
Redis列表Set
新增查询
//SADD [key] [member] [member]...,添加集合
//set集合会自动去重
SADD set01 1 1 2 2 3 3
//SMEMBERS [key],查询集合所有元素
SMEMBERS set01
//SISMEMBER [key] [member],查询集合中是否存在此元素
SISMEMBER set01 1
//SCARD [key],查询集合元素个数
SCARD set01
删除
//SREM [key] [member]
SREM set01 1
随机数
//SRANDMEMBER [key] [count],获取n个随机数
//在set01中随机获取2个元素
SRANDMEMBER set01 2
//SPOP [key] [count],随机出栈,与上类似
//取一个时,可以省略count,上同
SPOP set01
集合间移动元素
//SMOVE [key1] [key2] [member],将key1中的member移动到key2
SMOVE set01 set02 2
数学集合类
//SDIFF [key1] [key1] ...,差集,取出key1独有的元素
SDIFF set01 set02
//SINTER [key1] [key2] ...,交集
SINTER set01 set02
//SUNION [key1[ [key2] ...,并集
Redis哈希Hash(重要)
哈希表示在KV的V中存放KV
新增查询删除
//HSET [key] [field] [value],新增哈希map
HSET hash01 name aa
//HGET [key] [field],获取
//HMSET [key] [field] [value] ...,添加多个
HMSET hash01 age 12 email aa@qq
//HMGET [key] [field] ...,获取多个
HMGET hash01 name age email
//HGETALL [key],获取所有
HGETALL hash01
//HDEL [key] [field] ...,删除
HDEL hash01 age email
//HLEN [key],获取长度
HLEN hash01
//HKEYS [key],获取所有的field
HKEYS hash01
//HVALS [key],获取所有的value
HVALS hash01
//HSETNX [key] [field] [value],不存在才存入
HSETNX hash01 age 1
自增
//HINCRBY [key] [field] [increment],自增
HINCRBY hash01 age 2
//HINCRBYFLOAT [key] [field] [increment],浮点自增
HINCRBY hash01 salary 0.2
Redis有序集合ZSet
ZSet在Set的基础上添加了score
新增查询
//ZADD [key] [score] [member] ...,新增
ZADD zset01 60 v1 70 v2 80 v3 90 v4 100 v5
//ZRANGE [key] [start] [stop] (WITHSCORE),查询
ZRANGE zset01 0 -1 WITHSCORE
//ZRANGEBYSCORE [key] [min] [max] (WITHSCORE) (LIMIT),条件查询
//查询60-90之间的值,输出score,再从第3条开始,限制2条输出
ZRANGEBYSCORE zset01 60 90 WITHSCORE LIMIT 2 2
删除
//ZREM [key] [member] ...,删除
ZREM zset01 v5
获取长度
//ZCARD [key],获取长度
ZSET zset01
//ZCOUNT [key] [min] [max],条件获取长度
ZCOUNT zset01 60 80
//ZSCORE [key] [member],根据member获取score
ZSCORE zset01 v1
逆排序
//ZREVRANK [key] [member],获得逆序的下标
ZREVRANK zset01 v1
//ZREVRANGE [key] [start] [stop] (WITHSCORE),逆序查询
ZREVRANGE zset01 0 2 WITHSCORE
//ZREVRANGEBYSCORE [key] [min] [max] (WITHSCORE) (LIMIT),逆序条件查询
ZREVRANGEBYSCORE zset01 90 60 WITHSCORE LIMIT 2 2
持久化
RDB(Redis Database)
在指定的时间间隔内将内存中的数据集快照写入磁盘,也就是Snapshot快照,它恢复时是将快照文件直接读到内存里。
Redis会单独创建(fork)一个子进程来进行持久化,会先将数据写入到一个临时文件中,待持久化过程都结束了,再用这个临时文件替换上次持久化好的文件。整个过程中,主进程是不进行任何IO操作的,这就确保了极高的性能如果需要进行大规模数据的恢复,且对于数据恢复的完整性不是非常敏感,那RDB方式要比AOF方式更加的高效。RDB的缺点是最后一次持久化后的数据可能丢失。
配置文件
RDB的配置在redis.conf中,在SNAPSHOTTING模块
主要配置
//save <seconds> <changes>,表示在多少秒内达到多少次改动就出发保存
save 900 1
rdbcompression yes,是否压缩,默认压缩
dbfilename dump.rdb,持久化文件名
dir ./,保存所在目录
手动持久化
-
在客户端直接输入’SAVE‘命令即可手动持久化当前数据
-
‘FLUSHALL‘命令也会触发持久化数据操作
AOF(Append Only File)
以日志的形式来记录每个写操作,将Redis执行过的所有写指令记录下来(读操作不记录),只许追加文件但不可以改写文件,redis启动之初会读取该文件重新构建数据,换言之,redis重启的话就根据日志文件的内容将写指令从前到后执行一次以完成数据的恢复工作.
配置文件
RDB的配置在redis.conf中,在APPEND ONLY MODE模块
//打开AOF,默认为no
appendonly yes
//持久化文件名
appendfilename "appendonly.aof"
//记录时间,默认为一秒一次
appendfsync everysec
rewrite
AOF采用文件追加方式,文件会越来越大为避免出现此种情况,新增了重写机制,当AOF文件的大小超过所设定的阈值时,Redis就会启动AOF文件的内容压缩,只保留可以恢复数据的最小指令集.可以使用命令bgrewriteaof。
原理:AOF文件持续增长而过大时,会fork出一条新进程来将文件重写(也是先写临时文件最后再rename),遍历新进程的内存中数据,每条记录有一条的Set语句。重写aof文件的操作,并没有读取旧的aof文件,而是将整个内存中的数据库内容用命令的方式重写了一个新的aof文件,这点和快照有点类似。
触发机制:Redis会记录上次重写时的AOF大小,默认配置是当AOF文件大小是上次rewrite后大小的一倍且文件大于64M时触发
可在配置文件更改出发条件
//默认为一倍
auto-aof-rewrite-percentage 100
auto-aof-rewrite--min-size 64mb
修复appendonly.aof
可使用命令’redis-check-aof –fix‘修复appendonly.aof的指令,使其正确可用。
事务
使用
//开启事务
MULTI
//命令入队
set k1 v2
set k2 v2
//提交事务
EXEC
//放弃事务
DISCARD
//监听某个key,如果事务中间被人修改了,事务失败
WATCH [key]
//取消监听
UNWATCH [key]
如果其中的命令格式错误,使用’EXEC’提交后会回滚,即所有命令都不执行
但如果是命令执行时错误,那么错误的命令报错,其他命令继续执行
特性
-
单独的隔离操作:事务中的所有命令都会序列化、按顺序地执行。事务在执行的过程中,不会被其他客户端发送来的命令请求所打断。
-
没有隔离级别的概念:队列中的命令没有提交之前都不会实际的被执行,因为事务提交前任何指令都不会被实际执行,也就不存在”事务内的查询要看到事务里的更新,在事务外查询不能看到”这个让人万分头痛的问题。
-
不保证原子性:redis同一个事务中如果有一条命令执行失败,其后的命令仍然会被执行,没有回滚
主从复制
使用步骤
修改配置文件
复制三份配置文件’redis.conf’,分别命名为’redis6379.conf’,’redis6380.conf’,’redis6381.conf’
进入每个配置文件,按赋予的端口号修改信息,下面以6380端口为例
//开启守护线程运行
daemonize yes
//修改端口
port 6380
//修改pidfile
portfile /var/run/redis_6380.pid
//修改logfile
logfile "6380.log"
//修改备份文件dbfilename
dbfilename dump6380.rdb
使用
分别使用上面的三个配置文件开启三个redis服务,其中6379作为主库
在主库先存入3个KV数据
两个从库开启后输入命令连接从库
//SLAVEOF [ip] [port]
SLAVEOF 127.0.0.1 6379
//解除从库状态
SLAVE no one
//可查看数据库主从库情况
INFO REPLICATION
之后主库的所有数据都会复制到从库,但从库不可以写入数据,只能读取。
注意:主库关闭后,从库会待命,等待主库上线;从库关闭重新开启后不再连接主库,需要重新输入命令连接。
哨兵模式
所谓哨兵模式,就是监控主库,主库挂了以后,在从库中选出一个来当做主库
在’/myredis’下创建文件’sentinel.conf’,加入以下配置
//sentinel monitor <自定义主库名> ip port <投票大于数字>
sentinel monitor post6397 127.0.0.1 6379 1
在’/usr/local/bin’下输入’redis-sentinel /myredis/sentinel.conf’可开启哨兵监控。
当主库挂了以后,从库中的某一个库会当选为主库,此后主库再上线后不会恢复为主库,将降级为从库。