php fpm tomcat,haproxy中检测php-fpm或tomcat健康状态

一、问题

haproxy的server health check默认方法是尝试与backend服务器建立一个TCP连接。

如果指定了"option

httpchk"参数的话,则在TCP连接以后会发送给backend服务器一个HTTP请求。

如果backend返回2xx或3xx的响应,则认为backend服务器活着。

如果返回其他响应码则认为backend已经失败,从而会从负载中摘除。

但是对于nginx+php-fpm、nginx+tomcat这类的应用,haproxy默认的方法就不能很好的满足需求。

因为nginx负责静态内容部分,php-fpm或tomcat则负责动态部分(业务逻辑)。

当php-fpm或tomcat出现问题的时候,如果nginx是正常的(绝大部分时候都是如此),那么简单的HTTP请求会被nginx处理。所以haproxy认为backend一直是正常的,会持续分配连接给它,但事实上该backend已经不能正常服务了。

这种场景下我们希望通过判断backend上的php-fpm或tomcat的状态来决定是否将其从负载中摘除。

二、"option httpchk"

在haproxy的官方文档中是这样描述"option httpchk"

option httpchk method uri version

methodis

the optional HTTP method used with the requests. When not

set,

the "OPTIONS" method is used,

as it generally requires low server

processing and is easy to

filter out from the logs. Any method

may be used, though it is not

recommended to invent non-standard

ones.

uriis the URI referenced in the HTTP

requests. It defaults to " / "

which is accessible by

default on almost any server, but may be

changed to any other URI.

Query strings are permitted.

versionis the optional HTTP version string. It

defaults to "HTTP/1.0"

but some servers might behave

incorrectly in HTTP 1.0, so turning

it to HTTP/1.1 may sometimes

help. Note that the Host field is

mandatory in HTTP/1.1, and as

a trick, it is possible to pass it

after "\r\n" following the

version string.

其中的默认方法是"OPTIONS",默认URL是"/",默认Version是"HTTP/1.0"

作为后端检测,我们希望尽量少的影响backend上的正常服务,且传输数据量越少越好。

所以我们选择的尽量选择OPTIONS,GET,HEAD这三种。

我们来补充一下HTTP方法的相关背景知识:

按照RFC2616的排序,HTTP的方法包括:OPTIONS,GET,HEAD,POST,PUT,DELETE,TRACE

OPTIONS

使用该方法来获取资源支持的HTTP方法列表,或者ping服务器。

请求:只有header没有body。

响应:默认只有header,但是也可以在body中添加内容,比如描述性文字

示例:

# 测试对应资源所支持的方法

OPTIONS /test-options

HTTP/1.1

Host: localhost

# 响应

HTTP/1.1 204 No

Content

Allow: GET, POST,

OPTIONS

# ping服务器

OPTIONS * HTTP/1.1

Host: localhost

# 响应

HTTP/1.1 204 No

Content

安全:是

幂等:是

显然,它就是一个纯粹的信息读取的操作,不改变资源的状态,同时保证幂等性。

GET

该方法用以获取资源的表述。

请求:只有header,没有body。

响应:对应请求URI的资源表述,通常带有body。

响应header中的Content-Type,Content-Length,Content-Language,Last-Modified,ETag等应该和响应body的表述一致。

# 请求

GET /hello

HTTP/1.1

Host: localhost

# 响应

HTTP/1.1 200 OK

Content-Type: application/xml;

charset=UTF-8

Content-Length: 21

#

此处为空行,由于高亮插件原因,特此注明

tester

安全:是

幂等:是

简单的资源信息读取,不对资源状态造成影响,保证幂等性。

HEAD

使用该方法可以获取与GET响应相同的header,但是响应中没有任何body。

请求:只有header,没有body。

响应:只有header,没有body。服务器不能添加body。

# 请求

GET /hello

HTTP/1.1

Host: localhost

# 响应

HTTP/1.1 200 OK

Content-Type: application/xml;

charset=UTF-8

Content-Length: 21

安全:是

幂等:是

简单的资源信息读取,不对资源状态造成影响,保证幂等性。

三、具体实现

3.1 在backend的nginx配置中加入health check的URL

location = /health_check.php {

access_log off;

fastcgi_pass

127.0.0.1:9000;

fastcgi_index

index.php;

include

/etc/nginx/fastcgi_params;

}

3.2

在backend编写health_check.php(或.jsp),只需要简单的一个输出即可

# vi health_check.php

#< ?php echo "I'm healthy"; ? >

# vi

health_check.jsp

#< %out.print("I'm healthy");% >

3.3 在haproxy上配置option httpchk

backend appservers

mode http

option httpchk HEAD

/health_check.php HTTP/1.1\r\nHost:\ example.com

server web1 x.x.x.x:80

weight 5 check inter 2000

server web2 x.x.x.x:80

weight 5 check inter 2000

server web3 x.x.x.x:80

weight 5 check inter 2000

我们来解释一下这一行:

option httpchk HEAD /health_check.php HTTP/1.1\r\nHost:\

example.com

使用"HEAD"方法发送HTTP请求

"URI"是/health_check.php

"HTTP

version"使用HTTP/1.1,并且设置了主机头"example.com",这是HTTP/1.1强制要求的

这样就可以实现我们的目的啦!

参考文档:

http://iamseanmurphy.com/a-better-haproxy-health-check-for-dynamic-websites/

http://www.w3.org/Protocols/rfc2616/rfc2616-sec9.html

https://serversforhackers.com/load-balancing-with-haproxy

http://blog.lucode.net/protocol/http-method-tutorial.html

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值