小的网站结构

说明:如果部署在云上,比如阿里云上,不需要自己部署keepalived,直接买阿里云的slb即可,slb然后分发流量到两台haproxy机器

一、先部署两个web服务器

编译安装nginx(脚本很粗糙)

[root@007-web2 ~]# cat nginx.sh 

yum install -y vim lrzsz tree screen psmisc lsof tcpdump wget ntpdate gcc gcc-c++ glibc glibc-devel pcre pcre-devel openssl openssl-devel systemd-devel net-tools iotop bc zip unzip zlib-devel bash-completion nfs-utils automake libxml2 libxml2-devel libxslt libxslt-devel perl perl-ExtUtils-Embed

wget https://mirrors.huaweicloud.com/nginx/nginx-1.17.5.tar.gz
tar xf nginx-1.17.5.tar.gz
cd nginx-1.17.5/
./configure --prefix=/apps/nginx --user=nginx --group=nginx --with-http_ssl_module --with-http_v2_module --with-http_realip_module --with-http_stub_status_module --with-http_gzip_static_module --with-pcre --with-stream --with-stream_ssl_module --with-stream_realip_module --with-debug make -j 4
make install /usr/sbin/groupadd -g 995 -r nginx 2> /dev/null
/usr/sbin/useradd -c "Nginx web server" -u 997 -g nginx -s /sbin/nologin -r -d /var/lib/nginx nginx 2> /dev/null cat > /usr/lib/systemd/system/nginx.service <<'EOF'
[Unit]
Description=The nginx HTTP and reverse proxy server
After=network.target remote-fs.target nss-lookup.target
[Service]
Type=forking
PIDFile=/run/nginx.pid
ExecStartPre=/usr/bin/rm -f /run/nginx.pid
ExecStartPre=/apps/nginx/sbin/nginx -t
ExecStart=/apps/nginx/sbin/nginx
ExecReload=/bin/kill -s HUP $MAINPID
KillSignal=SIGQUIT
TimeoutStopSec=5
KillMode=process
PrivateTmp=true
[Install]
WantedBy=multi-user.target
EOF mkdir /apps/nginx/conf.d
cat > /apps/nginx/conf/nginx.conf <<'EOF'
user nginx;
worker_processes auto;
error_log /var/log/nginx/error.log;
pid /run/nginx.pid;
events {
worker_connections 1024;
}
http {
log_format main '$remote_addr - $remote_user [$time_local] "$request" '
'$status $body_bytes_sent "$http_referer" '
'"$http_user_agent" "$http_x_forwarded_for"';
access_log /var/log/nginx/access.log main;
sendfile on;
tcp_nopush on;
tcp_nodelay on;
keepalive_timeout 65;
types_hash_max_size 2048;
include /apps/nginx/conf/mime.types;
default_type application/octet-stream;
include /apps/nginx/conf.d/*.conf;
server {
server_name _;
root /apps/nginx/html;
location / {
}
error_page 500 502 503 504 /50x.html;
location = /50x.html {
}
}
}
EOF systemctl daemon-reload && systemctl enable nginx
systemctl start nginx

编译php脚本

[root@007-web2 ~]# cat php.sh
#!/bin/bash
RED="\033[0;31m"
GREEN="\033[0;32m"
NO_COLOR="\033[0m"
PREFIX=/usr/local/php #这个还是别改了,好多地方要改
SYSCONFDIR=
SRC=/usr/src
FLAG=$1
CPUS=`cat /proc/cpuinfo| grep "physical id"| sort| uniq| wc -l`
CORE=`cat /proc/cpuinfo| grep "cpu cores"| uniq | awk '{print $4}'`
J=$((${CPUS}*${CORE}))
FILEURL='http://ftp.ntu.edu.tw/pub/php/distributions/php-7.3.10.tar.gz'
# 判断是不是root
judge_root() {
[ $(id -u) != "0" ] && { echo -e "${RED}Error:${NO_COLOR} You must be root to run this script."; exit 1; }
}
# download
download_source() {
cd
yum install wget -y
wget ${FILEURL}
if [ ! "$?" -eq 0 ];then
echo "download failed!"
exit 1
fi
}
# install
install(){
# Add the "apache" group and user,需要的话改为nginx
#/usr/sbin/groupadd -g 48 -r apache 2> /dev/null || :
#/usr/sbin/useradd -c "Apache" -u 48 -g apache \
#-s /sbin/nologin -r -d /usr/share/httpd apache 2> /dev/null || :
/usr/sbin/groupadd -g 995 -r nginx 2> /dev/null
/usr/sbin/useradd -c "Nginx web server" -u 997 -g nginx -s /sbin/nologin -r -d /var/lib/nginx nginx 2> /dev/null
# epel
wget -O /etc/yum.repos.d/epel.repo http://mirrors.aliyun.com/repo/epel-7.repo
yum install gcc openssl-devel pcre-devel libnghttp2-devel ncurses-devel lbzip2 bzip2 expat-devel libxml2-devel libxml2 autoconf libtool -y
tar xf php-7.3.10.tar.gz -C ${SRC}/
cd ${SRC}/php-7.3.10/
./configure --prefix=/usr/local/php --enable-mysqlnd --with-mysqli=mysqlnd --with-pdo-mysql=mysqlnd --with-openssl --with-freetype-dir --with-jpeg-dir --with-png-dir --with-zlib --with-config-file-path=/usr/loca/php/etc --with-config-file-scan-dir=/usr/local/php/etc/php.d --enable-mbstring --enable-xml --enable-sockets --enable-fpm --enable-maintainer-zts --disable-fileinfo
make -j ${J}
make install
# config
cd ${PREFIX}/etc/
cp php-fpm.conf.default php-fpm.conf
cd ${PREFIX}/etc/php-fpm.d
cp www.conf.default www.conf
# init file
cp ${SRC}/php-7.3.10/sapi/fpm/init.d.php-fpm /etc/init.d/php-fpm
chmod +x /etc/init.d/php-fpm
# modify config file
sed -i 's@user = nobody@user = nginx@' ${PREFIX}/etc/php-fpm.d/www.conf
sed -i 's@group = nobody@group = nginx@' ${PREFIX}/etc/php-fpm.d/www.conf
sed -i 's@listen = 127.0.0.1:9000@listen = /var/run/php-fpm.sock@' ${PREFIX}/etc/php-fpm.d/www.conf
sed -i 's@;listen.mode = 0660@listen.mode = 0666@' ${PREFIX}/etc/php-fpm.d/www.conf
#reload
systemctl daemon-reload && systemctl enable php-fpm
}
test_php(){
systemctl start php-fpm
sleep 3
if ps -ef | grep php-fpm | grep -v grep;then
echo -e "${GREEN}Maybe php installed successfully...${NO_COLOR}"
else
echo -e "${RED}Maybe php installed failed...${NO_COLOR}"
fi
}
remove_php() {
systemctl stop php-fpm
sleep 3
if ps -ef | grep php-fpm | grep -v grep;then
echo -e "${RED}Php uninstall failed...Killing php process failed...${NO_COLOR}"
exit 2
fi
rm -rf ${PREFIX} ${SRC}/php-7.3.10 /etc/init.d/php-fpm
}
judge_uninstall(){
if [ "$FLAG" = "uninstall" ];then
remove_php
exit 0
fi
}
main() {
judge_uninstall
judge_root
download_source
install
test_php
}
main

nginx配置wordpress

[root@007-web1 ~]# mkdir /var/www/wordpress -p
#下载wordpress
[root@007-web1 ~]# unzip wordpress-5.2.3-zh_CN.zip -d /var/www/
[root@007-web1 ~]# chown nginx.nginx -R /var/www/wordpress/
[root@007-web1 ~]# cat /apps/nginx/conf.d/blog.jd.com.conf
server {
listen 80;
server_name blog.jd.com; charset utf-8;
access_log /var/log/nginx/blog.jd.com-access.log main;
error_log /var/log/nginx/blog.jd.com-error.log;
root /var/www/wordpress;
location / {
root /var/www/wordpress;
index index.php index.html index.htm;
} location ~ \.php$ {
#fastcgi_pass 127.0.0.1:9000;
fastcgi_pass unix:/var/run/php-fpm.sock;
fastcgi_split_path_info ^(.+\.php)(/.+)$;
fastcgi_index index.php;
fastcgi_buffer_size 128k;
fastcgi_buffers 64 128k;
fastcgi_intercept_errors on;
fastcgi_param PATH_INFO $fastcgi_path_info;
fastcgi_param HTTP_AUTHORIZATION $http_authorization;
fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
include fastcgi_params;
fastcgi_connect_timeout 300;
fastcgi_read_timeout 300;
fastcgi_send_timeout 300;
client_max_body_size 100m;
}
location ~ /.git
{
deny all;
}
}

测试当前服务器是否正常

[root@007-web1 ~]# /apps/nginx/sbin/nginx -t
nginx: the configuration file /apps/nginx/conf/nginx.conf syntax is ok
nginx: configuration file /apps/nginx/conf/nginx.conf test is successful
[root@007-web1 ~]# systemctl restart nginx
[root@007-web1 ~]# curl -vLH 'blog.jd.com' 127.0.0.1
* About to connect() to 127.0.0.1 port 80 (#0)
* Trying 127.0.0.1...
* Connected to 127.0.0.1 (127.0.0.1) port 80 (#0)
> GET / HTTP/1.1
> User-Agent: curl/7.29.0
> Host: 127.0.0.1
> Accept: */*
>
< HTTP/1.1 302 Found
< Server: nginx/1.17.5
... 显示了中文的配置wordpress即为ok

同步代码到web2

[root@007-web1 ~]# scp -p /apps/nginx/conf.d/blog.jd.com.conf 192.168.38.136:/apps/nginx/conf.d/
[root@007-web1 ~]# ssh 192.168.38.136 'mkdir -p /var/www/wordpress/'
[root@007-web1 ~]# scp -p -r /var/www/wordpress 192.168.38.136:/var/www/
[root@007-web1 ~]# ssh 192.168.38.136 'chown nginx.nginx -R /var/www/wordpress'
[root@007-web1 ~]# ssh 192.168.38.136 'systemctl restart nginx'
#测试
[root@007-web1 ~]# curl -vLH 'blog.jd.com' 192.168.38.136

二、部署数据库主从

二进制安装脚本

[root@007-mysql-master mysql-5.7-onekey-install]# cat mysql-install.sh
#!/bin/bash
CURRENTDIR=`pwd`
NAME="mysql-5.7.28-linux-glibc2.12-x86_64.tar.gz"
FULL_NAME=${CURRENTDIR}/${NAME}
DATA_DIR="/data/mysql/" StandardOutput(){
echo -e "\033[1;32m$1 ... \033[0m"
}
ErrorOutput(){
echo -e "\033[1;31m$1 ... \033[0m"
} is_empty_dir(){
return `ls -A $1 2>/dev/null | wc -l`
} judge_mysql(){
if [ -e /usr/local/mysql ];then
ErrorOutput "/usr/local/mysql目录存在...Mysql 似乎已经安装...终止安装..."
exit 10
fi
which mysqld &>/dev/null
if [ "$?" -eq 0 ];then
ErrorOutput "mysqld命令存在...Mysql 似乎已经安装...终止安装..."
exit 20
fi
if ss -ltn | grep 3306 -q;then
ErrorOutput "3306端口被占用...Mysql 似乎已经安装...终止安装..."
exit 30
fi
is_empty_dir $DATA_DIR
if [ ! "$?" -eq 0 ];then
ErrorOutput "$DATA_DIR 不为空...终止安装..."
exit 40
fi
} download_mysql(){
if [ -f ${FULL_NAME} ];then
StandardOutput "Mysql安装文件存在,开始安装..."
else
StandardOutput "Mysql安装文件不存在...开始下载..."
curl -o ${NAME} https://mirrors.huaweicloud.com/mysql/Downloads/MySQL-5.7/${NAME}
if [ ! "$?" -eq 0 ];then
ErrorOutput "下载失败...终止安装..." && exit 50
fi
fi
}
mysql_install(){
# install dependence
yum install -y libaio-devel
if id mysql &>/dev/null;then
StandardOutput "mysql 用户已经存在,跳过创建用户过程..."
else
useradd -r -s /sbin/nologin mysql
fi
tar xf ${FULL_NAME} -C /usr/local/
ln -sv /usr/local/mysql-5* /usr/local/mysql
chown -R mysql.mysql /usr/local/mysql/
if [ ! -d $DATA_DIR ];then
mkdir -pv $DATA_DIR && chown -R mysql.mysql $DATA_DIR -R
fi
/usr/local/mysql/bin/mysqld --initialize --datadir=$DATA_DIR --user=mysql &>mysql_install.log
cp /usr/local/mysql-5.*-x86_64/support-files/mysql.server /etc/init.d/mysqld
chmod a+x /etc/init.d/mysqld
cp ${CURRENTDIR}/my.cnf /etc/my.cnf
echo 'export PATH=/usr/local/mysql/bin/:$PATH' > /etc/profile.d/mysql.sh
source /etc/profile.d/mysql.sh
# /etc/init.d/mysqld start mkdir /var/lib/mysql /var/run/mysqld
chown mysql.mysql /var/lib/mysql/ /var/run/mysqld
systemctl daemon-reload
} mysql_check(){
systemctl start mysqld
if ss -ltn | grep 3306 -q ;then
StandardOutput "VERY GOOD..."
rm -f ${CURRENTDIR}/${NAME}
fi
echo -e "请手动执行:\033[1;32msource /etc/profile\033[0m"
echo -e "当前mysql数据库密码为:\033[1;32m$( grep "temporary password" ${CURRENTDIR}/mysql_install.log | awk '{print $NF}')\033[0m"
} main(){
judge_mysql
download_mysql
mysql_install
mysql_check
}
main

数据库密码

[root@007-mysql-master mysql-5.7-onekey-install]#
当前mysql数据库密码为:fO:Qd.jsl9GU
[root@007-mysql-master mysql-5.7-onekey-install]# mysqladmin -uroot -p$(grep " temporary password" mysql_install.log | awk '{print $NF}') password 123456
[root@007-slave mysql-5.7-onekey-install]#
当前mysql数据库密码为:le*gu=x4Emoi
[root@007-slave mysql-5.7-onekey-install]# mysqladmin -uroot -p$(grep " temporary password" mysql_install.log | awk '{print $NF}') password 123456

主数据库配置:

[root@007-mysql-master mysql-5.7-onekey-install]# cat /etc/my.cnf
# For advice on how to change settings please see
# http://dev.mysql.com/doc/refman/5.7/en/server-configuration-defaults.html [mysqld]
datadir=/data/mysql
socket=/var/lib/mysql/mysql.sock
log-bin
server-id=1
expire-logs-days=15
binlog-format=row
gtid_mode=on
enforce_gtid_consistency=on
skip_name_resolve # Disabling symbolic-links is recommended to prevent assorted security risks
symbolic-links=0 log-error=/var/log/mysqld.log
pid-file=/var/run/mysqld/mysqld.pid
[client]
socket = /var/lib/mysql/mysql.sock
port = 3306
[root@007-mysql-master ~]# systemctl restart mysqld && systemctl enable mysqld
mysqld.service is not a native service, redirecting to /sbin/chkconfig.
Executing /sbin/chkconfig mysqld on
[root@007-mysql-master ~]# /sbin/chkconfig mysqld on
mysql>  grant replication slave on *.* to 'repluser'@'192.168.38.147' identified by 'WWQD88OYrqSxLg';
mysql> create database wordpress character set utf8 collate utf8_bin;
mysql> grant all privileges on wordpress.* to 'wordpress'@'192.168.38.%' identified by 'j9DtO2Bf1DvRANQr';

从数据库配置

[root@007-slave mysql-5.7-onekey-install]# cat /etc/my.cnf
# For advice on how to change settings please see
# http://dev.mysql.com/doc/refman/5.7/en/server-configuration-defaults.html [mysqld]
datadir=/data/mysql
socket=/var/lib/mysql/mysql.sock
server-id=2
gtid_mode=on
enforce_gtid_consistency=on
skip_name_resolve # Disabling symbolic-links is recommended to prevent assorted security risks
symbolic-links=0 log-error=/var/log/mysqld.log
pid-file=/var/run/mysqld/mysqld.pid
[client]
socket = /var/lib/mysql/mysql.sock
port = 3306
[root@007-slave mysql-5.7-onekey-install]# systemctl restart mysqld && systemctl enable mysqld
[root@007-slave mysql-5.7-onekey-install]# /sbin/chkconfig mysqld on
mysql> CHANGE MASTER TO MASTER_HOST='192.168.38.138',MASTER_USER='repluser',MASTER_PASSWORD='WWQD88OYrqSxLg',MASTER_PORT=3306,MASTER_AUTO_POSITION=1;
mysql> start slave;
mysql> show slave status\G
...两个yes就OK...

三、mysql服务器充当NFS服务器

配置主NFS

[root@007-mysql-master ~]# yum install nfs-utils -y
[root@007-mysql-master ~]# mkdir /data/wordpress -p
[root@007-mysql-master ~]# cat /etc/exports
/data/wordpress 192.168.38.*(rw,sync,no_subtree_check,no_root_squash
[root@007-mysql-master ~]# systemctl restart nfs
[root@007-mysql-master ~]# systemctl enable nfs

007-web1挂载测试

[root@007-web1 ~]# yum install nfs-utils autofs -y
[root@007-web1 ~]# showmount -e 192.168.38.138
Export list for 192.168.38.138:
/data/wordpress 192.168.38.*
[root@007-web1 ~]# grep wordpress /etc/auto.master
/- /etc/auto.wordpress
[root@007-web1 ~]# cat /etc/auto.wordpress
/var/www/wordpress/wp-content/uploads 192.168.38.138:/data/wordpress
[root@007-web1 ~]# systemctl restart autofs

测试没问题同步到web2

[root@007-web1 ~]# ssh 192.168.38.136 ' yum install nfs-utils autofs -y'
[root@007-web1 ~]# scp /etc/auto.{master,wordpress} 192.168.38.136:/etc/
[root@007-web1 ~]# ssh 192.168.38.136 'systemctl restart autofs'
#测试没问题

配置自动同步

[root@007-mysql-master ~]# yum install rsync inotify-tools -y
[root@007-mysql-master ~]# ssh 192.168.38.147 'yum install rsync -y'
[root@007-mysql-master ~]# ssh 192.168.38.147 'mkdir /data/wordpress -p'
#密钥分发
[root@007-mysql-master ~]# ssh-keygen -f ~/.ssh/id_rsa -P ''
[root@007-mysql-master ~]# ssh-copy-id 192.168.38.147
#同步脚本
[root@007-mysql-master ~]# mkdir /scripts/
[root@007-mysql-master ~]# cat /scripts/inotify-data2.sh
[root@007-mysql-master wordpress]# cat /scripts/inotify-data2.sh
#!/bin/bash SRC=/data/wordpress
DEST='root@192.168.38.147:/data'
# BACKDIR=/tmp/backup/
/usr/bin/inotifywait -mrq --timefmt '%Y-%m-%d %H:%M' --format '%T %w %f %,e' -e delete,moved_to,moved_from,close_write,isdir,attrib ${SRC} | \
while read DATE TIME DIR FILE EVENT;do
FILEPATH=${DIR}${FILE}
# if echo $EVENT | grep -i delete;then
# mkdir $BACKDIR -p && \cp -a $FILEPATH $BACKDIR
# rsync -avz --delete ${SRC} ${DEST} \
# && echo "At ${TIME} on ${DATE}, file $FILEPATH was deleted via rsync" >> /var/log/deletelist.log
# else
rsync -avz --delete ${SRC} ${DEST} \
&& echo "At ${TIME} on ${DATE}, file $FILEPATH was backuped up via rsync" >> /var/log/changelist.log
# fi
done #screen运行
[root@007-mysql-master ~]# yum install screen -y
[root@007-mysql-master ~]# screen -S rsync
[root@007-mysql-master ~]# bash /scripts/inotify-data2.sh

四、配置haproxy

编译安装haproxy(粗糙的脚本)

[root@007-lb1 ~]# cat haproxy.sh
#!/bin/bash yum install -y gcc gcc-c++ glibc glibc-devel pcre pcre-devel openssl openssl-devel systemd-devel net-tools vim iotop bc zip unzip zlib-devel lrzsz tree screen lsof tcpdump wget chrony readline-devel if ! getent passwd haproxy >/dev/null ; then
if ! getent passwd 188 >/dev/null ; then
useradd -r -u 188 -g haproxy -d /var/lib/haproxy -s /sbin/nologin -c "haproxy" haproxy
else
useradd -r -g haproxy -d /var/lib/haproxy -s /sbin/nologin -c "haproxy" haproxy
fi
fi wget https://ftp.osuosl.org/pub/blfs/conglomeration/lua/lua-5.3.5.tar.gz
tar xf lua-5.3.5.tar.gz
cd lua-5.3.5/
make linux test
src/lua -v cd
wget https://mirrors.huaweicloud.com/haproxy/2.0/src/haproxy-2.0.8.tar.gz
tar xf haproxy-2.0.8.tar.gz
cd haproxy-2.0.8/
make ARCH=x86_64 TARGET=linux-glibc USE_PCRE=1 USE_OPENSSL=1 USE_ZLIB=1 USE_SYSTEMD=1 USE_CPU_AFFINITY=1 USE_LUA=1 LUA_INC=/root/lua-5.3.5/src/ LUA_LIB=/root/lua-5.3.5/src/ PREFIX=/usr/local/haproxy
make install PREFIX=/usr/local/haproxy
/usr/local/haproxy/sbin/haproxy -v
cat > /usr/lib/systemd/system/haproxy.service <<'EOF'
[Unit]
Description=HAProxy Load Balancer
After=syslog.target network.target
[Service]
ExecStartPre=/usr/local/haproxy/sbin/haproxy -f /etc/haproxy/haproxy.cfg -c -q
ExecStart=/usr/local/haproxy/sbin/haproxy -Ws -f /etc/haproxy/haproxy.cfg -p /var/lib/haproxy/haproxy.pid
ExecReload=/bin/kill -USR2 $MAINPID
[Install]
WantedBy=multi-user.target
EOF mkdir /etc/haproxy
cat > /etc/haproxy/haproxy.cfg <<'EOF'
global
log 127.0.0.1 local2
chroot /var/lib/haproxy
pidfile /var/run/haproxy.pid
maxconn 4000
uid haproxy
uid haproxy
daemon
stats socket /var/lib/haproxy/stats
defaults
mode http
log global
option httplog
option dontlognull
option http-server-close
option forwardfor except 127.0.0.0/8
option redispatch
retries 3
timeout http-request 10s
timeout queue 1m
timeout connect 10s
timeout client 1m
timeout server 1m
timeout http-keep-alive 10s
timeout check 10s
maxconn 3000
listen web_port
bind *:9999
stats enable
log global
stats uri /haproxy-status
stats auth haadmin:2NweRqCs
EOF mkdir /var/lib/haproxy/
systemctl daemon-reload
systemctl enable haproxy
systemctl start haproxy

配置文件的书写(不写stat就完全一样)

[root@007-lb1 ~]# cat /etc/haproxy/haproxy.cfg
global
log 127.0.0.1 local2
chroot /var/lib/haproxy
pidfile /var/run/haproxy.pid
maxconn 4000
user haproxy
group haproxy
daemon
stats socket /var/lib/haproxy/stats
defaults
mode http
log global
option httplog
option dontlognull
option http-server-close
option forwardfor except 127.0.0.0/8
option redispatch
retries 3
timeout http-request 10s
timeout queue 1m
timeout connect 10s
timeout client 1m
timeout server 1m
timeout http-keep-alive 10s
timeout check 10s
maxconn 3000
listen web_port
bind 192.168.38.131:9999
stats enable
log global
stats uri /haproxy-status
stats auth haadmin:2NweRqCs
frontend 007-web
bind *:80
mode http
default_backend bk_web
backend bk_web
mode http
balance source
cookie SERVERID insert indirect nocache
option forwardfor #转发客户IP到后端服务器
server 007-web1 192.168.38.133:80 cookie 007-web1 check inter 10000 rise 2 fall 5 weight 20
server 007-web2 192.168.38.136:80 cookie 007-web2 check inter 10000 rise 2 fall 5 weight 20

五、配置keepalived

VIP用192.168.38.188

邮件配置

yum install mailx -y
cat >> /etc/mail.rc <<'EOF'
set from=m17114517139_2@163.com
set smtp=smtps://smtp.163.com:465
set smtp-auth-user=m17114517139_2@163.com
set smtp-auth-password=zhj6b266
set smtp-auth=login
set nss-config-dir=/root/.certs
set ssl-verify=ignore
EOF
mkdir -p /root/.certs/
echo -n | openssl s_client -connect smtp.163.com:465 | sed -ne '/-BEGIN CERTIFICATE-/,/-END CERTIFICATE-/p' > ~/.certs/163.crt
certutil -A -n "GeoTrust SSL CA" -t "C,," -d ~/.certs -i ~/.certs/163.crt
certutil -A -n "GeoTrust Global CA" -t "C,," -d ~/.certs -i ~/.certs/163.crt
certutil -L -d /root/.certs
cd /root/.certs/
certutil -A -n "GeoTrust SSL CA - G3" -t "Pu,Pu,Pu" -d ./ -i 163.crt

编译安装keepalived

[root@007-lb1 ~]# cat keepalived.sh
#!/bin/bash
yum install -y libnfnetlink-devel libnfnetlink ipvsadm libnl libnl-devel libnl3 libnl3-devel lm_sensors-libs net-snmp-agent-libs net-snmp-libs openssh-server openssh-clients openssl openssl-devel automake iproute gcc pcre pcre-devel openssl openssl-devel wget https://mirrors.sjtug.sjtu.edu.cn/archlinux/sources/community/keepalived-2.0.19-1.src.tar.gz
tar xf keepalived-2.0.19-1.src.tar.gz
tar xf keepalived/keepalived-2.0.19.tar.gz -C /usr/local/src/
cd /usr/local/src/keepalived-2.0.19/
./configure --prefix=/usr/local/keepalived --disable-fwmark
make && make install cat > /usr/lib/systemd/system/keepalived.service <<'EOF'
[Unit]
Description=LVS and VRRP High Availability Monitor
After=network-online.target syslog.target
Wants=network-online.target
[Service]
Type=forking
PIDFile=/run/keepalived.pid
KillMode=process
EnvironmentFile=-/usr/local/keepalived/etc/sysconfig/keepalived
ExecStart=/usr/local/keepalived/sbin/keepalived $KEEPALIVED_OPTIONS
ExecReload=/bin/kill -HUP $MAINPID
[Install]
WantedBy=multi-user.target
EOF cp bin/keepalived /usr/sbin/ mkdir /etc/keepalived cat > /etc/keepalived/keepalived.conf <<'EOF'
global_defs {
router_id LVS_DEVEL
} vrrp_instance VI_1 {
state MASTER
interface eth0
virtual_router_id 80
priority 100
advert_int 1
unicast_src_ip 192.168.38.131
unicast_peer {
192.168.38.130
} authentication {
auth_type PASS
auth_pass 1111
}
virtual_ipaddress {
192.168.38.172 dev eth0 label eth0:0
}
}
EOF systemctl deamon-reload
systemctl start keepalived ps -ef | grep keepalived

发邮件脚本

[root@007-lb1 keepalived]# cat notify.sh
#!/bin/bash
#
#contact='root@localhost'
contact='admin@jd.com' notify() {
local mailsubject="$(hostname) to be $1, vip floating"
local mailbody="$(date +'%F %T'): vrrp transition, $(hostname) changed to be $1"
echo "$mailbody" | mail -s "$mailsubject" $contact
} case $1 in
master)
notify master
;;
backup)
notify backup
;;
fault)
notify fault
;;
*)
echo "Usage: $(basename $0) {master|backup|fault}"
exit 1
;;
esac

nginx检查脚本

[root@007-lb1 keepalived]# cat check_nginx.sh
#!/bin/bash
GREP_OPTIONS=""
Count1=`netstat -antp |grep -v grep |grep haproxy |wc -l` if [ $Count1 -eq 0 ]; then
exit 1
fi exit 0

lb1的keepalived.conf

[root@007-lb1 keepalived]# cat /etc/keepalived/keepalived.conf
! Configuration File for keepalived global_defs {
router_id node1
vrrp_mcast_group4 224.123.0.18
}
vrrp_script chk_nginx {
script "/etc/keepalived/check_nginx.sh"
interval 2
}
vrrp_instance VI_1 {
state MASTER
interface eth0
virtual_router_id 51
priority 100
advert_int 1
authentication {
auth_type PASS
auth_pass 1dadcvsd
}
virtual_ipaddress {
192.168.38.188/16 dev eth0
}
track_script {
chk_nginx
}
notify_master "/etc/keepalived/notify.sh master"
notify_backup "/etc/keepalived/notify.sh backup"
notify_fault "/etc/keepalived/notify.sh fault"
}

lb2的keepalived.conf

[root@007-lb2 keepalived]# cat keepalived.conf
! Configuration File for keepalived global_defs {
router_id node1
vrrp_mcast_group4 224.123.0.18
}
vrrp_script chk_nginx {
script "/etc/keepalived/check_nginx.sh"
interval 2
}
vrrp_instance VI_1 {
state BACKUP
interface eth0
virtual_router_id 51
priority 99
advert_int 1
authentication {
auth_type PASS
auth_pass 1dadcvsd
}
virtual_ipaddress {
192.168.38.188/16 dev eth0
}
track_script {
chk_nginx
}
notify_master "/etc/keepalived/notify.sh master"
notify_backup "/etc/keepalived/notify.sh backup"
notify_fault "/etc/keepalived/notify.sh fault"
}

测试VIP转移

[root@007-lb1 ~]# pkill haproxy
#vip转移
[root@007-lb2 keepalived]# ip addr show dev eth0
2: eth0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc pfifo_fast state UP group default qlen 1000
link/ether 00:0c:29:5c:b9:ce brd ff:ff:ff:ff:ff:ff
inet 192.168.38.132/24 brd 192.168.38.255 scope global noprefixroute dynamic eth0
valid_lft 2586860sec preferred_lft 2586860sec
inet6 fe80::20c:29ff:fe5c:b9ce/64 scope link noprefixroute
valid_lft forever preferred_lft forever

六、域名解析后就可以了,解析到vip

安装wordpress即可

七、将haproxy+keepalived换成keepalived+LVS

lvs1:192.168.38.134

lvs2:192.168.38.135

VIP:192.168.38.189

说明:如果部署在云上,比如阿里云上,不需要自己部署lvs,直接买阿里云的slb即可,slb然后分发流量到两台web机器,不过这种不推荐,推荐slb走自己的haproxy,进行7层反代

编译安装keepalived同上

邮件服务配置同上

notify脚本同上

check脚本

#!/bin/bash
GREP_OPTIONS=""
Count1=`ps -ef |grep keepalived | grep -v grep |wc -l` if [ $Count1 -eq 0 ]; then
exit 1
fi exit 0

lvs1的keepalived.conf

[root@lvs1 keepalived]# cat keepalived.conf
! Configuration File for keepalived global_defs {
router_id node1
vrrp_mcast_group4 224.123.0.19
}
vrrp_script chk_nginx {
script "/etc/keepalived/check_keepalived.sh"
interval 2
}
vrrp_instance VI_1 {
state MASTER
interface eth0
virtual_router_id 52
priority 100
advert_int 1
authentication {
auth_type PASS
auth_pass 1dadcvsd2
}
virtual_ipaddress {
192.168.38.189/16 dev eth0
}
track_script {
chk_nginx
}
notify_master "/etc/keepalived/notify.sh master"
notify_backup "/etc/keepalived/notify.sh backup"
notify_fault "/etc/keepalived/notify.sh fault"
} virtual_server 192.168.38.189 80 {
delay_loop 3
lb_algo sh
lb_kind DR
protocol TCP real_server 192.168.38.133 80 {
weight 1
HTTP_GET {
url {
path /
status_code 200
}
connect_timeout 1
nb_get_retry 3
delay_before_retry 1
}
}
real_server 192.168.38.136 80 {
weight 1
HTTP_GET {
url {
path /
status_code 200
}
connect_timeout 1
nb_get_retry 3
delay_before_retry 1
}
}
}

lvs2的keepalivbed.conf

[root@lvs2 keepalived]# cat keepalived.conf
[root@lvs1 keepalived]# cat keepalived.conf
! Configuration File for keepalived global_defs {
router_id node1
vrrp_mcast_group4 224.123.0.19
}
vrrp_script chk_nginx {
script "/etc/keepalived/check_keepalived.sh"
interval 2
}
vrrp_instance VI_1 {
state BACKUP
interface eth0
virtual_router_id 52
priority 99
advert_int 1
authentication {
auth_type PASS
auth_pass 1dadcvsd2
}
virtual_ipaddress {
192.168.38.189/16 dev eth0
}
track_script {
chk_nginx
}
notify_master "/etc/keepalived/notify.sh master"
notify_backup "/etc/keepalived/notify.sh backup"
notify_fault "/etc/keepalived/notify.sh fault"
} virtual_server 192.168.38.189 80 {
delay_loop 3
lb_algo sh
lb_kind DR
protocol TCP real_server 192.168.38.133 80 {
weight 1
HTTP_GET {
url {
path /
status_code 200
}
connect_timeout 1
nb_get_retry 3
delay_before_retry 1
}
}
real_server 192.168.38.136 80 {
weight 1
HTTP_GET {
url {
path /
status_code 200
}
connect_timeout 1
nb_get_retry 3
delay_before_retry 1
}
}
}

测试VIP转移

[root@lvs1 keepalived]# systemctl stop keepalived
[root@lvs2 keepalived]# ip a show dev eth0
2: eth0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc pfifo_fast state UP group default qlen 1000
link/ether 00:0c:29:d3:0f:22 brd ff:ff:ff:ff:ff:ff
inet 192.168.38.135/24 brd 192.168.38.255 scope global noprefixroute dynamic eth0
valid_lft 2591783sec preferred_lft 2591783sec
inet 192.168.38.189/16 scope global eth0
valid_lft forever preferred_lft forever
inet6 fe80::20c:29ff:fed3:f22/64 scope link noprefixroute
valid_lft forever preferred_lft forever

web1和web2绑定VIP

[root@007-web1 ~]# cat lvs-dr.sh
#!/bin/sh
#LVS DR模式初始化脚本
#Zhang Shijie:2017-08-18
LVS_VIP=192.168.38.189
source /etc/rc.d/init.d/functions
case "$1" in
start)
/sbin/ifconfig lo:0 $LVS_VIP netmask 255.255.255.255 broadcast $LVS_VIP
/sbin/route add -host $LVS_VIP dev lo:0
echo "1" >/proc/sys/net/ipv4/conf/lo/arp_ignore
echo "2" >/proc/sys/net/ipv4/conf/lo/arp_announce
echo "1" >/proc/sys/net/ipv4/conf/all/arp_ignore
echo "2" >/proc/sys/net/ipv4/conf/all/arp_announce
echo "RealServer Start OK"
;;
stop)
/sbin/ifconfig lo:0 down
/sbin/route del $LVS_VIP >/dev/null 2>&1
echo "0" >/proc/sys/net/ipv4/conf/lo/arp_ignore
echo "0" >/proc/sys/net/ipv4/conf/lo/arp_announce
echo "0" >/proc/sys/net/ipv4/conf/all/arp_ignore
echo "0" >/proc/sys/net/ipv4/conf/all/arp_announce
echo "RealServer Stoped"
;;
*)
echo "Usage: $0 {start|stop}"
exit 1
esac
exit 0
[root@007-web1 ~]# bash lvs-dr.sh start
RealServer Start OK
#web2同理

八、排查、lvs不显示后端服务器

[root@lvs1 keepalived]# ipvsadm -ln
IP Virtual Server version 1.2.1 (size=4096)
Prot LocalAddress:Port Scheduler Flags
-> RemoteAddress:Port Forward Weight ActiveConn InActConn
TCP 192.168.38.189:80 sh

手动curl发现返回302

[root@lvs1 keepalived]# curl 192.168.38.133 -I
HTTP/1.1 302 Found
Server: nginx/1.17.5
Date: Mon, 11 Nov 2019 03:39:12 GMT
Content-Type: text/html; charset=UTF-8
Connection: keep-alive
X-Powered-By: PHP/7.3.10
Location: http://192.168.38.133/wp-admin/setup-config.php

解决:web服务器创建test.html测试页面做健康检查

[root@007-web1 wordpress]# echo test > test.html
[root@007-web1 wordpress]# scp test.html 192.168.38.136:/va/www/wordpress/

两个lvs修改健康检查

[root@lvs2 keepalived]# vim /etc/keepalived/keepalived.conf
.......
real_server 192.168.38.133 80 {
weight 1
HTTP_GET {
url {
path /test.html
status_code 200
}
connect_timeout 1
nb_get_retry 3
delay_before_retry 1
}
}
real_server 192.168.38.136 80 {
weight 1
HTTP_GET {
url {
path /test.html
status_code 200
}
connect_timeout 1
nb_get_retry 3
delay_before_retry 1
}
}
......

随后停止并启动keepalived,就好了

[root@lvs2 keepalived]# ipvsadm -ln
IP Virtual Server version 1.2.1 (size=4096)
Prot LocalAddress:Port Scheduler Flags
-> RemoteAddress:Port Forward Weight ActiveConn InActConn
TCP 192.168.38.189:80 sh
-> 192.168.38.133:80 Route 1 0 0
-> 192.168.38.136:80 Route 1 0 0

另外wordpress的图片目录为uploads不是upload

九、优化

各个服务优化
NFS设置好权限控制,不能777
wordpress测试好友一些东西可以放到NFS,或者同步web1的网站数据到web2,主要是一些主题什么的

NFS权限限制

权限改成755还是成功了

[root@007-mysql-master ~]# chmod 755 -R /data/wordpress/
[root@007-mysql-master ~]# ll /data/wordpress/2019/11/
total 292
-rwxr-xr-x 1 mysql mysql 98728 Nov 11 20:18 89a9f78ed9a0e3a9d0ad9a4836a79c7f.png
-rw-r--r-- 1 mysql mysql 5101 Nov 11 20:20 9ad3c6f0d10514c88930974484e7a143.png
-rwxr-xr-x 1 mysql mysql 186355 Nov 11 20:17 da7999e9b9174995d894cab24e20565a.png

问什么呢?为啥能上传成功,且用户为mysql

原因:web客户端的nginx用户ID为995

[root@007-web2 ~]# id nginx
uid=997(nginx) gid=995(nginx) groups=995(nginx)

NFS这边mysql用户的id也是995

[root@007-mysql-master ~]# id mysql
uid=997(mysql) gid=995(mysql) groups=995(mysql)

/data/wordpress/2019是已经生成的,属主为mysql(id995)

[root@007-mysql-master ~]# ls -l /data/wordpress/
total 0
drwxr-xr-x 3 mysql mysql 16 Nov 11 20:17 2019

但是wordpress无法在/data/wordpress目录下生成新目录,可以设置acl权限给id为995用户(最好手动创建一个id为995的用户)

[root@007-mysql-master ~]# setfacl -m u:mysql:rwx /data/wordpress/
[root@007-mysql-master ~]# getfacl /data/wordpress/
getfacl: Removing leading '/' from absolute path names
# file: data/wordpress/
# owner: root
# group: root
user::rwx
user:mysql:rwx
group::r-x
mask::rwx
other::r-x

或者NFS设置权限,类似于下面这样:

web1和web2的

haproxy+keepalived练习的更多相关文章

  1. HaProxy+Keepalived+Mycat高可用群集配置

    概述 本章节主要介绍配置HaProxy+Keepalived高可用群集,Mycat的配置就不在这里做介绍,可以参考我前面写的几篇关于Mycat的文章. 部署图: 配置  HaProxy安装 181和1 ...

  2. haproxy +keepalived 原创

    Haproxy+keepalived 原理: HAProxy介绍及其定位 HAProxy提供高可用性.负载均衡以及基于TCP和HTTP应用的代理,支持虚拟主机,它是免费.快速并且可靠的一种解决方案.根 ...

  3. haproxy+keepalived实现高可用负载均衡

    软件负载均衡一般通过两种方式来实现:基于操作系统的软负载实现和基于第三方应用的软负载实现.LVS就是基于Linux操作系统实现的一种软负载,HAProxy就是开源的并且基于第三应用实现的软负载. HA ...

  4. HaProxy+keepalived实现负载均衡

    HAProxy提供高可用性.负载均衡以及基于TCP和HTTP应用的代理,支持虚拟主机,它是免费.快速并且可靠的一种解决方案.HAProxy特别适用于那些负载特大的web站点,这些站点通常又需要会话保持 ...

  5. Haproxy+Keepalived搭建Weblogic高可用负载均衡集群

    配置环境说明: KVM虚拟机配置 用途 数量 IP地址 机器名 虚拟IP地址 硬件 内存3G  系统盘20G cpu 4核 Haproxy keepalived 2台 192.168.1.10 192 ...

  6. 实现基于Haproxy+Keepalived负载均衡高可用架构

    1.项目介绍: 上上期我们实现了keepalived主从高可用集群网站架构,随着公司业务的发展,公司负载均衡服务已经实现四层负载均衡,但业务的复杂程度提升,公司要求把mobile手机站点作为单独的服务 ...

  7. Haproxy+Keepalived负载均衡

    Haproxy介绍 HAProxy是一个特别适用于高可用性环境的TCP/HTTP开源的反向代理和负载均衡软件.在7层负载均衡方面的功能很强大(支持cookie track, header rewrit ...

  8. 案例一(haproxy+keepalived高可用负载均衡系统)【转】

    1.搭建环境描述: 操作系统: [root@HA-1 ~]# cat /etc/redhat-release CentOS release 6.7 (Final) 地址规划: 主机名 IP地址 集群角 ...

  9. haproxy+keepalived(涵盖了lvs,nginx.haproxy比较)

    文章转载自: haproxy+keepalived    https://cloud.tencent.com/developer/article/1026385 网络四层和七层的区别   https: ...

  10. Haproxy+Keepalived高可用环境部署梳理(主主和主从模式)

    Nginx.LVS.HAProxy 是目前使用最广泛的三种负载均衡软件,本人都在多个项目中实施过,通常会结合Keepalive做健康检查,实现故障转移的高可用功能. 1)在四层(tcp)实现负载均衡的 ...

随机推荐

  1. Java8新特性之Lambda

    为什么要Lambda Java8应该是目前最大的一次更新了,更新后我们迎来了很多新特性,其中便包括Lambda表达式,函数式编程的思想正式进入Java,让我们看一个经典案例. 例1 按照两个人的年龄排 ...

  2. Ubuntu 搜狗输入法输入异常

    电脑放置一段时间,不使用.过了一会,再使用 sogou 输入法的时候,发现,输入法不起作用了. 切花到用户目录 ~/.config 里面 rm -rf Sogou* 删除搜狗的配置文件,退出当前账户, ...

  3. JavaScript中For循环以及For循环嵌套实例

    JavaScript中For循环实例 1.打印出所有的 "水仙花数 ",所谓 "水仙花数 "是指一个三位数,其各位数字立方和等于该数本身. 例如:153是一个 ...

  4. Ceph Paxos相关代码解析

    Leader选举 Ceph中的leader选举是一个Paxos Lease过程,与BasicPaxos的目的不同.后者用于解决数据一致性问题,而Paxos Lease是为了选举出一个leader承担m ...

  5. 使用js json/xml互相转换

    <html> <head> <title>json与xml互转</title> <script type="text/javascrip ...

  6. .NET如何将字符串分隔为字符

    .NET如何将字符串分隔为字符 如果这是一道面试题,答案也许非常简单:.ToCharArray(),这基本正确-- 我们以"AB吉

  7. 后台添加Textbox

    /// <summary> /// behind add textbox /// </summary> private void AddTextToTextBox() { Te ...

  8. konva canvas插件写雷达图示例

    最近,做了一个HTML5的项目,里面涉及到了雷达图效果,这里,我将react实战项目中,用到的雷达图单拎出来写一篇博客,供大家学习. 以下内容涉及的代码在我的gitlab仓库中:Konva canva ...

  9. SpringBoot 配置提示功能

    目的 配置自动提示的辅助功能可以让配置写起来更快,准确率大大提高. springboot jar 包含提供所有支持的配置属性细节的元数据文件.文件的目的是为了让 IDE 开发者在用户使用 applic ...

  10. RPA UiPath 官网视频

    RPA  UiPath 官网视频相关学习 有一些官网的截图翻译,本来打算把考试题也整理出来,结果没整,另附官网视频 RPA的好处: 广泛的自动化:跨越越来越多的行业,RPA加速在银行和金融,保险,医疗 ...