diff --git a/src/main/java/com/project/appeal/application/AppealApplication.java b/src/main/java/com/project/appeal/application/AppealApplication.java new file mode 100644 index 0000000..855afbd --- /dev/null +++ b/src/main/java/com/project/appeal/application/AppealApplication.java @@ -0,0 +1,20 @@ +package com.project.appeal.application; + +import com.baomidou.mybatisplus.core.metadata.IPage; +import com.project.appeal.domain.dto.AppealDTO; +import com.project.appeal.domain.param.AppealParam; +import com.project.base.domain.result.Result; + +import java.util.List; + +public interface AppealApplication { + /** + * 保存或修改申诉 + */ + Result saveOrUpdate(AppealDTO appealDTO); + + /** + * 查询申诉列表 + */ + Result> list(AppealParam appealParam); +} diff --git a/src/main/java/com/project/appeal/application/Impl/AppealApplicationImpl.java b/src/main/java/com/project/appeal/application/Impl/AppealApplicationImpl.java new file mode 100644 index 0000000..3c35102 --- /dev/null +++ b/src/main/java/com/project/appeal/application/Impl/AppealApplicationImpl.java @@ -0,0 +1,41 @@ +package com.project.appeal.application.Impl; + +import com.baomidou.mybatisplus.core.metadata.IPage; +import com.project.appeal.application.AppealApplication; +import com.project.appeal.domain.dto.AppealDTO; +import com.project.appeal.domain.param.AppealParam; +import com.project.appeal.domain.service.CheckAppealDomainService; +import com.project.appeal.domain.service.SaveAppealDomainService; +import com.project.appeal.domain.service.SearchAppealDomainService; +import com.project.base.domain.result.Result; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Service; + +import java.util.List; + +@Service +public class AppealApplicationImpl implements AppealApplication { + @Autowired + private SaveAppealDomainService saveAppealDomainService; + @Autowired + private CheckAppealDomainService checkAppealDomainService; + @Autowired + private SearchAppealDomainService searchAppealDomainService; + + /** + * 保存申诉 + */ + @Override + public Result saveOrUpdate(AppealDTO appealDTO) { + checkAppealDomainService.checkDto(appealDTO); + return saveAppealDomainService.saveOrUpdate(appealDTO); + } + + /** + * 查询申诉列表 + */ + @Override + public Result> list(AppealParam appealParam) { + return searchAppealDomainService.list(appealParam); + } +} diff --git a/src/main/java/com/project/appeal/controller/AppealController.java b/src/main/java/com/project/appeal/controller/AppealController.java new file mode 100644 index 0000000..3880c5a --- /dev/null +++ b/src/main/java/com/project/appeal/controller/AppealController.java @@ -0,0 +1,31 @@ +package com.project.appeal.controller; + +import com.baomidou.mybatisplus.core.metadata.IPage; +import com.project.appeal.application.AppealApplication; +import com.project.appeal.domain.dto.AppealDTO; +import com.project.appeal.domain.param.AppealParam; +import com.project.base.domain.result.Result; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.web.bind.annotation.*; + +import java.util.List; + +/** + * 申诉模块 + */ +@RequestMapping("/api/admin/appeal") +@RestController +public class AppealController { + @Autowired + private AppealApplication appealApplication; + + @PostMapping("saveOrUpdate") + public Result saveOrUpdate(@RequestBody AppealDTO appealDTO){ + return appealApplication.saveOrUpdate(appealDTO); + } + + @GetMapping("list") + public Result> list(AppealParam appealParam){ + return appealApplication.list(appealParam); + } +} diff --git a/src/main/java/com/project/appeal/domain/dto/AppealDTO.java b/src/main/java/com/project/appeal/domain/dto/AppealDTO.java new file mode 100644 index 0000000..7f537db --- /dev/null +++ b/src/main/java/com/project/appeal/domain/dto/AppealDTO.java @@ -0,0 +1,36 @@ +package com.project.appeal.domain.dto; + +import com.baomidou.mybatisplus.annotation.IdType; +import com.baomidou.mybatisplus.annotation.TableField; +import com.baomidou.mybatisplus.annotation.TableId; +import com.baomidou.mybatisplus.annotation.TableName; +import com.project.base.domain.dto.BaseDTO; +import com.project.base.domain.entity.BaseEntity; +import jakarta.persistence.Column; +import jakarta.persistence.Entity; +import jakarta.persistence.Id; +import jakarta.persistence.Table; +import lombok.Data; +import lombok.EqualsAndHashCode; +import org.hibernate.annotations.Comment; + +import java.util.List; + +@Data +public class AppealDTO extends BaseDTO { + private Long id; + private String userId; + private String userName; + private Long examId; + private Long taskId; + private String subLineName;//关联子产品线 + private Long questionId; + private String questionContent; //题干 + private String kpContentsStr; //知识点文本 + private List kpIdList; + private String rightAnswer;//正确答案 + private String userAnswer;//用户答案 + private Integer status = 1; + private String remark; + private String reason; +} diff --git a/src/main/java/com/project/appeal/domain/entity/AppealEntity.java b/src/main/java/com/project/appeal/domain/entity/AppealEntity.java new file mode 100644 index 0000000..8508223 --- /dev/null +++ b/src/main/java/com/project/appeal/domain/entity/AppealEntity.java @@ -0,0 +1,58 @@ +package com.project.appeal.domain.entity; + +import com.baomidou.mybatisplus.annotation.IdType; +import com.baomidou.mybatisplus.annotation.TableField; +import com.baomidou.mybatisplus.annotation.TableId; +import com.baomidou.mybatisplus.annotation.TableName; +import com.project.base.domain.entity.BaseEntity; +import jakarta.persistence.*; +import lombok.Data; +import lombok.EqualsAndHashCode; +import org.hibernate.annotations.Comment; + +@Data +@Table(name = "evaluator_appeal", + indexes = {@Index(name = "Idx_task_id" , columnList = "task_id"), + @Index(name = "Idx_question_id" , columnList = "question_id")}) +@Entity +@TableName(value = "evaluator_appeal") +@EqualsAndHashCode(callSuper = true) +public class AppealEntity extends BaseEntity { + @TableId(value = "id" , type = IdType.ASSIGN_ID) + @Id + private Long id; + + @TableField("user_id") + @Column(name = "user_id" , columnDefinition="varchar(50) comment '用户id'") + private String userId; + + @Column(name = "username" , columnDefinition="varchar(50) comment '用户名称'") + private String username; + + @TableField("exam_id") + @Column(name = "exam_id" , columnDefinition="bigint(20) comment '考试id'") + private Long examId; + + @TableField("task_id") + @Column(name = "task_id" , columnDefinition="bigint(20) comment '考试任务id'") + private Long taskId; + + @Column(name = "user_answer",columnDefinition = "varchar(255) comment '用户答案'") + @TableField("user_answer") + private Long userAnswer; + + @Column(name = "question_id") + @Comment("题目ID") + @TableField("question_id") + private Long questionId; + + @Column(name = "status") + @Comment("审批状态") + private Integer status; + + @Column(name = "remark",columnDefinition = "varchar(255) comment '申诉备注'") + private String remark; + + @Column(name = "reason",columnDefinition = "varchar(255) comment '审批理由'") + private String reason; +} diff --git a/src/main/java/com/project/appeal/domain/enums/StatusEnum.java b/src/main/java/com/project/appeal/domain/enums/StatusEnum.java new file mode 100644 index 0000000..90b6333 --- /dev/null +++ b/src/main/java/com/project/appeal/domain/enums/StatusEnum.java @@ -0,0 +1,16 @@ +package com.project.appeal.domain.enums; + +import com.project.base.domain.enums.HasValueEnum; +import lombok.Getter; +import lombok.RequiredArgsConstructor; + +@Getter +@RequiredArgsConstructor +public enum StatusEnum implements HasValueEnum { + PENDING_REVIEW(1,"待审核"), + PASS_REVIEW(2,"审核通过"), + REFUSE_REVIEW(3,"审核拒绝"); + + private final Integer value; + private final String desc; +} diff --git a/src/main/java/com/project/appeal/domain/param/AppealParam.java b/src/main/java/com/project/appeal/domain/param/AppealParam.java new file mode 100644 index 0000000..dc50320 --- /dev/null +++ b/src/main/java/com/project/appeal/domain/param/AppealParam.java @@ -0,0 +1,9 @@ +package com.project.appeal.domain.param; + +import com.project.base.domain.param.BaseParam; +import lombok.Data; + +@Data +public class AppealParam extends BaseParam { + public String subLineName; +} diff --git a/src/main/java/com/project/appeal/domain/service/AppealBaseService.java b/src/main/java/com/project/appeal/domain/service/AppealBaseService.java new file mode 100644 index 0000000..bbfd40e --- /dev/null +++ b/src/main/java/com/project/appeal/domain/service/AppealBaseService.java @@ -0,0 +1,7 @@ +package com.project.appeal.domain.service; + +import com.project.appeal.domain.entity.AppealEntity; +import com.project.base.domain.service.IBaseService; + +public interface AppealBaseService extends IBaseService { +} diff --git a/src/main/java/com/project/appeal/domain/service/CheckAppealDomainService.java b/src/main/java/com/project/appeal/domain/service/CheckAppealDomainService.java new file mode 100644 index 0000000..d9a946b --- /dev/null +++ b/src/main/java/com/project/appeal/domain/service/CheckAppealDomainService.java @@ -0,0 +1,7 @@ +package com.project.appeal.domain.service; + +import com.project.appeal.domain.dto.AppealDTO; + +public interface CheckAppealDomainService { + void checkDto(AppealDTO appealDTO); +} diff --git a/src/main/java/com/project/appeal/domain/service/Impl/AppealBaseServiceImpl.java b/src/main/java/com/project/appeal/domain/service/Impl/AppealBaseServiceImpl.java new file mode 100644 index 0000000..6965ea6 --- /dev/null +++ b/src/main/java/com/project/appeal/domain/service/Impl/AppealBaseServiceImpl.java @@ -0,0 +1,11 @@ +package com.project.appeal.domain.service.Impl; + +import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl; +import com.project.appeal.domain.entity.AppealEntity; +import com.project.appeal.domain.service.AppealBaseService; +import com.project.appeal.mapper.AppealMapper; +import org.springframework.stereotype.Service; + +@Service +public class AppealBaseServiceImpl extends ServiceImpl implements AppealBaseService { +} diff --git a/src/main/java/com/project/appeal/domain/service/Impl/CheckAppealDomainServiceImpl.java b/src/main/java/com/project/appeal/domain/service/Impl/CheckAppealDomainServiceImpl.java new file mode 100644 index 0000000..75a8f65 --- /dev/null +++ b/src/main/java/com/project/appeal/domain/service/Impl/CheckAppealDomainServiceImpl.java @@ -0,0 +1,45 @@ +package com.project.appeal.domain.service.Impl; + +import cn.hutool.core.util.ObjectUtil; +import com.project.appeal.domain.dto.AppealDTO; +import com.project.appeal.domain.service.CheckAppealDomainService; +import com.project.base.domain.exception.BusinessErrorException; +import com.project.base.domain.exception.MissingParameterException; +import org.apache.commons.lang3.StringUtils; +import org.springframework.stereotype.Service; + +@Service +public class CheckAppealDomainServiceImpl implements CheckAppealDomainService { + @Override + public void checkDto(AppealDTO appealDTO) { + if (ObjectUtil.isEmpty(appealDTO.getExamId())){ + throw new MissingParameterException("缺少考试ID"); + } + + if (ObjectUtil.isEmpty(appealDTO.getUserId())){ + throw new MissingParameterException("缺少用户ID"); + } + + if (StringUtils.isBlank(appealDTO.getUserName())){ + throw new MissingParameterException("缺少用户名称"); + } + + if (ObjectUtil.isEmpty(appealDTO.getQuestionContent())){ + throw new MissingParameterException("缺少题目ID"); + } + + if (StringUtils.isBlank(appealDTO.getUserAnswer())){ + throw new MissingParameterException("缺少用户答案"); + } + + if (StringUtils.isBlank(appealDTO.getRemark())){ + throw new MissingParameterException("缺少申诉理由"); + } + if (ObjectUtil.isEmpty(appealDTO.getId()) && appealDTO.getStatus() != 1){ + throw new BusinessErrorException("申诉状态错误"); + } + if (ObjectUtil.isNotEmpty(appealDTO.getId()) && appealDTO.getStatus() == 1){ + throw new BusinessErrorException("申诉状态错误"); + } + } +} diff --git a/src/main/java/com/project/appeal/domain/service/Impl/SaveAppealDomainServiceImpl.java b/src/main/java/com/project/appeal/domain/service/Impl/SaveAppealDomainServiceImpl.java new file mode 100644 index 0000000..193082c --- /dev/null +++ b/src/main/java/com/project/appeal/domain/service/Impl/SaveAppealDomainServiceImpl.java @@ -0,0 +1,95 @@ +package com.project.appeal.domain.service.Impl; + +import com.project.appeal.domain.dto.AppealDTO; +import com.project.appeal.domain.entity.AppealEntity; +import com.project.appeal.domain.service.AppealBaseService; +import com.project.appeal.domain.service.SaveAppealDomainService; +import com.project.base.domain.exception.BusinessErrorException; +import com.project.base.domain.result.Result; +import com.project.exam.domain.dto.ExamRecordDTO; +import com.project.exam.domain.entity.ExamRecordEntity; +import com.project.exam.domain.service.ExamRecordBaseService; +import com.project.task.domain.entity.TaskEntity; +import com.project.task.mapper.TaskMapper; +import org.redisson.mapreduce.Collector; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Service; + +import java.math.BigDecimal; +import java.math.RoundingMode; +import java.util.ArrayList; +import java.util.List; +import java.util.Optional; +import java.util.stream.Collectors; + +@Service +public class SaveAppealDomainServiceImpl implements SaveAppealDomainService { + @Autowired + private AppealBaseService appealBaseService; + @Autowired + private ExamRecordBaseService examRecordBaseService; + @Autowired + private TaskMapper taskMapper; + + + @Override + public Result saveOrUpdate(AppealDTO appealDTO) { + AppealEntity entity = appealDTO.toEntity(AppealEntity::new); + appealBaseService.saveOrUpdate(entity); + + //如果审核通过,需要为用户加分 + if (appealDTO.getStatus() != 2){ + return Result.success(appealDTO); + } + + ExamRecordEntity examRecord = examRecordBaseService.getById(appealDTO.getExamId()); + if (examRecord == null){ + throw new BusinessErrorException("用户未该场考试"); + } + //找到题目相关信息,获取该类型题目分数 + ExamRecordDTO examRecordDTO = examRecord.toDTO(ExamRecordDTO::new); + + ExamRecordDTO.QuestionSnapshotDTO questionSnapshotDTO = null; + Optional optionalDTO = examRecordDTO.getAnswerSnapshotDTOList().stream() + .filter(answerSnapshotDTO -> appealDTO.getQuestionId() != null + && appealDTO.getQuestionId().equals(answerSnapshotDTO.getQuestionId())) + .findFirst(); + if (optionalDTO.isPresent()) { + questionSnapshotDTO = optionalDTO.get(); + }else { + throw new BusinessErrorException("题目不存在"); + } + + //已申诉题目无法再申诉 + if(questionSnapshotDTO.getHasAppealed()){ + throw new BusinessErrorException("题目已申诉"); + } + + TaskEntity taskEntity = taskMapper.getTaskByTaskUserId(examRecord.getTaskUserId()); + + Double questionScore = switch (questionSnapshotDTO.getType()) { + case 1 -> taskEntity.getSingleChoiceScore(); + case 2 -> taskEntity.getMultipleChoiceScore(); + case 3 -> taskEntity.getTrueFalseScore(); + default -> throw new IllegalArgumentException( + "不支持的题目类型:" + questionSnapshotDTO.getType() + ); + }; + + //总分+单题分数 + BigDecimal score = BigDecimal.valueOf(questionScore).add(BigDecimal.valueOf(examRecordDTO.getScore())).setScale(2, RoundingMode.HALF_UP); + examRecord.setScore(score.doubleValue()); + + questionSnapshotDTO.setHasAppealed(true); + List questionSnapshotDTOList = examRecordDTO.getAnswerSnapshotDTOList().stream() + .filter(answerSnapshotDTO -> !appealDTO.getQuestionId().equals(answerSnapshotDTO.getQuestionId())) + .collect(Collectors.toCollection(ArrayList::new)); + questionSnapshotDTOList.add(questionSnapshotDTO); + examRecordDTO.setAnswerSnapshotDTOList(questionSnapshotDTOList); + + //保存 + examRecordBaseService.save(examRecordDTO.toEntity(ExamRecordEntity::new)); + + return Result.success(appealDTO); + } +} diff --git a/src/main/java/com/project/appeal/domain/service/Impl/SearchAppealDomainServiceImpl.java b/src/main/java/com/project/appeal/domain/service/Impl/SearchAppealDomainServiceImpl.java new file mode 100644 index 0000000..aebf2d3 --- /dev/null +++ b/src/main/java/com/project/appeal/domain/service/Impl/SearchAppealDomainServiceImpl.java @@ -0,0 +1,119 @@ +package com.project.appeal.domain.service.Impl; + +import cn.hutool.json.JSONUtil; +import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper; +import com.baomidou.mybatisplus.core.metadata.IPage; +import com.baomidou.mybatisplus.extension.plugins.pagination.Page; +import com.project.appeal.domain.dto.AppealDTO; +import com.project.appeal.domain.entity.AppealEntity; +import com.project.appeal.domain.param.AppealParam; +import com.project.appeal.domain.service.AppealBaseService; +import com.project.appeal.domain.service.SearchAppealDomainService; +import com.project.appeal.mapper.AppealMapper; +import com.project.base.domain.result.Result; +import com.project.base.domain.utils.PageConverter; +import com.project.exam.domain.entity.ExamRecordEntity; +import com.project.exam.domain.service.ExamRecordBaseService; +import com.project.information.domain.dto.InformationDTO; +import com.project.information.domain.entity.KnowledgePointEntity; +import com.project.information.domain.service.KnowledgePointBaseService; +import com.project.question.domain.entity.QuestionEntity; +import com.project.question.domain.service.QuestionBaseService; +import com.project.task.domain.dto.TaskDTO; +import com.project.task.mapper.TaskMapper; +import org.apache.commons.lang3.ObjectUtils; +import org.apache.commons.lang3.StringUtils; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Service; +import org.springframework.util.CollectionUtils; + +import java.util.*; +import java.util.stream.Collectors; + +@Service +public class SearchAppealDomainServiceImpl implements SearchAppealDomainService { + @Autowired + private AppealMapper appealMapper; + @Autowired + private QuestionBaseService questionBaseService; + @Autowired + private TaskMapper taskMapper; + @Autowired + private KnowledgePointBaseService knowledgePointBaseService; + + @Override + public Result> list(AppealParam appealParam) { + QueryWrapper appealEntityQueryWrapper = new QueryWrapper<>(); + IPage appealDTOIPage = new Page<>(); + Map taskIdToSubLineNameMap = Map.of(); + if (StringUtils.isBlank(appealParam.getSubLineName())){ + Page appealEntityPage = appealMapper.selectPage(PageConverter.toMpPage(appealParam), appealEntityQueryWrapper); + appealDTOIPage = appealEntityPage.convert(entity -> entity.toDTO(AppealDTO::new)); + }else{ + //查询产品线相关的考试任务 + List taskBySubLineName = taskMapper.getTaskBySubLineName(appealParam.getSubLineName()); + taskIdToSubLineNameMap = taskBySubLineName.stream().collect(Collectors.toMap(TaskDTO::getId, TaskDTO::getName)); + + //查询申诉列表 + appealEntityQueryWrapper.in("task_id",taskBySubLineName.stream().map(TaskDTO::getId).collect(Collectors.toList())); + Page appealEntityPage = appealMapper.selectPage(PageConverter.toMpPage(appealParam), appealEntityQueryWrapper); + appealDTOIPage = appealEntityPage.convert(entity -> entity.toDTO(AppealDTO::new)); + } + appealDTOIPage.setRecords(buildDTO(appealDTOIPage.getRecords(),taskIdToSubLineNameMap)); + return Result.success(appealDTOIPage); + } + + + /** + * 构建返回实体 + */ + private List buildDTO(List appealDTOList,Map taskIdToSubLineNameMap){ + if (CollectionUtils.isEmpty(appealDTOList)){ + return appealDTOList; + } + + //获取题目信息 + Set questionIdList = appealDTOList.stream() + .filter(appealDTO -> ObjectUtils.isNotEmpty(appealDTO.getExamId())) + .map(appealDTO -> appealDTO.getQuestionId()) + .collect(Collectors.toSet()); + Map questionEntityMap = questionBaseService.listByIds(questionIdList).stream() + .collect(Collectors.toMap(questionEntity -> questionEntity.getId(), questionEntity -> questionEntity)); + + //知识点拼接 + Set kpIdSet = new HashSet<>(); + appealDTOList.forEach(appealDTO -> { + if (questionEntityMap.containsKey(appealDTO.getQuestionId())){ + QuestionEntity questionEntity = questionEntityMap.get(appealDTO.getQuestionId()); + QuestionEntity.QuestionDetail questionDetail = questionEntity.getQuestionDetail(); + + appealDTO.setSubLineName(taskIdToSubLineNameMap.get(appealDTO.getTaskId())); + appealDTO.setQuestionContent(questionDetail.getQuestionContent()); + appealDTO.setRightAnswer(questionDetail.getRightAnswer()); + appealDTO.setKpIdList(questionEntity.getKpIdList()); + kpIdSet.addAll(questionEntity.getKpIdList()); + } + }); + + //查询知识点,构建知识点字段 + Map kpIdToEntityMap = knowledgePointBaseService.listByIds(kpIdSet).stream() + .collect(Collectors.toMap( + KnowledgePointEntity::getId, + kpEntity -> kpEntity + )); + + appealDTOList.forEach(appealDTO -> { + List kpIdList = appealDTO.getKpIdList(); + + String kpContentStr = kpIdList.stream() + .filter(kpId -> kpIdToEntityMap.containsKey(kpId)) + .map(kpId -> kpIdToEntityMap.get(kpId).getContent()) + .filter(StringUtils::isNotBlank) + .collect(Collectors.joining(",")); + + appealDTO.setKpContentsStr(kpContentStr); + }); + + return appealDTOList; + } +} diff --git a/src/main/java/com/project/appeal/domain/service/SaveAppealDomainService.java b/src/main/java/com/project/appeal/domain/service/SaveAppealDomainService.java new file mode 100644 index 0000000..5e587bc --- /dev/null +++ b/src/main/java/com/project/appeal/domain/service/SaveAppealDomainService.java @@ -0,0 +1,8 @@ +package com.project.appeal.domain.service; + +import com.project.appeal.domain.dto.AppealDTO; +import com.project.base.domain.result.Result; + +public interface SaveAppealDomainService { + Result saveOrUpdate(AppealDTO appealDTO); +} diff --git a/src/main/java/com/project/appeal/domain/service/SearchAppealDomainService.java b/src/main/java/com/project/appeal/domain/service/SearchAppealDomainService.java new file mode 100644 index 0000000..76b7146 --- /dev/null +++ b/src/main/java/com/project/appeal/domain/service/SearchAppealDomainService.java @@ -0,0 +1,10 @@ +package com.project.appeal.domain.service; + +import com.baomidou.mybatisplus.core.metadata.IPage; +import com.project.appeal.domain.dto.AppealDTO; +import com.project.appeal.domain.param.AppealParam; +import com.project.base.domain.result.Result; + +public interface SearchAppealDomainService { + Result> list(AppealParam appealParam); +} diff --git a/src/main/java/com/project/appeal/mapper/AppealMapper.java b/src/main/java/com/project/appeal/mapper/AppealMapper.java new file mode 100644 index 0000000..537e47d --- /dev/null +++ b/src/main/java/com/project/appeal/mapper/AppealMapper.java @@ -0,0 +1,14 @@ +package com.project.appeal.mapper; + +import com.baomidou.mybatisplus.core.mapper.BaseMapper; +import com.project.appeal.domain.dto.AppealDTO; +import com.project.appeal.domain.entity.AppealEntity; +import org.apache.ibatis.annotations.Mapper; +import org.apache.ibatis.annotations.Param; +import org.apache.ibatis.annotations.Select; + +import java.util.List; + +@Mapper +public interface AppealMapper extends BaseMapper { +} diff --git a/src/main/java/com/project/ding/utils/DingUtil.java b/src/main/java/com/project/ding/utils/DingUtil.java index 5d174e2..82b2832 100644 --- a/src/main/java/com/project/ding/utils/DingUtil.java +++ b/src/main/java/com/project/ding/utils/DingUtil.java @@ -6,6 +6,10 @@ import com.fasterxml.jackson.databind.ObjectMapper; import com.github.tingyugetc520.ali.dingtalk.api.DtService; import com.github.tingyugetc520.ali.dingtalk.bean.department.DtDepart; +import com.github.tingyugetc520.ali.dingtalk.bean.message.DtCorpConversationMessage; +import com.github.tingyugetc520.ali.dingtalk.bean.message.DtMessage; +import com.github.tingyugetc520.ali.dingtalk.error.DtErrorException; +import com.google.common.collect.Lists; import com.google.gson.JsonObject; import com.jayway.jsonpath.JsonPath; import com.project.ding.domain.dto.DepartmentDTO; @@ -130,6 +134,45 @@ public class DingUtil { return res; } + /** + * 发送工作通知 + */ + public void sendWorkNotice(String userId,String message) throws DtErrorException { + DtCorpConversationMessage corpConversationMessage = DtCorpConversationMessage.builder() + .agentId(dtService.getDtConfigStorage().getAgentId()) + .userIds(Lists.newArrayList(userId)) + .msg(DtMessage.MARKDOWN() + .content("AI考核-审批申诉结果") + .text(String.format("### AI考核-申诉审批完成\n" + + "\n" + + "#### 任务信息\n" + + "- 考试任务:%d\n" + + "- 题目名称:%d\n" + + "\n" + + "#### 审批结果\n" + + "- ✅ 审核通过\n" + + "\n" + + "---\n" + + "- \uD83D\uDCC5 审批时间:%d\n" + + "- \uD83D\uDC64 审批人:%d\n" + + "- \uD83D\uDCAC 审批意见:%d","任务1","题目1","时间","人","意见")) + .build()) + .build(); + +// dtService.getCorpConversationMsgService().send(corpConversationMessage); + } + /** + * 获取发送工作通知 + */ + public String getSendResult(String taskId){ + JsonObject jsonObject = new JsonObject(); + jsonObject.addProperty("task_id" , taskId); + jsonObject.addProperty("agent_id" , dtService.getDtConfigStorage().getAgentId()); + + String apiUrl = dtService.getDtConfigStorage().getApiUrl("/topapi/message/corpconversation/getsendresult"); + String res = Try.of(() -> dtService.post(apiUrl, jsonObject)).getOrElse(""); + return res; + } } diff --git a/src/main/java/com/project/information/application/InformationApplicationService.java b/src/main/java/com/project/information/application/InformationApplicationService.java index 1a6711c..8e59ac1 100644 --- a/src/main/java/com/project/information/application/InformationApplicationService.java +++ b/src/main/java/com/project/information/application/InformationApplicationService.java @@ -19,7 +19,7 @@ public interface InformationApplicationService { /** * 查询资料列表 */ - Result> list(InformationParam informationParam); + Result> list(InformationParam informationParam); /** * 删除资料 diff --git a/src/main/java/com/project/information/application/impl/InformationApplicationServiceImpl.java b/src/main/java/com/project/information/application/impl/InformationApplicationServiceImpl.java index 4496a7e..831d28b 100644 --- a/src/main/java/com/project/information/application/impl/InformationApplicationServiceImpl.java +++ b/src/main/java/com/project/information/application/impl/InformationApplicationServiceImpl.java @@ -39,7 +39,7 @@ public class InformationApplicationServiceImpl implements InformationApplication } @Override - public Result> list(InformationParam informationParam) { + public Result> list(InformationParam informationParam) { return searchInformationDomainService.list(informationParam); } diff --git a/src/main/java/com/project/information/controller/InformationController.java b/src/main/java/com/project/information/controller/InformationController.java index 8d510d1..a9e5f8c 100644 --- a/src/main/java/com/project/information/controller/InformationController.java +++ b/src/main/java/com/project/information/controller/InformationController.java @@ -37,7 +37,7 @@ public class InformationController { } @GetMapping("/list") - public Result> list(InformationParam informationParam) throws Exception { + public Result> list(InformationParam informationParam) throws Exception { return informationApplicationService.list(informationParam); } diff --git a/src/main/java/com/project/information/domain/service/SearchInformationDomainService.java b/src/main/java/com/project/information/domain/service/SearchInformationDomainService.java index a77784d..aec968a 100644 --- a/src/main/java/com/project/information/domain/service/SearchInformationDomainService.java +++ b/src/main/java/com/project/information/domain/service/SearchInformationDomainService.java @@ -9,7 +9,7 @@ import com.project.task.domain.dto.TaskDTO; import java.util.List; public interface SearchInformationDomainService { - Result> list(InformationParam informationParam); + Result> list(InformationParam informationParam); List selectBatchIds(List idList); } diff --git a/src/main/java/com/project/information/domain/service/impl/SearchInformationDomainServiceImpl.java b/src/main/java/com/project/information/domain/service/impl/SearchInformationDomainServiceImpl.java index fa94d61..b682618 100644 --- a/src/main/java/com/project/information/domain/service/impl/SearchInformationDomainServiceImpl.java +++ b/src/main/java/com/project/information/domain/service/impl/SearchInformationDomainServiceImpl.java @@ -26,7 +26,7 @@ public class SearchInformationDomainServiceImpl implements SearchInformationDoma private InformationMapper informationMapper; @Override - public Result> list(InformationParam informationParam) { + public Result> list(InformationParam informationParam) { if (ObjectUtil.isEmpty(informationParam.getSubLineId())){ throw new BusinessErrorException("产品线ID不能为空"); } @@ -34,12 +34,10 @@ public class SearchInformationDomainServiceImpl implements SearchInformationDoma LambdaQueryWrapper queryWrapper = new LambdaQueryWrapper<>(); queryWrapper.orderByDesc(InformationEntity::getCreateTime); queryWrapper.eq(InformationEntity::getSubLineId, informationParam.getSubLineId()); - IPage informationEntityIPage = informationMapper.selectPage( - PageConverter.toMpPage(informationParam), - queryWrapper); - IPage informationDTOIPage = informationEntityIPage.convert(entity -> entity.toDTO(InformationDTO::new)); + List informationDTOList = informationMapper.selectList(queryWrapper) + .stream().map(informationEntity -> informationEntity.toDTO(InformationDTO::new)).collect(Collectors.toList()); - return Result.page(informationDTOIPage); + return Result.success(informationDTOList); } @Override diff --git a/src/main/java/com/project/operation/aop/OperationLogAspect.java b/src/main/java/com/project/operation/aop/OperationLogAspect.java index 1499e64..a16be76 100644 --- a/src/main/java/com/project/operation/aop/OperationLogAspect.java +++ b/src/main/java/com/project/operation/aop/OperationLogAspect.java @@ -1,7 +1,5 @@ package com.project.operation.aop; -import cn.hutool.core.util.EnumUtil; -import com.baomidou.mybatisplus.core.toolkit.StringUtils; import com.project.base.domain.result.Result; import com.project.ding.domain.dto.LoginDTO; import com.project.ding.utils.JwtUtils; @@ -20,6 +18,8 @@ import org.aspectj.lang.annotation.Aspect; import org.aspectj.lang.annotation.Pointcut; import org.aspectj.lang.reflect.MethodSignature; import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.security.core.Authentication; +import org.springframework.security.core.context.SecurityContextHolder; import org.springframework.stereotype.Component; import org.springframework.web.context.request.RequestContextHolder; import org.springframework.web.context.request.ServletRequestAttributes; @@ -42,86 +42,119 @@ public class OperationLogAspect { @Autowired private DescriptionManager descriptionManager; - private final ThreadLocal operationLogDTOThreadLocal = new ThreadLocal<>(); - - //定义切点,拦截所有添加@OperationLog注解的方法 + // 定义切点,拦截所有添加@OperationLog注解的方法 @Pointcut("@annotation(com.project.operation.annotation.OperationLog)") public void pointcutOperationLog() {} - //环绕通知,在方法执行前后拦截,收集日志 + // 环绕通知,在方法执行前后拦截,收集日志(核心改造) @Around("pointcutOperationLog()") public Object around(ProceedingJoinPoint joinPoint) throws Throwable { - //获取开始时间 + //初始化日志DTO + OperationLogDTO operationLogDTO = new OperationLogDTO(); long startTime = System.currentTimeMillis(); + Object businessResult = null; - OperationLogDTO operationLogDTO = new OperationLogDTO(); - //获取客户端IP和操作用户 + try { + //收集请求上下文(IP、用户ID等) + collectRequestContext(operationLogDTO); + //收集方法和注解信息 + collectMethodAndAnnotationInfo(joinPoint, operationLogDTO); + //执行业务方法 + businessResult = joinPoint.proceed(); + //获取用户ID + handleLoginSceneUserId(operationLogDTO, joinPoint, businessResult); + operationLogDTO.setResult(0); + } catch (Exception e) { + operationLogDTO.setResult(1); + operationLogDTO.setException(e.getMessage()); + throw e; + } finally { + operationLogDTO.setCostTime(System.currentTimeMillis() - startTime); + saveOperationLogAsync(operationLogDTO); + } + + return businessResult; + } + + /** + * 收集请求上下文(IP、用户ID等) + */ + private void collectRequestContext(OperationLogDTO operationLogDTO) { ServletRequestAttributes requestAttributes = (ServletRequestAttributes) RequestContextHolder.getRequestAttributes(); - if (requestAttributes != null) { - HttpServletRequest request = requestAttributes.getRequest(); - operationLogDTO.setClientIp(request.getRemoteAddr()); - - String header = request.getHeader("Authorization"); - if (StringUtils.isNotBlank(header) && header.startsWith("Bearer ")) { - String token = header.substring(7); - String userId = jwtUtils.parseToken(token).getSubject(); - operationLogDTO.setCreatorId(Long.parseLong(userId)); + if (requestAttributes == null) { + return; + } + + HttpServletRequest request = requestAttributes.getRequest(); + // 收集客户端IP + operationLogDTO.setClientIp(request.getRemoteAddr()); + + // 收集登录用户ID + Authentication authentication = SecurityContextHolder.getContext().getAuthentication(); + if (authentication != null && authentication.getPrincipal() != null) { + Object principal = authentication.getPrincipal(); + try { + Long userId = Long.parseLong(principal.toString()); + operationLogDTO.setCreatorId(userId); + } catch (NumberFormatException e) { + log.warn("解析用户ID失败,principal:{}", principal, e); } } + } - //获取方法信息 + /** + * 收集方法和注解信息 + */ + private void collectMethodAndAnnotationInfo(ProceedingJoinPoint joinPoint, OperationLogDTO operationLogDTO) throws Exception { MethodSignature signature = (MethodSignature) joinPoint.getSignature(); Method method = signature.getMethod(); + // 方法全路径:包名+类名+方法名 operationLogDTO.setMethod(method.getDeclaringClass().getName() + "." + method.getName()); - //获取操作信息 + // 获取注解信息 OperationLog annotation = method.getAnnotation(OperationLog.class); operationLogDTO.setModule(annotation.module()); + ModuleEnum moduleEnum = ModuleEnum.findByValue(annotation.module()); - if(moduleEnum != null){ - descriptionManager.process(moduleEnum.name(),joinPoint.getArgs(),operationLogDTO,method.getName()); - }else{ + if (moduleEnum != null) { + descriptionManager.process(moduleEnum.name(), joinPoint.getArgs(), operationLogDTO, method.getName()); + } else { operationLogDTO.setAction(annotation.action()); operationLogDTO.setDescription(annotation.description()); } + } - - - Object businessResult; - try { - operationLogDTOThreadLocal.set(operationLogDTO); - businessResult = joinPoint.proceed(); - operationLogDTO.setResult(0); - }catch (Exception e){ - operationLogDTO.setResult(1); - operationLogDTO.setException(e.getMessage()); - throw e; - }finally { - operationLogDTO.setCostTime(System.currentTimeMillis() - startTime); - //保存日志 - operationLogApplicationService.saveOperationLog(operationLogDTO); + /** + * 处理登录场景的用户ID(从JWT Token解析) + */ + private void handleLoginSceneUserId(OperationLogDTO operationLogDTO, ProceedingJoinPoint joinPoint, Object businessResult) { + MethodSignature signature = (MethodSignature) joinPoint.getSignature(); + String methodFullName = signature.getMethod().getDeclaringClass().getName() + "." + signature.getMethod().getName(); + + // 仅登录方法处理JWT解析 + if (methodFullName.contains("login") && businessResult instanceof Result) { + try { + LoginDTO data = ((Result) businessResult).getData(); + if (data != null && data.getToken() != null) { + String userId = jwtUtils.parseToken(data.getToken()).getSubject(); + operationLogDTO.setCreatorId(Long.parseLong(userId)); + } + } catch (Exception e) { + log.error("解析登录Token获取用户ID失败", e); + } } - - return businessResult; } - @AfterReturning(returning = "result",pointcut = "pointcutOperationLog()") - public void afterReturning(Object result) throws Throwable { - OperationLogDTO operationLogDTO = operationLogDTOThreadLocal.get(); - if (operationLogDTO == null) { - return; // 无上下文,直接返回 - } + /** + * 异步保存操作日志 + */ + private void saveOperationLogAsync(OperationLogDTO operationLogDTO) { try { - //获取当前登陆用户 - if(operationLogDTO.getMethod().contains("login") && result instanceof Result){ - LoginDTO data = ((Result) result).getData(); - String userId = jwtUtils.parseToken(data.getToken()).getSubject(); - operationLogDTO.setCreatorId(Long.parseLong(userId)); - } - }finally { - operationLogDTOThreadLocal.remove(); + // 调用异步保存方法 + operationLogApplicationService.saveOperationLogAsync(operationLogDTO); + } catch (Exception e) { + log.error("提交异步保存日志任务失败", e); } } - } diff --git a/src/main/java/com/project/operation/application/OperationLogApplicationServiceImpl.java b/src/main/java/com/project/operation/application/OperationLogApplicationServiceImpl.java index c4e5529..b33015e 100644 --- a/src/main/java/com/project/operation/application/OperationLogApplicationServiceImpl.java +++ b/src/main/java/com/project/operation/application/OperationLogApplicationServiceImpl.java @@ -1,5 +1,6 @@ package com.project.operation.application; +import com.baomidou.mybatisplus.core.metadata.IPage; import com.project.base.domain.result.Result; import com.project.operation.application.impl.OperationLogApplicationService; import com.project.operation.domain.dto.OperationLogDTO; @@ -8,6 +9,7 @@ import com.project.operation.domain.service.OperationLogBaseService; import com.project.operation.domain.service.SaveOperationLogDomainService; import com.project.operation.domain.service.SearchOperationLogDomainService; import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.scheduling.annotation.Async; import org.springframework.stereotype.Service; import java.util.List; @@ -32,8 +34,14 @@ public class OperationLogApplicationServiceImpl implements OperationLogApplicati * 查询日志 */ @Override - public Result> list(OperationLogParam param) { + public Result> list(OperationLogParam param) { return searchOperationLogDomainService.list(param); } + @Override + @Async("operationLogExecutor") + public void saveOperationLogAsync(OperationLogDTO operationLogDTO) { + this.saveOperationLog(operationLogDTO); + } + } diff --git a/src/main/java/com/project/operation/application/impl/OperationLogApplicationService.java b/src/main/java/com/project/operation/application/impl/OperationLogApplicationService.java index a91278d..0a33109 100644 --- a/src/main/java/com/project/operation/application/impl/OperationLogApplicationService.java +++ b/src/main/java/com/project/operation/application/impl/OperationLogApplicationService.java @@ -1,5 +1,6 @@ package com.project.operation.application.impl; +import com.baomidou.mybatisplus.core.metadata.IPage; import com.project.base.domain.result.Result; import com.project.operation.domain.dto.OperationLogDTO; import com.project.operation.domain.param.OperationLogParam; @@ -15,5 +16,10 @@ public interface OperationLogApplicationService { /** * 查询日志 */ - Result> list(OperationLogParam param); + Result> list(OperationLogParam param); + + /** + * 异步保存日志 + */ + void saveOperationLogAsync(OperationLogDTO operationLogDTO); } diff --git a/src/main/java/com/project/operation/config/AsyncConfig.java b/src/main/java/com/project/operation/config/AsyncConfig.java new file mode 100644 index 0000000..f9c72a3 --- /dev/null +++ b/src/main/java/com/project/operation/config/AsyncConfig.java @@ -0,0 +1,40 @@ +package com.project.operation.config; + +import org.springframework.context.annotation.Bean; +import org.springframework.context.annotation.Configuration; +import org.springframework.scheduling.annotation.EnableAsync; +import org.springframework.scheduling.concurrent.ThreadPoolTaskExecutor; + +import java.util.concurrent.Executor; +import java.util.concurrent.ThreadPoolExecutor; + +/** + * 异步配置类:开启异步支持 + 自定义日志异步线程池 + */ +@Configuration +@EnableAsync +public class AsyncConfig { + + /** + * 自定义日志异步线程池 + */ + @Bean(name = "operationLogExecutor") + public Executor operationLogExecutor() { + ThreadPoolTaskExecutor executor = new ThreadPoolTaskExecutor(); + // 核心线程数(根据业务量调整) + executor.setCorePoolSize(5); + // 最大线程数 + executor.setMaxPoolSize(20); + // 队列容量 + executor.setQueueCapacity(100); + // 线程前缀名(便于日志排查) + executor.setThreadNamePrefix("operation-log-"); + // 线程空闲超时时间 + executor.setKeepAliveSeconds(60); + // 拒绝策略:队列满时由调用线程执行(避免日志丢失) + executor.setRejectedExecutionHandler(new ThreadPoolExecutor.CallerRunsPolicy()); + // 初始化线程池 + executor.initialize(); + return executor; + } +} diff --git a/src/main/java/com/project/operation/controller/OperationLogController.java b/src/main/java/com/project/operation/controller/OperationLogController.java index 6aecb62..6793b68 100644 --- a/src/main/java/com/project/operation/controller/OperationLogController.java +++ b/src/main/java/com/project/operation/controller/OperationLogController.java @@ -1,5 +1,6 @@ package com.project.operation.controller; +import com.baomidou.mybatisplus.core.metadata.IPage; import com.project.base.domain.result.Result; import com.project.operation.application.impl.OperationLogApplicationService; import com.project.operation.domain.dto.OperationLogDTO; @@ -19,7 +20,7 @@ public class OperationLogController { private OperationLogApplicationService operationLogApplicationService; @GetMapping("/list") - public Result> list(OperationLogParam param) throws Exception { + public Result> list(OperationLogParam param) throws Exception { return operationLogApplicationService.list(param); } } diff --git a/src/main/java/com/project/operation/domain/service/SearchOperationLogDomainService.java b/src/main/java/com/project/operation/domain/service/SearchOperationLogDomainService.java index b7313e3..240eaae 100644 --- a/src/main/java/com/project/operation/domain/service/SearchOperationLogDomainService.java +++ b/src/main/java/com/project/operation/domain/service/SearchOperationLogDomainService.java @@ -1,5 +1,6 @@ package com.project.operation.domain.service; +import com.baomidou.mybatisplus.core.metadata.IPage; import com.project.base.domain.result.Result; import com.project.operation.domain.dto.OperationLogDTO; import com.project.operation.domain.param.OperationLogParam; @@ -8,5 +9,5 @@ import java.util.List; public interface SearchOperationLogDomainService { - Result> list(OperationLogParam param); + Result> list(OperationLogParam param); } diff --git a/src/main/java/com/project/operation/domain/service/impl/SearchOperationLogDomainServiceImpl.java b/src/main/java/com/project/operation/domain/service/impl/SearchOperationLogDomainServiceImpl.java index 7ef8f28..4cc3362 100644 --- a/src/main/java/com/project/operation/domain/service/impl/SearchOperationLogDomainServiceImpl.java +++ b/src/main/java/com/project/operation/domain/service/impl/SearchOperationLogDomainServiceImpl.java @@ -5,6 +5,7 @@ import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper; import com.baomidou.mybatisplus.core.metadata.IPage; import com.baomidou.mybatisplus.extension.plugins.pagination.Page; import com.google.common.collect.Lists; +import com.project.appeal.domain.dto.AppealDTO; import com.project.base.domain.result.Result; import com.project.base.domain.utils.PageConverter; import com.project.ding.application.DepartmentApplicationService; @@ -17,6 +18,7 @@ import com.project.operation.domain.entity.OperationLogEntity; import com.project.operation.domain.param.OperationLogParam; import com.project.operation.domain.service.OperationLogBaseService; import com.project.operation.domain.service.SearchOperationLogDomainService; +import com.project.operation.mapper.OperationLogMapper; import com.project.task.domain.entity.TaskEntity; import org.apache.commons.lang3.StringUtils; import org.springframework.beans.factory.annotation.Autowired; @@ -32,7 +34,7 @@ import java.util.stream.Collectors; @Service public class SearchOperationLogDomainServiceImpl implements SearchOperationLogDomainService { @Autowired - private OperationLogBaseService operationLogBaseService; + private OperationLogMapper operationLogMapper; @Autowired private DepartmentApplicationService departmentApplicationService; @Autowired @@ -42,7 +44,7 @@ public class SearchOperationLogDomainServiceImpl implements SearchOperationLogDo * 查询日志 */ @Override - public Result> list(OperationLogParam param) { + public Result> list(OperationLogParam param) { QueryWrapper logQueryWrapper = new QueryWrapper<>(); if (StringUtils.isNotBlank(param.getAction())){ @@ -60,15 +62,17 @@ public class SearchOperationLogDomainServiceImpl implements SearchOperationLogDo //只查执行成功的日志 logQueryWrapper.eq("result",0); logQueryWrapper.orderByDesc("create_time"); - Page page = new Page<>(param.getCurrent(), param.getSize()); - List entityList = operationLogBaseService.page(page,logQueryWrapper).getRecords(); + Page operationLogEntityPage = operationLogMapper.selectPage(PageConverter.toMpPage(param), logQueryWrapper); + IPage operationLogDTOIPage = operationLogEntityPage.convert(entity -> entity.toDTO(OperationLogDTO::new)); + List entityList = operationLogDTOIPage.getRecords(); if (CollectionUtils.isEmpty(entityList)){ - return Result.success(Lists.newArrayList()); + return Result.success(operationLogDTOIPage); } + //收集用户ID,冗余字段 Set idSet = entityList.stream().filter(entity -> entity.getId() != null) - .map(OperationLogEntity::getCreatorId).collect(Collectors.toSet()); + .map(OperationLogDTO::getCreatorId).collect(Collectors.toSet()); List userDTOList = userApplicationService.searchByIds(idSet); Map userDTOMap = userDTOList .stream().collect(Collectors.toMap(userDTO -> userDTO.getId(), userDTO -> userDTO)); @@ -82,20 +86,21 @@ public class SearchOperationLogDomainServiceImpl implements SearchOperationLogDo Map departmentDTOMap = departmentApplicationService.searchByIds(deptIdSet) .stream().collect(Collectors.toMap(departmentDTO -> departmentDTO.getId(), departmentDTO -> departmentDTO)); - return Result.success(entityList.stream() + operationLogDTOIPage.setRecords(entityList.stream() .map(entity -> buildDTO(entity,userDTOMap,departmentDTOMap)) .collect(Collectors.toList())); + + return Result.success(operationLogDTOIPage); } /** * 构建日志DTO */ - private OperationLogDTO buildDTO(OperationLogEntity operationLogEntity,Map userDTOMap,Map departmentDTOMap){ - OperationLogDTO operationLogDTO = operationLogEntity.toDTO(OperationLogDTO::new); - if (!userDTOMap.containsKey(operationLogEntity.getCreatorId().toString())){ + private OperationLogDTO buildDTO(OperationLogDTO operationLogDTO,Map userDTOMap,Map departmentDTOMap){ + if (!userDTOMap.containsKey(operationLogDTO.getCreatorId().toString())){ return operationLogDTO; } - UserDTO userDTO = userDTOMap.get(operationLogEntity.getCreatorId().toString()); + UserDTO userDTO = userDTOMap.get(operationLogDTO.getCreatorId().toString()); operationLogDTO.setUsername(DesensitizedUtil.chineseName(userDTO.getName())); operationLogDTO.setPosition(userDTO.getTitle()); diff --git a/src/main/java/com/project/task/mapper/TaskMapper.java b/src/main/java/com/project/task/mapper/TaskMapper.java index a78267d..866d592 100644 --- a/src/main/java/com/project/task/mapper/TaskMapper.java +++ b/src/main/java/com/project/task/mapper/TaskMapper.java @@ -1,9 +1,39 @@ package com.project.task.mapper; import com.baomidou.mybatisplus.core.mapper.BaseMapper; +import com.project.task.domain.dto.TaskDTO; import com.project.task.domain.entity.TaskEntity; import org.apache.ibatis.annotations.Mapper; +import org.apache.ibatis.annotations.Select; +import org.springframework.data.repository.query.Param; + +import java.util.List; @Mapper public interface TaskMapper extends BaseMapper { + + /** + * 根据关联表单ID,查询考试任务 + */ + @Select({ + "SELECT t.* ", + "FROM evaluator_task t ", + "WHERE t.id = (", + " SELECT e.task_id ", + " FROM evaluator_task_user e ", + " WHERE e.id = #{taskUserId} ", + ")" + }) + TaskEntity getTaskByTaskUserId(@Param("taskUserId") Long taskUserId); + + /** + * 查询考试任务 + */ + @Select({ + "select e.id,l.name as subLineName" + + "from evaluator_task e " + + "LEFT join evaluator_product_line l on e.id = l.id" + + "where l.leaf = 1 and l.name LIKE CONCAT('%', #{subLineName}, '%')" + }) + List getTaskBySubLineName(@Param("subLineName") String subLineName); } diff --git a/src/main/resources/application.yml b/src/main/resources/application.yml index 5d81f67..388948d 100644 --- a/src/main/resources/application.yml +++ b/src/main/resources/application.yml @@ -64,6 +64,9 @@ milvus: host: 172.16.204.50 port: 19530 ding: - appKey: ding7ocyghkjyowg38ck - appSecret: x1SWUdGfiLzjeRAoicGQO49J73sI59gwgPXLLkcoI6DY4M0UZDDND4QT2laNtT22 - agentId: 4145005949 \ No newline at end of file + appKey: ding7qohu1rhsl5cflme + appSecret: GYxRa6GLbfpDTInpAOGrdvZZDWMSJkdDsxbjxnh6kxFijnswnO9oIT6Y9d598VKp + agentId: 4244362006 +algo: + clusterUrl: /api/algorithm/v1/cluster + baseUrl: / \ No newline at end of file