服务Actuator监控端点分析

服务Actuator监控端点分析

1       背景

调研当业务端口的性能出现瓶颈,导致undertow的XNIO线程池打满后,新的接口请求无法正常处理只能等待。等待过程会导致健康检查无法获取到数据而timeout问题。

希望通过优化配置解决该问题

 

1766982319962.png

 

2       分析过程

2.1 分析timeout原因

健康检查接口/health 出现timeout的原因,是因为业务端口与监控端口默认保持一致,导致资源竞争出现/health接口无法响应而timeout问题。

 

在现代技术架构下生产环境通常采用Kubernate云原生架构,其中探针会通过服务的端口暴露的/health接口进行周期性的健康检查,当/health接口无法正常返回健康状态并超过一定的频次时,Kubenates会认为服务出现异常而强制kill Pod。

 

这个策略在生产环境则表现为服务集体雪崩,出现致命的错误。

 

2.2 Actuator端口与业务端口一致对比

 

Actuator端口

优点

缺点

不特殊设置management.server.port,使用与主服务相同端口

       部署简单,无需额外网络配置

       减少开放端口数量,降低防火墙复杂度

       天然继承主服务的认证/授权体系

       监控流量与业务流量统一管理

       安全风险:暴露监控端点可能增加攻击面

       资源竞争:监控请求可能影响业务性能

       无法单独做网络隔离策略

       监控端点故障可能连带影响主服务

actuator使用独立端口

       安全性:可以完全隔离监控端点(内网访问/VPC访问)

       资源隔离:避免监控请求影响业务性能

       灵活管控:可单独配置TLS、限流、ACL等策略

       故障隔离:监控组件问题不影响主服务

       增加运维复杂度(需管理额外端口)

       需要额外的安全配置(跨端口认证)

       可能增加基础设施成本(LB配置等)

 

actuator监控独立端口配置方式:

management:
  server:
    port: 8081

 

2.3 将actuator监控端口独立后模拟业务端口阻塞

验证业务端口和监控端口独立后的情况。将监控端口配置为固定端口(在dev、test、prod环境将通过环境变量固定8000端口)本地运行还是与业务接口一致。

 

-Dmanagement.server.port=8000

1766982474811.png

在springbootadmin监控中,服务注册的监控端口更变为8000,业务端口8113端口已经隔离。

 

在线程dump监控中,XNIO-1XNIO-2 线程池,XNIO-1按照CPU*8 配置,而XNIO-2 按照固定5个工作线程配置(监控线程池的请求频率一般不会突增)

2.3.1           监控端口隔离后进行压力测试

Jemeter启动200线程 ,业务XNIO线程池满,打到77QPS 无异常,其他请求排队等待处理。springbootadmin监控正常,CPU无异常,监控无明显卡顿。


1766982533486.png1766982561481.png

 

2.4 结论

这种业务端口和监控端口隔离虽然增加了复杂度,但能有效降低攻击面,是生产环境推荐的安全实践。将Actuator监控端口与业务端口隔离是一种安全最佳实践目前生产环境33个服务,逐步推进监控端口隔离。

 

2.5 端口隔离后的监控问题

1、新增加了一套XNIO的核心线程和工作线程,会占用一定的资源。但资源占用通常较小

 

 

2、线程阻塞如何告警通知?

 

 

3、独立端口后对运行环境带来那些影响?

         Prometheus 是否采集acutator端口数据?

 

4、业务端口的线程池打满后不一定CPU负载高,这个时候服务健康检查是ok的,但是慢接口已经积压了,需要考虑扩容问题!

 

 

3       监控端口安全控制

监控端口独立后,目前还是无认证机制,在内网环境可访问,通过网关隔离。如果黑客攻击到服务内部,远程脚本攻击可能扫描到敏感接口。

这种隔离虽然增加了复杂度,但能有效降低攻击面,是生产环境推荐的安全实践。

4       监控端口改造工作

 

 

1、服务配置监控端口 8000

JAVA_OPTS 环境变量追加 -Dmanagement.server.port=8000

1766982591653.png

当全面覆盖后,可以在基础镜像中配置固定值,java命令后面追加 -Dmanagement.server.port=8000

 

2、k8s 健康检查改端口8000;

3、K8s shutdown hook 改端口为8000;

 

 

 

来源: 雨林博客(www.yl-blog.com)