Rails 如何给 Rails 做 health check

yakjuly · 2018年11月09日 · 最后由 southwolf 回复于 2018年12月05日 · 2084 次阅读

问题说明: 我们公司用 docker 部署 rails 项目,部署在 AWS 的 ECS 上,我们一般会设置一个 health check 的 API endpoint,让 AWS 监控这个 container 是健康的。然而最近内部另外一个项目会突然发起大规模请求到当前 rails 项目上。那么 puma 的进程和线程都去处理请求了,GET /health 就会超时。AWS 会认为这个 container 是不健康的,不但没有 scale up,创建新的 containers,反而把正在忙的 container 给 kill 了。

这里牵涉到一个问题: 如何判断一个 container 是正在忙碌,而不是真正死掉?

我假设的解决办法:

  1. AWS 目前只支持 http ping,可以在 container 内加 nginx,nginx 链接两个后端,一个后端是 puma 进程, 另外一个进程也是一个 http 程序,这个进程类似 god 负责检查 puma 的状态,如果 puma 是健康的,返回 /health 200,如果 puma 挂了,返回 503

  2. Hack 一下 puma,让 puma 永远空出一个 thread 去处理 /health 请求,这样不管如何忙碌,只要 puma 不挂掉,/health 就永远可以有返回内容。

不知道大家的公司是如何 scaling rails 程序的,如何做 health check?

k8s 也有健康检查 可以去参考下

这种情况应该更改的是监控的指标吧?比如说 x 分钟内 CPU、内存占用率之类的,通过这种指标来触发创建 container。 health check 和 load monitoring 应该分开

3楼 已删除

刚好看到 okcomputer,内置了比较常见的一些检查

coderliu 回复

我搞混了,scaling 是依赖别的指标,例如 CPU usage,requests count。但是 health check 是根据 ping 返回的状态来决定是不是要 kill container。

w7938940 回复

如果服务器非常忙,你 ping /okcomputer 也可能 timeout

yakjuly 回复

/health 会 timeout,说明此时该服务器的负载确实已经太高了。要么你的 timeout 太小了,要么就是触发创建新 container 条件不够 “敏感”

yakjuly 回复

那这时候服务是不是就可以被认为"不健康"了

yakjuly 回复

这个时候要加服务器了

我们目前也使用 AWS

scaling 使用的是 Auto Scaling,当 CPU 或者内存超过一定量的时候,就自动启动新的 EC2 Instance

health check 用的 NewRelic Infrastructure 来监视 nginx,unicorn 等进程,发现异常后发送到 slack

如果只是一时的大量请求,仅仅扩展 web server 就可以解决的话,用 Auto Scaling 应该可以解决问题

AWS 的 health check 没实际用过,看了下文档,好像支持任意的 command,可以换成监视 pumma 的进程挂没挂 https://docs.aws.amazon.com/AmazonECS/latest/APIReference/API_HealthCheck.html

42thcoder 回复

服务是不健康,需要 scale up。但是 container 是在工作的,只是比较忙而已,不应该 kill 掉忙的 container。

建议调整 health check 的 timeout,和业务请求的 timeout 匹配。

我们有几个线上的 rails/grape 项目用了 okcomputer, 有时即使负载并不高 (2k rpm) 也偶尔会有超时问题。要小心。

需要 登录 后方可回复, 如果你还没有账号请点击这里 注册