linux_11


1、简述redis特点及其应用场景

redis特点

速度快

说到Redis的速度快,大家的第一反应一定是内存读取,那是肯定的,但如果面试的时候仅仅说到这点,那还是远远不够的,至少还有以下三点要补充:

  • Redis是用C语言实现的,而众所周知,C语言是“距离”操作系统最近的的编程语言,执行速度快

  • Redis采用了单线程的架构(这点很容易遗忘,但是是Redis的最重要特性),避免了多线程的资源竞争问题

  • Redis的源码非常精简,可以说是集性能和优雅于一身的代码

基于键值对的服务器

Redis的全程是Remote Dictionary Server,是集合了五种数据结构:字符串、列表、哈希、集合、有序集合,可以说五种数据结构都是围绕于key-value的形式,而value不仅仅可以是值,还能是具体的数据结构,这给予了Redis强大的变化性和灵活能力。

丰富的功能

除了数据结构的强大,另外就是Redis所提供的丰富的功能了:

  • 提供了key过期的功能,这能运用于实现缓存

  • 提供了发布订阅的功能,可运用于消息队列,如celery

  • 支持lua脚本功能,当觉得Redis的命令实现功能不够时,就能利用lua来创建新的功能

  • 提供了简单的事务功能,不过不能支持回滚,但也能一定程度上保持事务的特性

  • 提供了pipeling功能,这样客户端可以将多条命令一次io,减少了网络的开销

简单稳定

Redis的简单表现在两方面,一方面是在3.0版本之前源代码仅3万行,后面3.0加入了集群后代码加到了5万行,而5万行的源代码对于开发人员来说,要理解掌握它也显得并不是那么难;另一方面就是Redis是单线程的结构,这使得Redis的服务端处理模型变得简单,客户端开发也显得简单。Redis虽然代码少,并且是单线程的,但是它又非常的稳定,很少会出现因为自身bug而down掉的情况。

客户端语言多

Redis目前基本可以说和MySQL的知名度一样高了,太多的运用场景,太多的支持语言,常见的比如:java的jedis,Python的redis、PHP、C、C++等等。

持久化

Redis还支持两种方式的持久化,即将数据写入磁盘的方法,RDB和AOF,两种方法各有利弊,这里就不详细介绍了。

主从复制

那数据库的主从复制、集群功能是非常重要的,可以在Redis异常挂了后不影响客户端的使用,而Redis也是支持主从复制功能。

高可用和分布式

Redis从2.8版本后提供了高可用实现的Redis Sentinel,即Redis的“哨兵机制”,可以保证Redis节点的故障发现和自动转移,这实现了Redis强大的分布式功能。

Redis的应用场景

缓存

缓存可以说是Redis最常用的功能之一了,合理的缓存不仅可以加快速度的访问速度,以及可以减少后端的压力(通常就是MySQL的压力)。可以说,一个合理的缓存可以极大地提高网站的性能。

排行榜系统

利用Redis的列表和有序集合的特点,可以制作排行榜系统,而排行榜系统目前在商城类、新闻类、博客类等等,都是比不可缺的。

计数器应用

计数器的应用基本和排行榜系统一样,都是多数网站的普遍需求,如视频网站的播放计数,电商网站的浏览数等等,但这些数量一般比较庞大,如果存到关系型数据库,对MySQL或者其他关系型数据库的挑战还是很大的,而Redis基本可以说是天然支持计数器应用。

消息队列系统

Redis支持发布订阅系统和阻塞队列的功能,可以充当一般的消息队列功能,虽然和专业的消息队列MQ比如RebbitMQ比起来还优点差距,但也基本够用了,比如celery的异步模型,Redis也是celery官方指定的2种队列的一种。

社交网络

对于社交网络来说,一般用户量是及其庞大的,此时的关系型数据库就捉襟见肘了,比如好有点赞、关注、推送等等功能,用Redis就能比较轻松地实现这些功能

 

 

 

 

2、对比redis的RDB、AOF模式的优缺点

redis虽然是一个内存级别的缓存程序,但是它可以将内存的数据按照一定的策略保存到硬盘中,从而实现数据的持久化保持。目前,redis支持两种不同方式的数据持久化保存机制,分别是RDB和AOF,这两种模式分别类似于MySQL备份中dump和二进制日志方式。

linux_11

RDB模式RDB模式工作原理

    RDB(Redis DataBase,redis数据库):基于时间的快照,默认只保留当前最新的一次快照,优点是执行速度比较快,缺点是可能会丢失上一次快照到当前快照时间点之间的数据。其工作原理如下图所示,首先redis将内存中的数据备份到二进制RDB文件中,之后如果redis处于关闭状态,则内存中的数据将不复存在,但是redis重启后,会自动加载之前备份的RDB文件,重新读取数据。

linux_11

    要想将redis内存中的数据备份到RDB文件中,我们可以使用到save指令(同步,会阻赛其它命令,不推荐使用)、bgsave指令(异步后台执行,不影响其它命令的执行)或者自动(制定规则,自动执行)的方式。例如RDB bgsave的方式,其实现快照的具体过程如下图所示:

linux_11

  RDB bgsave实现快照时,redis会从master主进程先fork一个子进程,使用写时复制机制,子进程将内存中的数据保存为一个临时RDB文件,当所有数据保存完毕之后再将上一次的RDB文件替换掉,然后关闭子进程,从而保证每一次做RDB快照所保存的数据都是完整的。

RDB模式的优缺点

RDB模式优点

    RDB模式的优点主要表现为以下几点:

    ①RDB快照保存了某个时间点的数据,可以通过脚本执行redis指令bgsave(非阻塞,后台执行)或者save(会阻塞写操作,不推荐)命令自定义时间点备份,可以保留多个备份,当出现问题可以恢复到不同时间点的版本,很适合备份,并且此文件格式也支持有不少第三方工具可以进行后续的数据分析。

    ②RDB可以最大化Redis的性能,父进程在保存RDB文件时唯一要做的就是fork出一个子进程,然后这个子进程就会处理接下来的所有保存工作,父进程无须执行任何磁盘I/O操作。

    ③RDB在大量数据,比如几个G的数据,恢复的速度比AOF的快。

RDB模式缺点

    RDB模式的缺点表现在两方面:

    ①不能实时保存数据,可能会丢失自上一次执行RDB备份到当前的内存数据。如果需要尽量避免在服务器故障时丢失数据,那么RDB并不适合。虽然Redis允许设置不同的保存点(save point)来控制保存RDB文件的频率,但RDB文件需要保存整个数据集的状态,所以它并不是一个轻松快速的操作,因此一般会超过5分钟以上才保存一次RDB文件,在这种情况下,一旦发生故障停机就可能会丢失好几分钟的数据。

    ②当数据量非常大的时候,从父进程fork子进程进行保存至RDB文件时需要一点时间,可能是毫秒或者秒,取决于磁盘IO性能。在数据集比较庞大时,fork()可能会非常耗时,造成服务器在一定时间内停止处理客户端,如果数据集非常巨大,并且CPU时间非常紧张的话,那么这种停止时间甚至可能会长达整整一秒或更久。虽然AOF重写也需要进行fork(),但无论AOF重写的执行间隔有多长,数据的持久性都不会有任何损失。

 

AOF模式AOF模式工作原理

linux_11

AOF(Append Only File):按照操作顺序依次将操作追加到指定的日志文件末尾。AOF模式和RDB模式一样使用了写时复制机制,AOF默认为每秒钟fsync一次,即将执行的命令保存到AOF文件当中,这样即使redis服务器发生故障最多只丢失1秒钟之内的数据,也可以设置不同的fsync策略always,即设置每次执行命令的时候执行fsync,fsync会在后台执行线程,所以主线程可以继续处理用户的正常请求而不受到写入AOF文件的I/O影响。同时启用RDB和AOF进行恢复时,默认AOF文件优先级高于RDB文件,即会使用AOF文件进行恢复。

    注意:AOF模式默认是关闭并且没有数据文件存在的,第一次开启AOF并重启服务生效后,会因为AOF的优先级高于RDB而导致所有数据丢失。

AOF模式的优缺点

AOF模式优点

    AOF模式的优点表现为:

    ①数据安全性相对较高,根据所使用的fsync策略(fsync是同步内存中redis所有已经修改的文件到存储设备),默认是appendfsync everysec,即每秒执行一次fsync,在这种配置下,redis仍然可以保持良好的性能,并且就算发生故障停机,也最多只会丢失一秒钟的数据( fsync会在后台线程执行,所以主线程可以继续努力地处理命令请求)。

    ②由于该机制对日志文件的写入操作采用的是append模式,因此在写入过程中不需要seek,即使出现宕机现象也不会破坏日志文件中已经存在的内容。如果本次操作只是写入了一半数据就出现了系统崩溃问题,在redis下次启动之前,可以通过redis-check-aof工具来解决数据一致性的问题。

    ③redis可以在AOF文件体积变得过大时自动地在后台对AOF进行重写,重写后的新AOF文件包含了恢复当前数据集所需的最小命令集合。整个重写操作是绝对安全的,因为redis在创建新AOF文件的过程中,append模式不断的将修改数据追加到现有的AOF文件里面,即使重写过程中发生停机,现有的 AOF文件也不会丢失。而一旦新AOF文件创建完毕,redis就会从旧AOF文件切换到新AOF文件,并开始对新AOF文件进行追加操作。

    ④AOF包含一个格式清晰、易于理解的日志文件用于记录所有的修改操作,事实上也可以通过该文件完成数据的重建。AOF文件有序地保存了对数据库执行的所有写入操作,这些写入操作以redis协议的格式保存,因此AOF文件的内容非常容易被人读懂,对文件进行分析(parse)也很轻松。

AOF模式缺点

    AOF模式的缺点表现为:

    ①即使有些操作是重复的也会全部记录,因此AOF的文件大小要大于RDB格式的文件。

    ②AOF在恢复大数据集时的速度比RDB的恢复速度要慢。

    ③根据fsync策略不同,AOF速度可能会慢于RDB。

    ④在AOF模式中,bug出现的可能性会更多。

 

RDB和AOF的选择    选择何种模式要依据实际情况来定:

    ①如果主要充当缓存功能,或者可以承受数分钟数据的丢失,通常生产环境中只开启RDB即可,这也是默认设置。

    ②如果数据需要持久保存,一点都不能丢失,可以同时开启RDB和AOF。

    ③一般不建议只开启AOF。

 

 

 

 

3、实现redis哨兵,模拟master故障场景

redis 哨兵(Sentinel)

redis 集群介绍

主从架构无法实现master和slave角色的自动切换,即当master出现redis服务异常、主机断电、磁盘损坏等问题导致master无法使用,而redis主从复制无法实现自动的故障转移(将slave 自动提升为新master),需要手动修改环境配置,才能切换到slave redis服务器,另外当单台Redis服务器性能无法满足业务写入需求的时候,也无法横向扩展Redis服务的并行写入性能

需要解决以上的两个核心问题:

master和slave角色的无缝切换,让业务无感知从而不影响业务使用可横向动态扩展Redis服务器,从而实现多台服务器并行写入以实现更高并发的目的。Redis 集群实现方式:

客户端分片:由应用决定将不同的KEY发送到不同的Redis服务器代理分片:由代理决定将不同的KEY发送到不同的Redis服务器,代理程序如:codis,twemproxy等Redis Cluster:着眼于扩展性,在单个redis内存不足时,使用Cluster进行分片存储。

哨兵 (Sentinel) 工作原理Redis Sentinal:着眼于高可用,在master宕机时会自动将slave提升为master,继续提供服务。

Sentinel 故障转移 :

(1)多个sentinel发现并确认master有问题(2)选举出一个sentinel作为领导(3)选出一个slave作为master(4)通知其余slave成为新master的slave(5)通知客户端主从变化(6)等待老的master复活成为新master的slave

Sentinel 进程是用于监控redis集群中Master主服务器工作的状态,在Master主服务器发生故障的时候,可以实现Master和Slave服务器的切换,保证系统的高可用,此功能在redis2.6+的版本已引用,Redis的哨兵模式到了2.8版本之后就稳定了下来。一般在生产环境也建议使用Redis的2.8版本的以后版本

哨兵(Sentinel) 是一个分布式系统,可以在一个架构中运行多个哨兵(sentinel) 进程,这些进程使用流言协议(gossip protocols)来接收关于Master主服务器是否下线的信息,并使用投票协议(Agreement Protocols)来决定是否执行自动故障迁移,以及选择哪个Slave作为新的Master

每个哨兵(Sentinel)进程会向其它哨兵(Sentinel)、Master、Slave定时发送消息,以确认对方是否”活”着,如果发现对方在指定配置时间(此项可配置)内未得到回应,则暂时认为对方已离线,也就是所谓的”主观认为宕机” (主观:是每个成员都具有的独自的而且可能相同也可能不同的意识),英文名称:Subjective Down,简称SDOWN

有主观宕机,对应的有客观宕机。当“哨兵群”中的多数Sentinel进程在对Master主服务器做出SDOWN的判断,并且通过 SENTINEL is-master-down-by-addr 命令互相交流之后,得出的Master Server下线判断,这种方式就是“客观宕机”(客观:是不依赖于某种意识而已经实际存在的一切事物),英文名称是:Objectively Down, 简称 ODOWN

通过一定的vote算法,从剩下的slave从服务器节点中,选一台提升为Master服务器节点,然后自动修改相关配置,并开启故障转移(failover)

Sentinel 机制可以解决master和slave角色的自动切换问题,但单个 Master 的性能瓶颈问题无法解决,类似于MySQL中的MHA功能

Redis Sentinel中的Sentinel节点个数应该为大于等于3且最好为奇数

客户端初始化时连接的是Sentinel节点集合,不再是具体的Redis节点,但Sentinel只是配置中心不是代理。

Redis Sentinel 节点与普通redis 没有区别,要实现读写分离依赖于客户端程序

redis 3.0 之前版本中,生产环境一般使用哨兵模式,3.0后推出redis cluster功能,可以支持更大规模的生产环境

sentinel中的三个定时任务:

  • 每10秒每个sentinel对master和slave执行info

    • 发现slave节点

    • 确认主从关系

  • 每2秒每个sentinel通过master节点的channel交换信息(pub/sub)

    • 通过sentinel__:hello频道交互

    • 交互对节点的“看法”和自身信息

  • 每1秒每个sentinel对其他sentinel和redis执行ping

实现redis哨兵

由于主从架构无法实现master和slave角色的自动切换,所以在发送master节点宕机时,redis主从复制无法实现自动的故障转移,即将slave 自动提升为新的master。因此,需要配置哨兵来”盯”着它们干活,一旦发现master节点宕机,会快速的将slave节点提升为新master节点。

关闭防火墙              systemctl disable –now firewalld

系统版本                  CentOS 7.9

master服务器          10.0.0.131(主机名:centos7-01)

salve服务器1           10.0.0.132(主机名:centos7-02)

salve服务器2           10.0.0.133(主机名:centos7-03)

哨兵的准备实现主从复制架构

#需要安装wget包
[root@centos7-01 ~]# yum -y install wget
#在所有节点都脚本编译安装redis 6.2.4
[root@centos7-01 ~]# ls
install_redis.sh
[root@centos7-01 ~]# cat install_redis.sh 
#!/bin/bash
VERSION=redis-6.2.4
PASSWORD=123456
INSTALL_DIR=/apps/redis

color () {
    RES_COL=60
    MOVE_TO_COL="echo -en //033[${RES_COL}G"
    SETCOLOR_SUCCESS="echo -en //033[1;32m"
    SETCOLOR_FAILURE="echo -en //033[1;31m"
    SETCOLOR_WARNING="echo -en //033[1;33m"
    SETCOLOR_NORMAL="echo -en /E[0m"
    echo -n "$1" && $MOVE_TO_COL
    echo -n "["
    if [ $2 = "success" -o $2 = "0" ] ;then
        ${SETCOLOR_SUCCESS}
        echo -n $"  OK  "    
    elif [ $2 = "failure" -o $2 = "1"  ] ;then 
        ${SETCOLOR_FAILURE}
        echo -n $"FAILED"
    else
        ${SETCOLOR_WARNING}
        echo -n $"WARNING"
    fi
    ${SETCOLOR_NORMAL}
    echo -n "]"
    echo 
}


install() {
yum  -y install gcc jemalloc-devel || { color "安装软件包失败,请检查网络配置" 1 ; exit; }

wget http://download.redis.io/releases/${VERSION}.tar.gz || { color "Redis 源码下载失败" 1 ; exit; }



tar xf ${VERSION}.tar.gz
cd ${VERSION}
make -j 4 PREFIX=${INSTALL_DIR} install && color "Redis 编译安装完成" 0 || { color "Redis 编译安装失败" 1 ;exit ; }


ln -s ${INSTALL_DIR}/bin/redis-*  /usr/bin/
mkdir -p ${INSTALL_DIR}/{etc,log,data,run}
cp redis.conf  ${INSTALL_DIR}/etc/

sed -i -e 's/bind 127.0.0.1/bind 0.0.0.0/'  -e "/# requirepass/a requirepass $PASSWORD"  -e "/^dir .*/c dir ${INSTALL_DIR}/data/"  -e "/logfile .*/c logfile ${INSTALL_DIR}/log/redis-6379.log"  -e  "/^pidfile .*/c  pidfile ${INSTALL_DIR}/run/redis_6379.pid" ${INSTALL_DIR}/etc/redis.conf


if id redis &> /dev/null ;then 
    color "Redis 用户已存在" 1 
else
    useradd -r -s /sbin/nologin redis
    color "Redis 用户创建成功" 0
fi

chown -R redis.redis ${INSTALL_DIR}

cat >> /etc/sysctl.conf <<EOF
net.core.somaxconn = 1024
vm.overcommit_memory = 1
EOF
sysctl -p 

echo 'echo never > /sys/kernel/mm/transparent_hugepage/enabled' >> /etc/rc.d/rc.local
chmod +x /etc/rc.d/rc.local
/etc/rc.d/rc.local

cat > /usr/lib/systemd/system/redis.service <<EOF
[Unit]
Description=Redis persistent key-value database
After=network.target

[Service]
ExecStart=${INSTALL_DIR}/bin/redis-server ${INSTALL_DIR}/etc/redis.conf --supervised systemd
ExecStop=/bin/kill -s QUIT /$MAINPID
#Type=notify
User=redis
Group=redis
RuntimeDirectory=redis
RuntimeDirectoryMode=0755

[Install]
WantedBy=multi-user.target

EOF
systemctl daemon-reload 
systemctl enable --now  redis &> /dev/null && color "Redis 服务启动成功,Redis信息如下:"  0 || { color "Redis 启动失败" 1 ;exit; } 
sleep 2
redis-cli -a $PASSWORD INFO Server 2> /dev/null

}

install 

#运行脚本开始安装redis
[root@centos7-01 ~]# bash install_redis.sh 
#安装完成查看端口是否启动
[root@centos7-01 ~]# ss -ntl
State       Recv-Q Send-Q                Peer Address:Port         Local Address:Port                                                                             
LISTEN      0      511                   *:6379                    *:*    
...省略...


#修改主节点配置文件如下:
[root@centos7-01 ~]# vim /apps/redis/etc/redis.conf
masterauth 123456
requirepass 123456
#修改两个从节点配置文件如下:
[root@centos7-01 ~]# vim /apps/redis/etc/redis.conf
replicaof 10.0.0.131 6379 
masterauth 123456 
#重启redis
[root@centos7-01 ~]# systemctl restart redis
#在master节点查看查看主从复制状态如下内容:
[root@centos7-01 ~]# redis-cli -a 123456 info replication
Warning: Using a password with '-a' or '-u' option on the command line interface may not be safe.
# Replication
role:master
connected_slaves:2
slave0:ip=10.0.0.133,port=6379,state=online,offset=0,lag=1
slave1:ip=10.0.0.132,port=6379,state=online,offset=0,lag=1
master_failover_state:no-failover
master_replid:5ecf0dd2e3af50946750a2f892bc84b1a4d57d0f
master_replid2:0000000000000000000000000000000000000000
master_repl_offset:0
second_repl_offset:-1
repl_backlog_active:1
repl_backlog_size:1048576
repl_backlog_first_byte_offset:1
repl_backlog_histlen:0

#查看salve服务器1从节点状态
[root@centos7-02 ~]# redis-cli -a 123456 info replication
Warning: Using a password with '-a' or '-u' option on the command line interface may not be safe.
# Replication
role:slave
master_host:10.0.0.131
master_port:6379
master_link_status:up
master_last_io_seconds_ago:1
master_sync_in_progress:0
slave_repl_offset:504
slave_priority:100
slave_read_only:1
replica_announced:1
connected_slaves:0
master_failover_state:no-failover
master_replid:5ecf0dd2e3af50946750a2f892bc84b1a4d57d0f
master_replid2:0000000000000000000000000000000000000000
master_repl_offset:504
second_repl_offset:-1
repl_backlog_active:1
repl_backlog_size:1048576
repl_backlog_first_byte_offset:1
repl_backlog_histlen:504
#查看salve服务器2从节点状态
[root@centos7-03 ~]# redis-cli -a 123456 info replication
Warning: Using a password with '-a' or '-u' option on the command line interface may not be safe.
# Replication
role:slave
master_host:10.0.0.131
master_port:6379
master_link_status:up
master_last_io_seconds_ago:8
master_sync_in_progress:0
slave_repl_offset:560
slave_priority:100
slave_read_only:1
replica_announced:1
connected_slaves:0
master_failover_state:no-failover
master_replid:5ecf0dd2e3af50946750a2f892bc84b1a4d57d0f
master_replid2:0000000000000000000000000000000000000000
master_repl_offset:560
second_repl_offset:-1
repl_backlog_active:1
repl_backlog_size:1048576
repl_backlog_first_byte_offset:1
repl_backlog_histlen:560

编辑哨兵的配置文件

Sentinel实际上是一个特殊的redis服务器,有些redis指令支持,但很多指令并不支持。默认监听在26379/tcp端口

哨兵可以不和Redis服务器部署在一起,但一般部署在一起以节约成本

所有redis节点使用相同的以下示例的配置文件

#在master服务器源码目录有sentinel.conf,复制到安装目录即可,如:/apps/redis/etc/sentinel.conf
[root@centos7-01 ~]# cd redis-6.2.4
[root@centos7-01 redis-6.2.4]# ls
00-RELEASENOTES  CONDUCT       COPYING  INSTALL   MANIFESTO  redis.conf  runtest-cluster    runtest-sentinel  src    TLS.md
BUGS             CONTRIBUTING  deps     Makefile  README.md  runtest     runtest-moduleapi  sentinel.conf     tests  utils
#拷贝sentinel到目录
[root@centos7-01 redis-6.2.4]# cp sentinel.conf /apps/redis/etc/
#编辑sentinel文件
[root@centos7-01 redis-6.2.4]# vim /apps/redis/etc/sentinel.conf
bind 0.0.0.0
port 26379
daemonize yes
pidfile /apps/redis/run/redis-sentinel.pid
logfile /apps/redis/log/sentinel_26379.log
dir /tmp

sentinel monitor mymaster 10.0.0.131 6379 2
#mymaster是集群的名称,此行指定当前mymaster集群中master服务器的地址和端口
#2为法定人数限制(quorum),即有几个sentinel认为master down了就进行故障转移,一般此值是所有sentinel节点(一般总数是>=3的奇数,如:3,5,7等)的一半以上的整数值,比如,总数是3,即3/2=1.5,取整为2,是master的ODOWN客观下线的依据

sentinel auth-pass mymaster 123456
#mymaster集群中master的密码,注意此行要在上面行的下面

sentinel down-after-milliseconds mymaster 3000
#(SDOWN)判断mymaster集群中所有节点的主观下线的时间,单位:毫秒,建议3000

sentinel parallel-syncs mymaster 1
#发生故障转移后,可以同时向新master同步数据的slave的数量,数字越小总同步时间越长,但可以减轻新master的负载压力

sentinel failover-timeout mymaster 180000
#所有slaves指向新的master所需的超时时间,单位:毫秒

sentinel deny-scripts-reconfig yes  #禁止修改脚本
#将配置文件拷贝到两台从节点上
[root@centos7-01 redis-6.2.4]# scp /apps/redis/etc/sentinel.conf 10.0.0.132:/apps/redis/etc/
[root@centos7-01 redis-6.2.4]# scp /apps/redis/etc/sentinel.conf 10.0.0.133:/apps/redis/etc/
#三个哨兵服务器的配置都如下
[root@centos7-01 redis-6.2.4]# grep -vE "^#|^$" /apps/redis/etc/sentinel.conf
bind 0.0.0.0
port 26379
daemonize yes
pidfile /apps/redis/run/redis-sentinel.pid
logfile "/apps/redis/log/sentinel_26379.log"
dir /tmp
sentinel monitor mymaster 10.0.0.131 6379 2
sentinel auth-pass mymaster 123456
sentinel down-after-milliseconds mymaster 3000
acllog-max-len 128
sentinel parallel-syncs mymaster 1
sentinel failover-timeout mymaster 180000
sentinel deny-scripts-reconfig yes
SENTINEL resolve-hostnames no
SENTINEL announce-hostnames no

#三台哨兵服务器都要启动
[root@centos7-01 redis-6.2.4]# vim /lib/systemd/system/redis-sentinel.service
[Unit]
Description=Redis Sentinel
After=network.target

[Service]
ExecStart=/apps/redis/bin/redis-sentinel /apps/redis/etc/sentinel.conf --supervised systemd

ExecStop=/bin/kill -s QUIT $MAINPID
User=redis
Group=redis
RuntimeDirectory=redis
RuntimeDirectoryMode=0755

[Install]
WantedBy=multi-user.target

#拷贝redis-sentinel.service到从服务器
[root@centos7-01 redis-6.2.4]# scp /lib/systemd/system/redis-sentinel.service 10.0.0.132:/lib/systemd/system/redis-sentinel.service
[root@centos7-01 redis-6.2.4]# scp /lib/systemd/system/redis-sentinel.service 10.0.0.133:/lib/systemd/system/redis-sentinel.service
#注意所有节点的目录权限,否则无法启动服务
[root@centos7-01 redis-6.2.4]# chown -R redis.redis /apps/redis/
[root@centos7-01 redis-6.2.4]# ll /apps/redis/etc/sentinel.conf
-rw-r--r-- 1 redis redis 13858 Jul  3 10:35 /apps/redis/etc/sentinel.conf

[root@centos7-02 redis-6.2.4]# chown -R redis.redis /apps/redis/
[root@centos7-02 redis-6.2.4]# ll /apps/redis/etc/sentinel.conf
-rw-r--r-- 1 redis redis 13858 Jul  3 10:35 /apps/redis/etc/sentinel.conf

[root@centos7-03 redis-6.2.4]# chown -R redis.redis /apps/redis/
[root@centos7-03 redis-6.2.4]# ll /apps/redis/etc/sentinel.conf
-rw-r--r-- 1 redis redis 13858 Jul  3 10:35 /apps/redis/etc/sentinel.conf
#所有节点重新加载配置文件
[root@centos7-01 ~]# systemctl daemon-reload
[root@centos7-02 ~]# systemctl daemon-reload
[root@centos7-03 ~]# systemctl daemon-reload
#如果是编译安装,在所有哨兵服务器执行下面操作启动哨兵
[root@centos7-01 redis-6.2.4]# /apps/redis/bin/redis-sentinel /apps/redis/etc/sentinel.conf
#所有节点都可以看到26379端口
[root@centos7-01 redis-6.2.4]# ss -ntl
State       Recv-Q Send-Q                       Peer Address:Port          Local Address:Port                                                                                    
LISTEN      0      511                             *:*                *:26379                               

#查看哨兵日志
[root@centos7-01 redis-6.2.4]# tail -f /apps/redis/log/sentinel_26379.log
7043:X 03 Jul 2022 10:46:05.337 # Configuration loaded
7043:X 03 Jul 2022 10:46:05.338 * Increased maximum number of open files to 10032 (it was originally set to 1024).
7043:X 03 Jul 2022 10:46:05.338 * monotonic clock: POSIX clock_gettime
7043:X 03 Jul 2022 10:46:05.339 * Running mode=sentinel, port=26379.
7043:X 03 Jul 2022 10:46:05.341 # Sentinel ID is 083f0611260042946e0766c35d1f7dbe7f991748
7043:X 03 Jul 2022 10:46:05.341 # +monitor master mymaster 10.0.0.131 6379 quorum 2
7043:X 03 Jul 2022 10:46:05.342 * +slave slave 10.0.0.133:6379 10.0.0.133 6379 @ mymaster 10.0.0.131 6379
7043:X 03 Jul 2022 10:46:05.344 * +slave slave 10.0.0.132:6379 10.0.0.132 6379 @ mymaster 10.0.0.131 6379
7043:X 03 Jul 2022 10:46:05.748 * +sentinel sentinel a99bf07a5f70522f095c742349f0bbed84516e51 10.0.0.132 26379 @ mymaster 10.0.0.131 6379
7043:X 03 Jul 2022 10:46:06.689 * +sentinel sentinel fa168d6a97026eb2216771164a3e8d5362298d7d 10.0.0.133 26379 @ mymaster 10.0.0.131 6379


slave的哨兵日志
[root@centos7-02 ~]# tail -f /apps/redis/log/sentinel_26379.log
5916:X 03 Jul 2022 10:46:01.632 # Configuration loaded
5916:X 03 Jul 2022 10:46:01.633 * Increased maximum number of open files to 10032 (it was originally set to 1024).
5916:X 03 Jul 2022 10:46:01.633 * monotonic clock: POSIX clock_gettime
5916:X 03 Jul 2022 10:46:01.634 * Running mode=sentinel, port=26379.
5916:X 03 Jul 2022 10:46:01.638 # Sentinel ID is a99bf07a5f70522f095c742349f0bbed84516e51
5916:X 03 Jul 2022 10:46:01.638 # +monitor master mymaster 10.0.0.131 6379 quorum 2
5916:X 03 Jul 2022 10:46:01.640 * +slave slave 10.0.0.133:6379 10.0.0.133 6379 @ mymaster 10.0.0.131 6379
5916:X 03 Jul 2022 10:46:01.641 * +slave slave 10.0.0.132:6379 10.0.0.132 6379 @ mymaster 10.0.0.131 6379
5916:X 03 Jul 2022 10:46:02.515 * +sentinel sentinel fa168d6a97026eb2216771164a3e8d5362298d7d 10.0.0.133 26379 @ mymaster 10.0.0.131 6379
5916:X 03 Jul 2022 10:46:07.261 * +sentinel sentinel 083f0611260042946e0766c35d1f7dbe7f991748 10.0.0.131 26379 @ mymaster 10.0.0.131 6379

#查看sentinel状态,在sentinel状态中尤其是最后一行,涉及到master IP是多少,有几个slave,有几个sentinels,必须是符合全部服务器数量

[root@centos7-01 redis-6.2.4]# redis-cli -p 26379 INFO sentinel
# Sentinel
sentinel_masters:1
sentinel_tilt:0
sentinel_running_scripts:0
sentinel_scripts_queue_length:0
sentinel_simulate_failure_flags:0
master0:name=mymaster,status=ok,address=10.0.0.131:6379,slaves=2,sentinels=3

#测试数据同步,主节点写入数据
[root@centos7-01 redis-6.2.4]# redis-cli
127.0.0.1:6379> AUTH 123456
OK
127.0.0.1:6379> set date 20220703
OK
#从节点查看数据
[root@centos7-02 ~]# redis-cli
127.0.0.1:6379> AUTH 123456
OK
127.0.0.1:6379> get date
"20220703"

[root@centos7-03 ~]# redis-cli
127.0.0.1:6379> AUTH 123456
OK
127.0.0.1:6379> get date
"20220703"


#停止主节点测试故障转移
[root@centos7-01 redis-6.2.4]# systemctl stop redis.service
#查看从节点上哨兵信息,发现已经转移到了10.0.0.132:
[root@centos7-02 ~]# redis-cli -p 26379 INFO sentinel
# Sentinel
sentinel_masters:1
sentinel_tilt:0
sentinel_running_scripts:0
sentinel_scripts_queue_length:0
sentinel_simulate_failure_flags:0
master0:name=mymaster,status=ok,address=10.0.0.132:6379,slaves=2,sentinels=3

#故障转移时sentinel的信息:
[root@centos7-02 ~]# tail -f /apps/redis/log/sentinel_26379.log
5916:X 03 Jul 2022 10:54:54.423 # +sdown master mymaster 10.0.0.131 6379
5916:X 03 Jul 2022 10:54:54.524 # +new-epoch 1
5916:X 03 Jul 2022 10:54:54.525 # +vote-for-leader 083f0611260042946e0766c35d1f7dbe7f991748 1
5916:X 03 Jul 2022 10:54:55.552 # +odown master mymaster 10.0.0.131 6379 #quorum 3/2
5916:X 03 Jul 2022 10:54:55.553 # Next failover delay: I will not start a failover before Sun Jul  3 11:00:55 2022
5916:X 03 Jul 2022 10:54:55.685 # +config-update-from sentinel 083f0611260042946e0766c35d1f7dbe7f991748 10.0.0.131 26379 @ mymaster 10.0.0.131 6379
5916:X 03 Jul 2022 10:54:55.685 # +switch-master mymaster 10.0.0.131 6379 10.0.0.132 6379
5916:X 03 Jul 2022 10:54:55.686 * +slave slave 10.0.0.133:6379 10.0.0.133 6379 @ mymaster 10.0.0.132 6379
5916:X 03 Jul 2022 10:54:55.686 * +slave slave 10.0.0.131:6379 10.0.0.131 6379 @ mymaster 10.0.0.132 6379
5916:X 03 Jul 2022 10:54:58.730 # +sdown slave 10.0.0.131:6379 10.0.0.131 6379 @ mymaster 10.0.0.132 6379

#故障转移后哨兵配置文件的sentinel monitor IP 会被修改
[root@centos7-02]# grep "monitor mymaster" /apps/redis/etc/sentinel.conf
sentinel monitor mymaster 10.0.0.132 6379 2  #自动修改此行

[root@centos7-03]# grep "monitor mymaster" /apps/redis/etc/sentinel.conf
sentinel monitor mymaster 10.0.0.132 6379 2

[root@centos7-01]# grep "monitor mymaster" /apps/redis/etc/sentinel.conf
sentinel monitor mymaster 10.0.0.132 6379 2

#查看当前 redis状态
#新的master 状态
[root@centos7-02 ~]#  redis-cli -a 123456 info replication
Warning: Using a password with '-a' or '-u' option on the command line interface may not be safe.
# Replication
role:master
connected_slaves:2
slave0:ip=10.0.0.133,port=6379,state=online,offset=286899,lag=0
slave1:ip=10.0.0.131,port=6379,state=online,offset=286764,lag=1
master_failover_state:no-failover
master_replid:43391e35ece748aa653500c971b8dca36d388161
master_replid2:5ecf0dd2e3af50946750a2f892bc84b1a4d57d0f
master_repl_offset:286899
second_repl_offset:108246
repl_backlog_active:1
repl_backlog_size:1048576
repl_backlog_first_byte_offset:1
repl_backlog_histlen:286899



#恢复故障的原master重新加入redis集群
#启动redis
[root@centos7-01 redis-6.2.4]# systemctl start redis.service
#查看状态,目前role:slave,主节点指向了10.0.0.132
[root@centos7-01 redis-6.2.4]# redis-cli -a 123456 info replication
Warning: Using a password with '-a' or '-u' option on the command line interface may not be safe.
# Replication
role:slave
master_host:10.0.0.132
master_port:6379
master_link_status:up
master_last_io_seconds_ago:0
master_sync_in_progress:0
slave_repl_offset:274800
slave_priority:100
slave_read_only:1
replica_announced:1
connected_slaves:0
master_failover_state:no-failover
master_replid:43391e35ece748aa653500c971b8dca36d388161
master_replid2:0000000000000000000000000000000000000000
master_repl_offset:274800
second_repl_offset:-1
repl_backlog_active:1
repl_backlog_size:1048576
repl_backlog_first_byte_offset:231554
repl_backlog_histlen:43247

[root@centos7-01 redis-6.2.4]# redis-cli -p 26379 INFO sentinel
# Sentinel
sentinel_masters:1
sentinel_tilt:0
sentinel_running_scripts:0
sentinel_scripts_queue_length:0
sentinel_simulate_failure_flags:0
master0:name=mymaster,status=ok,address=10.0.0.132:6379,slaves=2,sentinels=3

 

 

 

 

4、简述redis集群的实现原理

在哨兵sentinel机制中,可以解决redis高可用问题,即当master故障后可以自动将slave提升为master,从而可以保证redis服务的正常使用,但是无法解决redis单机写入的瓶颈问题,即单机redis写入性能受限于单机的内存大小、并发数量、网卡速率等因素。

早期Redis 分布式集群部署方案:

  • 客户端分区:由客户端程序决定key写分配和写入的redis node,但是需要客户端自己处理写入分配、高可用管理和故障转移等

  • 代理方案:基于三方软件实现redis proxy,客户端先连接之代理层,由代理层实现key的写入分配,对客户端来说是有比较简单,但是对于集群管节点增减相对比较麻烦,而且代理本身也是单点和性能瓶颈。

redis 3.0版本之后推出了无中心架构的redis cluster机制,在无中心的redis集群当中,其每个节点保存当前节点数据和整个集群状态,每个节点都和其他所有节点连接

Redis Cluster特点如下:

  • 所有Redis节点使用(PING机制)互联

  • 集群中某个节点的是否失效,是由整个集群中超过半数的节点监测都失效,才能算真正的失效

  • 客户端不需要proxy即可直接连接redis,应用程序中需要配置有全部的redis服务器IP

  • redis cluster把所有的redis node 平均映射到 0-16383个槽位(slot)上,读写需要到指定的redis node上进行操作,因此有多少个redis node相当于redis 并发扩展了多少倍,每个redis node 承担16384/N个槽位

  • Redis cluster预先分配16384个(slot)槽位,当需要在redis集群中写入一个key -value的时候,会使用CRC16(key) mod 16384之后的值,决定将key写入值哪一个槽位从而决定写入哪一个Redis节点上,从而有效解决单机瓶颈。

 

 

 

5、基于redis5的redis cluster部署

关闭防火墙                      systemctl disable –now firewalld

系统版本                          CentOS 7.9

redis服务器1                   10.0.0.131(主机名:node1)

redis服务器2                   10.0.0.132(主机名:node2)

redis服务器3                   10.0.0.133(主机名:node3)

redis服务器4                   10.0.0.134(主机名:node4)

redis服务器5                   10.0.0.135(主机名:node5)

redis服务器6                   10.0.0.136(主机名:node6)

 

部署redis

#安装需要wget包
[root@node1 ~]# yum -y install wget
#在所有节点都脚本编译安装redis-5.0.3
[root@node1 ~]# ls
install_redis.sh
[root@node1 ~]# cat install_redis.sh 
#!/bin/bash
VERSION=redis-5.0.3
PASSWORD=123456
INSTALL_DIR=/apps/redis

color () {
    RES_COL=60
    MOVE_TO_COL="echo -en //033[${RES_COL}G"
    SETCOLOR_SUCCESS="echo -en //033[1;32m"
    SETCOLOR_FAILURE="echo -en //033[1;31m"
    SETCOLOR_WARNING="echo -en //033[1;33m"
    SETCOLOR_NORMAL="echo -en /E[0m"
    echo -n "$1" && $MOVE_TO_COL
    echo -n "["
    if [ $2 = "success" -o $2 = "0" ] ;then
        ${SETCOLOR_SUCCESS}
        echo -n $"  OK  "    
    elif [ $2 = "failure" -o $2 = "1"  ] ;then 
        ${SETCOLOR_FAILURE}
        echo -n $"FAILED"
    else
        ${SETCOLOR_WARNING}
        echo -n $"WARNING"
    fi
    ${SETCOLOR_NORMAL}
    echo -n "]"
    echo 
}


install() {
yum  -y install gcc jemalloc-devel || { color "安装软件包失败,请检查网络配置" 1 ; exit; }

wget http://download.redis.io/releases/${VERSION}.tar.gz || { color "Redis 源码下载失败" 1 ; exit; }



tar xf ${VERSION}.tar.gz
cd ${VERSION}
make -j 4 PREFIX=${INSTALL_DIR} install && color "Redis 编译安装完成" 0 || { color "Redis 编译安装失败" 1 ;exit ; }


ln -s ${INSTALL_DIR}/bin/redis-*  /usr/bin/
mkdir -p ${INSTALL_DIR}/{etc,log,data,run}
cp redis.conf  ${INSTALL_DIR}/etc/

sed -i -e 's/bind 127.0.0.1/bind 0.0.0.0/'  -e "/# requirepass/a requirepass $PASSWORD"  -e "/^dir .*/c dir ${INSTALL_DIR}/data/"  -e "/logfile .*/c logfile ${INSTALL_DIR}/log/redis-6379.log"  -e  "/^pidfile .*/c  pidfile ${INSTALL_DIR}/run/redis_6379.pid" ${INSTALL_DIR}/etc/redis.conf


if id redis &> /dev/null ;then 
    color "Redis 用户已存在" 1 
else
    useradd -r -s /sbin/nologin redis
    color "Redis 用户创建成功" 0
fi

chown -R redis.redis ${INSTALL_DIR}

cat >> /etc/sysctl.conf <<EOF
net.core.somaxconn = 1024
vm.overcommit_memory = 1
EOF
sysctl -p 

echo 'echo never > /sys/kernel/mm/transparent_hugepage/enabled' >> /etc/rc.d/rc.local
chmod +x /etc/rc.d/rc.local
/etc/rc.d/rc.local

cat > /usr/lib/systemd/system/redis.service <<EOF
[Unit]
Description=Redis persistent key-value database
After=network.target

[Service]
ExecStart=${INSTALL_DIR}/bin/redis-server ${INSTALL_DIR}/etc/redis.conf --supervised systemd
ExecStop=/bin/kill -s QUIT /$MAINPID
#Type=notify
User=redis
Group=redis
RuntimeDirectory=redis
RuntimeDirectoryMode=0755

[Install]
WantedBy=multi-user.target

EOF
systemctl daemon-reload 
systemctl enable --now  redis &> /dev/null && color "Redis 服务启动成功,Redis信息如下:"  0 || { color "Redis 启动失败" 1 ;exit; } 
sleep 2
redis-cli -a $PASSWORD INFO Server 2> /dev/null

}

install 

#运行脚本开始安装redis
[root@node1 ~]# bash install_redis.sh 
#安装完成查看端口是否启动
[root@node1 ~]# ss -ntl
State       Recv-Q Send-Q                Peer Address:Port         Local Address:Port                                                                             
LISTEN      0      511                   *:6379                    *:*    
...省略...

配置redis cluster

[root@node1 ~]# redis-server --version
Redis server v=5.0.3 sha=00000000:0 malloc=jemalloc-5.1.0 bits=64 build=5fc1b390c8531b09
#每个节点修改redis配置,必须开启cluster功能的参数
#执行下面命令,批量修改
[root@node1 ~]# sed -i.bak -e '/masterauth/a masterauth 123456' -e '/# cluster-enabled yes/a cluster-enabled yes' -e '/# cluster-config-file nodes-6379.conf/a cluster-config-file nodes-6379.conf' -e '/cluster-require-full-coverage yes/ccluster-require-full-coverage no' /apps/redis/etc/redis.conf

#重新加载配置文件
[root@node1 ~]# systemctl daemon-reload

#重启redis服务
[root@node1 ~]# systemctl restart redis.service
[root@node1 ~]# ss -ntl
State       Recv-Q Send-Q                  Peer Address:Port                  Local Address:Port       
LISTEN      0      511                        *:*                              *:16379            
#注意进程有[cluster]状态
[root@node1 ~]# ps aux|grep redis
redis      5850  0.2  0.1 153980  3  Ssl  20:17   0:00 /apps/redis/bin/redis-server 0.0.0.0:6379 [cluster]
root       5858  0.0  0.0 112808   968 pts/0    S+   20:19   0:00 grep --color=auto redis

创建集群

#命令redis-cli的选项 --cluster-replicas 1 表示每个master对应一个slave节点
[root@node1 ~]# redis-cli -a 123456 --cluster create 10.0.0.131:6379 10.0.0.132:6379 10.0.0.133:6379 10.0.0.134:6379 10.0.0.135:6379 10.0.0.136:6379 --cluster-replicas 1
Warning: Using a password with '-a' or '-u' option on the command line interface may not be safe.
>>> Performing hash slots allocation on 6 nodes...
Master[0] -> Slots 0 - 5460
Master[1] -> Slots 5461 - 10922
Master[2] -> Slots 10923 - 16383
Adding replica 10.0.0.134:6379 to 10.0.0.131:6379
Adding replica 10.0.0.135:6379 to 10.0.0.132:6379
Adding replica 10.0.0.136:6379 to 10.0.0.133:6379
M: 13466080cae98b5e86eb6a1a3444c96d4e3110ec 10.0.0.131:6379    #带M的为master
   slots:[0-5460] (5461 slots) master                          #当前master的槽位起始和结束位
M: 0bed8d397b9288b0f78dfbbd1abd93e99dddc709 10.0.0.132:6379
   slots:[5461-10922] (5462 slots) master
M: 001cee9baf30a2d16f210789e0032fd2d0c595b7 10.0.0.133:6379
   slots:[10923-16383] (5461 slots) master
S: 1e934bf301f2ffc08e6fbbdbcc7caab3b1040e8f 10.0.0.134:6379    #带S的slave
   replicates 13466080cae98b5e86eb6a1a3444c96d4e3110ec
S: 4fa633be7f5dce581040067b31af15a735144940 10.0.0.135:6379
   replicates 0bed8d397b9288b0f78dfbbd1abd93e99dddc709
S: b6e1bbd3c09a73bdb756e4b066d8215af2a0763a 10.0.0.136:6379
   replicates 001cee9baf30a2d16f210789e0032fd2d0c595b7
Can I set the above configuration? (type 'yes' to accept): yes #输入yes自动创建集群
>>> Nodes configuration updated
>>> Assign a different config epoch to each node
>>> Sending CLUSTER MEET messages to join the cluster
Waiting for the cluster to join
........
>>> Performing Cluster Check (using node 10.0.0.131:6379)
M: 13466080cae98b5e86eb6a1a3444c96d4e3110ec 10.0.0.131:6379
   slots:[0-5460] (5461 slots) master
   1 additional replica(s)
M: 001cee9baf30a2d16f210789e0032fd2d0c595b7 10.0.0.133:6379
   slots:[10923-16383] (5461 slots) master                     #已经分配的槽位
   1 additional replica(s)                                     #分配了一个slave
S: 4fa633be7f5dce581040067b31af15a735144940 10.0.0.135:6379
   slots: (0 slots) slave                                      #slave没有分配槽位
   replicates 0bed8d397b9288b0f78dfbbd1abd93e99dddc709         #对应的master的10.0.0.132的ID   
S: b6e1bbd3c09a73bdb756e4b066d8215af2a0763a 10.0.0.136:6379
   slots: (0 slots) slave
   replicates 001cee9baf30a2d16f210789e0032fd2d0c595b7         #对应的master的10.0.0.133的ID
M: 0bed8d397b9288b0f78dfbbd1abd93e99dddc709 10.0.0.132:6379
   slots:[5461-10922] (5462 slots) master
   1 additional replica(s)
S: 1e934bf301f2ffc08e6fbbdbcc7caab3b1040e8f 10.0.0.134:6379
   slots: (0 slots) slave
   replicates 13466080cae98b5e86eb6a1a3444c96d4e3110ec         #对应的master的10.0.0.131的ID
[OK] All nodes agree about slots configuration.                #所有节点槽位分配完成
>>> Check for open slots...                                    #检查打开的槽位
>>> Check slots coverage...                                    #检查插槽覆盖范围
[OK] All 16384 slots covered.                                  #所有槽位(16384个)分配完成

#观察以上结果,可以看到3组master/slave
#master:10.0.0.131---slave:10.0.0.134
#master:10.0.0.132---slave:10.0.0.135
#master:10.0.0.133---slave:10.0.0.136

查看六台服务器的主从状态

[root@node1 ~]# redis-cli -a 123456 -c INFO replication
Warning: Using a password with '-a' or '-u' option on the command line interface may not be safe.
# Replication
role:master
connected_slaves:1
slave0:ip=10.0.0.134,port=6379,state=online,offset=588,lag=1
master_replid:466d2c27ec444c6029568fc5c2061b0c42624b63
master_replid2:0000000000000000000000000000000000000000
master_repl_offset:588
second_repl_offset:-1
repl_backlog_active:1
repl_backlog_size:1048576
repl_backlog_first_byte_offset:1
repl_backlog_histlen:588

[root@node2 ~]# redis-cli -a 123456 INFO replication
Warning: Using a password with '-a' or '-u' option on the command line interface may not be safe.
# Replication
role:master
connected_slaves:1
slave0:ip=10.0.0.135,port=6379,state=online,offset=672,lag=0
master_replid:cd2d0407eb96492af69adcfee231ee1b4c3d6136
master_replid2:0000000000000000000000000000000000000000
master_repl_offset:672
second_repl_offset:-1
repl_backlog_active:1
repl_backlog_size:1048576
repl_backlog_first_byte_offset:1
repl_backlog_histlen:672

[root@node3 ~]# redis-cli -a 123456 INFO replication
Warning: Using a password with '-a' or '-u' option on the command line interface may not be safe.
# Replication
role:master
connected_slaves:1
slave0:ip=10.0.0.136,port=6379,state=online,offset=700,lag=1
master_replid:bae53e2d5fa70c1c6f3e9c209cb1a1470f180996
master_replid2:0000000000000000000000000000000000000000
master_repl_offset:700
second_repl_offset:-1
repl_backlog_active:1
repl_backlog_size:1048576
repl_backlog_first_byte_offset:1
repl_backlog_histlen:700

[root@node4 ~]# redis-cli -a 123456 INFO replication
Warning: Using a password with '-a' or '-u' option on the command line interface may not be safe.
# Replication
role:slave
master_host:10.0.0.131
master_port:6379
master_link_status:up
master_last_io_seconds_ago:3
master_sync_in_progress:0
slave_repl_offset:756
slave_priority:100
slave_read_only:1
connected_slaves:0
master_replid:466d2c27ec444c6029568fc5c2061b0c42624b63
master_replid2:0000000000000000000000000000000000000000
master_repl_offset:756
second_repl_offset:-1
repl_backlog_active:1
repl_backlog_size:1048576
repl_backlog_first_byte_offset:1
repl_backlog_histlen:756


[root@node5 ~]# redis-cli -a 123456 INFO replication
Warning: Using a password with '-a' or '-u' option on the command line interface may not be safe.
# Replication
role:slave
master_host:10.0.0.132
master_port:6379
master_link_status:up
master_last_io_seconds_ago:9
master_sync_in_progress:0
slave_repl_offset:784
slave_priority:100
slave_read_only:1
connected_slaves:0
master_replid:cd2d0407eb96492af69adcfee231ee1b4c3d6136
master_replid2:0000000000000000000000000000000000000000
master_repl_offset:784
second_repl_offset:-1
repl_backlog_active:1
repl_backlog_size:1048576
repl_backlog_first_byte_offset:1
repl_backlog_histlen:784


[root@node6 ~]# redis-cli -a 123456 INFO replication
Warning: Using a password with '-a' or '-u' option on the command line interface may not be safe.
# Replication
role:slave
master_host:10.0.0.133
master_port:6379
master_link_status:up
master_last_io_seconds_ago:5
master_sync_in_progress:0
slave_repl_offset:812
slave_priority:100
slave_read_only:1
connected_slaves:0
master_replid:bae53e2d5fa70c1c6f3e9c209cb1a1470f180996
master_replid2:0000000000000000000000000000000000000000
master_repl_offset:812
second_repl_offset:-1
repl_backlog_active:1
repl_backlog_size:1048576
repl_backlog_first_byte_offset:1
repl_backlog_histlen:812

#查看集群node对应关系

[root@node6 ~]# redis-cli -a 123456  cluster nodes
Warning: Using a password with '-a' or '-u' option on the command line interface may not be safe.
4fa633be7f5dce581040067b31af15a735144940 10.0.0.135:6379@16379 slave 0bed8d397b9288b0f78dfbbd1abd93e99dddc709 0 1656880556608 5 connected
1e934bf301f2ffc08e6fbbdbcc7caab3b1040e8f 10.0.0.134:6379@16379 slave 13466080cae98b5e86eb6a1a3444c96d4e3110ec 0 1656880557622 4 connected
b6e1bbd3c09a73bdb756e4b066d8215af2a0763a 10.0.0.136:6379@16379 myself,slave 001cee9baf30a2d16f210789e0032fd2d0c595b7 0 1656880555000 6 connected
001cee9baf30a2d16f210789e0032fd2d0c595b7 10.0.0.133:6379@16379 master - 0 1656880556000 3 connected 10923-16383
0bed8d397b9288b0f78dfbbd1abd93e99dddc709 10.0.0.132:6379@16379 master - 0 1656880557000 2 connected 5461-10922
13466080cae98b5e86eb6a1a3444c96d4e3110ec 10.0.0.131:6379@16379 master - 0 1656880556000 1 connected 0-5460

验证集群状态

[root@node6 ~]# redis-cli -a 123456 CLUSTER INFO
Warning: Using a password with '-a' or '-u' option on the command line interface may not be safe.
cluster_state:ok
cluster_slots_assigned:16384
cluster_slots_ok:16384
cluster_slots_pfail:0
cluster_slots_fail:0
cluster_known_nodes:6   #6个节点
cluster_size:3          #3个集群
cluster_current_epoch:6
cluster_my_epoch:3
cluster_stats_messages_ping_sent:672
cluster_stats_messages_pong_sent:646
cluster_stats_messages_meet_sent:5
cluster_stats_messages_sent:1323
cluster_stats_messages_ping_received:646
cluster_stats_messages_pong_received:677
cluster_stats_messages_received:1323
#查看任意节点的集群状态
[root@node5 ~]# redis-cli -a 123456 --cluster info 10.0.0.135:6379
Warning: Using a password with '-a' or '-u' option on the command line interface may not be safe.
10.0.0.133:6379 (001cee9b...) -> 0 keys | 5461 slots | 1 slaves.
10.0.0.132:6379 (0bed8d39...) -> 0 keys | 5462 slots | 1 slaves.
10.0.0.131:6379 (13466080...) -> 0 keys | 5461 slots | 1 slaves.
[OK] 0 keys in 3 masters.
0.00 keys per slot on average.

#查看集群状态文件
[root@node5 ~]# cat /apps/redis/data/nodes-6379.conf
4fa633be7f5dce581040067b31af15a735144940 10.0.0.135:6379@16379 myself,slave 0bed8d397b9288b0f78dfbbd1abd93e99dddc709 0 1656879927000 5 connected
001cee9baf30a2d16f210789e0032fd2d0c595b7 10.0.0.133:6379@16379 master - 0 1656879924000 3 connected 10923-16383
0bed8d397b9288b0f78dfbbd1abd93e99dddc709 10.0.0.132:6379@16379 master - 0 1656879927000 2 connected 5461-10922
13466080cae98b5e86eb6a1a3444c96d4e3110ec 10.0.0.131:6379@16379 master - 0 1656879928000 1 connected 0-5460
b6e1bbd3c09a73bdb756e4b066d8215af2a0763a 10.0.0.136:6379@16379 slave 001cee9baf30a2d16f210789e0032fd2d0c595b7 0 1656879928768 6 connected
1e934bf301f2ffc08e6fbbdbcc7caab3b1040e8f 10.0.0.134:6379@16379 slave 13466080cae98b5e86eb6a1a3444c96d4e3110ec 0 1656879925000 4 connected
vars currentEpoch 6 lastVoteEpoch 0

模拟master故障,对应的slave节点自动提升为新master

[root@node1 ~]# redis-cli -a 123456 -c INFO replication
Warning: Using a password with '-a' or '-u' option on the command line interface may not be safe.
# Replication
role:master
connected_slaves:1
slave0:ip=10.0.0.134,port=6379,state=online,offset=1120,lag=0
master_replid:466d2c27ec444c6029568fc5c2061b0c42624b63
master_replid2:0000000000000000000000000000000000000000
master_repl_offset:1120
second_repl_offset:-1
repl_backlog_active:1
repl_backlog_size:1048576
repl_backlog_first_byte_offset:1
repl_backlog_histlen:1120
#模拟node1节点出故障,需要相应的数秒故障转移时间
[root@node1 ~]# redis-cli -a 123456  shutdown
[root@node1 ~]# tail -f /apps/redis/log/redis-6379.log
5850:M 03 Jul 2022 20:25:27.576 * Background saving started by pid 5863
5863:C 03 Jul 2022 20:25:27.579 * DB saved on disk
5863:C 03 Jul 2022 20:25:27.580 * RDB: 0 MB of memory used by copy-on-write
5850:M 03 Jul 2022 20:25:27.612 * Background saving terminated with success
5850:M 03 Jul 2022 20:25:27.613 * Synchronization with replica 10.0.0.134:6379 succeeded
5850:M 03 Jul 2022 20:39:45.801 # User requested shutdown...
5850:M 03 Jul 2022 20:39:45.801 * Saving the final RDB snapshot before exiting.
5850:M 03 Jul 2022 20:39:45.801 * DB saved on disk
5850:M 03 Jul 2022 20:39:45.801 * Removing the pid file.
5850:M 03 Jul 2022 20:39:45.802 # Redis is now ready to exit, bye bye...
#查看集群node对应关系
[root@node4 ~]# redis-cli -a 123456  cluster nodes
Warning: Using a password with '-a' or '-u' option on the command line interface may not be safe.
001cee9baf30a2d16f210789e0032fd2d0c595b7 10.0.0.133:6379@16379 master - 0 1656880839163 3 connected 10923-16383
4fa633be7f5dce581040067b31af15a735144940 10.0.0.135:6379@16379 slave 0bed8d397b9288b0f78dfbbd1abd93e99dddc709 0 1656880838135 5 connected
1e934bf301f2ffc08e6fbbdbcc7caab3b1040e8f 10.0.0.134:6379@16379 myself,master - 0 1656880839000 7 connected 0-5460
13466080cae98b5e86eb6a1a3444c96d4e3110ec 10.0.0.131:6379@16379 master,fail - 1656880785519 1656880783000 1 disconnected
0bed8d397b9288b0f78dfbbd1abd93e99dddc709 10.0.0.132:6379@16379 master - 0 1656880838000 2 connected 5461-10922
b6e1bbd3c09a73bdb756e4b066d8215af2a0763a 10.0.0.136:6379@16379 slave 001cee9baf30a2d16f210789e0032fd2d0c595b7 0 1656880840185 6 connected
#10.0.0.134自动提升为新的master
[root@node4 ~]# redis-cli -a 123456 INFO replication
Warning: Using a password with '-a' or '-u' option on the command line interface may not be safe.
# Replication
role:master
connected_slaves:0
master_replid:40dc16bb51ac8230e511b1edfaa7e572ef54823e
master_replid2:466d2c27ec444c6029568fc5c2061b0c42624b63
master_repl_offset:1176
second_repl_offset:1177
repl_backlog_active:1
repl_backlog_size:1048576
repl_backlog_first_byte_offset:1
repl_backlog_histlen:1176
[root@node4 ~]# tail -f /apps/redis/log/redis-6379.log
6575:S 03 Jul 2022 20:40:00.965 * FAIL message received from 0bed8d397b9288b0f78dfbbd1abd93e99dddc709 about 13466080cae98b5e86eb6a1a3444c96d4e3110ec
6575:S 03 Jul 2022 20:40:00.987 # Start of election delayed for 538 milliseconds (rank #0, offset 1176).
6575:S 03 Jul 2022 20:40:01.292 * Connecting to MASTER 10.0.0.131:6379
6575:S 03 Jul 2022 20:40:01.293 * MASTER <-> REPLICA sync started
6575:S 03 Jul 2022 20:40:01.293 # Error condition on socket for SYNC: Connection refused
6575:S 03 Jul 2022 20:40:01.600 # Starting a failover election for epoch 7.
6575:S 03 Jul 2022 20:40:01.607 # Failover election won: I'm the new master.
6575:S 03 Jul 2022 20:40:01.607 # configEpoch set to 7 after successful failover
6575:M 03 Jul 2022 20:40:01.607 # Setting secondary replication ID to 466d2c27ec444c6029568fc5c2061b0c42624b63, valid up to offset: 1177. New replication ID is 40dc16bb51ac8230e511b1edfaa7e572ef54823e
6575:M 03 Jul 2022 20:40:01.608 * Discarding previously cached master state.
#查看集群状态文件10.0.0.131:6379@16379 master,fail
[root@node4 ~]# cat /apps/redis/data/nodes-6379.conf
001cee9baf30a2d16f210789e0032fd2d0c595b7 10.0.0.133:6379@16379 master - 0 1656880801193 3 connected 10923-16383
4fa633be7f5dce581040067b31af15a735144940 10.0.0.135:6379@16379 slave 0bed8d397b9288b0f78dfbbd1abd93e99dddc709 0 1656880800000 5 connected
1e934bf301f2ffc08e6fbbdbcc7caab3b1040e8f 10.0.0.134:6379@16379 myself,master - 0 1656880799000 7 connected 0-5460
13466080cae98b5e86eb6a1a3444c96d4e3110ec 10.0.0.131:6379@16379 master,fail - 1656880785519 1656880783000 1 disconnected
0bed8d397b9288b0f78dfbbd1abd93e99dddc709 10.0.0.132:6379@16379 master - 0 1656880800178 2 connected 5461-10922
b6e1bbd3c09a73bdb756e4b066d8215af2a0763a 10.0.0.136:6379@16379 slave 001cee9baf30a2d16f210789e0032fd2d0c595b7 0 1656880799000 6 connected
vars currentEpoch 7 lastVoteEpoch 0

恢复故障节点node1可以自动成为slave节点

[root@node1 ~]# systemctl start redis
#查看集群状态文件,可以查看node1自动成为slave节点,10.0.0.131:6379@16379 myself,slave 
[root@node1 ~]# cat /apps/redis/data/nodes-6379.conf
001cee9baf30a2d16f210789e0032fd2d0c595b7 10.0.0.133:6379@16379 master - 0 1656881054170 3 connected 10923-16383
0bed8d397b9288b0f78dfbbd1abd93e99dddc709 10.0.0.132:6379@16379 master - 0 1656881054170 2 connected 5461-10922
b6e1bbd3c09a73bdb756e4b066d8215af2a0763a 10.0.0.136:6379@16379 slave 001cee9baf30a2d16f210789e0032fd2d0c595b7 0 1656881054170 6 connected
13466080cae98b5e86eb6a1a3444c96d4e3110ec 10.0.0.131:6379@16379 myself,slave 1e934bf301f2ffc08e6fbbdbcc7caab3b1040e8f 0 1656881054166 1 connected
1e934bf301f2ffc08e6fbbdbcc7caab3b1040e8f 10.0.0.134:6379@16379 master - 0 1656881054171 7 connected 0-5460
4fa633be7f5dce581040067b31af15a735144940 10.0.0.135:6379@16379 slave 0bed8d397b9288b0f78dfbbd1abd93e99dddc709 0 1656881054171 5 connected
vars currentEpoch 7 lastVoteEpoch 0
#自动变为10.0.0.134的slave
[root@node1 ~]# redis-cli -a 123456 INFO replication
Warning: Using a password with '-a' or '-u' option on the command line interface may not be safe.
# Replication
role:slave
master_host:10.0.0.134
master_port:6379
master_link_status:up
master_last_io_seconds_ago:3
master_sync_in_progress:0
slave_repl_offset:1260
slave_priority:100
slave_read_only:1
connected_slaves:0
master_replid:40dc16bb51ac8230e511b1edfaa7e572ef54823e
master_replid2:0000000000000000000000000000000000000000
master_repl_offset:1260
second_repl_offset:-1
repl_backlog_active:1
repl_backlog_size:1048576
repl_backlog_first_byte_offset:1177
repl_backlog_histlen:84
#查看集群node对应关系
[root@node1 ~]# redis-cli -a 123456  cluster nodes
Warning: Using a password with '-a' or '-u' option on the command line interface may not be safe.
001cee9baf30a2d16f210789e0032fd2d0c595b7 10.0.0.133:6379@16379 master - 0 1656881195000 3 connected 10923-16383
0bed8d397b9288b0f78dfbbd1abd93e99dddc709 10.0.0.132:6379@16379 master - 0 1656881196832 2 connected 5461-10922
b6e1bbd3c09a73bdb756e4b066d8215af2a0763a 10.0.0.136:6379@16379 slave 001cee9baf30a2d16f210789e0032fd2d0c595b7 0 1656881197848 6 connected
13466080cae98b5e86eb6a1a3444c96d4e3110ec 10.0.0.131:6379@16379 myself,slave 1e934bf301f2ffc08e6fbbdbcc7caab3b1040e8f 0 1656881195000 1 connected
1e934bf301f2ffc08e6fbbdbcc7caab3b1040e8f 10.0.0.134:6379@16379 master - 0 1656881195816 7 connected 0-5460
4fa633be7f5dce581040067b31af15a735144940 10.0.0.135:6379@16379 slave 0bed8d397b9288b0f78dfbbd1abd93e99dddc709 0 1656881197000 5 connected

 

 

 

 

 

6、部署Zabbix监控

关闭防火墙                       systemctl disable –now firewalld

系统版本                           CentOS 7.9

Zabbix服务器                   10.0.0.131(主机名:node1)

数据库服务器                    10.0.0.132(主机名:node2)

 

数据库服务器安装MariaDB 10.5.16

#yum源配置
[root@node2 ~]# vim /etc/yum.repos.d/mariadb.repo
[mariadb]
name = MariaDB
baseurl = https://mirrors.nju.edu.cn/mariadb/yum/10.5/centos7-amd64
gpgkey=https://mirrors.nju.edu.cn/mariadb/yum/RPM-GPG-KEY-MariaDB
gpgcheck=1
#安装mysql数据库
yum -y install mariadb-server
#启动数据库
[root@node2 ~]# systemctl start  mysqld
#创建初始数据库
[root@node2 ~]# mysql
Welcome to the MariaDB monitor.  Commands end with ; or /g.
Your MariaDB connection id is 5
Server version: 10.5.16-MariaDB MariaDB Server

Copyright (c) 2000, 2018, Oracle, MariaDB Corporation Ab and others.

Type 'help;' or '/h' for help. Type '/c' to clear the current input statement.

MariaDB [(none)]>  create database zabbix character set utf8 collate utf8_bin;
Query OK, 1 row affected (0.000 sec)

MariaDB [(none)]> create user zabbix@'10.0.0.%' identified by 'zabbix';
Query OK, 0 rows affected (0.001 sec)

MariaDB [(none)]> grant all privileges on zabbix.* to zabbix@'10.0.0.%';
Query OK, 0 rows affected (0.001 sec)

MariaDB [(none)]> FLUSH PRIVILEGES;
Query OK, 0 rows affected (0.000 sec)
MariaDB [(none)]> quit
Bye
#重启数据库
[root@node2 ~]# systemctl restart mysqld.service

安装zabbix

[root@node1 ~]# rpm -Uvh https://mirrors.aliyun.com/zabbix/zabbix/5.0/rhel/7/x86_64/zabbix-release-5.0-1.el7.noarch.rpm
[root@node1 ~]# rpm -Uvh https://mirrors.aliyun.com/zabbix/zabbix/5.0/rhel/7/x86_64/zabbix-release-5.0-1.el7.noarch.rpm
Retrieving https://mirrors.aliyun.com/zabbix/zabbix/5.0/rhel/7/x86_64/zabbix-release-5.0-1.el7.noarch.rpm
warning: /var/tmp/rpm-tmp.lBeUuA: Header V4 RSA/SHA512 Signature, key ID a14fe591: NOKEY
Preparing...                          ################################# [100%]
Updating / installing...
   1:zabbix-release-5.0-1.el7         ################################# [100%]
[root@node1 ~]# sed -i 's#http://repo.zabbix.com#https://mirrors.aliyun.com/zabbix#' /etc/yum.repos.d/zabbix.repo
[root@node1 ~]# yum clean all
Loaded plugins: fastestmirror
Repository epel is listed more than once in the configuration
Cleaning repos: BaseOS epel zabbix zabbix-non-supported
Cleaning up list of fastest mirrors
Other repos take up 135 M of disk space (use --verbose for details)
#安装zabbix server和agent
[root@node1 ~]# yum install -y zabbix-server-mysql zabbix-agent
#安装Zabbix前端
[root@node1 ~]# yum install -y centos-release-scl
#如果报错No package centos-release-scl available,执行以下可解决,再重新安装centos-release-scl
[root@node1 ~]# rpm -ivh https://cbs.centos.org/kojifiles/packages/centos-release-scl-rh/2/3.el7.centos/noarch/centos-release-scl-rh-2-3.el7.centos.noarch.rpm
[root@node1 ~]# rpm -ivh https://cbs.centos.org/kojifiles/packages/centos-release-scl/2/3.el7.centos/noarch/centos-release-scl-2-3.el7.centos.noarch.rpm
#编辑配置文件 /etc/yum.repos.d/zabbix.repo
[root@node1 ~]# vim /etc/yum.repos.d/zabbix.repo
[zabbix-frontend]
enabled=1
#安装Zabbix前端软件包
[root@node1 ~]# yum install -y zabbix-web-mysql-scl zabbix-apache-conf-scl
#导入初始架构和数据
[root@node1 ~]# ll /usr/share/doc/zabbix-server-mysql*/create.sql.gz
-rw-r--r-- 1 root root 2034736 Jun 27 08:14 /usr/share/doc/zabbix-server-mysql-5.0.25/create.sql.gz
[root@node1 ~]# zcat /usr/share/doc/zabbix-server-mysql*/create.sql.gz | mysql -uzabbix -pzabbix -h 10.0.0.132 zabbix
#如果报错ERROR 1045 (28000): Access denied for user 'zabbix'@'node1' (using password: YES),需要在数据库服务器执行命令后,再重新执行导入数据
[root@node2 ~]# mysql -uroot -e"delete from user where user=' ';" #删掉空用户
[root@node2 ~]# mysql -uroot -e"flush privileges;"         #刷新权限
#在数据库服务器查看是否导入成功
[root@node2 ~]# mysql
MariaDB [(none)]> show databases;
+--------------------+
| Database           |
+--------------------+
| information_schema |
| mysql              |
| performance_schema |
| test               |
| zabbix             |
+--------------------+
MariaDB [(none)]> use zabbix;
Reading table information for completion of table and column names
You can turn off this feature to get a quicker startup with -A

Database changed
MariaDB [zabbix]> show tables;
+----------------------------+
| Tables_in_zabbix           |
+----------------------------+
| acknowledges               |
| actions                    |
| alerts                     |
| application_discovery      |
| application_prototype      |
| application_template       |
| applications               |
| auditlog                   |
| auditlog_details           |
| autoreg_host               |
| conditions                 |
.......................................

#为Zabbix server配置数据库,需要改动以下内容
[root@node1 ~]# vim /etc/zabbix/zabbix_server.conf
ListenPort=10051
DBHost=10.0.0.132
DBName=zabbix
DBUser=zabbix
DBPassword=zabbix
DBPort=3306
#为Zabbix前端配置PHP,更改时区
[root@node1 ~]# vim /etc/opt/rh/rh-php72/php-fpm.d/zabbix.conf
php_value[date.timezone] = Asia/Shanghai

#启动Zabbix server和agent进程,并设置开机自启:
[root@node1 ~]# systemctl restart zabbix-server zabbix-agent httpd rh-php72-php-fpm
[root@node1 ~]# systemctl enable zabbix-server zabbix-agent httpd rh-php72-php-fpm

配置Zabbix前端

连接到新安装的Zabbix前端:10.0.0.131/zabbix

点击【next step】

linux_11

确认状态没问题,点击【next step】

linux_11

配置数据库连接,点击【next step】

linux_11

输入Zabbix server 详细信息,点击【next step】

linux_11

确认安装信息,点击【next step】

linux_11

完成安装【finish】

linux_11

登录zabbix,用户名为Admin,密码为zabbix

linux_11

登录成功

linux_11

配置中文语言

点击左下角【User settings】,选择【Chinese(zh_CH)】,点击【Update】更新

linux_11

监控图形出现乱码的解决办法

linux_11

在windows拷贝字体在windows上找到【C:/Windows/Fonts/楷体 常规(simkai.ttf)】(或者其他个人喜欢的中文字体),然后将字体拷贝到windows系统当前用户的桌面。

上传字体上传字体到zabbix_server服务器的/usr/share/zabbix/assets/fonts/目录下。

[root@node1 ~]# cd /usr/share/zabbix/assets/fonts/
[root@node1 fonts]# ll
total 11512
lrwxrwxrwx 1 root root       33 Jul  3 22:44 graphfont.ttf -> /etc/alternatives/zabbix-web-font
-rw-r--r-- 1 root root 11787328 Jul  3 23:12 simkai.ttf
#修改权限
[root@node1 fonts]# chown zabbix.zabbix ./*
[root@node1 fonts]# ll
total 11512
lrwxrwxrwx 1 root   root         33 Jul  3 22:44 graphfont.ttf -> /etc/alternatives/zabbix-web-font
-rw-r--r-- 1 zabbix zabbix 11787328 Jul  3 23:12 simkai.ttf
#修改配置文件
[root@node1 fonts]# vim /usr/share/zabbix/include/defines.inc.php
#第81行,注释掉graphfont,加入simkai
#define('ZBX_GRAPH_FONT_NAME',      'graphfont'); // font file name
define('ZBX_GRAPH_FONT_NAME',       'simkai'); // font file name

#第122行,注释掉graphfont,加入simkai
#define('ZBX_FONT_NAME', 'graphfont');
define('ZBX_FONT_NAME', 'simkai');

验证字体是否生效

linux_11

 

 

 

 

 

7、实现Nginx、Mysql的监控

关闭防火墙 systemctl disable –now firewalld

系统版本 CentOS 7.9

Zabbix服务器 10.0.0.131(主机名:node1)

Nginx服务器 10.0.0.132(主机名:node2)

数据库服务器 10.0.0.133(主机名:node3)

 

安装nginx-1.18.0

#安装依赖包
[root@node2 ~]# yum -y install gcc pcre-devel openssl-devel zlib-devel
#创建账号
[root@node2 ~]# useradd -s /sbin/nologin nginx
#下载nginx-1.18,注意需要提前安装wget依赖包
[root@node2 ~]# wget http://nginx.org/download/nginx-1.18.0.tar.gz
#解压缩
[root@node2 ~]# ls
anaconda-ks.cfg  nginx-1.18.0.tar.gz
[root@node2 ~]# tar xf nginx-1.18.0.tar.gz
[root@node2 ~]# cd nginx-1.18.0/
[root@node2 nginx-1.18.0]# ls
auto  CHANGES  CHANGES.ru  conf  configure  contrib  html  LICENSE  man  README  src
#创建文件夹
[root@node2 nginx-1.18.0]# mkdir -p  /apps/nginx
#编译http的监控模块
[root@node2 nginx-1.18.0]# ./configure --prefix=/apps/nginx --with-http_stub_status_module --without-http_rewrite_module
[root@node2 nginx-1.18.0]# make -j 2
#安装
[root@node2 nginx-1.18.0]# make install
#修改文件夹权限
[root@node2 nginx-1.18.0]# chown -R nginx.nginx /apps/nginx/
#生成的目录
[root@node2 nginx-1.18.0]# ll /apps/nginx/
total 0
drwxr-xr-x 2 nginx nginx 333 Jun 15 06:24 conf
drwxr-xr-x 2 nginx nginx  40 Jun 15 06:24 html
drwxr-xr-x 2 nginx nginx   6 Jun 15 06:24 logs
drwxr-xr-x 2 nginx nginx  19 Jun 15 06:24 sbin
#conf:保存nginx所有的配置文件,其中nginx.conf是nginx服务器的最核心最主要的配置文件,其他的.conf则是用来配置nginx相关的功能的,例如fastcgi功能使用的是fastcgi.conf和fastcgi_params两个文件,配置文件一般都有个样板配置文件,是文件名.default结尾,使用的使用将其复制为并将default去掉即可。

#html:保存了nginx服务器的web文件,但是可以更改为其他目录保存web文件,另外还有一个50x的web文件是默认的错误页面提示页面。

#logs:用来保存nginx服务器的访问日志错误日志等日志,logs目录可以放在其他路径,比如/var/logs/nginx里面。

#sbin:保存nginx二进制启动脚本,可以接受不同的参数以实现不同的功能。

#验证版本及编译参数
[root@node2 nginx-1.18.0]# ls /apps/nginx/sbin/
nginx
#创建软连接
[root@node2 nginx-1.18.0]# ln -s /apps/nginx/sbin/nginx /usr/sbin/
#查看版本
[root@node2 nginx-1.18.0]# nginx -v
nginx version: nginx/1.18.0
#查看编译参数
nginx version: nginx/1.18.0
built by gcc 4.8.5 20150623 (Red Hat 4.8.5-44) (GCC) 
configure arguments: --prefix=/apps/nginx --with-http_stub_status_module --without-http_rewrite_module


#创建service文件
[root@node2 nginx-1.18.0]# vim /usr/lib/systemd/system/nginx.service
[Unit]
Description=nginx - high performance web server
Documentation=http://nginx.org/en/docs/
After=network-online.target remote-fs.target nss-lookup.target
Wants=network-online.target

[Service]
Type=forking
PIDFile=/apps/nginx/run/nginx.pid
ExecStart=/apps/nginx/sbin/nginx -c /apps/nginx/conf/nginx.conf
ExecReload=/bin/kill -s HUP $MAINPID
ExecStop=/bin/kill -s TERM $MAINPID
LimitNOFILE=100000

[Install]
WantedBy=multi-user.target

##创建目录存放pid
[root@node2 nginx-1.18.0]# mkdir /apps/nginx/run/
[root@node2 nginx-1.18.0]# chown -R nginx.nginx /apps/nginx/run/
#修改配置文件
[root@node2 nginx-1.18.0]# vim /apps/nginx/conf/nginx.conf
#配置文件加入pid路径
pid        /apps/nginx/run/nginx.pid;
#验证 Nginx 自启动文件
[root@node2 nginx-1.18.0]# systemctl daemon-reload
[root@node2 nginx-1.18.0]# systemctl enable --now nginx
#80端口已启动
[root@node2 nginx-1.18.0]# ss -ntl
State       Recv-Q Send-Q                                                Local Address:Port                                                               Peer Address:Port              
LISTEN      0      128                                                               *:22                                                                            *:*                  
LISTEN      0      100                                                       127.0.0.1:25                                                                            *:*                  
LISTEN      0      128                                                            [::]:80                                                                         [::]:*                  
LISTEN      0      128                                                            [::]:22                                                                         [::]:*                  
LISTEN      0      100                                                           [::1]:25                                                                         [::]:*  

#pid已自动生成
[root@node2 nginx-1.18.0]# ll /apps/nginx/run/
total 4
-rw-r--r-- 1 root root 5 Jun 15 06:38 nginx.pid
#客户端测试验证
[root@node2 nginx]# curl -I 127.0.0.1
HTTP/1.1 200 OK
Server: nginx/1.18.0
Date: Mon, 04 Jul 2022 02:03:11 GMT
Content-Type: text/html
Content-Length: 612
Last-Modified: Mon, 04 Jul 2022 01:58:54 GMT
Connection: keep-alive
ETag: "62c2495e-264"
Accept-Ranges: bytes
#修改配置文件
[root@node2 nginx]# vim /apps/nginx/conf/nginx.conf
  ##添加location
 location /nginx_status {
    stub_status on;
    allow 10.0.0.0/16;
    allow 127.0.0.1;
    deny  all;
 }
#重启服务
[root@node2 nginx]# nginx -s reload
#测试状态页
[root@node2 nginx]# curl http://127.0.0.1/nginx_status
Active connections: 1 
server accepts handled requests
 3 3 3 
Reading: 0 Writing: 1 Waiting: 0 

其中信息的含义:

  • active connections – 活跃的连接数量

  • server accepts handled requests — 总共处理了3个连接 , 成功创建3次握手,总共处理了3个请求

  • reading — 读取客户端的连接数.

  • writing — 响应数据到客户端的数量

  • waiting — 开启 keep-alive 的情况下,这个值等于 active – (reading+writing), 意思就是 Nginx 已经处理完正在等候下一次请求指令的驻留连接.

Nginx服务器安装zabbix-agent

[root@node2 ~]# rpm -Uvh https://repo.zabbix.com/zabbix/5.0/rhel/7/x86_64/zabbix-release-5.0-1.el7.noarch.rpm
Retrieving https://repo.zabbix.com/zabbix/5.0/rhel/7/x86_64/zabbix-release-5.0-1.el7.noarch.rpm
warning: /var/tmp/rpm-tmp.YgdI7f: Header V4 RSA/SHA512 Signature, key ID a14fe591: NOKEY
Preparing...                          ################################# [100%]
Updating / installing...
   1:zabbix-release-5.0-1.el7         ################################# [100%]
#修改zabbix的repo文件中的源地址
[root@node2 ~]# vim /etc/yum.repos.d/zabbix.repo
[zabbix]
name=Zabbix Official Repository - $basearch
baseurl=http://mirrors.aliyun.com/zabbix/zabbix/4.0/rhel/7/$basearch/
enabled=1
gpgcheck=1
gpgkey=file:///etc/pki/rpm-gpg/RPM-GPG-KEY-ZABBIX-A14FE591

[zabbix-non-supported]
name=Zabbix Official Repository non-supported - $basearch
baseurl=http://mirrors.aliyun.com/zabbix/non-supported/rhel/7/$basearch/
enabled=1
gpgkey=file:///etc/pki/rpm-gpg/RPM-GPG-KEY-ZABBIX
gpgcheck=1
#安装 zabbix-agent
[root@node2 ~]# yum -y install zabbix-agent
#配置agent
[root@node2 ~]# vim /etc/zabbix/zabbix_agentd.conf
Server=10.10.0.131 #指向当前zabbix server
ListenPort=10050 #监听端口
ListenIP=0.0.0.0
startAgents=5 #被动状态时默认启动的实例数(进程数),为0不监听任何端口
Hostname=10.0.0.132
#启动agent
[root@node2 ~]# systemctl start zabbix-agent
# 制作监控脚本
[root@node2 ~]# cd /etc/zabbix/zabbix_agentd.d/
[root@node2 zabbix_agentd.d]# vim nginx_status.sh
nginx_status_fun(){ #函数内容
	NGINX_PORT=$1 #端口,函数的第一个参数是脚本的第二个参数,即脚本的第二个参数是段端口号
	NGINX_COMMAND=$2 #命令,函数的第二个参数是脚本的第三个参数,即脚本的第三个参数是命令
	nginx_active(){ #获取nginx_active数量,以下相同,这是开启了nginx状态但是只能从本机看到
        /usr/bin/curl "http://127.0.0.1:"$NGINX_PORT"/nginx_status/" 2>/dev/null| grep 'Active' | awk '{print $NF}'
        }
	nginx_reading(){ #获取nginx_reading状态的数量
        /usr/bin/curl "http://127.0.0.1:"$NGINX_PORT"/nginx_status/" 2>/dev/null| grep 'Reading' | awk '{print $2}'
       }
	nginx_writing(){
        /usr/bin/curl "http://127.0.0.1:"$NGINX_PORT"/nginx_status/" 2>/dev/null| grep 'Writing' | awk '{print $4}'
       }
	nginx_waiting(){
        /usr/bin/curl "http://127.0.0.1:"$NGINX_PORT"/nginx_status/" 2>/dev/null| grep 'Waiting' | awk '{print $6}'
       }
	nginx_accepts(){
        /usr/bin/curl "http://127.0.0.1:"$NGINX_PORT"/nginx_status/" 2>/dev/null| awk NR==3 | awk '{print $1}'
       }
	nginx_handled(){
        /usr/bin/curl "http://127.0.0.1:"$NGINX_PORT"/nginx_status/" 2>/dev/null| awk NR==3 | awk '{print $2}'
       }
	nginx_requests(){
        /usr/bin/curl "http://127.0.0.1:"$NGINX_PORT"/nginx_status/" 2>/dev/null| awk NR==3 | awk '{print $3}'
       }
  	case $NGINX_COMMAND in
		active)
			nginx_active;
			;;
		reading)
			nginx_reading;
			;;
		writing)
			nginx_writing;
			;;
		waiting)
			nginx_waiting;
			;;
		accepts)
			nginx_accepts;
			;;
		handled)
			nginx_handled;
			;;
		requests)
			nginx_requests;
		esac 
}

main(){ #主函数内容
	case $1 in #分支结构,用于判断用户的输入而进行响应的操作
		nginx_status) #当输入nginx_status就调用nginx_status_fun,并传递第二和第三个参数
			nginx_status_fun $2 $3;
			;;
		*) #其他的输入打印帮助信息
			echo $"Usage: $0 {nginx_status key}"
	esac #分支结束符
}

main $1 $2 $3


#zabbix agent 添加自定义监控项
[root@node2 zabbix_agentd.d]# vim userparameter_nginx.conf
UserParameter=nginx_status[*],/etc/zabbix/zabbix_agentd.d/nginx_status.sh "$1" "$2" "$3"
#重启zabbix agent
[root@node2 zabbix_agentd.d]# systemctl restart zabbix-agent

Zabbix服务器测试监控数据

#zabbix的repo文件中的源地址
[root@node1 ~]# vim /etc/yum.repos.d/zabbix.repo
[zabbix]
name=Zabbix Official Repository - $basearch
baseurl=https://mirrors.aliyun.com/zabbix/zabbix/5.0/rhel/7/$basearch/
enabled=1
gpgcheck=1
gpgkey=file:///etc/pki/rpm-gpg/RPM-GPG-KEY-ZABBIX-A14FE591

[zabbix-frontend]
name=Zabbix Official Repository frontend - $basearch
baseurl=https://mirrors.aliyun.com/zabbix/zabbix/5.0/rhel/7/$basearch/frontend
enabled=1
gpgcheck=1
gpgkey=file:///etc/pki/rpm-gpg/RPM-GPG-KEY-ZABBIX-A14FE591

[zabbix-debuginfo]
name=Zabbix Official Repository debuginfo - $basearch
baseurl=https://mirrors.aliyun.com/zabbix/zabbix/5.0/rhel/7/$basearch/debuginfo/
enabled=0
gpgkey=file:///etc/pki/rpm-gpg/RPM-GPG-KEY-ZABBIX-A14FE591
gpgcheck=1
         
[zabbix-non-supported]
name=Zabbix Official Repository non-supported - $basearch
baseurl=https://mirrors.aliyun.com/zabbix/non-supported/rhel/7/$basearch/
enabled=1
gpgkey=file:///etc/pki/rpm-gpg/RPM-GPG-KEY-ZABBIX
gpgcheck=1


#安装zabbix-get
[root@node1 ~]# yum install install zabbix-get -y
#测试是否可以获取到数据;如果有报错,请仔细检查文件内容;这里的nginx.active是文件对应的UserParameter的内容
[root@node1 ~]# zabbix_get -s 10.0.0.132 -p 10050 -k "nginx_status["nginx_status",80,"active"]"
1

监控模板制作

创建主机

linux_11

linux_11

创建模板

linux_11

linux_11

创建监控项

linux_11

linux_11

创建触发器

linux_11

设置表达式

linux_11

linux_11

添加完成

linux_11

创建图形

linux_11

linux_11

查看图形

linux_11

 

Mysql的监控

[root@node3 ~]# rpm -Uvh https://repo.zabbix.com/zabbix/5.0/rhel/7/x86_64/zabbix-release-5.0-1.el7.noarch.rpm
Retrieving https://repo.zabbix.com/zabbix/5.0/rhel/7/x86_64/zabbix-release-5.0-1.el7.noarch.rpm
warning: /var/tmp/rpm-tmp.YgdI7f: Header V4 RSA/SHA512 Signature, key ID a14fe591: NOKEY
Preparing...                          ################################# [100%]
Updating / installing...
   1:zabbix-release-5.0-1.el7         ################################# [100%]
#修改zabbix的repo文件中的源地址
[root@node3 ~]# vim /etc/yum.repos.d/zabbix.repo
[zabbix]
name=Zabbix Official Repository - $basearch
baseurl=http://mirrors.aliyun.com/zabbix/zabbix/4.0/rhel/7/$basearch/
enabled=1
gpgcheck=1
gpgkey=file:///etc/pki/rpm-gpg/RPM-GPG-KEY-ZABBIX-A14FE591

[zabbix-non-supported]
name=Zabbix Official Repository non-supported - $basearch
baseurl=http://mirrors.aliyun.com/zabbix/non-supported/rhel/7/$basearch/
enabled=1
gpgkey=file:///etc/pki/rpm-gpg/RPM-GPG-KEY-ZABBIX
gpgcheck=1
#安装 zabbix-agent
[root@node3 ~]# yum -y install zabbix-agent
#配置agent
[root@node3 ~]# vim /etc/zabbix/zabbix_agentd.conf
Server=10.10.0.131 #指向当前zabbix server
ListenPort=10050 #监听端口
ListenIP=0.0.0.0
startAgents=5 #被动状态时默认启动的实例数(进程数),为0不监听任何端口
Hostname=10.0.0.133
#启动agent
[root@node2 ~]# systemctl start zabbix-agent
#下载安装percona
[root@node3 ~]# wget https://www.percona.com/downloads/percona-monitoring-plugins/percona-monitoring-plugins-1.1.7/binary/redhat/7/x86_64/percona-zabbix-templates-1.1.7-2.noarch.rpm
#脚本需要安装php依赖包
[root@node3 scripts]# yum install php php-mysql
#进入percona目录
[root@node3 ~]# cd /var/lib/zabbix/percona/templates
#将文件拷贝到zabbix_agentd.d目录
[root@node3 templates]# cp userparameter_percona_mysql.conf /etc/zabbix/zabbix_agentd.d/
#就改连接密码
[root@node3 scripts]# vim ss_get_mysql_stats.php 
$mysql_user = 'zabbix';
$mysql_pass = 'zabbix';
[root@node3 scripts]# systemctl restart zabbix-agent

在zabbix网页中配置主机

linux_11

linux_11

添加模板

linux_11

在图像中查看

linux_11

 

 

 

 

 

8、实现故障和恢复的邮件通知

产生zabbix邮件通知的条件为:

  • 有可用的相关报警媒介;

  • 正确设置了被调用邮箱的授权;

  • 触发的相应动作调用了该报警媒介。

这里使用QQ邮箱作为zabbix调用的邮箱,即邮件通知的发件人是设置的QQ邮箱帐户。

使用zabbix调用QQ邮箱时,需要开启POP3/SMTP服务。

登录自己的QQ邮箱(即准备作为zabbix邮件通知发件人的邮箱),设置-帐户,找到“POP3/SMTP服务”,点击开启

linux_11

点开启,并发送手机短信后点击我已发送

linux_11

获取到授权码

linux_11

(如果需要更改授权码,可以点击“生成授权码”,重新生成)

zabbix创建报警媒介

linux_11

QQ邮箱所需的信息在帮助中心常用邮件客户端软件设置中都能找到:https://service.mail.qq.com/cgi-bin/help?subtype=1&&id=28&&no=371

linux_11

为zabbix的用户添加报警媒介

创建一个用户用来接收报警信息,当触发报警时自动发送给此用户的邮箱

linux_11

linux_11

linux_11

可发送邮件测试

linux_11

linux_11

登录邮箱查看收到邮件

linux_11

实现zabbix报警的邮件通知

实现:当被监控主机的Nginx服务80端口监听故障时,通过邮件通知到xiaoming用户。最多进行3次通知,每次通知间隔60s。

创建主机监控项,监听80端口故障

linux_11

linux_11

linux_11

创建触发器

linux_11

linux_11

linux_11

创建动作

基于触发器“Nginx监听80端口异常”,当触发器告警时,则激活动作。

linux_11

linux_11

linux_11

linux_11

#主题 
#新Zabbix恢复通知: {TRIGGER.NAME}:{TRIGGER.STATUS}
#消息  
#告警商户: {TRIGGER.HOSTGROUP.NAME}
#告警主机: {HOST.NAME}
#主机 IP: {IPADDRESS}
#告警时间: {EVENT.DATE} {EVENT.TIME}
#恢复时间: {DATE} {TIME}
#告警等级: {TRIGGER.SEVERITY}
#告警信息: {TRIGGER.NAME}
#问题详情: {ITEM.NAME}:{ITEM.VALUE}
#当前状态: {TRIGGER.STATUS}:{ITEM.VALUE1}
#事件 ID: {EVENT.ID}

关闭nginx测试邮件发送

[root@node2 zabbix_agentd.d]# systemctl stop nginx

邮件已经发送

linux_11

打开邮件查看邮件

linux_11

恢复nginx服务

root@node2 zabbix_agentd.d]# systemctl start nginx

打开邮件查看邮件

linux_11

原创文章,作者:3628473679,如若转载,请注明出处:https://blog.ytso.com/tech/aiops/271615.html

(0)
上一篇 2022年7月5日 04:44
下一篇 2022年7月5日 04:54

相关推荐

发表回复

登录后才能评论