报警工具类

This commit is contained in:
zhaoyong 2021-11-27 18:44:20 +08:00
parent 20500028e0
commit 883cd67f79
16 changed files with 506 additions and 0 deletions

View File

@ -0,0 +1,96 @@
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>cn.axzo.framework</groupId>
<artifactId>alarm-spring-boot-starter</artifactId>
<version>1.0.1</version>
<properties>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
<maven.compiler.source>1.8</maven.compiler.source>
<maven.compiler.target>1.8</maven.compiler.target>
<!-- tool -->
<spring.boot.version>2.2.5.RELEASE</spring.boot.version>
<lombok.version>1.18.18</lombok.version>
<slf4j-api.version>1.7.5</slf4j-api.version>
<lombok.version>1.18.18</lombok.version>
<fastjson.version>1.2.47</fastjson.version>
<spring.version>4.3.19.RELEASE</spring.version>
</properties>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-configuration-processor</artifactId>
<version>${spring.boot.version}</version>
<optional>true</optional>
<scope>provided</scope>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter</artifactId>
<version>${spring.boot.version}</version>
<scope>provided</scope>
</dependency>
<dependency>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-api</artifactId>
<version>${slf4j-api.version}</version>
<scope>provided</scope>
</dependency>
<dependency>
<groupId>com.alibaba</groupId>
<artifactId>fastjson</artifactId>
<version>${fastjson.version}</version>
<scope>provided</scope>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-web</artifactId>
<version>${spring.version}</version>
<scope>provided</scope>
</dependency>
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
<version>${lombok.version}</version>
<scope>provided</scope>
</dependency>
</dependencies>
<build>
<plugins>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-source-plugin</artifactId>
<executions>
<execution>
<id>attach-sources</id>
<goals>
<goal>jar</goal>
</goals>
</execution>
</executions>
</plugin>
</plugins>
</build>
<distributionManagement>
<!-- 两个ID必须与 setting.xml中的<server><id>Releases</id></server>保持一致 -->
<repository>
<id>rdc-releases</id>
<name>Nexus Release Repository</name>
<url>https://packages.aliyun.com/maven/repository/2005773-release-XI7cl5/</url>
</repository>
<snapshotRepository>
<id>rdc-snapshots</id>
<name>Nexus Snapshot Repository</name>
<url>https://packages.aliyun.com/maven/repository/2005773-snapshot-V5Gjdf/</url>
</snapshotRepository>
</distributionManagement>
</project>

View File

@ -0,0 +1,30 @@
package cn.axzo.framework.alarm.config;
import org.springframework.beans.factory.ObjectProvider;
import org.springframework.boot.autoconfigure.condition.ConditionalOnBean;
import org.springframework.boot.context.properties.EnableConfigurationProperties;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.web.client.RestTemplate;
/**
* 报警自动配置类
*
* @author zhaoyong
* @see AlarmAutoConfiguration
* @since 2021-11-25 16:45
*/
@Configuration
@EnableConfigurationProperties(AlarmProperties.class)
public class AlarmAutoConfiguration {
public static final String ALARM_SERVICE_BEAN_NAME = "alarmService";
@Bean(ALARM_SERVICE_BEAN_NAME)
@ConditionalOnBean(value = RestTemplate.class)
public AlarmService alarmService(ObjectProvider<RestTemplate> restTemplate, AlarmProperties alarmProperties){
AlarmService alarmService = new DingDingAlarmService(restTemplate, alarmProperties);
return alarmService;
}
}

View File

@ -0,0 +1,39 @@
package cn.axzo.framework.alarm.config;
import lombok.Data;
import org.springframework.boot.context.properties.ConfigurationProperties;
import java.util.ArrayList;
import java.util.List;
/**
* 报警参数
*
* @author zhaoyong
* @see AlarmProperties
* @since 2021-11-25 16:19
*/
@Data
@ConfigurationProperties(prefix = "alarm")
public class AlarmProperties {
private String appName;
private List<Destination> destinations;
@Data
public static final class Destination {
private String alarmName;
private String title;
private String messageType;
private String alarmUrl;
private List<String> atMobiles = new ArrayList<>();
}
}

View File

@ -0,0 +1,19 @@
package cn.axzo.framework.alarm.config;
/**
* 报警服务
*
* @author zhaoyong
* @see AlarmService
* @since 2021-11-25 16:19
*/
public interface AlarmService {
/**
* 报警
* @param alarmName 报警名称
* @param content 报警内容
*/
void alarm(String alarmName, String content);
}

View File

@ -0,0 +1,76 @@
package cn.axzo.framework.alarm.config;
import cn.axzo.framework.alarm.config.AlarmProperties.Destination;
import cn.axzo.framework.alarm.message.DingMessageFactory;
import cn.axzo.framework.alarm.message.DingMessageRequest;
import cn.axzo.framework.alarm.message.DingMessageResponse;
import com.alibaba.fastjson.JSON;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.ObjectProvider;
import org.springframework.util.Assert;
import org.springframework.util.CollectionUtils;
import org.springframework.util.StringUtils;
import org.springframework.web.client.RestTemplate;
import java.util.List;
/**
* 钉钉报警
*
* @author zhaoyong
* @see DingDingAlarmService
* @since 2021-11-25 16:21
*/
@Slf4j
public class DingDingAlarmService implements AlarmService {
private final RestTemplate restTemplate;
private final AlarmProperties alarmProperties;
public DingDingAlarmService(ObjectProvider<RestTemplate> restTemplate, AlarmProperties alarmProperties) {
this.restTemplate = restTemplate.getIfAvailable();
this.alarmProperties = alarmProperties;
}
@Override
public void alarm(String alarmName, String content) {
Assert.hasText(alarmName, "alarm name must not be null");
Assert.hasText(alarmName, "content must not be null");
try {
Destination destination = findDestination(alarmName);
if(destination == null) {
return;
}
DingMessageRequest request = DingMessageFactory.getMessageRequest(destination, content);
if(request == null) {
return;
}
String appName = getAppName();
log.info("[{} -> ding] AlarmService.alarm request param is {}", appName, JSON.toJSONString(request));
DingMessageResponse response = restTemplate.postForObject(destination.getAlarmUrl(), request, DingMessageResponse.class);
log.info("[{} <- ding] AlarmService.alarm response is {}", appName, JSON.toJSONString(response));
} catch (Exception e) {
log.error("[alarm <- ding] AlarmService.alarm response is error", e);
}
}
private String getAppName() {
String appName = alarmProperties.getAppName();
if(StringUtils.hasText(appName)) {
return appName;
}
return "alarm";
}
private Destination findDestination(String alarmName) {
List<Destination> destinations = alarmProperties.getDestinations();
if(CollectionUtils.isEmpty(destinations)) {
return null;
}
return destinations.stream().filter(v -> alarmName.equals(v.getAlarmName())).findFirst().orElse(null);
}
}

View File

@ -0,0 +1,32 @@
package cn.axzo.framework.alarm.message;
import lombok.Data;
import java.util.List;
/**
* 钉钉群 @ 通知人
*
* @author zhaoyong
* @see At
* @since 2021-07-12 11:31
*/
@Data
public class At {
/**
* @人的手机号
*/
private List<String> atMobiles;
/**
* @人的用户userid
*/
private List<String> atUserIds;
/**
* 是否@所有人
*/
private boolean isAtAll;
}

View File

@ -0,0 +1,33 @@
package cn.axzo.framework.alarm.message;
import lombok.AllArgsConstructor;
import lombok.Getter;
import java.util.stream.Stream;
/**
* 钉钉消息类型
*
* @author zhaoyong
* @see DingDingMessageType
* @since 2021-11-27 10:21
*/
@Getter
@AllArgsConstructor
public enum DingDingMessageType {
TEXT("text", "text"),
MARKDOWN("markdown", "markdown"),
;
private String code;
private String desc;
public static DingDingMessageType getByCode(String code) {
return Stream.of(DingDingMessageType.values())
.filter(item -> item.getCode().equals(code))
.findFirst().orElse(null);
}
}

View File

@ -0,0 +1,71 @@
package cn.axzo.framework.alarm.message;
import cn.axzo.framework.alarm.config.AlarmProperties.Destination;
import org.springframework.util.CollectionUtils;
import org.springframework.util.StringUtils;
/**
* 钉钉消息请求类
*
* @author zhaoyong
* @see DingMessageFactory
* @since 2021-11-27 10:38
*/
public class DingMessageFactory {
public static DingMessageRequest getMessageRequest(Destination destination, String content) {
if(destination == null) {
return null;
}
DingDingMessageType messageType = DingDingMessageType.getByCode(destination.getMessageType());
if(messageType == null) {
return null;
}
if(DingDingMessageType.TEXT == messageType) {
TextMessageRequest request = new TextMessageRequest();
request.setMsgtype(destination.getMessageType());
TextMessage text = new TextMessage();
text.setContent(content);
request.setText(text);
At at = new At();
if(CollectionUtils.isEmpty(destination.getAtMobiles())) {
at.setAtAll(true);
} else {
at.setAtMobiles(destination.getAtMobiles());
}
request.setAt(at);
return request;
}
if(DingDingMessageType.MARKDOWN == messageType) {
MarkdownMessageRequest request = new MarkdownMessageRequest();
request.setMsgtype(destination.getMessageType());
MarkdownMessage markdown = new MarkdownMessage();
markdown.setTitle(getTitle(destination));
markdown.setText(content);
request.setMarkdown(markdown);
At at = new At();
if(CollectionUtils.isEmpty(destination.getAtMobiles())) {
at.setAtAll(true);
} else {
at.setAtMobiles(destination.getAtMobiles());
}
request.setAt(at);
return request;
}
return null;
}
/**
* 获取 Markdown 标题
* @param destination
* @return
*/
private static String getTitle(Destination destination) {
String title = destination.getTitle();
if(StringUtils.hasText(title)) {
return title;
}
return destination.getAlarmName();
}
}

View File

@ -0,0 +1,17 @@
package cn.axzo.framework.alarm.message;
import lombok.Data;
/**
* 钉钉消息请求类
*
* @author zhaoyong
* @see DingMessageRequest
* @since 2021-07-12 13:16
*/
@Data
public class DingMessageRequest {
private String msgtype;
}

View File

@ -0,0 +1,18 @@
package cn.axzo.framework.alarm.message;
import lombok.Data;
/**
* 钉钉请求响应类
*
* @author zhaoyong
* @see DingMessageResponse
* @since 2021-07-12 11:02
*/
@Data
public class DingMessageResponse {
private int errcode;
private String errmsg;
}

View File

@ -0,0 +1,25 @@
package cn.axzo.framework.alarm.message;
import lombok.Data;
/**
* markdown
*
* @author zhaoyong
* @see MarkdownMessage
* @since 2021-11-27 10:47
*/
@Data
public class MarkdownMessage {
/**
* 首屏会话透出的展示内容
*/
private String title;
/**
* markdown格式的消息
*/
private String text;
}

View File

@ -0,0 +1,19 @@
package cn.axzo.framework.alarm.message;
import lombok.Data;
/**
* markdown 消息
*
* @author zhaoyong
* @see MarkdownMessageRequest
* @since 2021-11-27 10:50
*/
@Data
public class MarkdownMessageRequest extends DingMessageRequest {
private MarkdownMessage markdown;
private At at;
}

View File

@ -0,0 +1,10 @@
package cn.axzo.framework.alarm.message;
import lombok.Data;
@Data
public class TextMessage {
private String content;
}

View File

@ -0,0 +1,19 @@
package cn.axzo.framework.alarm.message;
import lombok.Data;
/**
* 文本消息类型
*
* @author zhaoyong
* @see TextMessageRequest
* @since 2021-11-27 10:28
*/
@Data
public class TextMessageRequest extends DingMessageRequest {
private TextMessage text;
private At at;
}

View File

@ -0,0 +1 @@
org.springframework.boot.autoconfigure.EnableAutoConfiguration=cn.axzo.framework.alarm.config.AlarmAutoConfiguration

View File

@ -15,6 +15,7 @@
<module>common-common</module> <module>common-common</module>
<module>smart-datasource</module> <module>smart-datasource</module>
<module>asyncTool</module> <module>asyncTool</module>
<module>alarm-spring-boot-starter</module>
</modules> </modules>
<build> <build>