springboot的actuator内置了/health的endpoint,很方便地规范了每个服务的健康状况的api,而且HealthIndicator可以自己去扩展,增加相关依赖服务的健康状态,非常灵活方便而且可扩展。

/health实例

{
"status": "UP",
"custom": {
"status": "UNKNOWN",
"custom": {
"status": "UNKNOWN",
"msg": "mock down to test aggregator"
}
},
"diskSpace": {
"status": "UP",
"total": 249779191808,
"free": 57925111808,
"threshold": 10485760
}
}

health的Status枚举

org.springframework.boot.actuate.health.Status.java

@JsonInclude(Include.NON_EMPTY)
public final class Status { /**
* {@link Status} indicating that the component or subsystem is in an unknown state.
*/
public static final Status UNKNOWN = new Status("UNKNOWN"); /**
* {@link Status} indicating that the component or subsystem is functioning as
* expected.
*/
public static final Status UP = new Status("UP"); /**
* {@link Status} indicating that the component or subsystem has suffered an
* unexpected failure.
*/
public static final Status DOWN = new Status("DOWN"); /**
* {@link Status} indicating that the component or subsystem has been taken out of
* service and should not be used.
*/
public static final Status OUT_OF_SERVICE = new Status("OUT_OF_SERVICE");

对多个Status的聚合

对于多个HealthIndicator的status,spring boot默认对其进行aggregrate,然后计算最顶层的status字段的值,而且对于status是DOWN或者是OUT_OF_SERVICE的,返回的http的状态码是503,这对于应用监控系统来说真是大大的贴心啊,再总结一下:

  • 自动聚合多个HealthIndicator的status
  • 对于status是DOWN或者是OUT_OF_SERVICE的,返回503

这样应用监控系统一来就无需去解析返回结果,直接根据http的状态码就可以判断了,非常方便,太省心了有没有。

看看AbstractHealthAggregator.java的抽象类,其中对状态的聚合是abstract的。

public abstract class AbstractHealthAggregator implements HealthAggregator {

    @Override
public final Health aggregate(Map<String, Health> healths) {
List<Status> statusCandidates = new ArrayList<Status>();
for (Map.Entry<String, Health> entry : healths.entrySet()) {
statusCandidates.add(entry.getValue().getStatus());
}
Status status = aggregateStatus(statusCandidates);
Map<String, Object> details = aggregateDetails(healths);
return new Health.Builder(status, details).build();
} /**
* Return the single 'aggregate' status that should be used from the specified
* candidates.
* @param candidates the candidates
* @return a single status
*/
protected abstract Status aggregateStatus(List<Status> candidates); /**
* Return the map of 'aggregate' details that should be used from the specified
* healths.
* @param healths the health instances to aggregate
* @return a map of details
* @since 1.3.1
*/
protected Map<String, Object> aggregateDetails(Map<String, Health> healths) {
return new LinkedHashMap<String, Object>(healths);
} }

自定义Status,以及对Status聚合逻辑的调整

重写参考了OrderedHealthAggregator类,增加了 GIT_WARNING

public class OrderedHealthAggregator extends AbstractHealthAggregator {

    private List<String> statusOrder;

    public static final Status GIT_WARNING = new Status("GIT_WARNING", "警告:config-server连不上gitlab,请及时处理.");

    /**
* Create a new {@link OrderedHealthAggregator} instance.
*/
public OrderedHealthAggregator() {
setStatusOrder(Status.DOWN, Status.OUT_OF_SERVICE, GIT_WARNING, Status.UP, Status.UNKNOWN);
} /**
* Set the ordering of the status.
* @param statusOrder an ordered list of the status
*/
public void setStatusOrder(Status... statusOrder) {
String[] order = new String[statusOrder.length];
for (int i = 0; i < statusOrder.length; i++) {
order[i] = statusOrder[i].getCode();
}
setStatusOrder(Arrays.asList(order));
} /**
* Set the ordering of the status.
* @param statusOrder an ordered list of the status codes
*/
public void setStatusOrder(List<String> statusOrder) {
Assert.notNull(statusOrder, "StatusOrder must not be null");
this.statusOrder = statusOrder;
} @Override
protected Status aggregateStatus(List<Status> candidates) {
// Only sort those status instances that we know about
List<Status> filteredCandidates = new ArrayList<Status>();
for (Status candidate : candidates) {
//只识别Status.DOWN, Status.OUT_OF_SERVICE, GIT_WARNING, Status.UP, Status.UNKNOWN几种状态
if (this.statusOrder.contains(candidate.getCode())) {
filteredCandidates.add(candidate);
}
}
// If no status is given return UNKNOWN
if (filteredCandidates.isEmpty()) {
return Status.UNKNOWN;
}
//对多个结果状态的排序,按照各个状态在statusOrder集合中的位置排序
Collections.sort(filteredCandidates, new StatusComparator(this.statusOrder)); //返回排在最上面的那个状态值
return filteredCandidates.get(0);
} /**
* {@link Comparator} used to order {@link Status}.
*/
private class StatusComparator implements Comparator<Status> { private final List<String> statusOrder; StatusComparator(List<String> statusOrder) {
this.statusOrder = statusOrder;
} @Override
public int compare(Status s1, Status s2) {
//对多个结果状态的排序,按照各个状态在statusOrder集合中的位置排序
int i1 = this.statusOrder.indexOf(s1.getCode());
int i2 = this.statusOrder.indexOf(s2.getCode());
return (i1 < i2 ? -1 : (i1 == i2 ? s1.getCode().compareTo(s2.getCode()) : 1));
} } }

即Status.DOWN, Status.OUT_OF_SERVICE, GIT_WARNING, Status.UP, Status.UNKNOWN优先级依次递减。status中一旦有出现DOWN的情况,整体的status就是DOWN,依次类推。

Springboot Actuator之五:Springboot中的HealthAggregator、新增自定义Status的更多相关文章

  1. Winform中实现ZedGraph新增自定义Y轴上下限、颜色、标题功能

    场景 Winform中实现ZedGraph的多条Y轴(附源码下载): https://blog.csdn.net/BADAO_LIUMANG_QIZHI/article/details/1001322 ...

  2. 5. SpringBoot —— Actuator简介

    Actuator是SpringBoot提供的用来帮助我们在将应用程序推向生产环境时对其进行监视和管理的工具集.使用Actuator最简单的方式,就是在pom文件中添加如下依赖: <depende ...

  3. SpringBoot actuator 应用监控。

    前言 : 今天在阅读 <SpringCloud微服务实战>一书时看到了SpringBoot actuator相关知识,并且自己也本地调试实践.觉得SpringBoot这一套监控还是挺有意思 ...

  4. springboot Actuator健康检查

    通过情况下,如我们想在系统中添加一个健康检查的接口,我们怎么做呢? 我们会新建一个类,或在已存在类的基础上添加检测接口. package com.crhms.medicareopinion; impo ...

  5. SpringBoot Actuator & SpringBoot Admin

    SpringBoot Actuator提供了很多监控和管理你的spring boot应用的HTTP或者JMX端点,并且你可以有选择地开启和关闭部分功能. 当你的spring boot应用中引入依赖之后 ...

  6. Springboot Actuator之八:actuator的执行原理

    本文接着<Springboot Actuator之七:actuator 中原生endpoint源码解析1>,前面主要分析了原生endpoint的作用. 现在着重了解actuator的执行原 ...

  7. SpringBoot Actuator监控【转】

    springboot actuator 监控 springboot1.5和springboot2.0 的actuator在启动日志上的差异就很大了. springboot1.5在启动时会打印很多/XX ...

  8. springboot actuator 配置安全

    springboot actuator监控是什么?类似php的phpinfor()函数,不过actuator更强大,可以查看的数据.状态更多.Actuator是Spring Boot提供的对应用系统的 ...

  9. SpringBoot Actuator — 埋点和监控

    项目中看到了有埋点监控.报表.日志分析,有点兴趣想慢慢捣鼓一下 1. 数据埋点 监控机器环境的性能和业务流程或逻辑等各项数据,并根据这些数据生成对应的指标,那么我们就称为数据埋点.比如我们想知道某个接 ...

随机推荐

  1. 配置WDA程序到NWBC

    NWBC是通过角色来做的权限管理,包括菜单项. 如果用户没有分配对应的,登陆后看到的东西很少,或者空白. 这里需要先将BC的个性化参数全部配齐,方便使用.BC最左上角,点击,设置,个性化设置. 如下几 ...

  2. centos6升级gcc版本

    初始版本: 下面是CentOS6.6将gcc升级至4.8.2的过程: 安装仓库: #安装仓库 wget http://people.centos.org/tru/devtools-2/devtools ...

  3. Transformer---BERT模型

    一.BERT介绍 论文地址:BERT: Pre-training of Deep Bidirectional Transformers for Language Understanding  BERT ...

  4. httprunner学习25-文件上传multipart/form-data

    前言 httprunner上传文件接口,其实跟requests上传文件的接口是一样的,之前在python接口系列里面有案例 python接口自动化16-multipart/form-data上传图片 ...

  5. amp加载速度比标准移动页面快85%

    6月13日,谷歌合作伙伴大会上Oliver Vidinovski先生(Google Global Head of eCommerce - CS/GCS) 释放了一个信息:amp加载速度比标准移动页面快 ...

  6. maven jar包冲突的发现与解决[工具篇]

    本文是我的第177篇文章. 关于jar冲突排查解决的问题,相信很多小伙伴也都知道有一些,无非就是两类:命令 or 工具. 命令方式比如: mvn dependency:tree 工具方式比如: Mav ...

  7. React的使用小规范----长期更新

    用this.state控制组件显示,用this.props控制页面业务数据,用this.other保存其他需要的属性,如计时器setInterval的id

  8. Windbg Watch(监视)窗口的使用

    在WinDbg中,可以使用“监视”窗口显示和更改全局和局部变量和寄存器信息. 您可以自定义此窗口以显示您正在跟踪的项..“监视”窗口可以显示所需的任何变量列表.这些变量可以包括来自任何函数的全局变量和 ...

  9. 研究下vc++的abort函数

    最近在调试几个问题时,发现跟abort函数有关,以前只是简单使用,现在却发现不简单,就多留意了下. 简介 abort中止当前进程并返回错误代码.异常终止一个进程.中止当前进程,返回一个错误代码.错误代 ...

  10. 5-STM32物联网开发WIFI(ESP8266)+GPRS(Air202)系统方案安全篇(配置MQTT的SSL证书,验证安全通信)

    4-STM32物联网开发WIFI(ESP8266)+GPRS(Air202)系统方案安全篇(为域名申请SSl证书) 前面的准备工作终于完了 复制这两个证书 放到云端MQTT的这个位置,其实放哪里都可以 ...