org.zodiac.actuate.sentinel.SentinelMonitorHealthIndicator Maven / Gradle / Ivy
The newest version!
package org.zodiac.actuate.sentinel;
import java.util.Collections;
import java.util.List;
import java.util.Map;
import org.springframework.beans.factory.support.DefaultListableBeanFactory;
import org.springframework.boot.actuate.health.AbstractHealthIndicator;
import org.springframework.boot.actuate.health.Health.Builder;
import org.springframework.boot.actuate.health.Status;
import org.zodiac.sdk.toolkit.util.collection.CollUtil;
import org.zodiac.sentinel.base.config.SentinelConfigInfo;
import com.alibaba.csp.sentinel.datasource.AbstractDataSource;
import com.alibaba.csp.sentinel.heartbeat.HeartbeatSenderProvider;
import com.alibaba.csp.sentinel.transport.HeartbeatSender;
import com.alibaba.csp.sentinel.transport.config.TransportConfig;
import com.alibaba.csp.sentinel.transport.endpoint.Endpoint;
public class SentinelMonitorHealthIndicator extends AbstractHealthIndicator {
public static final String ID = "sentinel-monitor";
private DefaultListableBeanFactory beanFactory;
private final SentinelConfigInfo sentinelConfigInfo;
public SentinelMonitorHealthIndicator(DefaultListableBeanFactory beanFactory,
SentinelConfigInfo sentinelConfigInfo) {
this.beanFactory = beanFactory;
this.sentinelConfigInfo = sentinelConfigInfo;
}
@Override
protected void doHealthCheck(Builder builder) throws Exception {
Map detailMap = CollUtil.map();
/*If sentinel isn't enabled, set the status up and set the enabled to false in detail.*/
if (!sentinelConfigInfo.isEnabled()) {
detailMap.put("enabled", false);
builder.up().withDetails(detailMap);
return;
}
detailMap.put("enabled", true);
/*Check health of Dashboard.*/
boolean dashboardUp = true;
List consoleServerList = TransportConfig.getConsoleServerList();
if (CollUtil.isEmptyColl(consoleServerList)) {
/*If Dashboard isn't configured, it's OK and mark the status of Dashboard with UNKNOWN.*/
detailMap.put("dashboard", new Status(Status.UNKNOWN.getCode(), "dashboard isn't configured"));
} else {
/*If Dashboard is configured, send a heartbeat message to it and check the result.*/
HeartbeatSender heartbeatSender = HeartbeatSenderProvider.getHeartbeatSender();
boolean result = heartbeatSender.sendHeartbeat();
if (result) {
detailMap.put("dashboard", Status.UP);
} else {
/*If failed to send heartbeat message, means that the Dashboard is DOWN.*/
dashboardUp = false;
detailMap.put("dashboard",
new Status(Status.UNKNOWN.getCode(), String.format("The dashboard servers [%s] one of them can't be connected", consoleServerList)));
}
}
/*Check health of DataSource.*/
boolean dataSourceUp = true;
Map dataSourceDetailMap = CollUtil.map();
detailMap.put("dataSource", dataSourceDetailMap);
/*
* Get all DataSources and each call loadConfig to check if it's OK.
* If no Exception thrown, it's OK.
*
* Note:
* Even if the dynamic config center is down, the loadConfig() might return successfully,
* e.g. for Nacos client, it might retrieve from the local cache).
* But in most circumstances it's okay
* */
Map dataSourceMap = beanFactory.getBeansOfType(AbstractDataSource.class);
for (Map.Entry dataSourceMapEntry : dataSourceMap.entrySet()) {
String dataSourceBeanName = dataSourceMapEntry.getKey();
AbstractDataSource dataSource = dataSourceMapEntry.getValue();
try {
dataSource.loadConfig();
dataSourceDetailMap.put(dataSourceBeanName, Status.UP);
} catch (Exception e) {
/*If one DataSource failed to loadConfig, means that the DataSource is DOWN.*/
dataSourceUp = false;
dataSourceDetailMap.put(dataSourceBeanName, new Status(Status.UNKNOWN.getCode(), e.getMessage()));
}
}
Map detailReultMap = Collections.unmodifiableMap(detailMap);
/*If Dashboard and DataSource are both OK, the health status is UP.*/
if (dashboardUp && dataSourceUp) {
builder.up().withDetails(detailReultMap);
}else {
builder.unknown().withDetails(detailReultMap);
}
}
}