mirror of
https://gitee.com/lab1024/smart-admin.git
synced 2025-11-21 18:06:52 +08:00
v1.1.0
This commit is contained in:
@@ -0,0 +1,35 @@
|
||||
package net.lab1024.smartadmin.common.anno;
|
||||
|
||||
import net.lab1024.smartadmin.common.domain.BaseEnum;
|
||||
|
||||
import java.lang.annotation.ElementType;
|
||||
import java.lang.annotation.Retention;
|
||||
import java.lang.annotation.RetentionPolicy;
|
||||
import java.lang.annotation.Target;
|
||||
|
||||
/**
|
||||
* 枚举类字段属性的注解
|
||||
*
|
||||
* @author listen
|
||||
* @date 2019/05/16 15:18
|
||||
*/
|
||||
@Target({ElementType.FIELD})
|
||||
@Retention(RetentionPolicy.RUNTIME)
|
||||
public @interface ApiModelPropertyEnum {
|
||||
|
||||
/**
|
||||
* 枚举类对象
|
||||
*
|
||||
* @return
|
||||
*/
|
||||
Class<? extends BaseEnum> value();
|
||||
|
||||
String example() default "";
|
||||
|
||||
boolean required() default true;
|
||||
|
||||
String dataType() default "";
|
||||
|
||||
String enumDesc() default "";
|
||||
|
||||
}
|
||||
@@ -0,0 +1,34 @@
|
||||
package net.lab1024.smartadmin.common.anno;
|
||||
|
||||
import net.lab1024.smartadmin.module.system.datascope.constant.DataScopeTypeEnum;
|
||||
|
||||
import java.lang.annotation.ElementType;
|
||||
import java.lang.annotation.Retention;
|
||||
import java.lang.annotation.RetentionPolicy;
|
||||
import java.lang.annotation.Target;
|
||||
|
||||
/**
|
||||
* [ 数据范围 ]
|
||||
*
|
||||
* @author yandanyang
|
||||
* @version 1.0
|
||||
* @company 1024lab.net
|
||||
* @copyright (c) 2019 1024lab.netInc. All rights reserved.
|
||||
* @date
|
||||
* @since JDK1.8
|
||||
*/
|
||||
@Retention(RetentionPolicy.RUNTIME)
|
||||
@Target(ElementType.METHOD)
|
||||
public @interface DataScope {
|
||||
|
||||
DataScopeTypeEnum dataScopeType() default DataScopeTypeEnum.DEFAULT;
|
||||
|
||||
/**
|
||||
* 第几个where 条件 从0开始
|
||||
* @return
|
||||
*/
|
||||
int whereIndex() default 0;
|
||||
|
||||
String joinSql() default "";
|
||||
|
||||
}
|
||||
@@ -0,0 +1,22 @@
|
||||
package net.lab1024.smartadmin.common.anno;
|
||||
|
||||
import java.lang.annotation.ElementType;
|
||||
import java.lang.annotation.Retention;
|
||||
import java.lang.annotation.RetentionPolicy;
|
||||
import java.lang.annotation.Target;
|
||||
|
||||
/**
|
||||
*
|
||||
* [ 不需要登陆 ]
|
||||
*
|
||||
* @version 1.0
|
||||
* @since JDK1.8
|
||||
* @author yandanyang
|
||||
* @company 1024lab.net
|
||||
* @copyright (c) 2019 1024lab.netInc. All rights reserved.
|
||||
* @date
|
||||
*/
|
||||
@Retention(RetentionPolicy.RUNTIME)
|
||||
@Target(ElementType.METHOD)
|
||||
public @interface NoNeedLogin {
|
||||
}
|
||||
@@ -0,0 +1,20 @@
|
||||
package net.lab1024.smartadmin.common.anno;
|
||||
|
||||
import java.lang.annotation.Retention;
|
||||
import java.lang.annotation.RetentionPolicy;
|
||||
|
||||
/**
|
||||
*
|
||||
* [ 不需要权限验证 ]
|
||||
*
|
||||
* @version 1.0
|
||||
* @since JDK1.8
|
||||
* @author yandanyang
|
||||
* @company 1024lab.net
|
||||
* @copyright (c) 2019 1024lab.netInc. All rights reserved.
|
||||
* @date
|
||||
*/
|
||||
@Retention(RetentionPolicy.RUNTIME)
|
||||
public @interface NoValidPrivilege {
|
||||
|
||||
}
|
||||
@@ -0,0 +1,20 @@
|
||||
package net.lab1024.smartadmin.common.anno;
|
||||
|
||||
import java.lang.annotation.*;
|
||||
|
||||
/**
|
||||
* [ 用户操作日志 ]
|
||||
*
|
||||
* @author yandanyang
|
||||
* @version 1.0
|
||||
* @company 1024lab.net
|
||||
* @copyright (c) 2019 1024lab.netInc. All rights reserved.
|
||||
* @date
|
||||
* @since JDK1.8
|
||||
*/
|
||||
@Retention(RetentionPolicy.RUNTIME)
|
||||
@Target(ElementType.TYPE)
|
||||
@Documented
|
||||
public @interface OperateLog {
|
||||
|
||||
}
|
||||
@@ -0,0 +1,57 @@
|
||||
package net.lab1024.smartadmin.common.constant;
|
||||
|
||||
|
||||
import net.lab1024.smartadmin.common.domain.BaseEnum;
|
||||
|
||||
/**
|
||||
* 全局排序枚举类
|
||||
*
|
||||
* @author listen
|
||||
* @date 2018/01/13 14:24
|
||||
*/
|
||||
public enum CommentSortTypeEnum implements BaseEnum {
|
||||
|
||||
/**
|
||||
* 正序 ASC 1
|
||||
*/
|
||||
ASC(1, "ASC"),
|
||||
|
||||
/**
|
||||
* 倒序 DESC 2
|
||||
*/
|
||||
DESC(2, "DESC");
|
||||
|
||||
private Integer value;
|
||||
|
||||
private String desc;
|
||||
|
||||
/**
|
||||
* 排序类型:1正序 | 2倒序
|
||||
*/
|
||||
public static final String INFO = "排序类型:1正序 | 2倒序";
|
||||
|
||||
CommentSortTypeEnum(Integer value, String desc) {
|
||||
this.value = value;
|
||||
this.desc = desc;
|
||||
}
|
||||
|
||||
/**
|
||||
* 获取枚举类的值
|
||||
*
|
||||
* @return Integer
|
||||
*/
|
||||
@Override
|
||||
public Integer getValue() {
|
||||
return value;
|
||||
}
|
||||
|
||||
/**
|
||||
* 获取枚举类的说明
|
||||
*
|
||||
* @return String
|
||||
*/
|
||||
@Override
|
||||
public String getDesc() {
|
||||
return desc;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,52 @@
|
||||
package net.lab1024.smartadmin.common.constant;
|
||||
|
||||
import net.lab1024.smartadmin.common.domain.BaseEnum;
|
||||
|
||||
import java.util.Arrays;
|
||||
import java.util.Optional;
|
||||
|
||||
/**
|
||||
*
|
||||
* [ 是与否]
|
||||
*
|
||||
* @version 1.0
|
||||
* @since JDK1.8
|
||||
* @author yandanyang
|
||||
* @company 1024lab.net
|
||||
* @copyright (c) 2019 1024lab.netInc. All rights reserved.
|
||||
* @date
|
||||
*/
|
||||
public enum JudgeEnum implements BaseEnum {
|
||||
|
||||
NO(0, "否"),
|
||||
|
||||
YES(1, "是");
|
||||
|
||||
private Integer value;
|
||||
private String desc;
|
||||
|
||||
JudgeEnum(Integer value, String desc) {
|
||||
this.value = value;
|
||||
this.desc = desc;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Integer getValue() {
|
||||
return value;
|
||||
}
|
||||
@Override
|
||||
public String getDesc() {
|
||||
return desc;
|
||||
}
|
||||
|
||||
public static JudgeEnum valueOf(Integer status) {
|
||||
JudgeEnum[] values = JudgeEnum.values();
|
||||
Optional<JudgeEnum> first = Arrays.stream(values).filter(e -> e.getValue().equals(status)).findFirst();
|
||||
return !first.isPresent() ? null : first.get();
|
||||
}
|
||||
|
||||
public static boolean isExist(Integer status) {
|
||||
JudgeEnum judgeEnum = valueOf(status);
|
||||
return judgeEnum != null;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,181 @@
|
||||
package net.lab1024.smartadmin.common.constant;
|
||||
|
||||
import net.lab1024.smartadmin.module.system.department.DepartmentResponseCodeConst;
|
||||
import net.lab1024.smartadmin.module.system.employee.constant.EmployeeResponseCodeConst;
|
||||
import net.lab1024.smartadmin.module.support.file.constant.FileResponseCodeConst;
|
||||
import net.lab1024.smartadmin.module.business.log.orderoperatelog.constant.OrderOperateLogOperateTypeConst;
|
||||
import net.lab1024.smartadmin.module.business.login.LoginResponseCodeConst;
|
||||
import net.lab1024.smartadmin.module.system.position.PositionResponseCodeConst;
|
||||
import net.lab1024.smartadmin.module.system.privilege.constant.PrivilegeResponseCodeConst;
|
||||
import net.lab1024.smartadmin.module.system.role.basic.RoleResponseCodeConst;
|
||||
import net.lab1024.smartadmin.module.system.systemconfig.constant.SystemConfigResponseCodeConst;
|
||||
import lombok.extern.slf4j.Slf4j;
|
||||
|
||||
import java.lang.reflect.Field;
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
|
||||
/**
|
||||
* 每个业务,100个范围值就够了.
|
||||
*/
|
||||
@Slf4j
|
||||
public class ResponseCodeConst {
|
||||
|
||||
// 范围声明
|
||||
static {
|
||||
// 系统功能,从0开始,step=1000
|
||||
ResponseCodeContainer.register(ResponseCodeConst.class, 0, 1000);
|
||||
ResponseCodeContainer.register(LoginResponseCodeConst.class, 1001, 1999);
|
||||
ResponseCodeContainer.register(DepartmentResponseCodeConst.class, 2001, 2999);
|
||||
ResponseCodeContainer.register(EmployeeResponseCodeConst.class, 3001, 3999);
|
||||
ResponseCodeContainer.register(FileResponseCodeConst.class, 4001, 4999);
|
||||
ResponseCodeContainer.register(SystemConfigResponseCodeConst.class, 5001, 5999);
|
||||
ResponseCodeContainer.register(RoleResponseCodeConst.class, 6001, 6999);
|
||||
ResponseCodeContainer.register(PrivilegeResponseCodeConst.class, 7001, 7999);
|
||||
ResponseCodeContainer.register(OrderOperateLogOperateTypeConst.class, 8001, 8999);
|
||||
ResponseCodeContainer.register(PositionResponseCodeConst.class, 13000, 13999);
|
||||
|
||||
}
|
||||
|
||||
public static final ResponseCodeConst SUCCESS = new ResponseCodeConst(1, "操作成功!", true);
|
||||
|
||||
public static final ResponseCodeConst ERROR_PARAM = new ResponseCodeConst(101, "参数异常!");
|
||||
|
||||
public static final ResponseCodeConst ERROR_PARAM_ANY = new ResponseCodeConst(102, "%s参数异常!");
|
||||
|
||||
public static final ResponseCodeConst SYSTEM_ERROR = new ResponseCodeConst(111, "系统错误");
|
||||
|
||||
public static final ResponseCodeConst DEVELOPMENT = new ResponseCodeConst(112, "此功能正在开发中");
|
||||
|
||||
public static final ResponseCodeConst NOT_EXISTS = new ResponseCodeConst(113, "数据不存在");
|
||||
|
||||
public static ResponseCodeConst REQUEST_METHOD_ERROR = new ResponseCodeConst(114, "请求方式错误");
|
||||
|
||||
public static ResponseCodeConst JSON_FORMAT_ERROR = new ResponseCodeConst(115, "JSON格式错误");
|
||||
|
||||
protected int code;
|
||||
|
||||
protected String msg;
|
||||
|
||||
protected boolean success;
|
||||
|
||||
public ResponseCodeConst() {
|
||||
}
|
||||
|
||||
protected ResponseCodeConst(int code, String msg) {
|
||||
super();
|
||||
this.code = code;
|
||||
this.msg = msg;
|
||||
ResponseCodeContainer.put(this);
|
||||
}
|
||||
|
||||
protected ResponseCodeConst(int code, String msg, boolean success) {
|
||||
super();
|
||||
this.code = code;
|
||||
this.msg = msg;
|
||||
this.success = success;
|
||||
ResponseCodeContainer.put(this);
|
||||
}
|
||||
|
||||
protected ResponseCodeConst(int code) {
|
||||
super();
|
||||
this.code = code;
|
||||
ResponseCodeContainer.put(this);
|
||||
}
|
||||
|
||||
public int getCode() {
|
||||
return code;
|
||||
}
|
||||
|
||||
public void setCode(int code) {
|
||||
this.code = code;
|
||||
}
|
||||
|
||||
public String getMsg() {
|
||||
return msg;
|
||||
}
|
||||
|
||||
public void setMsg(String msg) {
|
||||
this.msg = msg;
|
||||
}
|
||||
|
||||
public boolean isSuccess() {
|
||||
return success;
|
||||
}
|
||||
|
||||
public void setSuccess(boolean success) {
|
||||
this.success = success;
|
||||
}
|
||||
|
||||
public static void init() {
|
||||
log.info("ResponseCodeConst init....");
|
||||
}
|
||||
|
||||
// =======================分割=======================
|
||||
|
||||
/**
|
||||
* 内部类,用于检测code范围
|
||||
*
|
||||
* @author Anders
|
||||
*/
|
||||
@Slf4j
|
||||
private static class ResponseCodeContainer {
|
||||
|
||||
private static final Map<Integer, ResponseCodeConst> RESPONSE_CODE_MAP = new HashMap<>();
|
||||
|
||||
private static final Map<Class<? extends ResponseCodeConst>, int[]> RESPONSE_CODE_RANGE_MAP = new HashMap<>();
|
||||
|
||||
/**
|
||||
* id的范围:[start, end]左闭右闭
|
||||
*
|
||||
* @param clazz
|
||||
* @param start
|
||||
* @param end
|
||||
*/
|
||||
private static void register(Class<? extends ResponseCodeConst> clazz, int start, int end) {
|
||||
if (start > end) {
|
||||
throw new IllegalArgumentException("<ResponseDTO> start > end!");
|
||||
}
|
||||
|
||||
if (RESPONSE_CODE_RANGE_MAP.containsKey(clazz)) {
|
||||
throw new IllegalArgumentException(String.format("<ResponseDTO> Class:%s already exist!", clazz.getSimpleName()));
|
||||
}
|
||||
RESPONSE_CODE_RANGE_MAP.forEach((k, v) -> {
|
||||
if ((start >= v[0] && start <= v[1]) || (end >= v[0] && end <= v[1])) {
|
||||
throw new IllegalArgumentException(String.format("<ResponseDTO> Class:%s 's id range[%d,%d] has " + "intersection with " + "class:%s", clazz.getSimpleName(), start, end,
|
||||
k.getSimpleName()));
|
||||
}
|
||||
});
|
||||
|
||||
RESPONSE_CODE_RANGE_MAP.put(clazz, new int[]{start, end});
|
||||
|
||||
// 提前初始化static变量,进行范围检测
|
||||
Field[] fields = clazz.getFields();
|
||||
if (fields.length != 0) {
|
||||
try {
|
||||
fields[0].get(clazz);
|
||||
} catch (IllegalArgumentException | IllegalAccessException e) {
|
||||
log.error("", e);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public static void put(ResponseCodeConst codeConst) {
|
||||
int[] idRange = RESPONSE_CODE_RANGE_MAP.get(codeConst.getClass());
|
||||
if (idRange == null) {
|
||||
throw new IllegalArgumentException(String.format("<ResponseDTO> Class:%s has not been registered!", codeConst.getClass().getSimpleName()));
|
||||
}
|
||||
int code = codeConst.code;
|
||||
if (code < idRange[0] || code > idRange[1]) {
|
||||
throw new IllegalArgumentException(String.format("<ResponseDTO> Id(%d) out of range[%d,%d], " + "class:%s", code, idRange[0], idRange[1], codeConst.getClass().getSimpleName()));
|
||||
}
|
||||
if (RESPONSE_CODE_MAP.keySet().contains(code)) {
|
||||
log.error(String.format("<ResponseDTO> Id(%d) out of range[%d,%d], " + "class:%s code is repeat!", code, idRange[0], idRange[1], codeConst.getClass().getSimpleName()));
|
||||
System.exit(0);
|
||||
}
|
||||
RESPONSE_CODE_MAP.put(code, codeConst);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,42 @@
|
||||
package net.lab1024.smartadmin.common.controller;
|
||||
|
||||
import lombok.extern.slf4j.Slf4j;
|
||||
import org.apache.poi.ss.usermodel.Workbook;
|
||||
|
||||
import javax.servlet.http.HttpServletResponse;
|
||||
import java.io.IOException;
|
||||
import java.io.UnsupportedEncodingException;
|
||||
import java.net.URLEncoder;
|
||||
|
||||
/**
|
||||
* @author: zhuoda
|
||||
* @create: 2020-03-31 08:54 PM from win10
|
||||
*/
|
||||
|
||||
@Slf4j
|
||||
public class BaseController {
|
||||
|
||||
/**
|
||||
* 下载 Excel 消息头
|
||||
* @param fileName
|
||||
* @param workbook
|
||||
* @param response
|
||||
*/
|
||||
public void downloadExcel(String fileName, Workbook workbook, HttpServletResponse response) {
|
||||
try {
|
||||
fileName = URLEncoder.encode(fileName, "UTF-8");
|
||||
} catch (UnsupportedEncodingException e) {
|
||||
log.error("", e);
|
||||
}
|
||||
response.setCharacterEncoding("utf-8");
|
||||
response.setHeader("Content-Type", "application/vnd.ms-excel");
|
||||
response.setHeader("Content-Disposition", "attachment;filename=" + fileName + ".xls");
|
||||
try {
|
||||
workbook.write(response.getOutputStream());
|
||||
workbook.close();
|
||||
} catch (IOException e) {
|
||||
log.error("", e);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,38 @@
|
||||
package net.lab1024.smartadmin.common.domain;
|
||||
|
||||
import com.baomidou.mybatisplus.annotation.IdType;
|
||||
import com.baomidou.mybatisplus.annotation.TableId;
|
||||
import lombok.Data;
|
||||
|
||||
import java.util.Date;
|
||||
|
||||
/**
|
||||
* [ ]
|
||||
*
|
||||
* @author yandanyang
|
||||
* @version 1.0
|
||||
* @company 1024lab.net
|
||||
* @copyright (c) 2018 1024lab.netInc. All rights reserved.
|
||||
* @date 2019/3/27 0027 上午 11:15
|
||||
* @since JDK1.8
|
||||
*/
|
||||
@Data
|
||||
public class BaseEntity {
|
||||
|
||||
/**
|
||||
* 主键id
|
||||
*/
|
||||
@TableId(type = IdType.AUTO)
|
||||
private Long id;
|
||||
|
||||
/**
|
||||
* 更新时间
|
||||
*/
|
||||
private Date updateTime;
|
||||
|
||||
/**
|
||||
* 创建时间
|
||||
*/
|
||||
private Date createTime;
|
||||
|
||||
}
|
||||
@@ -0,0 +1,97 @@
|
||||
package net.lab1024.smartadmin.common.domain;
|
||||
|
||||
import com.alibaba.fastjson.JSON;
|
||||
import com.alibaba.fastjson.JSONAware;
|
||||
import com.alibaba.fastjson.JSONObject;
|
||||
import com.google.common.base.CaseFormat;
|
||||
import lombok.Data;
|
||||
|
||||
import java.util.LinkedHashMap;
|
||||
import java.util.Objects;
|
||||
|
||||
/**
|
||||
* @author listen
|
||||
* @date 2018-07-17 下午 3:52
|
||||
*/
|
||||
public interface BaseEnum {
|
||||
|
||||
/**
|
||||
* 获取枚举类的值
|
||||
*
|
||||
* @return Object
|
||||
*/
|
||||
Object getValue();
|
||||
|
||||
/**
|
||||
* 获取枚举类的说明
|
||||
*
|
||||
* @return String
|
||||
*/
|
||||
String getDesc();
|
||||
|
||||
/**
|
||||
* 比较参数是否与枚举类的value相同
|
||||
*
|
||||
* @param value
|
||||
* @return boolean
|
||||
*/
|
||||
default boolean equalsValue(Object value) {
|
||||
return Objects.equals(getValue(), value);
|
||||
}
|
||||
|
||||
/**
|
||||
* 比较枚举类是否相同
|
||||
*
|
||||
* @param baseEnum
|
||||
* @return boolean
|
||||
*/
|
||||
default boolean equals(BaseEnum baseEnum) {
|
||||
return Objects.equals(getValue(), baseEnum.getValue()) && Objects.equals(getDesc(), baseEnum.getDesc());
|
||||
}
|
||||
|
||||
/**
|
||||
* 返回枚举类的说明
|
||||
*
|
||||
* @param clazz 枚举类类对象
|
||||
* @return
|
||||
*/
|
||||
static String getInfo(Class<? extends BaseEnum> clazz) {
|
||||
BaseEnum[] enums = clazz.getEnumConstants();
|
||||
LinkedHashMap<String, JSONObject> json = new LinkedHashMap<>(enums.length);
|
||||
for (BaseEnum e : enums) {
|
||||
JSONObject jsonObject = new JSONObject();
|
||||
jsonObject.put("value", new DeletedQuotationAware(e.getValue()));
|
||||
jsonObject.put("desc", new DeletedQuotationAware(e.getDesc()));
|
||||
json.put(e.toString(), jsonObject);
|
||||
}
|
||||
|
||||
String enumJson = JSON.toJSONString(json, true);
|
||||
enumJson = enumJson.replaceAll("\"", "");
|
||||
enumJson= enumJson.replaceAll("\t"," ");
|
||||
enumJson = enumJson.replaceAll("\n","<br>");
|
||||
String prefix = " <br> export const <br> " + CaseFormat.UPPER_CAMEL.to(CaseFormat.UPPER_UNDERSCORE, clazz.getSimpleName() + " = <br> ");
|
||||
return prefix + "" + enumJson + " <br>";
|
||||
}
|
||||
|
||||
|
||||
@Data
|
||||
class DeletedQuotationAware implements JSONAware {
|
||||
|
||||
private String value;
|
||||
|
||||
public DeletedQuotationAware(Object value) {
|
||||
if(value == null){
|
||||
this.value = "";
|
||||
}else if (value instanceof String) {
|
||||
this.value = "'" + value + "'";
|
||||
}else {
|
||||
this.value = value.toString();
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toJSONString() {
|
||||
return value;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,16 @@
|
||||
package net.lab1024.smartadmin.common.domain;
|
||||
|
||||
/**
|
||||
* [ ]
|
||||
*
|
||||
* @author yandanyang
|
||||
* @version 1.0
|
||||
* @company 1024lab.net
|
||||
* @copyright (c) 2018 1024lab.netInc. All rights reserved.
|
||||
* @date 2019/4/13 0013 下午 14:23
|
||||
* @since JDK1.8
|
||||
*/
|
||||
public interface ITask {
|
||||
|
||||
void execute(String paramJson) throws Exception;
|
||||
}
|
||||
@@ -0,0 +1,16 @@
|
||||
package net.lab1024.smartadmin.common.domain;
|
||||
|
||||
import lombok.Data;
|
||||
import lombok.extern.slf4j.Slf4j;
|
||||
|
||||
/**
|
||||
* @author: zhuoda
|
||||
* @create: 2020-03-20 09:07 PM from win10
|
||||
*/
|
||||
|
||||
@Slf4j
|
||||
@Data
|
||||
public class OrderItemDTO {
|
||||
private String column;
|
||||
private boolean asc = true;
|
||||
}
|
||||
@@ -0,0 +1,33 @@
|
||||
package net.lab1024.smartadmin.common.domain;
|
||||
|
||||
import io.swagger.annotations.ApiModelProperty;
|
||||
import lombok.Data;
|
||||
|
||||
import javax.validation.constraints.Max;
|
||||
import javax.validation.constraints.NotNull;
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
* 分页基础参数
|
||||
*
|
||||
* @author lihaifan
|
||||
* @Date Created in 2017/10/28 16:19
|
||||
*/
|
||||
@Data
|
||||
public class PageParamDTO {
|
||||
|
||||
@NotNull(message = "分页参数不能为空")
|
||||
@ApiModelProperty(value = "页码(不能为空)", example = "1")
|
||||
protected Integer pageNum;
|
||||
|
||||
@NotNull(message = "每页数量不能为空")
|
||||
@ApiModelProperty(value = "每页数量(不能为空)", example = "10")
|
||||
@Max(value = 200, message = "每页最大为200")
|
||||
protected Integer pageSize;
|
||||
|
||||
@ApiModelProperty("是否查询总条数")
|
||||
protected Boolean searchCount;
|
||||
|
||||
@ApiModelProperty("排序")
|
||||
protected List<OrderItemDTO> orders;
|
||||
}
|
||||
@@ -0,0 +1,47 @@
|
||||
package net.lab1024.smartadmin.common.domain;
|
||||
|
||||
import io.swagger.annotations.ApiModelProperty;
|
||||
import lombok.Data;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
* Page返回对象
|
||||
*
|
||||
* @Author lihaifan
|
||||
* @Date Created in 2017/10/31 15:05
|
||||
*/
|
||||
@Data
|
||||
public class PageResultDTO<T> {
|
||||
|
||||
/**
|
||||
* 当前页
|
||||
*/
|
||||
@ApiModelProperty(value = "当前页")
|
||||
private Long pageNum;
|
||||
|
||||
/**
|
||||
* 每页的数量
|
||||
*/
|
||||
@ApiModelProperty(value = "每页的数量")
|
||||
private Long pageSize;
|
||||
|
||||
/**
|
||||
* 总记录数
|
||||
*/
|
||||
@ApiModelProperty(value = "总记录数")
|
||||
private Long total;
|
||||
|
||||
/**
|
||||
* 总页数
|
||||
*/
|
||||
@ApiModelProperty(value = "总页数")
|
||||
private Long pages;
|
||||
|
||||
/**
|
||||
* 结果集
|
||||
*/
|
||||
@ApiModelProperty(value = "结果集")
|
||||
private List<T> list;
|
||||
|
||||
}
|
||||
@@ -0,0 +1,128 @@
|
||||
package net.lab1024.smartadmin.common.domain;
|
||||
|
||||
|
||||
import net.lab1024.smartadmin.common.constant.ResponseCodeConst;
|
||||
|
||||
/**
|
||||
* 返回类
|
||||
*
|
||||
* @param <T>
|
||||
* @author zhuoda
|
||||
*/
|
||||
public class ResponseDTO<T> {
|
||||
|
||||
protected Integer code;
|
||||
|
||||
protected String msg;
|
||||
|
||||
protected Boolean success;
|
||||
|
||||
protected T data;
|
||||
|
||||
public ResponseDTO() {
|
||||
}
|
||||
|
||||
public ResponseDTO(ResponseCodeConst responseCodeConst, String msg) {
|
||||
this.code = responseCodeConst.getCode();
|
||||
this.msg = msg;
|
||||
this.success = responseCodeConst.isSuccess();
|
||||
}
|
||||
|
||||
public ResponseDTO(ResponseCodeConst responseCodeConst, T data) {
|
||||
super();
|
||||
this.code = responseCodeConst.getCode();
|
||||
this.msg = responseCodeConst.getMsg();
|
||||
this.data = data;
|
||||
this.success = responseCodeConst.isSuccess();
|
||||
}
|
||||
|
||||
public ResponseDTO(ResponseCodeConst responseCodeConst, T data, String msg) {
|
||||
super();
|
||||
this.code = responseCodeConst.getCode();
|
||||
this.msg = msg;
|
||||
this.data = data;
|
||||
this.success = responseCodeConst.isSuccess();
|
||||
}
|
||||
|
||||
private ResponseDTO(ResponseCodeConst responseCodeConst) {
|
||||
this.code = responseCodeConst.getCode();
|
||||
this.msg = responseCodeConst.getMsg();
|
||||
this.success = responseCodeConst.isSuccess();
|
||||
}
|
||||
|
||||
public ResponseDTO(ResponseDTO responseDTO) {
|
||||
this.code = responseDTO.getCode();
|
||||
this.msg = responseDTO.getMsg();
|
||||
this.success = responseDTO.isSuccess();
|
||||
}
|
||||
|
||||
public static <T> ResponseDTO<T> succ() {
|
||||
return new ResponseDTO(ResponseCodeConst.SUCCESS);
|
||||
}
|
||||
|
||||
public static <T> ResponseDTO<T> succData(T data, String msg) {
|
||||
return new ResponseDTO(ResponseCodeConst.SUCCESS, data, msg);
|
||||
}
|
||||
|
||||
public static <T> ResponseDTO<T> succData(T data) {
|
||||
return new ResponseDTO(ResponseCodeConst.SUCCESS, data);
|
||||
}
|
||||
|
||||
public static <T> ResponseDTO succMsg(String msg) {
|
||||
return new ResponseDTO(ResponseCodeConst.SUCCESS, msg);
|
||||
}
|
||||
|
||||
|
||||
public static <T> ResponseDTO<T> wrap(ResponseCodeConst codeConst) {
|
||||
return new ResponseDTO<>(codeConst);
|
||||
}
|
||||
|
||||
public static <T> ResponseDTO<T> wrap(ResponseCodeConst codeConst, T t) {
|
||||
return new ResponseDTO<T>(codeConst, t);
|
||||
}
|
||||
|
||||
public static <T> ResponseDTO<T> wrap(ResponseCodeConst codeConst, String msg) {
|
||||
return new ResponseDTO<T>(codeConst, msg);
|
||||
}
|
||||
|
||||
public String getMsg() {
|
||||
return msg;
|
||||
}
|
||||
|
||||
public ResponseDTO setMsg(String msg) {
|
||||
this.msg = msg;
|
||||
return this;
|
||||
}
|
||||
|
||||
public int getCode() {
|
||||
return code;
|
||||
}
|
||||
|
||||
public ResponseDTO setCode(Integer code) {
|
||||
this.code = code;
|
||||
return this;
|
||||
}
|
||||
|
||||
public T getData() {
|
||||
return data;
|
||||
}
|
||||
|
||||
public ResponseDTO setData(T data) {
|
||||
this.data = data;
|
||||
return this;
|
||||
}
|
||||
|
||||
public boolean isSuccess() {
|
||||
return success;
|
||||
}
|
||||
|
||||
public void setSuccess(boolean success) {
|
||||
this.success = success;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return "ResponseDTO{" + "code=" + code + ", msg='" + msg + '\'' + ", success=" + success + ", data=" + data +
|
||||
'}';
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,148 @@
|
||||
package net.lab1024.smartadmin.common.domain;
|
||||
|
||||
import javax.validation.Valid;
|
||||
import javax.validation.constraints.NotEmpty;
|
||||
import java.util.*;
|
||||
|
||||
/**
|
||||
* @author: zhuoda
|
||||
* @create: 2020-02-03 17:37 PM from win10
|
||||
*/
|
||||
public class ValidateList<E> implements List<E> {
|
||||
|
||||
@Valid
|
||||
@NotEmpty(message = "数据长度请大于0!")
|
||||
private List<E> list;
|
||||
|
||||
public ValidateList() {
|
||||
this.list = new ArrayList<>();
|
||||
}
|
||||
|
||||
public ValidateList(List<E> list) {
|
||||
this.list = list;
|
||||
}
|
||||
|
||||
public List<E> getList() {
|
||||
return list;
|
||||
}
|
||||
|
||||
public void setList(List<E> list) {
|
||||
this.list = list;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int size() {
|
||||
return list.size();
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isEmpty() {
|
||||
return list.isEmpty();
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean contains(Object o) {
|
||||
return list.contains(o);
|
||||
}
|
||||
|
||||
@Override
|
||||
public Iterator<E> iterator() {
|
||||
return list.iterator();
|
||||
}
|
||||
|
||||
@Override
|
||||
public Object[] toArray() {
|
||||
return list.toArray();
|
||||
}
|
||||
|
||||
@Override
|
||||
public <T> T[] toArray(T[] a) {
|
||||
return list.toArray(a);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean add(E e) {
|
||||
return list.add(e);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean remove(Object o) {
|
||||
return list.remove(o);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean containsAll(Collection<?> c) {
|
||||
return list.containsAll(c);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean addAll(Collection<? extends E> c) {
|
||||
return list.addAll(c);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean addAll(int index, Collection<? extends E> c) {
|
||||
return list.addAll(index, c);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean removeAll(Collection<?> c) {
|
||||
return list.removeAll(c);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean retainAll(Collection<?> c) {
|
||||
return list.retainAll(c);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void clear() {
|
||||
list.clear();
|
||||
}
|
||||
|
||||
@Override
|
||||
public E get(int index) {
|
||||
return list.get(index);
|
||||
}
|
||||
|
||||
@Override
|
||||
public E set(int index, E element) {
|
||||
return list.set(index, element);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void add(int index, E element) {
|
||||
list.add(index, element);
|
||||
}
|
||||
|
||||
@Override
|
||||
public E remove(int index) {
|
||||
return list.remove(index);
|
||||
}
|
||||
|
||||
@Override
|
||||
public int indexOf(Object o) {
|
||||
return list.indexOf(o);
|
||||
}
|
||||
|
||||
@Override
|
||||
public int lastIndexOf(Object o) {
|
||||
return list.lastIndexOf(o);
|
||||
}
|
||||
|
||||
@Override
|
||||
public ListIterator<E> listIterator() {
|
||||
return list.listIterator();
|
||||
}
|
||||
|
||||
@Override
|
||||
public ListIterator<E> listIterator(int index) {
|
||||
return list.listIterator(index);
|
||||
}
|
||||
|
||||
@Override
|
||||
public List<E> subList(int fromIndex, int toIndex) {
|
||||
return list.subList(fromIndex, toIndex);
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,33 @@
|
||||
package net.lab1024.smartadmin.common.exception;
|
||||
/**
|
||||
*
|
||||
* [ 业务逻辑异常,全局异常拦截后统一返回ResponseCodeConst.SYSTEM_ERROR ]
|
||||
*
|
||||
* @version 1.0
|
||||
* @since JDK1.8
|
||||
* @author yandanyang
|
||||
* @company 1024lab.net
|
||||
* @copyright (c) 2019 1024lab.netInc. All rights reserved.
|
||||
* @date
|
||||
*/
|
||||
public class SmartBusinessException extends RuntimeException {
|
||||
|
||||
public SmartBusinessException() {
|
||||
}
|
||||
|
||||
public SmartBusinessException(String message) {
|
||||
super(message);
|
||||
}
|
||||
|
||||
public SmartBusinessException(String message, Throwable cause) {
|
||||
super(message, cause);
|
||||
}
|
||||
|
||||
public SmartBusinessException(Throwable cause) {
|
||||
super(cause);
|
||||
}
|
||||
|
||||
public SmartBusinessException(String message, Throwable cause, boolean enableSuppression, boolean writableStackTrace) {
|
||||
super(message, cause, enableSuppression, writableStackTrace);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,24 @@
|
||||
package net.lab1024.smartadmin.common.exception;
|
||||
|
||||
/**
|
||||
* [ 全局异常拦截后保留ResponseCode码的异常]
|
||||
*
|
||||
* @author yandanyang
|
||||
* @version 1.0
|
||||
* @company 1024lab.net
|
||||
* @copyright (c) 2018 1024lab.netInc. All rights reserved.
|
||||
* @date 2019/8/7 0007 下午 16:11
|
||||
* @since JDK1.8
|
||||
*/
|
||||
public class SmartResponseCodeException extends RuntimeException{
|
||||
private Integer code;
|
||||
|
||||
public SmartResponseCodeException(Integer code, String message) {
|
||||
super(message);
|
||||
this.code = code;
|
||||
}
|
||||
|
||||
public Integer getCode() {
|
||||
return code;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,90 @@
|
||||
package net.lab1024.smartadmin.common.heartbeat;
|
||||
|
||||
import com.google.common.util.concurrent.ThreadFactoryBuilder;
|
||||
import java.util.Date;
|
||||
import java.util.List;
|
||||
import java.util.concurrent.*;
|
||||
|
||||
|
||||
/**
|
||||
* @Description: 心跳服务
|
||||
* @Author: simajinqiang
|
||||
* @Date: 2018/7/9 16:26
|
||||
*/
|
||||
public abstract class AbstractHeartBeatCommand implements HeartBeatRecordCommendInterface {
|
||||
|
||||
|
||||
ScheduledExecutorService executorService;
|
||||
|
||||
int threadNum = 1;
|
||||
|
||||
/**
|
||||
* 项目路径
|
||||
*/
|
||||
private String projectPath;
|
||||
/**
|
||||
* 服务器ip(多网卡)
|
||||
*/
|
||||
private List<String> serverIps;
|
||||
/**
|
||||
* 进程号
|
||||
*/
|
||||
private Integer processNo;
|
||||
/**
|
||||
* 进程开启时间
|
||||
*/
|
||||
private Date processStartTime;
|
||||
|
||||
HeartBeatLogger logger;
|
||||
|
||||
/**
|
||||
* 初始化
|
||||
*/
|
||||
public void init(HeartBeatConfig config, HeartBeatLogger logger){
|
||||
this.handlerHeartBeat();
|
||||
ThreadFactory threadFactory = new ThreadFactoryBuilder().setNameFormat("AbstractHeartBeatCommand-%s").build();
|
||||
executorService = Executors.newScheduledThreadPool(threadNum, threadFactory);
|
||||
executorService.scheduleWithFixedDelay(new DoHeartBeat(), config.getDelayHandlerTime(), config.getIntervalTime(), TimeUnit.MILLISECONDS);
|
||||
}
|
||||
|
||||
public void handlerHeartBeat(){
|
||||
try {
|
||||
projectPath = HeatBeatRecordHelper.getProjectPath();
|
||||
serverIps = IpUtil.getLocalIPS();
|
||||
processNo = HeatBeatRecordHelper.getProcessID();
|
||||
processStartTime = HeatBeatRecordHelper.getStartTime();
|
||||
}catch (Throwable e){
|
||||
logger.error("get heart beat info error.", e);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* 销毁线程池
|
||||
*/
|
||||
public void destroy(){
|
||||
if (executorService != null && !executorService.isShutdown()) {
|
||||
executorService.shutdown();
|
||||
executorService = null;
|
||||
}
|
||||
}
|
||||
|
||||
public class DoHeartBeat implements Runnable{
|
||||
|
||||
@Override
|
||||
public void run() {
|
||||
try {
|
||||
HeartBeatRecordDTO heartBeatRecord = new HeartBeatRecordDTO();
|
||||
heartBeatRecord.setProjectPath(projectPath);
|
||||
heartBeatRecord.setServerIp(StringUtil.join(serverIps,";"));
|
||||
heartBeatRecord.setProcessNo(processNo);
|
||||
heartBeatRecord.setProcessStartTime(processStartTime);
|
||||
heartBeatRecord.setHeartBeatTime(new Date());
|
||||
handler(heartBeatRecord);
|
||||
}catch (Throwable t){
|
||||
logger.error("handler heartbeat error.", t);
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,29 @@
|
||||
package net.lab1024.smartadmin.common.heartbeat;
|
||||
|
||||
import lombok.Builder;
|
||||
import lombok.Data;
|
||||
|
||||
/**
|
||||
* [ ]
|
||||
*
|
||||
* @author yandanyang
|
||||
* @version 1.0
|
||||
* @company 1024lab.net
|
||||
* @copyright (c) 2018 1024lab.netInc. All rights reserved.
|
||||
* @date 2019/8/8 0008 下午 16:22
|
||||
* @since JDK1.8
|
||||
*/
|
||||
@Data
|
||||
@Builder
|
||||
public class HeartBeatConfig {
|
||||
|
||||
/**
|
||||
* 延迟执行时间
|
||||
*/
|
||||
private Long delayHandlerTime;
|
||||
|
||||
/**
|
||||
* 间隔执行时间
|
||||
*/
|
||||
private Long intervalTime;
|
||||
}
|
||||
@@ -0,0 +1,20 @@
|
||||
package net.lab1024.smartadmin.common.heartbeat;
|
||||
|
||||
/**
|
||||
* [ ]
|
||||
*
|
||||
* @author yandanyang
|
||||
* @version 1.0
|
||||
* @company 1024lab.net
|
||||
* @copyright (c) 2018 1024lab.netInc. All rights reserved.
|
||||
* @date 2019/8/8 0008 下午 16:23
|
||||
* @since JDK1.8
|
||||
*/
|
||||
public interface HeartBeatLogger {
|
||||
|
||||
void error(String string);
|
||||
|
||||
void error(String string, Throwable e);
|
||||
|
||||
void info(String string);
|
||||
}
|
||||
@@ -0,0 +1,17 @@
|
||||
package net.lab1024.smartadmin.common.heartbeat;
|
||||
|
||||
|
||||
|
||||
/**
|
||||
* @Description:
|
||||
* @Author: simajinqiang
|
||||
* @Date: 2018/7/9 14:06
|
||||
*/
|
||||
public interface HeartBeatRecordCommendInterface {
|
||||
/**
|
||||
* 处理
|
||||
* @param heartBeatRecord
|
||||
*/
|
||||
void handler(HeartBeatRecordDTO heartBeatRecord);
|
||||
|
||||
}
|
||||
@@ -0,0 +1,37 @@
|
||||
package net.lab1024.smartadmin.common.heartbeat;
|
||||
|
||||
import lombok.Data;
|
||||
|
||||
import java.util.Date;
|
||||
|
||||
/**
|
||||
* @Description: 心跳记录日志
|
||||
* @Author: simajinqiang
|
||||
* @Date: 2018/7/9 11:11
|
||||
*/
|
||||
@Data
|
||||
public class HeartBeatRecordDTO {
|
||||
|
||||
/**
|
||||
* 项目名字
|
||||
*/
|
||||
private String projectPath;
|
||||
/**
|
||||
* 服务器ip
|
||||
*/
|
||||
private String serverIp;
|
||||
/**
|
||||
* 进程号
|
||||
*/
|
||||
private Integer processNo;
|
||||
/**
|
||||
* 进程开启时间
|
||||
*/
|
||||
private Date processStartTime;
|
||||
/**
|
||||
* 心跳当前时间
|
||||
*/
|
||||
private Date heartBeatTime;
|
||||
|
||||
|
||||
}
|
||||
@@ -0,0 +1,45 @@
|
||||
package net.lab1024.smartadmin.common.heartbeat;
|
||||
|
||||
|
||||
import java.lang.management.ManagementFactory;
|
||||
import java.lang.management.RuntimeMXBean;
|
||||
import java.util.Date;
|
||||
|
||||
/**
|
||||
* @Description: 心跳工具类
|
||||
* @Author: simajinqiang
|
||||
* @Date: 2018/7/9 11:48
|
||||
*/
|
||||
public class HeatBeatRecordHelper {
|
||||
|
||||
/**
|
||||
* 获取进程号
|
||||
* @return
|
||||
*/
|
||||
public static final Integer getProcessID() {
|
||||
RuntimeMXBean runtimeMXBean = ManagementFactory.getRuntimeMXBean();
|
||||
return Integer.valueOf(runtimeMXBean.getName().split("@")[0])
|
||||
.intValue();
|
||||
}
|
||||
|
||||
/**
|
||||
* 获取项目名称
|
||||
* @return
|
||||
*/
|
||||
public static final String getProjectPath(){
|
||||
return System.getProperty("user.dir");
|
||||
}
|
||||
|
||||
/**
|
||||
* 获取进程启动时间
|
||||
* @return
|
||||
*/
|
||||
public static final Date getStartTime(){
|
||||
RuntimeMXBean runtimeMXBean = ManagementFactory.getRuntimeMXBean();
|
||||
return new Date(runtimeMXBean.getStartTime());
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
}
|
||||
@@ -0,0 +1,81 @@
|
||||
package net.lab1024.smartadmin.common.heartbeat;
|
||||
|
||||
import java.net.InetAddress;
|
||||
import java.net.NetworkInterface;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Enumeration;
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
* @Description: ip工具类
|
||||
* @Author: sbq
|
||||
* @CreateDate: 2019/8/8 10:33
|
||||
* @Version: 1.0
|
||||
*/
|
||||
public class IpUtil {
|
||||
/**
|
||||
* 获得服务器的IP地址
|
||||
*/
|
||||
public static String getLocalIP() {
|
||||
String sIP = "";
|
||||
InetAddress ip = null;
|
||||
try {
|
||||
boolean bFindIP = false;
|
||||
Enumeration<NetworkInterface> netInterfaces = (Enumeration<NetworkInterface>) NetworkInterface
|
||||
.getNetworkInterfaces();
|
||||
while (netInterfaces.hasMoreElements()) {
|
||||
if (bFindIP) {
|
||||
break;
|
||||
}
|
||||
NetworkInterface ni = (NetworkInterface) netInterfaces
|
||||
.nextElement();
|
||||
Enumeration<InetAddress> ips = ni.getInetAddresses();
|
||||
while (ips.hasMoreElements()) {
|
||||
ip = (InetAddress) ips.nextElement();
|
||||
if (!ip.isLoopbackAddress()
|
||||
&& ip.getHostAddress().matches(
|
||||
"(\\d{1,3}\\.){3}\\d{1,3}")) {
|
||||
bFindIP = true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
} catch (Exception e) {
|
||||
}
|
||||
if (null != ip) {
|
||||
sIP = ip.getHostAddress();
|
||||
}
|
||||
return sIP;
|
||||
}
|
||||
|
||||
/**
|
||||
* @Description: 获得服务器的IP地址(多网卡)
|
||||
* @Author: sbq
|
||||
* @CreateDate: 2019/8/8 10:34
|
||||
* @Version: 1.0
|
||||
*/
|
||||
public static List<String> getLocalIPS() {
|
||||
InetAddress ip = null;
|
||||
List<String> ipList = new ArrayList<String>();
|
||||
try {
|
||||
Enumeration<NetworkInterface> netInterfaces = (Enumeration<NetworkInterface>) NetworkInterface
|
||||
.getNetworkInterfaces();
|
||||
while (netInterfaces.hasMoreElements()) {
|
||||
NetworkInterface ni = (NetworkInterface) netInterfaces
|
||||
.nextElement();
|
||||
Enumeration<InetAddress> ips = ni.getInetAddresses();
|
||||
while (ips.hasMoreElements()) {
|
||||
ip = (InetAddress) ips.nextElement();
|
||||
if (!ip.isLoopbackAddress()
|
||||
&& ip.getHostAddress().matches(
|
||||
"(\\d{1,3}\\.){3}\\d{1,3}")) {
|
||||
ipList.add(ip.getHostAddress());
|
||||
}
|
||||
}
|
||||
}
|
||||
} catch (Exception e) {
|
||||
}
|
||||
return ipList;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,60 @@
|
||||
package net.lab1024.smartadmin.common.heartbeat;
|
||||
|
||||
import java.util.Iterator;
|
||||
|
||||
/**
|
||||
* [ ]
|
||||
*
|
||||
* @author yandanyang
|
||||
* @version 1.0
|
||||
* @company 1024lab.net
|
||||
* @copyright (c) 2018 1024lab.netInc. All rights reserved.
|
||||
* @date 2019/8/8 0008 下午 16:27
|
||||
* @since JDK1.8
|
||||
*/
|
||||
public class StringUtil {
|
||||
|
||||
|
||||
|
||||
public static String join(Iterable<?> iterable, String separator) {
|
||||
return iterable == null ? null : join(iterable.iterator(), separator);
|
||||
}
|
||||
|
||||
|
||||
public static String join(Iterator<?> iterator, String separator) {
|
||||
if (iterator == null) {
|
||||
return null;
|
||||
} else if (!iterator.hasNext()) {
|
||||
return "";
|
||||
} else {
|
||||
Object first = iterator.next();
|
||||
if (!iterator.hasNext()) {
|
||||
String result = toString(first);
|
||||
return result;
|
||||
} else {
|
||||
StringBuilder buf = new StringBuilder(256);
|
||||
if (first != null) {
|
||||
buf.append(first);
|
||||
}
|
||||
|
||||
while(iterator.hasNext()) {
|
||||
if (separator != null) {
|
||||
buf.append(separator);
|
||||
}
|
||||
|
||||
Object obj = iterator.next();
|
||||
if (obj != null) {
|
||||
buf.append(obj);
|
||||
}
|
||||
}
|
||||
|
||||
return buf.toString();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public static String toString(Object obj) {
|
||||
return obj == null ? "" : obj.toString();
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,21 @@
|
||||
package net.lab1024.smartadmin.common.json;
|
||||
|
||||
import com.fasterxml.jackson.core.JsonParser;
|
||||
import com.fasterxml.jackson.core.JsonProcessingException;
|
||||
import com.fasterxml.jackson.databind.DeserializationContext;
|
||||
import com.fasterxml.jackson.databind.JsonDeserializer;
|
||||
|
||||
import java.io.IOException;
|
||||
|
||||
public class LongJsonDeserializer extends JsonDeserializer<Long> {
|
||||
|
||||
@Override
|
||||
public Long deserialize(JsonParser jsonParser, DeserializationContext deserializationContext) throws IOException, JsonProcessingException {
|
||||
String value = jsonParser.getText();
|
||||
try {
|
||||
return value == null ? null : Long.parseLong(value);
|
||||
} catch (NumberFormatException e) {
|
||||
return null;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,19 @@
|
||||
package net.lab1024.smartadmin.common.json;
|
||||
|
||||
|
||||
import com.fasterxml.jackson.core.JsonGenerator;
|
||||
import com.fasterxml.jackson.core.JsonProcessingException;
|
||||
import com.fasterxml.jackson.databind.JsonSerializer;
|
||||
import com.fasterxml.jackson.databind.SerializerProvider;
|
||||
|
||||
import java.io.IOException;
|
||||
|
||||
public class LongJsonSerializer extends JsonSerializer<Long> {
|
||||
@Override
|
||||
public void serialize(Long value, JsonGenerator jsonGenerator, SerializerProvider serializerProvider) throws IOException, JsonProcessingException {
|
||||
String text = (value == null ? null : String.valueOf(value));
|
||||
if (text != null) {
|
||||
jsonGenerator.writeString(text);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,39 @@
|
||||
package net.lab1024.smartadmin.common.kaptcha;
|
||||
|
||||
import com.google.common.collect.Lists;
|
||||
|
||||
import java.awt.*;
|
||||
import java.util.List;
|
||||
import java.util.Random;
|
||||
|
||||
/**
|
||||
* [ 验证码颜色 ]
|
||||
*
|
||||
* @author yandanyang
|
||||
* @version 1.0
|
||||
* @company 1024lab.net
|
||||
* @copyright (c) 2018 1024lab.netInc. All rights reserved.
|
||||
* @date 2019/7/6 0006 上午 10:51
|
||||
* @since JDK1.8
|
||||
*/
|
||||
public class KaptchaColor {
|
||||
|
||||
public static Color getColor() {
|
||||
|
||||
List<Color> colors = Lists.newArrayList();
|
||||
colors.add(new Color(0, 135, 255));
|
||||
colors.add(new Color(51, 153, 51));
|
||||
colors.add(new Color(255, 102, 102));
|
||||
colors.add(new Color(255, 153, 0));
|
||||
colors.add(new Color(153, 102, 0));
|
||||
colors.add(new Color(153, 102, 153));
|
||||
colors.add(new Color(51, 153, 153));
|
||||
colors.add(new Color(102, 102, 255));
|
||||
colors.add(new Color(0, 102, 204));
|
||||
colors.add(new Color(204, 51, 51));
|
||||
colors.add(new Color(128, 153, 65));
|
||||
Random random = new Random();
|
||||
int colorIndex = random.nextInt(10);
|
||||
return colors.get(colorIndex);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,44 @@
|
||||
package net.lab1024.smartadmin.common.kaptcha;
|
||||
|
||||
import com.google.code.kaptcha.NoiseProducer;
|
||||
import com.google.code.kaptcha.util.Configurable;
|
||||
|
||||
import java.awt.*;
|
||||
import java.awt.image.BufferedImage;
|
||||
import java.util.Random;
|
||||
|
||||
/**
|
||||
* [ 验证码加噪处理 ]
|
||||
*
|
||||
* @author yandanyang
|
||||
* @version 1.0
|
||||
* @company 1024lab.net
|
||||
* @copyright (c) 2018 1024lab.netInc. All rights reserved.
|
||||
* @date 2019/7/6 0006 上午 10:47
|
||||
* @since JDK1.8
|
||||
*/
|
||||
public class KaptchaNoise extends Configurable implements NoiseProducer {
|
||||
public KaptchaNoise() {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void makeNoise(BufferedImage image, float factorOne, float factorTwo, float factorThree, float factorFour) {
|
||||
|
||||
int width = image.getWidth();
|
||||
int height = image.getHeight();
|
||||
Graphics2D graph = (Graphics2D)image.getGraphics();
|
||||
graph.setRenderingHints(new RenderingHints(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON));
|
||||
graph.setStroke(new BasicStroke(1.0f, BasicStroke.CAP_BUTT, BasicStroke.JOIN_BEVEL));
|
||||
Random random = new Random();
|
||||
int noiseLineNum = random.nextInt(3);
|
||||
if(noiseLineNum == 0){
|
||||
noiseLineNum = 1;
|
||||
}
|
||||
for (int i = 0; i < noiseLineNum; i++){
|
||||
graph.setColor(KaptchaColor.getColor());
|
||||
graph.drawLine(random.nextInt(width), random.nextInt(height), 10 + random.nextInt(20), 10 + random.nextInt(20));
|
||||
}
|
||||
|
||||
graph.dispose();
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,75 @@
|
||||
package net.lab1024.smartadmin.common.kaptcha;
|
||||
|
||||
import com.google.code.kaptcha.util.Configurable;
|
||||
|
||||
import java.awt.*;
|
||||
import java.awt.font.FontRenderContext;
|
||||
import java.awt.font.GlyphVector;
|
||||
import java.awt.image.BufferedImage;
|
||||
import java.util.Random;
|
||||
|
||||
/**
|
||||
* [ 验证码字体生成 ]
|
||||
*
|
||||
* @author yandanyang
|
||||
* @version 1.0
|
||||
* @company 1024lab.net
|
||||
* @copyright (c) 2018 1024lab.netInc. All rights reserved.
|
||||
* @date 2019/7/6 0006 上午 9:43
|
||||
* @since JDK1.8
|
||||
*/
|
||||
public class KaptchaWordRenderer extends Configurable implements com.google.code.kaptcha.text.WordRenderer {
|
||||
|
||||
public KaptchaWordRenderer() {
|
||||
}
|
||||
|
||||
@Override
|
||||
public BufferedImage renderWord(String word, int width, int height) {
|
||||
int fontSize = this.getConfig().getTextProducerFontSize();
|
||||
Font[] fonts = this.getConfig().getTextProducerFonts(fontSize);
|
||||
int charSpace = this.getConfig().getTextProducerCharSpace();
|
||||
BufferedImage image = new BufferedImage(width, height, 2);
|
||||
|
||||
Graphics2D g2D = image.createGraphics();
|
||||
g2D.setColor(Color.WHITE);
|
||||
RenderingHints hints = new RenderingHints(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);
|
||||
hints.add(new RenderingHints(RenderingHints.KEY_RENDERING, RenderingHints.VALUE_RENDER_QUALITY));
|
||||
g2D.setRenderingHints(hints);
|
||||
g2D.setStroke(new BasicStroke(1.0f, BasicStroke.CAP_BUTT, BasicStroke.JOIN_BEVEL));
|
||||
|
||||
FontRenderContext frc = g2D.getFontRenderContext();
|
||||
Random random = new Random();
|
||||
int startPosY = (height - fontSize) / 5 + fontSize;
|
||||
char[] wordChars = word.toCharArray();
|
||||
Font[] chosenFonts = new Font[wordChars.length];
|
||||
int[] charWidths = new int[wordChars.length];
|
||||
int widthNeeded = 0;
|
||||
|
||||
int startPosX;
|
||||
for(startPosX = 0; startPosX < wordChars.length; ++startPosX) {
|
||||
chosenFonts[startPosX] = fonts[random.nextInt(fonts.length)];
|
||||
char[] charToDraw = new char[]{wordChars[startPosX]};
|
||||
GlyphVector gv = chosenFonts[startPosX].createGlyphVector(frc, charToDraw);
|
||||
charWidths[startPosX] = (int)gv.getVisualBounds().getWidth();
|
||||
if (startPosX > 0) {
|
||||
widthNeeded += 2;
|
||||
}
|
||||
|
||||
widthNeeded += charWidths[startPosX];
|
||||
}
|
||||
|
||||
startPosX = (width - widthNeeded) / 2;
|
||||
|
||||
for(int i = 0; i < wordChars.length; ++i) {
|
||||
g2D.setColor(KaptchaColor.getColor());
|
||||
g2D.setFont(chosenFonts[i].deriveFont(Font.PLAIN));
|
||||
char[] charToDraw = new char[]{wordChars[i]};
|
||||
g2D.drawChars(charToDraw, 0, charToDraw.length, startPosX, startPosY);
|
||||
startPosX = startPosX + charWidths[i] + charSpace;
|
||||
}
|
||||
|
||||
return image;
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
@@ -0,0 +1,46 @@
|
||||
package net.lab1024.smartadmin.common.mybatis;
|
||||
|
||||
import lombok.extern.slf4j.Slf4j;
|
||||
import org.apache.ibatis.mapping.BoundSql;
|
||||
import org.apache.ibatis.mapping.MappedStatement;
|
||||
import org.apache.ibatis.plugin.*;
|
||||
import org.apache.ibatis.session.ResultHandler;
|
||||
import org.apache.ibatis.session.RowBounds;
|
||||
|
||||
import java.util.Properties;
|
||||
|
||||
/**
|
||||
* [ mybaits sql 拦截 ]
|
||||
*
|
||||
* @author zhuoda
|
||||
* @version 1.0
|
||||
* @company 1024lab.net
|
||||
* @copyright (c) 2019 1024lab.netInc. All rights reserved.
|
||||
* @date
|
||||
* @since JDK1.8
|
||||
*/
|
||||
@Intercepts({@Signature(type = org.apache.ibatis.executor.Executor.class, method = "query", args = {MappedStatement.class, Object.class, RowBounds.class, ResultHandler.class})})
|
||||
@Slf4j
|
||||
public class MyBatisSqlQuerySqlDebugPlugin implements Interceptor {
|
||||
|
||||
@Override
|
||||
public Object intercept(Invocation invocation) throws Throwable {
|
||||
MappedStatement mappedStatement = (MappedStatement) invocation.getArgs()[0];
|
||||
Object parameter = invocation.getArgs()[1];
|
||||
BoundSql boundSql = mappedStatement.getBoundSql(parameter);
|
||||
log.info(boundSql.getSql()+"\r\n"+boundSql.getParameterMappings().toString());
|
||||
Object obj = invocation.proceed();
|
||||
return obj;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Object plugin(Object arg0) {
|
||||
return Plugin.wrap(arg0,this);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setProperties(Properties arg0) {
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,44 @@
|
||||
package net.lab1024.smartadmin.common.mybatis;
|
||||
|
||||
import lombok.extern.slf4j.Slf4j;
|
||||
import org.apache.ibatis.mapping.BoundSql;
|
||||
import org.apache.ibatis.mapping.MappedStatement;
|
||||
import org.apache.ibatis.plugin.*;
|
||||
|
||||
import java.util.Properties;
|
||||
|
||||
/**
|
||||
* [ mybaits sql 拦截 ]
|
||||
*
|
||||
* @author zhuoda
|
||||
* @version 1.0
|
||||
* @company 1024lab.net
|
||||
* @copyright (c) 2019 1024lab.netInc. All rights reserved.
|
||||
* @date
|
||||
* @since JDK1.8
|
||||
*/
|
||||
@Intercepts({@Signature(type = org.apache.ibatis.executor.Executor.class, method = "update", args = {MappedStatement.class, Object.class})})
|
||||
@Slf4j
|
||||
public class MyBatisSqlUpdateSqlDebugPlugin implements Interceptor {
|
||||
|
||||
@Override
|
||||
public Object intercept(Invocation invocation) throws Throwable {
|
||||
MappedStatement mappedStatement = (MappedStatement) invocation.getArgs()[0];
|
||||
Object parameter = invocation.getArgs()[1];
|
||||
BoundSql boundSql = mappedStatement.getBoundSql(parameter);
|
||||
log.info(boundSql.getSql()+"\r\n"+boundSql.getParameterMappings().toString());
|
||||
Object obj = invocation.proceed();
|
||||
return obj;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Object plugin(Object arg0) {
|
||||
return Plugin.wrap(arg0,this);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setProperties(Properties arg0) {
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,134 @@
|
||||
package net.lab1024.smartadmin.common.reload;
|
||||
|
||||
import net.lab1024.smartadmin.common.reload.annotation.SmartReload;
|
||||
import net.lab1024.smartadmin.common.reload.domain.AbstractSmartReloadObject;
|
||||
import net.lab1024.smartadmin.common.reload.domain.AnnotationReloadObject;
|
||||
import net.lab1024.smartadmin.common.reload.domain.InterfaceReloadObject;
|
||||
import net.lab1024.smartadmin.common.reload.domain.entity.ReloadItem;
|
||||
import net.lab1024.smartadmin.common.reload.domain.entity.SmartReloadResult;
|
||||
import net.lab1024.smartadmin.common.reload.interfaces.SmartReloadCommandInterface;
|
||||
import net.lab1024.smartadmin.common.reload.interfaces.SmartReloadThreadLogger;
|
||||
import net.lab1024.smartadmin.common.reload.interfaces.SmartReloadable;
|
||||
|
||||
import java.lang.reflect.Method;
|
||||
import java.util.Map;
|
||||
import java.util.concurrent.ConcurrentHashMap;
|
||||
import java.util.concurrent.TimeUnit;
|
||||
|
||||
import static java.util.Objects.requireNonNull;
|
||||
|
||||
/**
|
||||
* SmartReloadManager 管理器
|
||||
* <p>
|
||||
* 可以在此类中添加 检测任务 以及注册 处理程序
|
||||
*
|
||||
* @author zhuoda
|
||||
*/
|
||||
public class SmartReloadManager {
|
||||
|
||||
private Map<String, AbstractSmartReloadObject> tagReloadObject;
|
||||
|
||||
private SmartReloadScheduler reloadScheduler;
|
||||
|
||||
private SmartReloadThreadLogger logger;
|
||||
|
||||
public SmartReloadManager(SmartReloadThreadLogger logger, int threadCount) {
|
||||
this.tagReloadObject = new ConcurrentHashMap<>();
|
||||
if (logger == null) {
|
||||
throw new ExceptionInInitializerError("SmartReloadLoggerImp cannot be null");
|
||||
}
|
||||
|
||||
if (threadCount < 1) {
|
||||
throw new ExceptionInInitializerError("threadCount must be greater than 1");
|
||||
}
|
||||
|
||||
this.logger = logger;
|
||||
this.reloadScheduler = new SmartReloadScheduler(this.logger, threadCount);
|
||||
}
|
||||
|
||||
/**
|
||||
* 默认创建单个线程
|
||||
*
|
||||
* @param logger
|
||||
*/
|
||||
public SmartReloadManager(SmartReloadThreadLogger logger) {
|
||||
this(logger, 1);
|
||||
}
|
||||
|
||||
/**
|
||||
* 停止
|
||||
*/
|
||||
public void shutdown() {
|
||||
reloadScheduler.shutdown();
|
||||
}
|
||||
|
||||
/**
|
||||
* 添加任务
|
||||
*
|
||||
* @param command SmartReloadCommand实现类
|
||||
* @param initialDelay 第一次执行前的延迟时间
|
||||
* @param delay 任务间隔时间
|
||||
* @param unit 延迟单位 TimeUnit 天、小时、分、秒等
|
||||
*/
|
||||
public void addCommand(SmartReloadCommandInterface command, long initialDelay, long delay, TimeUnit unit) {
|
||||
reloadScheduler.addCommand(command, initialDelay, delay, unit);
|
||||
}
|
||||
|
||||
/**
|
||||
* 注册 实现接口的方式
|
||||
*
|
||||
* @param tag
|
||||
* @param reloadable
|
||||
*/
|
||||
public void register(String tag, SmartReloadable reloadable) {
|
||||
requireNonNull(reloadable);
|
||||
requireNonNull(tag);
|
||||
if (tagReloadObject.containsKey(tag)) {
|
||||
logger.error("<<SmartReloadManager>> register duplicated tag reload : " + tag + " , and it will be cover!");
|
||||
}
|
||||
tagReloadObject.put(tag, new InterfaceReloadObject(reloadable));
|
||||
}
|
||||
|
||||
/**
|
||||
* 注册 要求此类必须包含使用了SmartReload注解的方法
|
||||
*
|
||||
* @param reloadObject
|
||||
*/
|
||||
public void register(Object reloadObject) {
|
||||
requireNonNull(reloadObject);
|
||||
Method[] declaredMethods = reloadObject.getClass().getDeclaredMethods();
|
||||
if (declaredMethods != null) {
|
||||
for (int i = 0; i < declaredMethods.length; i++) {
|
||||
Method method = declaredMethods[i];
|
||||
SmartReload annotation = method.getAnnotation(SmartReload.class);
|
||||
if (annotation != null) {
|
||||
String reloadTag = annotation.value();
|
||||
this.register(reloadTag, new AnnotationReloadObject(reloadObject, method));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private void register(String tag, AbstractSmartReloadObject reloadObject) {
|
||||
if (tagReloadObject.containsKey(tag)) {
|
||||
logger.error("<<SmartReloadManager>> register duplicated tag reload : " + tag + " , and it will be cover!");
|
||||
}
|
||||
tagReloadObject.put(tag, reloadObject);
|
||||
}
|
||||
|
||||
/**
|
||||
* Reload 已注册的ReloadItem
|
||||
*
|
||||
* @param reloadItem
|
||||
* @return SmartReloadResult
|
||||
*/
|
||||
public SmartReloadResult doReload(ReloadItem reloadItem) {
|
||||
AbstractSmartReloadObject reloadObject = tagReloadObject.get(reloadItem.getTag());
|
||||
if (reloadObject != null) {
|
||||
return reloadObject.reload(reloadItem);
|
||||
}
|
||||
// 返回注册结果
|
||||
return new SmartReloadResult(reloadItem.getTag(), reloadItem.getArgs(), reloadItem.getIdentification(), false, "No registered reload handler was found");
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,87 @@
|
||||
package net.lab1024.smartadmin.common.reload;
|
||||
|
||||
import net.lab1024.smartadmin.common.reload.interfaces.SmartReloadCommandInterface;
|
||||
import net.lab1024.smartadmin.common.reload.interfaces.SmartReloadThreadLogger;
|
||||
|
||||
import java.util.concurrent.ScheduledThreadPoolExecutor;
|
||||
import java.util.concurrent.ThreadFactory;
|
||||
import java.util.concurrent.TimeUnit;
|
||||
import java.util.concurrent.atomic.AtomicInteger;
|
||||
|
||||
/**
|
||||
* Reload 调度器
|
||||
*
|
||||
* @author zhuoda
|
||||
*/
|
||||
public class SmartReloadScheduler {
|
||||
|
||||
private ScheduledThreadPoolExecutor executor;
|
||||
|
||||
private SmartReloadThreadLogger logger;
|
||||
|
||||
SmartReloadScheduler(SmartReloadThreadLogger logger, int threadCount) {
|
||||
this.executor = new ScheduledThreadPoolExecutor(threadCount, new SmartReloadSchedulerThreadFactory());
|
||||
this.logger = logger;
|
||||
}
|
||||
|
||||
void shutdown() {
|
||||
try {
|
||||
executor.shutdown();
|
||||
} catch (Throwable e) {
|
||||
logger.error("<<SmartReloadScheduler>> shutdown ", e);
|
||||
}
|
||||
}
|
||||
|
||||
void addCommand(SmartReloadCommandInterface command, long initialDelay, long delay, TimeUnit unit) {
|
||||
executor.scheduleWithFixedDelay(new ScheduleRunnable(command, this.logger), initialDelay, delay, unit);
|
||||
}
|
||||
|
||||
static class ScheduleRunnable implements Runnable {
|
||||
|
||||
private SmartReloadCommandInterface command;
|
||||
|
||||
private SmartReloadThreadLogger logger;
|
||||
|
||||
public ScheduleRunnable(SmartReloadCommandInterface command, SmartReloadThreadLogger logger) {
|
||||
this.command = command;
|
||||
this.logger = logger;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void run() {
|
||||
try {
|
||||
command.doTask();
|
||||
} catch (Throwable e) {
|
||||
logger.error("", e);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static class SmartReloadSchedulerThreadFactory implements ThreadFactory {
|
||||
|
||||
private static final AtomicInteger poolNumber = new AtomicInteger(1);
|
||||
|
||||
private final ThreadGroup group;
|
||||
|
||||
private final AtomicInteger threadNumber = new AtomicInteger(1);
|
||||
|
||||
private final String namePrefix;
|
||||
|
||||
SmartReloadSchedulerThreadFactory() {
|
||||
SecurityManager s = System.getSecurityManager();
|
||||
group = (s != null) ? s.getThreadGroup() : Thread.currentThread().getThreadGroup();
|
||||
namePrefix = "smartreload-" + poolNumber.getAndIncrement() + "-thread-";
|
||||
}
|
||||
|
||||
@Override
|
||||
public Thread newThread(Runnable r) {
|
||||
Thread t = new Thread(group, r, namePrefix + threadNumber.getAndIncrement(), 0);
|
||||
if (t.isDaemon())
|
||||
t.setDaemon(false);
|
||||
if (t.getPriority() != Thread.NORM_PRIORITY)
|
||||
t.setPriority(Thread.NORM_PRIORITY);
|
||||
return t;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,66 @@
|
||||
package net.lab1024.smartadmin.common.reload.abstracts;
|
||||
|
||||
import net.lab1024.smartadmin.common.reload.SmartReloadManager;
|
||||
import net.lab1024.smartadmin.common.reload.domain.entity.ReloadItem;
|
||||
import net.lab1024.smartadmin.common.reload.interfaces.SmartReloadCommandInterface;
|
||||
|
||||
import java.util.List;
|
||||
import java.util.concurrent.ConcurrentHashMap;
|
||||
|
||||
/**
|
||||
* 检测是否 Reload 的类
|
||||
*
|
||||
* @author zhuoda
|
||||
*/
|
||||
public abstract class AbstractSmartReloadCommand implements SmartReloadCommandInterface {
|
||||
|
||||
/**
|
||||
* 当前ReloadItem的存储器
|
||||
*/
|
||||
private ConcurrentHashMap<String, String> currentTags = null;
|
||||
|
||||
/**
|
||||
* Reload的执行类
|
||||
*/
|
||||
private SmartReloadManager reloadManager;
|
||||
|
||||
public AbstractSmartReloadCommand(SmartReloadManager reloadManager) {
|
||||
this.reloadManager = reloadManager;
|
||||
this.currentTags = new ConcurrentHashMap<>();
|
||||
// 初始获取ReloadItem数据
|
||||
List<ReloadItem> readTagStatesFromDb = readReloadItem();
|
||||
if (readTagStatesFromDb != null) {
|
||||
for (ReloadItem reloadItem : readTagStatesFromDb) {
|
||||
String tag = reloadItem.getTag();
|
||||
String tagChangeIdentifier = reloadItem.getIdentification();
|
||||
this.currentTags.put(tag, tagChangeIdentifier);
|
||||
}
|
||||
}
|
||||
}
|
||||
/**
|
||||
* 任务:
|
||||
* 读取数据库中 ReloadItem 数据
|
||||
* 校验是否发生变化
|
||||
* 执行重加载动作
|
||||
*/
|
||||
@Override
|
||||
public void doTask() {
|
||||
// 获取数据库数据
|
||||
List<ReloadItem> readTagStatesFromDb = readReloadItem();
|
||||
String tag;
|
||||
String tagIdentifier;
|
||||
String preTagChangeIdentifier;
|
||||
for (ReloadItem reloadItem : readTagStatesFromDb) {
|
||||
tag = reloadItem.getTag();
|
||||
tagIdentifier = reloadItem.getIdentification();
|
||||
preTagChangeIdentifier = currentTags.get(tag);
|
||||
// 数据不一致
|
||||
if (preTagChangeIdentifier == null || ! preTagChangeIdentifier.equals(tagIdentifier)) {
|
||||
// 更新map数据
|
||||
currentTags.put(tag, tagIdentifier);
|
||||
// 执行重新加载此项的动作
|
||||
handleReloadResult(this.reloadManager.doReload(reloadItem));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,67 @@
|
||||
package net.lab1024.smartadmin.common.reload.abstracts;
|
||||
|
||||
import net.lab1024.smartadmin.common.reload.SmartReloadManager;
|
||||
import net.lab1024.smartadmin.common.reload.domain.entity.ReloadItem;
|
||||
import net.lab1024.smartadmin.common.reload.interfaces.SmartReloadCommandInterface;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
|
||||
import java.util.List;
|
||||
import java.util.concurrent.ConcurrentHashMap;
|
||||
|
||||
/**
|
||||
* 检测是否 Reload 的类
|
||||
*
|
||||
* @author zhuoda
|
||||
*/
|
||||
public abstract class AbstractSmartReloadCommand4Spring implements SmartReloadCommandInterface {
|
||||
|
||||
/**
|
||||
* 当前ReloadItem的存储器
|
||||
*/
|
||||
protected ConcurrentHashMap<String, String> currentTags = new ConcurrentHashMap<>();
|
||||
|
||||
/**
|
||||
* Reload的执行类
|
||||
*/
|
||||
@Autowired
|
||||
protected SmartReloadManager reloadManager;
|
||||
|
||||
// @PostConstruct
|
||||
public void init() {
|
||||
List<ReloadItem> readTagStatesFromDb = readReloadItem();
|
||||
if (readTagStatesFromDb != null) {
|
||||
for (ReloadItem reloadItem : readTagStatesFromDb) {
|
||||
String tag = reloadItem.getTag();
|
||||
String tagChangeIdentifier = reloadItem.getIdentification();
|
||||
this.currentTags.put(tag, tagChangeIdentifier);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* 任务:
|
||||
* 读取数据库中 ReloadItem 数据
|
||||
* 校验是否发生变化
|
||||
* 执行重加载动作
|
||||
*/
|
||||
@Override
|
||||
public void doTask() {
|
||||
// 获取数据库数据
|
||||
List<ReloadItem> readTagStatesFromDb = readReloadItem();
|
||||
String tag;
|
||||
String tagIdentifier;
|
||||
String preTagChangeIdentifier;
|
||||
for (ReloadItem reloadItem : readTagStatesFromDb) {
|
||||
tag = reloadItem.getTag();
|
||||
tagIdentifier = reloadItem.getIdentification();
|
||||
preTagChangeIdentifier = currentTags.get(tag);
|
||||
// 数据不一致
|
||||
if (preTagChangeIdentifier == null || ! preTagChangeIdentifier.equals(tagIdentifier)) {
|
||||
// 更新map数据
|
||||
currentTags.put(tag, tagIdentifier);
|
||||
// 执行重新加载此项的动作
|
||||
handleReloadResult(this.reloadManager.doReload(reloadItem));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,18 @@
|
||||
package net.lab1024.smartadmin.common.reload.annotation;
|
||||
|
||||
import java.lang.annotation.ElementType;
|
||||
import java.lang.annotation.Retention;
|
||||
import java.lang.annotation.RetentionPolicy;
|
||||
import java.lang.annotation.Target;
|
||||
|
||||
/**
|
||||
* 定义 SmartReload 注解
|
||||
*
|
||||
* @author zhuoda
|
||||
*/
|
||||
@Target(ElementType.METHOD)
|
||||
@Retention(RetentionPolicy.RUNTIME)
|
||||
public @interface SmartReload {
|
||||
|
||||
String value();
|
||||
}
|
||||
@@ -0,0 +1,31 @@
|
||||
package net.lab1024.smartadmin.common.reload.domain;
|
||||
|
||||
import net.lab1024.smartadmin.common.reload.domain.entity.ReloadItem;
|
||||
import net.lab1024.smartadmin.common.reload.domain.entity.SmartReloadResult;
|
||||
|
||||
import java.io.PrintWriter;
|
||||
import java.io.StringWriter;
|
||||
/**
|
||||
* AbstractSmartReloadObject 处理程序的抽象类
|
||||
*
|
||||
* @author zhuoda
|
||||
*/
|
||||
public abstract class AbstractSmartReloadObject {
|
||||
|
||||
protected String getStackTrace(Throwable e) {
|
||||
StringWriter sw = new StringWriter();
|
||||
PrintWriter pw = new PrintWriter(sw);
|
||||
e.printStackTrace(pw);
|
||||
return sw.toString();
|
||||
}
|
||||
|
||||
/**
|
||||
* 通过reloadItem参数reload,获得结果
|
||||
*
|
||||
* @param reloadItem
|
||||
* @return boolean
|
||||
* @author zhuokongming
|
||||
* @date 2016年10月21日 下午2:09:44
|
||||
*/
|
||||
public abstract SmartReloadResult reload(ReloadItem reloadItem);
|
||||
}
|
||||
@@ -0,0 +1,44 @@
|
||||
package net.lab1024.smartadmin.common.reload.domain;
|
||||
|
||||
import net.lab1024.smartadmin.common.reload.annotation.SmartReload;
|
||||
import net.lab1024.smartadmin.common.reload.domain.entity.ReloadItem;
|
||||
import net.lab1024.smartadmin.common.reload.domain.entity.SmartReloadResult;
|
||||
|
||||
import java.lang.reflect.Method;
|
||||
|
||||
/**
|
||||
* Reload 处理程序的实现类
|
||||
* 用于包装以注解 SmartReload 实现的处理类
|
||||
*
|
||||
* @author zhuoda
|
||||
*/
|
||||
public class AnnotationReloadObject extends AbstractSmartReloadObject {
|
||||
|
||||
private Object reloadObject;
|
||||
|
||||
private Method method;
|
||||
|
||||
public AnnotationReloadObject(Object reloadObject, Method method) {
|
||||
super();
|
||||
this.reloadObject = reloadObject;
|
||||
this.method = method;
|
||||
this.method.setAccessible(true);
|
||||
}
|
||||
|
||||
@Override
|
||||
public SmartReloadResult reload(ReloadItem reloadItem) {
|
||||
SmartReloadResult result = new SmartReloadResult();
|
||||
String tag = method.getAnnotation(SmartReload.class).value();
|
||||
result.setTag(tag);
|
||||
result.setArgs(reloadItem.getArgs());
|
||||
result.setIdentification(reloadItem.getIdentification());
|
||||
try {
|
||||
Object invoke = method.invoke(reloadObject, reloadItem.getArgs());
|
||||
result.setResult((Boolean) invoke);
|
||||
} catch (Throwable e) {
|
||||
result.setException(getStackTrace(e));
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,37 @@
|
||||
package net.lab1024.smartadmin.common.reload.domain;
|
||||
|
||||
import net.lab1024.smartadmin.common.reload.domain.entity.ReloadItem;
|
||||
import net.lab1024.smartadmin.common.reload.domain.entity.SmartReloadResult;
|
||||
import net.lab1024.smartadmin.common.reload.interfaces.SmartReloadable;
|
||||
|
||||
/**
|
||||
* Reload 处理程序的实现类
|
||||
* 用于处理以接口实现的处理类
|
||||
*
|
||||
* @author zhuoda
|
||||
*/
|
||||
public class InterfaceReloadObject extends AbstractSmartReloadObject {
|
||||
|
||||
private SmartReloadable object;
|
||||
|
||||
public InterfaceReloadObject(SmartReloadable object) {
|
||||
super();
|
||||
this.object = object;
|
||||
}
|
||||
|
||||
@Override
|
||||
public SmartReloadResult reload(ReloadItem reloadItem) {
|
||||
SmartReloadResult reloadResult = new SmartReloadResult();
|
||||
reloadResult.setArgs(reloadItem.getArgs());
|
||||
reloadResult.setIdentification(reloadItem.getIdentification());
|
||||
reloadResult.setTag(reloadItem.getTag());
|
||||
try {
|
||||
boolean res = object.reload(reloadItem);
|
||||
reloadResult.setResult(res);
|
||||
} catch (Throwable e) {
|
||||
reloadResult.setException(getStackTrace(e));
|
||||
}
|
||||
return reloadResult;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,55 @@
|
||||
package net.lab1024.smartadmin.common.reload.domain.entity;
|
||||
/**
|
||||
* ReloadItem 类
|
||||
*
|
||||
* @author zhuoda
|
||||
*/
|
||||
public class ReloadItem {
|
||||
|
||||
/**
|
||||
* 项名称
|
||||
*/
|
||||
private String tag;
|
||||
|
||||
/**
|
||||
* 参数
|
||||
*/
|
||||
private String args;
|
||||
|
||||
/**
|
||||
* 标识
|
||||
*/
|
||||
private String identification;
|
||||
|
||||
public ReloadItem() {
|
||||
|
||||
}
|
||||
public ReloadItem(String tag, String identification, String args) {
|
||||
this.tag = tag;
|
||||
this.identification = identification;
|
||||
this.args = args;
|
||||
}
|
||||
|
||||
public String getTag() {
|
||||
return tag;
|
||||
}
|
||||
public void setTag(String tag) {
|
||||
this.tag = tag;
|
||||
}
|
||||
public String getIdentification() {
|
||||
return identification;
|
||||
}
|
||||
public void setIdentification(String identification) {
|
||||
this.identification = identification;
|
||||
}
|
||||
public String getArgs() {
|
||||
return args;
|
||||
}
|
||||
public void setArgs(String args) {
|
||||
this.args = args;
|
||||
}
|
||||
@Override
|
||||
public String toString() {
|
||||
return "ReloadItem{" + "tag='" + tag + '\'' + ", identification='" + identification + '\'' + ", args='" + args + '\'' + '}';
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,102 @@
|
||||
package net.lab1024.smartadmin.common.reload.domain.entity;
|
||||
/**
|
||||
* t_reload_result 表 实体类
|
||||
*
|
||||
* @author zhuoda
|
||||
*/
|
||||
public class SmartReloadResult {
|
||||
|
||||
/**
|
||||
* 项名称
|
||||
*/
|
||||
private String tag;
|
||||
|
||||
/**
|
||||
* 参数
|
||||
*/
|
||||
private String args;
|
||||
|
||||
/**
|
||||
* 标识
|
||||
*/
|
||||
private String identification;
|
||||
|
||||
/**
|
||||
* 处理结果
|
||||
*/
|
||||
private boolean result;
|
||||
|
||||
/**
|
||||
* 异常说明
|
||||
*/
|
||||
private String exception;
|
||||
|
||||
public SmartReloadResult() {
|
||||
}
|
||||
|
||||
public SmartReloadResult(String tag, String args, boolean result, String exception) {
|
||||
this.tag = tag;
|
||||
this.args = args;
|
||||
this.result = result;
|
||||
this.exception = exception;
|
||||
}
|
||||
|
||||
public SmartReloadResult(String tag, String args, String identification, boolean result, String exception) {
|
||||
this.tag = tag;
|
||||
this.args = args;
|
||||
this.identification = identification;
|
||||
this.result = result;
|
||||
this.exception = exception;
|
||||
}
|
||||
|
||||
public void setTag(String tag) {
|
||||
this.tag = tag;
|
||||
}
|
||||
|
||||
public void setArgs(String args) {
|
||||
this.args = args;
|
||||
}
|
||||
|
||||
public void setIdentification(String identification) {
|
||||
this.identification = identification;
|
||||
}
|
||||
|
||||
public void setResult(boolean result) {
|
||||
this.result = result;
|
||||
}
|
||||
|
||||
public void setException(String exception) {
|
||||
this.exception = exception;
|
||||
}
|
||||
|
||||
public String getTag() {
|
||||
return tag;
|
||||
}
|
||||
|
||||
public String getArgs() {
|
||||
return args;
|
||||
}
|
||||
|
||||
public String getIdentification() {
|
||||
return identification;
|
||||
}
|
||||
|
||||
public boolean isResult() {
|
||||
return result;
|
||||
}
|
||||
|
||||
public String getException() {
|
||||
return exception;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return "SmartReloadResult{" +
|
||||
"tag='" + tag + '\'' +
|
||||
", args='" + args + '\'' +
|
||||
", identification='" + identification + '\'' +
|
||||
", result=" + result +
|
||||
", exception='" + exception + '\'' +
|
||||
'}';
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,38 @@
|
||||
package net.lab1024.smartadmin.common.reload.interfaces;
|
||||
|
||||
import net.lab1024.smartadmin.common.reload.domain.entity.ReloadItem;
|
||||
import net.lab1024.smartadmin.common.reload.domain.entity.SmartReloadResult;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
* 检测是否 Reload 的类
|
||||
*
|
||||
* @author zhuoda
|
||||
*/
|
||||
public interface SmartReloadCommandInterface {
|
||||
|
||||
/**
|
||||
* 任务:
|
||||
* 读取数据库中 ReloadItem 数据
|
||||
* 校验是否发生变化
|
||||
* 执行重加载动作
|
||||
*/
|
||||
void doTask();
|
||||
|
||||
/**
|
||||
* 该方法返回一个List<ReloadItem></>:<br>
|
||||
* ReloadItem对象的tagIdentify为:该tag的 状态(状态其实就是个字符串,如果该字符串跟上次有变化则进行reload操作)<br>
|
||||
* ReloadItem对象的args为: reload操作需要的参数<br><br>
|
||||
*
|
||||
* @return List<ReloadItem>
|
||||
*/
|
||||
List<ReloadItem> readReloadItem();
|
||||
|
||||
/**
|
||||
* 处理Reload结果
|
||||
*
|
||||
* @param reloadResult
|
||||
*/
|
||||
void handleReloadResult(SmartReloadResult reloadResult);
|
||||
}
|
||||
@@ -0,0 +1,12 @@
|
||||
package net.lab1024.smartadmin.common.reload.interfaces;
|
||||
|
||||
/**
|
||||
* SmartReloadThreadLogger 日志类
|
||||
*/
|
||||
public interface SmartReloadThreadLogger {
|
||||
|
||||
void error(String string);
|
||||
|
||||
void error(String string, Throwable e);
|
||||
|
||||
}
|
||||
@@ -0,0 +1,19 @@
|
||||
package net.lab1024.smartadmin.common.reload.interfaces;
|
||||
|
||||
import net.lab1024.smartadmin.common.reload.domain.entity.ReloadItem;
|
||||
|
||||
/**
|
||||
* reload 接口<br>
|
||||
* 需要reload的业务实现类
|
||||
*/
|
||||
@FunctionalInterface
|
||||
public interface SmartReloadable {
|
||||
|
||||
/**
|
||||
* reload
|
||||
*
|
||||
* @param reloadItem
|
||||
* @return boolean
|
||||
*/
|
||||
boolean reload(ReloadItem reloadItem);
|
||||
}
|
||||
@@ -0,0 +1,89 @@
|
||||
/*
|
||||
*
|
||||
* Copyright 2015 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*
|
||||
*
|
||||
*/
|
||||
|
||||
package net.lab1024.smartadmin.common.swagger;
|
||||
|
||||
import net.lab1024.smartadmin.common.anno.ApiModelPropertyEnum;
|
||||
import net.lab1024.smartadmin.common.domain.BaseEnum;
|
||||
import com.google.common.base.Function;
|
||||
import com.google.common.base.Optional;
|
||||
import org.apache.commons.lang3.StringUtils;
|
||||
import org.springframework.core.annotation.AnnotationUtils;
|
||||
import springfox.documentation.spi.DocumentationType;
|
||||
import springfox.documentation.spi.schema.ModelPropertyBuilderPlugin;
|
||||
import springfox.documentation.spi.schema.contexts.ModelPropertyContext;
|
||||
import springfox.documentation.swagger.common.SwaggerPluginSupport;
|
||||
|
||||
import java.lang.reflect.AnnotatedElement;
|
||||
|
||||
import static springfox.documentation.schema.Annotations.findPropertyAnnotation;
|
||||
|
||||
/**
|
||||
* swagger 用于说明枚举类字段说明
|
||||
* SWAGGER_PLUGIN_ORDER+1 是将此配置放在原来的后面执行
|
||||
*
|
||||
* @author listen
|
||||
* @date 2019年5月16日 15:36:56
|
||||
*/
|
||||
public class SmartSwaggerApiModelEnumPlugin implements ModelPropertyBuilderPlugin {
|
||||
|
||||
@Override
|
||||
public void apply(ModelPropertyContext context) {
|
||||
Optional<ApiModelPropertyEnum> annotation = Optional.absent();
|
||||
|
||||
if (context.getAnnotatedElement().isPresent()) {
|
||||
annotation = annotation.or(findApiModePropertyAnnotation(context.getAnnotatedElement().get()));
|
||||
}
|
||||
if (context.getBeanPropertyDefinition().isPresent()) {
|
||||
annotation = annotation.or(findPropertyAnnotation(context.getBeanPropertyDefinition().get(), ApiModelPropertyEnum.class));
|
||||
}
|
||||
|
||||
if (annotation.isPresent()) {
|
||||
Class<? extends BaseEnum> aClass = annotation.get().value();
|
||||
String enumInfo = BaseEnum.getInfo(aClass);
|
||||
String enumDesc = annotation.get().enumDesc();
|
||||
context.getBuilder().required(annotation.transform(toIsRequired()).or(false))
|
||||
.description(enumDesc +":"+enumInfo)
|
||||
.example(annotation.transform(toExample()).orNull());
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean supports(DocumentationType delimiter) {
|
||||
return SwaggerPluginSupport.pluginDoesApply(delimiter);
|
||||
}
|
||||
|
||||
static Function<ApiModelPropertyEnum, Boolean> toIsRequired() {
|
||||
return annotation -> annotation.required();
|
||||
}
|
||||
|
||||
public static Optional<ApiModelPropertyEnum> findApiModePropertyAnnotation(AnnotatedElement annotated) {
|
||||
return Optional.fromNullable(AnnotationUtils.getAnnotation(annotated, ApiModelPropertyEnum.class));
|
||||
}
|
||||
|
||||
static Function<ApiModelPropertyEnum, String> toExample() {
|
||||
return annotation -> {
|
||||
String example = annotation.example();
|
||||
if (StringUtils.isBlank(example)) {
|
||||
return "";
|
||||
}
|
||||
return example;
|
||||
};
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,73 @@
|
||||
package net.lab1024.smartadmin.common.validator.bigdecimal;
|
||||
|
||||
import net.lab1024.smartadmin.util.SmartBigDecimalUtil;
|
||||
|
||||
import javax.validation.ConstraintValidator;
|
||||
import javax.validation.ConstraintValidatorContext;
|
||||
import java.math.BigDecimal;
|
||||
|
||||
/**
|
||||
* BigDecimal 类校验器
|
||||
*
|
||||
* @author listen
|
||||
* @date 2018年3月20日 13:51:46
|
||||
*/
|
||||
public class BigDecimalValidator implements ConstraintValidator<CheckBigDecimal, BigDecimal> {
|
||||
|
||||
/**
|
||||
* 获取定义的数值
|
||||
*/
|
||||
private BigDecimal value;
|
||||
|
||||
/**
|
||||
* 获取比较符
|
||||
*/
|
||||
private ComparisonSymbolEnum symbolEnum;
|
||||
|
||||
/**
|
||||
* 是否必须
|
||||
*/
|
||||
private boolean required;
|
||||
|
||||
@Override
|
||||
public void initialize(CheckBigDecimal constraintAnnotation) {
|
||||
// 初始化属性
|
||||
value = new BigDecimal(constraintAnnotation.value());
|
||||
symbolEnum = constraintAnnotation.symbolEnum();
|
||||
required = constraintAnnotation.required();
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isValid(BigDecimal decimal, ConstraintValidatorContext constraintValidatorContext) {
|
||||
|
||||
// 如果数值为空,校验是否必须
|
||||
if (null == decimal) {
|
||||
return ! required;
|
||||
}
|
||||
|
||||
// 根据操作符,校验结果
|
||||
switch (symbolEnum) {
|
||||
// 等于
|
||||
case EQUAL:
|
||||
return SmartBigDecimalUtil.equals(decimal, value);
|
||||
// 不等于
|
||||
case NOT_EQUAL:
|
||||
return ! SmartBigDecimalUtil.equals(decimal, value);
|
||||
// 小于
|
||||
case LESS_THAN:
|
||||
return SmartBigDecimalUtil.isLessThan(decimal, value);
|
||||
// 小于等于
|
||||
case LESS_THAN_OR_EQUAL:
|
||||
return SmartBigDecimalUtil.isLessThan(decimal, value) || SmartBigDecimalUtil.equals(decimal, value);
|
||||
// 大于
|
||||
case GREATER_THAN:
|
||||
return SmartBigDecimalUtil.isGreaterThan(decimal, value);
|
||||
// 大于等于
|
||||
case GREATER_THAN_OR_EQUAL:
|
||||
return SmartBigDecimalUtil.isGreaterThan(decimal, value) || SmartBigDecimalUtil.equals(decimal, value);
|
||||
default:
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,53 @@
|
||||
package net.lab1024.smartadmin.common.validator.bigdecimal;
|
||||
|
||||
import javax.validation.Constraint;
|
||||
import javax.validation.Payload;
|
||||
import java.lang.annotation.ElementType;
|
||||
import java.lang.annotation.Retention;
|
||||
import java.lang.annotation.RetentionPolicy;
|
||||
import java.lang.annotation.Target;
|
||||
|
||||
/**
|
||||
* 自定义的属性校验注解
|
||||
*
|
||||
* @author listen
|
||||
* @date 2018年3月20日 13:53:33
|
||||
*/
|
||||
@Target(ElementType.FIELD)
|
||||
@Retention(RetentionPolicy.RUNTIME)
|
||||
@Constraint(validatedBy = BigDecimalValidator.class)// 自定义验证的处理类
|
||||
public @interface CheckBigDecimal {
|
||||
|
||||
/**
|
||||
* 与这个数值校验
|
||||
*
|
||||
* @return
|
||||
*/
|
||||
String value();
|
||||
|
||||
/**
|
||||
* 比较符 请使用 ComparisonSymbolEnum 枚举类
|
||||
*
|
||||
* @return
|
||||
*/
|
||||
ComparisonSymbolEnum symbolEnum();
|
||||
|
||||
/**
|
||||
* 默认的错误提示信息
|
||||
*
|
||||
* @return String
|
||||
*/
|
||||
String message() default "非法的数值";
|
||||
|
||||
/**
|
||||
* 是否必须 : 默认 true
|
||||
*
|
||||
* @return boolean
|
||||
*/
|
||||
boolean required() default true;
|
||||
|
||||
//下面这两个属性必须添加 :不然会报错
|
||||
Class<?>[] groups() default {};
|
||||
|
||||
Class<? extends Payload>[] payload() default {};
|
||||
}
|
||||
@@ -0,0 +1,40 @@
|
||||
package net.lab1024.smartadmin.common.validator.bigdecimal;
|
||||
|
||||
/**
|
||||
* 比较符枚举类
|
||||
*
|
||||
* @author listen
|
||||
* @date 2018/03/20 14:01
|
||||
*/
|
||||
public enum ComparisonSymbolEnum {
|
||||
|
||||
/**
|
||||
* 等于
|
||||
*/
|
||||
EQUAL,
|
||||
|
||||
/**
|
||||
* 不等于
|
||||
*/
|
||||
NOT_EQUAL,
|
||||
|
||||
/**
|
||||
* 小于
|
||||
*/
|
||||
LESS_THAN,
|
||||
|
||||
/**
|
||||
* 小于等于
|
||||
*/
|
||||
LESS_THAN_OR_EQUAL,
|
||||
|
||||
/**
|
||||
* 大于
|
||||
*/
|
||||
GREATER_THAN,
|
||||
|
||||
/**
|
||||
* 大于等于
|
||||
*/
|
||||
GREATER_THAN_OR_EQUAL,
|
||||
}
|
||||
@@ -0,0 +1,50 @@
|
||||
package net.lab1024.smartadmin.common.validator.en;
|
||||
|
||||
|
||||
import net.lab1024.smartadmin.common.domain.BaseEnum;
|
||||
|
||||
import javax.validation.Constraint;
|
||||
import javax.validation.Payload;
|
||||
import java.lang.annotation.ElementType;
|
||||
import java.lang.annotation.Retention;
|
||||
import java.lang.annotation.RetentionPolicy;
|
||||
import java.lang.annotation.Target;
|
||||
|
||||
/**
|
||||
* 自定义的属性校验注解
|
||||
* 为了方便与校验属性的值是否为合法的枚举值
|
||||
*
|
||||
* @author listen
|
||||
* @date 2017/11/11 15:31
|
||||
*/
|
||||
@Target(ElementType.FIELD)
|
||||
@Retention(RetentionPolicy.RUNTIME)
|
||||
@Constraint(validatedBy = EnumValidator.class)// 自定义验证的处理类
|
||||
public @interface CheckEnum {
|
||||
|
||||
/**
|
||||
* 默认的错误提示信息
|
||||
*
|
||||
* @return String
|
||||
*/
|
||||
String message() default "非法的枚举值";
|
||||
|
||||
/**
|
||||
* 枚举类对象 必须实现BaseEnum接口
|
||||
*
|
||||
* @return
|
||||
*/
|
||||
Class<? extends BaseEnum> enumClazz();
|
||||
|
||||
/**
|
||||
* 是否必须
|
||||
*
|
||||
* @return boolean
|
||||
*/
|
||||
boolean required() default false;
|
||||
|
||||
//下面这两个属性必须添加 :不然会报错
|
||||
Class<?>[] groups() default {};
|
||||
|
||||
Class<? extends Payload>[] payload() default {};
|
||||
}
|
||||
@@ -0,0 +1,80 @@
|
||||
package net.lab1024.smartadmin.common.validator.en;
|
||||
|
||||
import net.lab1024.smartadmin.common.domain.BaseEnum;
|
||||
|
||||
import javax.validation.ConstraintValidator;
|
||||
import javax.validation.ConstraintValidatorContext;
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
* 枚举类校验器
|
||||
*
|
||||
* @author listen
|
||||
* @date 2017/11/11 15:34
|
||||
*/
|
||||
public class EnumValidator implements ConstraintValidator<CheckEnum, Object> {
|
||||
|
||||
/**
|
||||
* 枚举类的类对象
|
||||
*/
|
||||
private Class<? extends BaseEnum> enumClass;
|
||||
|
||||
/**
|
||||
* 是否必须
|
||||
*/
|
||||
private boolean required;
|
||||
|
||||
@Override
|
||||
public void initialize(CheckEnum constraintAnnotation) {
|
||||
// 获取注解传入的枚举类对象
|
||||
enumClass = constraintAnnotation.enumClazz();
|
||||
required = constraintAnnotation.required();
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isValid(Object value, ConstraintValidatorContext constraintValidatorContext) {
|
||||
// 判断是否必须
|
||||
if (null == value) {
|
||||
return !required;
|
||||
}
|
||||
|
||||
if (value instanceof List) {
|
||||
// 如果为 List 集合数据
|
||||
return this.checkList((List<Object>) value);
|
||||
}
|
||||
|
||||
// 校验是否为合法的枚举值
|
||||
return this.hasEnum(value);
|
||||
}
|
||||
|
||||
/**
|
||||
* 校验集合类型
|
||||
*
|
||||
* @param list
|
||||
* @return
|
||||
*/
|
||||
private boolean checkList(List<Object> list) {
|
||||
if (required && list.isEmpty()) {
|
||||
// 必须的情况下 list 不能为空
|
||||
return false;
|
||||
}
|
||||
for (Object obj : list) {
|
||||
boolean hasEnum = this.hasEnum(obj);
|
||||
if (!hasEnum) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
private boolean hasEnum(Object value) {
|
||||
// 校验是否为合法的枚举值
|
||||
BaseEnum[] enums = enumClass.getEnumConstants();
|
||||
for (BaseEnum baseEnum : enums) {
|
||||
if (baseEnum.getValue().equals(value)) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user