supervisor 安装和使用

安裝 supervisord

wget -c https://bootstrap.pypa.io/ez_setup.py
python ez_setup.py
easy_install supervisor

配置

### 生成配置文件,且放在/etc目录下
echo_supervisord_conf > /etc/supervisord.conf  

### 为了不将所有新增配置信息全写在一个配置文件里,这里新建一个文件夹,每个程序设置一个配置文件,相互隔离
mkdir /etc/supervisord.d/  

### 修改配置文件
vim /etc/supervisord.conf

### 加入以下配置信息
[include]
files = /etc/supervisord.d/*.conf

### 在supervisord.conf中设置通过web可以查看管理的进程,加入以下代码(默认即有,取消注释即可)  
[inet_http_server] 
port=9001
username=user      
password=123

添加一个示例进程

将下面代码保存为:

<?php

$i=0;
while(true){
    sleep(1);
    echo $i++."n";
}

/root/demo.php

在 /etc/supervisord.d/ 下添加 demo.conf, 内容为:

[program:demo]
### 启动命令
command=/usr/local/server/php/bin/php -f /root/demo.php  
### 进程数
numprocs=2 
### 进程名称
process_name=%(program_name)s_%(process_num)02d 
startsecs=0  
stopwaitsecs=0
### 是否自动启动
autostart=true  
### 当进程丢失自动重启
autorestart=true  
stdout_logfile=/var/log/demo.log
stderr_logfile=/var/log/demo.log

启动:

supervisord -c /etc/supervisord.conf
supervisorctl start demo

查看启动的进程:

supervisorctl status

常用命令

查看状态:

supervisorctl status

启动进程:

supervisorctl start demo

重启进程:

supervisorctl restart demo

重新加载配置:

supervisorctl reload

注意新增或修改了配置都需要执行 reload 命令来让修改生效

Postgresql不重启加载配置文件

当我们新加入数据库用户默认是无法连接的,因为pg_hba.conf不允许连接,当然这个要看你的配置文件规则。

如果现在我添加了一个用户规则配置而我不想重启pgsql就让配置生效怎么半?

pgsql提供了一个方法

Pg_ctl

pg_ctl 是一个用于初始化,启动,停止, 或者重起 PostgreSQL 后端服务器(postgres), 或者显示一个运行着的服务器的状态的工具, 尽管我们可以手动启动服务器,但是 pg_ctl 封装了重新定向日志输出,与终端和进程组合理分离,以及另外提供了方便的选项用于有控制的关闭。

执行命令

pg_ctl reload
返回server signaled成功

常见报错

pg_ctl: no database directory specified and environment variable PGDATA unset

解决办法

你没有设置PGDATA环境变量,设置临时环境变量即可

export PGDATA=/data/pgsql/data

firewalld的9个zone、firewalld关于zone和service的操作

firewalld的9个zone

centos7 默认的防火墙工具为firewalld

  • 打开firewalld
[root@localhost ~]# systemctl disable iptables
Removed symlink /etc/systemd/system/basic.target.wants/iptables.service.
[root@localhost ~]# systemctl stop iptables
[root@localhost ~]# systemctl enable firewalld
Created symlink from /etc/systemd/system/dbus-org.fedoraproject.FirewallD1.service to /usr/lib/systemd/system/firewalld.service.
Created symlink from /etc/systemd/system/basic.target.wants/firewalld.service to /usr/lib/systemd/system/firewalld.service.
[root@localhost ~]# systemctl start firewalld

将之前打开的iptables关掉,启动firewalld。可以用iptables查看表的规则。

  • firewalld的9个zone
[root@localhost ~]# firewall-cmd --get-zones     #查看是所有zone
block dmz drop external home internal public trusted work
[root@localhost ~]# firewall-cmd --get-default-zone      #查看默认zone
public

block dmz drop external home internal public trusted work 是firewalld的9个zone,默认的zone为public。

  • firewall的9个zone的区别
    未分类

firewalld关于zone的操作

  • 修改默认的zone
[root@localhost ~]# firewall-cmd --get-default-zone      #查看默认zone
public
[root@localhost ~]# firewall-cmd --set-default-zone=work     #将默认的zone修改为work
success
[root@localhost ~]# firewall-cmd --get-default-zone      #查看默认的zone
work 
  • 查看指定网卡的zone
[root@localhost ~]# firewall-cmd --get-zone-of-interface=ens33   #查看ens33网卡的zone
work
[root@localhost ~]# firewall-cmd --get-zone-of-interface=ens37   #查看ens37网卡的zone
work
[root@localhost ~]# firewall-cmd --get-zone-of-interface=lo  #查看lo的zone
no zone
  • 给指定网卡增加zone
[root@localhost ~]# firewall-cmd --zone=public --add-interface=lo    #给lo网卡指定zone为public
success
[root@localhost ~]# firewall-cmd --get-zone-of-interface=lo  #查看lo网卡的zone
public
  • 修改指定网卡的zone
[root@localhost ~]# firewall-cmd --zone=block --change-interface=ens37   #将网卡ens37的zone改成block
The interface is under control of NetworkManager, setting zone to 'block'.
success
[root@localhost ~]# firewall-cmd     --get-zone-of-interface=ens37
block
  • 删除指定网卡的zone
[root@localhost ~]# firewall-cmd --zone=block --remove-interface=ens37   #删除ens37网卡的block zone
The interface is under control of NetworkManager, setting zone to default.
success
[root@localhost ~]# firewall-cmd --get-zone-of-interface=ens37
work

删除指定网卡修改的zone之后,它的zone会变回默认的zone

  • 查看系统中所有网卡所在的zone
[root@localhost ~]# firewall-cmd --get-active-zones  #查看系统中所有网卡所在的zone
work
    interfaces: ens33 ens37
public
    interfaces: lo

firewalld关于service的操作

service 就是zone下面的一个子单元,可以理解成指定的一个端口。

  • 查看所有的servie
[root@localhost ~]# firewall-cmd --get-service
RH-Satellite-6 amanda-client amanda-k5-client bacula bacula-client bitcoin bitcoin-rpc bitcoin-testnet bitcoin-testnet-rpc ceph ceph-mon cfengine condor-collector ctdb dhcp dhcpv6 dhcpv6-client dns docker-registry dropbox-lansync elasticsearch freeipa-ldap freeipa-ldaps freeipa-replication freeipa-trust ftp ganglia-client ganglia-master high-availability http https imap imaps ipp ipp-client ipsec iscsi-target kadmin kerberos kibana klogin kpasswd kshell ldap ldaps libvirt libvirt-tls managesieve mdns mosh mountd ms-wbt mssql mysql nfs nrpe ntp openvpn ovirt-imageio ovirt-storageconsole ovirt-vmconsole pmcd pmproxy pmwebapi pmwebapis pop3 pop3s postgresql privoxy proxy-dhcp ptp pulseaudio puppetmaster quassel radius rpc-bind rsh rsyncd samba samba-client sane sip sips smtp smtp-submission smtps snmp snmptrap spideroak-lansync squid ssh synergy syslog syslog-tls telnet tftp tftp-client tinc tor-socks transmission-client vdsm vnc-server wbem-https xmpp-bosh xmpp-client xmpp-local xmpp-server
  • 查看当前zone下的service
[root@localhost ~]# firewall-cmd --list-service
ssh dhcpv6-client
  • 查看指定zone下的service
[root@localhost ~]# firewall-cmd --zone=public --list-service    #指定查看zone=public 下的service
dhcpv6-client ssh
  • 把服务增加到public的zone下(临时添加)
[root@localhost ~]# firewall-cmd --zone=public --add-service=http    #把http服务临时添加到public的zone下
success
[root@localhost ~]# firewall-cmd --zone=public --list-service
dhcpv6-client ssh http

临时添加的service是在内存中,配置文件中没有,重启之后

  • 把服务增加到public的zone下(永久添加,即更改配置文件)
    zone的配置文件路径/etc/firewalld/zones/
[root@localhost ~]# firewall-cmd --zone=public --add-service=http     --permanent
success
[root@localhost ~]# firewall-cmd --zone=public --list-service
dhcpv6-client ssh http

–permanent 将配置写到配置文件中

[root@localhost ~]# ls /etc/firewalld/zones
public.xml  public.xml.old

每当永久修改完配置文件之后,系统都会将修改之前的配置文件备份一份,后缀名是old。

  • zone的配置文件模板
zone,service配置文件的模板存放路径:
/usr/lib/firewalld/zones
/usr/lib/firewalld/services
  • 删除zone下的某服务
[root@localhost ~]# firewall-cmd --zone=public --remove-service=http     #临时删除
[root@localhost ~]# firewall-cmd --zone=public --remove-service=http --permanent     #永久删除
  • 需求:ftp服务自定义端口1121,需要在work zone下面放行ftp
第一步:复制ftp的配置文件到/etc/firewalld/services/

[root@localhost ~]# cp /usr/lib/firewalld/services/ftp.xml  /etc/firewalld/services/

第二步:编辑该文件,将port="21"改为port="1121"

[root@localhost ~]# vim /etc/firewalld/services/ftp.xml
<?xml version="1.0" encoding="utf-8"?>
<service>
 <short>FTP</short>
 <description>FTP is a protocol used for remote file transfer. If you plan to make your FTP server publicly available, enable this option. You need the vsftpd package installed for this option to be useful.</description>
 <port protocol="tcp" port="1121"/>
 <module name="nf_conntrack_ftp"/>
</service>

第三步:复制workzone的配置文件到/etc/firewalld/zones/

[root@localhost ~]# cp /usr/lib/firewalld/zones/work.xml /etc/firewalld/zones/

第四步:编辑该文件,增加“<service name="ftp"/>”

[root@localhost ~]# vim /etc/firewalld/zones/work.xml
<?xml version="1.0" encoding="utf-8"?>
<zone>
<short>Work</short>
 <description>For use in work areas. You mostly trust the other computers on networks to not harm your computer. Only selected incoming connections are accepted.</description>
 <service name="ssh"/>
 <service name="dhcpv6-client"/>
 <service name="ftp"/>
</zone>

第六步:重新加载

[root@localhost ~]# firewall-cmd --reload
success

CentOS7防火墙firewalld

防火墙守护 firewalld 服务引入了一个信任级别的概念来管理与之相关联的连接与接口。它支持 ipv4 与 ipv6,并支持网桥,采用 firewall-cmd (command) 或 firewall-config (gui) 来动态的管理 kernel netfilter 的临时或永久的接口规则,并实时生效而无需重启服务。

firewalld和iptables的关系

firewalld自身并不具备防火墙的功能,而是和iptables一样需要通过内核的netfilter来实现,也就是说firewalld和iptables一样,他们的作用都是用于维护规则, 而真正使用规则干活的是内核的netfilter,只不过firewalld和iptables的结构以及使用方法不一样罢了

firewalld的配置模式

firewalld 将配置储存在 /usr/lib/firewalld/ 和 /etc/firewalld/ 中的各种 XML 文件里

/usr/lib/firewalld 中的默认/备用配置
该目录包含了由 firewalld 提供的默认以及备用的 ICMP 类型、服务、区域配置。由 firewalld 软件包提供的这些文件不能被修改,即使修改也会随着 firewalld 软件包的更新被重置。 其他的 ICMP 类型、服务、区域配置可以通过软件包或者创建文件的方式提供。

/etc/firewalld 中的系统配置设置
存储在此的系统或者用户配置文件可以是系统管理员通过配置接口定制的,也可以是手动定制的。这些文件将重载默认配置文件。
为了手动修改预定义的 icmp 类型,区域或者服务,从默认配置目录将配置拷贝到相应的系统配置目录,然后根据需求进行修改。
如果你加载了有默认和备用配置的区域,在 /etc/firewalld 下的对应文件将被重命名为 .old 然后启用备用配置

区域管理

通过将网络划分成不同的区域(通常情况下称为 zones),制定出不同区域之间的访问控制策略来控制不同任程度区域间传送的数据流。例如互联网是不可信任的区域,而内部网络是高度信任的区域。以避免安全策略中禁止的一些通信。它有控制信息基本的任务在不同信任的区域。典型信任的区域包括互联网 ( 一个没有信任的区域 ) 和一个内部网络 ( 一个高信任的区域 )。最终目标是提供受控连通性在不同水平的信任区域通过安全政策的运行和连通性模型之间根据最少特权原则。例如:公共 WIFI 网络连接应该不信任,而家庭有线网络连接就应该完全信任。网络安全模型可以在安装、初次启动和首次建立网络连接时选择初始化。该模型描述了主机所联的整个网络环境的可信级别,并定义了新连接的处理方式。在 /etc/firewalld/ 的区域设定是一系列可以被快速执行到网络接口的预设定。有几种不同的初始化区域:

  • drop(丢弃)
    任何接收的网络数据包都被丢弃,没有任何回复。仅能有发送出去的网络连接。

  • block(限制)
    任何接收的网络连接都被 IPv4 的 icmp-host-prohibited 信息和 IPv6 的 icmp6-adm-prohibited 信息所拒绝。

  • public(公共)
    在公共区域内使用,不能相信网络内的其他计算机不会对您的计算机造成危害,只能接收经过选取的连接。

  • external(外部)
    特别是为路由器启用了伪装功能的外部网。您不能信任来自网络的其他计算,不能相信它们不会对您的计算机造成危害,只能接收经过选择的连接。

  • dmz(非军事区)
    用于您的非军事区内的电脑,此区域内可公开访问,可以有限地进入您的内部网络,仅仅接收经过选择的连接。

  • work(工作)
    用于工作区。您可以基本相信网络内的其他电脑不会危害您的电脑。仅仅接收经过选择的连接。

  • home(家庭)
    用于家庭网络。您可以基本信任网络内的其他计算机不会危害您的计算机。仅仅接收经过选择的连接。

  • internal(内部)
    用于内部网络。您可以基本上信任网络内的其他计算机不会威胁您的计算机。仅仅接受经过选择的连接。

  • trusted(信任)
    可接受所有的网络连接。

说明:firewalld 的缺省区域是 public。
对于区域的修改,可使用网络管理器NetworkManager搞定

firewalld 基本操作

安装firewalld

# yum install firewalld firewall-config

firewalld启动,停止,开机启动与否,查看状态

# systemctl start  firewalld.service       启动
# systemctl enable  firewalld.service      开机自启
# systemctl stop  firewalld.service        停止
# systemctl disable firewalld.service      开机禁止启动
# systemctl status  firewalld.service      查看状态

firewall-cmd命令

基本命令

# firewall-cmd --version    查看版本
# firewall-cmd --help    查看帮助
# firewall-cmd --state    显示状态
# firewall-cmd --panic-on    拒绝所有包
# firewall-cmd --panic-off    取消拒绝状态
# firewall-cmd --query-panic    查看是否拒绝
# firewall-cmd --reload    重新加载防火墙,并不中断用户连接(firewalld特性之一动态添加规则)
# firewall-cmd --complete-reload    重新加载防火墙并中断用户连接(类似于重启服务)

跟zone相关的

# firewall-cmd --get-zones    显示支持的区域列表
# firewall-cmd --get-active-zones    查看当前的区域
# firewall-cmd --get-default-zone    查看默认区域
# firewall-cmd --set-default-zone=home    设置默认区域为 home
# firewall-cmd --zone=public --list-interfaces    显示显示公共区域(public)所有接口
# firewall-cmd --zone=public --list-all    显示公共区域(public)所有设置
# firewall-cmd --get-zone-of-interface=ens33    查看指定接口 ens33 所属区域
# firewall-cmd --zone=internal --change-interface=ens33   临时修改网络接口 ens33 为内部区域(internal),永久修改加上 --permanent 参数
# firewall-cmd --zone=public --add-interface=ens37    为公共区域(public)增加一个接口 ens37  

跟service相关的

# firewall-cmd --get-service    显示服务列表
# firewall-cmd --list-service    显示当前服务
# firewall-cmd --enable service=ssh    允许SSH服务通过
# firewall-cmd --disable service=ssh    禁止SSH服务通过
# firewall-cmd --enable service=samba --timeout=600    临时允许 samba 服务通过 600 秒
# firewall-cmd --permanent --zone=internal --add-service=http    添加 http 服务到内部区域(internal)
# firewall-cmd --zone=work --add-service=smtp    把 smtp 服务加入工作区域(work) 
# firewall-cmd --zone=work --remove-service=smtp    从工作区域(work)移除 smtp 服务

跟port相关的

# firewall-cmd --zone=internal --add-port=443/tcp    在内部区域(internal)打开 443/tcp 端口
# firewall-cmd --zone=external --add-forward-port=port=22:proto=tcp:toport=52222:toaddr=192.168.1.20  
把外部区域(external)的 22 端口转发到 192.168.1.20 的 52222 端口

跟地址伪装相关的

# firewall-cmd --zone=external --query-masquerade    查询外部区域(external)是否能伪装ip,结果为yes
# firewall-cmd --zone=external --add-masquerade     外部区域(external)启用IP伪装(masquerade)
# firewall-cmd --zone=external --remove-masquerade    外部区域(external)禁用用IP伪装

更多内容请参考官方文档

https://access.redhat.com/documentation/en-us/red_hat_enterprise_linux/7/html/security_guide/sec-using_firewalls

CentOS7防火墙firewalld配置

启动:

systemctl start firewalld

停止:

systemctl stop firewalld

重启:

systemctl restart firewalld.service

查看状态:

systemctl status firewalld

开机启动:

systemctl enable firewalld.service

开机禁用:

systemctl disable firewalld

查看服务是否开机启动:

systemctl is-enabled firewalld.service

查看已启动的服务列表:

systemctl list-unit-files|grep enabled

查看启动失败的服务列表:

systemctl --failed

查看版本:

firewall-cmd --version

查看帮助:

firewall-cmd --help

显示状态:

firewall-cmd --state

查看所有打开的端口:

firewall-cmd --zone=public --list-ports

更新防火墙规则:

firewall-cmd --reload

查看区域信息:

firewall-cmd --get-active-zones

查看指定接口所属区域:

firewall-cmd --get-zone-of-interface=eth0

拒绝所有包:

firewall-cmd --panic-on

取消拒绝状态:

firewall-cmd --panic-off

查看是否拒绝:

firewall-cmd --query-panic

开放80端口:

firewall-cmd --zone=public --add-port=80/tcp --permanent (--permanent永久生效,没有此参数重启后失效)

查看80端口:

firewall-cmd --zone=public --query-port=80/tcp

删除80端口:

firewall-cmd --zone=public --remove-port=80/tcp --permanent

开放端口区间:

firewall-cmd --permanent --zone=public --add-port=8080-9999/tcp //永久

重新载入使配置立即生效:

firewall-cmd --reload

Docker2(docker仓库+cgroup)

一.Docker仓库

1.创建docker仓库

docekr load -i registry:2.3.1

2.Docker 官方已经把仓库封装为镜像,直接通过启动容器就可以部署完成仓库

 docker run -d --name registry -p 5000:5000 -v/opt/registry:/var/lib/registry registry:2.3.1

3.默认docker 仓库远程推送拉取需要TLS加密支持,走的是https协议,如需开启http方式,
需要做如下修改:

vim /etc/systemd/system/docker.service(此处docker.service文件是链接或者cp过来的)
ExecStart=/usr/bin/docker daemon -H fd:// -H tcp://0.0.0.0:2375 -H unix:///var/run/docker.sock
--bip 192.168.0.1/24 --insecure-registry 172.25.254.7:5000
 systemctl daemon-reload
 systemctl restart docker

4.将镜像放进仓库中(push)
未分类
未分类
5.从仓库中拉取镜像
未分类
未分类
6.仓库认证
仓库不能是公开的(不能说随便谁都可以进行push和pull),最好有用户和权限

(1)创建目录/opt/auth,并创建用户用户admin,密码为westos;多个用户时,只需追加就好,此例中追加了一个用户haha ,密码为redhat
未分类
(2)生成容器vm1

docker run -d -p 5000:5000 --name vm1 -v  /opt/registry:/var/lib/registry -v /opt/auth:/auth -e "REGISTRY_AUTH=htpasswd" -e "REGISTRY_AUTH_HTPASSWD_REALM=Registry
Realm" -e "REGISTRY_AUTH_HTPASSWD_PATH=/auth/htpasswd" registry:2.3.1

未分类
(3)若不登录,则不能push进仓库
未分类
未分类
(4)用户admin登录,push
未分类

二.cgroup ##(此例是在redhat6.5中做测试)

cgroups 实现了对资源的配额和度量.(此例中凡是需要/etc/init.d/cgconfig restart 均需跳出cgroup目录进行操作,否则会重启失败)

1.安装
未分类
未分类
2.memory 内存相关的限制,此例中限制在200M=20010241024B
未分类
(1)编写配置文件(x1为自定义名字,限制使用内存字节以及swap字节,总共200M),记得跳出cgroup目录,进行重启

vim /etc/cgconfig.conf

未分类
(2)测试,当申请300M文件时,只能分给200M
未分类
(3)例子

(3.1)memapp1 memapp2 本身开启他们并没有内存限制,我们的例子为限制memapp2,允许memapp1开启
未分类
未分类
(3.2)将两个小程序所有者改为用户haha
未分类
未分类
未分类
(3.3)我们从(3.1)中可看出,memapp1启动需要将近4096个内存页,所以为了简单起见,我们将内存限制设置为5000内存页(即500010244B)

vim /etc/cgconfig.conf

未分类
未分类
3.cpu 在 cgroup 中,并不能像硬件虚拟化方案一样能够定义 CPU 能力,但是能够定义 CPU 轮转的优先级,因此具有较高 CPU 优先级的进程会更可能得到 CPU 运算。 通过将参数写入 cpu.shares ,即可定义改 cgroup 的 CPU 优先级 – 这里是一个相对权重,而非绝对值

(1)没有cpu限制,可看到为99.9%
未分类
未分类
(2)有了内存限制,设置为100,接近原来1024的十分之一
未分类
未分类
(3)blkio block IO 相关的统计和限制,byte/operation 统计和限制 (IOPS 等),读写速度限制等,但是这里主要统计的都是同步 IO

(3.1)没有读取限制(安装iotop,用iotop命令查看读取速度)

dd if=/dev/vda of=/dev/null &

未分类
未分类
(3.2)读取限制
未分类
未分类
未分类
(4)冻结freezer

(4.1)本身存在一进程8924
未分类
(4.2)vim /etc/cgconfig
未分类
(4.3)若freezer.state状态为FROZEN,则冻结该进程
未分类
未分类
(4.4)若修改为THAWED,则恢复该进程
未分类
未分类

HAProxy系列—Linux下的安装

HAProxy是一个使用C语言编写的自由及开放源代码软件,其提供高可用性、负载均衡,以及基于TCP和HTTP的应用程序代理。
  
HAProxy特别适用于那些负载特大的web站点,这些站点通常又需要会话保持或七层处理。HAProxy运行在当前的硬件上,完全可以支持数以万计的并发连接。并且它的运行模式使得它可以很简单安全的整合进您当前的架构中, 同时可以保护你的web服务器不被暴露到网络上。
  
HAProxy实现了一种事件驱动, 单一进程模型,此模型支持非常大的并发连接数。多进程或多线程模型受内存限制 、系统调度器限制以及无处不在的锁限制,很少能处理数千并发连接。事件驱动模型因为在有更好的资源和时间管理的用户空间(User-Space) 实现所有这些任务,所以没有这些问题。此模型的弊端是,在多核系统上,这些程序通常扩展性较差。这就是为什么他们必须进行优化以 使每个CPU时间片(Cycle)做更多的工作。

一、下载并解压

下载地址:http://pkgs.fedoraproject.org/repo/pkgs/haproxy/

[root@haproxy-server-master ~]# cd /usr/local/src/
[root@haproxy-server-master src]# wget http://pkgs.fedoraproject.org/repo/pkgs/haproxy/haproxy-1.7.9.tar.gz/sha512/d1ed791bc9607dbeabcfc6a1853cf258e28b3a079923b63d3bf97504dd59e64a5f5f44f9da968c23c12b4279e8d45ff3bd39418942ca6f00d9d548c9a0ccfd73/haproxy-1.7.9.tar.gz
[root@haproxy-server-master src]# tar zxvf haproxy-1.7.9.tar.gz

二、安装

[root@haproxy-server-master src]# cd haproxy-1.7.9
[root@haproxy-server-master haproxy-1.7.9]# uname -r
3.10.0-514.el7.x86_64
[root@haproxy-server-master haproxy-1.7.9]# make TARGET=linux310 ARCH=x86_64 PREFIX=/usr/local/haproxy
[root@haproxy-server-master haproxy-1.7.9]# make install PREFIX=/usr/local/haproxy

参数说明:

  • TARGET=linux310,内核版本,使用uname -r查看内核,如:3.10.0-514.el7,此时该参数就为linux310;kernel 大于2.6.28的可以用:TARGET=linux2628;
  • ARCH=x86_64,系统位数;
  • PREFIX=/usr/local/haprpxy #/usr/local/haprpxy,为haprpxy安装路径。

三、添加配置文件

1.79及以后的版本解压后文件内就没有haproxy.cfg文件,所以需要我们自己找个模板写一下。

由于没有配置其他的服务器,这里就简单的添加一个可以让Haproxy启动的配置。

[root@haproxy-server-master haproxy]# mkdir conf
[root@haproxy-server-master haproxy]# ls
conf  doc  sbin  share
[root@haproxy-server-master haproxy]# cd conf/
[root@haproxy-server-master conf]# vim haproxy.cfg

global
        log 127.0.0.1   local0
        maxconn 1000
        daemon

defaults
        log     global
        mode    http
        option  httplog
        option  dontlognull
        retries 3
        timeout connect 5000
        timeout client  50000
        timeout server 50000

listen admin_stats
        bind 0.0.0.0:1080
        mode http
        option httplog
        maxconn 10
        stats refresh 30s
        stats uri /stats
        stats realm XingCloud Haproxy
        stats auth admin:admin
        stats auth  Frank:Frank
        stats hide-version
        stats  admin if TRUE

四、启动haproxy

[root@haproxy-server-master conf]# /usr/local/haproxy/sbin/haproxy -f /usr/local/haproxy/conf/haproxy.cfg

验证一下是否启动成功:

[root@haproxy-server-master conf]# lsof -i :1080
COMMAND  PID USER   FD   TYPE DEVICE SIZE/OFF NODE NAME
haproxy 2221 root    3u  IPv4  20285      0t0  TCP *:socks (LISTEN)

五、访问统计页面

地址:http://10.73.150.4:1080/stats

未分类

附:其他问题

六、haproxy记录日志

在配置前,我们先来了解一下日志的level:local0~local7 16~23保留为本地使用:

  • emerg 0 系统不可用;
  • alert 1 必须马上采取行动的事件;
  • crit 2 关键的事件;
  • err 3 错误事件;
  • warning 4 警告事件;
  • notice 5 普通但重要的事件;
  • info 6 有用的信息;
  • debug 7 调试信息。

默认 haproxy 是不记录日志的,为了记录日志还需要配置 syslog 模块,在 linux 下是 rsyslogd 服务。

1、先安装 rsyslog(系统应该都安装了,先查看一下)

[root@haproxy-server-master /]# yum -y install rsyslog

2、添加haproxy的日志配置

[root@haproxy-server-master /]# vim /etc/rsyslog.d/haproxy.conf

$ModLoad imudp
$UDPServerRun 514
local0.* /var/log/haproxy.log

[root@haproxy-server-master /]# ls /etc/rsyslog.d/
haproxy.conf  listen.conf

3、修改 /etc/rsyslog.conf 文件

在#### RULES ####上面一行的地方加入以下内容(文件里应该默认有这个配置,可以看一下):

[root@haproxy-server-master /]# vim /etc/rsyslog.conf

# Include all config files in /etc/rsyslog.d/
$IncludeConfig /etc/rsyslog.d/*.conf

4、修改 /etc/sysconfig/rsyslog 文件

把SYSLOGD_OPTIONS=”-m 0”改成 SYSLOGD_OPTIONS=”-r -m 0 -c 2”

[root@haproxy-server-master /]# vim /etc/sysconfig/rsyslog

SYSLOGD_OPTIONS="-r -m 0 -c 2"

相关解释说明:

  • -r:打开接受外来日志消息的功能,其监控514 UDP端口;
  • -x:关闭自动解析对方日志服务器的FQDN信息,这能避免DNS不完整所带来的麻烦;
  • -m:修改syslog的内部mark消息写入间隔时间(0为关闭),例如240为每隔240分钟写入一次”–MARK–”信息;
  • -h:默认情况下,syslog不会发送从远端接受过来的消息到其他主机,而使用该选项,则把该开关打开,所有 接受到的信息都可根据syslog.conf中定义的@主机转发过去。

3、保存,重启 rsyslog 服务

[root@haproxy-server-master /]# systemctl restart rsyslog.service
[root@haproxy-server-master /]# systemctl status rsyslog.service
● rsyslog.service - System Logging Service
   Loaded: loaded (/usr/lib/systemd/system/rsyslog.service; enabled; vendor preset: enabled)
   Active: active (running) since 一 2017-11-27 10:51:26 CST; 11s ago
     Docs: man:rsyslogd(8)
           www.rsyslog.com/doc/
 Main PID: 3855 (rsyslogd)
   CGroup: /system.slice/rsyslog.service
           └─3855 /usr/sbin/rsyslogd -n

11月 27 10:51:26 haproxy-server-master systemd[1]: Starting System Logging Service...
11月 27 10:51:26 haproxy-server-master rsyslogd[3855]:  [origin software="rsyslogd" swVersion="8.24.0" x-pid="38...tart
11月 27 10:51:26 haproxy-server-master systemd[1]: Started System Logging Service.
Hint: Some lines were ellipsized, use -l to show in full.

现在你就可以看到日志(/var/log/haproxy.log)了(如果没有,重启一下Haproxy)。

percona-toolkit 基本使用

运行环境:

Master:10.168.1.216
Slave:10.168.1.217

一、pt-heartbeat

监控mysql复制延迟

1.1、创建一个后台进程定期更新主上的test库的heartbeat表()默认是1s,可以–interval指定,执行后会成一个heartbeat表,ismarthome库为我监控的同步库

pt-heartbeat -D ismarthome --update --user=root --password=123456 -h10.168.1.216 --create-table –daemonize

1.2、监控复制在slave上的落后程度(会一直监控)

pt-heartbeat -D ismarthome --monitor --user=root --password=daqi-123456 -h10.168.1.217

1.3、监控复制在slave上的落后程度(监控一次退出)

pt-heartbeat -D ismarthome --check --user=root --password=daqi-123456 -h10.168.1.217

二、 pt-slave-find

查找和打印mysql所有从服务器复制层级关系

2.1、查找主服务器的mysql有所有从的层级关系

pt-slave-find --user=root --password=123456--host=10.168.1.216

三、pt-slave-restart

监视mysql复制错误,并尝试重启mysql复制当复制停止的时候

3.1、监视从,跳过1个错误

pt-slave-restart --user=root --password=daqi-123456 --host=10.168.1.217 --skip-count=1

3.2、监视从,跳过错误代码为1062的错误

pt-slave-restart --user=root --password=daqi-123456 --host=10.168.1.217 --error-numbers=1062

四、pt-table-checksum

检查数据是否一致(在主库执行)

4.1、比较test数据库同步是否一致,结果显示所有的表

pt-table-checksum  --nocheck-replication-filters --databases=testDb --replicate=testDb.checksums --create-replicate-table  --host=10.168.1.216  --port 3306  -uroot -p123456

参数说明:第一次运行的时候需要添加–create-replicate-table参数,如果不加这个就需要手工运行添加表结构的SQL,表结构SQL如下:

CREATE TABLE checksums (
   db             char(64)     NOT NULL,
   tbl            char(64)     NOT NULL,
   chunk          int          NOT NULL,
   chunk_time     float            NULL,
   chunk_index    varchar(200)     NULL,
   lower_boundary text             NULL,
   upper_boundary text             NULL,
   this_crc       char(40)     NOT NULL,
   this_cnt       int          NOT NULL,
   master_crc     char(40)         NULL,
   master_cnt     int              NULL,
   ts             timestamp    NOT NULL,
   PRIMARY KEY (db, tbl, chunk),
   INDEX ts_db_tbl (ts, db, tbl)
) ENGINE=InnoDB
  • –nocheck-replication-filters :不检查复制过滤器,建议启用。后面可以用–databases来指定需要检查的数据库。
  • –no-check-binlog-format :不检查复制的binlog模式,要是binlog模式是ROW,则会报错。

  • –replicate-check-only :只显示不同步的信息。(注意:要谨慎使用,此参数不会生成新的checksums数据,只会根据checksums表已经有的数据来显示。)

  • –replicate= :把checksum的信息写入到指定表中,建议直接写到被检查的数据库当中。
  • –databases= :指定需要被检查的数据库,多个则用逗号隔开。
  • –tables= :指定需要被检查的表,多个用逗号隔开
  • h=127.0.0.1 :Master的地址
  • u=root :用户名
  • p=123456 :密码
  • P=3306 :端口

运行结果行显示的结果参数说明:

  • TS :完成检查的时间。
  • ERRORS :检查时候发生错误和警告的数量。
  • DIFFS :0表示一致,1表示不一致。当指定–no– – replicate-check时,会一直为0,当指定–replicate-check-only会显示不同的信息。
  • ROWS :表的行数。
  • CHUNKS :被划分到表中的块的数目。
  • SKIPPED :由于错误或警告或过大,则跳过块的数目。
  • TIME :执行的时间。
  • TABLE :被检查的表名。

备注:

(pt-table-checksum 其工作原理是通过计算每个表的散列值 并将计算过程在服务器上重放 从而拿到主从各自的散列值做比较,但是pt-table-checksum 不是直接计算整个表的散列值,而是分块计算避免服务器长时间延时 因此在计算散列过程重放时是基与statement 不能基于row)

五、pt-table-sync

高效同步mysql表的数据
原理:总是在主上执行数据的更改,再同步到从上,不会直接更改成从的数据,在主上执行更改是基于主上现在的数据,不会更改主上的数据。注意使用之前先备份你的数据,避免造成数据的丢失.执行execute之前最好先换成–print或–dry-run查看一下会变更哪些数据。

  • –print :打印,但不执行命令。
  • –execute :执行命令。

5.1、同步Master(10.168.1.216)上a表数据到Slave(10.168.1.217),在执行之前可以用–execute参数换成–print来查看会变更什么东西,命令里有2个ip,第一次出现的是M的地址,第2次是Slave的地址

查看:pt-table-sync –print –user=root –password=123456 h=10.168.1.216,D=testDb,t=aaa h=192.168.3.92

同步:pt-table-sync –execute –user=root –password=123456 h=10.168.1.216,D=testDb,t=aaa h=192.168.3.92

5.2、同步Master(10.168.1.216)上数据到Slave(10.168.1.217)

pt-table-sync --execute --sync-to-master --user=root --password=123456  h=10.168.1.217 --database testDb

5.3、只同步指定的a表

pt-table-sync --execute --sync-to-master --user=root --password=123456  h=10.168.1.217,D=testDb,t=a

5.4、根据pt-table-checksum的结果进行数据同步

pt-table-sync --execute --replicate testDb.checksums --user=root --password=123456 h=10.168.1.216

5.5、根据pt-table-checksum使从的数据和主的数据一致

pt-table-sync --execute --replicate test.checksums --user=root --password=123456  --sync-to-master h=10.168.1.217,D=testDb,t=a

使用haproxy进行会话保持

现象说明

http出口的负载均衡策略是roundrobin,部分业务系统将会话信息保存在backend server,backend server之间未做同步。

用户在访问、操作的时候,会出现会话不连贯的现象 。

方案说明

haproxy可以使用多种方式做到会话保持,可以在balance中指定均衡算法:

balance <algorithm> [ <arguments> ]
balance url_param <param> [check_post]

source的方式将同一个源IP的请求转发给同一个backend server,可以作用于tcp和http。但是当某个源IP的请求量较大,或者用户请求经过NAT后到达,会导致backend server的负载严重不均衡。不采用。

url_param的方式,需要业务在url中带有sessionid,适用于http。不采用。

也可以使用stick-tables的方式。stick-table设置复杂,且需要维护记录表。不采用。

还可以使用cookie的方式。cookie本身也有多种策略,例如insert,prefix,rewrite等,适用于http。

经过对比,决定采用以下方式:

cookie cookie.XXXXX.cn insert indirect postonly

即:

只有遇到post请求的时候,haproxy在响应中设置一个名为
`cookie.XXXXX.cn`的cookie,后续带有该cookie的请求到达
haproxy时,haproxy将该cookie去除后,转发给cookie指定的backen server。

过程说明

未发送post请求之前,依然采用roundrobin的方式

第一次get请求:

未分类

第二次get请求:

未分类

发送了post请求后,被设置cookie

cookie的值为处理post请求的backend server的ID。

未分类

后续请求被转发到同一个backend server

用户后续所有http请求,都会带上cookie,被转发到同一个backend server。

未分类

未分类

绑定的backend server宕机后,cookie失效

绑定的backend server宕机后,虽然后续发送的请求中依然会带有cookie,但是这时候会重新回到roundrobin的状态,直到用户再次发送POST请求,重新绑定backend server。

宕机后,再次发送POST的情形:

未分类

HAProxy常用配置介绍,ACL详解

一、HAProxy简介

HAProxy 是一款高性能TCP/HTTP 反向代理负载均衡服务器,具有如下功能:

  • 根据静态分配的cookies完成HTTP请求转发
  • 在多个服务器间实现负载均衡,并且根据HTTP cookies 实现会话粘性
  • 主备服务器切换
  • 接受访问特定端口实现服务监控
  • 实现平滑关闭服务,不中断已建立连接的请求响应,拒绝新的请求
  • 在请求或响应HTTP报文中添加,修改,或删除首部信息
  • 根据正则规则阻断请求
  • 提供带有用户认证机制的服务状态报告页面

HAProxy特别适用于那些负载特大的web站点,这些站点通常又需要会话保持或七层处理。HAProxy运行在时下的硬件上,完全可以支持数以万计的 并发连接。并且它的运行模式使得它可以很简单安全的整合进您当前的架构中, 同时可以保护你的web服务器不被暴露到网络上。

HAProxy 实现了一种事件驱动、单一进程模型,此模型支持非常大的并发连接数。多进程或多线程模型受内存限制 、系统调度器限制以及无处不在的锁限制,很少能处理数千并发连接。事件驱动模型因为在有更好的资源和时间管理的用户端(User-Space) 实现所有这些任务,所以没有这些问题。此模型的弊端是,在多核系统上,这些程序通常扩展性较差。这就是为什么他们必须进行优化以 使每个CPU时间片(Cycle)做更多的工作。

HAProxy实际工作中,它占用用户空间时间要比内核运行时间少20倍,所以对系统参数调优是十分必要的一项工作。

另外衡量一个负载均衡服务器主要考量三个指标

  • session rate
    此项指标非常重要,它决定了一个load balancer 能不能分发所有接受的请求。这项指标通常是由CPU性能决定。测量指标的大小跟传输的每个对象的大小有关,通常用空对象来测试,Session rates 在 100,000 sessions/s 左右,使用 Xeon E5 在 2014测试。

  • session concurrency
    该指标与前一指标相关联。这一指标与服务器内存和系统可以处理的文件描述符数量有关。 通常每个session占用34KB,即大概3W个session占用1GB内存空间,实际上,socket buffer也会占用内存空间,2W个session socket占用1GB内存。

  • data forwarding rate
    这一指标与 session rate 相对立,它的衡量单位通常是 Megabytes/s (MB/s), 或者 Gigabits/s (Gbps)。传输较大的对象有利于该指标的提升,因为较大的对象传输可以减少session建立和关闭浪费的时间。而测量session rate 则在传输小对象时有利于指标提升。haproxy 在2014年使用 Xeon E5 测试成绩为40 Gbps。

二、HAProxy程序环境

本文环境:CentOS7.2 haproxy 1.5 通过yum 安装

程序环境:
    配置文件:/etc/haproxy/haproxy.cfg
        Unit File: haproxy.service
        主程序:/usr/sbin/haproxy

配置文件:
    global:全局配置段
        进程及安全配置相关的参数
        性能调整相关的参数
        Debug相关的参数
    proxies:代理配置段
        defaults:为frontend, backend以及listen提供默认配置;
        frontend:前端,相当于Nginx中的server{ ... };
        backend:后端,相当于nginx中的upstream { ...  };
        listen:前后端的直接组合;
    **关于前端与后端的关系:一个前端可以指向多个后端;同时一个后端可以被多个调用。

三、HAProxy配置详解

3.1 global配置段

3.1.1 进程相关配置

  • 定义日志系统相关属性
log <address> [len <length>] <facility> [max level [min level]]

harpoxy 将日志发送到指定的rsyslog服务器,在本地记录也要开启rsyslog服务;
全局端最多可配置两个log 服务器;
< address> :日志服务器地址
[ len ] 指定记录的日志最大长度

  • 定义运行用户,所属组

username
group groupname

  • 运行方式

意味着后台守护进程

3.1.2 参数调优

    maxconn <number>:设定单haproxy进程的最大并发连接数;
    maxconnrate <number>:设定单haproxy进程每秒接受的连接数;
    maxsslconn <number>:设定单haproxy进程的ssl连接最大并发连接数;
    maxsslrate <number>:单haproxy进程的ssl连接的创建速率上限;
    spread-checks <0..50, in percent>:避免对于后端检测同时并发造成
    的问题,设置错开时间比,范围0到50,一般设置2-5较好。

3.1.3 用户列表

用于对haproxy 状态监控页面的用户认证。至少要定义一个用户列表并且添加一个用户
密码可以加密或明文。

Example:

userlist L1
  group G1 users tiger,scott
  group G2 users xdb,scott

  user tiger password $6$k6y3o.eP$JlKqe4(...)xHSwRv6J.C0/D7cV91
  user scott insecure-password elgato
  user xdb insecure-password hello

userlist L2
  group G1
  group G2

  user tiger password $6$k6y3o.eP$JlKBx(...)xHSwRv6J.C0/D7cV91 groups G1
  user scott insecure-password elgato groups G1,G2
  user xdb insecure-password hello groups G2

3.2 proxy配置段

这部分配置在下列定义区域下使用

        - defaults  < name >
        - frontend < name >
        - backend  < name >
        - listen   < name >
  • “defaults” 区域定义了frontend,backend,listen 的默认参数
  • “frontend“ 区域描述了接收客户端请求的监听配置
  • ”backend“ 区域描述接受请求处理的后端服务器配置
  • ”listen“ 区域描述一组前端和后端直接一对一绑定的组配置

HAProxy 配置的关键字与区域限制特性,即有些关键字在某个区域不可以使用
下面开始讲解关键字的用法

3.2.1 常用配置指令

bind [<address>]:<port_range> [, ...] [param*]

仅在frontend和listen区域使用。定义服务监听端口地址等参数
[ param* ] 参数根据系统而定,一般不需要指定
example:

bind :80     #监听本机所有IP的80端口
bind *:80    #监听本机所有IP的80端口
bind 192.168.12.1:8080,10.1.0.12:8090
mode {tcp|http|health}

tcp:基于layer4实现代理,可代理大多数基于tcp的应用层协议,例如ssh/mysql/pgsql等;
http:客户端的http请求会被深度解析;
health:工作为健康状态检查响应模式,当请求到达时仅回应“OK”即断开连接;

balance <algorithm> [ <arguments> ]
balance url_param <param> [check_post]

在backend区域定义调度算法
< algorithm > 如下:

  • roundrobin
带有权重的轮询调度算法;
server后面使用weight来定义权重;
动态算法:支持权重的运行时调整,支持慢启动(缓慢接收大量请求在刚启动时);仅支持最大4095个后端活动主机
  • static-rr
    静态的roundrobin算法;

不支持权重的运行时调整及慢启动;但后端主机数量无限制;

  • leastconn
    带权重的最少连接分配动态算法;

适用长连接应用协议,如ssh等

  • first
    第一优先算法;

如果第一个服务端可接受请求则总是把连接分配给它,直到第一个服务端处于繁忙,分配给下一个,顺序按服务端的数字ID从小到大排列

  • source
    源IP hash 算法;

该算法保证在后端服务器组没有减少或增加的情况下,能将来自同一客户端IP的请求分配至同一个服务端;
该算法适合在无法使用cookie插入的TCP模式下使用
动态算法或静态算法取决于hash-type;

  • uri
    uri hash 算法;
    该算法hash uri 的查询标记的左侧部分,或者指定whole 参数时hash全部uri;
    该算法保证访问同一uri的请求分配至同一服务端,适用于后端为缓存服务器的情况,以提高缓存命中率;
    动态算法或静态算法取决于hash-type;
    另外:该算法支持追加参数[ < arguments > ]:
    (1) whole :hash完整uri
    (2) len number:hash指定uri的长度
    (3) depth nubmer:hash指定目录深度,每个”/”代表一个深度

  • uri_param

param hash 算法;

对用户请求的url中的< param >部分中的指定的参数的值(uri中”=”部分)作hash计算;
该算法适用于有用户识别参数的uri ,它保证同一user id 的请求分配至同一服务端;
若果check_post 标识启用,则在uri中没有找到”?”参数时,对HTTP Post 请求实体查找参数声明;
动态算法或静态算法取决于hash-type;

Example:

balance url_param userid
balance url_param session_id check_post 64
  • hdr(< name >)
    HTTP 首部字段hash算法;

指定的http首部将会被取出做hash计算。如果没有值,则降至轮询调度;
动态算法或静态算法取决于hash-type;

hash_type < method >

在balance 指令中选定与hash 有关的算法,都会受此影响。
默认采取的方法为map-based
< method > 如下:

  • map-based:取模法,hash数据结构是静态数组;
    该hash是静态的,不支持在线调整权重,不支持慢启动;

该算法调度平滑,后端服务器能够均匀承受负载;
缺点也是明显的:当服务器的总权重发生变化时,即有服务器上线或下线,都会导致调度结果整体改变。如果想避免此种情况应采用consistent 方法;

  • consistent:一致性哈希,哈希的数据结构是“树”;
    该hash是动态的,支持在线调整权重,支持慢启动

每一个server 会在”树”中出现多次, 在树中查找hash key,并选择最近的server;
该方法的优点在于,当服务器的总权重发生变化时,对调度结果影响是局部的,不会引起大的变动。所以十分适合缓存服务器;
缺点:该算法不够平滑,很容易导致后端服务器负载不均衡。所以很有必要对服务器的权重以或者服务器ID进行调整;
为保持均匀负载,应该保证所有服务器ID保持一致;

server <name> <address>[:[port]] [param*]
default-server [param*]

server用于在backend和listen中定义一个主机;
default-server 用于设定server的默认参数;

[param*] 如下:

  • weight < weight >:当前server的权重;
  • id < number > :设定server ID
  • cookie < value >:为当前server指定其cookie值,此值会在收到请求报文时进行检测,其功能在于实现基于cookie会话保持;
  • check:对当前server进行健康状态检测;
    inter < delay >:时间间隔;
    rise < count >:判定为“健康”状态需要检测的次数,默认2;
    fall < count >:判定为“不健康”状态需要检测的次数,默认3;
    addr <ipv4|ipv6>:健康状态检测时使用的地址;
    port < port >:健康状态检测时使用的端口;
    注意:默认为传输层检测,即探测端口是否能响应;需要执行应用层检测,则需要httpchk, smtpchk, mysql-check, pgsql-check, ssl-hello-chk;
  • maxconn :当前server的最大并发连接数;
  • maxqueue :当前server的等待队列的最大长度;
  • disabled:将主机标记为不可用;
  • redir
    :将发往当前server的所有请求GET和HEAD类的请求均重定向至指定的URL;
Examples :
server first  10.1.1.1:1080 id 3 cookie first  check inter 1000 maxconn 10000 maxqueue 2000
server second 10.1.1.2:1080 id 4 cookie second check inter 1000
option httpchk
option httpchk <uri>
option httpchk <method> <uri>
option httpchk <method> <uri> <version>    

基于http协议作7层健康状态检测机制,默认是基于tcp层进行检测;
TCP 模式也可以使用该检测机制
< method > < uri > < version >:请求报文的超始行;
method 默认方法为 OPTIONS;返回状态码2XX,3XX意味成功;

Examples :
# Relay HTTPS traffic to Apache instance and check service availability
# using HTTP request "OPTIONS * HTTP/1.1" on port 80.
backend https_relay
    mode tcp
    option httpchk OPTIONS /index.html HTTP/1.1rnHost: www
    server apache1 192.168.1.1:443 check port 80
http-check expect [!] <match> <pattern>

定义检测有效期望值;
! 表示认定的错误值;< match > 可取值为:

  • status < string >
  • rstatus < regex > 正则方式
  • string < string >
  • rstring < regex >
Examples :
# only accept status 200 as valid
http-check expect status 200

# consider SQL errors as errors
http-check expect ! string SQL Error

# consider status 5xx only as errors
http-check expect ! rstatus ^5

# check that we have a correct hexadecimal tag before /html
http-check expect rstring <!--tag:[0-9a-f]*</html>
cookie <name> [ rewrite | insert | prefix ] [ indirect ] [ nocache ] [ postonly ] [ preserve ] [ httponly ] [ secure ] [ domain <domain> ]* [ maxidle <idle> ] [ maxlife <life> ]

启用基于cookie的会话黏性,要结合server指定的cookie参数一起实现;
常用形式:cookie WEBSRV insert nocache indirect

Example:
backend websrvs
balance     roundrobin
cookie WEBSRV insert nocache indirect
server      web1 10.1.0.68:80 check weight 2 maxconn 5000 cookie web1
server      web2 10.1.0.69:80 check weight 1 maxconn 3000 cookie web2
default_backend <backend>

当use_backend 的使用规则没有被匹配时,由default_backend 指定默认服务器组;
关于use_backend 使用后续会在acl 章节中讲解;

3.2.2 log 相关

为frontend或backend定义日志记录机制;

log global  :使用全局定义的日志记录方式
log <address> [len <length>] <facility> [<level> [<minlevel>]]:自定义
no log :不记录
capture request header <name> len <length>
-->记录请求报文中的指定的首部的值于日志中;len用于指定要记录的信息的长度;
capture response header <name> len <length>
-->记录响应报文中的指定的首部的值于日志中;len用于指定要记录的信息的长度;
示例:
    capture request header Referer len 30

3.2.3 自定义错误页面

- errorfile <code> <file>

< code > 指定HTTP返回的状态码。200, 400, 403, 408, 500, 502, 503, and 504 可使用;
< file > 指定一个文件代替HTTP响应;
Example:errorfile 503 /etc/haproxy/errorfiles/503sorry.http

- errorloc <code> <url>
- errorloc302 <code> <url>

发生错误时由haproxy重定向至指定url,以上两个命令等同,响应状态码为302
Example:errorloc 503 http://www.mydomain.com/index…

- errorloc303 <code> <url>

响应状态码为303,表示以GET方法重新请求页面

3.2.4 修改请求或响应报文首部

option forwardfor [ except <network> ] [ header <name> ] [ if-none ]

HAProxy把请求报文发往后端主机之前在请求报文添加“X-Forwared-For”首部
目的为使后端服务器可记录发出请求客户端的IP地址
[ except < network> ] :选择排除的网络地址
[ header < name> ] :不使用X-Forwared-For,自定义名称
[ if-none ]:有时请求原来带有该字段,此时不再更改
Example:option forwardfor if-none

reqadd  <string> [{if | unless} <cond>]
rspadd <string> [{if | unless} <cond>]

在HTTP请求或响应首部内容尾部添加值
Example:rspadd X-Via: HAProxy/1.5

reqdel  <search> [{if | unless} <cond>]
reqidel <search> [{if | unless} <cond>]  (不区分大小写)        

删除HTTP请求中正则匹配的所有首部

rspdel  <search> [{if | unless} <cond>]
rspidel <search> [{if | unless} <cond>]  (不区分大小写)

删除HTTP响应中正则匹配的所有首部。属于安全加强策略,删除一些服务器版本信息,防止针对攻击
Example:rspidel Server.*

3.2.5 超时时长设定

timeout client <timeout>

设定客户端最大非活动时长, 默认单位是ms;最好与timeout server一致

timeout server <timeout>

设定服务端最大非活动时长, 默认单位是ms;

timeout connect <timeout>

设定最大与服务端建立连接的时长

timeout http-keep-alive <timeout>

设定最大等待新请求的空闲时长,默认单位为ms;

timeout client-fin <timeout>

在客户端侧设定半关闭连接非活动超时

timeout server-fin <timeout>

在服务端侧设定半关闭连接非活动超时
Example:

defaults http
timeout connect 5s
timeout client 30s
timeout server 30s
timeout client-fin 10s
timeout http-keep-alive 500

四、使用ACLs和获取样本

Haproxy 能够从请求报文,响应报文,从客户端或者服务端信息,从表,环境信息等等中提取数据。提取这样的数据的动作我们称之为获取样本。进行检索时,这些样本可以用来实现各种目的,比如作为粘滞表的键,最常用的用途是,根据预定义的模式来进行匹配。
访问控制列表(ACL)提供一个灵活方案进行内容切换,或者在从请求,响应,任何环境状态中提取的数据基础之上做出决策。控制列表的原则很简单:

  • 从数据流,表,环境中提取数据样本
  • 对提取的样本可选地应用格式转换
  • 对一个样本应用一个或多个模式匹配
  • 当模式匹配样本时才执行动作

执行的动作通常是阻断请求,选择一个后端服务器或者添加一个HTTP首部
需要提醒的是,获取的样本数据不光可以使用在acl中,也可以使用别处,例如记录log中
定义ACL的语法为:

acl <aclname> <criterion> [flags] [operator] [<value>] ...

这样一条语句建立了一个acl 测试;
这些测试应用在请求或响应中被”标准”< criterion > 部分所指定的内容,而且可以指定[ flags] 进行特性调整,有些< criterion > 支持操作符[operator] 进行运算,同时一些转换格式的关键字可以跟在< criterion >后面,使用” , “隔开。而值[< value >] 要求被
< criterion > 所支持的数据形式,多个值使用空格分隔。
< criterion > 通常是指获取样本方法的名称。使用一个获取样本方法,暗含着其输出样本的类型,类型是以下列出的一种:

  • boolean
  • integer (signed or unsigned)
  • IPv4 or IPv6 address
  • string
  • data block

ACL引擎匹配数据使用的模式类型如下:

  • boolean
  • integer or integer range
  • IP address / network
  • string (exact, substring, suffix, prefix, subdir, domain)
  • regular expression
  • hex block

ACL flags 可用列表如下:

  • -i : 忽略大小写
  • -f filename : 从文件中载入模式
  • -m method : 指定模式匹配方法
  • -n : 禁止DNS解析
  • -M : -f 载入的文件作为映射文件使用
  • -u : 强制ACL的名称唯一
  • — : 强制结束flag结束,避免了字符串中含有的- 引起混淆

其中flag中的 -m 选项可使用的模式匹配方法如下,需要说明的是有些方法已被默认指定无需声明,例如int,ip

  • “found” : 只是用来探测数据流中是否存在指定数据,不进行任何比较
  • “bool” : 检查结果返回布尔值。匹配没有模式,可以匹配布尔值或整数,不匹配0和false,其他值可以匹配
  • “int” : 匹配整数类型数据;可以处理整数和布尔值类型样本,0代表false,1代表true
  • “ip” : 匹配IPv4,IPv6地址类型数据。该模式仅被IP地址兼容,不需要特别指定
  • “bin” : 匹配二进制数据
  • “len” : 匹配样本的长度的整数值
  • “str” : 精确匹配,根据字符串匹配文本
  • “sub” : 子串匹配,匹配文本是否包含子串
  • “reg” : 正则匹配,根据正则表达式列表匹配文本
  • “beg” : 前缀匹配,检查文本是否以指定字符串开头
  • “end” : 后缀匹配,检查文本是否以指定字符串结尾
  • “dir” : 子目录匹配,检查部分文本中以” / “作为分隔符的内容是否含有指定字符串
  • “dom” : 域匹配。检查部分文本中以” . “作为分隔符的内容是否含有指定字符串

如果获取样本值为整数,数值比较符可使用,:

eq : true if the tested value equals at least one value
ge : true if the tested value is greater than or equal to at least one value
gt : true if the tested value is greater than at least one value
le : true if the tested value is less than or equal to at least one value
lt : true if the tested value is less than at least one value

想必前面一堆理论性的论述已经把大家搞的晕头转向,下面结合获取样本方法和访问控制动作指令具体阐述ACL使用方法

先介绍控制动作指令

  • layer 4 传输层控制指令
tcp-request connection <action> [{if | unless} <condition>]

对tcp请求控制指令
< condition > 即为ACL定义的访问控制列表
< action > 常用值有 “accept”, “reject”

  • layer 7 应用层控制指令
#阻断符合ACL的访问请求
block { if | unless } <condition> 
#http请求的控制指令
http-request { allow | deny}  [ { if | unless } <condition> ]
  • 后端主机调用
#根据条件来调用指定后端
use_backend <backend> [{if | unless} <condition>]
  • 由ACL定义的多个< condition > 组成联合条件,逻辑符为
    • and (默认操作符,可省略)
    • or (或者使用 “||”)
    • ! (取反)

4.1 获取内部状态样本

# 与后端建立会话速率,每秒钟建立的新会话
be_sess_rate([<backend>]) : integer

Example :

# 某后端被请求过于繁忙,则重定向至错误页
    mode http
    acl being_scanned be_sess_rate gt 100
    redirect location /denied.html if being_scanned

4.2 获取layer 4 样本

在传输层获取样本,通常是TCP/IP 协议的IP和端口,以及建立连接速率等等。而且此部分样本通常用于”tcp-request connection”指令中的规则之中。

        dst : ip             #目标地址
        dst_port : integer
        src : ip             #源地址
        src_port : integer

Example:

#阻断来自非指定IP的访问8080端口的请求
acl myhost src 10.1.0.200
acl myport dst_port 8080
tcp-request connection reject if !myhost myport        

4.3 获取layer 7 样本

/1

path : string

提取请求url的地址信息,从第一个”/”开始,不包含host,不包含参数
ACL 衍生,即包含了-m 选项中匹配模式方法 :

path : exact string match
path_beg : prefix match
path_dir : subdir match
path_dom : domain match
path_end : suffix match
path_len : length match
path_reg : regex match
path_sub : substring match

Example:

#请求资源为图片,则调用图片服务器后端
 acl picture path_end -i .jpg .png .gif
 use_backend server_pic if picture

/2

url : string

提取URL的全部内容,包含host和参数
ACL 衍生类似,不再列举

/3

req.hdr([<name>[,<occ>]]) : string

提取http请求的指定首部字段值,< occ >可指定出现的位置
ACL 衍生 :

  hdr([<name>[,<occ>]])     : exact string match
  hdr_beg([<name>[,<occ>]]) : prefix match
  hdr_dir([<name>[,<occ>]]) : subdir match
  hdr_dom([<name>[,<occ>]]) : domain match
  hdr_end([<name>[,<occ>]]) : suffix match
  hdr_len([<name>[,<occ>]]) : length match
  hdr_reg([<name>[,<occ>]]) : regex match
  hdr_sub([<name>[,<occ>]]) : substring match

Example:

#阻断火狐浏览器发送的请求
acl firefox hdr_reg(User-Agent)     -i      .*firefox.*
block if firefox

/4

method : integer + string

提取请求报文中的请求方法

Example:

#拒绝GET HEAD 方式之外的HTTP请求
acl valid_method method GET HEAD
http-request deny if ! valid_method

4.4 内建ACL

HAProxy有众多内建的ACLs,这些ACLs可直接调用,例如

  • LOCALHOST 匹配来自本地IP的连接,127.0.0.1/8
  • HTTP_1.1 匹配http版本1.1
  • METH_GET 匹配http请求GET或HEAD方法
  • TRUE
  • FALSE

Example:

#拒绝GET HEAD 方式之外的HTTP请求
http-request deny if ! METH_GET

传送门:官方1.5使用手册 http://cbonte.github.io/haproxy-dconv/1.5/configuration.html

— EOF —