步骤如下: 1、首先新建2个model(LogInfo,MonitorInfo)
public class LogInfo implements Serializable {
private static final long serialVersionUID = 5289821541255302264L;
private String sql;
private String sqlParam;
private int maxParallel;
private long executeMillisTotal;
private long executeCount;
private long executeErrorCount;
private Date maxOccurTime;
private long histogram_0_1;
private long histogram_1_10;
private int histogram_100_1000;
private int histogram_1000_10000;
private int histogram_10000_100000;
private int histogram_100000_1000000;
private int histogram_1000000_more;
private String lastError;
private String lastErrorMessage;
private String lastErrorStackTrace;
private String lastErrorClass;
private Date lastErrorTime;
private int histogram_10_100;
private long executeMillisMax;
public String getSql() {
return sql;
}
public void setSql(String sql) {
this.sql = sql;
}
public String getSqlParam() {
return sqlParam;
}
public void setSqlParam(String sqlParam) {
this.sqlParam = sqlParam;
}
public int getMaxParallel() {
return maxParallel;
}
public void setMaxParallel(int maxParallel) {
this.maxParallel = maxParallel;
}
public long getExecuteMillisTotal() {
return executeMillisTotal;
}
public void setExecuteMillisTotal(long executeMillisTotal) {
this.executeMillisTotal = executeMillisTotal;
}
public long getExecuteCount() {
return executeCount;
}
public void setExecuteCount(long executeCount) {
this.executeCount = executeCount;
}
public long getExecuteErrorCount() {
return executeErrorCount;
}
public void setExecuteErrorCount(long executeErrorCount) {
this.executeErrorCount = executeErrorCount;
}
public Date getMaxOccurTime() {
return maxOccurTime;
}
public void setMaxOccurTime(Date maxOccurTime) {
this.maxOccurTime = maxOccurTime;
}
public long getHistogram_0_1() {
return histogram_0_1;
}
public void setHistogram_0_1(long histogram_0_1) {
this.histogram_0_1 = histogram_0_1;
}
public long getHistogram_1_10() {
return histogram_1_10;
}
public void setHistogram_1_10(long histogram_1_10) {
this.histogram_1_10 = histogram_1_10;
}
public int getHistogram_100_1000() {
return histogram_100_1000;
}
public void setHistogram_100_1000(int histogram_100_1000) {
this.histogram_100_1000 = histogram_100_1000;
}
public int getHistogram_1000_10000() {
return histogram_1000_10000;
}
public void setHistogram_1000_10000(int histogram_1000_10000) {
this.histogram_1000_10000 = histogram_1000_10000;
}
public int getHistogram_10000_100000() {
return histogram_10000_100000;
}
public void setHistogram_10000_100000(int histogram_10000_100000) {
this.histogram_10000_100000 = histogram_10000_100000;
}
public int getHistogram_100000_1000000() {
return histogram_100000_1000000;
}
public void setHistogram_100000_1000000(int histogram_100000_1000000) {
this.histogram_100000_1000000 = histogram_100000_1000000;
}
public int getHistogram_1000000_more() {
return histogram_1000000_more;
}
public void setHistogram_1000000_more(int histogram_1000000_more) {
this.histogram_1000000_more = histogram_1000000_more;
}
public String getLastError() {
return lastError;
}
public void setLastError(String lastError) {
this.lastError = lastError;
}
public String getLastErrorMessage() {
return lastErrorMessage;
}
public void setLastErrorMessage(String lastErrorMessage) {
this.lastErrorMessage = lastErrorMessage;
}
public String getLastErrorStackTrace() {
return lastErrorStackTrace;
}
public void setLastErrorStackTrace(String lastErrorStackTrace) {
this.lastErrorStackTrace = lastErrorStackTrace;
}
public String getLastErrorClass() {
return lastErrorClass;
}
public void setLastErrorClass(String lastErrorClass) {
this.lastErrorClass = lastErrorClass;
}
public Date getLastErrorTime() {
return lastErrorTime;
}
public void setLastErrorTime(Date lastErrorTime) {
this.lastErrorTime = lastErrorTime;
}
public int getHistogram_10_100() {
return histogram_10_100;
}
public void setHistogram_10_100(int histogram_10_100) {
this.histogram_10_100 = histogram_10_100;
}
public long getExecuteMillisMax() {
return executeMillisMax;
}
public void setExecuteMillisMax(long executeMillisMax) {
this.executeMillisMax = executeMillisMax;
}
}
public class MonitorInfo implements Serializable {
private static final long serialVersionUID = -2127636421971490585L;
private List<LogInfo> LogInfos;
private String sysIdentify;
public List<LogInfo> getLogInfos() {
return LogInfos;
}
public void setLogInfos(List<LogInfo> logInfos) {
LogInfos = logInfos;
}
public String getSysIdentify() {
return sysIdentify;
}
public void setSysIdentify(String sysIdentify) {
this.sysIdentify = sysIdentify;
}
}
2、model建好之后,自定义一个StatLogger,创建一个抽象类 MonitorDataSourceSql来实现获取监控数据,代码如下:
public abstract class MonitorDataSourceSql extends DruidDataSourceStatLoggerAdapter
implements DruidDataSourceStatLogger {
private final static Log logger = LogFactory.getLog(DruidPooledConnection.class);
public MonitorDataSourceSql() {
this.configFromProperties(System.getProperties());
}
/*
* DruidDataSourceStatValue包含这整个SQL监控数据,按需索取
*
**/
@Override
public void log(DruidDataSourceStatValue statValue) {
List<JdbcSqlStatValue> sqlList = statValue.getSqlList();
if (sqlList != null && sqlList.size() > 0) {
List<LogInfo> logInfos = new ArrayList<LogInfo>(sqlList.size());
MonitorInfo monitorInfo = new MonitorInfo();
JdbcSqlStatValue value = null;
Throwable executeThrowable = null;
LogInfo info = null;
try {
for (int i = 0; i < sqlList.size(); i++) {
value = sqlList.get(i);
info = new LogInfo();
info.setHistogram_0_1(value.getHistogram_0_1());
info.setHistogram_1_10(value.getHistogram_1_10());
info.setHistogram_10_100(value.getHistogram_10_100());
info.setHistogram_100_1000(value.getHistogram_100_1000());
info.setHistogram_1000_10000(value.getHistogram_1000_10000());
info.setHistogram_1000000_more(value.getHistogram_1000000_more());
info.setHistogram_100000_1000000(value.getHistogram_100000_1000000());
info.setHistogram_10000_100000(value.getHistogram_10000_100000());
info.setMaxParallel(value.getConcurrentMax());
info.setMaxOccurTime(value.getExecuteNanoSpanMaxOccurTime());
info.setSql(value.getSql());
info.setSqlParam(value.getLastSlowParameters());
info.setExecuteMillisTotal(value.getExecuteMillisTotal());
info.setExecuteErrorCount(value.getExecuteErrorCount());
info.setExecuteMillisMax(value.getExecuteMillisMax());
info.setExecuteCount(value.getExecuteCount());
executeThrowable = value.getExecuteErrorLast();
if (executeThrowable != null) {
info.setLastErrorClass(executeThrowable.getClass().getName());
info.setLastErrorMessage(executeThrowable.getMessage());
info.setLastErrorStackTrace(Utils.toString(executeThrowable.getStackTrace()));
info.setLastErrorTime(value.getExecuteErrorLastTime());
}
logInfos.add(info);
}
} catch (Exception e) {
e.printStackTrace();
logger.error("监控数据转换异常", e);
}
monitorInfo.setLogInfos(logInfos);
monitorInfo.setSysIdentify(getIdentify());
sendMonitorLog(monitorInfo);
}
}
/**
* 监控数据
*
**/
public abstract void sendMonitorLog(MonitorInfo monitorInfo);
public abstract String getIdentify();
@Override
public void configFromProperties(Properties properties) {
super.configFromProperties(properties);
}
@Override
public void setLogger(Log logger) {
}
@Override
public void setLoggerName(String loggerName) {
super.setLoggerName(loggerName);
}
}
3、创建MonitorDataSourceSqlImpl 继承刚才创建的抽象类并引入redis,将监控数据放到redis中,这里的JSON使用的也是阿里巴巴的fastjson
public class MonitorDataSourceSqlImpl extends MonitorDataSourceSql {
@Autowired
private IRedisService cacheService;
@Override
public void sendMonitorLog(MonitorInfo monitorInfo) {
try {
String str = JSONObject.toJSONString(monitorInfo);
this.cacheService.set(RedisKey.MONITORLOG, str);
} catch (Exception e) {
e.printStackTrace();
}
}
@Override
public String getIdentify() {
return null;
}
}
4、数据源配置,代码如下:
<bean id="webDataSource" class="com.alibaba.druid.pool.DruidDataSource"
init-method="init" destroy-method="close">
<property name="driverClassName" value="com.mysql.jdbc.Driver" />
<property name="url" value="${web.jdbcUrl}" />
<property name="username" value="${web.user}" />
<property name="password" value="${web.password}" />
<!-- 配置初始化大小、最小、最大 -->
<property name="initialSize" value="5" />
<property name="minIdle" value="2" />
<property name="maxActive" value="200" />
<!-- 设置数据库编码 为utf8mb4 -->
<property name="connectionInitSqls" value="set names utf8mb4;" />
<!-- 配置获取连接等待超时的时间 -->
<property name="maxWait" value="60000" />
<!-- 配置间隔多久才进行一次检测,检测需要关闭的空闲连接,单位是毫秒 -->
<property name="timeBetweenEvictionRunsMillis" value="60000" />
<!-- 配置一个连接在池中最小生存的时间,单位是毫秒 -->
<property name="minEvictableIdleTimeMillis" value="300000" />
<property name="validationQuery" value="SELECT 'x'" />
<property name="testWhileIdle" value="true" />
<property name="testOnBorrow" value="false" />
<property name="testOnReturn" value="false" />
<!-- 记录sql -->
<property name="filters" value="config,stat,log4j,mergeStat" />
<!-- 慢sql 时间定义 -->
<property name="connectionProperties" value="druid.stat.slowSqlMillis=5000;config.decrypt=true;config.decrypt.key=${tgbweb.publicKey}" />
<!-- 每3秒保存日志 -->
<property name="timeBetweenLogStatsMillis" value="3000" />
<!-- 合并多个DruidDataSource的监控数据 -->
<!-- <property name="useGlobalDataSourceStat" value="true" /> -->
<!-- 定制化日志输出 -->
<property name="statLogger" ref="myStatLogger" />
</bean>
<bean id="myStatLogger" class="com.taoguba.monitor.sql.impl.MonitorDataSourceSqlImpl">
</bean>
5、通过Controller获取数据并返回JSON给前端
@RestController
@RequestMapping(value = "/new/monitor")
@Scope(value = ConfigurableBeanFactory.SCOPE_PROTOTYPE)
public class MonitorController extends BaseController{
@Autowired
protected IRedisService cacheService;
@GetMapping(value = "/getDataSourceSql")
public Result getDataSourceSql() {
String data = this.cacheService.get(RedisKey.MONITORLOG);
MonitorInfo mon= JSONObject.parseObject(data,MonitorInfo.class);
return new Result(mon);
}
}
6、JSON数据,前端取到这些数据展示即可(此处暂不展示效果了。。)
{
status: true,
errorCode: 0,
errorMessage: "",
dto: {
sysIdentify: null,
logInfos: [
{
sql: "select count(*) from topi where beFg='Y' and usefulnum > 0 and catD between 2 and 3 and uid=?",
sqlParam: null,
maxParallel: 2,
executeMillisTotal: 3,
executeCount: 2,
executeErrorCount: 0,
maxOccurTime: 1505988865405,
histogram_0_1: 0,
histogram_1_10: 2,
histogram_100_1000: 0,
histogram_1000_10000: 0,
histogram_10000_100000: 0,
histogram_100000_1000000: 0,
histogram_1000000_more: 0,
lastError: null,
lastErrorMessage: null,
lastErrorStackTrace: null,
lastErrorClass: null,
lastErrorTime: null,
histogram_10_100: 0,
executeMillisMax: 1
}]
},
_t: 1505988871072
7、至此微服务项目集成Druid 监控数据 完成收集展示,如有问题 ,欢迎留言指正。