ruoyi-applet/src/main/java/com/ruoyi/web/controller/api/TMissionController.java
@@ -5,11 +5,18 @@ import com.ruoyi.common.basic.PageInfo; import com.ruoyi.common.core.domain.BasePage; import com.ruoyi.common.core.domain.R; import com.ruoyi.common.core.redis.RedisCache; import com.ruoyi.framework.web.service.TokenService; import com.ruoyi.system.dto.TMissionUserDto; import com.ruoyi.system.model.TAppUser; import com.ruoyi.system.model.TMission; import com.ruoyi.system.model.TMissionReassign; import com.ruoyi.system.model.TMissionUser; import com.ruoyi.system.service.TAppUserService; import com.ruoyi.system.service.TMissionReassignService; import com.ruoyi.system.service.TMissionService; import com.ruoyi.system.vo.MissionTotalVo; import com.ruoyi.system.vo.TotalHistoryVo; import io.swagger.annotations.Api; import io.swagger.annotations.ApiOperation; import org.springframework.beans.factory.annotation.Autowired; @@ -17,6 +24,8 @@ import org.springframework.web.bind.annotation.RequestBody; import org.springframework.web.bind.annotation.RequestMapping; import org.springframework.web.bind.annotation.RestController; import java.time.LocalDateTime; /** * <p> @@ -33,12 +42,15 @@ private final TokenService tokenService; private final TAppUserService appUserService; private final TMissionService missionService; private final TMissionReassignService missionReassignService; @Autowired public TMissionController(TokenService tokenService, TAppUserService appUserService, TMissionService missionService) { public TMissionController(TokenService tokenService, TAppUserService appUserService, TMissionService missionService, RedisCache redisCache, TMissionReassignService missionReassignService) { this.tokenService = tokenService; this.appUserService = appUserService; this.missionService = missionService; this.missionReassignService = missionReassignService; } @@ -54,10 +66,11 @@ */ // @PreAuthorize("@ss.hasPermi('system:mission:list')") @ApiOperation(value = "获取任务列表--待执行任务", response = TMission.class) @PostMapping(value = "/api/t-mission/pageList") @PostMapping(value = "/api/t-mission/pageNowList") public R<PageInfo<TMission>> pageList(@RequestBody String param) { BasePage query = JSON.parseObject(param, BasePage.class); return R.ok(missionService.pageList(query)); String userId = tokenService.getLoginUserApplet().getUserId(); return R.ok(missionService.pageNowList(query,userId)); } /** * 获取任务列表 @@ -67,7 +80,7 @@ @PostMapping(value = "/api/t-mission/pageGrabList") public R<PageInfo<TMission>> pageGrabList(@RequestBody String param) { BasePage query = JSON.parseObject(param, BasePage.class); return R.ok(missionService.pageList(query)); return R.ok(missionService.pageGrabList(query)); } /** * 获取任务列表 @@ -77,7 +90,80 @@ @PostMapping(value = "/api/t-mission/pageHistoryList") public R<PageInfo<TMission>> pageHistoryList(@RequestBody String param) { BasePage query = JSON.parseObject(param, BasePage.class); return R.ok(missionService.pageList(query)); String userId = tokenService.getLoginUserApplet().getUserId(); return R.ok(missionService.pageHistoryList(query,userId)); } @ApiOperation(value = "获取任务列表--历史任务汇总", response = TotalHistoryVo.class) @PostMapping(value = "/t-mission/totalHistory") public R<TotalHistoryVo> totalHistory() { String userId = tokenService.getLoginUserApplet().getUserId(); // String userId ="1"; return R.ok(missionService.totalHistory(userId)); } /** * 添加任务 */ @ApiOperation(value = "获取任务列表--添加任务", response = TMission.class) @PostMapping(value = "/api/t-mission/addMission") public R<String> addMission(@RequestBody String param) { TMission tMission = JSON.parseObject(param, TMission.class); String userId = tokenService.getLoginUserApplet().getUserId(); TAppUser appUser = appUserService.getById(userId); tMission.setCommitUserId(userId); tMission.setCommitTime(LocalDateTime.now()); tMission.setCommitUserName(appUser.getNickName()); tMission.setCommitType(2); tMission.setIsMissionPool(0); missionService.save(tMission); return R.ok(tMission.getId()); } /** * 抢单任务 */ @ApiOperation(value = "获取任务列表--抢单任务", response = TMission.class) @PostMapping(value = "/api/t-mission/grabMission") public R<String> grabMission(@RequestBody String param) { String missionId = JSON.parseObject(param, String.class); String userId = tokenService.getLoginUserApplet().getUserId(); return R.ok( missionService.grabMission(missionId,userId)); } /** * 申请支援 */ @ApiOperation(value = "获取任务列表--申请支援/改派", response = TMission.class) @PostMapping(value = "/api/t-mission/requestSupport") public R<?> requestSupport(@RequestBody String param) { TMissionReassign tMissionReassign = JSON.parseObject(param, TMissionReassign.class); String userId = tokenService.getLoginUserApplet().getUserId(); TAppUser appUser = appUserService.getById(userId); tMissionReassign.setCommitUserId(userId); tMissionReassign.setCommitTime(LocalDateTime.now()); tMissionReassign.setCommitUserName(appUser.getNickName()); missionReassignService.save(tMissionReassign); return R.ok(); } /** * 完成任务 */ @ApiOperation(value = "获取任务列表--完成任务汇报", response = TMission.class) @PostMapping(value = "/api/t-mission/successMission") public R<?> successMission(@RequestBody String param) { TMissionUserDto dto = JSON.parseObject(param, TMissionUserDto.class); // String userId = tokenService.getLoginUserApplet().getUserId(); missionService.successMission(dto); return R.ok(); } } ruoyi-applet/src/main/resources/application-test.yml
@@ -95,7 +95,7 @@ druid: # 主库数据源 master: url: jdbc:mysql://127.0.0.1:3306/intelligent_dispatching?autoReconnect=true&useUnicode=true&characterEncoding=utf8&zeroDateTimeBehavior=convertToNull&allowPublicKeyRetrieval=true&useSSL=false&serverTimezone=Asia/Shanghai url: jdbc:mysql://192.168.110.34:3306/intelligent_dispatching?autoReconnect=true&useUnicode=true&characterEncoding=utf8&zeroDateTimeBehavior=convertToNull&allowPublicKeyRetrieval=true&useSSL=false&serverTimezone=Asia/Shanghai username: root password: 123456 # 从库数据源 ruoyi-common/src/main/java/com/ruoyi/common/utils/poi/ExcelHandlerAdapter.java
@@ -1,7 +1,6 @@ package com.ruoyi.common.utils.poi; import javafx.scene.control.Cell; /** * Excel数据格式处理适配器 ruoyi-framework/src/main/java/com/ruoyi/framework/config/SecurityConfig.java
@@ -118,7 +118,7 @@ "/applet/changepwd", "/captchaImage","/getCode","/loginCode", "/operations/getBySingleNum/**", "/user/getUserInfoByNumber/**", "/wxLogin/**","/cos/get/**" "/wxLogin/**","/cos/get/**","/t-mission/**" ).permitAll() // 静态资源,可匿名访问 .antMatchers(HttpMethod.GET, "/", "/*.html", "/**/*.html", "/**/*.css", "/**/*.js", "/profile/**").permitAll() ruoyi-system/src/main/java/com/ruoyi/system/dto/TMissionUserDto.java
New file @@ -0,0 +1,67 @@ package com.ruoyi.system.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 io.swagger.annotations.ApiModel; import io.swagger.annotations.ApiModelProperty; import lombok.Data; import lombok.EqualsAndHashCode; import java.io.Serializable; import java.time.LocalDateTime; import java.util.Date; /** * <p> * 任务用户 * </p> * * @author xiaochen * @since 2025-09-28 */ @Data @ApiModel("完成汇报Dto") public class TMissionUserDto{ @TableId(value = "id", type = IdType.ASSIGN_ID) private String id; @ApiModelProperty(value = "接单用户") @TableField("app_user_id") private String appUserId; @ApiModelProperty(value = "任务id") @TableField("mission_id") private String missionId; @ApiModelProperty(value = "任务状态 1已完成 2未完成") private Integer status; @ApiModelProperty(value = "战损备注") @TableField("loss_remark") private String lossRemark; @ApiModelProperty(value = "战果备注") @TableField("victory_remark") private String victoryRemark; @ApiModelProperty(value = "战损json详情") @TableField("loss_text") private String lossText; @ApiModelProperty(value = "战果json详情") @TableField("victory_text") private String victoryText; @ApiModelProperty(value = "任务结果") private String result; @ApiModelProperty(value = "任务结果图片") @TableField("result_img") private String resultImg; @ApiModelProperty(value = "任务结果视频") @TableField("result_video") private String resultVideo; @ApiModelProperty(value = "任务结果音频") @TableField("result_voice") private String resultVoice; } ruoyi-system/src/main/java/com/ruoyi/system/mapper/TMissionMapper.java
@@ -3,6 +3,9 @@ import com.baomidou.mybatisplus.core.mapper.BaseMapper; import com.ruoyi.common.basic.PageInfo; import com.ruoyi.system.model.TMission; import org.apache.ibatis.annotations.Param; import java.util.List; import com.ruoyi.system.query.TMissionQuery; import com.ruoyi.system.vo.TMissionReassignVO; import com.ruoyi.system.vo.TMissionVO; @@ -20,6 +23,12 @@ */ public interface TMissionMapper extends BaseMapper<TMission> { List<TMission> pageNowList(@Param("pageInfo") PageInfo<TMission> pageInfo, @Param("userId") String userId); List<TMission> pageHistoryList(@Param("pageInfo") PageInfo<TMission> pageInfo, @Param("userId") String userId); /** * 获取任务管理列表 * @param pageInfo ruoyi-system/src/main/java/com/ruoyi/system/model/TMission.java
@@ -128,4 +128,10 @@ private Integer isMissionPool; @ApiModelProperty(value = "用户任务id") @TableField(exist = false) private String userMissionId; } ruoyi-system/src/main/java/com/ruoyi/system/model/TMissionUser.java
@@ -11,6 +11,7 @@ import java.io.Serializable; import java.time.LocalDateTime; import java.util.Date; /** * <p> @@ -46,4 +47,37 @@ @TableField("user_type") private Integer userType; @ApiModelProperty(value = "任务状态 0待完成 1已完成 2未完成") private Integer status; @ApiModelProperty(value = "任务完成时间") @TableField("success_time") private Date successTime; @ApiModelProperty(value = "战损备注") @TableField("loss_remark") private String lossRemark; @ApiModelProperty(value = "战果备注") @TableField("victory_remark") private String victoryRemark; @ApiModelProperty(value = "战损json详情") @TableField("loss_text") private String lossText; @ApiModelProperty(value = "战果json详情") @TableField("victory_text") private String victoryText; @ApiModelProperty(value = "任务结果") private String result; @ApiModelProperty(value = "任务结果图片") @TableField("result_img") private String resultImg; @ApiModelProperty(value = "任务结果视频") @TableField("result_video") private String resultVideo; @ApiModelProperty(value = "任务结果音频") @TableField("result_voice") private String resultVoice; } ruoyi-system/src/main/java/com/ruoyi/system/service/TMissionService.java
@@ -2,10 +2,14 @@ import com.baomidou.mybatisplus.extension.service.IService; import com.ruoyi.common.basic.PageInfo; import com.ruoyi.common.core.domain.BasePage; import com.ruoyi.system.dto.TMissionUserDto; import com.ruoyi.system.model.TMission; import com.ruoyi.system.query.TMissionQuery; import com.ruoyi.system.vo.MissionTotalVo; import com.ruoyi.system.vo.TMissionReassignVO; import com.ruoyi.system.vo.TMissionVO; import com.ruoyi.system.vo.TotalHistoryVo; /** * <p> @@ -22,6 +26,21 @@ * @param query * @return */ PageInfo<TMissionVO> pageList(TMissionQuery query); MissionTotalVo missionTotal(String userId); String grabMission(String missionId, String userId); PageInfo<TMission> pageNowList(BasePage query,String userId); PageInfo<TMission> pageGrabList(BasePage query); PageInfo<TMission> pageHistoryList(BasePage query, String userId); PageInfo<TMissionVO> pageListAssigned(TMissionQuery query); /** @@ -38,4 +57,9 @@ */ PageInfo<TMissionVO> pageListMissionPool(TMissionQuery query); TotalHistoryVo totalHistory(String userId); void successMission(TMissionUserDto dto); } ruoyi-system/src/main/java/com/ruoyi/system/service/impl/TMissionServiceImpl.java
@@ -1,19 +1,38 @@ package com.ruoyi.system.service.impl; import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper; import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl; import com.ruoyi.common.basic.PageInfo; import com.ruoyi.common.core.domain.BaseModel; import com.ruoyi.common.core.domain.BasePage; import com.ruoyi.common.core.redis.RedisCache; import com.ruoyi.system.dto.TMissionUserDto; import com.ruoyi.system.mapper.TMissionMapper; import com.ruoyi.system.mapper.TMissionUserMapper; import com.ruoyi.system.model.TMission; import com.ruoyi.system.model.TMissionUser; import com.ruoyi.system.query.TMissionQuery; import com.ruoyi.system.service.TMissionService; import com.ruoyi.system.vo.MissionTotalVo; import com.ruoyi.system.vo.TMissionReassignVO; import com.ruoyi.system.vo.TMissionVO; import com.ruoyi.system.vo.TotalHistoryVo; import org.springframework.stereotype.Service; import org.springframework.util.CollectionUtils; import java.text.SimpleDateFormat; import java.time.Duration; import java.time.LocalDate; import java.time.LocalDateTime; import java.util.List; import java.util.Objects; import javax.annotation.Resource; import java.math.BigDecimal; import java.math.RoundingMode; import java.util.List; import java.util.UUID; import java.util.stream.Collectors; /** * <p> @@ -25,6 +44,12 @@ */ @Service public class TMissionServiceImpl extends ServiceImpl<TMissionMapper, TMission> implements TMissionService { @Resource private TMissionUserMapper missionUserMapper; @Resource private RedisCache redisCache; @Override public PageInfo<TMissionVO> pageListAssigned(TMissionQuery query) { @@ -89,4 +114,106 @@ pageInfo.setRecords(list); return pageInfo; } @Override public TotalHistoryVo totalHistory(String userId) { TotalHistoryVo totalHistoryVo = new TotalHistoryVo(); List<TMissionUser> tMissionUsers = missionUserMapper.selectList(new LambdaQueryWrapper<TMissionUser>().eq(TMissionUser::getAppUserId, userId)); if(tMissionUsers.isEmpty()){ return totalHistoryVo; } long count = tMissionUsers.stream().filter(e -> e.getStatus() == 1).count(); BigDecimal successRate = new BigDecimal(count).divide(new BigDecimal(tMissionUsers.size()), 4, RoundingMode.HALF_UP).multiply(BigDecimal.valueOf(100)); totalHistoryVo.setSuccessRate(successRate); long count1 = tMissionUsers.stream().filter(e -> e.getStatus() == 2).count(); BigDecimal failRate = new BigDecimal(count1).divide(new BigDecimal(tMissionUsers.size()), 4, RoundingMode.HALF_UP).multiply(BigDecimal.valueOf(100)); totalHistoryVo.setFailRate(failRate); SimpleDateFormat simpleDateFormat = new SimpleDateFormat("yyyy-MM-dd"); SimpleDateFormat simpleDateFormat1 = new SimpleDateFormat("yyyy-MM"); // 查询当前时间的年月日 String now = LocalDate.now().toString(); List<TMissionUser> todayMissionUsers = tMissionUsers.stream().filter(e -> now.equals(simpleDateFormat.format(e.getSuccessTime()))).collect(Collectors.toList()); totalHistoryVo.setTodaySuccessNum(todayMissionUsers.size()); // 查询当前时间的年月 String firstDayOfMonth = LocalDate.now().withDayOfMonth(1).toString().substring(0, 7); List<TMissionUser> monthMissionUsers = tMissionUsers.stream().filter(e -> firstDayOfMonth.equals(simpleDateFormat1.format(e.getSuccessTime()))).collect(Collectors.toList()); totalHistoryVo.setMonthSuccessNum(monthMissionUsers.size()); return totalHistoryVo; } @Override public void successMission(TMissionUserDto dto) { } @Override public PageInfo<TMissionVO> pageList(TMissionQuery query) { return null; } @Override public MissionTotalVo missionTotal(String userId) { MissionTotalVo missionTotalVo = new MissionTotalVo(); List<TMissionUser> tMissionUsers = missionUserMapper.selectList(new LambdaQueryWrapper<TMissionUser>().eq(TMissionUser::getAppUserId, userId).eq(TMissionUser::getStatus, 0)); if(tMissionUsers.isEmpty()){ return missionTotalVo; } List<String> missionIds = tMissionUsers.stream().map(TMissionUser::getMissionId).collect(Collectors.toList()); List<TMission> tMissions = this.baseMapper.selectBatchIds(missionIds); long count = tMissions.stream().filter(e -> e.getStatus() == 2).count(); missionTotalVo.setNowNum((int) count); missionTotalVo.setWaitNum(tMissions.size()-missionTotalVo.getNowNum()); List<TMissionUser> collect = tMissionUsers.stream().filter(e -> e.getStatus() == 1).collect(Collectors.toList()); missionTotalVo.setRate(new BigDecimal(collect.size()).divide(new BigDecimal(tMissionUsers.size()),2, RoundingMode.HALF_UP)); return missionTotalVo; } @Override public String grabMission(String missionId, String userId) { try { boolean b = redisCache.trylockLoop(missionId, UUID.randomUUID().toString(), 30); if(b){ TMissionUser tMissionUser = new TMissionUser(); tMissionUser.setAppUserId(userId); tMissionUser.setMissionId(missionId); tMissionUser.setStatus(0); tMissionUser.setUserType(1); missionUserMapper.insert(tMissionUser); return tMissionUser.getMissionId(); } }finally { redisCache.unlock(missionId, UUID.randomUUID().toString()); } return null; } @Override public PageInfo<TMission> pageNowList(BasePage query,String userId) { PageInfo<TMission> pageInfo = new PageInfo<>(query.getPageNum(), query.getPageSize()); List<TMission> list = this.baseMapper.pageNowList(pageInfo,userId); pageInfo.setRecords(list); return pageInfo; } @Override public PageInfo<TMission> pageGrabList(BasePage query) { PageInfo<TMission> pageInfo = new PageInfo<>(query.getPageNum(), query.getPageSize()); PageInfo<TMission> tMissionPageInfo = this.baseMapper.selectPage(pageInfo, new LambdaQueryWrapper<TMission>().eq(TMission::getStatus, 1).eq(TMission::getIsMissionPool, 1).orderByDesc(BaseModel::getCreateTime)); return tMissionPageInfo; } @Override public PageInfo<TMission> pageHistoryList(BasePage query, String userId) { PageInfo<TMission> pageInfo = new PageInfo<>(query.getPageNum(), query.getPageSize()); List<TMission> list = this.baseMapper.pageHistoryList(pageInfo,userId); pageInfo.setRecords(list); return pageInfo; } } ruoyi-system/src/main/java/com/ruoyi/system/vo/MissionTotalVo.java
@@ -9,12 +9,12 @@ @Data @ApiModel("app任务汇总数") public class MissionTotalVo { @ApiModelProperty("执行中") private Integer nowNum; @ApiModelProperty("执行中 2=待完成") private Integer nowNum=0; @ApiModelProperty("待执行") private Integer waitNum; private Integer waitNum=0; @ApiModelProperty("进度") private BigDecimal rate; private BigDecimal rate=BigDecimal.ZERO; } ruoyi-system/src/main/java/com/ruoyi/system/vo/TotalHistoryVo.java
New file @@ -0,0 +1,22 @@ package com.ruoyi.system.vo; import io.swagger.annotations.ApiModel; import io.swagger.annotations.ApiModelProperty; import lombok.Data; import java.math.BigDecimal; @Data @ApiModel("app历史任务顶部汇总") public class TotalHistoryVo { @ApiModelProperty("任务完成率") private BigDecimal successRate=BigDecimal.ZERO; @ApiModelProperty("任务失败率") private BigDecimal failRate=BigDecimal.ZERO; @ApiModelProperty("今日完成数") private Integer todaySuccessNum=0; @ApiModelProperty("本月完成数") private Integer monthSuccessNum=0; } ruoyi-system/src/main/resources/mapper/system/TMissionMapper.xml
@@ -42,6 +42,16 @@ address_score, time_score, person_count_score, equipment_score, attempt_score,assign_time,receive_time, finish_time,is_mission_pool, create_time,update_time, create_by, update_by, disabled </sql> <select id="pageNowList" resultType="com.ruoyi.system.model.TMission"> select t1.id as userMissionId,t2.* from t_mission_user t1 left join t_mission t2 on t1.mission_id =t2.id where t1.status =0 and t1.app_user_id = #{userId} and t2.status = 2 order by t2.create_time desc </select> <select id="pageHistoryList" resultType="com.ruoyi.system.model.TMission"> select t2.* from t_mission_user t1 left join t_mission t2 on t1.mission_id =t2.id where t1.status =1 and t1.app_user_id = #{userId} order by t2.create_time desc </select> <select id="pageListAssigned" resultType="com.ruoyi.system.vo.TMissionVO"> select tm.id, tm.urgency_level, tm.address, tm.mission_lon, tm.mission_lat, tm.mission_content, tm.mission_audio, tm.mission_pictures, tm.mission_electronic, tm.status, tm.mission_type_id, tm.assign_time,tm.receive_time,tm.finish_time,tmu.app_user_id,