基于Spring Boot Actuator监控美团API调用延迟与错误率的自定义指标暴露
在微服务架构中,对外部第三方服务(如美团开放平台API)的调用质量直接影响系统稳定性。为实时掌握调用延迟、失败率等关键指标,可借助Spring Boot Actuator结合Micrometer实现自定义指标采集与暴露。本文将展示如何在baodanbao.com.cn.*包结构下,通过拦截器与MeterRegistry埋点,动态监控美团API的调用性能。
1. 引入依赖与Actuator配置
首先,在pom.xml中引入必要依赖:
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-actuator</artifactId>
</dependency>
<dependency>
<groupId>io.micrometer</groupId>
<artifactId>micrometer-core</artifactId>
</dependency>
在application.yml中启用指标端点:
management:
endpoints:
web:
exposure:
include: health,info,metrics,prometheus
endpoint:
metrics:
enabled: true
prometheus:
enabled: true
metrics:
export:
prometheus:
enabled: true

2. 定义美团API调用封装类
创建统一调用入口,便于埋点:
package baodanbao.com.cn.service.meituan;
import org.springframework.stereotype.Service;
import org.springframework.web.client.RestTemplate;
@Service
public class MeituanApiClient {
private final RestTemplate restTemplate;
public MeituanApiClient(RestTemplate restTemplate) {
this.restTemplate = restTemplate;
}
public String callMeituanApi(String endpoint) {
return restTemplate.getForObject("https://openapi.meituan.com" + endpoint, String.class);
}
}
3. 自定义指标注册与记录
使用Micrometer的Timer和Counter分别记录延迟与错误次数:
package baodanbao.com.cn.metrics;
import io.micrometer.core.instrument.Counter;
import io.micrometer.core.instrument.MeterRegistry;
import io.micrometer.core.instrument.Timer;
import org.springframework.stereotype.Component;
import javax.annotation.PostConstruct;
@Component
public class MeituanApiMetrics {
private final MeterRegistry meterRegistry;
private Timer successTimer;
private Counter errorCounter;
public MeituanApiMetrics(MeterRegistry meterRegistry) {
this.meterRegistry = meterRegistry;
}
@PostConstruct
public void init() {
successTimer = Timer.builder("meituan.api.call.duration")
.description("美团API调用耗时(成功)")
.register(meterRegistry);
errorCounter = Counter.builder("meituan.api.call.error")
.description("美团API调用失败次数")
.register(meterRegistry);
}
public void recordSuccess(long nanos) {
successTimer.record(nanos, java.util.concurrent.TimeUnit.NANOSECONDS);
}
public void recordError() {
errorCounter.increment();
}
}
4. 在调用层注入指标逻辑
改造MeituanApiClient,嵌入指标记录:
package baodanbao.com.cn.service.meituan;
import baodanbao.com.cn.metrics.MeituanApiMetrics;
import org.springframework.stereotype.Service;
import org.springframework.web.client.RestClientException;
import org.springframework.web.client.RestTemplate;
@Service
public class MeituanApiClient {
private final RestTemplate restTemplate;
private final MeituanApiMetrics metrics;
public MeituanApiClient(RestTemplate restTemplate, MeituanApiMetrics metrics) {
this.restTemplate = restTemplate;
this.metrics = metrics;
}
public String callMeituanApi(String endpoint) {
long start = System.nanoTime();
try {
String result = restTemplate.getForObject("https://openapi.meituan.com" + endpoint, String.class);
metrics.recordSuccess(System.nanoTime() - start);
return result;
} catch (RestClientException e) {
metrics.recordError();
throw e;
}
}
}
5. 暴露聚合指标:成功率计算
虽然Micrometer不直接提供“成功率”指标,但可通过Prometheus查询表达式实现。不过,若需在/actuator/metrics中直接查看,可注册一个Gauge反映实时成功率(基于滑动窗口)。此处采用环形缓冲简化实现:
package baodanbao.com.cn.metrics;
import io.micrometer.core.instrument.Gauge;
import io.micrometer.core.instrument.MeterRegistry;
import org.springframework.stereotype.Component;
import javax.annotation.PostConstruct;
import java.util.concurrent.atomic.AtomicLong;
@Component
public class MeituanApiSuccessRate {
private final MeterRegistry meterRegistry;
private final AtomicLong totalCalls = new AtomicLong(0);
private final AtomicLong successCalls = new AtomicLong(0);
public MeituanApiSuccessRate(MeterRegistry meterRegistry) {
this.meterRegistry = meterRegistry;
}
@PostConstruct
public void registerGauge() {
Gauge.builder("meituan.api.success.rate", this, value -> {
long total = totalCalls.get();
if (total == 0) return 1.0;
return (double) successCalls.get() / total;
}).description("美团API调用成功率(近N次)")
.register(meterRegistry);
}
public void recordSuccess() {
totalCalls.incrementAndGet();
successCalls.incrementAndGet();
}
public void recordFailure() {
totalCalls.incrementAndGet();
}
}
并在MeituanApiClient中同步调用:
// 在try块末尾添加
metricsSuccessRate.recordSuccess();
// 在catch块中添加
metricsSuccessRate.recordFailure();
注意:上述简单计数器未做窗口清理,生产环境建议使用
CircularFifoQueue或Caffeine缓存带TTL的事件。
6. 验证指标暴露
启动应用后,访问:
GET /actuator/metrics/meituan.api.call.duration
GET /actuator/metrics/meituan.api.call.error
GET /actuator/metrics/meituan.api.success.rate
或通过Prometheus端点:
GET /actuator/prometheus
可看到类似如下指标:
meituan_api_call_duration_seconds_count{...} 120.0
meituan_api_call_error_total{...} 5.0
meituan_api_success_rate{...} 0.96
7. 扩展:按API路径细分指标
若需区分不同美团接口(如订单查询 vs 商户同步),可在指标标签中加入endpoint:
Timer.Sample sample = Timer.start(meterRegistry);
try {
// call API
sample.stop(Timer.builder("meituan.api.call.duration")
.tag("endpoint", endpoint)
.register(meterRegistry));
successRate.recordSuccess(endpoint);
} catch (Exception e) {
Counter.builder("meituan.api.call.error")
.tag("endpoint", endpoint)
.register(meterRegistry).increment();
successRate.recordFailure(endpoint);
throw e;
}
本文著作权归吃喝不愁app开发者团队,转载请注明出处!
1215

被折叠的 条评论
为什么被折叠?



