文章目录
- 1. 关系缘由
- 2. Actuator简介及简单使用
- 3. Endpoint和Actuator的关系
- 4. Endpoint和HasFeatures的关系
- 5. Endpoint和HasFeatures原理解析
- 5.1 Endpoint的实现原理
- 5.2 HasFeatures的实现原理
- 6. 个人闲谈
1. 关系缘由
我们经常可以在Springboot
中看到@Endpoint
注解,被该注解标注的类里面一般都会有@XXXOperation
注解,也可以在Springcloud
中看到带有Endpoint
字样的实现类和带有Features
等字样的实现类,初次看到总会觉得很疑惑,完全不知道这些类的作用以及相关的框架,但却很常见。这次我们便来捋一下各种带有Endpoint
、HasFeatures
和NamedFeature
这些类具体的作用以及和Actuator
的关系。
2. Actuator简介及简单使用
Actuator
是基于Springboot
体系开发的,其作用在于实时的监控程序,获取程序的运行数据,如获取健康检查、指标收集、程序bean运行情况及配置属性等信息。因此Actuator
的作用便是对外暴露获取程序信息的HTTP接口,可以对Actuator
进行扩展,从而实现实时监控的目的。下面是Actuator
的简介图:
想要引入Actuator
也非常简单,只需要配置以下maven配置即可:
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-actuator</artifactId>
<version>${springboot对应的版本}</version>
</dependency>
引入后配置需要加载哪些监听信息:
management:
endpoints:
web:
exposure:
include: '*'
上面的配置意为开放所有的HTTP接口,调用/actuator
接口即可查看具体有哪些接口开放,至于Actuator
有哪些接口、作用是什么及调用路径是什么这里便不一一介绍了。
3. Endpoint和Actuator的关系
前面说了Actuator
的主要作用便是开放HTTP接口供开发者查询程序的运行状态,而支持哪些HTTP接口便是由Endpoint
来决定的。Endpoint
一般指的是Springboot
的@Endpoint
注解,而被该注解标注的类名称一般都会带有Endpoint
的字样,该注解源码如下:
@Target(ElementType.TYPE)
@Retention(RetentionPolicy.RUNTIME)
@Documented
public @interface Endpoint {
/** Endpoint的唯一名称,该属性为开放的HTTP接口路径名称 */
String id() default "";
/** 是否默认打开,设置为false则需要手动配置打开 */
boolean enableByDefault() default true;
}
所以我们可以把@Endpoint
的功能近似理解成SpringMVC
中的@RequestMapping
注解,其仅仅是用来标注类,并定义HTTP接口的路径。所以当我们看到某个类被@Endpoint
标注了,我们就能知道这是Actuator
开放出去用来监听程序信息的HTTP接口。
那现在又有个问题,看@Endpoint
的代码我们可知这个注解只能标注在类上,那我开放出去的这个HTTP接口被调用了会具体应该调用哪个方法?这就涉及到另外一些必须搭配使用的三个注解@ReadOperation
、@WriteOperation
和@DeleteOperation
。
@Endpoint
一般都会前面三个注解当中的一个进行搭配使用,@Endpoint
用来定义HTTP接口的路径,而@XXXOperation
注解则用来定义接收请求的调用方法。搭配使用就做到了Actuator
对开发者开放监听系统层面HTTP接口的能力。其关系图如下:
至此,Actuator
和@Endpoint
、@ReadOperation
、@WriteOperation
、@DeleteOperation
四个注解的关系便讲到这里。
4. Endpoint和HasFeatures的关系
如果要说Endpoint
和HasFeatures
的关系,我们就需要先知道Springcloud
和Actuator
的关系。Actuator
是基于Springboot
开发的,而Springcloud
则是在Springboot
的基础上扩展了微服务相关的框架和功能,因此Springcloud
天然的支持使用Actuator
。
Springcloud
是面向于微服务的,因此注定了框架会十分的庞杂,想要不仔细看系统从而精确的掌握某个微服务使用的技术栈是不现实的问题。因此Springcloud
就需要一个机制来让开发者可以快速的了解程序使用的技术栈及其版本,而天然支持的Actuator
则是不二之选。
Springcloud
使用Actuator
管理对外暴露的HTTP接口,在此基础上又开发了一套由HasFeatures
、NamedFeature
和Feature
所组成的功能注册机制,需要对接进来的框架只需要往Spring
容器中注册HasFeatures
对象,Springcloud
便可以使用Actuator
暴露的接口返回程序具体使用了哪些框架。示意图如下:
所以HasFeatures
、NamedFeature
和Features
这一套是Springcloud
开放给其它框架用来注册自身的机制,再使用@Endpoint
注解结合Actuator
对外暴露HTTP接口,最终使开发者可以快速了解程序所使用的框架。
5. Endpoint和HasFeatures原理解析
对于@Endpoint
和HasFeatures
的原理解析我们分为两个大阶段:
- 解析
@Endpoint
的实现原理,这部分是基于Springboot
实现的; - 在
@Endpoint
实现原理基础上再去分析HasFeatures
的原理,这部分是Springcloud
新增的特性。
5.1 Endpoint的实现原理
先分析Actuator
原本最基础的@Endpoint
注解实现原理,我们也把这个实现原理分为4部分:
- 搜索并创建
@Endpoint
注解的bean对象; - 处理bean对象中被
@XXXOperation
注解的方法,并将其解析成WebOperation
对象; - 将获取到的
Endpoint
对象信息注册为Servlet的HTTP接口; - 调用时解析HTTP请求并调用到
WebOperation
对象中完成方法的调用与返回。
5.2 HasFeatures的实现原理
HasFeatures
是Springcloud
引入的新机制,其实现也非常简单,只需要各个框架使用HasFeatures
封装框架的核心类并注册到Spring
容器即可。Springcloud
会从Spring
容器中获取所有的HasFeatures
类并传递到FeaturesEndpoint
,调用HTTP接口时便转成Features
对象返回注册的功能特性。总的来说可以总结成三步:
- 框架使用
HasFeatures
封装核心类并注册到Spring
容器中; - 从
Spring
容器中获取所有的HasFeatures
并传递到FeaturesEndpoint
bean中; - 调用HTTP接口时将
HasFeatures
转成Features
对象并返回。
下图将以Feign框架为例:
6. 个人闲谈
这套实现单独拎出来分析确实是比较简单的,只要对Spring
容器和Servlet的注册实现机制稍微有所了解,就可以把整个来龙去脉理的比较清楚,因此便不对源码进行过多的分析了。
Springcloud
框架提供出了HasFeatures
功能特性注册机制,确实是一种非常好的思路,可以让开发者通过调用一次HTTP接口便可以得知系统所引入的功能特性。但这种基于Actuator
的机制还是不够便利,并且而不是所有的人都需要使用Actuator
来对程序进行监控,有一定规模的公司都有自己的监控系统,Actuator
反倒是有点鸡肋了。
因此个人认为,Springcloud
除了可以将HasFeatures
对接进Actuator
的规范和实现方式,还可以把HasFeatures
机制和Logger
结合,提供一个开关,系统启动时直接打印引入的功能特性,这样或许可以提升一定的独立性和便利性,使用面更广。