This commit is contained in:
2026-01-22 16:00:00 +08:00
20 changed files with 165 additions and 91 deletions

View File

@@ -6,7 +6,7 @@ spring:
name: capability
datasource:
username: root
password: mysql
password: ENC(o5nKvbyfceJryxfBBGTi9w==)
jdbc-url: jdbc:mysql://192.168.30.146:3306/spdm_baseline?useUnicode=true&characterEncoding=utf-8&useSSL=true&serverTimezone=Asia/Shanghai
driver-class-name: com.mysql.cj.jdbc.Driver
hikari:
@@ -17,12 +17,12 @@ spring:
connection-timeout: 30000 # 获取连接超时时间30秒避免线程阻塞
master:
username: root
password: mysql
password: ENC(o5nKvbyfceJryxfBBGTi9w==)
jdbc-url: jdbc:mysql://192.168.30.146:3306/spdm_baseline?useUnicode=true&characterEncoding=utf-8&useSSL=true&serverTimezone=Asia/Shanghai
driver-class-name: com.mysql.cj.jdbc.Driver
slave:
username: root
password: mysql
password: ENC(o5nKvbyfceJryxfBBGTi9w==)
jdbc-url: jdbc:mysql://192.168.30.146:3306/spdm_baseline?useUnicode=true&characterEncoding=utf-8&useSSL=true&serverTimezone=Asia/Shanghai
driver-class-name: com.mysql.cj.jdbc.Driver
enable: true

View File

@@ -207,13 +207,14 @@ public class AESUtil {
public static void main(String[] args) {
try {
// 优先读取JVM参数然后环境变量参数没有就报错
// String spdmEnkey = "H7qGt/DO3VdaAVKzY3PNvQ==";
String spdmEnkey = StringUtils.isBlank(System.getProperty("spdm.enkey"))?
System.getenv("spdm.enkey"):System.getProperty("spdm.enkey");
if(StringUtils.isBlank(spdmEnkey)){
throw new RuntimeException("spdm加密配置密钥读取失败");
}
System.out.println("密钥是:"+spdmEnkey);
String ret = encodeNew("我是原文8899",spdmEnkey);
String ret = encodeNew("EP_DM@123.COM",spdmEnkey);
System.out.println("encode:" + ret);
String raw = decodeNew(ret,spdmEnkey);
System.out.println("decode:" + raw);

View File

@@ -0,0 +1,54 @@
package com.sdm.common.utils;
import javax.crypto.SecretKey;
import javax.crypto.SecretKeyFactory;
import javax.crypto.spec.PBEKeySpec;
import javax.crypto.spec.SecretKeySpec;
import java.security.spec.KeySpec;
import java.util.Base64;
public class RandomByteUtils {
public static void main(String[] args) throws Exception {
// 你的原始12字节密钥
byte[] original12BytesKey = new byte[12];
// 示例填充随机值模拟你的12字节密钥实际替换为你的真实密钥
new java.security.SecureRandom().nextBytes(original12BytesKey);
// 方案1将12字节密钥扩展为16字节128位的合法AES密钥
SecretKey validAesKey = generateValidAesKey(original12BytesKey, 16);
// 验证密钥长度输出16
byte[] encoded = validAesKey.getEncoded();
System.out.println("合法AES密钥:"+Base64.getEncoder().encodeToString(encoded));
System.out.println("合法AES密钥长度字节: " + validAesKey.getEncoded().length);
}
/**
* 将任意长度的原始密钥派生为指定长度的合法AES密钥
* @param originalKey 原始密钥如12字节
* @param targetLength 目标长度16/24/32
* @return 合法AES密钥
*/
private static SecretKey generateValidAesKey(byte[] originalKey, int targetLength) throws Exception {
// 盐值(随机生成,实际使用时建议固定或持久化)
byte[] salt = new byte[16];
new java.security.SecureRandom().nextBytes(salt);
// PBKDF2密钥派生参数迭代次数建议≥10000
KeySpec spec = new PBEKeySpec(
new String(originalKey).toCharArray(), // 原始密钥转为字符数组
salt, // 盐值
65536, // 迭代次数
targetLength * 8 // 目标密钥长度(位)
);
// 生成派生密钥
SecretKeyFactory factory = SecretKeyFactory.getInstance("PBKDF2WithHmacSHA256");
byte[] derivedKey = factory.generateSecret(spec).getEncoded();
// 转换为AES密钥
return new SecretKeySpec(derivedKey, "AES");
}
}

View File

@@ -6,7 +6,7 @@ spring:
name: data
datasource:
username: root
password: mysql
password: ENC(o5nKvbyfceJryxfBBGTi9w==)
jdbc-url: jdbc:mysql://192.168.30.146:3306/spdm_baseline?useUnicode=true&characterEncoding=utf-8&useSSL=true&serverTimezone=Asia/Shanghai
driver-class-name: com.mysql.cj.jdbc.Driver
hikari:
@@ -22,12 +22,12 @@ spring:
connection-timeout: 30000 # 30s
master:
username: root
password: mysql
password: ENC(o5nKvbyfceJryxfBBGTi9w==)
jdbc-url: jdbc:mysql://192.168.30.146:3306/spdm_baseline?useUnicode=true&characterEncoding=utf-8&useSSL=true&serverTimezone=Asia/Shanghai
driver-class-name: com.mysql.cj.jdbc.Driver
slave:
username: root
password: mysql
password: ENC(o5nKvbyfceJryxfBBGTi9w==)
jdbc-url: jdbc:mysql://192.168.30.146:3306/spdm_baseline?useUnicode=true&characterEncoding=utf-8&useSSL=true&serverTimezone=Asia/Shanghai
driver-class-name: com.mysql.cj.jdbc.Driver
enable: true

View File

@@ -6,7 +6,7 @@ spring:
datasource:
url: jdbc:mysql://192.168.30.146:3306/flowable?useUnicode=true&characterEncoding=UTF-8&serverTimezone=Asia/Shanghai
username: root
password: mysql
password: ENC(o5nKvbyfceJryxfBBGTi9w==)
driver-class-name: com.mysql.cj.jdbc.Driver
flowable:
# ?????????

View File

@@ -2,12 +2,9 @@ spring:
datasource:
second:
username: EP_DM
password: EP_DM@123.COM
# username: root
# password: mysql
password: ENC(c04rt9Z6Ygz024EU9eWvig==)
# todo 生产地址
jdbc-url: jdbc:mysql://10.122.48.11:13306/easy_project?useUnicode=true&characterEncoding=utf-8&useSSL=true&serverTimezone=Asia/Shanghai
# jdbc-url: jdbc:mysql://127.0.0.1:3306/second_db?useUnicode=true&characterEncoding=utf-8&useSSL=true&serverTimezone=Asia/Shanghai
driver-class-name: com.mysql.cj.jdbc.Driver
# 测试开发环境

View File

@@ -6,7 +6,7 @@ spring:
name: pbs
datasource:
username: root
password: mysql
password: ENC(o5nKvbyfceJryxfBBGTi9w==)
jdbc-url: jdbc:mysql://192.168.30.146:3306/spdm_baseline?useUnicode=true&characterEncoding=utf-8&useSSL=true&serverTimezone=Asia/Shanghai
driver-class-name: com.mysql.cj.jdbc.Driver
hikari:
@@ -22,12 +22,12 @@ spring:
connection-timeout: 30000 # 30s
master:
username: root
password: mysql
password: ENC(o5nKvbyfceJryxfBBGTi9w==)
jdbc-url: jdbc:mysql://192.168.30.146:3306/spdm_baseline?useUnicode=true&characterEncoding=utf-8&useSSL=true&serverTimezone=Asia/Shanghai
driver-class-name: com.mysql.cj.jdbc.Driver
slave:
username: root
password: mysql
password: ENC(o5nKvbyfceJryxfBBGTi9w==)
jdbc-url: jdbc:mysql://192.168.30.146:3306/spdm_baseline?useUnicode=true&characterEncoding=utf-8&useSSL=true&serverTimezone=Asia/Shanghai
driver-class-name: com.mysql.cj.jdbc.Driver
enable: true

View File

@@ -162,6 +162,7 @@ public class TaskNodePo extends NodeAllBase {
@JsonProperty("bCapacity")
private String bCapacity;
private String flowTemplate;
private String flowTemplateName;
private String englishName;
private String description;

View File

@@ -200,7 +200,7 @@ public class NodeServiceImpl extends ServiceImpl<SimulationNodeMapper, Simulatio
String nodeType = addNode.getNodeType();
if (SYNC_PROJECT_SOURCE.equals(projectSource) && NodeTypeEnum.PROJECT.getValue().equals(nodeType)) {
// 同步待办信息
getTodoListByProjectNum(addNode.getNodeCode());
getTodoListByProjectNum(addNode.getNodeCode(),addNodeList);
// TODO 同步主计划信息
// getMainPlanListByProjectId(addNode.getProjectId(),addNode.getUuid());
}
@@ -1984,7 +1984,7 @@ public class NodeServiceImpl extends ServiceImpl<SimulationNodeMapper, Simulatio
return SdmResponse.success();
}
public SdmResponse getTodoListByProjectNum(String projectNum) {
public SdmResponse getTodoListByProjectNum(String projectNum,List<SpdmProjectNodeEditReq> allNodeList) {
log.info("同步代办时,项目号为:{}", projectNum);
if (StringUtils.isBlank(projectNum)) {
log.error("同步待办时,项目号不能为空");
@@ -2032,31 +2032,19 @@ public class NodeServiceImpl extends ServiceImpl<SimulationNodeMapper, Simulatio
spdmAddDemandReq.setProgress(0);
spdmAddDemandReq.setBeginTime(emulation.getPlanStartTime());
spdmAddDemandReq.setEndTime(emulation.getClosedTime());
List<String> projectCodeList = todoInfoList.stream().map(LyricVTodoEmulationInfoDM::getProject).filter(StringUtils::isNotBlank).toList();
List<SimulationNode> allNodeList = new ArrayList<>();
if (CollectionUtils.isNotEmpty(projectCodeList)) {
List<SimulationNode> allProjectNodeList = this.lambdaQuery().in(SimulationNode::getNodeCode, projectCodeList).list();
if (CollectionUtils.isNotEmpty(allNodeList)) {
List<String> projectIdList = allProjectNodeList.stream().map(SimulationNode::getUuid).toList();
allNodeList = this.lambdaQuery().in(SimulationNode::getTag1,projectIdList).list();
}
}
if (CollectionUtils.isNotEmpty(allNodeList)) {
String projectNode = emulation.getProject();
String phaseNode = emulation.getProjectStage();
String workspaceNode = emulation.getStationNum();
Optional<SimulationNode> projectOptional = allNodeList.stream().filter(node -> node.getNodeCode().equals(projectNode)
&& NodeTypeEnum.PROJECT.getValue().equals(node.getNodeType())).findFirst();
Optional<SimulationNode> phaseOptional = allNodeList.stream().filter(node -> node.getNodeCode().equals(phaseNode)
&& NodeTypeEnum.PHASE.getValue().equals(node.getNodeType())).findFirst();
Optional<SimulationNode> workspaceOptional = allNodeList.stream().filter(node -> node.getNodeCode().equals(workspaceNode)
&& NodeTypeEnum.WORKSPACE.getValue().equals(node.getNodeType())).findFirst();
// 转换为project的uuid
projectOptional.ifPresent(simulationNode -> spdmAddDemandReq.setProjectId(simulationNode.getUuid()));
phaseOptional.ifPresent(simulationNode -> spdmAddDemandReq.setPhaseId(simulationNode.getUuid()));
workspaceOptional.ifPresent(simulationNode -> spdmAddDemandReq.setNodeId(simulationNode.getUuid()));
}
String projectNode = emulation.getProject();
String phaseNode = emulation.getProjectStage();
String workspaceNode = emulation.getStationNum();
Optional<SpdmProjectNodeEditReq> projectOptional = allNodeList.stream().filter(node -> node.getNodeCode().equals(projectNode)
&& NodeTypeEnum.PROJECT.getValue().equals(node.getNodeType())).findFirst();
Optional<SpdmProjectNodeEditReq> phaseOptional = allNodeList.stream().filter(node -> node.getNodeCode().equals(phaseNode)
&& NodeTypeEnum.PHASE.getValue().equals(node.getNodeType())).findFirst();
Optional<SpdmProjectNodeEditReq> workspaceOptional = allNodeList.stream().filter(node -> node.getNodeCode().equals(workspaceNode)
&& NodeTypeEnum.WORKSPACE.getValue().equals(node.getNodeType())).findFirst();
// 转换为project的uuid
projectOptional.ifPresent(simulationNode -> spdmAddDemandReq.setProjectId(simulationNode.getUuid()));
phaseOptional.ifPresent(simulationNode -> spdmAddDemandReq.setPhaseId(simulationNode.getUuid()));
workspaceOptional.ifPresent(simulationNode -> spdmAddDemandReq.setNodeId(simulationNode.getUuid()));
spdmAddDemandReq.setCreateTime(curDateStr);
spdmAddDemandReq.setDemandSource(SYNC_PROJECT_SOURCE);
// 需求的成员

View File

@@ -15,10 +15,12 @@ import com.sdm.common.entity.req.system.SendMsgReq;
import com.sdm.common.entity.req.system.UserQueryReq;
import com.sdm.common.entity.req.task.TaskTreeExportExcelFormat;
import com.sdm.common.entity.req.task.TaskTreeExportExcelParam;
import com.sdm.common.entity.resp.capability.FlowTemplateResp;
import com.sdm.common.entity.resp.data.FileMetadataInfoResp;
import com.sdm.common.entity.resp.project.SpdmTaskVo;
import com.sdm.common.entity.resp.project.TaskNodeExtraPo;
import com.sdm.common.entity.resp.system.CIDUserResp;
import com.sdm.common.feign.impl.capability.SimulationFlowFeignClientImpl;
import com.sdm.common.feign.impl.data.DataClientFeignClientImpl;
import com.sdm.common.feign.impl.system.MessageFeignClientImpl;
import com.sdm.common.feign.impl.system.SysUserFeignClientImpl;
@@ -111,6 +113,9 @@ public class ProjectServiceImpl extends BaseService implements IProjectService {
@Autowired
private LyricVProjectStationPlanToDmService lyricVProjectStationPlanToDmService;
@Autowired
private SimulationFlowFeignClientImpl flowFeignClient;
@Value("${commitmentDeadlineStatusTask.schedule.calculationInterval:5}")
private int calculationInterval;
@@ -725,6 +730,21 @@ public class ProjectServiceImpl extends BaseService implements IProjectService {
}
taskNodePo.setStandardName(String.join(";", fileNameList));
}
if (StringUtils.isNotBlank(taskNodePo.getFlowTemplate())) {
// 转换模板名称
List<String> flowTemplateNameList = new ArrayList<>();
String[] flowTemplateArr = taskNodePo.getFlowTemplate().split(",");
for (String flowTemplate : flowTemplateArr) {
SdmResponse<FlowTemplateResp> flowTemplateResp = flowFeignClient.queryFlowTemplateInfoByTemplateCode(flowTemplate);
if (flowTemplateResp.getData() == null) {
continue;
}
flowTemplateNameList.add(flowTemplateResp.getData().getTemplateName());
}
if (CollectionUtils.isNotEmpty(flowTemplateNameList)) {
taskNodePo.setFlowTemplateName(String.join(",", flowTemplateNameList));
}
}
}
// 查询当前任务下指标
@@ -1792,6 +1812,7 @@ public class ProjectServiceImpl extends BaseService implements IProjectService {
projectNodeList.forEach(node ->
{
node.setCreateTime(curDateStr);
node.setCreator(userId);
node.setOwnRootNodeUuid(ownRootNodeUuid);
});
@@ -1854,7 +1875,7 @@ public class ProjectServiceImpl extends BaseService implements IProjectService {
if (CollectionUtils.isNotEmpty(taskNodeList)) {
taskNodeList.forEach(projectNode -> {
// projectNode.setCreator(jobNumber);
projectNode.setCreator(userId);
projectNode.setCreateTime(createTime);
});
if (mapper.batchAddSimulationTask(taskNodeList) <= 0) {
@@ -1923,7 +1944,10 @@ public class ProjectServiceImpl extends BaseService implements IProjectService {
}
}
if (CollectionUtils.isNotEmpty(projectNodePerformanceList)) {
projectNodePerformanceList.forEach(projectNode -> projectNode.setCreateTime(createTime));
projectNodePerformanceList.forEach(projectNode -> {
projectNode.setCreator(userId);
projectNode.setCreateTime(createTime);
});
if (mapper.batchAddSimulationPerformance(projectNodePerformanceList) <= 0) {
response = SdmResponse.failed("新增指标失败");
return response;

View File

@@ -778,6 +778,7 @@ public class TaskServiceImpl implements ITaskService {
}
List<String> myTaskIdList = taskAttentionMemberVoList.stream().map(SpdmTaskAttentionMemberVo::getTaskId).toList();
taskList = taskList.stream().filter(task -> myTaskIdList.contains(task.getUuid())).toList();
todayTmrTaskList = todayTmrTaskList.stream().filter(task -> myTaskIdList.contains(task.getUuid())).toList();
countTask(taskList, todayTmrTaskList, taskCountResp);
}
}
@@ -2839,7 +2840,7 @@ public class TaskServiceImpl implements ITaskService {
log.info("flowTemplate为{}",spdmExportNewTaskVo.getFlowTemplate());
if (StringUtils.isNotBlank(spdmExportNewTaskVo.getFlowTemplate())) {
List<String> flowTemplateNameList = new ArrayList<>();
String[] flowTemplateArr = spdmExportNewTaskVo.getFlowTemplate().split(";");
String[] flowTemplateArr = spdmExportNewTaskVo.getFlowTemplate().split(",");
for (String flowTemplate : flowTemplateArr) {
log.info("查询flowTemplate为{}",flowTemplate);
SdmResponse<FlowTemplateResp> flowTemplateResp = flowFeignClient.queryFlowTemplateInfoByTemplateCode(flowTemplate);

View File

@@ -6,7 +6,7 @@ spring:
name: project
datasource:
username: root
password: mysql
password: ENC(o5nKvbyfceJryxfBBGTi9w==)
jdbc-url: jdbc:mysql://192.168.30.146:3306/spdm_baseline?useUnicode=true&characterEncoding=utf-8&useSSL=true&serverTimezone=Asia/Shanghai
driver-class-name: com.mysql.cj.jdbc.Driver
hikari:
@@ -22,12 +22,12 @@ spring:
connection-timeout: 30000 # 30s
master:
username: root
password: mysql
password: ENC(o5nKvbyfceJryxfBBGTi9w==)
jdbc-url: jdbc:mysql://192.168.30.146:3306/spdm_baseline?useUnicode=true&characterEncoding=utf-8&useSSL=true&serverTimezone=Asia/Shanghai
driver-class-name: com.mysql.cj.jdbc.Driver
slave:
username: root
password: mysql
password: ENC(o5nKvbyfceJryxfBBGTi9w==)
jdbc-url: jdbc:mysql://192.168.30.146:3306/spdm_baseline?useUnicode=true&characterEncoding=utf-8&useSSL=true&serverTimezone=Asia/Shanghai
driver-class-name: com.mysql.cj.jdbc.Driver
enable: true

View File

@@ -66,9 +66,9 @@
</insert>
<insert id="batchAddSimulationPerformance" useGeneratedKeys="true" keyProperty="id">
insert into simulation_performance (uuid,taskId,taskName,standard,nodeId,nodeName,nodeCode,englishName,performanceType,unit,lowValue,highValue,method,description,tenantId) values
insert into simulation_performance (uuid,taskId,taskName,standard,nodeId,nodeName,nodeCode,englishName,performanceType,unit,lowValue,highValue,method,description,tenantId,creator) values
<foreach collection='list' item='it' index='index' separator=','>
(#{it.uuid},#{it.taskId},#{it.taskName},#{it.standard},#{it.nodeId},#{it.nodeName},#{it.nodeCode},#{it.englishName},#{it.performanceType},#{it.unit},#{it.lowValue},#{it.highValue},#{it.method},#{it.description},#{it.tenantId})
(#{it.uuid},#{it.taskId},#{it.taskName},#{it.standard},#{it.nodeId},#{it.nodeName},#{it.nodeCode},#{it.englishName},#{it.performanceType},#{it.unit},#{it.lowValue},#{it.highValue},#{it.method},#{it.description},#{it.tenantId},#{it.creator})
</foreach>
</insert>

View File

@@ -31,8 +31,7 @@ public interface SysLogMapper extends BaseMapper<SysLog> {
/**
* 查找用户在指定时间之后的下一次退出时间
*/
List<UserLogoutDto> findNextLogoutTimes(@Param("userIds") List<String> userIds,
@Param("afterTime") LocalDateTime afterTime,
List<UserLogoutDto> findNextLogoutTimes(@Param("userLoginTimes") List<UserLastLoginDto> userLoginTimes,
@Param("tenantId") Long tenantId);

View File

@@ -1,10 +1,12 @@
package com.sdm.system.model.dto;
import lombok.AllArgsConstructor;
import lombok.Data;
import java.time.LocalDateTime;
@Data
@AllArgsConstructor
public class UserLastLoginDto {
private String userId;
private LocalDateTime lastLoginTime;

View File

@@ -8,7 +8,7 @@ import java.time.LocalDateTime;
@Data
@AllArgsConstructor
public class UserSessionDto {
private String username;
private String userId;
private LocalDateTime loginTime;
private LocalDateTime effectiveLogoutTime;
}

View File

@@ -25,6 +25,7 @@ import com.sdm.system.model.entity.SysLog;
import com.sdm.system.model.resp.DailyOnlineStateResp;
import com.sdm.system.model.resp.LoginStateResp;
import com.sdm.system.service.ISysLogService;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.collections4.CollectionUtils;
import org.apache.commons.lang3.ObjectUtils;
import org.springframework.beans.BeanUtils;
@@ -45,6 +46,7 @@ import static com.mysql.cj.util.TimeUtil.DATE_FORMATTER;
* </p>
*/
@Service
@Slf4j
public class ISysLogServiceImpl extends ServiceImpl<SysLogMapper, SysLog> implements ISysLogService {
@Autowired
@@ -64,7 +66,7 @@ public class ISysLogServiceImpl extends ServiceImpl<SysLogMapper, SysLog> implem
wrapper.ge(SysLog::getCreateTime, sysLog.getCreateTimeArr()[0])
.le(SysLog::getCreateTime, sysLog.getCreateTimeArr()[1]);
}
wrapper.eq(SysLog::getTenantId, sysLog.getTenantId());
wrapper.eq(SysLog::getTenantId, ThreadLocalContext.getTenantId());
wrapper.orderByDesc(SysLog::getCreateTime);
PageHelper.startPage(sysLog.getCurrent(), sysLog.getSize());
List<SysLog> sysLogList = this.list(wrapper);
@@ -137,7 +139,7 @@ public class ISysLogServiceImpl extends ServiceImpl<SysLogMapper, SysLog> implem
LocalDate today = now.toLocalDate();
// 如果查询的是今天,只统计到当前小时
int maxHour = 23;
int maxHour = 24;
if (targetDate.equals(today)) {
maxHour = now.getHour(); // 只统计到当前小时
}
@@ -151,8 +153,7 @@ public class ISysLogServiceImpl extends ServiceImpl<SysLogMapper, SysLog> implem
// 3. 获取这些用户在目标日期及之后的退出时间
Map<String, LocalDateTime> userLogoutTimes = getUserNextLogoutTimes(
UserLastLoginDtos.stream().map(UserLastLoginDto::getUserId).collect(Collectors.toList()),
targetDayStart,
UserLastLoginDtos,
tenantId
);
@@ -183,9 +184,8 @@ public class ISysLogServiceImpl extends ServiceImpl<SysLogMapper, SysLog> implem
// 会话开始时间 < 目标日期结束时间
boolean sessionStartedBeforeTargetEnd = loginTime.isBefore(targetDayEnd);
// 会话结束时间 > 目标日期开始时间 或 会话未结束
boolean sessionEndedAfterTargetStart = logoutTime == null ||
logoutTime.isAfter(targetDayStart);
// 会话结束时间 > 目标日期开始时间 或 会话未结束(有些上个月最后一次登录的了)
boolean sessionEndedAfterTargetStart = logoutTime == null || logoutTime.isAfter(targetDayStart);
if (sessionStartedBeforeTargetEnd && sessionEndedAfterTargetStart) {
// 计算有效的退出时间
@@ -236,23 +236,29 @@ public class ISysLogServiceImpl extends ServiceImpl<SysLogMapper, SysLog> implem
// 用户在该时段在线的条件:
// 1. 会话开始时间 < 时段结束时间(用户在时段结束前已登录)
// 2. 会话结束时间 > 时段开始时间(用户在时段开始后未退出)
return session.getLoginTime().isBefore(periodEnd) &&
session.getEffectiveLogoutTime().isAfter(periodStart);
boolean flag = session.getLoginTime().isBefore(periodEnd) && session.getEffectiveLogoutTime().isAfter(periodStart);
log.info("userId:{}, onlineFlag:{}, time interval:{}", session.getUserId(), flag, periodStart.toString() + "-" + periodEnd.toString());
return flag;
}
private Map<String, LocalDateTime> getUserNextLogoutTimes(List<String> userIds, LocalDateTime afterTime, Long tenantId) {
private Map<String, LocalDateTime> getUserNextLogoutTimes(
List<UserLastLoginDto> userLastLogins, Long tenantId) {
Map<String, LocalDateTime> logoutTimes = new HashMap<>();
Map<String, LocalDateTime> logoutTimes = new HashMap<>();
// 批量查询用户的下一次退出时间
List<UserLogoutDto> logouts = baseMapper.findNextLogoutTimes(userIds, afterTime, tenantId);
if (userLastLogins.isEmpty()) {
return logoutTimes;
}
for (UserLogoutDto logout : logouts) {
logoutTimes.put(logout.getUserId(), logout.getLogoutTime());
}
// 批量查询每个用户在其最后登录时间之后的退出记录
List<UserLogoutDto> logouts = baseMapper.findNextLogoutTimes(userLastLogins, tenantId);
return logoutTimes;
}
for (UserLogoutDto logout : logouts) {
logoutTimes.put(logout.getUserId(), logout.getLogoutTime());
}
return logoutTimes;
}
private void setCreatorNames(List<SysLogDTO> list) {
try {

View File

@@ -6,7 +6,7 @@ spring:
name: system
datasource:
username: root
password: mysql
password: ENC(o5nKvbyfceJryxfBBGTi9w==)
jdbc-url: jdbc:mysql://192.168.30.146:3306/spdm_baseline?useUnicode=true&characterEncoding=utf-8&useSSL=true&serverTimezone=Asia/Shanghai
driver-class-name: com.mysql.cj.jdbc.Driver
hikari:
@@ -22,12 +22,12 @@ spring:
connection-timeout: 30000 # 30s
master:
username: root
password: mysql
password: ENC(o5nKvbyfceJryxfBBGTi9w==)
jdbc-url: jdbc:mysql://192.168.30.146:3306/spdm_baseline?useUnicode=true&characterEncoding=utf-8&useSSL=true&serverTimezone=Asia/Shanghai
driver-class-name: com.mysql.cj.jdbc.Driver
slave:
username: root
password: mysql
password: ENC(o5nKvbyfceJryxfBBGTi9w==)
jdbc-url: jdbc:mysql://192.168.30.146:3306/spdm_baseline?useUnicode=true&characterEncoding=utf-8&useSSL=true&serverTimezone=Asia/Shanghai
driver-class-name: com.mysql.cj.jdbc.Driver
enable: true

View File

@@ -70,20 +70,21 @@
<select id="findNextLogoutTimes" resultType="com.sdm.system.model.dto.UserLogoutDto">
SELECT
l1.createBy as userId,
MIN(l2.createTime) as logoutTime
FROM sys_log l1
INNER JOIN sys_log l2 ON l1.createBy = l2.createBy
WHERE l1.title = '登录成功'
AND l2.title = '退出登录'
AND l2.createTime &gt; l1.createTime
AND l2.createTime &gt;= #{afterTime}
AND l1.createBy IN
<foreach collection='userIds' item='userId' open='(' separator=',' close=')'>
#{userId}
</foreach>
AND l1.tenantId = #{tenantId}
GROUP BY l1.createBy, l1.createTime
user_logins.userId as userId,
MIN(l2.createTime) as logoutTime
FROM (
<foreach collection='userLoginTimes' item='item' separator=' UNION ALL '>
SELECT #{item.userId} as userId, #{item.lastLoginTime} as loginTime
</foreach>
) user_logins
LEFT JOIN sys_log l1 ON user_logins.userId = l1.createBy
AND l1.title = '登录成功'
AND l1.createTime = user_logins.loginTime
AND l1.tenantId = #{tenantId}
LEFT JOIN sys_log l2 ON user_logins.userId = l2.createBy
AND l2.title = '退出登录'
AND l2.createTime > user_logins.loginTime
GROUP BY user_logins.userId
</select>
</mapper>

View File

@@ -7,7 +7,7 @@ spring:
name: task
datasource:
username: root
password: mysql
password: ENC(o5nKvbyfceJryxfBBGTi9w==)
jdbc-url: jdbc:mysql://192.168.30.146:3306/spdm_baseline?useUnicode=true&characterEncoding=utf-8&useSSL=true&serverTimezone=Asia/Shanghai
driver-class-name: com.mysql.cj.jdbc.Driver
hikari:
@@ -23,12 +23,12 @@ spring:
connection-timeout: 30000 # 30s
master:
username: root
password: mysql
password: ENC(o5nKvbyfceJryxfBBGTi9w==)
jdbc-url: jdbc:mysql://192.168.30.146:3306/spdm_baseline?useUnicode=true&characterEncoding=utf-8&useSSL=true&serverTimezone=Asia/Shanghai
driver-class-name: com.mysql.cj.jdbc.Driver
slave:
username: root
password: mysql
password: ENC(o5nKvbyfceJryxfBBGTi9w==)
jdbc-url: jdbc:mysql://192.168.30.146:3306/spdm_baseline?useUnicode=true&characterEncoding=utf-8&useSSL=true&serverTimezone=Asia/Shanghai
driver-class-name: com.mysql.cj.jdbc.Driver
enable: true