mirror of
https://gitee.com/lab1024/smart-admin.git
synced 2025-11-09 20:23:50 +08:00
Compare commits
43 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
4362e8df8b | ||
|
|
6855b8b088 | ||
|
|
92dddd507b | ||
|
|
013d1c237b | ||
|
|
8920b35945 | ||
|
|
d702e6cca4 | ||
|
|
3fcb764078 | ||
|
|
f4923487b4 | ||
|
|
6bcb9b296f | ||
|
|
be56a0b505 | ||
|
|
b16d8a6128 | ||
|
|
66cd067fa1 | ||
|
|
ff03f07b3f | ||
|
|
6c28721b38 | ||
|
|
dc9f4b7953 | ||
|
|
594c847523 | ||
|
|
a1043083dc | ||
|
|
a5a7fdf61a | ||
|
|
6f183c3366 | ||
|
|
84b5d338b6 | ||
|
|
f8039df1bf | ||
|
|
8fd02fc519 | ||
|
|
949f7a209c | ||
|
|
15cc4a9003 | ||
|
|
ecd671682e | ||
|
|
bf64f525fb | ||
|
|
694aa18452 | ||
|
|
7d8879abcb | ||
|
|
2f5683ac9d | ||
|
|
6f3d7dc3a2 | ||
|
|
36e554d8ed | ||
|
|
ac7c9940bf | ||
|
|
fed72d0c34 | ||
|
|
cbdac440d3 | ||
|
|
4a4d7115ef | ||
|
|
201b6a5018 | ||
|
|
716b6303e3 | ||
|
|
3bfd00a416 | ||
|
|
23e8ea55e1 | ||
|
|
3678687114 | ||
|
|
32f45a6651 | ||
|
|
42b6689b80 | ||
|
|
3c4e683ff0 |
19
README.md
19
README.md
@@ -79,22 +79,7 @@
|
|||||||
|
|
||||||
|
|
||||||
|
|
||||||
### **联系我们**
|
### **特别鸣谢**
|
||||||
|
|
||||||
[1024 创新实验室-主任:卓大](https://zhuoda.vip),混迹于各个技术圈,研究过计算机,熟悉点 java,略懂点前端。
|
|
||||||
[1024 创新实验室(河南·洛阳)](https://1024lab.net) 致力于成为中原领先、国内一流的技术团队,以技术创新为驱动,合作各类项目(软件外包、技术顾问、培训等等)。
|
|
||||||
|
|
||||||
<table>
|
|
||||||
<tr>
|
|
||||||
<td><img src="https://img.smartadmin.1024lab.net/wechat/zhuoda-wechat.jpg" width="250" /></td>
|
|
||||||
<td><img src="https://img.smartadmin.1024lab.net/wechat/liubianxing-gzh.jpg" width="250" /></td>
|
|
||||||
<td><img src="https://img.smartadmin.1024lab.net/wechat/zhuoda-wechat-money-v1.jpg" width="250" /></td>
|
|
||||||
</tr>
|
|
||||||
<tr>
|
|
||||||
<td style="text-align:center">加 主任 “卓大” 微信 <br> 拉你入群,一起学习</td>
|
|
||||||
<td style="text-align:center">关注 “六边形工程师” <br> 分享:赚钱、代码、生活</td>
|
|
||||||
<td style="text-align:center">请 “1024创新实验室” 喝咖啡 <br> 支持我们的开源与分享 </td>
|
|
||||||
</tr>
|
|
||||||
</table>
|
|
||||||
|
|
||||||
|
**特别感谢 Gitee 提供的开源代码平台**
|
||||||
|
|
||||||
|
|||||||
@@ -19,9 +19,10 @@
|
|||||||
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
|
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
|
||||||
<project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>
|
<project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>
|
||||||
<java.version>1.8</java.version>
|
<java.version>1.8</java.version>
|
||||||
<springboot.version>2.7.5</springboot.version>
|
<springboot.version>2.7.18</springboot.version>
|
||||||
<spring-mock.version>2.0.8</spring-mock.version>
|
<spring-mock.version>2.0.8</spring-mock.version>
|
||||||
<mybatis-plus.version>3.5.2</mybatis-plus.version>
|
<mybatis-plus.version>3.5.2</mybatis-plus.version>
|
||||||
|
<mysql-connector-j.version>8.0.33</mysql-connector-j.version>
|
||||||
<p6spy.version>3.9.1</p6spy.version>
|
<p6spy.version>3.9.1</p6spy.version>
|
||||||
<springdoc-openapi-ui.version>1.7.0</springdoc-openapi-ui.version>
|
<springdoc-openapi-ui.version>1.7.0</springdoc-openapi-ui.version>
|
||||||
<knife4j.version>4.3.0</knife4j.version>
|
<knife4j.version>4.3.0</knife4j.version>
|
||||||
@@ -36,12 +37,13 @@
|
|||||||
<commons-lang3.version>3.12.0</commons-lang3.version>
|
<commons-lang3.version>3.12.0</commons-lang3.version>
|
||||||
<commons-collections4.version>4.4</commons-collections4.version>
|
<commons-collections4.version>4.4</commons-collections4.version>
|
||||||
<commons-codec.version>1.13</commons-codec.version>
|
<commons-codec.version>1.13</commons-codec.version>
|
||||||
|
<commons-text.version>1.9</commons-text.version>
|
||||||
<xerces.version>2.12.0</xerces.version>
|
<xerces.version>2.12.0</xerces.version>
|
||||||
<easy-excel.version>3.3.2</easy-excel.version>
|
<easy-excel.version>3.3.2</easy-excel.version>
|
||||||
<poi.version>5.2.4</poi.version>
|
<poi.version>5.2.4</poi.version>
|
||||||
<ooxml-schemas.version>1.4</ooxml-schemas.version>
|
<ooxml-schemas.version>1.4</ooxml-schemas.version>
|
||||||
<aws-java-sdk.version>1.11.842</aws-java-sdk.version>
|
<aws-java-sdk.version>1.11.842</aws-java-sdk.version>
|
||||||
<log4j-spring-boot.version>2.17.2</log4j-spring-boot.version>
|
<log4j-spring-boot.version>2.23.1</log4j-spring-boot.version>
|
||||||
<hutool.version>5.7.22</hutool.version>
|
<hutool.version>5.7.22</hutool.version>
|
||||||
<velocity-engine-core.version>2.3</velocity-engine-core.version>
|
<velocity-engine-core.version>2.3</velocity-engine-core.version>
|
||||||
<jjwt.version>0.9.1</jjwt.version>
|
<jjwt.version>0.9.1</jjwt.version>
|
||||||
@@ -51,7 +53,12 @@
|
|||||||
<ip2region.version>2.7.0</ip2region.version>
|
<ip2region.version>2.7.0</ip2region.version>
|
||||||
<bcprov.version>1.59</bcprov.version>
|
<bcprov.version>1.59</bcprov.version>
|
||||||
<jackson-datatype-jsr310.version>2.13.4</jackson-datatype-jsr310.version>
|
<jackson-datatype-jsr310.version>2.13.4</jackson-datatype-jsr310.version>
|
||||||
|
<jackson-dataformat-yaml.version>2.16.1</jackson-dataformat-yaml.version>
|
||||||
<smartdb.version>1.2.0</smartdb.version>
|
<smartdb.version>1.2.0</smartdb.version>
|
||||||
|
<redisson.version>3.25.0</redisson.version>
|
||||||
|
<snakeyaml.version>2.2</snakeyaml.version>
|
||||||
|
<freemarker.version>2.3.33</freemarker.version>
|
||||||
|
<jsoup.version>1.18.1</jsoup.version>
|
||||||
</properties>
|
</properties>
|
||||||
|
|
||||||
<dependencyManagement>
|
<dependencyManagement>
|
||||||
@@ -79,6 +86,12 @@
|
|||||||
</exclusions>
|
</exclusions>
|
||||||
</dependency>
|
</dependency>
|
||||||
|
|
||||||
|
<dependency>
|
||||||
|
<groupId>com.mysql</groupId>
|
||||||
|
<artifactId>mysql-connector-j</artifactId>
|
||||||
|
<version>${mysql-connector-j.version}</version>
|
||||||
|
</dependency>
|
||||||
|
|
||||||
<dependency>
|
<dependency>
|
||||||
<groupId>com.baomidou</groupId>
|
<groupId>com.baomidou</groupId>
|
||||||
<artifactId>mybatis-plus-boot-starter</artifactId>
|
<artifactId>mybatis-plus-boot-starter</artifactId>
|
||||||
@@ -194,9 +207,9 @@
|
|||||||
</dependency>
|
</dependency>
|
||||||
|
|
||||||
<dependency>
|
<dependency>
|
||||||
<groupId>org.apache.logging.log4j</groupId>
|
<groupId>org.apache.commons</groupId>
|
||||||
<artifactId>log4j-spring-boot</artifactId>
|
<artifactId>commons-text</artifactId>
|
||||||
<version>${log4j-spring-boot.version}</version>
|
<version>${commons-text.version}</version>
|
||||||
</dependency>
|
</dependency>
|
||||||
|
|
||||||
<dependency>
|
<dependency>
|
||||||
@@ -301,11 +314,62 @@
|
|||||||
<version>${jackson-datatype-jsr310.version}</version>
|
<version>${jackson-datatype-jsr310.version}</version>
|
||||||
</dependency>
|
</dependency>
|
||||||
|
|
||||||
|
<dependency>
|
||||||
|
<groupId>com.fasterxml.jackson.dataformat</groupId>
|
||||||
|
<artifactId>jackson-dataformat-yaml</artifactId>
|
||||||
|
<version>${jackson-dataformat-yaml.version}</version>
|
||||||
|
</dependency>
|
||||||
|
|
||||||
<dependency>
|
<dependency>
|
||||||
<groupId>net.1024lab</groupId>
|
<groupId>net.1024lab</groupId>
|
||||||
<artifactId>smartdb</artifactId>
|
<artifactId>smartdb</artifactId>
|
||||||
<version>${smartdb.version}</version>
|
<version>${smartdb.version}</version>
|
||||||
</dependency>
|
</dependency>
|
||||||
|
|
||||||
|
<!-- redisson 排除和依赖data-27 为了springboot2.x 和 java8 -->
|
||||||
|
<dependency>
|
||||||
|
<groupId>org.redisson</groupId>
|
||||||
|
<artifactId>redisson-spring-boot-starter</artifactId>
|
||||||
|
<version>${redisson.version}</version>
|
||||||
|
<exclusions>
|
||||||
|
<exclusion>
|
||||||
|
<groupId>org.springframework.boot</groupId>
|
||||||
|
<artifactId>spring-boot-starter-actuator</artifactId>
|
||||||
|
</exclusion>
|
||||||
|
<exclusion>
|
||||||
|
<groupId>org.redisson</groupId>
|
||||||
|
<artifactId>redisson-spring-data-32</artifactId>
|
||||||
|
</exclusion>
|
||||||
|
<exclusion>
|
||||||
|
<artifactId>objenesis</artifactId>
|
||||||
|
<groupId>org.objenesis</groupId>
|
||||||
|
</exclusion>
|
||||||
|
</exclusions>
|
||||||
|
</dependency>
|
||||||
|
<dependency>
|
||||||
|
<groupId>org.redisson</groupId>
|
||||||
|
<artifactId>redisson-spring-data-27</artifactId>
|
||||||
|
<version>${redisson.version}</version>
|
||||||
|
</dependency>
|
||||||
|
|
||||||
|
<dependency>
|
||||||
|
<groupId>org.yaml</groupId>
|
||||||
|
<artifactId>snakeyaml</artifactId>
|
||||||
|
<version>${snakeyaml.version}</version>
|
||||||
|
</dependency>
|
||||||
|
|
||||||
|
<dependency>
|
||||||
|
<groupId>org.jsoup</groupId>
|
||||||
|
<artifactId>jsoup</artifactId>
|
||||||
|
<version>${jsoup.version}</version>
|
||||||
|
</dependency>
|
||||||
|
|
||||||
|
<dependency>
|
||||||
|
<groupId>org.freemarker</groupId>
|
||||||
|
<artifactId>freemarker</artifactId>
|
||||||
|
<version>${freemarker.version}</version>
|
||||||
|
</dependency>
|
||||||
|
|
||||||
</dependencies>
|
</dependencies>
|
||||||
|
|
||||||
</dependencyManagement>
|
</dependencyManagement>
|
||||||
|
|||||||
@@ -25,6 +25,7 @@ public class AdminSwaggerTagConst extends SwaggerTagConst {
|
|||||||
public static final String OA_INVOICE = "OA办公-发票信息";
|
public static final String OA_INVOICE = "OA办公-发票信息";
|
||||||
|
|
||||||
public static final String OA_NOTICE = "OA办公-通知公告";
|
public static final String OA_NOTICE = "OA办公-通知公告";
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@@ -48,6 +49,8 @@ public class AdminSwaggerTagConst extends SwaggerTagConst {
|
|||||||
|
|
||||||
public static final String SYSTEM_ROLE_MENU = "系统-角色-菜单";
|
public static final String SYSTEM_ROLE_MENU = "系统-角色-菜单";
|
||||||
|
|
||||||
|
public static final String SYSTEM_POSITION = "系统-职务管理";
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
@@ -50,9 +50,6 @@ public class AdminInterceptor implements HandlerInterceptor {
|
|||||||
@Resource
|
@Resource
|
||||||
private SystemEnvironment systemEnvironment;
|
private SystemEnvironment systemEnvironment;
|
||||||
|
|
||||||
@Value("${sa-token.active-timeout}")
|
|
||||||
private long tokenActiveTimeout;
|
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
|
public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
|
||||||
|
|
||||||
@@ -158,11 +155,6 @@ public class AdminInterceptor implements HandlerInterceptor {
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
// 小于1 ,也不需要检测
|
|
||||||
if (tokenActiveTimeout < 1) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
StpUtil.checkActiveTimeout();
|
StpUtil.checkActiveTimeout();
|
||||||
StpUtil.updateLastActiveToNow();
|
StpUtil.updateLastActiveToNow();
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,9 +1,11 @@
|
|||||||
package net.lab1024.sa.admin.module.business.goods.domain.form;
|
package net.lab1024.sa.admin.module.business.goods.domain.form;
|
||||||
|
|
||||||
|
import com.fasterxml.jackson.databind.annotation.JsonDeserialize;
|
||||||
import io.swagger.v3.oas.annotations.media.Schema;
|
import io.swagger.v3.oas.annotations.media.Schema;
|
||||||
import lombok.Data;
|
import lombok.Data;
|
||||||
import net.lab1024.sa.admin.module.business.goods.constant.GoodsStatusEnum;
|
import net.lab1024.sa.admin.module.business.goods.constant.GoodsStatusEnum;
|
||||||
import net.lab1024.sa.base.common.domain.PageParam;
|
import net.lab1024.sa.base.common.domain.PageParam;
|
||||||
|
import net.lab1024.sa.base.common.json.deserializer.DictValueVoDeserializer;
|
||||||
import net.lab1024.sa.base.common.swagger.SchemaEnum;
|
import net.lab1024.sa.base.common.swagger.SchemaEnum;
|
||||||
import net.lab1024.sa.base.common.validator.enumeration.CheckEnum;
|
import net.lab1024.sa.base.common.validator.enumeration.CheckEnum;
|
||||||
import org.hibernate.validator.constraints.Length;
|
import org.hibernate.validator.constraints.Length;
|
||||||
@@ -32,6 +34,7 @@ public class GoodsQueryForm extends PageParam {
|
|||||||
private Integer goodsStatus;
|
private Integer goodsStatus;
|
||||||
|
|
||||||
@Schema(description = "产地")
|
@Schema(description = "产地")
|
||||||
|
@JsonDeserialize(using = DictValueVoDeserializer.class)
|
||||||
private String place;
|
private String place;
|
||||||
|
|
||||||
@Schema(description = "上架状态")
|
@Schema(description = "上架状态")
|
||||||
|
|||||||
@@ -199,7 +199,7 @@ public class GoodsService {
|
|||||||
GoodsExcelVO.builder()
|
GoodsExcelVO.builder()
|
||||||
.goodsStatus(SmartEnumUtil.getEnumDescByValue(e.getGoodsStatus(), GoodsStatusEnum.class))
|
.goodsStatus(SmartEnumUtil.getEnumDescByValue(e.getGoodsStatus(), GoodsStatusEnum.class))
|
||||||
.categoryName(categoryQueryService.queryCategoryName(e.getCategoryId()))
|
.categoryName(categoryQueryService.queryCategoryName(e.getCategoryId()))
|
||||||
.place(dictCacheService.selectValueNameByValueCode(e.getPlace()))
|
.place(Arrays.stream(e.getPlace().split(",")).map(code -> dictCacheService.selectValueNameByValueCode(code)).collect(Collectors.joining(",")))
|
||||||
.price(e.getPrice())
|
.price(e.getPrice())
|
||||||
.goodsName(e.getGoodsName())
|
.goodsName(e.getGoodsName())
|
||||||
.remark(e.getRemark())
|
.remark(e.getRemark())
|
||||||
|
|||||||
@@ -114,4 +114,14 @@ public interface NoticeDao extends BaseMapper<NoticeEntity> {
|
|||||||
*/
|
*/
|
||||||
void updateViewRecord(@Param("noticeId")Long noticeId, @Param("employeeId")Long requestEmployeeId,@Param("ip") String ip, @Param("userAgent")String userAgent);
|
void updateViewRecord(@Param("noticeId")Long noticeId, @Param("employeeId")Long requestEmployeeId,@Param("ip") String ip, @Param("userAgent")String userAgent);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 更新 浏览量
|
||||||
|
*
|
||||||
|
* @param noticeId 通知 id
|
||||||
|
* @param pageViewCountIncrement 页面浏览量的增量
|
||||||
|
* @param userViewCountIncrement 用户浏览量的增量
|
||||||
|
*/
|
||||||
|
void updateViewCount(@Param("noticeId")Long noticeId,@Param("pageViewCountIncrement") Integer pageViewCountIncrement, @Param("userViewCountIncrement")Integer userViewCountIncrement);
|
||||||
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -52,10 +52,10 @@ public class NoticeEmployeeService {
|
|||||||
public ResponseDTO<PageResult<NoticeEmployeeVO>> queryList(Long requestEmployeeId, NoticeEmployeeQueryForm noticeEmployeeQueryForm) {
|
public ResponseDTO<PageResult<NoticeEmployeeVO>> queryList(Long requestEmployeeId, NoticeEmployeeQueryForm noticeEmployeeQueryForm) {
|
||||||
Page<?> page = SmartPageUtil.convert2PageQuery(noticeEmployeeQueryForm);
|
Page<?> page = SmartPageUtil.convert2PageQuery(noticeEmployeeQueryForm);
|
||||||
|
|
||||||
//获取请求人的 部门及其子部门
|
|
||||||
List<Long> employeeDepartmentIdList = Lists.newArrayList();
|
List<Long> employeeDepartmentIdList = Lists.newArrayList();
|
||||||
EmployeeEntity employeeEntity = employeeService.getById(requestEmployeeId);
|
EmployeeEntity employeeEntity = employeeService.getById(requestEmployeeId);
|
||||||
if (employeeEntity.getDepartmentId() != null) {
|
// 如果不是管理员 则获取请求人的 部门及其子部门
|
||||||
|
if (!employeeEntity.getAdministratorFlag() && employeeEntity.getDepartmentId() != null) {
|
||||||
employeeDepartmentIdList = departmentService.selfAndChildrenIdList(employeeEntity.getDepartmentId());
|
employeeDepartmentIdList = departmentService.selfAndChildrenIdList(employeeEntity.getDepartmentId());
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -106,8 +106,15 @@ public class NoticeEmployeeService {
|
|||||||
long viewCount = noticeDao.viewRecordCount(noticeId, requestEmployeeId);
|
long viewCount = noticeDao.viewRecordCount(noticeId, requestEmployeeId);
|
||||||
if (viewCount == 0) {
|
if (viewCount == 0) {
|
||||||
noticeDao.insertViewRecord(noticeId, requestEmployeeId, ip, userAgent, 1);
|
noticeDao.insertViewRecord(noticeId, requestEmployeeId, ip, userAgent, 1);
|
||||||
|
// 该员工对于这个通知是第一次查看 页面浏览量+1 用户浏览量+1
|
||||||
|
noticeDao.updateViewCount(noticeId, 1, 1);
|
||||||
|
noticeDetailVO.setPageViewCount(noticeDetailVO.getPageViewCount() + 1);
|
||||||
|
noticeDetailVO.setUserViewCount(noticeDetailVO.getUserViewCount() + 1);
|
||||||
} else {
|
} else {
|
||||||
noticeDao.updateViewRecord(noticeId, requestEmployeeId, ip, userAgent);
|
noticeDao.updateViewRecord(noticeId, requestEmployeeId, ip, userAgent);
|
||||||
|
// 该员工对于这个通知不是第一次查看 页面浏览量+1 用户浏览量+0
|
||||||
|
noticeDao.updateViewCount(noticeId, 1, 0);
|
||||||
|
noticeDetailVO.setPageViewCount(noticeDetailVO.getPageViewCount() + 1);
|
||||||
}
|
}
|
||||||
|
|
||||||
return ResponseDTO.ok(noticeDetailVO);
|
return ResponseDTO.ok(noticeDetailVO);
|
||||||
|
|||||||
@@ -3,6 +3,8 @@ package net.lab1024.sa.admin.module.system.department.domain.vo;
|
|||||||
import io.swagger.v3.oas.annotations.media.Schema;
|
import io.swagger.v3.oas.annotations.media.Schema;
|
||||||
import lombok.Data;
|
import lombok.Data;
|
||||||
|
|
||||||
|
import java.time.LocalDateTime;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 部门
|
* 部门
|
||||||
*
|
*
|
||||||
@@ -33,4 +35,10 @@ public class DepartmentVO {
|
|||||||
@Schema(description = "排序")
|
@Schema(description = "排序")
|
||||||
private Integer sort;
|
private Integer sort;
|
||||||
|
|
||||||
|
@Schema(description = "更新时间")
|
||||||
|
private LocalDateTime updateTime;
|
||||||
|
|
||||||
|
@Schema(description = "创建时间")
|
||||||
|
private LocalDateTime createTime;
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -143,10 +143,12 @@ public class DepartmentCacheManager {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* 构建所有根节点的下级树形结构
|
* 构建所有根节点的下级树形结构
|
||||||
*
|
* 返回值为层序遍历结果
|
||||||
|
* [由于departmentDao中listAll给出数据根据Sort降序 所以同一层中Sort值较大的优先遍历]
|
||||||
*/
|
*/
|
||||||
private void recursiveBuildTree(List<DepartmentTreeVO> nodeList, List<DepartmentVO> allDepartmentList) {
|
private List<Long> recursiveBuildTree(List<DepartmentTreeVO> nodeList, List<DepartmentVO> allDepartmentList) {
|
||||||
int nodeSize = nodeList.size();
|
int nodeSize = nodeList.size();
|
||||||
|
List<Long> childIdList = new ArrayList<>();
|
||||||
for(int i = 0; i < nodeSize; i++) {
|
for(int i = 0; i < nodeSize; i++) {
|
||||||
int preIndex = i - 1;
|
int preIndex = i - 1;
|
||||||
int nextIndex = i + 1;
|
int nextIndex = i + 1;
|
||||||
@@ -158,16 +160,34 @@ public class DepartmentCacheManager {
|
|||||||
node.setNextId(nodeList.get(nextIndex).getDepartmentId());
|
node.setNextId(nodeList.get(nextIndex).getDepartmentId());
|
||||||
}
|
}
|
||||||
|
|
||||||
ArrayList<Long> selfAndAllChildrenIdList = Lists.newArrayList();
|
|
||||||
selfAndAllChildrenIdList.add(node.getDepartmentId());
|
|
||||||
node.setSelfAndAllChildrenIdList(selfAndAllChildrenIdList);
|
|
||||||
|
|
||||||
List<DepartmentTreeVO> children = getChildren(node.getDepartmentId(), allDepartmentList);
|
List<DepartmentTreeVO> children = getChildren(node.getDepartmentId(), allDepartmentList);
|
||||||
|
|
||||||
|
List<Long> tempChildIdList = new ArrayList<>();
|
||||||
if (CollectionUtils.isNotEmpty(children)) {
|
if (CollectionUtils.isNotEmpty(children)) {
|
||||||
node.setChildren(children);
|
node.setChildren(children);
|
||||||
this.recursiveBuildTree(children, allDepartmentList);
|
tempChildIdList = this.recursiveBuildTree(children, allDepartmentList);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if(CollectionUtils.isEmpty(node.getSelfAndAllChildrenIdList())) {
|
||||||
|
node.setSelfAndAllChildrenIdList(
|
||||||
|
new ArrayList<>()
|
||||||
|
);
|
||||||
}
|
}
|
||||||
|
node.getSelfAndAllChildrenIdList().add(node.getDepartmentId());
|
||||||
|
|
||||||
|
if(CollectionUtils.isNotEmpty(tempChildIdList)) {
|
||||||
|
node.getSelfAndAllChildrenIdList().addAll(tempChildIdList);
|
||||||
|
childIdList.addAll(tempChildIdList);
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
// 保证本层遍历顺序
|
||||||
|
for(int i = nodeSize - 1; i >= 0; i--) {
|
||||||
|
childIdList.add(0, nodeList.get(i).getDepartmentId());
|
||||||
|
}
|
||||||
|
|
||||||
|
return childIdList;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
@@ -92,7 +92,7 @@ public class DepartmentService {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// 是否有未删除员工
|
// 是否有未删除员工
|
||||||
int employeeNum = employeeDao.countByDepartmentId(departmentId);
|
int employeeNum = employeeDao.countByDepartmentId(departmentId, Boolean.FALSE);
|
||||||
if (employeeNum > 0) {
|
if (employeeNum > 0) {
|
||||||
return ResponseDTO.userErrorParam("请先删除部门员工");
|
return ResponseDTO.userErrorParam("请先删除部门员工");
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -10,6 +10,8 @@ import net.lab1024.sa.admin.module.system.employee.service.EmployeeService;
|
|||||||
import net.lab1024.sa.base.common.domain.PageResult;
|
import net.lab1024.sa.base.common.domain.PageResult;
|
||||||
import net.lab1024.sa.base.common.domain.ResponseDTO;
|
import net.lab1024.sa.base.common.domain.ResponseDTO;
|
||||||
import net.lab1024.sa.base.common.util.SmartRequestUtil;
|
import net.lab1024.sa.base.common.util.SmartRequestUtil;
|
||||||
|
import net.lab1024.sa.base.module.support.apiencrypt.annotation.ApiDecrypt;
|
||||||
|
import net.lab1024.sa.base.module.support.securityprotect.service.Level3ProtectConfigService;
|
||||||
import org.springframework.web.bind.annotation.*;
|
import org.springframework.web.bind.annotation.*;
|
||||||
|
|
||||||
import javax.annotation.Resource;
|
import javax.annotation.Resource;
|
||||||
@@ -32,6 +34,9 @@ public class EmployeeController {
|
|||||||
@Resource
|
@Resource
|
||||||
private EmployeeService employeeService;
|
private EmployeeService employeeService;
|
||||||
|
|
||||||
|
@Resource
|
||||||
|
private Level3ProtectConfigService level3ProtectConfigService;
|
||||||
|
|
||||||
@PostMapping("/employee/query")
|
@PostMapping("/employee/query")
|
||||||
@Operation(summary = "员工管理查询 @author 卓大")
|
@Operation(summary = "员工管理查询 @author 卓大")
|
||||||
public ResponseDTO<PageResult<EmployeeVO>> query(@Valid @RequestBody EmployeeQueryForm query) {
|
public ResponseDTO<PageResult<EmployeeVO>> query(@Valid @RequestBody EmployeeQueryForm query) {
|
||||||
@@ -52,6 +57,20 @@ public class EmployeeController {
|
|||||||
return employeeService.updateEmployee(employeeUpdateForm);
|
return employeeService.updateEmployee(employeeUpdateForm);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Operation(summary = "更新登录人信息 @author 善逸")
|
||||||
|
@PostMapping("/employee/update/login")
|
||||||
|
public ResponseDTO<String> updateByLogin(@Valid @RequestBody EmployeeUpdateForm employeeUpdateForm) {
|
||||||
|
employeeUpdateForm.setEmployeeId(SmartRequestUtil.getRequestUserId());
|
||||||
|
return employeeService.updateEmployee(employeeUpdateForm);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Operation(summary = "更新登录人头像 @author 善逸")
|
||||||
|
@PostMapping("/employee/update/avatar")
|
||||||
|
public ResponseDTO<String> updateAvatar(@Valid @RequestBody EmployeeUpdateAvatarForm employeeUpdateAvatarForm) {
|
||||||
|
employeeUpdateAvatarForm.setEmployeeId(SmartRequestUtil.getRequestUserId());
|
||||||
|
return employeeService.updateAvatar(employeeUpdateAvatarForm);
|
||||||
|
}
|
||||||
|
|
||||||
@Operation(summary = "更新员工禁用/启用状态 @author 卓大")
|
@Operation(summary = "更新员工禁用/启用状态 @author 卓大")
|
||||||
@GetMapping("/employee/update/disabled/{employeeId}")
|
@GetMapping("/employee/update/disabled/{employeeId}")
|
||||||
@SaCheckPermission("system:employee:disabled")
|
@SaCheckPermission("system:employee:disabled")
|
||||||
@@ -75,9 +94,17 @@ public class EmployeeController {
|
|||||||
|
|
||||||
@Operation(summary = "修改密码 @author 卓大")
|
@Operation(summary = "修改密码 @author 卓大")
|
||||||
@PostMapping("/employee/update/password")
|
@PostMapping("/employee/update/password")
|
||||||
|
@ApiDecrypt
|
||||||
public ResponseDTO<String> updatePassword(@Valid @RequestBody EmployeeUpdatePasswordForm updatePasswordForm) {
|
public ResponseDTO<String> updatePassword(@Valid @RequestBody EmployeeUpdatePasswordForm updatePasswordForm) {
|
||||||
updatePasswordForm.setEmployeeId(SmartRequestUtil.getRequestUserId());
|
updatePasswordForm.setEmployeeId(SmartRequestUtil.getRequestUserId());
|
||||||
return employeeService.updatePassword(updatePasswordForm);
|
return employeeService.updatePassword(SmartRequestUtil.getRequestUser(), updatePasswordForm);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Operation(summary = "获取密码复杂度 @author 卓大")
|
||||||
|
@GetMapping("/employee/getPasswordComplexityEnabled")
|
||||||
|
@ApiDecrypt
|
||||||
|
public ResponseDTO<Boolean> getPasswordComplexityEnabled() {
|
||||||
|
return ResponseDTO.ok(level3ProtectConfigService.isPasswordComplexityEnabled());
|
||||||
}
|
}
|
||||||
|
|
||||||
@Operation(summary = "重置员工密码 @author 卓大")
|
@Operation(summary = "重置员工密码 @author 卓大")
|
||||||
|
|||||||
@@ -69,7 +69,7 @@ public interface EmployeeDao extends BaseMapper<EmployeeEntity> {
|
|||||||
* 获取某个部门员工数
|
* 获取某个部门员工数
|
||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
Integer countByDepartmentId(@Param("departmentId") Long departmentId);
|
Integer countByDepartmentId(@Param("departmentId") Long departmentId, @Param("deletedFlag") Boolean deletedFlag);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 获取一批员工
|
* 获取一批员工
|
||||||
|
|||||||
@@ -38,6 +38,11 @@ public class EmployeeEntity {
|
|||||||
*/
|
*/
|
||||||
private String actualName;
|
private String actualName;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 头像
|
||||||
|
*/
|
||||||
|
private String avatar;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 性别
|
* 性别
|
||||||
*/
|
*/
|
||||||
@@ -48,11 +53,21 @@ public class EmployeeEntity {
|
|||||||
*/
|
*/
|
||||||
private String phone;
|
private String phone;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 邮箱
|
||||||
|
*/
|
||||||
|
private String email;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 部门id
|
* 部门id
|
||||||
*/
|
*/
|
||||||
private Long departmentId;
|
private Long departmentId;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 职务级别ID
|
||||||
|
*/
|
||||||
|
private Long positionId;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 是否为超级管理员: 0 不是,1是
|
* 是否为超级管理员: 0 不是,1是
|
||||||
*/
|
*/
|
||||||
|
|||||||
@@ -51,6 +51,17 @@ public class EmployeeAddForm {
|
|||||||
@Pattern(regexp = SmartVerificationUtil.PHONE_REGEXP, message = "手机号格式不正确")
|
@Pattern(regexp = SmartVerificationUtil.PHONE_REGEXP, message = "手机号格式不正确")
|
||||||
private String phone;
|
private String phone;
|
||||||
|
|
||||||
|
@Schema(description = "邮箱")
|
||||||
|
private String email;
|
||||||
|
|
||||||
@Schema(description = "角色列表")
|
@Schema(description = "角色列表")
|
||||||
private List<Long> roleIdList;
|
private List<Long> roleIdList;
|
||||||
|
|
||||||
|
@Schema(description = "备注")
|
||||||
|
@Length(max = 30, message = "备注最多200字符")
|
||||||
|
private String remark;
|
||||||
|
|
||||||
|
@Schema(description = "职务级别ID")
|
||||||
|
private Long positionId;
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -0,0 +1,28 @@
|
|||||||
|
package net.lab1024.sa.admin.module.system.employee.domain.form;
|
||||||
|
|
||||||
|
import io.swagger.v3.oas.annotations.media.Schema;
|
||||||
|
import lombok.Data;
|
||||||
|
import net.lab1024.sa.base.common.util.SmartVerificationUtil;
|
||||||
|
|
||||||
|
import javax.validation.constraints.NotBlank;
|
||||||
|
import javax.validation.constraints.Pattern;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 修改登录人头像
|
||||||
|
*
|
||||||
|
* @Author 1024创新实验室: 善逸
|
||||||
|
* @Date 2024年6月30日00:26:35
|
||||||
|
* @Wechat zhuoda1024
|
||||||
|
* @Email lab1024@163.com
|
||||||
|
* @Copyright <a href="https://1024lab.net">1024创新实验室</a>
|
||||||
|
*/
|
||||||
|
@Data
|
||||||
|
public class EmployeeUpdateAvatarForm {
|
||||||
|
|
||||||
|
@Schema(hidden = true)
|
||||||
|
private Long employeeId;
|
||||||
|
|
||||||
|
@Schema(description = "头像")
|
||||||
|
@NotBlank(message = "头像不能为空哦")
|
||||||
|
private String avatar;
|
||||||
|
}
|
||||||
@@ -24,11 +24,9 @@ public class EmployeeUpdatePasswordForm {
|
|||||||
|
|
||||||
@Schema(description = "原密码")
|
@Schema(description = "原密码")
|
||||||
@NotBlank(message = "原密码不能为空哦")
|
@NotBlank(message = "原密码不能为空哦")
|
||||||
@Pattern(regexp = SmartVerificationUtil.PWD_REGEXP, message = "原密码请输入6-15位(数字|大小写字母|小数点)")
|
|
||||||
private String oldPassword;
|
private String oldPassword;
|
||||||
|
|
||||||
@Schema(description = "新密码")
|
@Schema(description = "新密码")
|
||||||
@NotBlank(message = "新密码不能为空哦")
|
@NotBlank(message = "新密码不能为空哦")
|
||||||
@Pattern(regexp = SmartVerificationUtil.PWD_REGEXP, message = "新密码请输入6-15位(数字|大小写字母|小数点)")
|
|
||||||
private String newPassword;
|
private String newPassword;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -55,4 +55,14 @@ public class EmployeeVO {
|
|||||||
|
|
||||||
@Schema(description = "角色名称列表")
|
@Schema(description = "角色名称列表")
|
||||||
private List<String> roleNameList;
|
private List<String> roleNameList;
|
||||||
|
|
||||||
|
@Schema(description = "职务ID")
|
||||||
|
private Long positionId;
|
||||||
|
|
||||||
|
@Schema(description = "职务名称")
|
||||||
|
private String positionName;
|
||||||
|
|
||||||
|
@Schema(description = "邮箱")
|
||||||
|
private String email;
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -60,11 +60,15 @@ public class EmployeeManager extends ServiceImpl<EmployeeDao, EmployeeEntity> {
|
|||||||
// 保存员工 获得id
|
// 保存员工 获得id
|
||||||
employeeDao.updateById(employee);
|
employeeDao.updateById(employee);
|
||||||
|
|
||||||
if (CollectionUtils.isNotEmpty(roleIdList)) {
|
// 若为空,则删除所有角色
|
||||||
|
if (CollectionUtils.isEmpty(roleIdList)) {
|
||||||
|
roleEmployeeDao.deleteByEmployeeId(employee.getEmployeeId());
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
List<RoleEmployeeEntity> roleEmployeeList = roleIdList.stream().map(e -> new RoleEmployeeEntity(e, employee.getEmployeeId())).collect(Collectors.toList());
|
List<RoleEmployeeEntity> roleEmployeeList = roleIdList.stream().map(e -> new RoleEmployeeEntity(e, employee.getEmployeeId())).collect(Collectors.toList());
|
||||||
this.updateEmployeeRole(employee.getEmployeeId(), roleEmployeeList);
|
this.updateEmployeeRole(employee.getEmployeeId(), roleEmployeeList);
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 更新员工角色
|
* 更新员工角色
|
||||||
|
|||||||
@@ -12,19 +12,24 @@ import net.lab1024.sa.admin.module.system.employee.domain.entity.EmployeeEntity;
|
|||||||
import net.lab1024.sa.admin.module.system.employee.domain.form.*;
|
import net.lab1024.sa.admin.module.system.employee.domain.form.*;
|
||||||
import net.lab1024.sa.admin.module.system.employee.domain.vo.EmployeeVO;
|
import net.lab1024.sa.admin.module.system.employee.domain.vo.EmployeeVO;
|
||||||
import net.lab1024.sa.admin.module.system.employee.manager.EmployeeManager;
|
import net.lab1024.sa.admin.module.system.employee.manager.EmployeeManager;
|
||||||
|
import net.lab1024.sa.admin.module.system.login.service.LoginService;
|
||||||
|
import net.lab1024.sa.admin.module.system.position.dao.PositionDao;
|
||||||
|
import net.lab1024.sa.admin.module.system.position.domain.entity.PositionEntity;
|
||||||
import net.lab1024.sa.admin.module.system.role.dao.RoleEmployeeDao;
|
import net.lab1024.sa.admin.module.system.role.dao.RoleEmployeeDao;
|
||||||
import net.lab1024.sa.admin.module.system.role.domain.vo.RoleEmployeeVO;
|
import net.lab1024.sa.admin.module.system.role.domain.vo.RoleEmployeeVO;
|
||||||
import net.lab1024.sa.base.common.code.UserErrorCode;
|
import net.lab1024.sa.base.common.code.UserErrorCode;
|
||||||
import net.lab1024.sa.base.common.constant.StringConst;
|
import net.lab1024.sa.base.common.constant.StringConst;
|
||||||
import net.lab1024.sa.base.common.domain.PageResult;
|
import net.lab1024.sa.base.common.domain.PageResult;
|
||||||
|
import net.lab1024.sa.base.common.domain.RequestUser;
|
||||||
import net.lab1024.sa.base.common.domain.ResponseDTO;
|
import net.lab1024.sa.base.common.domain.ResponseDTO;
|
||||||
import net.lab1024.sa.base.common.enumeration.UserTypeEnum;
|
import net.lab1024.sa.base.common.enumeration.UserTypeEnum;
|
||||||
import net.lab1024.sa.base.common.util.SmartBeanUtil;
|
import net.lab1024.sa.base.common.util.SmartBeanUtil;
|
||||||
import net.lab1024.sa.base.common.util.SmartPageUtil;
|
import net.lab1024.sa.base.common.util.SmartPageUtil;
|
||||||
import net.lab1024.sa.base.module.support.securityprotect.service.ProtectPasswordService;
|
import net.lab1024.sa.base.module.support.securityprotect.service.SecurityPasswordService;
|
||||||
import org.apache.commons.codec.digest.DigestUtils;
|
|
||||||
import org.apache.commons.collections4.CollectionUtils;
|
import org.apache.commons.collections4.CollectionUtils;
|
||||||
|
import org.springframework.context.annotation.Lazy;
|
||||||
import org.springframework.stereotype.Service;
|
import org.springframework.stereotype.Service;
|
||||||
|
import org.springframework.transaction.annotation.Transactional;
|
||||||
|
|
||||||
import javax.annotation.Resource;
|
import javax.annotation.Resource;
|
||||||
import java.util.*;
|
import java.util.*;
|
||||||
@@ -42,8 +47,6 @@ import java.util.stream.Collectors;
|
|||||||
@Service
|
@Service
|
||||||
public class EmployeeService {
|
public class EmployeeService {
|
||||||
|
|
||||||
private static final String PASSWORD_SALT_FORMAT = "smart_%s_admin_$^&*";
|
|
||||||
|
|
||||||
@Resource
|
@Resource
|
||||||
private EmployeeDao employeeDao;
|
private EmployeeDao employeeDao;
|
||||||
|
|
||||||
@@ -60,7 +63,14 @@ public class EmployeeService {
|
|||||||
private DepartmentService departmentService;
|
private DepartmentService departmentService;
|
||||||
|
|
||||||
@Resource
|
@Resource
|
||||||
private ProtectPasswordService protectPasswordService;
|
private SecurityPasswordService securityPasswordService;
|
||||||
|
|
||||||
|
@Resource
|
||||||
|
@Lazy
|
||||||
|
private LoginService loginService;
|
||||||
|
|
||||||
|
@Resource
|
||||||
|
private PositionDao positionDao;
|
||||||
|
|
||||||
public EmployeeEntity getById(Long employeeId) {
|
public EmployeeEntity getById(Long employeeId) {
|
||||||
return employeeDao.selectById(employeeId);
|
return employeeDao.selectById(employeeId);
|
||||||
@@ -69,7 +79,6 @@ public class EmployeeService {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* 查询员工列表
|
* 查询员工列表
|
||||||
*
|
|
||||||
*/
|
*/
|
||||||
public ResponseDTO<PageResult<EmployeeVO>> queryEmployee(EmployeeQueryForm employeeQueryForm) {
|
public ResponseDTO<PageResult<EmployeeVO>> queryEmployee(EmployeeQueryForm employeeQueryForm) {
|
||||||
employeeQueryForm.setDeletedFlag(false);
|
employeeQueryForm.setDeletedFlag(false);
|
||||||
@@ -86,16 +95,22 @@ public class EmployeeService {
|
|||||||
return ResponseDTO.ok(pageResult);
|
return ResponseDTO.ok(pageResult);
|
||||||
}
|
}
|
||||||
|
|
||||||
List<Long> employeeIdList = employeeList.stream().map(EmployeeVO::getEmployeeId).collect(Collectors.toList());
|
|
||||||
// 查询员工角色
|
// 查询员工角色
|
||||||
List<RoleEmployeeVO> roleEmployeeEntityList = roleEmployeeDao.selectRoleByEmployeeIdList(employeeIdList);
|
List<Long> employeeIdList = employeeList.stream().map(EmployeeVO::getEmployeeId).collect(Collectors.toList());
|
||||||
|
List<RoleEmployeeVO> roleEmployeeEntityList = employeeIdList.isEmpty() ? Collections.emptyList() : roleEmployeeDao.selectRoleByEmployeeIdList(employeeIdList);
|
||||||
Map<Long, List<Long>> employeeRoleIdListMap = roleEmployeeEntityList.stream().collect(Collectors.groupingBy(RoleEmployeeVO::getEmployeeId, Collectors.mapping(RoleEmployeeVO::getRoleId, Collectors.toList())));
|
Map<Long, List<Long>> employeeRoleIdListMap = roleEmployeeEntityList.stream().collect(Collectors.groupingBy(RoleEmployeeVO::getEmployeeId, Collectors.mapping(RoleEmployeeVO::getRoleId, Collectors.toList())));
|
||||||
Map<Long, List<String>> employeeRoleNameListMap = roleEmployeeEntityList.stream().collect(Collectors.groupingBy(RoleEmployeeVO::getEmployeeId, Collectors.mapping(RoleEmployeeVO::getRoleName, Collectors.toList())));
|
Map<Long, List<String>> employeeRoleNameListMap = roleEmployeeEntityList.stream().collect(Collectors.groupingBy(RoleEmployeeVO::getEmployeeId, Collectors.mapping(RoleEmployeeVO::getRoleName, Collectors.toList())));
|
||||||
|
|
||||||
|
// 查询员工职位
|
||||||
|
List<Long> positionIdList = employeeList.stream().map(EmployeeVO::getPositionId).filter(Objects::nonNull).collect(Collectors.toList());
|
||||||
|
List<PositionEntity> positionEntityList = positionIdList.isEmpty() ? Collections.emptyList() : positionDao.selectBatchIds(positionIdList);
|
||||||
|
Map<Long, String> positionNameMap = positionEntityList.stream().collect(Collectors.toMap(PositionEntity::getPositionId, PositionEntity::getPositionName));
|
||||||
|
|
||||||
employeeList.forEach(e -> {
|
employeeList.forEach(e -> {
|
||||||
e.setRoleIdList(employeeRoleIdListMap.getOrDefault(e.getEmployeeId(), Lists.newArrayList()));
|
e.setRoleIdList(employeeRoleIdListMap.getOrDefault(e.getEmployeeId(), Lists.newArrayList()));
|
||||||
e.setRoleNameList(employeeRoleNameListMap.getOrDefault(e.getEmployeeId(), Lists.newArrayList()));
|
e.setRoleNameList(employeeRoleNameListMap.getOrDefault(e.getEmployeeId(), Lists.newArrayList()));
|
||||||
e.setDepartmentName(departmentService.getDepartmentPath(e.getDepartmentId()));
|
e.setDepartmentName(departmentService.getDepartmentPath(e.getDepartmentId()));
|
||||||
|
e.setPositionName(positionNameMap.get(e.getPositionId()));
|
||||||
});
|
});
|
||||||
PageResult<EmployeeVO> pageResult = SmartPageUtil.convert2PageResult(pageParam, employeeList);
|
PageResult<EmployeeVO> pageResult = SmartPageUtil.convert2PageResult(pageParam, employeeList);
|
||||||
return ResponseDTO.ok(pageResult);
|
return ResponseDTO.ok(pageResult);
|
||||||
@@ -103,19 +118,13 @@ public class EmployeeService {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* 新增员工
|
* 新增员工
|
||||||
*
|
|
||||||
*/
|
*/
|
||||||
public synchronized ResponseDTO<String> addEmployee(EmployeeAddForm employeeAddForm) {
|
public synchronized ResponseDTO<String> addEmployee(EmployeeAddForm employeeAddForm) {
|
||||||
// 校验名称是否重复
|
// 校验登录名是否重复
|
||||||
EmployeeEntity employeeEntity = employeeDao.getByLoginName(employeeAddForm.getLoginName(), null);
|
EmployeeEntity employeeEntity = employeeDao.getByLoginName(employeeAddForm.getLoginName(), null);
|
||||||
if (null != employeeEntity) {
|
if (null != employeeEntity) {
|
||||||
return ResponseDTO.userErrorParam("登录名重复");
|
return ResponseDTO.userErrorParam("登录名重复");
|
||||||
}
|
}
|
||||||
// 校验姓名是否重复
|
|
||||||
employeeEntity = employeeDao.getByActualName(employeeAddForm.getActualName(), null);
|
|
||||||
if (null != employeeEntity) {
|
|
||||||
return ResponseDTO.userErrorParam("姓名重复");
|
|
||||||
}
|
|
||||||
// 校验电话是否存在
|
// 校验电话是否存在
|
||||||
employeeEntity = employeeDao.getByPhone(employeeAddForm.getPhone(), null);
|
employeeEntity = employeeDao.getByPhone(employeeAddForm.getPhone(), null);
|
||||||
if (null != employeeEntity) {
|
if (null != employeeEntity) {
|
||||||
@@ -131,8 +140,8 @@ public class EmployeeService {
|
|||||||
EmployeeEntity entity = SmartBeanUtil.copy(employeeAddForm, EmployeeEntity.class);
|
EmployeeEntity entity = SmartBeanUtil.copy(employeeAddForm, EmployeeEntity.class);
|
||||||
|
|
||||||
// 设置密码 默认密码
|
// 设置密码 默认密码
|
||||||
String password = protectPasswordService.randomPassword();
|
String password = securityPasswordService.randomPassword();
|
||||||
entity.setLoginPwd(getEncryptPwd(password));
|
entity.setLoginPwd(SecurityPasswordService.getEncryptPwd(password));
|
||||||
|
|
||||||
// 保存数据
|
// 保存数据
|
||||||
entity.setDeletedFlag(Boolean.FALSE);
|
entity.setDeletedFlag(Boolean.FALSE);
|
||||||
@@ -143,7 +152,6 @@ public class EmployeeService {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* 更新员工
|
* 更新员工
|
||||||
*
|
|
||||||
*/
|
*/
|
||||||
public synchronized ResponseDTO<String> updateEmployee(EmployeeUpdateForm employeeUpdateForm) {
|
public synchronized ResponseDTO<String> updateEmployee(EmployeeUpdateForm employeeUpdateForm) {
|
||||||
|
|
||||||
@@ -171,11 +179,6 @@ public class EmployeeService {
|
|||||||
return ResponseDTO.userErrorParam("手机号已存在");
|
return ResponseDTO.userErrorParam("手机号已存在");
|
||||||
}
|
}
|
||||||
|
|
||||||
existEntity = employeeDao.getByActualName(employeeUpdateForm.getActualName(), null);
|
|
||||||
if (null != existEntity && !Objects.equals(existEntity.getEmployeeId(), employeeId)) {
|
|
||||||
return ResponseDTO.userErrorParam("姓名重复");
|
|
||||||
}
|
|
||||||
|
|
||||||
// 不更新密码
|
// 不更新密码
|
||||||
EmployeeEntity entity = SmartBeanUtil.copy(employeeUpdateForm, EmployeeEntity.class);
|
EmployeeEntity entity = SmartBeanUtil.copy(employeeUpdateForm, EmployeeEntity.class);
|
||||||
entity.setLoginPwd(null);
|
entity.setLoginPwd(null);
|
||||||
@@ -183,12 +186,38 @@ public class EmployeeService {
|
|||||||
// 更新数据
|
// 更新数据
|
||||||
employeeManager.updateEmployee(entity, employeeUpdateForm.getRoleIdList());
|
employeeManager.updateEmployee(entity, employeeUpdateForm.getRoleIdList());
|
||||||
|
|
||||||
|
// 清除员工缓存
|
||||||
|
loginService.clearLoginEmployeeCache(employeeId);
|
||||||
|
|
||||||
|
return ResponseDTO.ok();
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 更新登录人头像
|
||||||
|
*
|
||||||
|
* @param employeeUpdateAvatarForm
|
||||||
|
* @return
|
||||||
|
*/
|
||||||
|
public ResponseDTO<String> updateAvatar(EmployeeUpdateAvatarForm employeeUpdateAvatarForm) {
|
||||||
|
Long employeeId = employeeUpdateAvatarForm.getEmployeeId();
|
||||||
|
EmployeeEntity employeeEntity = employeeDao.selectById(employeeId);
|
||||||
|
if (employeeEntity == null) {
|
||||||
|
return ResponseDTO.error(UserErrorCode.DATA_NOT_EXIST);
|
||||||
|
}
|
||||||
|
// 更新头像
|
||||||
|
EmployeeEntity updateEntity = new EmployeeEntity();
|
||||||
|
updateEntity.setEmployeeId(employeeId);
|
||||||
|
updateEntity.setAvatar(employeeUpdateAvatarForm.getAvatar());
|
||||||
|
employeeDao.updateById(updateEntity);
|
||||||
|
|
||||||
|
// 清除员工缓存
|
||||||
|
loginService.clearLoginEmployeeCache(employeeId);
|
||||||
return ResponseDTO.ok();
|
return ResponseDTO.ok();
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 更新禁用/启用状态
|
* 更新禁用/启用状态
|
||||||
*
|
|
||||||
*/
|
*/
|
||||||
public ResponseDTO<String> updateDisableFlag(Long employeeId) {
|
public ResponseDTO<String> updateDisableFlag(Long employeeId) {
|
||||||
if (null == employeeId) {
|
if (null == employeeId) {
|
||||||
@@ -210,7 +239,6 @@ public class EmployeeService {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* 批量删除员工
|
* 批量删除员工
|
||||||
*
|
|
||||||
*/
|
*/
|
||||||
public ResponseDTO<String> batchUpdateDeleteFlag(List<Long> employeeIdList) {
|
public ResponseDTO<String> batchUpdateDeleteFlag(List<Long> employeeIdList) {
|
||||||
if (CollectionUtils.isEmpty(employeeIdList)) {
|
if (CollectionUtils.isEmpty(employeeIdList)) {
|
||||||
@@ -239,7 +267,6 @@ public class EmployeeService {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* 批量更新部门
|
* 批量更新部门
|
||||||
*
|
|
||||||
*/
|
*/
|
||||||
public ResponseDTO<String> batchUpdateDepartment(EmployeeBatchUpdateDepartmentForm batchUpdateDepartmentForm) {
|
public ResponseDTO<String> batchUpdateDepartment(EmployeeBatchUpdateDepartmentForm batchUpdateDepartmentForm) {
|
||||||
List<Long> employeeIdList = batchUpdateDepartmentForm.getEmployeeIdList();
|
List<Long> employeeIdList = batchUpdateDepartmentForm.getEmployeeIdList();
|
||||||
@@ -262,44 +289,52 @@ public class EmployeeService {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* 更新密码
|
* 更新密码
|
||||||
*
|
|
||||||
*/
|
*/
|
||||||
public ResponseDTO<String> updatePassword(EmployeeUpdatePasswordForm updatePasswordForm) {
|
@Transactional(rollbackFor = Throwable.class)
|
||||||
|
public ResponseDTO<String> updatePassword(RequestUser requestUser, EmployeeUpdatePasswordForm updatePasswordForm) {
|
||||||
Long employeeId = updatePasswordForm.getEmployeeId();
|
Long employeeId = updatePasswordForm.getEmployeeId();
|
||||||
EmployeeEntity employeeEntity = employeeDao.selectById(employeeId);
|
EmployeeEntity employeeEntity = employeeDao.selectById(employeeId);
|
||||||
if (employeeEntity == null) {
|
if (employeeEntity == null) {
|
||||||
return ResponseDTO.error(UserErrorCode.DATA_NOT_EXIST);
|
return ResponseDTO.error(UserErrorCode.DATA_NOT_EXIST);
|
||||||
}
|
}
|
||||||
// 校验原始密码
|
// 校验原始密码
|
||||||
String encryptPwd = getEncryptPwd(updatePasswordForm.getOldPassword());
|
String oldPassword = SecurityPasswordService.getEncryptPwd(updatePasswordForm.getOldPassword());
|
||||||
if (!Objects.equals(encryptPwd, employeeEntity.getLoginPwd())) {
|
if (!Objects.equals(oldPassword, employeeEntity.getLoginPwd())) {
|
||||||
return ResponseDTO.userErrorParam("原密码有误,请重新输入");
|
return ResponseDTO.userErrorParam("原密码有误,请重新输入");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// 校验密码复杂度
|
||||||
|
ResponseDTO<String> validatePassComplexity = securityPasswordService.validatePasswordComplexity(updatePasswordForm.getNewPassword());
|
||||||
|
if (!validatePassComplexity.getOk()) {
|
||||||
|
return validatePassComplexity;
|
||||||
|
}
|
||||||
|
|
||||||
// 新旧密码相同
|
// 新旧密码相同
|
||||||
String newPassword = updatePasswordForm.getNewPassword();
|
String newPassword = SecurityPasswordService.getEncryptPwd(updatePasswordForm.getNewPassword());
|
||||||
if (Objects.equals(updatePasswordForm.getOldPassword(), newPassword)) {
|
if (Objects.equals(oldPassword, newPassword)) {
|
||||||
return ResponseDTO.userErrorParam("新密码与原始密码相同,请重新输入");
|
return ResponseDTO.userErrorParam("新密码与原始密码相同,请重新输入");
|
||||||
}
|
}
|
||||||
|
|
||||||
// 校验密码复杂度
|
// 根据三级等保规则,校验密码是否重复
|
||||||
ResponseDTO<String> validatePassComplexity = protectPasswordService.validatePassComplexity(newPassword);
|
ResponseDTO<String> passwordRepeatTimes = securityPasswordService.validatePasswordRepeatTimes(requestUser, updatePasswordForm.getNewPassword());
|
||||||
if (!validatePassComplexity.getOk()) {
|
if (!passwordRepeatTimes.getOk()) {
|
||||||
return validatePassComplexity;
|
return ResponseDTO.error(passwordRepeatTimes);
|
||||||
}
|
}
|
||||||
|
|
||||||
// 更新密码
|
// 更新密码
|
||||||
EmployeeEntity updateEntity = new EmployeeEntity();
|
EmployeeEntity updateEntity = new EmployeeEntity();
|
||||||
updateEntity.setEmployeeId(employeeId);
|
updateEntity.setEmployeeId(employeeId);
|
||||||
updateEntity.setLoginPwd(getEncryptPwd(newPassword));
|
updateEntity.setLoginPwd(newPassword);
|
||||||
employeeDao.updateById(updateEntity);
|
employeeDao.updateById(updateEntity);
|
||||||
|
|
||||||
|
// 保存修改密码密码记录
|
||||||
|
securityPasswordService.saveUserChangePasswordLog(requestUser, newPassword, oldPassword);
|
||||||
|
|
||||||
return ResponseDTO.ok();
|
return ResponseDTO.ok();
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 获取某个部门的员工信息
|
* 获取某个部门的员工信息
|
||||||
*
|
|
||||||
*/
|
*/
|
||||||
public ResponseDTO<List<EmployeeVO>> getAllEmployeeByDepartmentId(Long departmentId, Boolean disabledFlag) {
|
public ResponseDTO<List<EmployeeVO>> getAllEmployeeByDepartmentId(Long departmentId, Boolean disabledFlag) {
|
||||||
List<EmployeeEntity> employeeEntityList = employeeDao.selectByDepartmentId(departmentId, disabledFlag);
|
List<EmployeeEntity> employeeEntityList = employeeDao.selectByDepartmentId(departmentId, disabledFlag);
|
||||||
@@ -326,26 +361,16 @@ public class EmployeeService {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* 重置密码
|
* 重置密码
|
||||||
*
|
|
||||||
*/
|
*/
|
||||||
public ResponseDTO<String> resetPassword(Integer employeeId) {
|
public ResponseDTO<String> resetPassword(Integer employeeId) {
|
||||||
String password = protectPasswordService.randomPassword();
|
String password = securityPasswordService.randomPassword();
|
||||||
employeeDao.updatePassword(employeeId, getEncryptPwd(password));
|
employeeDao.updatePassword(employeeId, SecurityPasswordService.getEncryptPwd(password));
|
||||||
return ResponseDTO.ok(password);
|
return ResponseDTO.ok(password);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* 获取 加密后 的密码
|
|
||||||
*
|
|
||||||
*/
|
|
||||||
public static String getEncryptPwd(String password) {
|
|
||||||
return DigestUtils.md5Hex(String.format(PASSWORD_SALT_FORMAT, password));
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 查询全部员工
|
* 查询全部员工
|
||||||
*
|
|
||||||
*/
|
*/
|
||||||
public ResponseDTO<List<EmployeeVO>> queryAllEmployee(Boolean disabledFlag) {
|
public ResponseDTO<List<EmployeeVO>> queryAllEmployee(Boolean disabledFlag) {
|
||||||
List<EmployeeVO> employeeList = employeeDao.selectEmployeeByDisabledAndDeleted(disabledFlag, Boolean.FALSE);
|
List<EmployeeVO> employeeList = employeeDao.selectEmployeeByDisabledAndDeleted(disabledFlag, Boolean.FALSE);
|
||||||
@@ -354,7 +379,6 @@ public class EmployeeService {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* 根据登录名获取员工
|
* 根据登录名获取员工
|
||||||
*
|
|
||||||
*/
|
*/
|
||||||
public EmployeeEntity getByLoginName(String loginName) {
|
public EmployeeEntity getByLoginName(String loginName) {
|
||||||
return employeeDao.getByLoginName(loginName, null);
|
return employeeDao.getByLoginName(loginName, null);
|
||||||
|
|||||||
@@ -2,8 +2,8 @@ package net.lab1024.sa.admin.module.system.login.controller;
|
|||||||
|
|
||||||
import cn.dev33.satoken.stp.StpUtil;
|
import cn.dev33.satoken.stp.StpUtil;
|
||||||
import cn.hutool.extra.servlet.ServletUtil;
|
import cn.hutool.extra.servlet.ServletUtil;
|
||||||
import io.swagger.v3.oas.annotations.tags.Tag;
|
|
||||||
import io.swagger.v3.oas.annotations.Operation;
|
import io.swagger.v3.oas.annotations.Operation;
|
||||||
|
import io.swagger.v3.oas.annotations.tags.Tag;
|
||||||
import net.lab1024.sa.admin.constant.AdminSwaggerTagConst;
|
import net.lab1024.sa.admin.constant.AdminSwaggerTagConst;
|
||||||
import net.lab1024.sa.admin.module.system.login.domain.LoginForm;
|
import net.lab1024.sa.admin.module.system.login.domain.LoginForm;
|
||||||
import net.lab1024.sa.admin.module.system.login.domain.LoginResultVO;
|
import net.lab1024.sa.admin.module.system.login.domain.LoginResultVO;
|
||||||
@@ -14,6 +14,7 @@ import net.lab1024.sa.base.common.constant.RequestHeaderConst;
|
|||||||
import net.lab1024.sa.base.common.domain.ResponseDTO;
|
import net.lab1024.sa.base.common.domain.ResponseDTO;
|
||||||
import net.lab1024.sa.base.common.util.SmartRequestUtil;
|
import net.lab1024.sa.base.common.util.SmartRequestUtil;
|
||||||
import net.lab1024.sa.base.module.support.captcha.domain.CaptchaVO;
|
import net.lab1024.sa.base.module.support.captcha.domain.CaptchaVO;
|
||||||
|
import net.lab1024.sa.base.module.support.securityprotect.service.Level3ProtectConfigService;
|
||||||
import org.springframework.web.bind.annotation.*;
|
import org.springframework.web.bind.annotation.*;
|
||||||
|
|
||||||
import javax.annotation.Resource;
|
import javax.annotation.Resource;
|
||||||
@@ -36,6 +37,9 @@ public class LoginController {
|
|||||||
@Resource
|
@Resource
|
||||||
private LoginService loginService;
|
private LoginService loginService;
|
||||||
|
|
||||||
|
@Resource
|
||||||
|
private Level3ProtectConfigService level3ProtectConfigService;
|
||||||
|
|
||||||
@NoNeedLogin
|
@NoNeedLogin
|
||||||
@PostMapping("/login")
|
@PostMapping("/login")
|
||||||
@Operation(summary = "登录 @author 卓大")
|
@Operation(summary = "登录 @author 卓大")
|
||||||
@@ -48,8 +52,8 @@ public class LoginController {
|
|||||||
@GetMapping("/login/getLoginInfo")
|
@GetMapping("/login/getLoginInfo")
|
||||||
@Operation(summary = "获取登录结果信息 @author 卓大")
|
@Operation(summary = "获取登录结果信息 @author 卓大")
|
||||||
public ResponseDTO<LoginResultVO> getLoginInfo() {
|
public ResponseDTO<LoginResultVO> getLoginInfo() {
|
||||||
LoginResultVO loginResult = loginService.getLoginResult(AdminRequestUtil.getRequestUser());
|
|
||||||
String tokenValue = StpUtil.getTokenValue();
|
String tokenValue = StpUtil.getTokenValue();
|
||||||
|
LoginResultVO loginResult = loginService.getLoginResult(AdminRequestUtil.getRequestUser(), tokenValue);
|
||||||
loginResult.setToken(tokenValue);
|
loginResult.setToken(tokenValue);
|
||||||
return ResponseDTO.ok(loginResult);
|
return ResponseDTO.ok(loginResult);
|
||||||
}
|
}
|
||||||
@@ -67,4 +71,20 @@ public class LoginController {
|
|||||||
return loginService.getCaptcha();
|
return loginService.getCaptcha();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@NoNeedLogin
|
||||||
|
@GetMapping("/login/sendEmailCode/{loginName}")
|
||||||
|
@Operation(summary = "获取邮箱登录验证码 @author 卓大")
|
||||||
|
public ResponseDTO<String> sendEmailCode(@PathVariable String loginName) {
|
||||||
|
return loginService.sendEmailCode(loginName);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@NoNeedLogin
|
||||||
|
@GetMapping("/login/getTwoFactorLoginFlag")
|
||||||
|
@Operation(summary = "获取双因子登录标识 @author 卓大")
|
||||||
|
public ResponseDTO<Boolean> getTwoFactorLoginFlag() {
|
||||||
|
// 双因子登录
|
||||||
|
boolean twoFactorLoginEnabled = level3ProtectConfigService.isTwoFactorLoginEnabled();
|
||||||
|
return ResponseDTO.ok(twoFactorLoginEnabled);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -34,4 +34,7 @@ public class LoginForm extends CaptchaForm {
|
|||||||
@SchemaEnum(desc = "登录终端", value = LoginDeviceEnum.class)
|
@SchemaEnum(desc = "登录终端", value = LoginDeviceEnum.class)
|
||||||
@CheckEnum(value = LoginDeviceEnum.class, required = true, message = "此终端不允许登录")
|
@CheckEnum(value = LoginDeviceEnum.class, required = true, message = "此终端不允许登录")
|
||||||
private Integer loginDevice;
|
private Integer loginDevice;
|
||||||
|
|
||||||
|
@Schema(description = "邮箱验证码")
|
||||||
|
private String emailCode;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -26,6 +26,9 @@ public class LoginResultVO extends RequestEmployee {
|
|||||||
@Schema(description = "菜单列表")
|
@Schema(description = "菜单列表")
|
||||||
private List<MenuVO> menuList;
|
private List<MenuVO> menuList;
|
||||||
|
|
||||||
|
@Schema(description = "是否需要修改密码")
|
||||||
|
private Boolean needUpdatePwdFlag;
|
||||||
|
|
||||||
@Schema(description = "上次登录ip")
|
@Schema(description = "上次登录ip")
|
||||||
private String lastLoginIp;
|
private String lastLoginIp;
|
||||||
|
|
||||||
|
|||||||
@@ -31,6 +31,9 @@ public class RequestEmployee implements RequestUser {
|
|||||||
@Schema(description = "员工名称")
|
@Schema(description = "员工名称")
|
||||||
private String actualName;
|
private String actualName;
|
||||||
|
|
||||||
|
@Schema(description = "头像")
|
||||||
|
private String avatar;
|
||||||
|
|
||||||
@SchemaEnum(GenderEnum.class)
|
@SchemaEnum(GenderEnum.class)
|
||||||
private Integer gender;
|
private Integer gender;
|
||||||
|
|
||||||
@@ -43,9 +46,15 @@ public class RequestEmployee implements RequestUser {
|
|||||||
@Schema(description = "部门名称")
|
@Schema(description = "部门名称")
|
||||||
private String departmentName;
|
private String departmentName;
|
||||||
|
|
||||||
|
@Schema(description = "是否禁用")
|
||||||
|
private Boolean disabledFlag;
|
||||||
|
|
||||||
@Schema(description = "是否为超管")
|
@Schema(description = "是否为超管")
|
||||||
private Boolean administratorFlag;
|
private Boolean administratorFlag;
|
||||||
|
|
||||||
|
@Schema(description = "备注")
|
||||||
|
private String remark;
|
||||||
|
|
||||||
@Schema(description = "请求ip")
|
@Schema(description = "请求ip")
|
||||||
private String ip;
|
private String ip;
|
||||||
|
|
||||||
|
|||||||
@@ -3,6 +3,8 @@ package net.lab1024.sa.admin.module.system.login.service;
|
|||||||
import cn.dev33.satoken.stp.StpInterface;
|
import cn.dev33.satoken.stp.StpInterface;
|
||||||
import cn.dev33.satoken.stp.StpUtil;
|
import cn.dev33.satoken.stp.StpUtil;
|
||||||
import cn.hutool.core.lang.UUID;
|
import cn.hutool.core.lang.UUID;
|
||||||
|
import cn.hutool.core.util.NumberUtil;
|
||||||
|
import cn.hutool.core.util.RandomUtil;
|
||||||
import cn.hutool.extra.servlet.ServletUtil;
|
import cn.hutool.extra.servlet.ServletUtil;
|
||||||
import com.googlecode.concurrentlinkedhashmap.ConcurrentLinkedHashMap;
|
import com.googlecode.concurrentlinkedhashmap.ConcurrentLinkedHashMap;
|
||||||
import lombok.extern.slf4j.Slf4j;
|
import lombok.extern.slf4j.Slf4j;
|
||||||
@@ -27,18 +29,27 @@ import net.lab1024.sa.base.common.enumeration.UserTypeEnum;
|
|||||||
import net.lab1024.sa.base.common.util.SmartBeanUtil;
|
import net.lab1024.sa.base.common.util.SmartBeanUtil;
|
||||||
import net.lab1024.sa.base.common.util.SmartEnumUtil;
|
import net.lab1024.sa.base.common.util.SmartEnumUtil;
|
||||||
import net.lab1024.sa.base.common.util.SmartIpUtil;
|
import net.lab1024.sa.base.common.util.SmartIpUtil;
|
||||||
|
import net.lab1024.sa.base.common.util.SmartStringUtil;
|
||||||
import net.lab1024.sa.base.constant.LoginDeviceEnum;
|
import net.lab1024.sa.base.constant.LoginDeviceEnum;
|
||||||
|
import net.lab1024.sa.base.constant.RedisKeyConst;
|
||||||
|
import net.lab1024.sa.base.module.support.apiencrypt.service.ApiEncryptService;
|
||||||
import net.lab1024.sa.base.module.support.captcha.CaptchaService;
|
import net.lab1024.sa.base.module.support.captcha.CaptchaService;
|
||||||
import net.lab1024.sa.base.module.support.captcha.domain.CaptchaVO;
|
import net.lab1024.sa.base.module.support.captcha.domain.CaptchaVO;
|
||||||
import net.lab1024.sa.base.module.support.config.ConfigKeyEnum;
|
import net.lab1024.sa.base.module.support.config.ConfigKeyEnum;
|
||||||
import net.lab1024.sa.base.module.support.config.ConfigService;
|
import net.lab1024.sa.base.module.support.config.ConfigService;
|
||||||
|
import net.lab1024.sa.base.module.support.file.service.IFileStorageService;
|
||||||
import net.lab1024.sa.base.module.support.loginlog.LoginLogResultEnum;
|
import net.lab1024.sa.base.module.support.loginlog.LoginLogResultEnum;
|
||||||
import net.lab1024.sa.base.module.support.loginlog.LoginLogService;
|
import net.lab1024.sa.base.module.support.loginlog.LoginLogService;
|
||||||
import net.lab1024.sa.base.module.support.loginlog.domain.LoginLogEntity;
|
import net.lab1024.sa.base.module.support.loginlog.domain.LoginLogEntity;
|
||||||
import net.lab1024.sa.base.module.support.loginlog.domain.LoginLogVO;
|
import net.lab1024.sa.base.module.support.loginlog.domain.LoginLogVO;
|
||||||
|
import net.lab1024.sa.base.module.support.mail.MailService;
|
||||||
|
import net.lab1024.sa.base.module.support.mail.constant.MailTemplateCodeEnum;
|
||||||
|
import net.lab1024.sa.base.module.support.redis.RedisService;
|
||||||
import net.lab1024.sa.base.module.support.securityprotect.domain.LoginFailEntity;
|
import net.lab1024.sa.base.module.support.securityprotect.domain.LoginFailEntity;
|
||||||
import net.lab1024.sa.base.module.support.securityprotect.service.ProtectLoginService;
|
import net.lab1024.sa.base.module.support.securityprotect.service.Level3ProtectConfigService;
|
||||||
import net.lab1024.sa.base.module.support.securityprotect.service.ProtectPasswordService;
|
import net.lab1024.sa.base.module.support.securityprotect.service.SecurityLoginService;
|
||||||
|
import net.lab1024.sa.base.module.support.securityprotect.service.SecurityPasswordService;
|
||||||
|
import org.apache.commons.lang3.BooleanUtils;
|
||||||
import org.apache.commons.lang3.StringUtils;
|
import org.apache.commons.lang3.StringUtils;
|
||||||
import org.springframework.stereotype.Service;
|
import org.springframework.stereotype.Service;
|
||||||
|
|
||||||
@@ -105,10 +116,25 @@ public class LoginService implements StpInterface {
|
|||||||
private RoleMenuService roleMenuService;
|
private RoleMenuService roleMenuService;
|
||||||
|
|
||||||
@Resource
|
@Resource
|
||||||
private ProtectLoginService protectLoginService;
|
private SecurityLoginService securityLoginService;
|
||||||
|
|
||||||
@Resource
|
@Resource
|
||||||
private ProtectPasswordService profectPasswordService;
|
private SecurityPasswordService protectPasswordService;
|
||||||
|
|
||||||
|
@Resource
|
||||||
|
private IFileStorageService fileStorageService;
|
||||||
|
|
||||||
|
@Resource
|
||||||
|
private ApiEncryptService apiEncryptService;
|
||||||
|
|
||||||
|
@Resource
|
||||||
|
private Level3ProtectConfigService level3ProtectConfigService;
|
||||||
|
|
||||||
|
@Resource
|
||||||
|
private MailService mailService;
|
||||||
|
|
||||||
|
@Resource
|
||||||
|
private RedisService redisService;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 获取验证码
|
* 获取验证码
|
||||||
@@ -148,12 +174,18 @@ public class LoginService implements StpInterface {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// 解密前端加密的密码
|
// 解密前端加密的密码
|
||||||
String requestPassword = profectPasswordService.decryptPassword(loginForm.getPassword());
|
String requestPassword = apiEncryptService.decrypt(loginForm.getPassword());
|
||||||
|
|
||||||
// 验证密码 是否为万能密码
|
// 验证密码 是否为万能密码
|
||||||
String superPassword = configService.getConfigValue(ConfigKeyEnum.SUPER_PASSWORD);
|
String superPassword = configService.getConfigValue(ConfigKeyEnum.SUPER_PASSWORD);
|
||||||
boolean superPasswordFlag = superPassword.equals(requestPassword);
|
boolean superPasswordFlag = superPassword.equals(requestPassword);
|
||||||
|
|
||||||
|
// 校验双因子登录
|
||||||
|
ResponseDTO<String> validateEmailCode = validateEmailCode(loginForm, employeeEntity, superPasswordFlag);
|
||||||
|
if (!validateEmailCode.getOk()) {
|
||||||
|
return ResponseDTO.error(validateEmailCode);
|
||||||
|
}
|
||||||
|
|
||||||
// 万能密码特殊操作
|
// 万能密码特殊操作
|
||||||
if (superPasswordFlag) {
|
if (superPasswordFlag) {
|
||||||
|
|
||||||
@@ -165,23 +197,27 @@ public class LoginService implements StpInterface {
|
|||||||
} else {
|
} else {
|
||||||
|
|
||||||
// 按照等保登录要求,进行登录失败次数校验
|
// 按照等保登录要求,进行登录失败次数校验
|
||||||
ResponseDTO<LoginFailEntity> loginFailEntityResponseDTO = protectLoginService.checkLogin(employeeEntity.getEmployeeId(), UserTypeEnum.ADMIN_EMPLOYEE);
|
ResponseDTO<LoginFailEntity> loginFailEntityResponseDTO = securityLoginService.checkLogin(employeeEntity.getEmployeeId(), UserTypeEnum.ADMIN_EMPLOYEE);
|
||||||
if (!loginFailEntityResponseDTO.getOk()) {
|
if (!loginFailEntityResponseDTO.getOk()) {
|
||||||
return ResponseDTO.error(loginFailEntityResponseDTO);
|
return ResponseDTO.error(loginFailEntityResponseDTO);
|
||||||
}
|
}
|
||||||
|
|
||||||
// 密码错误
|
// 密码错误
|
||||||
if (!employeeEntity.getLoginPwd().equals(EmployeeService.getEncryptPwd(requestPassword))) {
|
if (!employeeEntity.getLoginPwd().equals(SecurityPasswordService.getEncryptPwd(requestPassword))) {
|
||||||
// 记录登录失败
|
// 记录登录失败
|
||||||
saveLoginLog(employeeEntity, ip, userAgent, "密码错误", LoginLogResultEnum.LOGIN_FAIL);
|
saveLoginLog(employeeEntity, ip, userAgent, "密码错误", LoginLogResultEnum.LOGIN_FAIL);
|
||||||
// 记录等级保护次数
|
// 记录等级保护次数
|
||||||
String msg = protectLoginService.recordLoginFail(employeeEntity.getEmployeeId(), UserTypeEnum.ADMIN_EMPLOYEE, employeeEntity.getLoginName(), loginFailEntityResponseDTO.getData());
|
String msg = securityLoginService.recordLoginFail(employeeEntity.getEmployeeId(), UserTypeEnum.ADMIN_EMPLOYEE, employeeEntity.getLoginName(), loginFailEntityResponseDTO.getData());
|
||||||
return msg == null ? ResponseDTO.userErrorParam("登录名或密码错误!") : ResponseDTO.error(UserErrorCode.LOGIN_FAIL_WILL_LOCK, msg);
|
return msg == null ? ResponseDTO.userErrorParam("登录名或密码错误!") : ResponseDTO.error(UserErrorCode.LOGIN_FAIL_WILL_LOCK, msg);
|
||||||
}
|
}
|
||||||
|
|
||||||
String saTokenLoginId = UserTypeEnum.ADMIN_EMPLOYEE.getValue() + StringConst.COLON + employeeEntity.getEmployeeId();
|
String saTokenLoginId = UserTypeEnum.ADMIN_EMPLOYEE.getValue() + StringConst.COLON + employeeEntity.getEmployeeId();
|
||||||
|
|
||||||
// 登录
|
// 登录
|
||||||
StpUtil.login(saTokenLoginId, String.valueOf(loginDeviceEnum.getDesc()));
|
StpUtil.login(saTokenLoginId, String.valueOf(loginDeviceEnum.getDesc()));
|
||||||
|
|
||||||
|
// 移除邮箱验证码
|
||||||
|
deleteEmailCode(employeeEntity.getEmployeeId());
|
||||||
}
|
}
|
||||||
|
|
||||||
// 获取员工信息
|
// 获取员工信息
|
||||||
@@ -191,16 +227,17 @@ public class LoginService implements StpInterface {
|
|||||||
loginEmployeeCache.put(employeeEntity.getEmployeeId(), requestEmployee);
|
loginEmployeeCache.put(employeeEntity.getEmployeeId(), requestEmployee);
|
||||||
|
|
||||||
// 移除登录失败
|
// 移除登录失败
|
||||||
protectLoginService.removeLoginFail(employeeEntity.getEmployeeId(), UserTypeEnum.ADMIN_EMPLOYEE);
|
securityLoginService.removeLoginFail(employeeEntity.getEmployeeId(), UserTypeEnum.ADMIN_EMPLOYEE);
|
||||||
|
|
||||||
// 获取登录结果信息
|
// 获取登录结果信息
|
||||||
LoginResultVO loginResultVO = getLoginResult(requestEmployee);
|
String token = StpUtil.getTokenValue();
|
||||||
|
LoginResultVO loginResultVO = getLoginResult(requestEmployee, token);
|
||||||
|
|
||||||
//保存登录记录
|
//保存登录记录
|
||||||
saveLoginLog(employeeEntity, ip, userAgent, superPasswordFlag ? "万能密码登录" : loginDeviceEnum.getDesc(), LoginLogResultEnum.LOGIN_SUCCESS);
|
saveLoginLog(employeeEntity, ip, userAgent, superPasswordFlag ? "万能密码登录" : loginDeviceEnum.getDesc(), LoginLogResultEnum.LOGIN_SUCCESS);
|
||||||
|
|
||||||
// 设置 token
|
// 设置 token
|
||||||
loginResultVO.setToken(StpUtil.getTokenValue());
|
loginResultVO.setToken(token);
|
||||||
|
|
||||||
// 清除权限缓存
|
// 清除权限缓存
|
||||||
permissionCache.remove(employeeEntity.getEmployeeId());
|
permissionCache.remove(employeeEntity.getEmployeeId());
|
||||||
@@ -212,7 +249,7 @@ public class LoginService implements StpInterface {
|
|||||||
/**
|
/**
|
||||||
* 获取登录结果信息
|
* 获取登录结果信息
|
||||||
*/
|
*/
|
||||||
public LoginResultVO getLoginResult(RequestEmployee requestEmployee) {
|
public LoginResultVO getLoginResult(RequestEmployee requestEmployee, String token) {
|
||||||
|
|
||||||
// 基础信息
|
// 基础信息
|
||||||
LoginResultVO loginResultVO = SmartBeanUtil.copy(requestEmployee, LoginResultVO.class);
|
LoginResultVO loginResultVO = SmartBeanUtil.copy(requestEmployee, LoginResultVO.class);
|
||||||
@@ -235,6 +272,16 @@ public class LoginService implements StpInterface {
|
|||||||
loginResultVO.setLastLoginUserAgent(loginLogVO.getUserAgent());
|
loginResultVO.setLastLoginUserAgent(loginLogVO.getUserAgent());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// 是否需要强制修改密码
|
||||||
|
boolean needChangePasswordFlag = protectPasswordService.checkNeedChangePassword(requestEmployee.getUserType().getValue(), requestEmployee.getUserId());
|
||||||
|
loginResultVO.setNeedUpdatePwdFlag(needChangePasswordFlag);
|
||||||
|
|
||||||
|
// 万能密码登录,则不需要设置强制修改密码
|
||||||
|
String loginIdByToken = (String) StpUtil.getLoginIdByToken(token);
|
||||||
|
if (loginIdByToken != null && loginIdByToken.startsWith(SUPER_PASSWORD_LOGIN_ID_PREFIX)) {
|
||||||
|
loginResultVO.setNeedUpdatePwdFlag(false);
|
||||||
|
}
|
||||||
|
|
||||||
return loginResultVO;
|
return loginResultVO;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -252,6 +299,15 @@ public class LoginService implements StpInterface {
|
|||||||
DepartmentVO department = departmentService.getDepartmentById(employeeEntity.getDepartmentId());
|
DepartmentVO department = departmentService.getDepartmentById(employeeEntity.getDepartmentId());
|
||||||
requestEmployee.setDepartmentName(null == department ? StringConst.EMPTY : department.getName());
|
requestEmployee.setDepartmentName(null == department ? StringConst.EMPTY : department.getName());
|
||||||
|
|
||||||
|
// 头像信息
|
||||||
|
String avatar = employeeEntity.getAvatar();
|
||||||
|
if (StringUtils.isNotBlank(avatar)) {
|
||||||
|
ResponseDTO<String> getFileUrl = fileStorageService.getFileUrl(avatar);
|
||||||
|
if (BooleanUtils.isTrue(getFileUrl.getOk())) {
|
||||||
|
requestEmployee.setAvatar(getFileUrl.getData());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
return requestEmployee;
|
return requestEmployee;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -341,6 +397,14 @@ public class LoginService implements StpInterface {
|
|||||||
return ResponseDTO.ok();
|
return ResponseDTO.ok();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 清除员工登录缓存
|
||||||
|
*/
|
||||||
|
public void clearLoginEmployeeCache(Long employeeId) {
|
||||||
|
// 清空登录信息缓存
|
||||||
|
loginEmployeeCache.remove(employeeId);
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 保存登录日志
|
* 保存登录日志
|
||||||
*/
|
*/
|
||||||
@@ -428,4 +492,94 @@ public class LoginService implements StpInterface {
|
|||||||
|
|
||||||
return userPermission;
|
return userPermission;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 发送 邮箱 验证码
|
||||||
|
*/
|
||||||
|
public ResponseDTO<String> sendEmailCode(String loginName) {
|
||||||
|
|
||||||
|
// 开启双因子登录
|
||||||
|
if (!level3ProtectConfigService.isTwoFactorLoginEnabled()) {
|
||||||
|
return ResponseDTO.userErrorParam("无需使用邮箱验证码");
|
||||||
|
}
|
||||||
|
|
||||||
|
// 验证登录名
|
||||||
|
EmployeeEntity employeeEntity = employeeService.getByLoginName(loginName);
|
||||||
|
if (null == employeeEntity) {
|
||||||
|
return ResponseDTO.userErrorParam("登录名不存在!");
|
||||||
|
}
|
||||||
|
|
||||||
|
// 验证账号状态
|
||||||
|
if (employeeEntity.getDisabledFlag()) {
|
||||||
|
return ResponseDTO.userErrorParam("您的账号已被禁用,请联系工作人员!");
|
||||||
|
}
|
||||||
|
|
||||||
|
String mail = employeeEntity.getEmail();
|
||||||
|
if (SmartStringUtil.isBlank(mail)) {
|
||||||
|
return ResponseDTO.userErrorParam("您暂未配置邮箱地址,请联系管理员配置邮箱");
|
||||||
|
}
|
||||||
|
|
||||||
|
// 校验验证码发送时间,60秒内不能重复发生
|
||||||
|
String redisVerificationCodeKey = redisService.generateRedisKey(RedisKeyConst.Support.LOGIN_VERIFICATION_CODE, UserTypeEnum.ADMIN_EMPLOYEE.getValue() + RedisKeyConst.SEPARATOR + employeeEntity.getEmployeeId());
|
||||||
|
String emailCode = redisService.get(redisVerificationCodeKey);
|
||||||
|
long sendCodeTimeMills = -1;
|
||||||
|
if (!SmartStringUtil.isEmpty(emailCode)) {
|
||||||
|
sendCodeTimeMills = NumberUtil.parseLong(emailCode.split(StringConst.UNDERLINE)[1]);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (System.currentTimeMillis() - sendCodeTimeMills < 60 * 1000) {
|
||||||
|
return ResponseDTO.userErrorParam("邮箱验证码已发送,一分钟内请勿重复发送");
|
||||||
|
}
|
||||||
|
|
||||||
|
//生成验证码
|
||||||
|
long currentTimeMillis = System.currentTimeMillis();
|
||||||
|
String verificationCode = RandomUtil.randomNumbers(4);
|
||||||
|
redisService.set(redisVerificationCodeKey, verificationCode + StringConst.UNDERLINE + currentTimeMillis, 300);
|
||||||
|
|
||||||
|
// 发送邮件验证码
|
||||||
|
HashMap<String, Object> mailParams = new HashMap<>();
|
||||||
|
mailParams.put("code", verificationCode);
|
||||||
|
return mailService.sendMail(MailTemplateCodeEnum.LOGIN_VERIFICATION_CODE, mailParams, Collections.singletonList(employeeEntity.getEmail()));
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 校验邮箱验证码
|
||||||
|
*/
|
||||||
|
private ResponseDTO<String> validateEmailCode(LoginForm loginForm, EmployeeEntity employeeEntity, boolean superPasswordFlag) {
|
||||||
|
// 万能密码则不校验
|
||||||
|
if (superPasswordFlag) {
|
||||||
|
return ResponseDTO.ok();
|
||||||
|
}
|
||||||
|
|
||||||
|
// 未开启双因子登录
|
||||||
|
if (!level3ProtectConfigService.isTwoFactorLoginEnabled()) {
|
||||||
|
return ResponseDTO.ok();
|
||||||
|
}
|
||||||
|
|
||||||
|
if (SmartStringUtil.isEmpty(loginForm.getEmailCode())) {
|
||||||
|
return ResponseDTO.userErrorParam("请输入邮箱验证码");
|
||||||
|
}
|
||||||
|
|
||||||
|
// 校验验证码
|
||||||
|
String redisVerificationCodeKey = redisService.generateRedisKey(RedisKeyConst.Support.LOGIN_VERIFICATION_CODE, UserTypeEnum.ADMIN_EMPLOYEE.getValue() + RedisKeyConst.SEPARATOR + employeeEntity.getEmployeeId());
|
||||||
|
String emailCode = redisService.get(redisVerificationCodeKey);
|
||||||
|
if (SmartStringUtil.isEmpty(emailCode)) {
|
||||||
|
return ResponseDTO.userErrorParam("邮箱验证码已失效,请重新发送");
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!emailCode.split(StringConst.UNDERLINE)[0].equals(loginForm.getEmailCode().trim())) {
|
||||||
|
return ResponseDTO.userErrorParam("邮箱验证码错误,请重新填写");
|
||||||
|
}
|
||||||
|
|
||||||
|
return ResponseDTO.ok();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 移除邮箱验证码
|
||||||
|
*/
|
||||||
|
private void deleteEmailCode(Long employeeId) {
|
||||||
|
String redisVerificationCodeKey = redisService.generateRedisKey(RedisKeyConst.Support.LOGIN_VERIFICATION_CODE, UserTypeEnum.ADMIN_EMPLOYEE.getValue() + RedisKeyConst.SEPARATOR + employeeId);
|
||||||
|
redisService.delete(redisVerificationCodeKey);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -0,0 +1,75 @@
|
|||||||
|
package net.lab1024.sa.admin.module.system.position.controller;
|
||||||
|
|
||||||
|
import net.lab1024.sa.admin.constant.AdminSwaggerTagConst;
|
||||||
|
import net.lab1024.sa.admin.module.system.position.domain.form.PositionAddForm;
|
||||||
|
import net.lab1024.sa.admin.module.system.position.domain.form.PositionQueryForm;
|
||||||
|
import net.lab1024.sa.admin.module.system.position.domain.form.PositionUpdateForm;
|
||||||
|
import net.lab1024.sa.admin.module.system.position.domain.vo.PositionVO;
|
||||||
|
import net.lab1024.sa.admin.module.system.position.service.PositionService;
|
||||||
|
import net.lab1024.sa.base.common.domain.ValidateList;
|
||||||
|
import org.springframework.web.bind.annotation.GetMapping;
|
||||||
|
import org.springframework.web.bind.annotation.PathVariable;
|
||||||
|
import net.lab1024.sa.base.common.domain.ResponseDTO;
|
||||||
|
import net.lab1024.sa.base.common.domain.PageResult;
|
||||||
|
import org.springframework.web.bind.annotation.PostMapping;
|
||||||
|
import org.springframework.web.bind.annotation.RequestBody;
|
||||||
|
import org.springframework.web.bind.annotation.RestController;
|
||||||
|
import io.swagger.v3.oas.annotations.tags.Tag;
|
||||||
|
import io.swagger.v3.oas.annotations.Operation;
|
||||||
|
|
||||||
|
import javax.annotation.Resource;
|
||||||
|
import javax.validation.Valid;
|
||||||
|
import java.util.List;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 职务表 Controller
|
||||||
|
*
|
||||||
|
* @Author kaiyun
|
||||||
|
* @Date 2024-06-23 23:31:38
|
||||||
|
* @Copyright <a href="https://1024lab.net">1024创新实验室</a>
|
||||||
|
*/
|
||||||
|
|
||||||
|
@RestController
|
||||||
|
@Tag(name = AdminSwaggerTagConst.System.SYSTEM_POSITION)
|
||||||
|
public class PositionController {
|
||||||
|
|
||||||
|
@Resource
|
||||||
|
private PositionService positionService;
|
||||||
|
|
||||||
|
@Operation(summary = "分页查询 @author kaiyun")
|
||||||
|
@PostMapping("/position/queryPage")
|
||||||
|
public ResponseDTO<PageResult<PositionVO>> queryPage(@RequestBody @Valid PositionQueryForm queryForm) {
|
||||||
|
return ResponseDTO.ok(positionService.queryPage(queryForm));
|
||||||
|
}
|
||||||
|
|
||||||
|
@Operation(summary = "添加 @author kaiyun")
|
||||||
|
@PostMapping("/position/add")
|
||||||
|
public ResponseDTO<String> add(@RequestBody @Valid PositionAddForm addForm) {
|
||||||
|
return positionService.add(addForm);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Operation(summary = "更新 @author kaiyun")
|
||||||
|
@PostMapping("/position/update")
|
||||||
|
public ResponseDTO<String> update(@RequestBody @Valid PositionUpdateForm updateForm) {
|
||||||
|
return positionService.update(updateForm);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Operation(summary = "批量删除 @author kaiyun")
|
||||||
|
@PostMapping("/position/batchDelete")
|
||||||
|
public ResponseDTO<String> batchDelete(@RequestBody ValidateList<Long> idList) {
|
||||||
|
return positionService.batchDelete(idList);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Operation(summary = "单个删除 @author kaiyun")
|
||||||
|
@GetMapping("/position/delete/{positionId}")
|
||||||
|
public ResponseDTO<String> batchDelete(@PathVariable Long positionId) {
|
||||||
|
return positionService.delete(positionId);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@Operation(summary = "不分页查询 @author kaiyun")
|
||||||
|
@GetMapping("/position/queryList")
|
||||||
|
public ResponseDTO<List<PositionVO>> queryList() {
|
||||||
|
return ResponseDTO.ok(positionService.queryList());
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -0,0 +1,41 @@
|
|||||||
|
package net.lab1024.sa.admin.module.system.position.dao;
|
||||||
|
|
||||||
|
import java.util.List;
|
||||||
|
import net.lab1024.sa.admin.module.system.position.domain.entity.PositionEntity;
|
||||||
|
import net.lab1024.sa.admin.module.system.position.domain.form.PositionQueryForm;
|
||||||
|
import net.lab1024.sa.admin.module.system.position.domain.vo.PositionVO;
|
||||||
|
import com.baomidou.mybatisplus.core.mapper.BaseMapper;
|
||||||
|
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
|
||||||
|
import org.apache.ibatis.annotations.Mapper;
|
||||||
|
import org.apache.ibatis.annotations.Param;
|
||||||
|
import org.springframework.stereotype.Component;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 职务表 Dao
|
||||||
|
*
|
||||||
|
* @Author kaiyun
|
||||||
|
* @Date 2024-06-23 23:31:38
|
||||||
|
* @Copyright <a href="https://1024lab.net">1024创新实验室</a>
|
||||||
|
*/
|
||||||
|
|
||||||
|
@Mapper
|
||||||
|
@Component
|
||||||
|
public interface PositionDao extends BaseMapper<PositionEntity> {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 分页 查询
|
||||||
|
*
|
||||||
|
* @param page
|
||||||
|
* @param queryForm
|
||||||
|
* @return
|
||||||
|
*/
|
||||||
|
List<PositionVO> queryPage(Page page, @Param("queryForm") PositionQueryForm queryForm);
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 查询
|
||||||
|
* @param deletedFlag
|
||||||
|
* @return
|
||||||
|
*/
|
||||||
|
List<PositionVO> queryList(@Param("deletedFlag") Boolean deletedFlag);
|
||||||
|
}
|
||||||
@@ -0,0 +1,61 @@
|
|||||||
|
package net.lab1024.sa.admin.module.system.position.domain.entity;
|
||||||
|
|
||||||
|
import com.baomidou.mybatisplus.annotation.IdType;
|
||||||
|
import com.baomidou.mybatisplus.annotation.TableId;
|
||||||
|
import com.baomidou.mybatisplus.annotation.TableName;
|
||||||
|
|
||||||
|
import java.time.LocalDateTime;
|
||||||
|
|
||||||
|
import lombok.Data;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 职务表 实体类
|
||||||
|
*
|
||||||
|
* @Author kaiyun
|
||||||
|
* @Date 2024-06-23 23:31:38
|
||||||
|
* @Copyright <a href="https://1024lab.net">1024创新实验室</a>
|
||||||
|
*/
|
||||||
|
|
||||||
|
@Data
|
||||||
|
@TableName("t_position")
|
||||||
|
public class PositionEntity {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 职务ID
|
||||||
|
*/
|
||||||
|
@TableId(type = IdType.AUTO)
|
||||||
|
private Long positionId;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 职务名称
|
||||||
|
*/
|
||||||
|
private String positionName;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 职级
|
||||||
|
*/
|
||||||
|
private String level;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 排序
|
||||||
|
*/
|
||||||
|
private Integer sort;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 备注
|
||||||
|
*/
|
||||||
|
private String remark;
|
||||||
|
|
||||||
|
private Boolean deletedFlag;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 创建时间
|
||||||
|
*/
|
||||||
|
private LocalDateTime createTime;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 更新时间
|
||||||
|
*/
|
||||||
|
private LocalDateTime updateTime;
|
||||||
|
|
||||||
|
}
|
||||||
@@ -0,0 +1,34 @@
|
|||||||
|
package net.lab1024.sa.admin.module.system.position.domain.form;
|
||||||
|
|
||||||
|
import io.swagger.v3.oas.annotations.media.Schema;
|
||||||
|
import javax.validation.constraints.NotBlank;
|
||||||
|
import javax.validation.constraints.NotNull;
|
||||||
|
|
||||||
|
import lombok.Data;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 职务表 新建表单
|
||||||
|
*
|
||||||
|
* @Author kaiyun
|
||||||
|
* @Date 2024-06-23 23:31:38
|
||||||
|
* @Copyright <a href="https://1024lab.net">1024创新实验室</a>
|
||||||
|
*/
|
||||||
|
|
||||||
|
@Data
|
||||||
|
public class PositionAddForm {
|
||||||
|
|
||||||
|
@Schema(description = "职务名称", requiredMode = Schema.RequiredMode.REQUIRED)
|
||||||
|
@NotBlank(message = "职务名称 不能为空")
|
||||||
|
private String positionName;
|
||||||
|
|
||||||
|
@Schema(description = "职级")
|
||||||
|
private String level;
|
||||||
|
|
||||||
|
@Schema(description = "排序")
|
||||||
|
@NotNull(message = "排序不能为空")
|
||||||
|
private Integer sort;
|
||||||
|
|
||||||
|
@Schema(description = "备注")
|
||||||
|
private String remark;
|
||||||
|
|
||||||
|
}
|
||||||
@@ -0,0 +1,23 @@
|
|||||||
|
package net.lab1024.sa.admin.module.system.position.domain.form;
|
||||||
|
|
||||||
|
import net.lab1024.sa.base.common.domain.PageParam;
|
||||||
|
import io.swagger.v3.oas.annotations.media.Schema;
|
||||||
|
import lombok.Data;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 职务表 分页查询表单
|
||||||
|
*
|
||||||
|
* @Author kaiyun
|
||||||
|
* @Date 2024-06-23 23:31:38
|
||||||
|
* @Copyright <a href="https://1024lab.net">1024创新实验室</a>
|
||||||
|
*/
|
||||||
|
|
||||||
|
@Data
|
||||||
|
public class PositionQueryForm extends PageParam{
|
||||||
|
|
||||||
|
@Schema(description = "关键字查询")
|
||||||
|
private String keywords;
|
||||||
|
|
||||||
|
@Schema(hidden = true)
|
||||||
|
private Boolean deletedFlag;
|
||||||
|
}
|
||||||
@@ -0,0 +1,24 @@
|
|||||||
|
package net.lab1024.sa.admin.module.system.position.domain.form;
|
||||||
|
|
||||||
|
import io.swagger.v3.oas.annotations.media.Schema;
|
||||||
|
|
||||||
|
import javax.validation.constraints.NotNull;
|
||||||
|
|
||||||
|
import lombok.Data;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 职务表 更新表单
|
||||||
|
*
|
||||||
|
* @Author kaiyun
|
||||||
|
* @Date 2024-06-23 23:31:38
|
||||||
|
* @Copyright <a href="https://1024lab.net">1024创新实验室</a>
|
||||||
|
*/
|
||||||
|
|
||||||
|
@Data
|
||||||
|
public class PositionUpdateForm extends PositionAddForm {
|
||||||
|
|
||||||
|
@Schema(description = "职务ID", requiredMode = Schema.RequiredMode.REQUIRED)
|
||||||
|
@NotNull(message = "职务ID 不能为空")
|
||||||
|
private Long positionId;
|
||||||
|
|
||||||
|
}
|
||||||
@@ -0,0 +1,40 @@
|
|||||||
|
package net.lab1024.sa.admin.module.system.position.domain.vo;
|
||||||
|
|
||||||
|
import io.swagger.v3.oas.annotations.media.Schema;
|
||||||
|
import java.time.LocalDateTime;
|
||||||
|
import lombok.Data;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 职务表 列表VO
|
||||||
|
*
|
||||||
|
* @Author kaiyun
|
||||||
|
* @Date 2024-06-23 23:31:38
|
||||||
|
* @Copyright <a href="https://1024lab.net">1024创新实验室</a>
|
||||||
|
*/
|
||||||
|
|
||||||
|
@Data
|
||||||
|
public class PositionVO {
|
||||||
|
|
||||||
|
|
||||||
|
@Schema(description = "职务ID")
|
||||||
|
private Long positionId;
|
||||||
|
|
||||||
|
@Schema(description = "职务名称")
|
||||||
|
private String positionName;
|
||||||
|
|
||||||
|
@Schema(description = "职级")
|
||||||
|
private String level;
|
||||||
|
|
||||||
|
@Schema(description = "排序")
|
||||||
|
private Integer sort;
|
||||||
|
|
||||||
|
@Schema(description = "备注")
|
||||||
|
private String remark;
|
||||||
|
|
||||||
|
@Schema(description = "创建时间")
|
||||||
|
private LocalDateTime createTime;
|
||||||
|
|
||||||
|
@Schema(description = "更新时间")
|
||||||
|
private LocalDateTime updateTime;
|
||||||
|
|
||||||
|
}
|
||||||
@@ -0,0 +1,20 @@
|
|||||||
|
package net.lab1024.sa.admin.module.system.position.manager;
|
||||||
|
|
||||||
|
import net.lab1024.sa.admin.module.system.position.dao.PositionDao;
|
||||||
|
import net.lab1024.sa.admin.module.system.position.domain.entity.PositionEntity;
|
||||||
|
|
||||||
|
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
|
||||||
|
import org.springframework.stereotype.Service;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 职务表 Manager
|
||||||
|
*
|
||||||
|
* @Author kaiyun
|
||||||
|
* @Date 2024-06-23 23:31:38
|
||||||
|
* @Copyright <a href="https://1024lab.net">1024创新实验室</a>
|
||||||
|
*/
|
||||||
|
@Service
|
||||||
|
public class PositionManager extends ServiceImpl<PositionDao, PositionEntity> {
|
||||||
|
|
||||||
|
|
||||||
|
}
|
||||||
@@ -0,0 +1,105 @@
|
|||||||
|
package net.lab1024.sa.admin.module.system.position.service;
|
||||||
|
|
||||||
|
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
|
||||||
|
import net.lab1024.sa.admin.module.system.position.dao.PositionDao;
|
||||||
|
import net.lab1024.sa.admin.module.system.position.domain.entity.PositionEntity;
|
||||||
|
import net.lab1024.sa.admin.module.system.position.domain.form.PositionAddForm;
|
||||||
|
import net.lab1024.sa.admin.module.system.position.domain.form.PositionQueryForm;
|
||||||
|
import net.lab1024.sa.admin.module.system.position.domain.form.PositionUpdateForm;
|
||||||
|
import net.lab1024.sa.admin.module.system.position.domain.vo.PositionVO;
|
||||||
|
import net.lab1024.sa.base.common.domain.PageResult;
|
||||||
|
import net.lab1024.sa.base.common.domain.ResponseDTO;
|
||||||
|
import net.lab1024.sa.base.common.util.SmartBeanUtil;
|
||||||
|
import net.lab1024.sa.base.common.util.SmartPageUtil;
|
||||||
|
import org.apache.commons.collections4.CollectionUtils;
|
||||||
|
import org.springframework.stereotype.Service;
|
||||||
|
|
||||||
|
import javax.annotation.Resource;
|
||||||
|
import java.util.List;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 职务表 Service
|
||||||
|
*
|
||||||
|
* @Author kaiyun
|
||||||
|
* @Date 2024-06-23 23:31:38
|
||||||
|
* @Copyright <a href="https://1024lab.net">1024创新实验室</a>
|
||||||
|
*/
|
||||||
|
|
||||||
|
@Service
|
||||||
|
public class PositionService {
|
||||||
|
|
||||||
|
@Resource
|
||||||
|
private PositionDao positionDao;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 分页查询
|
||||||
|
*
|
||||||
|
* @param queryForm
|
||||||
|
* @return
|
||||||
|
*/
|
||||||
|
public PageResult<PositionVO> queryPage(PositionQueryForm queryForm) {
|
||||||
|
queryForm.setDeletedFlag(Boolean.FALSE);
|
||||||
|
Page<?> page = SmartPageUtil.convert2PageQuery(queryForm);
|
||||||
|
List<PositionVO> list = positionDao.queryPage(page, queryForm);
|
||||||
|
PageResult<PositionVO> pageResult = SmartPageUtil.convert2PageResult(page, list);
|
||||||
|
return pageResult;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 添加
|
||||||
|
*/
|
||||||
|
public ResponseDTO<String> add(PositionAddForm addForm) {
|
||||||
|
PositionEntity positionEntity = SmartBeanUtil.copy(addForm, PositionEntity.class);
|
||||||
|
positionDao.insert(positionEntity);
|
||||||
|
return ResponseDTO.ok();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 更新
|
||||||
|
*
|
||||||
|
* @param updateForm
|
||||||
|
* @return
|
||||||
|
*/
|
||||||
|
public ResponseDTO<String> update(PositionUpdateForm updateForm) {
|
||||||
|
PositionEntity positionEntity = SmartBeanUtil.copy(updateForm, PositionEntity.class);
|
||||||
|
positionDao.updateById(positionEntity);
|
||||||
|
return ResponseDTO.ok();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 批量删除
|
||||||
|
*
|
||||||
|
* @param idList
|
||||||
|
* @return
|
||||||
|
*/
|
||||||
|
public ResponseDTO<String> batchDelete(List<Long> idList) {
|
||||||
|
if (CollectionUtils.isEmpty(idList)){
|
||||||
|
return ResponseDTO.ok();
|
||||||
|
}
|
||||||
|
|
||||||
|
positionDao.deleteBatchIds(idList);
|
||||||
|
return ResponseDTO.ok();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 单个删除
|
||||||
|
*/
|
||||||
|
public ResponseDTO<String> delete(Long positionId) {
|
||||||
|
if (null == positionId){
|
||||||
|
return ResponseDTO.ok();
|
||||||
|
}
|
||||||
|
|
||||||
|
positionDao.deleteById(positionId);
|
||||||
|
return ResponseDTO.ok();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 分页查询
|
||||||
|
*
|
||||||
|
* @return
|
||||||
|
*/
|
||||||
|
public List<PositionVO> queryList() {
|
||||||
|
List<PositionVO> list = positionDao.queryList(Boolean.FALSE);
|
||||||
|
return list;
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -12,6 +12,7 @@ import net.lab1024.sa.admin.module.system.role.domain.form.RoleEmployeeQueryForm
|
|||||||
import net.lab1024.sa.admin.module.system.role.domain.vo.RoleEmployeeVO;
|
import net.lab1024.sa.admin.module.system.role.domain.vo.RoleEmployeeVO;
|
||||||
|
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
import java.util.Set;
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -50,7 +51,7 @@ public interface RoleEmployeeDao extends BaseMapper<RoleEmployeeEntity> {
|
|||||||
/**
|
/**
|
||||||
* 查询角色下的人员id
|
* 查询角色下的人员id
|
||||||
*/
|
*/
|
||||||
List<Long> selectEmployeeIdByRoleIdList(@Param("roleIdList") List<Long> roleIdList);
|
Set<Long> selectEmployeeIdByRoleIdList(@Param("roleIdList") List<Long> roleIdList);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
*
|
*
|
||||||
@@ -79,5 +80,10 @@ public interface RoleEmployeeDao extends BaseMapper<RoleEmployeeEntity> {
|
|||||||
/**
|
/**
|
||||||
* 批量删除某个角色下的某批用户的关联关系
|
* 批量删除某个角色下的某批用户的关联关系
|
||||||
*/
|
*/
|
||||||
void batchDeleteEmployeeRole(@Param("roleId") Long roleId,@Param("employeeIds")List<Long> employeeIds);
|
void batchDeleteEmployeeRole(@Param("roleId") Long roleId, @Param("employeeIds") Set<Long> employeeIds);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 判断某个角色下是否存在用户
|
||||||
|
*/
|
||||||
|
Integer existsByRoleId(@Param("roleId") Long roleId);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -5,7 +5,7 @@ import lombok.Data;
|
|||||||
|
|
||||||
import javax.validation.constraints.NotEmpty;
|
import javax.validation.constraints.NotEmpty;
|
||||||
import javax.validation.constraints.NotNull;
|
import javax.validation.constraints.NotNull;
|
||||||
import java.util.List;
|
import java.util.Set;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 角色的员工更新
|
* 角色的员工更新
|
||||||
@@ -25,6 +25,6 @@ public class RoleEmployeeUpdateForm {
|
|||||||
|
|
||||||
@Schema(description = "员工id集合")
|
@Schema(description = "员工id集合")
|
||||||
@NotEmpty(message = "员工id不能为空")
|
@NotEmpty(message = "员工id不能为空")
|
||||||
protected List<Long> employeeIdList;
|
protected Set<Long> employeeIdList;
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -2,12 +2,8 @@ package net.lab1024.sa.admin.module.system.role.manager;
|
|||||||
|
|
||||||
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
|
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
|
||||||
import net.lab1024.sa.admin.module.system.role.dao.RoleEmployeeDao;
|
import net.lab1024.sa.admin.module.system.role.dao.RoleEmployeeDao;
|
||||||
import org.apache.commons.collections4.CollectionUtils;
|
|
||||||
import org.springframework.stereotype.Service;
|
|
||||||
import org.springframework.transaction.annotation.Transactional;
|
|
||||||
import net.lab1024.sa.admin.module.system.role.domain.entity.RoleEmployeeEntity;
|
import net.lab1024.sa.admin.module.system.role.domain.entity.RoleEmployeeEntity;
|
||||||
|
import org.springframework.stereotype.Service;
|
||||||
import java.util.List;
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 角色员工 manager
|
* 角色员工 manager
|
||||||
@@ -21,15 +17,4 @@ import java.util.List;
|
|||||||
@Service
|
@Service
|
||||||
public class RoleEmployeeManager extends ServiceImpl<RoleEmployeeDao, RoleEmployeeEntity> {
|
public class RoleEmployeeManager extends ServiceImpl<RoleEmployeeDao, RoleEmployeeEntity> {
|
||||||
|
|
||||||
/**
|
|
||||||
* 保存 角色员工
|
|
||||||
*
|
|
||||||
*/
|
|
||||||
@Transactional(rollbackFor = Throwable.class)
|
|
||||||
public void saveRoleEmployee(Long roleId, List<RoleEmployeeEntity> roleEmployeeList) {
|
|
||||||
this.getBaseMapper().deleteByRoleId(roleId);
|
|
||||||
if (CollectionUtils.isNotEmpty(roleEmployeeList)) {
|
|
||||||
this.saveBatch(roleEmployeeList);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,6 +1,7 @@
|
|||||||
package net.lab1024.sa.admin.module.system.role.service;
|
package net.lab1024.sa.admin.module.system.role.service;
|
||||||
|
|
||||||
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
|
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
|
||||||
|
import com.google.common.collect.Lists;
|
||||||
import net.lab1024.sa.admin.module.system.department.dao.DepartmentDao;
|
import net.lab1024.sa.admin.module.system.department.dao.DepartmentDao;
|
||||||
import net.lab1024.sa.admin.module.system.department.domain.entity.DepartmentEntity;
|
import net.lab1024.sa.admin.module.system.department.domain.entity.DepartmentEntity;
|
||||||
import net.lab1024.sa.admin.module.system.employee.domain.vo.EmployeeVO;
|
import net.lab1024.sa.admin.module.system.employee.domain.vo.EmployeeVO;
|
||||||
@@ -20,12 +21,12 @@ import net.lab1024.sa.base.common.util.SmartBeanUtil;
|
|||||||
import net.lab1024.sa.base.common.util.SmartPageUtil;
|
import net.lab1024.sa.base.common.util.SmartPageUtil;
|
||||||
import org.apache.commons.collections4.CollectionUtils;
|
import org.apache.commons.collections4.CollectionUtils;
|
||||||
import org.springframework.stereotype.Service;
|
import org.springframework.stereotype.Service;
|
||||||
import org.springframework.transaction.annotation.Transactional;
|
|
||||||
|
|
||||||
import javax.annotation.Resource;
|
import javax.annotation.Resource;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
import java.util.Map;
|
import java.util.Map;
|
||||||
import java.util.Objects;
|
import java.util.Objects;
|
||||||
|
import java.util.Set;
|
||||||
import java.util.stream.Collectors;
|
import java.util.stream.Collectors;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -88,7 +89,6 @@ public class RoleEmployeeService {
|
|||||||
* 移除员工角色
|
* 移除员工角色
|
||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
@Transactional(rollbackFor = Exception.class)
|
|
||||||
public ResponseDTO<String> removeRoleEmployee(Long employeeId, Long roleId) {
|
public ResponseDTO<String> removeRoleEmployee(Long employeeId, Long roleId) {
|
||||||
if (null == employeeId || null == roleId) {
|
if (null == employeeId || null == roleId) {
|
||||||
return ResponseDTO.userErrorParam();
|
return ResponseDTO.userErrorParam();
|
||||||
@@ -112,16 +112,21 @@ public class RoleEmployeeService {
|
|||||||
*/
|
*/
|
||||||
public ResponseDTO<String> batchAddRoleEmployee(RoleEmployeeUpdateForm roleEmployeeUpdateForm) {
|
public ResponseDTO<String> batchAddRoleEmployee(RoleEmployeeUpdateForm roleEmployeeUpdateForm) {
|
||||||
Long roleId = roleEmployeeUpdateForm.getRoleId();
|
Long roleId = roleEmployeeUpdateForm.getRoleId();
|
||||||
List<Long> employeeIdList = roleEmployeeUpdateForm.getEmployeeIdList();
|
|
||||||
// 保存新的角色员工
|
// 已选择的员工id列表
|
||||||
List<RoleEmployeeEntity> roleEmployeeList = null;
|
Set<Long> selectedEmployeeIdList = roleEmployeeUpdateForm.getEmployeeIdList();
|
||||||
if (CollectionUtils.isNotEmpty(employeeIdList)) {
|
// 数据库里已有的员工id列表
|
||||||
roleEmployeeList = employeeIdList.stream()
|
Set<Long> dbEmployeeIdList = roleEmployeeDao.selectEmployeeIdByRoleIdList(Lists.newArrayList(roleId));
|
||||||
|
// 从已选择的员工id列表里 过滤数据库里不存在的 即需要添加的员工 id
|
||||||
|
Set<Long> addEmployeeIdList = selectedEmployeeIdList.stream().filter(id -> !dbEmployeeIdList.contains(id)).collect(Collectors.toSet());
|
||||||
|
|
||||||
|
// 添加角色员工
|
||||||
|
if (CollectionUtils.isNotEmpty(addEmployeeIdList)) {
|
||||||
|
List<RoleEmployeeEntity> roleEmployeeList = addEmployeeIdList.stream()
|
||||||
.map(employeeId -> new RoleEmployeeEntity(roleId, employeeId))
|
.map(employeeId -> new RoleEmployeeEntity(roleId, employeeId))
|
||||||
.collect(Collectors.toList());
|
.collect(Collectors.toList());
|
||||||
|
roleEmployeeManager.saveBatch(roleEmployeeList);
|
||||||
}
|
}
|
||||||
// 保存数据
|
|
||||||
roleEmployeeManager.saveRoleEmployee(roleId, roleEmployeeList);
|
|
||||||
return ResponseDTO.ok();
|
return ResponseDTO.ok();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -65,6 +65,11 @@ public class RoleService {
|
|||||||
if (null == roleEntity) {
|
if (null == roleEntity) {
|
||||||
return ResponseDTO.error(UserErrorCode.DATA_NOT_EXIST);
|
return ResponseDTO.error(UserErrorCode.DATA_NOT_EXIST);
|
||||||
}
|
}
|
||||||
|
// 当没有员工绑定这个角色时才可以删除
|
||||||
|
Integer exists = roleEmployeeDao.existsByRoleId(roleId);
|
||||||
|
if (exists != null) {
|
||||||
|
return ResponseDTO.error(UserErrorCode.ALREADY_EXIST, "该角色下存在员工,无法删除");
|
||||||
|
}
|
||||||
roleDao.deleteById(roleId);
|
roleDao.deleteById(roleId);
|
||||||
roleMenuDao.deleteByRoleId(roleId);
|
roleMenuDao.deleteByRoleId(roleId);
|
||||||
roleEmployeeDao.deleteByRoleId(roleId);
|
roleEmployeeDao.deleteByRoleId(roleId);
|
||||||
@@ -86,7 +91,7 @@ public class RoleService {
|
|||||||
}
|
}
|
||||||
|
|
||||||
existRoleEntity = roleDao.getByRoleCode(roleUpdateForm.getRoleCode());
|
existRoleEntity = roleDao.getByRoleCode(roleUpdateForm.getRoleCode());
|
||||||
if (null != existRoleEntity) {
|
if (null != existRoleEntity && !existRoleEntity.getRoleId().equals(roleUpdateForm.getRoleId())) {
|
||||||
return ResponseDTO.userErrorParam("角色编码重复,重复的角色为:" + existRoleEntity.getRoleName());
|
return ResponseDTO.userErrorParam("角色编码重复,重复的角色为:" + existRoleEntity.getRoleName());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -0,0 +1,88 @@
|
|||||||
|
package net.lab1024.sa.admin.module.system.support;
|
||||||
|
|
||||||
|
import cn.hutool.core.util.RandomUtil;
|
||||||
|
import io.swagger.v3.oas.annotations.Operation;
|
||||||
|
import io.swagger.v3.oas.annotations.tags.Tag;
|
||||||
|
import lombok.Data;
|
||||||
|
import net.lab1024.sa.base.common.controller.SupportBaseController;
|
||||||
|
import net.lab1024.sa.base.common.domain.ResponseDTO;
|
||||||
|
import net.lab1024.sa.base.constant.SwaggerTagConst;
|
||||||
|
import net.lab1024.sa.base.module.support.datamasking.DataMasking;
|
||||||
|
import net.lab1024.sa.base.module.support.datamasking.DataMaskingTypeEnum;
|
||||||
|
import org.apache.commons.lang3.RandomStringUtils;
|
||||||
|
import org.springframework.web.bind.annotation.GetMapping;
|
||||||
|
import org.springframework.web.bind.annotation.RestController;
|
||||||
|
|
||||||
|
import java.util.ArrayList;
|
||||||
|
import java.util.List;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 数据脱敏demo
|
||||||
|
*
|
||||||
|
* @Author 1024创新实验室-主任:卓大
|
||||||
|
* @Date 2024/08/01 22:07:27
|
||||||
|
* @Wechat zhuoda1024
|
||||||
|
* @Email lab1024@163.com
|
||||||
|
* @Copyright <a href="https://1024lab.net">1024创新实验室</a>,Since 2012
|
||||||
|
*/
|
||||||
|
|
||||||
|
@RestController
|
||||||
|
@Tag(name = SwaggerTagConst.Support.DATA_MASKING)
|
||||||
|
public class AdminDataMaskingDemoController extends SupportBaseController {
|
||||||
|
|
||||||
|
@Operation(summary = "数据脱敏demo @author 1024创新实验室-主任-卓大")
|
||||||
|
@GetMapping("/dataMasking/demo/query")
|
||||||
|
public ResponseDTO<List<DataVO>> query() {
|
||||||
|
|
||||||
|
List<DataVO> list = new ArrayList<>();
|
||||||
|
for (int i = 0; i < RandomUtil.randomInt(10,16); i++) {
|
||||||
|
DataVO data = new DataVO();
|
||||||
|
data.setUserId(RandomUtil.randomLong(1328479238, 83274298347982L));
|
||||||
|
data.setPhone("1" + RandomUtil.randomNumbers(10));
|
||||||
|
data.setIdCard("410" + RandomUtil.randomNumbers(3) + RandomUtil.randomInt(1980, 2010) + RandomUtil.randomInt(10, 12) + RandomUtil.randomInt(10, 30) + RandomUtil.randomNumbers(4));
|
||||||
|
data.setAddress(RandomUtil.randomBoolean() ? "河南省洛阳市洛龙区一零二四大街1024号" : "河南省郑州市高新区六边形大街六边形大楼");
|
||||||
|
data.setPassword(RandomUtil.randomString(10));
|
||||||
|
data.setEmail(RandomUtil.randomString(RandomUtil.randomInt(6, 10)) + "@" + RandomUtil.randomString(2) + ".com");
|
||||||
|
data.setCarLicense("豫" + RandomStringUtils.randomAlphabetic(1).toUpperCase()+" " + RandomStringUtils.randomAlphanumeric(5).toUpperCase());
|
||||||
|
data.setBankCard("6225" + RandomStringUtils.randomNumeric(14));
|
||||||
|
data.setOther(RandomStringUtils.randomAlphanumeric(1, 12));
|
||||||
|
list.add(data);
|
||||||
|
}
|
||||||
|
|
||||||
|
return ResponseDTO.ok(list);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@Data
|
||||||
|
public static class DataVO {
|
||||||
|
|
||||||
|
@DataMasking(DataMaskingTypeEnum.USER_ID)
|
||||||
|
private Long userId;
|
||||||
|
|
||||||
|
@DataMasking(DataMaskingTypeEnum.PHONE)
|
||||||
|
private String phone;
|
||||||
|
|
||||||
|
@DataMasking(DataMaskingTypeEnum.ID_CARD)
|
||||||
|
private String idCard;
|
||||||
|
|
||||||
|
@DataMasking(DataMaskingTypeEnum.ADDRESS)
|
||||||
|
private String address;
|
||||||
|
|
||||||
|
@DataMasking(DataMaskingTypeEnum.PASSWORD)
|
||||||
|
private String password;
|
||||||
|
|
||||||
|
@DataMasking(DataMaskingTypeEnum.EMAIL)
|
||||||
|
private String email;
|
||||||
|
|
||||||
|
@DataMasking(DataMaskingTypeEnum.CAR_LICENSE)
|
||||||
|
private String carLicense;
|
||||||
|
|
||||||
|
@DataMasking(DataMaskingTypeEnum.BANK_CARD)
|
||||||
|
private String bankCard;
|
||||||
|
|
||||||
|
@DataMasking
|
||||||
|
private String other;
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
@@ -5,7 +5,9 @@ import io.swagger.v3.oas.annotations.tags.Tag;
|
|||||||
import io.swagger.v3.oas.annotations.Operation;
|
import io.swagger.v3.oas.annotations.Operation;
|
||||||
import net.lab1024.sa.base.common.controller.SupportBaseController;
|
import net.lab1024.sa.base.common.controller.SupportBaseController;
|
||||||
import net.lab1024.sa.base.common.domain.PageResult;
|
import net.lab1024.sa.base.common.domain.PageResult;
|
||||||
|
import net.lab1024.sa.base.common.domain.RequestUser;
|
||||||
import net.lab1024.sa.base.common.domain.ResponseDTO;
|
import net.lab1024.sa.base.common.domain.ResponseDTO;
|
||||||
|
import net.lab1024.sa.base.common.util.SmartRequestUtil;
|
||||||
import net.lab1024.sa.base.constant.SwaggerTagConst;
|
import net.lab1024.sa.base.constant.SwaggerTagConst;
|
||||||
import net.lab1024.sa.base.module.support.loginlog.LoginLogService;
|
import net.lab1024.sa.base.module.support.loginlog.LoginLogService;
|
||||||
import net.lab1024.sa.base.module.support.loginlog.domain.LoginLogQueryForm;
|
import net.lab1024.sa.base.module.support.loginlog.domain.LoginLogQueryForm;
|
||||||
@@ -39,5 +41,14 @@ public class AdminLoginLogController extends SupportBaseController {
|
|||||||
return loginLogService.queryByPage(queryForm);
|
return loginLogService.queryByPage(queryForm);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Operation(summary = "分页查询当前登录人信息 @author 善逸")
|
||||||
|
@PostMapping("/loginLog/page/query/login")
|
||||||
|
public ResponseDTO<PageResult<LoginLogVO>> queryByPageLogin(@RequestBody LoginLogQueryForm queryForm) {
|
||||||
|
RequestUser requestUser = SmartRequestUtil.getRequestUser();
|
||||||
|
queryForm.setUserId(requestUser.getUserId());
|
||||||
|
queryForm.setUserType(requestUser.getUserType().getValue());
|
||||||
|
return loginLogService.queryByPage(queryForm);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -5,7 +5,9 @@ import io.swagger.v3.oas.annotations.tags.Tag;
|
|||||||
import io.swagger.v3.oas.annotations.Operation;
|
import io.swagger.v3.oas.annotations.Operation;
|
||||||
import net.lab1024.sa.base.common.controller.SupportBaseController;
|
import net.lab1024.sa.base.common.controller.SupportBaseController;
|
||||||
import net.lab1024.sa.base.common.domain.PageResult;
|
import net.lab1024.sa.base.common.domain.PageResult;
|
||||||
|
import net.lab1024.sa.base.common.domain.RequestUser;
|
||||||
import net.lab1024.sa.base.common.domain.ResponseDTO;
|
import net.lab1024.sa.base.common.domain.ResponseDTO;
|
||||||
|
import net.lab1024.sa.base.common.util.SmartRequestUtil;
|
||||||
import net.lab1024.sa.base.constant.SwaggerTagConst;
|
import net.lab1024.sa.base.constant.SwaggerTagConst;
|
||||||
import net.lab1024.sa.base.module.support.operatelog.OperateLogService;
|
import net.lab1024.sa.base.module.support.operatelog.OperateLogService;
|
||||||
import net.lab1024.sa.base.module.support.operatelog.domain.OperateLogQueryForm;
|
import net.lab1024.sa.base.module.support.operatelog.domain.OperateLogQueryForm;
|
||||||
@@ -44,4 +46,13 @@ public class AdminOperateLogController extends SupportBaseController {
|
|||||||
return operateLogService.detail(operateLogId);
|
return operateLogService.detail(operateLogId);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Operation(summary = "分页查询当前登录人信息 @author 善逸")
|
||||||
|
@PostMapping("/operateLog/page/query/login")
|
||||||
|
public ResponseDTO<PageResult<OperateLogVO>> queryByPageLogin(@RequestBody OperateLogQueryForm queryForm) {
|
||||||
|
RequestUser requestUser = SmartRequestUtil.getRequestUser();
|
||||||
|
queryForm.setOperateUserId(requestUser.getUserId());
|
||||||
|
queryForm.setOperateUserType(requestUser.getUserType().getValue());
|
||||||
|
return operateLogService.queryByPage(queryForm);
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,15 +1,20 @@
|
|||||||
package net.lab1024.sa.admin.module.system.support;
|
package net.lab1024.sa.admin.module.system.support;
|
||||||
|
|
||||||
import io.swagger.v3.oas.annotations.tags.Tag;
|
|
||||||
import io.swagger.v3.oas.annotations.Operation;
|
import io.swagger.v3.oas.annotations.Operation;
|
||||||
|
import io.swagger.v3.oas.annotations.tags.Tag;
|
||||||
import net.lab1024.sa.base.common.controller.SupportBaseController;
|
import net.lab1024.sa.base.common.controller.SupportBaseController;
|
||||||
import net.lab1024.sa.base.common.domain.PageResult;
|
import net.lab1024.sa.base.common.domain.PageResult;
|
||||||
import net.lab1024.sa.base.common.domain.ResponseDTO;
|
import net.lab1024.sa.base.common.domain.ResponseDTO;
|
||||||
import net.lab1024.sa.base.common.domain.ValidateList;
|
import net.lab1024.sa.base.common.domain.ValidateList;
|
||||||
import net.lab1024.sa.base.constant.SwaggerTagConst;
|
import net.lab1024.sa.base.constant.SwaggerTagConst;
|
||||||
|
import net.lab1024.sa.base.module.support.config.ConfigKeyEnum;
|
||||||
|
import net.lab1024.sa.base.module.support.config.ConfigService;
|
||||||
|
import net.lab1024.sa.base.module.support.securityprotect.domain.Level3ProtectConfigForm;
|
||||||
import net.lab1024.sa.base.module.support.securityprotect.domain.LoginFailQueryForm;
|
import net.lab1024.sa.base.module.support.securityprotect.domain.LoginFailQueryForm;
|
||||||
import net.lab1024.sa.base.module.support.securityprotect.domain.LoginFailVO;
|
import net.lab1024.sa.base.module.support.securityprotect.domain.LoginFailVO;
|
||||||
import net.lab1024.sa.base.module.support.securityprotect.service.ProtectLoginService;
|
import net.lab1024.sa.base.module.support.securityprotect.service.Level3ProtectConfigService;
|
||||||
|
import net.lab1024.sa.base.module.support.securityprotect.service.SecurityLoginService;
|
||||||
|
import org.springframework.web.bind.annotation.GetMapping;
|
||||||
import org.springframework.web.bind.annotation.PostMapping;
|
import org.springframework.web.bind.annotation.PostMapping;
|
||||||
import org.springframework.web.bind.annotation.RequestBody;
|
import org.springframework.web.bind.annotation.RequestBody;
|
||||||
import org.springframework.web.bind.annotation.RestController;
|
import org.springframework.web.bind.annotation.RestController;
|
||||||
@@ -18,7 +23,6 @@ import javax.annotation.Resource;
|
|||||||
import javax.validation.Valid;
|
import javax.validation.Valid;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
*
|
|
||||||
* 网络安全
|
* 网络安全
|
||||||
*
|
*
|
||||||
* @Author 1024创新实验室-主任:卓大
|
* @Author 1024创新实验室-主任:卓大
|
||||||
@@ -33,20 +37,37 @@ import javax.validation.Valid;
|
|||||||
public class AdminProtectController extends SupportBaseController {
|
public class AdminProtectController extends SupportBaseController {
|
||||||
|
|
||||||
@Resource
|
@Resource
|
||||||
private ProtectLoginService protectLoginService;
|
private SecurityLoginService securityLoginService;
|
||||||
|
|
||||||
|
@Resource
|
||||||
|
private Level3ProtectConfigService level3ProtectConfigService;
|
||||||
|
|
||||||
|
@Resource
|
||||||
|
private ConfigService configService;
|
||||||
|
|
||||||
|
|
||||||
@Operation(summary = "分页查询 @author 1024创新实验室-主任-卓大")
|
@Operation(summary = "分页查询 @author 1024创新实验室-主任-卓大")
|
||||||
@PostMapping("/protect/loginFail/queryPage")
|
@PostMapping("/protect/loginFail/queryPage")
|
||||||
public ResponseDTO<PageResult<LoginFailVO>> queryPage(@RequestBody @Valid LoginFailQueryForm queryForm) {
|
public ResponseDTO<PageResult<LoginFailVO>> queryPage(@RequestBody @Valid LoginFailQueryForm queryForm) {
|
||||||
return ResponseDTO.ok(protectLoginService.queryPage(queryForm));
|
return ResponseDTO.ok(securityLoginService.queryPage(queryForm));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@Operation(summary = "批量删除 @author 1024创新实验室-主任-卓大")
|
@Operation(summary = "批量删除 @author 1024创新实验室-主任-卓大")
|
||||||
@PostMapping("/protect/loginFail/batchDelete")
|
@PostMapping("/protect/loginFail/batchDelete")
|
||||||
public ResponseDTO<String> batchDelete(@RequestBody ValidateList<Long> idList) {
|
public ResponseDTO<String> batchDelete(@RequestBody ValidateList<Long> idList) {
|
||||||
return protectLoginService.batchDelete(idList);
|
return securityLoginService.batchDelete(idList);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Operation(summary = "更新三级等保配置 @author 1024创新实验室-主任-卓大")
|
||||||
|
@PostMapping("/protect/level3protect/updateConfig")
|
||||||
|
public ResponseDTO<String> updateConfig(@RequestBody @Valid Level3ProtectConfigForm configForm) {
|
||||||
|
return level3ProtectConfigService.updateLevel3Config(configForm);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Operation(summary = "查询 三级等保配置 @author 1024创新实验室-主任-卓大")
|
||||||
|
@GetMapping("/protect/level3protect/getConfig")
|
||||||
|
public ResponseDTO<String> getConfig() {
|
||||||
|
return ResponseDTO.ok(configService.getConfigValue(ConfigKeyEnum.LEVEL3_PROTECT_CONFIG));
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -0,0 +1,79 @@
|
|||||||
|
package net.lab1024.sa.admin.module.system.support;
|
||||||
|
|
||||||
|
import io.swagger.v3.oas.annotations.Operation;
|
||||||
|
import io.swagger.v3.oas.annotations.tags.Tag;
|
||||||
|
import net.lab1024.sa.base.common.controller.SupportBaseController;
|
||||||
|
import net.lab1024.sa.base.common.domain.PageResult;
|
||||||
|
import net.lab1024.sa.base.common.domain.RequestUser;
|
||||||
|
import net.lab1024.sa.base.common.domain.ResponseDTO;
|
||||||
|
import net.lab1024.sa.base.common.util.SmartRequestUtil;
|
||||||
|
import net.lab1024.sa.base.constant.SwaggerTagConst;
|
||||||
|
import net.lab1024.sa.base.module.support.job.api.SmartJobService;
|
||||||
|
import net.lab1024.sa.base.module.support.job.api.domain.*;
|
||||||
|
import net.lab1024.sa.base.module.support.job.config.SmartJobAutoConfiguration;
|
||||||
|
import net.lab1024.sa.base.module.support.repeatsubmit.annoation.RepeatSubmit;
|
||||||
|
import org.springframework.beans.factory.annotation.Autowired;
|
||||||
|
import org.springframework.boot.autoconfigure.condition.ConditionalOnBean;
|
||||||
|
import org.springframework.web.bind.annotation.*;
|
||||||
|
|
||||||
|
import javax.validation.Valid;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 定时任务 管理接口
|
||||||
|
*
|
||||||
|
* @author huke
|
||||||
|
* @date 2024/6/17 20:41
|
||||||
|
*/
|
||||||
|
@Tag(name = SwaggerTagConst.Support.JOB)
|
||||||
|
@RestController
|
||||||
|
@ConditionalOnBean(SmartJobAutoConfiguration.class)
|
||||||
|
public class AdminSmartJobController extends SupportBaseController {
|
||||||
|
|
||||||
|
@Autowired
|
||||||
|
private SmartJobService jobService;
|
||||||
|
|
||||||
|
@Operation(summary = "定时任务-立即执行 @huke")
|
||||||
|
@PostMapping("/job/execute")
|
||||||
|
@RepeatSubmit
|
||||||
|
public ResponseDTO<String> execute(@RequestBody @Valid SmartJobExecuteForm executeForm) {
|
||||||
|
RequestUser requestUser = SmartRequestUtil.getRequestUser();
|
||||||
|
executeForm.setUpdateName(requestUser.getUserName());
|
||||||
|
return jobService.execute(executeForm);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Operation(summary = "定时任务-查询详情 @huke")
|
||||||
|
@GetMapping("/job/{jobId}")
|
||||||
|
public ResponseDTO<SmartJobVO> queryJobInfo(@PathVariable Integer jobId) {
|
||||||
|
return jobService.queryJobInfo(jobId);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Operation(summary = "定时任务-分页查询 @huke")
|
||||||
|
@PostMapping("/job/query")
|
||||||
|
public ResponseDTO<PageResult<SmartJobVO>> queryJob(@RequestBody @Valid SmartJobQueryForm queryForm) {
|
||||||
|
return jobService.queryJob(queryForm);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Operation(summary = "定时任务-更新-任务信息 @huke")
|
||||||
|
@PostMapping("/job/update")
|
||||||
|
@RepeatSubmit
|
||||||
|
public ResponseDTO<String> updateJob(@RequestBody @Valid SmartJobUpdateForm updateForm) {
|
||||||
|
RequestUser requestUser = SmartRequestUtil.getRequestUser();
|
||||||
|
updateForm.setUpdateName(requestUser.getUserName());
|
||||||
|
return jobService.updateJob(updateForm);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Operation(summary = "定时任务-更新-开启状态 @huke")
|
||||||
|
@PostMapping("/job/update/enabled")
|
||||||
|
@RepeatSubmit
|
||||||
|
public ResponseDTO<String> updateJobEnabled(@RequestBody @Valid SmartJobEnabledUpdateForm updateForm) {
|
||||||
|
RequestUser requestUser = SmartRequestUtil.getRequestUser();
|
||||||
|
updateForm.setUpdateName(requestUser.getUserName());
|
||||||
|
return jobService.updateJobEnabled(updateForm);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Operation(summary = "定时任务-执行记录-分页查询 @huke")
|
||||||
|
@PostMapping("/job/log/query")
|
||||||
|
public ResponseDTO<PageResult<SmartJobLogVO>> queryJobLog(@RequestBody @Valid SmartJobLogQueryForm queryForm) {
|
||||||
|
return jobService.queryJobLog(queryForm);
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -8,7 +8,7 @@
|
|||||||
# 项目配置: 名称、日志目录
|
# 项目配置: 名称、日志目录
|
||||||
project:
|
project:
|
||||||
name: sa-admin
|
name: sa-admin
|
||||||
log-directory: /home/logs/smart_admin_v3/${project.name}/${spring.profiles.active}
|
log-directory: ${localPath:/home}/logs/smart_admin_v3/${project.name}/${spring.profiles.active}
|
||||||
|
|
||||||
# 项目端口和url根路径
|
# 项目端口和url根路径
|
||||||
server:
|
server:
|
||||||
@@ -20,32 +20,3 @@ server:
|
|||||||
spring:
|
spring:
|
||||||
profiles:
|
profiles:
|
||||||
active: '@profiles.active@'
|
active: '@profiles.active@'
|
||||||
|
|
||||||
# swagger文档
|
|
||||||
swagger:
|
|
||||||
host: localhost:${server.port}
|
|
||||||
tag-class: net.lab1024.sa.admin.constant.AdminSwaggerTagConst
|
|
||||||
|
|
||||||
|
|
||||||
####################################### 安全等级保护 相关配置 ##################################################
|
|
||||||
# #
|
|
||||||
# 建议开启 "三级等保" 所要求的配置,具体如下: #
|
|
||||||
# 1)连续登录失败 5 次锁定账户 30 分钟, #
|
|
||||||
# 2)登录超时时长建议为 30分钟,超过此时间没有访问系统会重新要求登录 #
|
|
||||||
# 3)密码复杂度至少三种字符,最小 8 位 #
|
|
||||||
# #
|
|
||||||
#############################################################################################################
|
|
||||||
|
|
||||||
classified-protect:
|
|
||||||
# 连续登录失败次数则锁定,-1表示不受限制,可以一直尝试登录
|
|
||||||
login-max-fail-times: 5
|
|
||||||
# 连续登录失败锁定时间(单位:秒),-1表示不锁定,建议锁定30分钟
|
|
||||||
login-fail-locked-seconds: 1800
|
|
||||||
# 密码复杂度开启(默认复杂度为:至少三种字符,最小 8 位), true 开启,false 不开启,建议开启
|
|
||||||
password-complexity-enabled: true
|
|
||||||
|
|
||||||
sa-token:
|
|
||||||
# token 最低活跃频率(单位:秒),如果 token 超过此时间没有访问系统就会被冻结,默认-1 代表不限制,永不冻结
|
|
||||||
active-timeout: 1800
|
|
||||||
# token 有效期(单位:秒) 1天(86400秒),-1 代表永久有效
|
|
||||||
timeout: 86400
|
|
||||||
@@ -18,7 +18,7 @@
|
|||||||
INSTR(goods_name,#{query.searchWord})
|
INSTR(goods_name,#{query.searchWord})
|
||||||
</if>
|
</if>
|
||||||
<if test="query.place != null">
|
<if test="query.place != null">
|
||||||
AND place = #{query.place}
|
AND INSTR(place,#{query.place})
|
||||||
</if>
|
</if>
|
||||||
<if test="query.goodsStatus != null">
|
<if test="query.goodsStatus != null">
|
||||||
AND goods_status = #{query.goodsStatus}
|
AND goods_status = #{query.goodsStatus}
|
||||||
|
|||||||
@@ -1,69 +0,0 @@
|
|||||||
<?xml version="1.0" encoding="UTF-8"?>
|
|
||||||
<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
|
|
||||||
<mapper namespace="net.lab1024.sa.admin.module.business.notice.NoticeDao">
|
|
||||||
<update id="updateWatchAmount">
|
|
||||||
UPDATE t_notice
|
|
||||||
SET watch_amount = watch_amount + 1
|
|
||||||
WHERE notice_id = #{noticeId}
|
|
||||||
</update>
|
|
||||||
<update id="batchDeleteNotice">
|
|
||||||
UPDATE t_notice
|
|
||||||
SET deleted_flag = #{deletedFlag}
|
|
||||||
WHERE notice_id IN
|
|
||||||
<foreach collection="noticeIdList" open="(" close=")" separator="," item="item">
|
|
||||||
#{item}
|
|
||||||
</foreach>
|
|
||||||
</update>
|
|
||||||
<update id="updateNotice">
|
|
||||||
UPDATE t_notice
|
|
||||||
SET notice_type = #{noticeType},
|
|
||||||
notice_belong_type = #{noticeBelongType},
|
|
||||||
notice_title = #{noticeTitle},
|
|
||||||
notice_content = #{noticeContent},
|
|
||||||
link_address = #{linkAddress},
|
|
||||||
cover_file_key = #{coverFileKey},
|
|
||||||
accessory_file_keys = #{accessoryFileKeys},
|
|
||||||
top_flag = #{topFlag},
|
|
||||||
publish_time = #{publishTime},
|
|
||||||
disabled_flag = #{disabledFlag}
|
|
||||||
WHERE notice_id = #{noticeId}
|
|
||||||
</update>
|
|
||||||
<select id="queryPage" resultType="net.lab1024.sa.admin.module.business.oa.notice.domain.vo.NoticeVO">
|
|
||||||
SELECT t_notice.*,
|
|
||||||
t_employee.actual_name AS createUserName
|
|
||||||
FROM t_notice
|
|
||||||
LEFT JOIN t_employee ON t_notice.create_user_id = t_employee.employee_id
|
|
||||||
<where>
|
|
||||||
t_notice.deleted_flag = #{queryForm.deletedFlag}
|
|
||||||
<if test="queryForm.keywords != null and queryForm.keywords != ''">
|
|
||||||
AND (INSTR(t_notice.notice_title,#{queryForm.keywords}) OR INSTR(t_employee.actual_name,#{queryForm.keywords}))
|
|
||||||
</if>
|
|
||||||
<if test="queryForm.noticeType != null">
|
|
||||||
AND t_notice.notice_type = #{queryForm.noticeType}
|
|
||||||
</if>
|
|
||||||
<if test="queryForm.noticeBelongType != null">
|
|
||||||
AND t_notice.notice_belong_type = #{queryForm.noticeBelongType}
|
|
||||||
</if>
|
|
||||||
<if test="queryForm.startTime != null">
|
|
||||||
AND DATE_FORMAT(t_notice.publish_time, '%Y-%m-%d') >= #{queryForm.startTime}
|
|
||||||
</if>
|
|
||||||
<if test="queryForm.endTime != null">
|
|
||||||
AND DATE_FORMAT(t_notice.publish_time, '%Y-%m-%d') <= #{queryForm.endTime}
|
|
||||||
</if>
|
|
||||||
<if test="queryForm.disabledFlag != null">
|
|
||||||
AND t_notice.disabled_flag = #{queryForm.disabledFlag}
|
|
||||||
</if>
|
|
||||||
</where>
|
|
||||||
<if test="queryForm.sortItemList == null or queryForm.sortItemList.size == 0">
|
|
||||||
ORDER BY t_notice.top_flag DESC,t_notice.publish_time DESC
|
|
||||||
</if>
|
|
||||||
</select>
|
|
||||||
<select id="getDetail" resultType="net.lab1024.sa.admin.module.business.oa.notice.domain.vo.NoticeVO">
|
|
||||||
SELECT tn.*,
|
|
||||||
e.actual_name AS createUserName
|
|
||||||
FROM t_notice tn
|
|
||||||
LEFT JOIN t_employee e ON tn.create_user_id = e.employee_id
|
|
||||||
WHERE tn.notice_id = #{noticeId}
|
|
||||||
AND tn.deleted_flag = #{deletedFlag}
|
|
||||||
</select>
|
|
||||||
</mapper>
|
|
||||||
@@ -242,5 +242,11 @@
|
|||||||
where notice_id = #{noticeId}
|
where notice_id = #{noticeId}
|
||||||
and employee_id = #{employeeId}
|
and employee_id = #{employeeId}
|
||||||
</update>
|
</update>
|
||||||
|
<update id="updateViewCount">
|
||||||
|
update t_notice
|
||||||
|
set page_view_count = page_view_count + #{pageViewCountIncrement},
|
||||||
|
user_view_count = user_view_count + #{userViewCountIncrement}
|
||||||
|
where notice_id = #{noticeId}
|
||||||
|
</update>
|
||||||
|
|
||||||
</mapper>
|
</mapper>
|
||||||
@@ -0,0 +1,25 @@
|
|||||||
|
<?xml version="1.0" encoding="UTF-8"?>
|
||||||
|
<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
|
||||||
|
<mapper namespace="net.lab1024.sa.admin.module.system.position.dao.PositionDao">
|
||||||
|
|
||||||
|
<!-- 分页查询 -->
|
||||||
|
<select id="queryPage" resultType="net.lab1024.sa.admin.module.system.position.domain.vo.PositionVO">
|
||||||
|
SELECT
|
||||||
|
*
|
||||||
|
FROM t_position
|
||||||
|
<where>
|
||||||
|
deleted_flag = #{queryForm.deletedFlag}
|
||||||
|
<!--关键字查询-->
|
||||||
|
<if test="queryForm.keywords != null and queryForm.keywords != ''">
|
||||||
|
AND INSTR(t_position.position_name,#{queryForm.keywords})
|
||||||
|
</if>
|
||||||
|
</where>
|
||||||
|
</select>
|
||||||
|
|
||||||
|
|
||||||
|
<select id="queryList" resultType="net.lab1024.sa.admin.module.system.position.domain.vo.PositionVO">
|
||||||
|
SELECT *
|
||||||
|
FROM t_position
|
||||||
|
where deleted_flag = #{deletedFlag}
|
||||||
|
</select>
|
||||||
|
</mapper>
|
||||||
@@ -85,7 +85,7 @@
|
|||||||
<select id="countByDepartmentId" resultType="integer">
|
<select id="countByDepartmentId" resultType="integer">
|
||||||
SELECT count(1) FROM t_employee
|
SELECT count(1) FROM t_employee
|
||||||
WHERE
|
WHERE
|
||||||
department_id = #{departmentId}
|
department_id = #{departmentId} AND deleted_flag = #{deletedFlag}
|
||||||
</select>
|
</select>
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
@@ -138,4 +138,12 @@
|
|||||||
#{item}
|
#{item}
|
||||||
</foreach>
|
</foreach>
|
||||||
</delete>
|
</delete>
|
||||||
|
|
||||||
|
<select id="existsByRoleId" resultType="java.lang.Integer">
|
||||||
|
SELECT 1
|
||||||
|
FROM t_role_employee er
|
||||||
|
WHERE er.role_id = #{roleId}
|
||||||
|
LIMIT 1
|
||||||
|
</select>
|
||||||
|
|
||||||
</mapper>
|
</mapper>
|
||||||
@@ -20,32 +20,3 @@ server:
|
|||||||
spring:
|
spring:
|
||||||
profiles:
|
profiles:
|
||||||
active: '@profiles.active@'
|
active: '@profiles.active@'
|
||||||
|
|
||||||
# swagger文档
|
|
||||||
swagger:
|
|
||||||
host: localhost:${server.port}
|
|
||||||
tag-class: net.lab1024.sa.admin.constant.AdminSwaggerTagConst
|
|
||||||
|
|
||||||
|
|
||||||
####################################### 安全等级保护 相关配置 ##################################################
|
|
||||||
# #
|
|
||||||
# 建议开启 "三级等保" 所要求的配置,具体如下: #
|
|
||||||
# 1)连续登录失败 5 次锁定账户 30 分钟, #
|
|
||||||
# 2)登录超时时长建议为 30分钟,超过此时间没有访问系统会重新要求登录 #
|
|
||||||
# 3)密码复杂度至少三种字符,最小 8 位 #
|
|
||||||
# #
|
|
||||||
#############################################################################################################
|
|
||||||
|
|
||||||
classified-protect:
|
|
||||||
# 连续登录失败次数则锁定,-1表示不受限制,可以一直尝试登录
|
|
||||||
login-max-fail-times: 5
|
|
||||||
# 连续登录失败锁定时间(单位:秒),-1表示不锁定,建议锁定30分钟
|
|
||||||
login-fail-locked-seconds: 1800
|
|
||||||
# 密码复杂度开启(默认复杂度为:至少三种字符,最小 8 位), true 开启,false 不开启,建议开启
|
|
||||||
password-complexity-enabled: true
|
|
||||||
|
|
||||||
sa-token:
|
|
||||||
# token 最低活跃频率(单位:秒),如果 token 超过此时间没有访问系统就会被冻结,默认-1 代表不限制,永不冻结
|
|
||||||
active-timeout: 1800
|
|
||||||
# token 有效期(单位:秒) 1天(86400秒),-1 代表永久有效
|
|
||||||
timeout: 86400
|
|
||||||
@@ -20,32 +20,3 @@ server:
|
|||||||
spring:
|
spring:
|
||||||
profiles:
|
profiles:
|
||||||
active: '@profiles.active@'
|
active: '@profiles.active@'
|
||||||
|
|
||||||
# swagger文档
|
|
||||||
swagger:
|
|
||||||
host: localhost:${server.port}
|
|
||||||
tag-class: net.lab1024.sa.admin.constant.AdminSwaggerTagConst
|
|
||||||
|
|
||||||
|
|
||||||
####################################### 安全等级保护 相关配置 ##################################################
|
|
||||||
# #
|
|
||||||
# 建议开启 "三级等保" 所要求的配置,具体如下: #
|
|
||||||
# 1)连续登录失败 5 次锁定账户 30 分钟, #
|
|
||||||
# 2)登录超时时长建议为 30分钟,超过此时间没有访问系统会重新要求登录 #
|
|
||||||
# 3)密码复杂度至少三种字符,最小 8 位 #
|
|
||||||
# #
|
|
||||||
#############################################################################################################
|
|
||||||
|
|
||||||
classified-protect:
|
|
||||||
# 连续登录失败次数则锁定,-1表示不受限制,可以一直尝试登录
|
|
||||||
login-max-fail-times: 5
|
|
||||||
# 连续登录失败锁定时间(单位:秒),-1表示不锁定,建议锁定30分钟
|
|
||||||
login-fail-locked-seconds: 1800
|
|
||||||
# 密码复杂度开启(默认复杂度为:至少三种字符,最小 8 位), true 开启,false 不开启,建议开启
|
|
||||||
password-complexity-enabled: true
|
|
||||||
|
|
||||||
sa-token:
|
|
||||||
# token 最低活跃频率(单位:秒),如果 token 超过此时间没有访问系统就会被冻结,默认-1 代表不限制,永不冻结
|
|
||||||
active-timeout: 1800
|
|
||||||
# token 有效期(单位:秒) 1天(86400秒),-1 代表永久有效
|
|
||||||
timeout: 86400
|
|
||||||
@@ -8,11 +8,11 @@
|
|||||||
# 项目配置: 名称、日志目录
|
# 项目配置: 名称、日志目录
|
||||||
project:
|
project:
|
||||||
name: sa-admin
|
name: sa-admin
|
||||||
log-directory: /home/logs/smart_admin_v3/${project.name}/${spring.profiles.active}
|
log-directory: /home/project/smartadmin/test/log
|
||||||
|
|
||||||
# 项目端口和url根路径
|
# 项目端口和url根路径
|
||||||
server:
|
server:
|
||||||
port: 1024
|
port: 11024
|
||||||
servlet:
|
servlet:
|
||||||
context-path: /
|
context-path: /
|
||||||
|
|
||||||
@@ -20,32 +20,3 @@ server:
|
|||||||
spring:
|
spring:
|
||||||
profiles:
|
profiles:
|
||||||
active: '@profiles.active@'
|
active: '@profiles.active@'
|
||||||
|
|
||||||
# swagger文档
|
|
||||||
swagger:
|
|
||||||
host: localhost:${server.port}
|
|
||||||
tag-class: net.lab1024.sa.admin.constant.AdminSwaggerTagConst
|
|
||||||
|
|
||||||
|
|
||||||
####################################### 安全等级保护 相关配置 ##################################################
|
|
||||||
# #
|
|
||||||
# 建议开启 "三级等保" 所要求的配置,具体如下: #
|
|
||||||
# 1)连续登录失败 5 次锁定账户 30 分钟, #
|
|
||||||
# 2)登录超时时长建议为 30分钟,超过此时间没有访问系统会重新要求登录 #
|
|
||||||
# 3)密码复杂度至少三种字符,最小 8 位 #
|
|
||||||
# #
|
|
||||||
#############################################################################################################
|
|
||||||
|
|
||||||
classified-protect:
|
|
||||||
# 连续登录失败次数则锁定,-1表示不受限制,可以一直尝试登录
|
|
||||||
login-max-fail-times: 5
|
|
||||||
# 连续登录失败锁定时间(单位:秒),-1表示不锁定,建议锁定30分钟
|
|
||||||
login-fail-locked-seconds: 1800
|
|
||||||
# 密码复杂度开启(默认复杂度为:至少三种字符,最小 8 位), true 开启,false 不开启,建议开启
|
|
||||||
password-complexity-enabled: true
|
|
||||||
|
|
||||||
sa-token:
|
|
||||||
# token 最低活跃频率(单位:秒),如果 token 超过此时间没有访问系统就会被冻结,默认-1 代表不限制,永不冻结
|
|
||||||
active-timeout: 1800
|
|
||||||
# token 有效期(单位:秒) 1天(86400秒),-1 代表永久有效
|
|
||||||
timeout: 86400
|
|
||||||
@@ -88,8 +88,8 @@
|
|||||||
</dependency>
|
</dependency>
|
||||||
|
|
||||||
<dependency>
|
<dependency>
|
||||||
<groupId>mysql</groupId>
|
<groupId>com.mysql</groupId>
|
||||||
<artifactId>mysql-connector-java</artifactId>
|
<artifactId>mysql-connector-j</artifactId>
|
||||||
</dependency>
|
</dependency>
|
||||||
|
|
||||||
<dependency>
|
<dependency>
|
||||||
@@ -113,6 +113,11 @@
|
|||||||
<artifactId>commons-pool2</artifactId>
|
<artifactId>commons-pool2</artifactId>
|
||||||
</dependency>
|
</dependency>
|
||||||
|
|
||||||
|
<dependency>
|
||||||
|
<groupId>org.apache.commons</groupId>
|
||||||
|
<artifactId>commons-text</artifactId>
|
||||||
|
</dependency>
|
||||||
|
|
||||||
<dependency>
|
<dependency>
|
||||||
<groupId>org.springframework</groupId>
|
<groupId>org.springframework</groupId>
|
||||||
<artifactId>spring-mock</artifactId>
|
<artifactId>spring-mock</artifactId>
|
||||||
@@ -258,12 +263,46 @@
|
|||||||
<artifactId>jackson-datatype-jsr310</artifactId>
|
<artifactId>jackson-datatype-jsr310</artifactId>
|
||||||
</dependency>
|
</dependency>
|
||||||
|
|
||||||
|
<dependency>
|
||||||
|
<groupId>com.fasterxml.jackson.dataformat</groupId>
|
||||||
|
<artifactId>jackson-dataformat-yaml</artifactId>
|
||||||
|
</dependency>
|
||||||
|
|
||||||
<dependency>
|
<dependency>
|
||||||
<groupId>net.1024lab</groupId>
|
<groupId>net.1024lab</groupId>
|
||||||
<artifactId>smartdb</artifactId>
|
<artifactId>smartdb</artifactId>
|
||||||
<version>${smartdb.version}</version>
|
<version>${smartdb.version}</version>
|
||||||
</dependency>
|
</dependency>
|
||||||
|
|
||||||
|
<dependency>
|
||||||
|
<groupId>org.redisson</groupId>
|
||||||
|
<artifactId>redisson-spring-boot-starter</artifactId>
|
||||||
|
</dependency>
|
||||||
|
<dependency>
|
||||||
|
<groupId>org.redisson</groupId>
|
||||||
|
<artifactId>redisson-spring-data-27</artifactId>
|
||||||
|
</dependency>
|
||||||
|
|
||||||
|
<dependency>
|
||||||
|
<groupId>org.yaml</groupId>
|
||||||
|
<artifactId>snakeyaml</artifactId>
|
||||||
|
</dependency>
|
||||||
|
|
||||||
|
<dependency>
|
||||||
|
<groupId>org.springframework.boot</groupId>
|
||||||
|
<artifactId>spring-boot-starter-mail</artifactId>
|
||||||
|
</dependency>
|
||||||
|
|
||||||
|
<dependency>
|
||||||
|
<groupId>org.jsoup</groupId>
|
||||||
|
<artifactId>jsoup</artifactId>
|
||||||
|
</dependency>
|
||||||
|
|
||||||
|
<dependency>
|
||||||
|
<groupId>org.freemarker</groupId>
|
||||||
|
<artifactId>freemarker</artifactId>
|
||||||
|
</dependency>
|
||||||
|
|
||||||
|
|
||||||
</dependencies>
|
</dependencies>
|
||||||
|
|
||||||
|
|||||||
@@ -28,19 +28,19 @@ public class DictValueVoDeserializer extends JsonDeserializer<String> {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public String deserialize(JsonParser jsonParser, DeserializationContext deserializationContext) throws IOException, JsonProcessingException {
|
public String deserialize(JsonParser jsonParser, DeserializationContext deserializationContext) throws IOException, JsonProcessingException {
|
||||||
List<DictValueVO> list = new ArrayList<>();
|
List<String> list = new ArrayList<>();
|
||||||
ObjectCodec objectCodec = jsonParser.getCodec();
|
ObjectCodec objectCodec = jsonParser.getCodec();
|
||||||
JsonNode listOrObjectNode = objectCodec.readTree(jsonParser);
|
JsonNode listOrObjectNode = objectCodec.readTree(jsonParser);
|
||||||
String deserialize = "";
|
String deserialize = "";
|
||||||
try {
|
try {
|
||||||
if (listOrObjectNode.isArray()) {
|
if (listOrObjectNode.isArray()) {
|
||||||
for (JsonNode node : listOrObjectNode) {
|
for (JsonNode node : listOrObjectNode) {
|
||||||
list.add(objectCodec.treeToValue(node, DictValueVO.class));
|
list.add(node.asText());
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
list.add(objectCodec.treeToValue(listOrObjectNode, DictValueVO.class));
|
list.add(listOrObjectNode.asText());
|
||||||
}
|
}
|
||||||
deserialize = list.stream().map(DictValueVO::getValueCode).collect(Collectors.joining(","));
|
deserialize = String.join(",", list);
|
||||||
} catch (Exception e) {
|
} catch (Exception e) {
|
||||||
log.error(e.getMessage(), e);
|
log.error(e.getMessage(), e);
|
||||||
deserialize = listOrObjectNode.asText();
|
deserialize = listOrObjectNode.asText();
|
||||||
|
|||||||
@@ -0,0 +1,59 @@
|
|||||||
|
package net.lab1024.sa.base.common.json.serializer;
|
||||||
|
|
||||||
|
import com.fasterxml.jackson.core.JsonGenerator;
|
||||||
|
import com.fasterxml.jackson.databind.BeanProperty;
|
||||||
|
import com.fasterxml.jackson.databind.JsonMappingException;
|
||||||
|
import com.fasterxml.jackson.databind.JsonSerializer;
|
||||||
|
import com.fasterxml.jackson.databind.SerializerProvider;
|
||||||
|
import com.fasterxml.jackson.databind.ser.ContextualSerializer;
|
||||||
|
import net.lab1024.sa.base.module.support.datamasking.DataMasking;
|
||||||
|
import net.lab1024.sa.base.module.support.datamasking.DataMaskingTypeEnum;
|
||||||
|
import net.lab1024.sa.base.module.support.datamasking.SmartDataMaskingUtil;
|
||||||
|
import org.apache.commons.lang3.ObjectUtils;
|
||||||
|
|
||||||
|
import java.io.IOException;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 脱敏序列化
|
||||||
|
*
|
||||||
|
* @author 罗伊
|
||||||
|
* @description:
|
||||||
|
* @date 2024/7/21 4:39 下午
|
||||||
|
*/
|
||||||
|
public class DataMaskingSerializer extends JsonSerializer<Object> implements ContextualSerializer {
|
||||||
|
|
||||||
|
private DataMaskingTypeEnum typeEnum;
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void serialize(Object value, JsonGenerator jsonGenerator, SerializerProvider serializers) throws IOException {
|
||||||
|
|
||||||
|
if (ObjectUtils.isEmpty(value)) {
|
||||||
|
jsonGenerator.writeObject(value);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (typeEnum == null) {
|
||||||
|
jsonGenerator.writeObject(SmartDataMaskingUtil.dataMasking(String.valueOf(value)));
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
jsonGenerator.writeObject(SmartDataMaskingUtil.dataMasking(value, typeEnum));
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public JsonSerializer<?> createContextual(SerializerProvider prov, BeanProperty property) throws JsonMappingException {
|
||||||
|
// 判断beanProperty是不是空
|
||||||
|
if (null == property) {
|
||||||
|
return prov.findNullValueSerializer(property);
|
||||||
|
}
|
||||||
|
|
||||||
|
DataMasking annotation = property.getAnnotation(DataMasking.class);
|
||||||
|
if (null == annotation) {
|
||||||
|
return prov.findValueSerializer(property.getType(), property);
|
||||||
|
}
|
||||||
|
|
||||||
|
typeEnum = annotation.value();
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
@@ -40,7 +40,7 @@ public class DictValueVoSerializer extends JsonSerializer<String> {
|
|||||||
List<DictValueVO> dictValueVOList = Lists.newArrayList();
|
List<DictValueVO> dictValueVOList = Lists.newArrayList();
|
||||||
valueCodeList.forEach(e->{
|
valueCodeList.forEach(e->{
|
||||||
if(StringUtils.isNotBlank(e)){
|
if(StringUtils.isNotBlank(e)){
|
||||||
DictValueVO dictValueVO = dictCacheService.selectValueByValueCode(value);
|
DictValueVO dictValueVO = dictCacheService.selectValueByValueCode(e);
|
||||||
if(dictValueVO != null){
|
if(dictValueVO != null){
|
||||||
dictValueVOList.add(dictValueVO);
|
dictValueVOList.add(dictValueVO);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -0,0 +1,25 @@
|
|||||||
|
package net.lab1024.sa.base.common.json.serializer.enumeration;
|
||||||
|
|
||||||
|
import com.fasterxml.jackson.annotation.JacksonAnnotationsInside;
|
||||||
|
import com.fasterxml.jackson.databind.annotation.JsonSerialize;
|
||||||
|
import net.lab1024.sa.base.common.enumeration.BaseEnum;
|
||||||
|
|
||||||
|
import java.lang.annotation.ElementType;
|
||||||
|
import java.lang.annotation.Retention;
|
||||||
|
import java.lang.annotation.RetentionPolicy;
|
||||||
|
import java.lang.annotation.Target;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 枚举类 序列化 注解
|
||||||
|
*
|
||||||
|
* @author huke
|
||||||
|
* @date 2024年6月29日
|
||||||
|
*/
|
||||||
|
@Target(ElementType.FIELD)
|
||||||
|
@Retention(RetentionPolicy.RUNTIME)
|
||||||
|
@JacksonAnnotationsInside
|
||||||
|
@JsonSerialize(using = EnumSerializer.class, nullsUsing = EnumSerializer.class)
|
||||||
|
public @interface EnumSerialize {
|
||||||
|
|
||||||
|
Class<? extends BaseEnum> value();
|
||||||
|
}
|
||||||
@@ -0,0 +1,53 @@
|
|||||||
|
package net.lab1024.sa.base.common.json.serializer.enumeration;
|
||||||
|
|
||||||
|
import com.fasterxml.jackson.core.JsonGenerator;
|
||||||
|
import com.fasterxml.jackson.databind.BeanProperty;
|
||||||
|
import com.fasterxml.jackson.databind.JsonMappingException;
|
||||||
|
import com.fasterxml.jackson.databind.JsonSerializer;
|
||||||
|
import com.fasterxml.jackson.databind.SerializerProvider;
|
||||||
|
import com.fasterxml.jackson.databind.ser.ContextualSerializer;
|
||||||
|
import net.lab1024.sa.base.common.constant.StringConst;
|
||||||
|
import net.lab1024.sa.base.common.enumeration.BaseEnum;
|
||||||
|
import net.lab1024.sa.base.common.util.SmartEnumUtil;
|
||||||
|
import net.lab1024.sa.base.common.util.SmartStringUtil;
|
||||||
|
|
||||||
|
import java.io.IOException;
|
||||||
|
import java.util.stream.Collectors;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 枚举 序列化
|
||||||
|
*
|
||||||
|
* @author huke
|
||||||
|
* @date 2024年6月29日
|
||||||
|
*/
|
||||||
|
public class EnumSerializer extends JsonSerializer<Object> implements ContextualSerializer {
|
||||||
|
|
||||||
|
private Class<? extends BaseEnum> enumClazz;
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void serialize(Object value, JsonGenerator gen, SerializerProvider serializers) throws IOException {
|
||||||
|
gen.writeObject(value);
|
||||||
|
String fieldName = gen.getOutputContext().getCurrentName() + "Desc";
|
||||||
|
Object desc;
|
||||||
|
// 多个枚举类 逗号分割
|
||||||
|
if (value instanceof String && String.valueOf(value).contains(StringConst.SEPARATOR)) {
|
||||||
|
desc = SmartStringUtil.splitConvertToIntList(String.valueOf(value), StringConst.SEPARATOR)
|
||||||
|
.stream().map(e -> SmartEnumUtil.getEnumDescByValue(e, enumClazz)).collect(Collectors.toList());
|
||||||
|
|
||||||
|
} else {
|
||||||
|
BaseEnum anEnum = SmartEnumUtil.getEnumByValue(value, enumClazz);
|
||||||
|
desc = null != anEnum ? anEnum.getDesc() : null;
|
||||||
|
}
|
||||||
|
gen.writeObjectField(fieldName, desc);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public JsonSerializer<?> createContextual(SerializerProvider prov, BeanProperty property) throws JsonMappingException {
|
||||||
|
EnumSerialize annotation = property.getAnnotation(EnumSerialize.class);
|
||||||
|
if (null == annotation) {
|
||||||
|
return prov.findValueSerializer(property.getType(), property);
|
||||||
|
}
|
||||||
|
enumClazz = annotation.value();
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -4,8 +4,12 @@ import lombok.extern.slf4j.Slf4j;
|
|||||||
import net.lab1024.sa.base.common.constant.StringConst;
|
import net.lab1024.sa.base.common.constant.StringConst;
|
||||||
import org.lionsoul.ip2region.xdb.Searcher;
|
import org.lionsoul.ip2region.xdb.Searcher;
|
||||||
|
|
||||||
|
import java.net.InetAddress;
|
||||||
|
import java.net.NetworkInterface;
|
||||||
|
import java.net.SocketException;
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.Arrays;
|
import java.util.Arrays;
|
||||||
|
import java.util.Enumeration;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -81,4 +85,39 @@ public class SmartIpUtil {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 获取本机第一个ip
|
||||||
|
*
|
||||||
|
* @return
|
||||||
|
*/
|
||||||
|
public static String getLocalFirstIp() {
|
||||||
|
List<String> list = getLocalIp();
|
||||||
|
return list.size() > 0 ? list.get(0) : null;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 获取本机ip
|
||||||
|
*
|
||||||
|
* @return
|
||||||
|
*/
|
||||||
|
public static List<String> getLocalIp() {
|
||||||
|
List<String> ipList = new ArrayList<>();
|
||||||
|
try {
|
||||||
|
Enumeration<NetworkInterface> networkInterfaces = NetworkInterface.getNetworkInterfaces();
|
||||||
|
while (networkInterfaces.hasMoreElements()) {
|
||||||
|
NetworkInterface networkInterface = networkInterfaces.nextElement();
|
||||||
|
Enumeration<InetAddress> inetAddresses = networkInterface.getInetAddresses();
|
||||||
|
while (inetAddresses.hasMoreElements()) {
|
||||||
|
InetAddress inetAddress = inetAddresses.nextElement();
|
||||||
|
// 排除回环地址和IPv6地址
|
||||||
|
if (!inetAddress.isLoopbackAddress() && !inetAddress.getHostAddress().contains(StringConst.COLON)) {
|
||||||
|
ipList.add(inetAddress.getHostAddress());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
} catch (SocketException e) {
|
||||||
|
e.printStackTrace();
|
||||||
|
}
|
||||||
|
return ipList;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -12,7 +12,6 @@ import org.apache.commons.collections4.CollectionUtils;
|
|||||||
|
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
import java.util.stream.Collectors;
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 分页工具类
|
* 分页工具类
|
||||||
@@ -32,6 +31,10 @@ public class SmartPageUtil {
|
|||||||
public static Page<?> convert2PageQuery(PageParam pageParam) {
|
public static Page<?> convert2PageQuery(PageParam pageParam) {
|
||||||
Page<?> page = new Page<>(pageParam.getPageNum(), pageParam.getPageSize());
|
Page<?> page = new Page<>(pageParam.getPageNum(), pageParam.getPageSize());
|
||||||
|
|
||||||
|
if (pageParam.getSearchCount() != null) {
|
||||||
|
page.setSearchCount(pageParam.getSearchCount());
|
||||||
|
}
|
||||||
|
|
||||||
List<PageParam.SortItem> sortItemList = pageParam.getSortItemList();
|
List<PageParam.SortItem> sortItemList = pageParam.getSortItemList();
|
||||||
if (CollectionUtils.isEmpty(sortItemList)) {
|
if (CollectionUtils.isEmpty(sortItemList)) {
|
||||||
return page;
|
return page;
|
||||||
|
|||||||
@@ -7,10 +7,12 @@ import com.alibaba.druid.support.http.StatViewServlet;
|
|||||||
import com.alibaba.druid.support.http.WebStatFilter;
|
import com.alibaba.druid.support.http.WebStatFilter;
|
||||||
import com.alibaba.druid.support.spring.stat.DruidStatInterceptor;
|
import com.alibaba.druid.support.spring.stat.DruidStatInterceptor;
|
||||||
import com.baomidou.mybatisplus.annotation.DbType;
|
import com.baomidou.mybatisplus.annotation.DbType;
|
||||||
|
import com.baomidou.mybatisplus.core.config.GlobalConfig;
|
||||||
import com.baomidou.mybatisplus.extension.plugins.MybatisPlusInterceptor;
|
import com.baomidou.mybatisplus.extension.plugins.MybatisPlusInterceptor;
|
||||||
import com.baomidou.mybatisplus.extension.spring.MybatisSqlSessionFactoryBean;
|
import com.baomidou.mybatisplus.extension.spring.MybatisSqlSessionFactoryBean;
|
||||||
import lombok.extern.slf4j.Slf4j;
|
import lombok.extern.slf4j.Slf4j;
|
||||||
import net.lab1024.sa.base.common.domain.DataScopePlugin;
|
import net.lab1024.sa.base.common.domain.DataScopePlugin;
|
||||||
|
import net.lab1024.sa.base.handler.MybatisPlusFillHandler;
|
||||||
import org.apache.ibatis.plugin.Interceptor;
|
import org.apache.ibatis.plugin.Interceptor;
|
||||||
import org.apache.ibatis.session.SqlSessionFactory;
|
import org.apache.ibatis.session.SqlSessionFactory;
|
||||||
import org.springframework.aop.support.DefaultPointcutAdvisor;
|
import org.springframework.aop.support.DefaultPointcutAdvisor;
|
||||||
@@ -144,6 +146,8 @@ public class DataSourceConfig {
|
|||||||
pluginsList.add(dataScopePlugin);
|
pluginsList.add(dataScopePlugin);
|
||||||
}
|
}
|
||||||
factoryBean.setPlugins(pluginsList.toArray(new Interceptor[pluginsList.size()]));
|
factoryBean.setPlugins(pluginsList.toArray(new Interceptor[pluginsList.size()]));
|
||||||
|
// 添加字段自动填充处理
|
||||||
|
factoryBean.setGlobalConfig(new GlobalConfig().setBanner(false).setMetaObjectHandler(new MybatisPlusFillHandler()));
|
||||||
|
|
||||||
return factoryBean.getObject();
|
return factoryBean.getObject();
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -6,6 +6,7 @@ import com.fasterxml.jackson.annotation.PropertyAccessor;
|
|||||||
import com.fasterxml.jackson.databind.DeserializationFeature;
|
import com.fasterxml.jackson.databind.DeserializationFeature;
|
||||||
import com.fasterxml.jackson.databind.ObjectMapper;
|
import com.fasterxml.jackson.databind.ObjectMapper;
|
||||||
import com.fasterxml.jackson.databind.SerializationFeature;
|
import com.fasterxml.jackson.databind.SerializationFeature;
|
||||||
|
import com.fasterxml.jackson.databind.jsontype.impl.LaissezFaireSubTypeValidator;
|
||||||
import com.fasterxml.jackson.datatype.jsr310.JavaTimeModule;
|
import com.fasterxml.jackson.datatype.jsr310.JavaTimeModule;
|
||||||
import org.springframework.context.annotation.Bean;
|
import org.springframework.context.annotation.Bean;
|
||||||
import org.springframework.context.annotation.Configuration;
|
import org.springframework.context.annotation.Configuration;
|
||||||
@@ -43,7 +44,8 @@ public class RedisConfig {
|
|||||||
.setSerializationInclusion(JsonInclude.Include.NON_NULL);
|
.setSerializationInclusion(JsonInclude.Include.NON_NULL);
|
||||||
|
|
||||||
om.setVisibility(PropertyAccessor.ALL, JsonAutoDetect.Visibility.ANY);
|
om.setVisibility(PropertyAccessor.ALL, JsonAutoDetect.Visibility.ANY);
|
||||||
om.enableDefaultTyping(ObjectMapper.DefaultTyping.NON_FINAL);
|
// enableDefaultTyping 官方已弃用 所以改为 activateDefaultTyping
|
||||||
|
om.activateDefaultTyping(LaissezFaireSubTypeValidator.instance, ObjectMapper.DefaultTyping.NON_FINAL);
|
||||||
jackson2JsonRedisSerializer.setObjectMapper(om);
|
jackson2JsonRedisSerializer.setObjectMapper(om);
|
||||||
RedisTemplate<String, Object> template = new RedisTemplate<>();
|
RedisTemplate<String, Object> template = new RedisTemplate<>();
|
||||||
template.setConnectionFactory(factory);
|
template.setConnectionFactory(factory);
|
||||||
|
|||||||
@@ -1,5 +1,6 @@
|
|||||||
package net.lab1024.sa.base.config;
|
package net.lab1024.sa.base.config;
|
||||||
|
|
||||||
|
import com.google.common.collect.Lists;
|
||||||
import io.swagger.v3.oas.models.Components;
|
import io.swagger.v3.oas.models.Components;
|
||||||
import io.swagger.v3.oas.models.OpenAPI;
|
import io.swagger.v3.oas.models.OpenAPI;
|
||||||
import io.swagger.v3.oas.models.info.Contact;
|
import io.swagger.v3.oas.models.info.Contact;
|
||||||
@@ -10,14 +11,25 @@ import lombok.extern.slf4j.Slf4j;
|
|||||||
import net.lab1024.sa.base.common.constant.RequestHeaderConst;
|
import net.lab1024.sa.base.common.constant.RequestHeaderConst;
|
||||||
import net.lab1024.sa.base.common.swagger.SmartOperationCustomizer;
|
import net.lab1024.sa.base.common.swagger.SmartOperationCustomizer;
|
||||||
import net.lab1024.sa.base.constant.SwaggerTagConst;
|
import net.lab1024.sa.base.constant.SwaggerTagConst;
|
||||||
import org.springdoc.core.GroupedOpenApi;
|
import org.apache.commons.lang3.StringUtils;
|
||||||
|
import org.springdoc.core.*;
|
||||||
|
import org.springdoc.core.customizers.OpenApiBuilderCustomizer;
|
||||||
|
import org.springdoc.core.customizers.ServerBaseUrlCustomizer;
|
||||||
|
import org.springdoc.core.providers.JavadocProvider;
|
||||||
|
import org.springframework.beans.factory.annotation.Value;
|
||||||
import org.springframework.context.annotation.Bean;
|
import org.springframework.context.annotation.Bean;
|
||||||
import org.springframework.context.annotation.Conditional;
|
import org.springframework.context.annotation.Conditional;
|
||||||
import org.springframework.context.annotation.Configuration;
|
import org.springframework.context.annotation.Configuration;
|
||||||
|
|
||||||
|
import java.util.List;
|
||||||
|
import java.util.Optional;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* springdoc-openapi 配置
|
* springdoc-openapi 配置
|
||||||
*
|
* nginx配置前缀时如果需要访问【/swagger-ui/index.html】需添加额外nginx配置
|
||||||
|
* location /v3/api-docs/ {
|
||||||
|
* proxy_pass http://127.0.0.1:1024/v3/api-docs/;
|
||||||
|
* }
|
||||||
* @Author 1024创新实验室-主任: 卓大
|
* @Author 1024创新实验室-主任: 卓大
|
||||||
* @Date 2020-03-25 22:54:46
|
* @Date 2020-03-25 22:54:46
|
||||||
* @Wechat zhuoda1024
|
* @Wechat zhuoda1024
|
||||||
@@ -28,6 +40,11 @@ import org.springframework.context.annotation.Configuration;
|
|||||||
@Configuration
|
@Configuration
|
||||||
@Conditional(SystemEnvironmentConfig.class)
|
@Conditional(SystemEnvironmentConfig.class)
|
||||||
public class SwaggerConfig {
|
public class SwaggerConfig {
|
||||||
|
/**
|
||||||
|
* 用于解决/swagger-ui/index.html页面ServersUrl 测试环境部署错误问题
|
||||||
|
*/
|
||||||
|
@Value("${springdoc.swagger-ui.server-base-url}")
|
||||||
|
private String serverBaseUrl;
|
||||||
|
|
||||||
public static final String[] SWAGGER_WHITELIST = {
|
public static final String[] SWAGGER_WHITELIST = {
|
||||||
"/swagger-ui/**",
|
"/swagger-ui/**",
|
||||||
@@ -78,4 +95,37 @@ public class SwaggerConfig {
|
|||||||
.addOperationCustomizer(new SmartOperationCustomizer())
|
.addOperationCustomizer(new SmartOperationCustomizer())
|
||||||
.build();
|
.build();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 以下代码可以用于设置 /swagger-ui/index.html 的serverBaseUrl
|
||||||
|
* 如果使用knife4j则不需要
|
||||||
|
* @param openAPI
|
||||||
|
* @param securityParser
|
||||||
|
* @param springDocConfigProperties
|
||||||
|
* @param propertyResolverUtils
|
||||||
|
* @param openApiBuilderCustomizers
|
||||||
|
* @param serverBaseUrlCustomizers
|
||||||
|
* @param javadocProvider
|
||||||
|
* @return
|
||||||
|
*/
|
||||||
|
@Bean
|
||||||
|
public OpenAPIService openApiBuilder(Optional<OpenAPI> openAPI,
|
||||||
|
SecurityService securityParser,
|
||||||
|
SpringDocConfigProperties springDocConfigProperties,
|
||||||
|
PropertyResolverUtils propertyResolverUtils,
|
||||||
|
Optional<List<OpenApiBuilderCustomizer>> openApiBuilderCustomizers,
|
||||||
|
Optional<List<ServerBaseUrlCustomizer>> serverBaseUrlCustomizers,
|
||||||
|
Optional<JavadocProvider> javadocProvider) {
|
||||||
|
List<ServerBaseUrlCustomizer> list = Lists.newArrayList(new ServerBaseUrlCustomizer() {
|
||||||
|
@Override
|
||||||
|
public String customize(String baseUrl) {
|
||||||
|
if (StringUtils.isNotBlank(serverBaseUrl)) {
|
||||||
|
return serverBaseUrl;
|
||||||
|
}
|
||||||
|
return baseUrl;
|
||||||
|
}
|
||||||
|
});
|
||||||
|
return new OpenAPIService(openAPI, securityParser, springDocConfigProperties,
|
||||||
|
propertyResolverUtils, openApiBuilderCustomizers, Optional.of(list), javadocProvider);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -23,5 +23,7 @@ public class RedisKeyConst {
|
|||||||
|
|
||||||
public static final String CAPTCHA = "captcha:";
|
public static final String CAPTCHA = "captcha:";
|
||||||
|
|
||||||
|
public static final String LOGIN_VERIFICATION_CODE = "login:verification-code:";
|
||||||
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -48,6 +48,12 @@ public class SwaggerTagConst {
|
|||||||
public static final String TABLE_COLUMN = "业务支撑-列自定义";
|
public static final String TABLE_COLUMN = "业务支撑-列自定义";
|
||||||
|
|
||||||
public static final String PROTECT = "业务支撑-网络安全";
|
public static final String PROTECT = "业务支撑-网络安全";
|
||||||
|
|
||||||
|
public static final String DATA_MASKING = "业务支撑-数据脱敏";
|
||||||
|
|
||||||
|
public static final String JOB = "业务支撑-定时任务";
|
||||||
|
|
||||||
|
public static final String MESSAGE = "业务支撑-消息";
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -9,7 +9,6 @@ import net.lab1024.sa.base.common.domain.SystemEnvironment;
|
|||||||
import net.lab1024.sa.base.common.enumeration.SystemEnvironmentEnum;
|
import net.lab1024.sa.base.common.enumeration.SystemEnvironmentEnum;
|
||||||
import net.lab1024.sa.base.common.exception.BusinessException;
|
import net.lab1024.sa.base.common.exception.BusinessException;
|
||||||
import org.springframework.beans.TypeMismatchException;
|
import org.springframework.beans.TypeMismatchException;
|
||||||
import org.springframework.beans.factory.annotation.Autowired;
|
|
||||||
import org.springframework.http.converter.HttpMessageNotReadableException;
|
import org.springframework.http.converter.HttpMessageNotReadableException;
|
||||||
import org.springframework.validation.BindException;
|
import org.springframework.validation.BindException;
|
||||||
import org.springframework.validation.FieldError;
|
import org.springframework.validation.FieldError;
|
||||||
@@ -59,10 +58,6 @@ public class GlobalExceptionHandler {
|
|||||||
@ResponseBody
|
@ResponseBody
|
||||||
@ExceptionHandler({TypeMismatchException.class, BindException.class})
|
@ExceptionHandler({TypeMismatchException.class, BindException.class})
|
||||||
public ResponseDTO<?> paramExceptionHandler(Exception e) {
|
public ResponseDTO<?> paramExceptionHandler(Exception e) {
|
||||||
if (!systemEnvironment.isProd()) {
|
|
||||||
log.error("全局参数异常,URL:{}", getCurrentRequestUrl(), e);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (e instanceof BindException) {
|
if (e instanceof BindException) {
|
||||||
if (e instanceof MethodArgumentNotValidException) {
|
if (e instanceof MethodArgumentNotValidException) {
|
||||||
List<FieldError> fieldErrors = ((MethodArgumentNotValidException) e).getBindingResult().getFieldErrors();
|
List<FieldError> fieldErrors = ((MethodArgumentNotValidException) e).getBindingResult().getFieldErrors();
|
||||||
@@ -75,7 +70,6 @@ public class GlobalExceptionHandler {
|
|||||||
String errorMsg = UserErrorCode.PARAM_ERROR.getMsg() + ":" + error;
|
String errorMsg = UserErrorCode.PARAM_ERROR.getMsg() + ":" + error;
|
||||||
return ResponseDTO.error(UserErrorCode.PARAM_ERROR, errorMsg);
|
return ResponseDTO.error(UserErrorCode.PARAM_ERROR, errorMsg);
|
||||||
}
|
}
|
||||||
|
|
||||||
return ResponseDTO.error(UserErrorCode.PARAM_ERROR);
|
return ResponseDTO.error(UserErrorCode.PARAM_ERROR);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -0,0 +1,40 @@
|
|||||||
|
package net.lab1024.sa.base.handler;
|
||||||
|
|
||||||
|
import com.baomidou.mybatisplus.core.handlers.MetaObjectHandler;
|
||||||
|
import lombok.extern.slf4j.Slf4j;
|
||||||
|
import org.apache.ibatis.reflection.MetaObject;
|
||||||
|
import org.springframework.stereotype.Component;
|
||||||
|
|
||||||
|
import java.time.LocalDateTime;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Mybatis Plus 插入或者更新时指定字段设置值
|
||||||
|
*
|
||||||
|
* @author zhoumingfa
|
||||||
|
*/
|
||||||
|
@Component
|
||||||
|
@Slf4j
|
||||||
|
public class MybatisPlusFillHandler implements MetaObjectHandler {
|
||||||
|
|
||||||
|
public static final String CREATE_TIME = "createTime";
|
||||||
|
|
||||||
|
public static final String UPDATE_TIME = "updateTime";
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void insertFill(MetaObject metaObject) {
|
||||||
|
if (metaObject.hasSetter(CREATE_TIME)) {
|
||||||
|
this.fillStrategy(metaObject, CREATE_TIME, LocalDateTime.now());
|
||||||
|
}
|
||||||
|
if (metaObject.hasSetter(UPDATE_TIME)) {
|
||||||
|
this.fillStrategy(metaObject, UPDATE_TIME, LocalDateTime.now());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void updateFill(MetaObject metaObject) {
|
||||||
|
if (metaObject.hasSetter(UPDATE_TIME)) {
|
||||||
|
this.fillStrategy(metaObject, UPDATE_TIME, LocalDateTime.now());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
@@ -87,13 +87,14 @@ public class WebServerListener implements ApplicationListener<WebServerInitializ
|
|||||||
*/
|
*/
|
||||||
private void initReload(WebServerApplicationContext applicationContext) {
|
private void initReload(WebServerApplicationContext applicationContext) {
|
||||||
// 将applicationContext转换为ConfigurableApplicationContext
|
// 将applicationContext转换为ConfigurableApplicationContext
|
||||||
ConfigurableApplicationContext configurableApplicationContext = (ConfigurableApplicationContext) applicationContext;
|
// ConfigurableApplicationContext configurableApplicationContext = (ConfigurableApplicationContext) applicationContext;
|
||||||
|
//
|
||||||
//获取BeanFactory
|
//
|
||||||
DefaultListableBeanFactory defaultListableBeanFactory = (DefaultListableBeanFactory) configurableApplicationContext.getAutowireCapableBeanFactory();
|
// //获取BeanFactory
|
||||||
|
// DefaultListableBeanFactory defaultListableBeanFactory = (DefaultListableBeanFactory) configurableApplicationContext.getAutowireCapableBeanFactory();
|
||||||
//动态注册bean
|
//
|
||||||
SmartReloadManager reloadManager = new SmartReloadManager(applicationContext.getBean(ReloadCommand.class), intervalSeconds);
|
// //动态注册bean
|
||||||
defaultListableBeanFactory.registerSingleton("smartReloadManager", reloadManager);
|
// SmartReloadManager reloadManager = new SmartReloadManager(applicationContext.getBean(ReloadCommand.class), intervalSeconds);
|
||||||
|
// defaultListableBeanFactory.registerSingleton("smartReloadManager", reloadManager);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -42,8 +42,10 @@ public class CaptchaService {
|
|||||||
|
|
||||||
@Resource
|
@Resource
|
||||||
private DefaultKaptcha defaultKaptcha;
|
private DefaultKaptcha defaultKaptcha;
|
||||||
@Autowired
|
|
||||||
|
@Resource
|
||||||
private SystemEnvironment systemEnvironment;
|
private SystemEnvironment systemEnvironment;
|
||||||
|
|
||||||
@Resource
|
@Resource
|
||||||
private RedisService redisService;
|
private RedisService redisService;
|
||||||
|
|
||||||
|
|||||||
@@ -41,7 +41,7 @@ public enum CodeFrontComponentEnum implements BaseEnum {
|
|||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public Object getValue() {
|
public String getValue() {
|
||||||
return value;
|
return value;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -32,7 +32,6 @@ public class CodeGeneratorConfigForm {
|
|||||||
@Schema(description = "表名")
|
@Schema(description = "表名")
|
||||||
private String tableName;
|
private String tableName;
|
||||||
|
|
||||||
|
|
||||||
@Valid
|
@Valid
|
||||||
@NotNull(message = "基础信息不能为空")
|
@NotNull(message = "基础信息不能为空")
|
||||||
@Schema(description = "基础信息")
|
@Schema(description = "基础信息")
|
||||||
|
|||||||
@@ -39,8 +39,8 @@ public class CodeInsertAndUpdateField {
|
|||||||
@Schema(description = "更新标识")
|
@Schema(description = "更新标识")
|
||||||
private Boolean updateFlag;
|
private Boolean updateFlag;
|
||||||
|
|
||||||
@SchemaEnum(value = CodeGeneratorPageTypeEnum.class)
|
@SchemaEnum(value = CodeFrontComponentEnum.class)
|
||||||
@CheckEnum(value = CodeFrontComponentEnum.class, message = "3.增加、修改 增加、修改 组件类型 枚举值错误", required = true)
|
@CheckEnum(value = CodeFrontComponentEnum.class, message = "3.增加、修改 组件类型 枚举值错误", required = true)
|
||||||
private String frontComponent;
|
private String frontComponent;
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -13,16 +13,13 @@ import net.lab1024.sa.base.common.util.SmartStringUtil;
|
|||||||
import net.lab1024.sa.base.module.support.codegenerator.domain.entity.CodeGeneratorConfigEntity;
|
import net.lab1024.sa.base.module.support.codegenerator.domain.entity.CodeGeneratorConfigEntity;
|
||||||
import net.lab1024.sa.base.module.support.codegenerator.domain.form.CodeGeneratorConfigForm;
|
import net.lab1024.sa.base.module.support.codegenerator.domain.form.CodeGeneratorConfigForm;
|
||||||
import net.lab1024.sa.base.module.support.codegenerator.domain.model.*;
|
import net.lab1024.sa.base.module.support.codegenerator.domain.model.*;
|
||||||
import net.lab1024.sa.base.module.support.codegenerator.service.variable.backend.ControllerVariableService;
|
import net.lab1024.sa.base.module.support.codegenerator.service.variable.CodeGenerateBaseVariableService;
|
||||||
import net.lab1024.sa.base.module.support.codegenerator.service.variable.backend.DaoVariableService;
|
import net.lab1024.sa.base.module.support.codegenerator.service.variable.backend.*;
|
||||||
import net.lab1024.sa.base.module.support.codegenerator.service.variable.backend.ManagerVariableService;
|
|
||||||
import net.lab1024.sa.base.module.support.codegenerator.service.variable.backend.ServiceVariableService;
|
|
||||||
import net.lab1024.sa.base.module.support.codegenerator.service.variable.backend.domain.*;
|
import net.lab1024.sa.base.module.support.codegenerator.service.variable.backend.domain.*;
|
||||||
import net.lab1024.sa.base.module.support.codegenerator.service.variable.front.ApiVariableService;
|
import net.lab1024.sa.base.module.support.codegenerator.service.variable.front.ApiVariableService;
|
||||||
import net.lab1024.sa.base.module.support.codegenerator.service.variable.front.ConstVariableService;
|
import net.lab1024.sa.base.module.support.codegenerator.service.variable.front.ConstVariableService;
|
||||||
import net.lab1024.sa.base.module.support.codegenerator.service.variable.front.FormVariableService;
|
import net.lab1024.sa.base.module.support.codegenerator.service.variable.front.FormVariableService;
|
||||||
import net.lab1024.sa.base.module.support.codegenerator.service.variable.front.ListVariableService;
|
import net.lab1024.sa.base.module.support.codegenerator.service.variable.front.ListVariableService;
|
||||||
import net.lab1024.sa.base.module.support.codegenerator.service.variable.CodeGenerateBaseVariableService;
|
|
||||||
import net.lab1024.sa.base.module.support.codegenerator.util.CodeGeneratorTool;
|
import net.lab1024.sa.base.module.support.codegenerator.util.CodeGeneratorTool;
|
||||||
import org.apache.commons.collections4.CollectionUtils;
|
import org.apache.commons.collections4.CollectionUtils;
|
||||||
import org.apache.velocity.Template;
|
import org.apache.velocity.Template;
|
||||||
@@ -36,7 +33,7 @@ import javax.annotation.PostConstruct;
|
|||||||
import java.io.File;
|
import java.io.File;
|
||||||
import java.io.OutputStream;
|
import java.io.OutputStream;
|
||||||
import java.io.StringWriter;
|
import java.io.StringWriter;
|
||||||
import java.nio.charset.Charset;
|
import java.nio.charset.StandardCharsets;
|
||||||
import java.util.*;
|
import java.util.*;
|
||||||
import java.util.stream.Collectors;
|
import java.util.stream.Collectors;
|
||||||
|
|
||||||
@@ -70,6 +67,8 @@ public class CodeGeneratorTemplateService {
|
|||||||
map.put("java/manager/Manager.java", new ManagerVariableService());
|
map.put("java/manager/Manager.java", new ManagerVariableService());
|
||||||
map.put("java/dao/Dao.java", new DaoVariableService());
|
map.put("java/dao/Dao.java", new DaoVariableService());
|
||||||
map.put("java/mapper/Mapper.xml", new MapperVariableService());
|
map.put("java/mapper/Mapper.xml", new MapperVariableService());
|
||||||
|
// 菜单 SQL
|
||||||
|
map.put("java/sql/Menu.sql", new MenuVariableService());
|
||||||
// 前端
|
// 前端
|
||||||
map.put("js/api.js", new ApiVariableService());
|
map.put("js/api.js", new ApiVariableService());
|
||||||
map.put("js/const.js", new ConstVariableService());
|
map.put("js/const.js", new ConstVariableService());
|
||||||
@@ -94,6 +93,7 @@ public class CodeGeneratorTemplateService {
|
|||||||
String fileName = templateFile.startsWith("java") ? upperCamel + templateSplit[templateSplit.length - 1] : lowerHyphen + "-" + templateSplit[templateSplit.length - 1];
|
String fileName = templateFile.startsWith("java") ? upperCamel + templateSplit[templateSplit.length - 1] : lowerHyphen + "-" + templateSplit[templateSplit.length - 1];
|
||||||
String fullPathFileName = templateFile.replaceAll(templateSplit[templateSplit.length - 1], fileName);
|
String fullPathFileName = templateFile.replaceAll(templateSplit[templateSplit.length - 1], fileName);
|
||||||
fullPathFileName = fullPathFileName.replaceAll("java/", "java/" + basic.getModuleName().toLowerCase() + "/");
|
fullPathFileName = fullPathFileName.replaceAll("java/", "java/" + basic.getModuleName().toLowerCase() + "/");
|
||||||
|
fullPathFileName = fullPathFileName.replaceAll("js/", "js/" + lowerHyphen + "/");
|
||||||
|
|
||||||
String fileContent = generate(tableName, templateFile, codeGeneratorConfigEntity);
|
String fileContent = generate(tableName, templateFile, codeGeneratorConfigEntity);
|
||||||
File file = new File(uuid + "/" + fullPathFileName);
|
File file = new File(uuid + "/" + fullPathFileName);
|
||||||
@@ -129,7 +129,7 @@ public class CodeGeneratorTemplateService {
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
ZipUtil.zip(outputStream, Charset.forName("utf-8"), false, null, dir);
|
ZipUtil.zip(outputStream, StandardCharsets.UTF_8, false, null, dir);
|
||||||
|
|
||||||
FileUtil.del(dir);
|
FileUtil.del(dir);
|
||||||
|
|
||||||
|
|||||||
@@ -2,6 +2,7 @@ package net.lab1024.sa.base.module.support.codegenerator.service.variable;
|
|||||||
|
|
||||||
import com.google.common.base.CaseFormat;
|
import com.google.common.base.CaseFormat;
|
||||||
import net.lab1024.sa.base.common.util.SmartStringUtil;
|
import net.lab1024.sa.base.common.util.SmartStringUtil;
|
||||||
|
import net.lab1024.sa.base.module.support.codegenerator.constant.CodeFrontComponentEnum;
|
||||||
import net.lab1024.sa.base.module.support.codegenerator.domain.form.CodeGeneratorConfigForm;
|
import net.lab1024.sa.base.module.support.codegenerator.domain.form.CodeGeneratorConfigForm;
|
||||||
import net.lab1024.sa.base.module.support.codegenerator.domain.model.CodeField;
|
import net.lab1024.sa.base.module.support.codegenerator.domain.model.CodeField;
|
||||||
import net.lab1024.sa.base.module.support.codegenerator.domain.model.CodeInsertAndUpdate;
|
import net.lab1024.sa.base.module.support.codegenerator.domain.model.CodeInsertAndUpdate;
|
||||||
@@ -88,43 +89,33 @@ public abstract class CodeGenerateBaseVariableService {
|
|||||||
}
|
}
|
||||||
|
|
||||||
CodeInsertAndUpdateField field = first.get();
|
CodeInsertAndUpdateField field = first.get();
|
||||||
return SmartStringUtil.contains(field.getFrontComponent(), "Upload" );
|
return SmartStringUtil.equals(field.getFrontComponent(), CodeFrontComponentEnum.FILE_UPLOAD.getValue());
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 是否为 枚举
|
* 是否为 字典
|
||||||
*/
|
*/
|
||||||
protected boolean isDict(String columnName, CodeGeneratorConfigForm form) {
|
protected boolean isDict(String columnName, CodeGeneratorConfigForm form) {
|
||||||
List<CodeField> fields = form.getFields();
|
CodeField codeField = getCodeField(columnName, form);
|
||||||
if (CollectionUtils.isEmpty(fields)) {
|
return codeField != null && codeField.getDict() != null;
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
Optional<CodeField> first = fields.stream().filter(e -> columnName.equals(e.getColumnName())).findFirst();
|
|
||||||
if (first.isPresent()) {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
CodeField codeField = first.get();
|
|
||||||
return codeField.getDict() != null;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 是否为 枚举
|
* 是否为 枚举
|
||||||
*/
|
*/
|
||||||
protected boolean isEnum(String columnName, CodeGeneratorConfigForm form) {
|
protected boolean isEnum(String columnName, CodeGeneratorConfigForm form) {
|
||||||
|
CodeField codeField = getCodeField(columnName, form);
|
||||||
|
return codeField != null && codeField.getEnumName() != null;
|
||||||
|
}
|
||||||
|
|
||||||
|
private CodeField getCodeField(String columnName, CodeGeneratorConfigForm form) {
|
||||||
List<CodeField> fields = form.getFields();
|
List<CodeField> fields = form.getFields();
|
||||||
if (CollectionUtils.isEmpty(fields)) {
|
if (CollectionUtils.isEmpty(fields)) {
|
||||||
return false;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
Optional<CodeField> first = fields.stream().filter(e -> columnName.equals(e.getColumnName())).findFirst();
|
Optional<CodeField> first = fields.stream().filter(e -> columnName.equals(e.getColumnName())).findFirst();
|
||||||
if (first.isPresent()) {
|
return first.orElse(null);
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
CodeField codeField = first.get();
|
|
||||||
return codeField.getEnumName() != null;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|||||||
@@ -0,0 +1,27 @@
|
|||||||
|
package net.lab1024.sa.base.module.support.codegenerator.service.variable.backend;
|
||||||
|
|
||||||
|
import net.lab1024.sa.base.module.support.codegenerator.domain.form.CodeGeneratorConfigForm;
|
||||||
|
import net.lab1024.sa.base.module.support.codegenerator.service.variable.CodeGenerateBaseVariableService;
|
||||||
|
|
||||||
|
import java.util.HashMap;
|
||||||
|
import java.util.Map;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 目前暂时没用到 这是一个空实现
|
||||||
|
*
|
||||||
|
* @author zhoumingfa
|
||||||
|
* @date 2024/8/13
|
||||||
|
*/
|
||||||
|
public class MenuVariableService extends CodeGenerateBaseVariableService {
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean isSupport(CodeGeneratorConfigForm form) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public Map<String, Object> getInjectVariablesMap(CodeGeneratorConfigForm form) {
|
||||||
|
return new HashMap<>(2);
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
@@ -2,6 +2,7 @@ package net.lab1024.sa.base.module.support.codegenerator.service.variable.backen
|
|||||||
|
|
||||||
import cn.hutool.core.bean.BeanUtil;
|
import cn.hutool.core.bean.BeanUtil;
|
||||||
import net.lab1024.sa.base.common.util.SmartStringUtil;
|
import net.lab1024.sa.base.common.util.SmartStringUtil;
|
||||||
|
import net.lab1024.sa.base.module.support.codegenerator.constant.CodeFrontComponentEnum;
|
||||||
import net.lab1024.sa.base.module.support.codegenerator.domain.form.CodeGeneratorConfigForm;
|
import net.lab1024.sa.base.module.support.codegenerator.domain.form.CodeGeneratorConfigForm;
|
||||||
import net.lab1024.sa.base.module.support.codegenerator.domain.model.CodeField;
|
import net.lab1024.sa.base.module.support.codegenerator.domain.model.CodeField;
|
||||||
import net.lab1024.sa.base.module.support.codegenerator.domain.model.CodeInsertAndUpdate;
|
import net.lab1024.sa.base.module.support.codegenerator.domain.model.CodeInsertAndUpdate;
|
||||||
@@ -100,7 +101,6 @@ public class AddFormVariableService extends CodeGenerateBaseVariableService {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
//字典
|
//字典
|
||||||
if (SmartStringUtil.isNotEmpty(codeField.getDict())) {
|
if (SmartStringUtil.isNotEmpty(codeField.getDict())) {
|
||||||
finalFieldMap.put("dict", "\n @JsonDeserialize(using = DictValueVoDeserializer.class)");
|
finalFieldMap.put("dict", "\n @JsonDeserialize(using = DictValueVoDeserializer.class)");
|
||||||
@@ -109,7 +109,7 @@ public class AddFormVariableService extends CodeGenerateBaseVariableService {
|
|||||||
}
|
}
|
||||||
|
|
||||||
//文件上传
|
//文件上传
|
||||||
if (SmartStringUtil.contains(field.getFrontComponent(), "Upload")) {
|
if (CodeFrontComponentEnum.FILE_UPLOAD.equalsValue(field.getFrontComponent())) {
|
||||||
finalFieldMap.put("file", "\n @JsonDeserialize(using = FileKeyVoDeserializer.class)");
|
finalFieldMap.put("file", "\n @JsonDeserialize(using = FileKeyVoDeserializer.class)");
|
||||||
packageList.add("import com.fasterxml.jackson.databind.annotation.JsonDeserialize;");
|
packageList.add("import com.fasterxml.jackson.databind.annotation.JsonDeserialize;");
|
||||||
packageList.add("import net.lab1024.sa.base.common.json.deserializer.FileKeyVoDeserializer;");
|
packageList.add("import net.lab1024.sa.base.common.json.deserializer.FileKeyVoDeserializer;");
|
||||||
|
|||||||
@@ -54,14 +54,21 @@ public class EntityVariableService extends CodeGenerateBaseVariableService {
|
|||||||
// mybatis plus
|
// mybatis plus
|
||||||
result.add("import com.baomidou.mybatisplus.annotation.TableName;");
|
result.add("import com.baomidou.mybatisplus.annotation.TableName;");
|
||||||
|
|
||||||
|
// 自动填充注解
|
||||||
|
boolean existCreateAndUpdate = fields.stream().anyMatch(e -> "create_time".equals(e.getColumnName()) || "update_time".equals(e.getColumnName()));
|
||||||
|
if (existCreateAndUpdate) {
|
||||||
|
result.add("import com.baomidou.mybatisplus.annotation.FieldFill;");
|
||||||
|
result.add("import com.baomidou.mybatisplus.annotation.TableField;");
|
||||||
|
}
|
||||||
|
|
||||||
//主键
|
//主键
|
||||||
boolean isExistPrimaryKey = fields.stream().filter(e -> e.getPrimaryKeyFlag() != null && e.getPrimaryKeyFlag()).findFirst().isPresent();
|
boolean isExistPrimaryKey = fields.stream().anyMatch(e -> e.getPrimaryKeyFlag() != null && e.getPrimaryKeyFlag());
|
||||||
if (isExistPrimaryKey) {
|
if (isExistPrimaryKey) {
|
||||||
result.add("import com.baomidou.mybatisplus.annotation.TableId;");
|
result.add("import com.baomidou.mybatisplus.annotation.TableId;");
|
||||||
}
|
}
|
||||||
|
|
||||||
//自增
|
//自增
|
||||||
boolean isExistAutoIncrease = fields.stream().filter(e -> e.getAutoIncreaseFlag() != null && e.getAutoIncreaseFlag()).findFirst().isPresent();
|
boolean isExistAutoIncrease = fields.stream().anyMatch(e -> e.getAutoIncreaseFlag() != null && e.getAutoIncreaseFlag());
|
||||||
if (isExistAutoIncrease) {
|
if (isExistAutoIncrease) {
|
||||||
result.add("import com.baomidou.mybatisplus.annotation.IdType;");
|
result.add("import com.baomidou.mybatisplus.annotation.IdType;");
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -3,12 +3,13 @@ package net.lab1024.sa.base.module.support.codegenerator.service.variable.backen
|
|||||||
import cn.hutool.core.bean.BeanUtil;
|
import cn.hutool.core.bean.BeanUtil;
|
||||||
import net.lab1024.sa.base.module.support.codegenerator.constant.CodeQueryFieldQueryTypeEnum;
|
import net.lab1024.sa.base.module.support.codegenerator.constant.CodeQueryFieldQueryTypeEnum;
|
||||||
import net.lab1024.sa.base.module.support.codegenerator.domain.form.CodeGeneratorConfigForm;
|
import net.lab1024.sa.base.module.support.codegenerator.domain.form.CodeGeneratorConfigForm;
|
||||||
import net.lab1024.sa.base.module.support.codegenerator.domain.model.CodeInsertAndUpdateField;
|
|
||||||
import net.lab1024.sa.base.module.support.codegenerator.domain.model.CodeQueryField;
|
import net.lab1024.sa.base.module.support.codegenerator.domain.model.CodeQueryField;
|
||||||
import net.lab1024.sa.base.module.support.codegenerator.service.variable.CodeGenerateBaseVariableService;
|
import net.lab1024.sa.base.module.support.codegenerator.service.variable.CodeGenerateBaseVariableService;
|
||||||
import org.apache.commons.collections4.CollectionUtils;
|
|
||||||
|
|
||||||
import java.util.*;
|
import java.util.ArrayList;
|
||||||
|
import java.util.HashMap;
|
||||||
|
import java.util.List;
|
||||||
|
import java.util.Map;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @Author 1024创新实验室-主任:卓大
|
* @Author 1024创新实验室-主任:卓大
|
||||||
@@ -64,7 +65,15 @@ public class MapperVariableService extends CodeGenerateBaseVariableService {
|
|||||||
stringBuilder.append("\n )");
|
stringBuilder.append("\n )");
|
||||||
}
|
}
|
||||||
fieldMap.put("likeStr", stringBuilder.toString());
|
fieldMap.put("likeStr", stringBuilder.toString());
|
||||||
}else{
|
} else if (CodeQueryFieldQueryTypeEnum.DICT.equalsValue(queryField.getQueryTypeEnum())) {
|
||||||
|
String stringBuilder = "AND INSTR(" +
|
||||||
|
form.getTableName() + "." + queryField.getColumnNameList().get(0) +
|
||||||
|
",#{queryForm." +
|
||||||
|
queryField.getFieldName() +
|
||||||
|
"})";
|
||||||
|
fieldMap.put("likeStr", stringBuilder);
|
||||||
|
}
|
||||||
|
else {
|
||||||
fieldMap.put("columnName", queryField.getColumnNameList().get(0));
|
fieldMap.put("columnName", queryField.getColumnNameList().get(0));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -74,20 +83,4 @@ public class MapperVariableService extends CodeGenerateBaseVariableService {
|
|||||||
return variablesMap;
|
return variablesMap;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
public List<String> getPackageList(List<CodeInsertAndUpdateField> fields, CodeGeneratorConfigForm form) {
|
|
||||||
if (CollectionUtils.isEmpty(fields)) {
|
|
||||||
return new ArrayList<>();
|
|
||||||
}
|
|
||||||
|
|
||||||
HashSet<String> packageList = new HashSet<>();
|
|
||||||
|
|
||||||
//1、javabean相关的包
|
|
||||||
packageList.addAll(getJavaBeanImportClass(form));
|
|
||||||
|
|
||||||
//2、dao
|
|
||||||
packageList.add("import " + form.getBasic().getJavaPackageName() + ".dao." + form.getBasic().getModuleName() + "Dao;" );
|
|
||||||
return new ArrayList<>(packageList);
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -2,6 +2,7 @@ package net.lab1024.sa.base.module.support.codegenerator.service.variable.backen
|
|||||||
|
|
||||||
import cn.hutool.core.bean.BeanUtil;
|
import cn.hutool.core.bean.BeanUtil;
|
||||||
import net.lab1024.sa.base.common.util.SmartEnumUtil;
|
import net.lab1024.sa.base.common.util.SmartEnumUtil;
|
||||||
|
import net.lab1024.sa.base.common.util.SmartStringUtil;
|
||||||
import net.lab1024.sa.base.module.support.codegenerator.constant.CodeQueryFieldQueryTypeEnum;
|
import net.lab1024.sa.base.module.support.codegenerator.constant.CodeQueryFieldQueryTypeEnum;
|
||||||
import net.lab1024.sa.base.module.support.codegenerator.domain.form.CodeGeneratorConfigForm;
|
import net.lab1024.sa.base.module.support.codegenerator.domain.form.CodeGeneratorConfigForm;
|
||||||
import net.lab1024.sa.base.module.support.codegenerator.domain.model.CodeField;
|
import net.lab1024.sa.base.module.support.codegenerator.domain.model.CodeField;
|
||||||
@@ -41,14 +42,11 @@ public class QueryFormVariableService extends CodeGenerateBaseVariableService {
|
|||||||
|
|
||||||
|
|
||||||
public ImmutablePair<List<String>, List<Map<String, Object>>> getPackageListAndFields(CodeGeneratorConfigForm form) {
|
public ImmutablePair<List<String>, List<Map<String, Object>>> getPackageListAndFields(CodeGeneratorConfigForm form) {
|
||||||
|
|
||||||
List<CodeQueryField> fields = form.getQueryFields();
|
List<CodeQueryField> fields = form.getQueryFields();
|
||||||
if (CollectionUtils.isEmpty(fields)) {
|
|
||||||
return ImmutablePair.of(new ArrayList<>(), new ArrayList<>());
|
|
||||||
}
|
|
||||||
|
|
||||||
HashSet<String> packageList = new HashSet<>();
|
HashSet<String> packageList = new HashSet<>();
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 1、LocalDate、LocalDateTime、BigDecimal 类型的包名
|
* 1、LocalDate、LocalDateTime、BigDecimal 类型的包名
|
||||||
* 2、排序
|
* 2、排序
|
||||||
@@ -75,9 +73,6 @@ public class QueryFormVariableService extends CodeGenerateBaseVariableService {
|
|||||||
CodeField codeField = null;
|
CodeField codeField = null;
|
||||||
|
|
||||||
switch (queryTypeEnum) {
|
switch (queryTypeEnum) {
|
||||||
case LIKE:
|
|
||||||
finalFieldMap.put("javaType", "String");
|
|
||||||
break;
|
|
||||||
case EQUAL:
|
case EQUAL:
|
||||||
codeField = getCodeFieldByColumnName(field.getColumnNameList().get(0), form);
|
codeField = getCodeFieldByColumnName(field.getColumnNameList().get(0), form);
|
||||||
if (codeField == null) {
|
if (codeField == null) {
|
||||||
@@ -109,6 +104,14 @@ public class QueryFormVariableService extends CodeGenerateBaseVariableService {
|
|||||||
|
|
||||||
finalFieldMap.put("javaType", codeField.getJavaType());
|
finalFieldMap.put("javaType", codeField.getJavaType());
|
||||||
break;
|
break;
|
||||||
|
case DICT:
|
||||||
|
codeField = getCodeFieldByColumnName(field.getColumnNameList().get(0), form);
|
||||||
|
if (SmartStringUtil.isNotEmpty(codeField.getDict())) {
|
||||||
|
finalFieldMap.put("dict", "\n @JsonDeserialize(using = DictValueVoDeserializer.class)");
|
||||||
|
packageList.add("import com.fasterxml.jackson.databind.annotation.JsonDeserialize;");
|
||||||
|
packageList.add("import net.lab1024.sa.base.common.json.deserializer.DictValueVoDeserializer;");
|
||||||
|
}
|
||||||
|
finalFieldMap.put("javaType", "String");
|
||||||
default:
|
default:
|
||||||
finalFieldMap.put("javaType", "String");
|
finalFieldMap.put("javaType", "String");
|
||||||
}
|
}
|
||||||
@@ -116,12 +119,11 @@ public class QueryFormVariableService extends CodeGenerateBaseVariableService {
|
|||||||
finalFieldList.add(finalFieldMap);
|
finalFieldList.add(finalFieldMap);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
// lombok
|
// lombok
|
||||||
packageList.add("import lombok.Data;");
|
packageList.add("import lombok.Data;");
|
||||||
|
packageList.add("import lombok.EqualsAndHashCode;");
|
||||||
|
|
||||||
List<String> packageNameList = packageList.stream().filter(Objects::nonNull).collect(Collectors.toList());
|
List<String> packageNameList = packageList.stream().filter(Objects::nonNull).sorted().collect(Collectors.toList());
|
||||||
Collections.sort(packageNameList);
|
|
||||||
return ImmutablePair.of(packageNameList, finalFieldList);
|
return ImmutablePair.of(packageNameList, finalFieldList);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -2,6 +2,7 @@ package net.lab1024.sa.base.module.support.codegenerator.service.variable.backen
|
|||||||
|
|
||||||
import cn.hutool.core.bean.BeanUtil;
|
import cn.hutool.core.bean.BeanUtil;
|
||||||
import net.lab1024.sa.base.common.util.SmartStringUtil;
|
import net.lab1024.sa.base.common.util.SmartStringUtil;
|
||||||
|
import net.lab1024.sa.base.module.support.codegenerator.constant.CodeFrontComponentEnum;
|
||||||
import net.lab1024.sa.base.module.support.codegenerator.domain.form.CodeGeneratorConfigForm;
|
import net.lab1024.sa.base.module.support.codegenerator.domain.form.CodeGeneratorConfigForm;
|
||||||
import net.lab1024.sa.base.module.support.codegenerator.domain.model.CodeField;
|
import net.lab1024.sa.base.module.support.codegenerator.domain.model.CodeField;
|
||||||
import net.lab1024.sa.base.module.support.codegenerator.domain.model.CodeInsertAndUpdate;
|
import net.lab1024.sa.base.module.support.codegenerator.domain.model.CodeInsertAndUpdate;
|
||||||
@@ -123,7 +124,7 @@ public class UpdateFormVariableService extends CodeGenerateBaseVariableService {
|
|||||||
}
|
}
|
||||||
|
|
||||||
//文件上传
|
//文件上传
|
||||||
if (SmartStringUtil.contains(field.getFrontComponent(), "Upload")) {
|
if (CodeFrontComponentEnum.FILE_UPLOAD.equalsValue(field.getFrontComponent())) {
|
||||||
finalFieldMap.put("file", "\n @JsonDeserialize(using = FileKeyVoDeserializer.class)");
|
finalFieldMap.put("file", "\n @JsonDeserialize(using = FileKeyVoDeserializer.class)");
|
||||||
packageList.add("import com.fasterxml.jackson.databind.annotation.JsonDeserialize;");
|
packageList.add("import com.fasterxml.jackson.databind.annotation.JsonDeserialize;");
|
||||||
packageList.add("import net.lab1024.sa.base.common.json.deserializer.FileKeyVoDeserializer;");
|
packageList.add("import net.lab1024.sa.base.common.json.deserializer.FileKeyVoDeserializer;");
|
||||||
|
|||||||
@@ -87,16 +87,16 @@ public class VOVariableService extends CodeGenerateBaseVariableService {
|
|||||||
|
|
||||||
//字典
|
//字典
|
||||||
if (isDict(field.getColumnName(), form)) {
|
if (isDict(field.getColumnName(), form)) {
|
||||||
finalFieldMap.put("dict", "\n @JsonDeserialize(using = DictValueVoDeserializer.class)");
|
finalFieldMap.put("dict", "\n @JsonSerialize(using = DictValueVoSerializer.class)");
|
||||||
packageList.add("import com.fasterxml.jackson.databind.annotation.JsonDeserialize;");
|
packageList.add("import com.fasterxml.jackson.databind.annotation.JsonSerialize;");
|
||||||
packageList.add("import net.lab1024.sa.base.common.json.deserializer.DictValueVoDeserializer;");
|
packageList.add("import net.lab1024.sa.base.common.json.serializer.DictValueVoSerializer;");
|
||||||
}
|
}
|
||||||
|
|
||||||
//文件上传
|
//文件上传
|
||||||
if (isFile(field.getColumnName(), form)) {
|
if (isFile(field.getColumnName(), form)) {
|
||||||
finalFieldMap.put("file", "\n @JsonDeserialize(using = FileKeyVoDeserializer.class)");
|
finalFieldMap.put("file", "\n @JsonSerialize(using = FileKeyVoSerializer.class)");
|
||||||
packageList.add("import com.fasterxml.jackson.databind.annotation.JsonDeserialize;");
|
packageList.add("import com.fasterxml.jackson.databind.annotation.JsonSerialize;");
|
||||||
packageList.add("import net.lab1024.sa.base.common.json.deserializer.FileKeyVoDeserializer;");
|
packageList.add("import net.lab1024.sa.base.common.json.serializer.FileKeyVoSerializer;");
|
||||||
}
|
}
|
||||||
|
|
||||||
packageList.add(getJavaPackageName(codeField.getJavaType()));
|
packageList.add(getJavaPackageName(codeField.getJavaType()));
|
||||||
|
|||||||
@@ -57,19 +57,20 @@ public class FormVariableService extends CodeGenerateBaseVariableService {
|
|||||||
|
|
||||||
fieldsVariableList.add(objectMap);
|
fieldsVariableList.add(objectMap);
|
||||||
|
|
||||||
if (CodeFrontComponentEnum.ENUM_SELECT.getValue().equals(field.getFrontComponent())) {
|
if (CodeFrontComponentEnum.ENUM_SELECT.equalsValue(field.getFrontComponent())) {
|
||||||
frontImportSet.add("import SmartEnumSelect from '/@/components/framework/smart-enum-select/index.vue';");
|
frontImportSet.add("import SmartEnumSelect from '/@/components/framework/smart-enum-select/index.vue';");
|
||||||
}
|
}
|
||||||
|
|
||||||
if (CodeFrontComponentEnum.BOOLEAN_SELECT.getValue().equals(field.getFrontComponent())) {
|
if (CodeFrontComponentEnum.BOOLEAN_SELECT.equalsValue(field.getFrontComponent())) {
|
||||||
frontImportSet.add("import BooleanSelect from '/@/components/framework/boolean-select/index.vue';");
|
frontImportSet.add("import BooleanSelect from '/@/components/framework/boolean-select/index.vue';");
|
||||||
}
|
}
|
||||||
|
|
||||||
if (CodeFrontComponentEnum.DICT_SELECT.getValue().equals(field.getFrontComponent())) {
|
if (CodeFrontComponentEnum.DICT_SELECT.equalsValue(field.getFrontComponent())) {
|
||||||
frontImportSet.add("import DictSelect from '/@/components/support/dict-select/index.vue';");
|
frontImportSet.add("import DictSelect from '/@/components/support/dict-select/index.vue';");
|
||||||
}
|
}
|
||||||
|
|
||||||
if (CodeFrontComponentEnum.FILE_UPLOAD.getValue().equals(field.getFrontComponent())) {
|
if (CodeFrontComponentEnum.FILE_UPLOAD.equalsValue(field.getFrontComponent())) {
|
||||||
|
frontImportSet.add("import { FILE_FOLDER_TYPE_ENUM } from '/@/constants/support/file-const';");
|
||||||
frontImportSet.add("import FileUpload from '/@/components/support/file-upload/index.vue';");
|
frontImportSet.add("import FileUpload from '/@/components/support/file-upload/index.vue';");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -4,6 +4,7 @@ import cn.hutool.core.bean.BeanUtil;
|
|||||||
import com.google.common.base.CaseFormat;
|
import com.google.common.base.CaseFormat;
|
||||||
import net.lab1024.sa.base.module.support.codegenerator.constant.CodeQueryFieldQueryTypeEnum;
|
import net.lab1024.sa.base.module.support.codegenerator.constant.CodeQueryFieldQueryTypeEnum;
|
||||||
import net.lab1024.sa.base.module.support.codegenerator.domain.form.CodeGeneratorConfigForm;
|
import net.lab1024.sa.base.module.support.codegenerator.domain.form.CodeGeneratorConfigForm;
|
||||||
|
import net.lab1024.sa.base.module.support.codegenerator.domain.model.CodeField;
|
||||||
import net.lab1024.sa.base.module.support.codegenerator.domain.model.CodeQueryField;
|
import net.lab1024.sa.base.module.support.codegenerator.domain.model.CodeQueryField;
|
||||||
import net.lab1024.sa.base.module.support.codegenerator.service.variable.CodeGenerateBaseVariableService;
|
import net.lab1024.sa.base.module.support.codegenerator.service.variable.CodeGenerateBaseVariableService;
|
||||||
|
|
||||||
@@ -35,19 +36,23 @@ public class ListVariableService extends CodeGenerateBaseVariableService {
|
|||||||
|
|
||||||
for (CodeQueryField queryField : queryFields) {
|
for (CodeQueryField queryField : queryFields) {
|
||||||
Map<String, Object> objectMap = BeanUtil.beanToMap(queryField);
|
Map<String, Object> objectMap = BeanUtil.beanToMap(queryField);
|
||||||
variableList.add(objectMap);
|
|
||||||
|
|
||||||
if("Enum".equals(queryField.getQueryTypeEnum())){
|
CodeField codeField = getCodeFieldByColumnName(queryField.getColumnNameList().get(0), form);
|
||||||
|
objectMap.put("frontEnumName", codeField.getEnumName());
|
||||||
|
objectMap.put("dict", codeField.getDict());
|
||||||
|
|
||||||
|
if(CodeQueryFieldQueryTypeEnum.ENUM.equalsValue(queryField.getQueryTypeEnum())){
|
||||||
frontImportSet.add("import SmartEnumSelect from '/@/components/framework/smart-enum-select/index.vue';");
|
frontImportSet.add("import SmartEnumSelect from '/@/components/framework/smart-enum-select/index.vue';");
|
||||||
}
|
}
|
||||||
|
|
||||||
if("Dict".equals(queryField.getQueryTypeEnum())){
|
if(CodeQueryFieldQueryTypeEnum.DICT.equalsValue(queryField.getQueryTypeEnum())){
|
||||||
frontImportSet.add("import DictSelect from '/@/components/support/dict-select/index.vue';");
|
frontImportSet.add("import DictSelect from '/@/components/support/dict-select/index.vue';");
|
||||||
}
|
}
|
||||||
|
|
||||||
if(CodeQueryFieldQueryTypeEnum.DATE_RANGE.getValue().equals(queryField.getQueryTypeEnum())){
|
if(CodeQueryFieldQueryTypeEnum.DATE_RANGE.equalsValue(queryField.getQueryTypeEnum())){
|
||||||
frontImportSet.add("import { defaultTimeRanges } from '/@/lib/default-time-ranges';");
|
frontImportSet.add("import { defaultTimeRanges } from '/@/lib/default-time-ranges';");
|
||||||
}
|
}
|
||||||
|
variableList.add(objectMap);
|
||||||
|
|
||||||
}
|
}
|
||||||
variablesMap.put("queryFields",variableList);
|
variablesMap.put("queryFields",variableList);
|
||||||
|
|||||||
@@ -22,6 +22,7 @@ public enum ConfigKeyEnum implements BaseEnum {
|
|||||||
*/
|
*/
|
||||||
SUPER_PASSWORD("super_password", "万能密码"),
|
SUPER_PASSWORD("super_password", "万能密码"),
|
||||||
|
|
||||||
|
LEVEL3_PROTECT_CONFIG("level3_protect_config", "三级等保配置"),
|
||||||
;
|
;
|
||||||
|
|
||||||
private final String value;
|
private final String value;
|
||||||
|
|||||||
@@ -37,7 +37,7 @@ public class ConfigService {
|
|||||||
/**
|
/**
|
||||||
* 一个简单的系统配置缓存
|
* 一个简单的系统配置缓存
|
||||||
*/
|
*/
|
||||||
private final ConcurrentHashMap<String, ConfigEntity> configCache = new ConcurrentHashMap<>();
|
private final ConcurrentHashMap<String, ConfigEntity> CONFIG_CACHE = new ConcurrentHashMap<>();
|
||||||
|
|
||||||
@Resource
|
@Resource
|
||||||
private ConfigDao configDao;
|
private ConfigDao configDao;
|
||||||
@@ -52,13 +52,13 @@ public class ConfigService {
|
|||||||
*/
|
*/
|
||||||
@PostConstruct
|
@PostConstruct
|
||||||
private void loadConfigCache() {
|
private void loadConfigCache() {
|
||||||
configCache.clear();
|
CONFIG_CACHE.clear();
|
||||||
List<ConfigEntity> entityList = configDao.selectList(null);
|
List<ConfigEntity> entityList = configDao.selectList(null);
|
||||||
if (CollectionUtils.isEmpty(entityList)) {
|
if (CollectionUtils.isEmpty(entityList)) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
entityList.forEach(entity -> this.configCache.put(entity.getConfigKey().toLowerCase(), entity));
|
entityList.forEach(entity -> this.CONFIG_CACHE.put(entity.getConfigKey().toLowerCase(), entity));
|
||||||
log.info("################# 系统配置缓存初始化完毕:{} ###################", configCache.size());
|
log.info("################# 系统配置缓存初始化完毕:{} ###################", CONFIG_CACHE.size());
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -70,7 +70,7 @@ public class ConfigService {
|
|||||||
if (null == configEntity) {
|
if (null == configEntity) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
this.configCache.put(configEntity.getConfigKey().toLowerCase(), configEntity);
|
this.CONFIG_CACHE.put(configEntity.getConfigKey().toLowerCase(), configEntity);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -100,7 +100,7 @@ public class ConfigService {
|
|||||||
if (StrUtil.isBlank(configKey)) {
|
if (StrUtil.isBlank(configKey)) {
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
ConfigEntity entity = this.configCache.get(configKey.toLowerCase());
|
ConfigEntity entity = this.CONFIG_CACHE.get(configKey.toLowerCase());
|
||||||
return SmartBeanUtil.copy(entity, ConfigVO.class);
|
return SmartBeanUtil.copy(entity, ConfigVO.class);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -109,7 +109,8 @@ public class ConfigService {
|
|||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
public String getConfigValue(ConfigKeyEnum configKey) {
|
public String getConfigValue(ConfigKeyEnum configKey) {
|
||||||
return this.getConfig(configKey).getConfigValue();
|
ConfigVO config = this.getConfig(configKey);
|
||||||
|
return config == null ? null : config.getConfigValue();
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -125,12 +126,12 @@ public class ConfigService {
|
|||||||
* 添加系统配置
|
* 添加系统配置
|
||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
public ResponseDTO<String> add(ConfigAddForm configAddDTO) {
|
public ResponseDTO<String> add(ConfigAddForm configAddForm) {
|
||||||
ConfigEntity entity = configDao.selectByKey(configAddDTO.getConfigKey());
|
ConfigEntity entity = configDao.selectByKey(configAddForm.getConfigKey());
|
||||||
if (null != entity) {
|
if (null != entity) {
|
||||||
return ResponseDTO.error(UserErrorCode.ALREADY_EXIST);
|
return ResponseDTO.error(UserErrorCode.ALREADY_EXIST);
|
||||||
}
|
}
|
||||||
entity = SmartBeanUtil.copy(configAddDTO, ConfigEntity.class);
|
entity = SmartBeanUtil.copy(configAddForm, ConfigEntity.class);
|
||||||
configDao.insert(entity);
|
configDao.insert(entity);
|
||||||
|
|
||||||
// 刷新缓存
|
// 刷新缓存
|
||||||
|
|||||||
@@ -0,0 +1,27 @@
|
|||||||
|
package net.lab1024.sa.base.module.support.datamasking;
|
||||||
|
|
||||||
|
import com.fasterxml.jackson.annotation.JacksonAnnotationsInside;
|
||||||
|
import com.fasterxml.jackson.databind.annotation.JsonSerialize;
|
||||||
|
import net.lab1024.sa.base.common.json.serializer.DataMaskingSerializer;
|
||||||
|
|
||||||
|
import java.lang.annotation.ElementType;
|
||||||
|
import java.lang.annotation.Retention;
|
||||||
|
import java.lang.annotation.RetentionPolicy;
|
||||||
|
import java.lang.annotation.Target;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 脱敏注解
|
||||||
|
*
|
||||||
|
* @author 罗伊
|
||||||
|
* @description:
|
||||||
|
* @date 2024/7/21 4:39 下午
|
||||||
|
*/
|
||||||
|
@Target(ElementType.FIELD)
|
||||||
|
@Retention(RetentionPolicy.RUNTIME)
|
||||||
|
@JacksonAnnotationsInside
|
||||||
|
@JsonSerialize(using = DataMaskingSerializer.class, nullsUsing = DataMaskingSerializer.class)
|
||||||
|
public @interface DataMasking {
|
||||||
|
|
||||||
|
DataMaskingTypeEnum value() default DataMaskingTypeEnum.COMMON;
|
||||||
|
|
||||||
|
}
|
||||||
@@ -0,0 +1,40 @@
|
|||||||
|
package net.lab1024.sa.base.module.support.datamasking;
|
||||||
|
|
||||||
|
import cn.hutool.core.util.DesensitizedUtil;
|
||||||
|
import lombok.AllArgsConstructor;
|
||||||
|
import lombok.Getter;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 脱敏数据类型
|
||||||
|
*
|
||||||
|
* @Author 1024创新实验室-创始人兼主任:卓大
|
||||||
|
* @Date 2024/8/1
|
||||||
|
* @Wechat zhuoda1024
|
||||||
|
* @Email lab1024@163.com
|
||||||
|
* @Copyright <a href="https://1024lab.net">1024创新实验室</a> ,Since 2012
|
||||||
|
*/
|
||||||
|
|
||||||
|
@AllArgsConstructor
|
||||||
|
@Getter
|
||||||
|
public enum DataMaskingTypeEnum {
|
||||||
|
|
||||||
|
COMMON(null, "通用"),
|
||||||
|
PHONE(DesensitizedUtil.DesensitizedType.MOBILE_PHONE, "手机号"),
|
||||||
|
CHINESE_NAME(DesensitizedUtil.DesensitizedType.CHINESE_NAME, "中文名"),
|
||||||
|
ID_CARD(DesensitizedUtil.DesensitizedType.ID_CARD, "身份证号"),
|
||||||
|
FIXED_PHONE(DesensitizedUtil.DesensitizedType.FIXED_PHONE, "座机号"),
|
||||||
|
ADDRESS(DesensitizedUtil.DesensitizedType.ADDRESS, "地址"),
|
||||||
|
EMAIL(DesensitizedUtil.DesensitizedType.EMAIL, "电子邮件"),
|
||||||
|
PASSWORD(DesensitizedUtil.DesensitizedType.PASSWORD, "密码"),
|
||||||
|
CAR_LICENSE(DesensitizedUtil.DesensitizedType.CAR_LICENSE, "中国大陆车牌"),
|
||||||
|
BANK_CARD(DesensitizedUtil.DesensitizedType.BANK_CARD, "银行卡"),
|
||||||
|
USER_ID(DesensitizedUtil.DesensitizedType.USER_ID, "用户id");
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
private DesensitizedUtil.DesensitizedType type;
|
||||||
|
|
||||||
|
private String desc;
|
||||||
|
|
||||||
|
|
||||||
|
}
|
||||||
@@ -0,0 +1,216 @@
|
|||||||
|
package net.lab1024.sa.base.module.support.datamasking;
|
||||||
|
|
||||||
|
import cn.hutool.core.util.DesensitizedUtil;
|
||||||
|
import cn.hutool.core.util.StrUtil;
|
||||||
|
import org.apache.commons.collections4.CollectionUtils;
|
||||||
|
import org.apache.commons.lang3.StringUtils;
|
||||||
|
|
||||||
|
import java.beans.IntrospectionException;
|
||||||
|
import java.beans.PropertyDescriptor;
|
||||||
|
import java.lang.reflect.Field;
|
||||||
|
import java.lang.reflect.InvocationTargetException;
|
||||||
|
import java.lang.reflect.Method;
|
||||||
|
import java.lang.reflect.Type;
|
||||||
|
import java.util.ArrayList;
|
||||||
|
import java.util.Collection;
|
||||||
|
import java.util.List;
|
||||||
|
import java.util.concurrent.ConcurrentHashMap;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 脱敏工具类
|
||||||
|
*
|
||||||
|
* @Author 1024创新实验室-主任: 卓大
|
||||||
|
* @Date 2024-07-23 21:38:52
|
||||||
|
* @Wechat zhuoda1024
|
||||||
|
* @Email lab1024@163.com
|
||||||
|
* @Copyright <a href="https://1024lab.net">1024创新实验室</a>
|
||||||
|
*/
|
||||||
|
public class SmartDataMaskingUtil {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 类 加注解字段缓存
|
||||||
|
*/
|
||||||
|
private static final ConcurrentHashMap<Class<?>, List<Field>> fieldMap = new ConcurrentHashMap<>();
|
||||||
|
|
||||||
|
public static String dataMasking(String value) {
|
||||||
|
if (StringUtils.isBlank(value)) {
|
||||||
|
return value;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (value.length() < 4) {
|
||||||
|
return StrUtil.hide(value, 0, value.length());
|
||||||
|
}
|
||||||
|
|
||||||
|
int valueLength = value.length();
|
||||||
|
int startHideIndex = getHideStartIndex(valueLength);
|
||||||
|
int endHideIndex = getHideEndIndex(valueLength);
|
||||||
|
return StrUtil.hide(value, startHideIndex, endHideIndex);
|
||||||
|
}
|
||||||
|
|
||||||
|
public static Object dataMasking(Object value, DataMaskingTypeEnum dataType) {
|
||||||
|
|
||||||
|
if (value == null) {
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (dataType == null) {
|
||||||
|
return dataMasking(String.valueOf(value));
|
||||||
|
}
|
||||||
|
|
||||||
|
switch (dataType) {
|
||||||
|
case PHONE:
|
||||||
|
return DesensitizedUtil.mobilePhone(String.valueOf(value));
|
||||||
|
case CHINESE_NAME:
|
||||||
|
return DesensitizedUtil.chineseName(String.valueOf(value));
|
||||||
|
case ID_CARD:
|
||||||
|
return DesensitizedUtil.idCardNum(String.valueOf(value), 6, 2);
|
||||||
|
case FIXED_PHONE:
|
||||||
|
return DesensitizedUtil.fixedPhone(String.valueOf(value));
|
||||||
|
case ADDRESS:
|
||||||
|
return StrUtil.hide(String.valueOf(value), 6, String.valueOf(value).length() - 1);
|
||||||
|
case EMAIL:
|
||||||
|
return DesensitizedUtil.email(String.valueOf(value));
|
||||||
|
case PASSWORD:
|
||||||
|
return DesensitizedUtil.password(String.valueOf(value));
|
||||||
|
case CAR_LICENSE:
|
||||||
|
return DesensitizedUtil.carLicense(String.valueOf(value));
|
||||||
|
case BANK_CARD:
|
||||||
|
return DesensitizedUtil.bankCard(String.valueOf(value));
|
||||||
|
case USER_ID:
|
||||||
|
return DesensitizedUtil.userId();
|
||||||
|
default:
|
||||||
|
return dataMasking(String.valueOf(value));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 批量脱敏
|
||||||
|
*/
|
||||||
|
public static <T> void dataMasking(Collection<T> objectList) throws IntrospectionException, InvocationTargetException, IllegalAccessException {
|
||||||
|
if (CollectionUtils.isEmpty(objectList)) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
for (T object : objectList) {
|
||||||
|
dataMasking(object);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 单个脱敏
|
||||||
|
*/
|
||||||
|
public static <T> void dataMasking(T object) throws IntrospectionException, InvocationTargetException, IllegalAccessException {
|
||||||
|
Class<?> tClass = object.getClass();
|
||||||
|
List<Field> fieldList = getField(object);
|
||||||
|
for (Field field : fieldList) {
|
||||||
|
field.setAccessible(true);
|
||||||
|
String fieldValue = "";
|
||||||
|
try {
|
||||||
|
PropertyDescriptor pd = new PropertyDescriptor(field.getName(), tClass);
|
||||||
|
Method getMethod = pd.getReadMethod();
|
||||||
|
Object value = getMethod.invoke(object);
|
||||||
|
if (value != null) {
|
||||||
|
fieldValue = value.toString();
|
||||||
|
}
|
||||||
|
} catch (Exception e) {
|
||||||
|
throw new RuntimeException(e);
|
||||||
|
}
|
||||||
|
if (StringUtils.isBlank(fieldValue)) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
int valueLength = fieldValue.length();
|
||||||
|
int startHideIndex = getHideStartIndex(valueLength);
|
||||||
|
int endHideIndex = getHideEndIndex(valueLength);
|
||||||
|
try {
|
||||||
|
field.set(object, StrUtil.hide(fieldValue, startHideIndex, endHideIndex));
|
||||||
|
} catch (Exception e1) {
|
||||||
|
throw new RuntimeException(e1);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private static int getHideStartIndex(int totalLength) {
|
||||||
|
if (totalLength <= 4) {
|
||||||
|
return 1;
|
||||||
|
} else if (totalLength <= 6) {
|
||||||
|
return 1;
|
||||||
|
} else if (totalLength <= 10) {
|
||||||
|
return 2;
|
||||||
|
} else if (totalLength <= 18) {
|
||||||
|
return 3;
|
||||||
|
} else if (totalLength <= 27) {
|
||||||
|
return 5;
|
||||||
|
} else if (totalLength <= 34) {
|
||||||
|
return 7;
|
||||||
|
} else if (totalLength <= 41) {
|
||||||
|
return 9;
|
||||||
|
} else {
|
||||||
|
return 15;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private static int getHideEndIndex(int totalLength) {
|
||||||
|
if (totalLength <= 4) {
|
||||||
|
return totalLength - 1;
|
||||||
|
} else if (totalLength <= 6) {
|
||||||
|
return totalLength - 2;
|
||||||
|
} else if (totalLength <= 10) {
|
||||||
|
return totalLength - 2;
|
||||||
|
} else if (totalLength <= 18) {
|
||||||
|
return totalLength - 4;
|
||||||
|
} else if (totalLength <= 27) {
|
||||||
|
return totalLength - 6;
|
||||||
|
} else if (totalLength <= 34) {
|
||||||
|
return totalLength - 8;
|
||||||
|
} else if (totalLength <= 41) {
|
||||||
|
return totalLength - 10;
|
||||||
|
} else {
|
||||||
|
return totalLength - 16;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
public static List<Field> getField(Object object) throws IntrospectionException {
|
||||||
|
// 从缓存中查询
|
||||||
|
Class<?> tClass = object.getClass();
|
||||||
|
List<Field> fieldList = fieldMap.get(tClass);
|
||||||
|
if (null != fieldList) {
|
||||||
|
return fieldList;
|
||||||
|
}
|
||||||
|
|
||||||
|
// 这一段递归代码 是为了 从父类中获取属性
|
||||||
|
Class<?> tempClass = tClass;
|
||||||
|
fieldList = new ArrayList<>();
|
||||||
|
while (tempClass != null) {
|
||||||
|
Field[] declaredFields = tempClass.getDeclaredFields();
|
||||||
|
for (Field field : declaredFields) {
|
||||||
|
boolean stringField = false;
|
||||||
|
try {
|
||||||
|
PropertyDescriptor pd = new PropertyDescriptor(field.getName(), tClass);
|
||||||
|
Method getMethod = pd.getReadMethod();
|
||||||
|
Type returnType = getMethod.getGenericReturnType();
|
||||||
|
stringField = "java.lang.String".equals(returnType.getTypeName());
|
||||||
|
} catch (Exception e) {
|
||||||
|
throw new RuntimeException(e);
|
||||||
|
}
|
||||||
|
if (field.isAnnotationPresent(DataMasking.class) && stringField) {
|
||||||
|
field.setAccessible(true);
|
||||||
|
fieldList.add(field);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
tempClass = tempClass.getSuperclass();
|
||||||
|
}
|
||||||
|
fieldMap.put(tClass, fieldList);
|
||||||
|
return fieldList;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static void main(String[] args) {
|
||||||
|
System.out.println(dataMasking("a", null));
|
||||||
|
System.out.println(dataMasking("ab", null));
|
||||||
|
System.out.println(dataMasking("abc", null));
|
||||||
|
System.out.println(dataMasking("abcd", null));
|
||||||
|
System.out.println(dataMasking("abcde", null));
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
@@ -19,9 +19,9 @@ import net.lab1024.sa.base.module.support.file.domain.vo.FileDownloadVO;
|
|||||||
import net.lab1024.sa.base.module.support.file.domain.vo.FileUploadVO;
|
import net.lab1024.sa.base.module.support.file.domain.vo.FileUploadVO;
|
||||||
import net.lab1024.sa.base.module.support.file.domain.vo.FileVO;
|
import net.lab1024.sa.base.module.support.file.domain.vo.FileVO;
|
||||||
import net.lab1024.sa.base.module.support.redis.RedisService;
|
import net.lab1024.sa.base.module.support.redis.RedisService;
|
||||||
|
import net.lab1024.sa.base.module.support.securityprotect.service.SecurityFileService;
|
||||||
import org.apache.commons.collections4.CollectionUtils;
|
import org.apache.commons.collections4.CollectionUtils;
|
||||||
import org.apache.commons.lang3.StringUtils;
|
import org.apache.commons.lang3.StringUtils;
|
||||||
import org.springframework.beans.factory.annotation.Value;
|
|
||||||
import org.springframework.stereotype.Service;
|
import org.springframework.stereotype.Service;
|
||||||
import org.springframework.web.multipart.MultipartFile;
|
import org.springframework.web.multipart.MultipartFile;
|
||||||
|
|
||||||
@@ -58,9 +58,8 @@ public class FileService {
|
|||||||
@Resource
|
@Resource
|
||||||
private RedisService redisService;
|
private RedisService redisService;
|
||||||
|
|
||||||
@Value("${spring.servlet.multipart.max-file-size}")
|
@Resource
|
||||||
private String maxFileSize;
|
private SecurityFileService securityFileService;
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 文件上传服务
|
* 文件上传服务
|
||||||
@@ -89,11 +88,10 @@ public class FileService {
|
|||||||
return ResponseDTO.userErrorParam("文件名称最大长度为:" + FILE_NAME_MAX_LENGTH);
|
return ResponseDTO.userErrorParam("文件名称最大长度为:" + FILE_NAME_MAX_LENGTH);
|
||||||
}
|
}
|
||||||
|
|
||||||
// 校验文件大小
|
// 校验文件大小以及安全性
|
||||||
String maxSizeStr = maxFileSize.toLowerCase().replace("mb", "");
|
ResponseDTO<String> validateFile = securityFileService.checkFile(file);
|
||||||
long maxSize = Integer.parseInt(maxSizeStr) * 1024 * 1024L;
|
if (!validateFile.getOk()) {
|
||||||
if (file.getSize() > maxSize) {
|
return ResponseDTO.error(validateFile);
|
||||||
return ResponseDTO.userErrorParam("上传文件最大为:" + maxSize);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// 进行上传
|
// 进行上传
|
||||||
|
|||||||
@@ -0,0 +1,164 @@
|
|||||||
|
package net.lab1024.sa.base.module.support.job.api;
|
||||||
|
|
||||||
|
import cn.hutool.core.util.IdUtil;
|
||||||
|
import com.google.common.collect.Lists;
|
||||||
|
import lombok.extern.slf4j.Slf4j;
|
||||||
|
import net.lab1024.sa.base.module.support.job.api.domain.SmartJobMsg;
|
||||||
|
import net.lab1024.sa.base.module.support.job.config.SmartJobAutoConfiguration;
|
||||||
|
import net.lab1024.sa.base.module.support.job.core.SmartJob;
|
||||||
|
import net.lab1024.sa.base.module.support.job.core.SmartJobExecutor;
|
||||||
|
import net.lab1024.sa.base.module.support.job.core.SmartJobLauncher;
|
||||||
|
import net.lab1024.sa.base.module.support.job.repository.SmartJobRepository;
|
||||||
|
import net.lab1024.sa.base.module.support.job.repository.domain.SmartJobEntity;
|
||||||
|
import org.redisson.api.RLock;
|
||||||
|
import org.redisson.api.RTopic;
|
||||||
|
import org.redisson.api.RedissonClient;
|
||||||
|
import org.redisson.api.listener.MessageListener;
|
||||||
|
import org.springframework.boot.autoconfigure.condition.ConditionalOnBean;
|
||||||
|
import org.springframework.stereotype.Service;
|
||||||
|
|
||||||
|
import javax.annotation.PreDestroy;
|
||||||
|
import java.util.List;
|
||||||
|
import java.util.Objects;
|
||||||
|
import java.util.Optional;
|
||||||
|
import java.util.concurrent.TimeUnit;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* smart job 执行端管理
|
||||||
|
* 分布式系统之间 用发布/订阅消息的形式 来管理多个job
|
||||||
|
*
|
||||||
|
* @author huke
|
||||||
|
* @date 2024/6/22 20:31
|
||||||
|
*/
|
||||||
|
@ConditionalOnBean(SmartJobAutoConfiguration.class)
|
||||||
|
@Slf4j
|
||||||
|
@Service
|
||||||
|
public class SmartJobClientManager {
|
||||||
|
|
||||||
|
private final SmartJobLauncher jobLauncher;
|
||||||
|
|
||||||
|
private final SmartJobRepository jobRepository;
|
||||||
|
|
||||||
|
private final List<SmartJob> jobInterfaceList;
|
||||||
|
|
||||||
|
private static final String EXECUTE_LOCK = "smart-job-lock-msg-execute-";
|
||||||
|
|
||||||
|
private static final String TOPIC = "smart-job-instance";
|
||||||
|
|
||||||
|
private final RedissonClient redissonClient;
|
||||||
|
|
||||||
|
private final RTopic topic;
|
||||||
|
|
||||||
|
private final SmartJobMsgListener jobMsgListener;
|
||||||
|
|
||||||
|
public SmartJobClientManager(SmartJobLauncher jobLauncher,
|
||||||
|
SmartJobRepository jobRepository,
|
||||||
|
List<SmartJob> jobInterfaceList,
|
||||||
|
RedissonClient redissonClient) {
|
||||||
|
this.jobLauncher = jobLauncher;
|
||||||
|
this.jobRepository = jobRepository;
|
||||||
|
this.jobInterfaceList = jobInterfaceList;
|
||||||
|
this.redissonClient = redissonClient;
|
||||||
|
|
||||||
|
// 添加监听器
|
||||||
|
this.topic = redissonClient.getTopic(TOPIC);
|
||||||
|
this.jobMsgListener = new SmartJobMsgListener();
|
||||||
|
topic.addListener(SmartJobMsg.class, jobMsgListener);
|
||||||
|
log.info("==== SmartJob ==== client-manager init");
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 发布消息
|
||||||
|
*/
|
||||||
|
public void publishToClient(SmartJobMsg msgDTO) {
|
||||||
|
msgDTO.setMsgId(IdUtil.fastSimpleUUID());
|
||||||
|
topic.publish(msgDTO);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 处理消息
|
||||||
|
*/
|
||||||
|
private class SmartJobMsgListener implements MessageListener<SmartJobMsg> {
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void onMessage(CharSequence channel, SmartJobMsg msg) {
|
||||||
|
log.info("==== SmartJob ==== on-message :{}", msg);
|
||||||
|
// 判断消息类型 业务简单就直接判断 复杂的话可以策略模式
|
||||||
|
SmartJobMsg.MsgTypeEnum msgType = msg.getMsgType();
|
||||||
|
// 更新任务
|
||||||
|
if (SmartJobMsg.MsgTypeEnum.UPDATE_JOB == msgType) {
|
||||||
|
updateJob(msg.getJobId());
|
||||||
|
}
|
||||||
|
// 执行任务
|
||||||
|
if (SmartJobMsg.MsgTypeEnum.EXECUTE_JOB == msgType) {
|
||||||
|
executeJob(msg);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 获取任务执行类
|
||||||
|
*
|
||||||
|
* @param jobClass
|
||||||
|
* @return
|
||||||
|
*/
|
||||||
|
private Optional<SmartJob> queryJobImpl(String jobClass) {
|
||||||
|
return jobInterfaceList.stream().filter(e -> Objects.equals(e.getClassName(), jobClass)).findFirst();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 更新任务
|
||||||
|
*
|
||||||
|
* @param jobId
|
||||||
|
*/
|
||||||
|
private void updateJob(Integer jobId) {
|
||||||
|
SmartJobEntity jobEntity = jobRepository.getJobDao().selectById(jobId);
|
||||||
|
if (null == jobEntity) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
jobLauncher.startOrRefreshJob(Lists.newArrayList(jobEntity));
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 立即执行任务
|
||||||
|
*
|
||||||
|
* @param msg
|
||||||
|
*/
|
||||||
|
private void executeJob(SmartJobMsg msg) {
|
||||||
|
Integer jobId = msg.getJobId();
|
||||||
|
SmartJobEntity jobEntity = jobRepository.getJobDao().selectById(jobId);
|
||||||
|
if (null == jobEntity) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
// 获取定时任务实现类
|
||||||
|
Optional<SmartJob> optional = this.queryJobImpl(jobEntity.getJobClass());
|
||||||
|
if (!optional.isPresent()) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// 获取执行锁 无需主动释放
|
||||||
|
RLock rLock = redissonClient.getLock(EXECUTE_LOCK + msg.getMsgId());
|
||||||
|
try {
|
||||||
|
boolean getLock = rLock.tryLock(0, 20, TimeUnit.SECONDS);
|
||||||
|
if (!getLock) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
} catch (InterruptedException e) {
|
||||||
|
log.error("==== SmartJob ==== msg execute err:", e);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// 通过执行器 执行任务
|
||||||
|
jobEntity.setParam(msg.getParam());
|
||||||
|
SmartJobExecutor jobExecutor = new SmartJobExecutor(jobEntity, jobRepository, optional.get(), redissonClient);
|
||||||
|
jobExecutor.execute(msg.getUpdateName());
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@PreDestroy
|
||||||
|
public void destroy() {
|
||||||
|
topic.removeListener(jobMsgListener);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
}
|
||||||
@@ -0,0 +1,246 @@
|
|||||||
|
package net.lab1024.sa.base.module.support.job.api;
|
||||||
|
|
||||||
|
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
|
||||||
|
import com.google.common.collect.Lists;
|
||||||
|
import net.lab1024.sa.base.common.code.UserErrorCode;
|
||||||
|
import net.lab1024.sa.base.common.domain.PageResult;
|
||||||
|
import net.lab1024.sa.base.common.domain.ResponseDTO;
|
||||||
|
import net.lab1024.sa.base.common.util.SmartBeanUtil;
|
||||||
|
import net.lab1024.sa.base.common.util.SmartPageUtil;
|
||||||
|
import net.lab1024.sa.base.module.support.job.api.domain.*;
|
||||||
|
import net.lab1024.sa.base.module.support.job.config.SmartJobAutoConfiguration;
|
||||||
|
import net.lab1024.sa.base.module.support.job.constant.SmartJobTriggerTypeEnum;
|
||||||
|
import net.lab1024.sa.base.module.support.job.constant.SmartJobUtil;
|
||||||
|
import net.lab1024.sa.base.module.support.job.repository.SmartJobDao;
|
||||||
|
import net.lab1024.sa.base.module.support.job.repository.SmartJobLogDao;
|
||||||
|
import net.lab1024.sa.base.module.support.job.repository.domain.SmartJobEntity;
|
||||||
|
import net.lab1024.sa.base.module.support.job.repository.domain.SmartJobLogEntity;
|
||||||
|
import org.apache.commons.collections4.CollectionUtils;
|
||||||
|
import org.springframework.beans.factory.annotation.Autowired;
|
||||||
|
import org.springframework.boot.autoconfigure.condition.ConditionalOnBean;
|
||||||
|
import org.springframework.stereotype.Service;
|
||||||
|
|
||||||
|
import javax.annotation.Resource;
|
||||||
|
import java.time.LocalDateTime;
|
||||||
|
import java.util.Collections;
|
||||||
|
import java.util.List;
|
||||||
|
import java.util.Map;
|
||||||
|
import java.util.Objects;
|
||||||
|
import java.util.stream.Collectors;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 定时任务 接口业务管理
|
||||||
|
* 如果不需要通过接口管理定时任务 可以删除此类
|
||||||
|
*
|
||||||
|
* @author huke
|
||||||
|
* @date 2024/6/17 20:41
|
||||||
|
*/
|
||||||
|
@ConditionalOnBean(SmartJobAutoConfiguration.class)
|
||||||
|
@Service
|
||||||
|
public class SmartJobService {
|
||||||
|
|
||||||
|
@Resource
|
||||||
|
private SmartJobDao jobDao;
|
||||||
|
|
||||||
|
@Resource
|
||||||
|
private SmartJobLogDao jobLogDao;
|
||||||
|
|
||||||
|
@Resource
|
||||||
|
private SmartJobClientManager jobClientManager;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 查询 定时任务详情
|
||||||
|
*
|
||||||
|
* @param jobId
|
||||||
|
* @return
|
||||||
|
*/
|
||||||
|
public ResponseDTO<SmartJobVO> queryJobInfo(Integer jobId) {
|
||||||
|
SmartJobEntity jobEntity = jobDao.selectById(jobId);
|
||||||
|
if (null == jobEntity) {
|
||||||
|
return ResponseDTO.error(UserErrorCode.DATA_NOT_EXIST);
|
||||||
|
}
|
||||||
|
SmartJobVO jobVO = SmartBeanUtil.copy(jobEntity, SmartJobVO.class);
|
||||||
|
// 处理设置job详情
|
||||||
|
this.handleJobInfo(Lists.newArrayList(jobVO));
|
||||||
|
return ResponseDTO.ok(jobVO);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 分页查询 定时任务
|
||||||
|
*
|
||||||
|
* @param queryForm
|
||||||
|
* @return
|
||||||
|
*/
|
||||||
|
public ResponseDTO<PageResult<SmartJobVO>> queryJob(SmartJobQueryForm queryForm) {
|
||||||
|
Page<?> page = SmartPageUtil.convert2PageQuery(queryForm);
|
||||||
|
List<SmartJobVO> jobList = jobDao.query(page, queryForm);
|
||||||
|
PageResult<SmartJobVO> pageResult = SmartPageUtil.convert2PageResult(page, jobList);
|
||||||
|
// 处理设置job详情
|
||||||
|
this.handleJobInfo(jobList);
|
||||||
|
return ResponseDTO.ok(pageResult);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 处理设置 任务信息
|
||||||
|
*
|
||||||
|
* @param jobList
|
||||||
|
*/
|
||||||
|
private void handleJobInfo(List<SmartJobVO> jobList) {
|
||||||
|
if (CollectionUtils.isEmpty(jobList)) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
// 查询最后一次执行记录
|
||||||
|
List<Long> logIdList = jobList.stream().map(SmartJobVO::getLastExecuteLogId).filter(Objects::nonNull).collect(Collectors.toList());
|
||||||
|
Map<Long, SmartJobLogVO> lastLogMap = Collections.emptyMap();
|
||||||
|
if (CollectionUtils.isNotEmpty(logIdList)) {
|
||||||
|
lastLogMap = jobLogDao.selectBatchIds(logIdList)
|
||||||
|
.stream()
|
||||||
|
.collect(Collectors.toMap(SmartJobLogEntity::getLogId, e -> SmartBeanUtil.copy(e, SmartJobLogVO.class)));
|
||||||
|
}
|
||||||
|
|
||||||
|
// 循环处理任务信息
|
||||||
|
for (SmartJobVO jobVO : jobList) {
|
||||||
|
// 设置最后一次执行记录
|
||||||
|
Long lastExecuteLogId = jobVO.getLastExecuteLogId();
|
||||||
|
if (null != lastExecuteLogId) {
|
||||||
|
jobVO.setLastJobLog(lastLogMap.get(lastExecuteLogId));
|
||||||
|
}
|
||||||
|
// 计算未来5次执行时间
|
||||||
|
if (jobVO.getEnabledFlag()) {
|
||||||
|
List<LocalDateTime> nextTimeList = SmartJobUtil.queryNextTimeFromNow(jobVO.getTriggerType(), jobVO.getTriggerValue(), jobVO.getLastExecuteTime(), 5);
|
||||||
|
jobVO.setNextJobExecuteTimeList(nextTimeList);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 分页查询 定时任务-执行记录
|
||||||
|
*
|
||||||
|
* @param queryForm
|
||||||
|
* @return
|
||||||
|
*/
|
||||||
|
public ResponseDTO<PageResult<SmartJobLogVO>> queryJobLog(SmartJobLogQueryForm queryForm) {
|
||||||
|
Page<?> page = SmartPageUtil.convert2PageQuery(queryForm);
|
||||||
|
List<SmartJobLogVO> jobList = jobLogDao.query(page, queryForm);
|
||||||
|
PageResult<SmartJobLogVO> pageResult = SmartPageUtil.convert2PageResult(page, jobList);
|
||||||
|
return ResponseDTO.ok(pageResult);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 更新定时任务
|
||||||
|
*
|
||||||
|
* @param updateForm
|
||||||
|
* @return
|
||||||
|
*/
|
||||||
|
public ResponseDTO<String> updateJob(SmartJobUpdateForm updateForm) {
|
||||||
|
// 校验参数
|
||||||
|
Integer jobId = updateForm.getJobId();
|
||||||
|
SmartJobEntity jobEntity = jobDao.selectById(jobId);
|
||||||
|
if (null == jobEntity) {
|
||||||
|
return ResponseDTO.error(UserErrorCode.DATA_NOT_EXIST);
|
||||||
|
}
|
||||||
|
// 校验触发时间配置
|
||||||
|
String triggerType = updateForm.getTriggerType();
|
||||||
|
String triggerValue = updateForm.getTriggerValue();
|
||||||
|
if (SmartJobTriggerTypeEnum.CRON.equalsValue(triggerType) && !SmartJobUtil.checkCron(triggerValue)) {
|
||||||
|
return ResponseDTO.userErrorParam("cron表达式错误");
|
||||||
|
}
|
||||||
|
if (SmartJobTriggerTypeEnum.FIXED_DELAY.equalsValue(triggerType) && !SmartJobUtil.checkFixedDelay(triggerValue)) {
|
||||||
|
return ResponseDTO.userErrorParam("固定间隔错误:整数且大于0");
|
||||||
|
}
|
||||||
|
|
||||||
|
// 更新数据
|
||||||
|
jobEntity = SmartBeanUtil.copy(updateForm, SmartJobEntity.class);
|
||||||
|
jobDao.updateById(jobEntity);
|
||||||
|
|
||||||
|
// 更新执行端
|
||||||
|
SmartJobMsg jobMsg = new SmartJobMsg();
|
||||||
|
jobMsg.setJobId(jobId);
|
||||||
|
jobMsg.setMsgType(SmartJobMsg.MsgTypeEnum.UPDATE_JOB);
|
||||||
|
jobMsg.setUpdateName(updateForm.getUpdateName());
|
||||||
|
jobClientManager.publishToClient(jobMsg);
|
||||||
|
return ResponseDTO.ok();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 更新定时任务-是否开启
|
||||||
|
*
|
||||||
|
* @param updateForm
|
||||||
|
* @return
|
||||||
|
*/
|
||||||
|
public ResponseDTO<String> updateJobEnabled(SmartJobEnabledUpdateForm updateForm) {
|
||||||
|
Integer jobId = updateForm.getJobId();
|
||||||
|
SmartJobEntity jobEntity = jobDao.selectById(jobId);
|
||||||
|
if (null == jobEntity) {
|
||||||
|
return ResponseDTO.error(UserErrorCode.DATA_NOT_EXIST);
|
||||||
|
}
|
||||||
|
Boolean enabledFlag = updateForm.getEnabledFlag();
|
||||||
|
if (Objects.equals(enabledFlag, jobEntity.getEnabledFlag())) {
|
||||||
|
return ResponseDTO.ok();
|
||||||
|
}
|
||||||
|
// 更新数据
|
||||||
|
jobEntity = new SmartJobEntity();
|
||||||
|
jobEntity.setJobId(jobId);
|
||||||
|
jobEntity.setEnabledFlag(enabledFlag);
|
||||||
|
jobEntity.setUpdateName(updateForm.getUpdateName());
|
||||||
|
jobDao.updateById(jobEntity);
|
||||||
|
|
||||||
|
// 更新执行端
|
||||||
|
SmartJobMsg jobMsg = new SmartJobMsg();
|
||||||
|
jobMsg.setJobId(jobId);
|
||||||
|
jobMsg.setMsgType(SmartJobMsg.MsgTypeEnum.UPDATE_JOB);
|
||||||
|
jobMsg.setUpdateName(updateForm.getUpdateName());
|
||||||
|
jobClientManager.publishToClient(jobMsg);
|
||||||
|
return ResponseDTO.ok();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 执行定时任务
|
||||||
|
* 忽略任务的开启状态,立即执行一次
|
||||||
|
*
|
||||||
|
* @param executeForm
|
||||||
|
* @return
|
||||||
|
*/
|
||||||
|
public ResponseDTO<String> execute(SmartJobExecuteForm executeForm) {
|
||||||
|
Integer jobId = executeForm.getJobId();
|
||||||
|
SmartJobEntity jobEntity = jobDao.selectById(jobId);
|
||||||
|
if (null == jobEntity) {
|
||||||
|
return ResponseDTO.error(UserErrorCode.DATA_NOT_EXIST);
|
||||||
|
}
|
||||||
|
|
||||||
|
// 更新执行端
|
||||||
|
SmartJobMsg jobMsg = new SmartJobMsg();
|
||||||
|
jobMsg.setJobId(jobId);
|
||||||
|
jobMsg.setParam(executeForm.getParam());
|
||||||
|
jobMsg.setMsgType(SmartJobMsg.MsgTypeEnum.EXECUTE_JOB);
|
||||||
|
jobMsg.setUpdateName(executeForm.getUpdateName());
|
||||||
|
jobClientManager.publishToClient(jobMsg);
|
||||||
|
return ResponseDTO.ok();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 新增定时任务
|
||||||
|
* ps:目前没有业务场景需要通过接口 添加任务
|
||||||
|
* 因为新增定时任务无论如何都需要 手动编码
|
||||||
|
* 需要时手动给数据库增加一条就行
|
||||||
|
*
|
||||||
|
* @return
|
||||||
|
* @author huke
|
||||||
|
*/
|
||||||
|
public ResponseDTO<String> addJob() {
|
||||||
|
return ResponseDTO.userErrorParam("暂未支持");
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 移除定时任务
|
||||||
|
* ps:目前没有业务场景需要通过接口移除,理由同 {@link SmartJobService#addJob},
|
||||||
|
* 彻底移除始终都需要手动删除代码
|
||||||
|
* 如果只是想暂停任务执行,可以调用 {@link SmartJobService#updateJobEnabled}
|
||||||
|
*
|
||||||
|
* @return
|
||||||
|
* @author huke
|
||||||
|
*/
|
||||||
|
public ResponseDTO<String> delJob() {
|
||||||
|
return ResponseDTO.userErrorParam("暂未支持");
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -0,0 +1,27 @@
|
|||||||
|
package net.lab1024.sa.base.module.support.job.api.domain;
|
||||||
|
|
||||||
|
import io.swagger.v3.oas.annotations.media.Schema;
|
||||||
|
import lombok.Data;
|
||||||
|
|
||||||
|
import javax.validation.constraints.NotNull;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 定时任务-更新-开启状态
|
||||||
|
*
|
||||||
|
* @author huke
|
||||||
|
* @date 2024/6/17 21:30
|
||||||
|
*/
|
||||||
|
@Data
|
||||||
|
public class SmartJobEnabledUpdateForm {
|
||||||
|
|
||||||
|
@Schema(description = "任务id")
|
||||||
|
@NotNull(message = "任务id不能为空")
|
||||||
|
private Integer jobId;
|
||||||
|
|
||||||
|
@Schema(description = "是否启用")
|
||||||
|
@NotNull(message = "是否启用不能为空")
|
||||||
|
private Boolean enabledFlag;
|
||||||
|
|
||||||
|
@Schema(hidden = true)
|
||||||
|
private String updateName;
|
||||||
|
}
|
||||||
@@ -0,0 +1,28 @@
|
|||||||
|
package net.lab1024.sa.base.module.support.job.api.domain;
|
||||||
|
|
||||||
|
import io.swagger.v3.oas.annotations.media.Schema;
|
||||||
|
import lombok.Data;
|
||||||
|
import org.hibernate.validator.constraints.Length;
|
||||||
|
|
||||||
|
import javax.validation.constraints.NotNull;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 定时任务-手动执行
|
||||||
|
*
|
||||||
|
* @author huke
|
||||||
|
* @date 2024/6/18 20:30
|
||||||
|
*/
|
||||||
|
@Data
|
||||||
|
public class SmartJobExecuteForm {
|
||||||
|
|
||||||
|
@Schema(description = "任务id")
|
||||||
|
@NotNull(message = "任务id不能为空")
|
||||||
|
private Integer jobId;
|
||||||
|
|
||||||
|
@Schema(description = "定时任务参数|可选")
|
||||||
|
@Length(max = 2000, message = "定时任务参数最多2000字符")
|
||||||
|
private String param;
|
||||||
|
|
||||||
|
@Schema(hidden = true)
|
||||||
|
private String updateName;
|
||||||
|
}
|
||||||
@@ -0,0 +1,34 @@
|
|||||||
|
package net.lab1024.sa.base.module.support.job.api.domain;
|
||||||
|
|
||||||
|
import io.swagger.v3.oas.annotations.media.Schema;
|
||||||
|
import lombok.Data;
|
||||||
|
import net.lab1024.sa.base.common.domain.PageParam;
|
||||||
|
import org.hibernate.validator.constraints.Length;
|
||||||
|
|
||||||
|
import java.time.LocalDate;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 定时任务-执行记录 分页查询
|
||||||
|
*
|
||||||
|
* @author huke
|
||||||
|
* @date 2024/6/17 20:50
|
||||||
|
*/
|
||||||
|
@Data
|
||||||
|
public class SmartJobLogQueryForm extends PageParam {
|
||||||
|
|
||||||
|
@Schema(description = "搜索词|可选")
|
||||||
|
@Length(max = 50, message = "搜索词最多50字符")
|
||||||
|
private String searchWord;
|
||||||
|
|
||||||
|
@Schema(description = "任务id|可选")
|
||||||
|
private Integer jobId;
|
||||||
|
|
||||||
|
@Schema(description = "是否成功|可选")
|
||||||
|
private Boolean successFlag;
|
||||||
|
|
||||||
|
@Schema(description = "开始时间|可选", example = "2024-06-06")
|
||||||
|
private LocalDate startTime;
|
||||||
|
|
||||||
|
@Schema(description = "截止时间|可选", example = "2025-10-15")
|
||||||
|
private LocalDate endTime;
|
||||||
|
}
|
||||||
@@ -0,0 +1,56 @@
|
|||||||
|
package net.lab1024.sa.base.module.support.job.api.domain;
|
||||||
|
|
||||||
|
import io.swagger.v3.oas.annotations.media.Schema;
|
||||||
|
import lombok.Data;
|
||||||
|
|
||||||
|
import java.time.LocalDateTime;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 定时任务-执行记录 vo
|
||||||
|
*
|
||||||
|
* @author huke
|
||||||
|
* @date 2024/6/17 21:30
|
||||||
|
*/
|
||||||
|
@Data
|
||||||
|
public class SmartJobLogVO {
|
||||||
|
|
||||||
|
@Schema(description = "logId")
|
||||||
|
private Long logId;
|
||||||
|
|
||||||
|
@Schema(description = "任务id")
|
||||||
|
private Integer jobId;
|
||||||
|
|
||||||
|
@Schema(description = "任务名称")
|
||||||
|
private String jobName;
|
||||||
|
|
||||||
|
@Schema(description = "定时任务参数|可选")
|
||||||
|
private String param;
|
||||||
|
|
||||||
|
@Schema(description = "执行结果是否成功")
|
||||||
|
private Boolean successFlag;
|
||||||
|
|
||||||
|
@Schema(description = "开始执行时间")
|
||||||
|
private LocalDateTime executeStartTime;
|
||||||
|
|
||||||
|
@Schema(description = "执行时长-毫秒")
|
||||||
|
private Long executeTimeMillis;
|
||||||
|
|
||||||
|
@Schema(description = "执行结果描述")
|
||||||
|
private String executeResult;
|
||||||
|
|
||||||
|
@Schema(description = "执行结束时间")
|
||||||
|
private LocalDateTime executeEndTime;
|
||||||
|
|
||||||
|
@Schema(description = "ip")
|
||||||
|
private String ip;
|
||||||
|
|
||||||
|
@Schema(description = "进程id")
|
||||||
|
private String processId;
|
||||||
|
|
||||||
|
@Schema(description = "程序目录")
|
||||||
|
private String programPath;
|
||||||
|
|
||||||
|
private String createName;
|
||||||
|
|
||||||
|
private LocalDateTime createTime;
|
||||||
|
}
|
||||||
@@ -0,0 +1,59 @@
|
|||||||
|
package net.lab1024.sa.base.module.support.job.api.domain;
|
||||||
|
|
||||||
|
import lombok.AllArgsConstructor;
|
||||||
|
import lombok.Data;
|
||||||
|
import lombok.Getter;
|
||||||
|
import net.lab1024.sa.base.common.enumeration.BaseEnum;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 定时任务 发布/订阅消息对象
|
||||||
|
*
|
||||||
|
* @author huke
|
||||||
|
* @date 2024/6/20 21:10
|
||||||
|
*/
|
||||||
|
@Data
|
||||||
|
public class SmartJobMsg {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 消息id 无需设置
|
||||||
|
*/
|
||||||
|
private String msgId;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 任务id
|
||||||
|
*/
|
||||||
|
private Integer jobId;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 任务参数
|
||||||
|
*/
|
||||||
|
private String param;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 消息类型
|
||||||
|
*/
|
||||||
|
private MsgTypeEnum msgType;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 更新人
|
||||||
|
*/
|
||||||
|
private String updateName;
|
||||||
|
|
||||||
|
@Getter
|
||||||
|
@AllArgsConstructor
|
||||||
|
public enum MsgTypeEnum implements BaseEnum {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 1 更新任务
|
||||||
|
*/
|
||||||
|
UPDATE_JOB(1, "更新任务"),
|
||||||
|
|
||||||
|
EXECUTE_JOB(2, "执行任务"),
|
||||||
|
|
||||||
|
;
|
||||||
|
|
||||||
|
private final Integer value;
|
||||||
|
|
||||||
|
private final String desc;
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -0,0 +1,30 @@
|
|||||||
|
package net.lab1024.sa.base.module.support.job.api.domain;
|
||||||
|
|
||||||
|
import io.swagger.v3.oas.annotations.media.Schema;
|
||||||
|
import lombok.Data;
|
||||||
|
import net.lab1024.sa.base.common.domain.PageParam;
|
||||||
|
import net.lab1024.sa.base.common.swagger.SchemaEnum;
|
||||||
|
import net.lab1024.sa.base.common.validator.enumeration.CheckEnum;
|
||||||
|
import net.lab1024.sa.base.module.support.job.constant.SmartJobTriggerTypeEnum;
|
||||||
|
import org.hibernate.validator.constraints.Length;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 定时任务 分页查询
|
||||||
|
*
|
||||||
|
* @author huke
|
||||||
|
* @date 2024/6/17 20:50
|
||||||
|
*/
|
||||||
|
@Data
|
||||||
|
public class SmartJobQueryForm extends PageParam {
|
||||||
|
|
||||||
|
@Schema(description = "搜索词|可选")
|
||||||
|
@Length(max = 50, message = "搜索词最多50字符")
|
||||||
|
private String searchWord;
|
||||||
|
|
||||||
|
@SchemaEnum(desc = "触发类型", value = SmartJobTriggerTypeEnum.class)
|
||||||
|
@CheckEnum(value = SmartJobTriggerTypeEnum.class, message = "触发类型错误")
|
||||||
|
private String triggerType;
|
||||||
|
|
||||||
|
@Schema(description = "是否启用|可选")
|
||||||
|
private Boolean enabledFlag;
|
||||||
|
}
|
||||||
@@ -0,0 +1,63 @@
|
|||||||
|
package net.lab1024.sa.base.module.support.job.api.domain;
|
||||||
|
|
||||||
|
import io.swagger.v3.oas.annotations.media.Schema;
|
||||||
|
import lombok.Data;
|
||||||
|
import net.lab1024.sa.base.common.swagger.SchemaEnum;
|
||||||
|
import net.lab1024.sa.base.common.validator.enumeration.CheckEnum;
|
||||||
|
import net.lab1024.sa.base.module.support.job.constant.SmartJobTriggerTypeEnum;
|
||||||
|
import org.hibernate.validator.constraints.Length;
|
||||||
|
|
||||||
|
import javax.validation.constraints.NotBlank;
|
||||||
|
import javax.validation.constraints.NotNull;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 定时任务 更新
|
||||||
|
*
|
||||||
|
* @author huke
|
||||||
|
* @date 2024/6/17 21:30
|
||||||
|
*/
|
||||||
|
@Data
|
||||||
|
public class SmartJobUpdateForm {
|
||||||
|
|
||||||
|
@Schema(description = "任务id")
|
||||||
|
@NotNull(message = "任务id不能为空")
|
||||||
|
private Integer jobId;
|
||||||
|
|
||||||
|
@Schema(description = "任务名称")
|
||||||
|
@NotBlank(message = "任务名称不能为空")
|
||||||
|
@Length(max = 100, message = "任务名称最多100字符")
|
||||||
|
private String jobName;
|
||||||
|
|
||||||
|
@Schema(description = "任务执行类")
|
||||||
|
@NotBlank(message = "任务执行类不能为空")
|
||||||
|
@Length(max = 200, message = "任务执行类最多200字符")
|
||||||
|
private String jobClass;
|
||||||
|
|
||||||
|
@SchemaEnum(desc = "触发类型", value = SmartJobTriggerTypeEnum.class)
|
||||||
|
@CheckEnum(value = SmartJobTriggerTypeEnum.class, required = true, message = "触发类型错误")
|
||||||
|
private String triggerType;
|
||||||
|
|
||||||
|
@Schema(description = "触发配置")
|
||||||
|
@NotBlank(message = "触发配置不能为空")
|
||||||
|
@Length(max = 100, message = "触发配置最多100字符")
|
||||||
|
private String triggerValue;
|
||||||
|
|
||||||
|
@Schema(description = "定时任务参数|可选")
|
||||||
|
@Length(max = 1000, message = "定时任务参数最多1000字符")
|
||||||
|
private String param;
|
||||||
|
|
||||||
|
@Schema(description = "是否开启")
|
||||||
|
@NotNull(message = "是否开启不能为空")
|
||||||
|
private Boolean enabledFlag;
|
||||||
|
|
||||||
|
@Schema(description = "备注")
|
||||||
|
@Length(max = 250, message = "任务备注最多250字符")
|
||||||
|
private String remark;
|
||||||
|
|
||||||
|
@NotNull(message = "排序不能为空")
|
||||||
|
@Schema(description = "排序")
|
||||||
|
private Integer sort;
|
||||||
|
|
||||||
|
@Schema(hidden = true)
|
||||||
|
private String updateName;
|
||||||
|
}
|
||||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user