diff --git a/urbanops-module-garden/src/main/java/com/zteits/urbanops/module/garden/controller/app/homepage/vo/TaskDetailsRspVo.java b/urbanops-module-garden/src/main/java/com/zteits/urbanops/module/garden/controller/app/homepage/vo/TaskDetailsRspVo.java index d4634ad..7a698d0 100644 --- a/urbanops-module-garden/src/main/java/com/zteits/urbanops/module/garden/controller/app/homepage/vo/TaskDetailsRspVo.java +++ b/urbanops-module-garden/src/main/java/com/zteits/urbanops/module/garden/controller/app/homepage/vo/TaskDetailsRspVo.java @@ -17,9 +17,13 @@ public class TaskDetailsRspVo { private String taskName; /*创建时间或完成时间*/ private LocalDateTime busiDateTime; - /** - * 紧急程度:1:特急;2:紧急;3:一般 - */ + /*紧急程度:1:特急;2:紧急;3:一般*/ private Integer pressingType; + /*计划编码*/ + private String planNo; + /*批次号*/ + private String batchNo; + /*任务类型:inspection/maintain/workorder*/ + private String taskType; } diff --git a/urbanops-module-garden/src/main/java/com/zteits/urbanops/module/garden/controller/app/homepage/vo/TaskDistanceSortRespVO.java b/urbanops-module-garden/src/main/java/com/zteits/urbanops/module/garden/controller/app/homepage/vo/TaskDistanceSortRespVO.java index 85777f8..b39709b 100644 --- a/urbanops-module-garden/src/main/java/com/zteits/urbanops/module/garden/controller/app/homepage/vo/TaskDistanceSortRespVO.java +++ b/urbanops-module-garden/src/main/java/com/zteits/urbanops/module/garden/controller/app/homepage/vo/TaskDistanceSortRespVO.java @@ -14,9 +14,6 @@ import java.math.BigDecimal; @EqualsAndHashCode(callSuper = true) public class TaskDistanceSortRespVO extends TaskDetailsRspVo { - /** 任务类型:inspection / maintain / workorder */ - private String taskType; - /** 任务点经度 */ private BigDecimal taskLon; @@ -47,6 +44,9 @@ public class TaskDistanceSortRespVO extends TaskDetailsRspVo { /** 效率得分(已截断) */ private Double efficiencyScore; + /** 员工历史任务完成效率 %,100=班组均值,大于100比班组快,小于100比班组慢 */ + private Integer efficiencyPercent; + /** 综合得分 */ private Double compositeScore; diff --git a/urbanops-module-garden/src/main/java/com/zteits/urbanops/module/garden/service/homepage/HomepageSummaryServiceImpl.java b/urbanops-module-garden/src/main/java/com/zteits/urbanops/module/garden/service/homepage/HomepageSummaryServiceImpl.java index d7ebc7d..5517afc 100644 --- a/urbanops-module-garden/src/main/java/com/zteits/urbanops/module/garden/service/homepage/HomepageSummaryServiceImpl.java +++ b/urbanops-module-garden/src/main/java/com/zteits/urbanops/module/garden/service/homepage/HomepageSummaryServiceImpl.java @@ -3,6 +3,7 @@ package com.zteits.urbanops.module.garden.service.homepage; import cn.hutool.core.bean.BeanUtil; import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper; import com.baomidou.mybatisplus.core.metadata.IPage; +import com.alibaba.fastjson.JSON; import com.esotericsoftware.minlog.Log; import com.zteits.urbanops.framework.common.pojo.PageResult; import com.zteits.urbanops.framework.common.util.date.DateUtils; @@ -465,6 +466,7 @@ public class HomepageSummaryServiceImpl implements HomepageSummaryService{ result.setEstimatedTotalWalkingMinutes(totalWalkMin); result.setEstimatedTotalTricycleMinutes(totalTriMin); + Log.info("返回App参数: " + JSON.toJSONString(result)); return result; } @@ -480,10 +482,15 @@ public class HomepageSummaryServiceImpl implements HomepageSummaryService{ if (mpPage != null && CollectionUtils.isNotEmpty(mpPage.getRecords())) { int i = 0; for (TaskDetailsRspVo vo : mpPage.getRecords()) { + // 跳过工单,仅返回巡查/养护 + if ("workorder".equals(vo.getTaskType())) continue; TaskDistanceSortRespVO sortVo = new TaskDistanceSortRespVO(); sortVo.setTaskName(vo.getTaskName()); sortVo.setBusiDateTime(vo.getBusiDateTime()); sortVo.setPressingType(vo.getPressingType()); + sortVo.setPlanNo(vo.getPlanNo()); + sortVo.setBatchNo(vo.getBatchNo()); + sortVo.setTaskType(vo.getTaskType()); sortVo.setSortOrder(++i); sortVo.setDistance(null); sortVo.setCumulativeDistance(null); @@ -492,6 +499,7 @@ public class HomepageSummaryServiceImpl implements HomepageSummaryService{ result.add(sortVo); } } + Log.info("返回App参数: " + JSON.toJSONString(result)); return result; } @@ -620,8 +628,9 @@ public class HomepageSummaryServiceImpl implements HomepageSummaryService{ } int memberCount = teamData.size(); teamProgress.setTeamMemberCount(memberCount); - teamProgress.setTeamAverage(memberCount > 0 - ? Math.round(totalCompleted * 10.0 / memberCount) / 10.0 : 0.0); + double avg = memberCount > 0 ? Math.round(totalCompleted * 10.0 / memberCount) / 10.0 : 0.0; + if (avg == 0.0 && totalCompleted > 0) avg = 0.1; + teamProgress.setTeamAverage(avg); teamProgress.setTeamMax(maxCompleted); } } catch (Exception e) { @@ -643,7 +652,8 @@ public class HomepageSummaryServiceImpl implements HomepageSummaryService{ result.setSortedTasks(sortedTasks); result.setTeamProgress(teamProgress); result.setTotalPendingTasks(sortedTasks.size()); - return result; + Log.info("返回App参数: " + JSON.toJSONString(result)); + return result; } List roleIds = roleApi.getRoleIdsByUserId(userId); @@ -676,31 +686,34 @@ public class HomepageSummaryServiceImpl implements HomepageSummaryService{ .queryPendingTaskDetailsWithGps(roleIds, userId, deptId, LocalDateTime.now()); // 3. 查询效率矩阵 - Map effMap = loadEfficiencyMap(userId); + Map effMap = loadEfficiencyMap(userId); // 4. 为每个任务打分 List tasksWithGps = new ArrayList<>(); List tasksWithoutGps = new ArrayList<>(); if (CollectionUtils.isNotEmpty(allTasks)) { for (TaskDistanceSortRespVO task : allTasks) { + UserTaskEfficiencyDO effDO = lookupEfficiency(effMap, task.getTaskType(), task.getTaskSubType()); + BigDecimal effRatio = (effDO != null && effDO.getEfficiencyRatio() != null) + ? effDO.getEfficiencyRatio() : BigDecimal.ONE; + double effScore = clamp(effRatio.doubleValue(), clampMin, clampMax); + task.setEfficiencyScore(Math.round(effScore * 100.0) / 100.0); + task.setEfficiencyPercent((int) Math.round(effRatio.doubleValue() * 100)); + if (effDO != null) { + task.setUserAvgMinutes(effDO.getAvgMinutes()); + task.setTeamAvgMinutes(effDO.getTeamAvgMinutes()); + } + if (task.getTaskLat() != null && task.getTaskLon() != null) { double dist = GpsDistanceUtil.haversineDistance( req.getCurrentLat().doubleValue(), req.getCurrentLon().doubleValue(), task.getTaskLat().doubleValue(), task.getTaskLon().doubleValue()); double distScore = Math.max(0, 1 - dist / threshold); task.setDistanceScore(Math.round(distScore * 100.0) / 100.0); - - BigDecimal effRatio = lookupEfficiency(effMap, task.getTaskType(), task.getTaskSubType()); - double effScore = clamp(effRatio.doubleValue(), clampMin, clampMax); - task.setEfficiencyScore(Math.round(effScore * 100.0) / 100.0); - task.setCompositeScore(Math.round((distWeight * distScore + effWeight * effScore) * 100.0) / 100.0); tasksWithGps.add(task); } else { - BigDecimal effRatio = lookupEfficiency(effMap, task.getTaskType(), task.getTaskSubType()); - double effScore = clamp(effRatio.doubleValue(), clampMin, clampMax); task.setDistanceScore(0.0); - task.setEfficiencyScore(Math.round(effScore * 100.0) / 100.0); task.setCompositeScore(Math.round((effWeight * effScore) * 100.0) / 100.0); tasksWithoutGps.add(task); } @@ -744,19 +757,19 @@ public class HomepageSummaryServiceImpl implements HomepageSummaryService{ if (t.getDistance() != null) totalDist += t.getDistance(); } result.setEstimatedTotalDistance(totalDist); + Log.info("返回App参数: " + JSON.toJSONString(result)); return result; } /** * 加载当前用户当月效率矩阵 */ - private Map loadEfficiencyMap(Long userId) { - Map map = new LinkedHashMap<>(); + private Map loadEfficiencyMap(Long userId) { + Map map = new LinkedHashMap<>(); try { String statPeriod = java.time.LocalDate.now().format(java.time.format.DateTimeFormatter.ofPattern("yyyy-MM")); List list = userTaskEfficiencyMapper.selectByUserIdAndPeriod(userId, statPeriod); if (CollectionUtils.isEmpty(list)) { - // fallback: 查最近一个周期的数据 String latestPeriod = userTaskEfficiencyMapper.selectLatestPeriod(userId); if (latestPeriod != null) { list = userTaskEfficiencyMapper.selectByUserIdAndPeriod(userId, latestPeriod); @@ -765,7 +778,7 @@ public class HomepageSummaryServiceImpl implements HomepageSummaryService{ if (CollectionUtils.isNotEmpty(list)) { for (UserTaskEfficiencyDO e : list) { String key = e.getTaskCategory() + "_" + e.getTaskType(); - map.put(key, e.getEfficiencyRatio() != null ? e.getEfficiencyRatio() : BigDecimal.ONE); + map.put(key, e); } } } catch (Exception e) { @@ -774,18 +787,12 @@ public class HomepageSummaryServiceImpl implements HomepageSummaryService{ return map; } - /** - * 从效率矩阵查找,先精确匹配再 fallback 大类 - */ - private BigDecimal lookupEfficiency(Map map, String category, String subType) { - // 精确匹配 + private UserTaskEfficiencyDO lookupEfficiency(Map map, String category, String subType) { String exactKey = category + "_" + subType; if (map.containsKey(exactKey)) return map.get(exactKey); - // fallback: 大类汇总 String fallbackKey = category + "_ALL"; if (map.containsKey(fallbackKey)) return map.get(fallbackKey); - // 无数据:中性 - return BigDecimal.ONE; + return null; } private double clamp(double val, double min, double max) { diff --git a/urbanops-module-garden/src/main/resources/mapper/homepage/HomepageSummaryMapper.xml b/urbanops-module-garden/src/main/resources/mapper/homepage/HomepageSummaryMapper.xml index 2cc3067..f15b98b 100644 --- a/urbanops-module-garden/src/main/resources/mapper/homepage/HomepageSummaryMapper.xml +++ b/urbanops-module-garden/src/main/resources/mapper/homepage/HomepageSummaryMapper.xml @@ -376,26 +376,29 @@ - SELECT taskName, busiDateTime, pressingType, taskLat, taskLon, taskType, taskSubType + SELECT taskName, busiDateTime, pressingType, taskLat, taskLon, taskType, taskSubType, planNo, batchNo FROM ( SELECT a.plan_name AS taskName, @@ -628,7 +631,9 @@ (CAST(r.starting_longitude AS DECIMAL(18,10)) + CAST(r.end_longitude AS DECIMAL(18,10))) / 2 AS taskLon, 'inspection' AS taskType, - a.plan_type_id AS taskSubType + a.plan_type_id AS taskSubType, + c.plan_no AS planNo, + c.batch_no AS batchNo FROM garden_inspection_plan a INNER JOIN garden_inspection_plan_role b ON a.batch_no = b.batch_no INNER JOIN garden_inspection_plan_detail c ON a.batch_no = c.batch_no @@ -655,7 +660,9 @@ (CAST(r.starting_longitude AS DECIMAL(18,10)) + CAST(r.end_longitude AS DECIMAL(18,10))) / 2 AS taskLon, 'maintain' AS taskType, - a.plan_type_id AS taskSubType + a.plan_type_id AS taskSubType, + c.plan_no AS planNo, + c.batch_no AS batchNo FROM garden_maintain_plan a INNER JOIN garden_maintain_plan_role b ON a.batch_no = b.batch_no INNER JOIN garden_maintain_plan_detail c ON a.batch_no = c.batch_no @@ -670,23 +677,6 @@ #{roleId} AND r.starting_latitude IS NOT NULL AND r.starting_latitude != '' - - UNION ALL - - SELECT - m.order_name AS taskName, - m.create_time AS busiDateTime, - m.pressing_type AS pressingType, - m.lat AS taskLat, - m.lon AS taskLon, - 'workorder' AS taskType, - m.order_type AS taskSubType - FROM act_ru_task t - LEFT JOIN workorder_main_info m - ON t.PROC_INST_ID_ = m.process_instance_id AND m.deleted = 0 - WHERE t.SUSPENSION_STATE_ = 1 - AND m.order_name IS NOT NULL - AND t.ASSIGNEE_ = #{userId} ) t