Redis 学习

Redis 学习

1. redis 简介

Redis是什么 (biancheng.net)

  • yum 安装

    yum install epel-release
    yum install -y redis
    
  • redis 可执行文件

    redis-benchmark  # redis性能测试
    redis-check-aof  # 检查修复aof文件
    redis-check-rdb  # 检查修复rdb文件
    redis-cli        # redis的客户端
    redis-sentinel   # redis的集群
    redis-server     # redis的服务端
    
  • 启动redis

    systemctl start redis
    # 默认端口: 6379
    

2 性能测试

# redis-benchmark -q
PING_INLINE: 29904.30 requests per second
PING_BULK: 32669.06 requests per second
SET: 33255.74 requests per second
GET: 32030.75 requests per second
INCR: 33036.01 requests per second
LPUSH: 40600.89 requests per second
RPUSH: 37341.30 requests per second
LPOP: 38880.25 requests per second
RPOP: 32372.94 requests per second
SADD: 37693.18 requests per second
HSET: 38986.36 requests per second
SPOP: 33898.30 requests per second
LPUSH (needed to benchmark LRANGE): 39888.31 requests per second
LRANGE_100 (first 100 elements): 15898.25 requests per second
LRANGE_300 (first 300 elements): 5742.51 requests per second
LRANGE_500 (first 450 elements): 3673.63 requests per second
LRANGE_600 (first 600 elements): 2999.58 requests per second
MSET (10 keys): 27723.87 requests per second
默认是100000,50个同时发起连接

3 连接 redis 服务并配置

3.1 连接 redis

redis-cli -h hostname -p port -a password
# 默认无密码连接本地127.0.0.1的6379端口
# redis的命令不区分大小写

3.2 redis的数据类型

  1. string
  2. hash
  3. list
  4. set:集合
  5. zset:有序集合

3.3 命令相关

3.3.1 基础命令

# ping用来测试redis是否连通,成功返回值是pong
127.0.0.1:6379> ping
PONG

# auth 密码认证
127.0.0.1:6379> info 
NOAUTH Authentication required.
127.0.0.1:6379> auth Admin@123
OK

# save 保存
127.0.0.1:6379> save
OK

# flushall 清空所有数据
127.0.0.1:6379> KEYS *
1) "s1"
2) "l1"
3) "abc"
4) "mylist"
5) "rand01"
6) "new"
7) "conter01"
8) "dbs"
127.0.0.1:6379> save
OK
127.0.0.1:6379> FLUSHALL 
OK
127.0.0.1:6379> keys *
(empty list or set)

# info 获取系统的信息
127.0.0.1:6379> info 
# Server
redis_version:3.2.12
redis_git_sha1:00000000
redis_git_dirty:0
redis_build_id:7897e7d0e13773f
redis_mode:standalone

# echo 打印回显
127.0.0.1:6379> echo fcarey
"fcarey"

# select 切换redis的库,总共有16个,0-15
127.0.0.1:6379[10]> select 0
OK

# EXISTS 判断key 是否存在,存在是1,不存在是0
127.0.0.1:6379> EXISTS fcarey
(integer) 0

# EXPIRE 给指定的key设置存活时间s秒,当key过期以后,就自动删除
127.0.0.1:6379> EXPIRE fcarey 3
(integer) 1

# pexpire 给一个key 设置过期时间,单位毫秒
127.0.0.1:6379[1]> keys *
1) "abc"
127.0.0.1:6379[1]> PEXPIRE abc 1
(integer) 1
127.0.0.1:6379[1]> keys *
(empty list or set)

# TTL 查看key的存活时间s秒,-2:key不存在; -1:永久生效
127.0.0.1:6379> TTL fcarey 
(integer) -2

# PTTL 查看key的存活时间毫秒,-2:key不存在; -1:永久生效
127.0.0.1:6379> PTTL aaa
(integer) -1

# KEYS 查找所有符合 pattern 的 key,支持通配符
127.0.0.1:6379> KEYS *
1) "abc"
2) "counter:__rand_int__"
3) "aaa"

# move 移动当前的key到指定的db里面,成功返回1,失败返回0
127.0.0.1:6379> MOVE abc 1
(integer) 1
127.0.0.1:6379> SELECT 1
OK
127.0.0.1:6379[1]> keys *
1) "abc"

# randromkey 随机获取一个key,但是不删除,如果数据库为空,则返回空
127.0.0.1:6379> RANDOMKEY 
"counter:__rand_int__"
127.0.0.1:6379> RANDOMKEY 
"mylist"

# RENAME 重命名key,如果源key不存在,则报错;如果目标key存在,则覆盖
127.0.0.1:6379> keys *
1) "aaa"
2) "key:__rand_int__"
127.0.0.1:6379> RENAME "key:__rand_int__" rand01
OK
127.0.0.1:6379> keys *
1) "aaa"
2) "rand01"

# RENAMENX 重命名key,如果源key不存在,则报错;如果目标key存在,则不变
127.0.0.1:6379> KEYS *
1) "aaa"
127.0.0.1:6379> RENAMENX aaa new
(integer) 1
127.0.0.1:6379> KEYS *
1) "new"

# type 查看key所存储的数据类型,如果没有这个key,则返回none
127.0.0.1:6379> type new
hash

3.3.2 string 相关命令

# set 设置key value。如果key存在,则覆盖,不存在,则新建
- ex second 设置key的存活时间,单位是秒
- px 毫秒 设置key的存活时间,单位是毫秒
- nx 如果键不存在,则新建,如果存在,则返回nil
- xx 只有键存在,才能操作

127.0.0.1:6379> type new
hash
127.0.0.1:6379> set new 111 xx
OK
127.0.0.1:6379> keys *
1) "new"
127.0.0.1:6379> type new
string

# get 获取key对应的value,只能获取一个。如果key存在,则返回值,如果key不存在,则返回nil
127.0.0.1:6379> get new
"111"

# mset 批量创建key vlaue对应关系,会覆盖已存在的key
127.0.0.1:6379> mset new 321 abc 123
OK
127.0.0.1:6379> keys *
1) "abc"
2) "new"
127.0.0.1:6379> get abc
"123"
127.0.0.1:6379> get new 
"321"

# MGET 批量获取key,如果不存在,则返回nil
127.0.0.1:6379> MGET abc aaa
1) "123"
2) (nil)

# getset 给指定的key设置新value,并返回原来的value,如果key不存在,则返回nil
127.0.0.1:6379> GETSET abc 12321
"123"
127.0.0.1:6379> get abc
"12321"

# STRLEN 返回value的长度
127.0.0.1:6379> STRLEN abc
(integer) 5

# APPEND 如果key存在,则追加,如果key不存在,则新建
127.0.0.1:6379> APPEND abc 2
(integer) 6
127.0.0.1:6379> get abc
"123212"

# INCR 将key中存在的数加1,只能对数字有效
127.0.0.1:6379> INCR abc
(integer) 123213

# DECR 将key中存在的数值减1,只能对数字有效
127.0.0.1:6379> DECR abc
(integer) 123212

# INCRBY 将key中存在的数值增加指定有值,只对数字有效
127.0.0.1:6379> INCRBY abc 3
(integer) 123215

# DECRBY 将key中存在的数值减少指定的值,只能对数字有效
127.0.0.1:6379> DECRBY abc 5
(integer) 123210

# GETRANGE 字符串切换
127.0.0.1:6379> GETRANGE abc 0 -1
"123210"

# INCRBYFLOAT 将key中存在的数值增加指定的浮点数,默认保留17位
127.0.0.1:6379> INCRBYFLOAT abc 0.009
"123210.00900000000000034"

3.3.3 list

# LPUSH 将一个或者多个value插入到列表的头部
127.0.0.1:6379> LPUSH l1 123 321
(integer) 3

# LRANGE 查看列表指定的元素,全部显示是0,-1
127.0.0.1:6379> LRANGE l1 0 -1
1) "321"
2) "123"
3) "abc"

# LPOP 移除并返回列表key的第一个元素
127.0.0.1:6379> LPOP l1
"321"

# rpush 将一个或者多个value插入到列表的尾部(最后边)
127.0.0.1:6379> RPUSH l1 efg hij
(integer) 4
127.0.0.1:6379> LRANGE l1 0 -1
1) "123"
2) "abc"
3) "efg"
4) "hij"

# RPOP 删除尾部的值
127.0.0.1:6379> RPOP l1
"hij"

# rpushx 将value插入到列表的尾部,列表必须存在才可以
127.0.0.1:6379> rpushx l1 efg
(integer) 4
127.0.0.1:6379> LRANGE l1 0 -1
1) "123"
2) "abc"
3) "efg"
4) "efg"

# LPUSHX 将value插入到key的头部,key必须存在才可以
127.0.0.1:6379> LPUSHX l1 321
(integer) 5

# LINDEX 从列表头开始,获取下标为index的value
127.0.0.1:6379> LINDEX l1 1
"123"

# LINSERT 将value插入到key指定的元素前或者后;如果value不存在,则不操作
127.0.0.1:6379> LRANGE l1 0 -1
1) "321"
2) "123"
3) "abc"
4) "efg"
5) "efg"
127.0.0.1:6379> LINSERT l1 before efg hij
(integer) 6
127.0.0.1:6379> LRANGE l1 0 -1
1) "321"
2) "123"
3) "abc"
4) "hij"
5) "efg"
6) "efg"

# 获取列表长度
127.0.0.1:6379> LLEN l1
(integer) 6

# LREM 删除列表中的value
- count > 0 从表头往表尾的方向查找,删除指定的个数
- count = 0 全部删除
- count < 0 从表尾的位置往表头的方向查找,删除指定的个数
127.0.0.1:6379> LREM l1 -1 efg
(integer) 1

# LSET 替换指定的索引位置的value,如果索引超出范围,则报错。从0开始
127.0.0.1:6379> LRANGE l1 0 -1 
1) "321"
2) "abc"
3) "hij"
4) "efg"
127.0.0.1:6379> LSET l1 3 jih
OK
127.0.0.1:6379> LRANGE l1 0 -1 
1) "321"
2) "abc"
3) "hij"
4) "jih"
127.0.0.1:6379> 

# LTRIM 对列表切片
127.0.0.1:6379> LRANGE l1 0 -1 
1) "321"
2) "abc"
3) "hij"
4) "jih"
127.0.0.1:6379> LTRIM l1 1 3
OK
127.0.0.1:6379> LRANGE l1 0 -1 
1) "abc"
2) "hij"
3) "jih"

3.3.4 hash

# HSET 给hash增加key value值
127.0.0.1:6379> HSET dbs redis redis.conf
(integer) 1
127.0.0.1:6379> hset dbs mysql my.cnf
(integer) 1
127.0.0.1:6379> hset dbs ssh sshd.conf
(integer) 1

# HLEN 获取hash的长度
127.0.0.1:6379> HLEN dbs
(integer) 3

# hget 获取hash里面key的value
127.0.0.1:6379> HGET dbs ssh
"sshd.conf"

# 获取所有的键值对
127.0.0.1:6379> HGETALL dbs
1) "redis"
2) "redis.conf"
3) "mysql"
4) "my.cnf"
5) "ssh"
6) "sshd.conf"

# HMSET 批量增加键值对
127.0.0.1:6379> HMSET dbs nginx nginx.conf apache httpd.conf
OK

# HMGET 批量获取键值对
127.0.0.1:6379> HMGET dbs nginx apache
1) "nginx.conf"
2) "httpd.conf"


# HSETNX 给指定的hash增加键值对,如果原来的field存在,则操作无效。如果不存在,则新增
127.0.0.1:6379> HSETNX dbs redis fault
(integer) 0
127.0.0.1:6379> HGET dbs redis
"redis.conf"

# HKEYS 获取hash表中所有的field
127.0.0.1:6379> HKEYS dbs
1) "redis"
2) "mysql"
3) "ssh"
4) "nginx"
5) "apache"

# HVALS 获取hash表中所有的value
127.0.0.1:6379> HVALS dbs
1) "redis.conf"
2) "my.cnf"
3) "sshd.conf"
4) "nginx.conf"
5) "httpd.conf"

# HDEL 删除hash表中的一个或者多个field
127.0.0.1:6379> HDEL dbs nginx apache
(integer) 2

# HEXISTS 判断hash表中的field是否存在,如果存在为1;不存在则为0
127.0.0.1:6379> HEXISTS dbs nginx
(integer) 0

# HINCRBY 给hash表中的field增加指定的数值,只限于数字
127.0.0.1:6379> HSET dbs int 1
(integer) 1
127.0.0.1:6379> HINCRBY dbs int 4
(integer) 5
127.0.0.1:6379> HGET dbs int
"5"

# hincrbyfloat 给hash表中的field增加指定的浮点,只限于数字
127.0.0.1:6379> HINCRBYFLOAT dbs int 0.05
"5.05"

3.3.5 set

# SADD 给集合添加值,如果值存在,则什么都不操作,如果值不存在,则添加
127.0.0.1:6379> SADD s1 user01 user02 user02 user03
(integer) 3

# SMEMBERS 获取集合所有的成员
127.0.0.1:6379> SMEMBERS s1
1) "user03"
2) "user02"
3) "user01"

# SCARD 获取集合的个数
127.0.0.1:6379> SCARD s1
(integer) 3

# 获取两个集合的差集,只输出前面集合中的差集,不显示后面集合的差集
127.0.0.1:6379> SADD s2 user03 user04 
(integer) 2
127.0.0.1:6379> SDIFF s1 s2 
1) "user02"
2) "user01"

# SINTER 获取两个集合的差集,前面存在,但是后面不存在的
127.0.0.1:6379> SINTER s1 s2
1) "user03"

# SUNION 获取两个集合的并集
127.0.0.1:6379> SUNION s1 s2 
1) "user04"
2) "user03"
3) "user02"
4) "user01"

# SISMEMBER 判断元素是否在集合中,如果存在为1,不存在则为0
127.0.0.1:6379> SISMEMBER s1 user05
(integer) 0

#  SMOVE将指定的元素从一个集合移动到另外一个集合中。
# 如果源集合存在,则移动;
# 如果不存在,则忽略;
# 如果目标集合存在,直接移动;
# 如果目标集合不存在,则新建集合并移动 
127.0.0.1:6379> SMOVE s1 s2 user01
(integer) 1
127.0.0.1:6379> SMEMBERS s2 
1) "user04"
2) "user03"
3) "user01"

# spop随机删除集合指定个数的元素,并把删除的元素打印出来
127.0.0.1:6379> spop s2 2 
1) "user03"
2) "user01"
127.0.0.1:6379> SMEMBERS s2 
1) "user04"

# SRANDMEMBER 随机获取指定个数的元素,默认随机获取一个
- count > 0,
  - count大于集合的总数的话,则全部取出
  - count小于集合总数的话,则随机取出count个
- count<0,则随机count的绝对值次取出值
127.0.0.1:6379> SMOVE s2 s1 user04
(integer) 1
127.0.0.1:6379> SRANDMEMBER s1 2
1) "user03"
2) "user04"

# SREM 删除指定的一个或者多个元素
127.0.0.1:6379> SREM s1 user03
(integer) 1
127.0.0.1:6379> SMEMBERS s1
1) "user04"
2) "user02"

3.3.6 SUBSCRIBE

# SUBSCRIBE 订阅一个或者多个频道
127.0.0.1:6379> SUBSCRIBE c1 c2
Reading messages... (press Ctrl-C to quit)
1) "subscribe"
2) "c1"
3) (integer) 1
1) "subscribe"
2) "c2"
3) (integer) 2

# PUBLISH 给指定的频道发送消息
127.0.0.1:6379> PUBLISH c1 "hello, it's user01!"
(integer) 1
127.0.0.1:6379> SUBSCRIBE c1 c2
Reading messages... (press Ctrl-C to quit)
...
1) "message"
2) "c1"
3) "hello, it's user01!"

# PUBSUB channels 查看当前活跃的频道
127.0.0.1:6379> PUBSUB channels
1) "c2"
2) "c1"

# PUBSUB numsub 查看当前频道的订阅人数
127.0.0.1:6379> PUBSUB numsub c1
1) "c1"
2) (integer) 1

3.3.7 zset

# 在有序集合中添加成员
127.0.0.1:6379> ZADD users 1 admin 2 root
(integer) 2

#查询指定区间上的元素
127.0.0.1:6379> ZRANGE users 0 3
1) "admin"
2) "root"
3) "guanli"
4) "sa"

# 降序查看指定区间上的元素
127.0.0.1:6379> ZREVRANGE users 0 2
1) "sa"
2) "guanli"
3) "root"

#查看指定元素的分值
127.0.0.1:6379> ZSCORE users admin
"1"

#查看所有元素和分值
127.0.0.1:6379> ZRANGE users 0 4 withscores
1) "admin"
2) "1"
3) "root"
4) "2"
5) "guanli"
6) "3"
7) "sa"
8) "4"

#统计指定值范围内的元素个数1<=score<=2
127.0.0.1:6379> ZCOUNT users 1 2
(integer) 2

#表示1<score<=2
127.0.0.1:6379> ZCOUNT users (1 2
(integer) 1

#返回指定值范围内的score和成员,限制条件是跳过1个元素,返回2个元素。
127.0.0.1:6379> ZRANGEBYSCORE users 1 3 withscores limit 1 2
1) "root"
2) "2"
3) "guanli"
4) "3"

#查看有序集合在指定字典区间内的成员的数
#其中 - 表示最小值,而 + 则表示最大值
127.0.0.1:6379> ZLEXCOUNT users - +
(integer) 4

4 redis 配置文件解析

[root@ac ~]# egrep -v "^#|^$" /etc/redis.conf 
# 监听的地址
bind 127.0.0.1
protected-mode yes
# 监听端口
port 6379
tcp-backlog 511
timeout 0
tcp-keepalive 300
# 是否以守护进程开启redis
daemonize no
supervised no
pidfile /var/run/redis_6379.pid
loglevel notice
logfile /var/log/redis/redis.log
databases 16
# 若在900秒以内有1次更新,就会持久化
save 900 1
save 300 10
save 60 10000
stop-writes-on-bgsave-error yes
rdbcompression yes
rdbchecksum yes
# 数据的保存文件
dbfilename dump.rdb
dir /var/lib/redis
slave-serve-stale-data yes
slave-read-only yes
repl-diskless-sync no
repl-diskless-sync-delay 5
repl-disable-tcp-nodelay no
slave-priority 100
appendonly no
appendfilename "appendonly.aof"
appendfsync everysec
no-appendfsync-on-rewrite no
auto-aof-rewrite-percentage 100
auto-aof-rewrite-min-size 64mb
aof-load-truncated yes
lua-time-limit 5000
slowlog-log-slower-than 10000
slowlog-max-len 128
latency-monitor-threshold 0
notify-keyspace-events ""
hash-max-ziplist-entries 512
hash-max-ziplist-value 64
list-max-ziplist-size -2
list-compress-depth 0
set-max-intset-entries 512
zset-max-ziplist-entries 128
zset-max-ziplist-value 64
hll-sparse-max-bytes 3000
activerehashing yes
client-output-buffer-limit normal 0 0 0
client-output-buffer-limit slave 256mb 64mb 60
client-output-buffer-limit pubsub 32mb 8mb 60
hz 10
aof-rewrite-incremental-fsync yes
# 设置redis密码
# requirepass foobared
  • 默认安装没有启用密码,应急响应碰到的redis相关安全问题,几乎都跟这有关系。

5 redis 主从复制

  • 此处简单配置,详细请参考:Redis主从复制 - 百里浅暮 - 博客园 (cnblogs.com)
  • 主从复制简单步骤
    1. 从节点服务器内部维护了两个字段,即masterhost和masterport字段,用于存储主节点的ip和port信息。
    2. slave内部有个定时任务,每1s检查是否有新的master要连接和复制,若发现,就跟master建立socket网络连接。
    3. 口令认证 - 若master设置了requirepass,那么salve必须同时发送masterauth的口令认证
    4. master 第一次执行全量复制,将所有数据发给slave 。(run id不同就做全量复制)
    5. master后续持续将写命令,异步复制给slave。
  • 全量复制过程
    • 主节点收到全量复制的命令后,执行bgsave,在后台生成RDB文件,并使用一个缓冲区(称为复制缓冲区)记录从现在开始执行的所有写命令。
    • 主节点的bgsave执行完成后,将RDB文件发送给从节点;从节点首先清除自己的旧数据,然后载入接收的RDB文件,将数据库状态更新至主节点执行bgsave时的数据库状态。
    • 主节点将前述复制缓冲区中的所有写命令发送给从节点,从节点执行这些写命令,将数据库状态更新至主节点的最新状态。
    • 如果从节点开启了AOF,则会触发bgrewriteaof的执行,从而保证AOF文件更新至主节点的最新状态。
  • 服务器运行ID(runid)
    • 每个Redis节点(无论主从),在启动时都会自动生成一个随机ID(每次启动都不一样),由40个随机的十六进制字符组成;runid用来唯一识别一个Redis节点。通过info Server命令,可以查看节点的runid:
    • 主从节点初次复制时,主节点将自己的runid发送给从节点,从节点将这个runid保存起来;当断线重连时,从节点会将这个runid发送给主节点;主节点根据runid判断能否进行全量复制:
    • 如果从节点保存的runid与主节点现在的runid不同,说明从节点在断线前同步的Redis节点并不是当前的主节点,进行全量复制。
  • 一个主可以多个从,从服务器也可以配置从的从服务器
  • 复制功能不会阻塞主服务器与从服务器

5.1 命令行下配置主从复制

在从redis上配置:
127.0.0.1:6379> SLAVEOF 10.1.1.8 6379
OK
# 命令行模式下配置
127.0.0.1:6379> CONFIG SET masterauth Admin@123
OK

5.2 配置文件下配置主从复制

从redis配置:
# slaveof <masterip> <masterport>
slaveof 10.1.1.8 6379

# 若主redis配置了密码
# masterauth  <master-password>
masterauth Admin@123

5.3 配置主从复制成功后的信息

# 若配置成功后,可在主redis上查看到如下信息
[root@ac ~]# tail -f /var/log/redis/redis.log 
1524:S 21 Oct 10:27:36.311 * Connecting to MASTER 10.1.1.8:6379
1524:S 21 Oct 10:27:36.312 * MASTER <-> SLAVE sync started
1524:S 21 Oct 10:27:36.312 * Non blocking connect for SYNC fired the event.
1524:S 21 Oct 10:27:36.313 * Master replied to PING, replication can continue...
1524:S 21 Oct 10:27:36.313 * Partial resynchronization not possible (no cached master)
1524:S 21 Oct 10:27:36.315 * Full resync from master: 32bea713f239143a27f7fc4cd19ed055d42414c9:1
1524:S 21 Oct 10:27:36.414 * MASTER <-> SLAVE sync: receiving 95 bytes from master
1524:S 21 Oct 10:27:36.414 * MASTER <-> SLAVE sync: Flushing old data
1524:S 21 Oct 10:27:36.415 * MASTER <-> SLAVE sync: Loading DB in memory
1524:S 21 Oct 10:27:36.415 * MASTER <-> SLAVE sync: Finished with success

# 成功master_last_io_seconds_ago
127.0.0.1:6379> info replication
# Replication
role:slave
master_host:10.1.1.8
master_port:6379
master_link_status:up
master_last_io_seconds_ago:4
master_sync_in_progress:0
slave_repl_offset:519
slave_priority:100
slave_read_only:1
connected_slaves:0
master_repl_offset:0
repl_backlog_active:0
repl_backlog_size:1048576
repl_backlog_first_byte_offset:0
repl_backlog_histlen:0
127.0.0.1:6379> 

# 若失败会出现:master_link_down_since_seconds
127.0.0.1:6379> info replication
# Replication
role:slave
master_host:10.1.1.8
master_port:6379
master_link_status:down
master_last_io_seconds_ago:-1
master_sync_in_progress:0
slave_repl_offset:1
master_link_down_since_seconds:1666318919
slave_priority:100
slave_read_only:1
connected_slaves:0
master_repl_offset:0
repl_backlog_active:0
repl_backlog_size:1048576
repl_backlog_first_byte_offset:0
repl_backlog_histlen:0

6 redis的持久化

6.1 RDB

  • RDB的优点:
    1. 最大化Redis的性能:父进程在保存RDB文件时唯一要做的就是fork出一个子进程,然后这个子进程就会处理接下来的所有保存工作,父进程无需执行任何磁盘I/O操作。
    2. RDB生成二进制文件,非常紧凑,节省内存空间;
    3. RDB 在恢复大数据集时的速度比 AOF 的恢复速度要快;
    4. 适合全量备份、全量复制的场景,经常用于灾难恢复(对数据的完整性和一致性要求相对较低的场合)
  • RDB的缺点:
    1. 服务器宕机时,可能会丢失部分数据;
    2. 每次保存RDB的时候,Redis都要fork出一个子进程,这个过程是阻塞的,如果数据集巨大,那阻塞的时间就会很长。
[root@ac ~]# egrep -v "^#|^$" /etc/redis.conf 
# 在900秒以内有1次更新,就会持久化
save 900 1
save 300 10
save 60 10000
stop-writes-on-bgsave-error yes
rdbcompression yes
rdbchecksum yes
# 数据的保存文件
dbfilename dump.rdb
# 保存目录
dir /var/lib/redis

6.2 AOF

  • AOF的优点:
    1. 持久化更好,数据更加完整,丢失数据的可能性较低;
    2. AOF日志文件可读,并且可以对AOF文件修复。
    3. aof将所有的操作都追加到一个文件中,redis-check-aof
  • AOF的缺点:
    1. AOF日志记录在长期运行中逐渐庞大,恢复起来非常耗时,需要定期对AOF日志进行瘦身处理;
    2. 恢复备份速度比较慢。AOF的速度会比RDB慢,AOF 使用的是fsync
[root@ac ~]# egrep -v "^#|^$" /etc/redis.conf 
appendonly yes
appendfilename "appendonly.aof"
appendfsync everysec

6.3 命令行持久化方式切换

127.0.0.1:6379> CONFIG SET appendonly yes
OK
127.0.0.1:6379> CONFIG SET save ""
OK

7 Python 简单操作 Redis

7.1 操作单个redis

  • 下载redis pip 库:pip install redis -i https://pypi.douban.com/simple
import redis

r = redis.StrictRedis(host="10.1.1.8",password="Admin@123",decode_responses=True)
#r=redis.Redis()# 向后兼容老版本
r.set("user01", "admin")
print(r.keys())

7.2 操作redis集群

  • 下载redis集群 pip 库:pip install redis-py-cluster -i https://pypi.douban.com/simple
import rediscluster

nodes = [{"host": "10.1.1.8", "port": 6380}, {"host": "10.1.1.8", "port": 6381}, {"host": "10.1.1.8", "port": 6382},
         {"host": "10.1.1.8", "port": 6383}, {"host": "10.1.1.8", "port": 6384}]

c = rediscluster.RedisCluster(startup_nodes=nodes, decode_responses=True)
print(c.get('name'))

8 Redis安全

Vulhub 漏洞学习之:Redis - f_carey - 博客园 (cnblogs.com)

posted @ 2022-10-22 22:57  f_carey  阅读(23)  评论(0编辑  收藏  举报