xp-robotaxi-api/src/main/java/com/xiaopeng/api/factory/maintenance/XpTaskClientFallbackFactory.java
New file @@ -0,0 +1,27 @@ package com.xiaopeng.api.factory.maintenance; import com.xiaopeng.api.feignClient.maintenance.XpTaskClient; import com.xiaopeng.api.model.maintenance.XpTask; import com.xiaopeng.common.core.domain.R; import lombok.extern.slf4j.Slf4j; import org.springframework.cloud.openfeign.FallbackFactory; import org.springframework.stereotype.Component; @Slf4j @Component public class XpTaskClientFallbackFactory implements FallbackFactory<XpTaskClient> { @Override public XpTaskClient create(Throwable cause) { return new XpTaskClient() { @Override public R<XpTask> queryInfoByVehicleId(Long vehicleId) { log.error("通过车辆id查询上一次保养记录失败, vehicleId={}, 异常: {}", vehicleId, cause.getMessage(), cause); // 降级策略: 返回 false (未上班状态) return R.fail("通过车辆id查询上一次保养记录失败,"+cause.getMessage()); } }; } } xp-robotaxi-api/src/main/java/com/xiaopeng/api/factory/maintenance/XpTaskHandleDetailRoutineClientFallbackFactory.java
New file @@ -0,0 +1,20 @@ package com.xiaopeng.api.factory.maintenance; import com.xiaopeng.api.feignClient.maintenance.XpTaskHandleDetailRoutineClient; import com.xiaopeng.api.model.maintenance.XpTaskHandleDetailRoutine; import com.xiaopeng.common.core.domain.R; import lombok.extern.slf4j.Slf4j; import org.springframework.cloud.openfeign.FallbackFactory; import org.springframework.stereotype.Component; @Slf4j @Component public class XpTaskHandleDetailRoutineClientFallbackFactory implements FallbackFactory<XpTaskHandleDetailRoutineClient> { @Override public XpTaskHandleDetailRoutineClient create(Throwable cause) { return new XpTaskHandleDetailRoutineClient() { }; } } xp-robotaxi-api/src/main/java/com/xiaopeng/api/factory/maintenance/XpTaskRuleClientFallbackFactory.java
New file @@ -0,0 +1,26 @@ package com.xiaopeng.api.factory.maintenance; import com.xiaopeng.api.feignClient.maintenance.XpTaskRuleClient; import com.xiaopeng.api.model.maintenance.XpTaskRule; import com.xiaopeng.common.core.domain.R; import lombok.extern.slf4j.Slf4j; import org.springframework.cloud.openfeign.FallbackFactory; import org.springframework.stereotype.Component; @Slf4j @Component public class XpTaskRuleClientFallbackFactory implements FallbackFactory<XpTaskRuleClient> { @Override public XpTaskRuleClient create(Throwable cause) { return new XpTaskRuleClient() { @Override public R<XpTaskRule> queryDetail() { log.error("查询运维规则失败, 异常: {}", cause.getMessage(), cause); return R.fail("查询运维规则失败,"+cause.getMessage()); } }; } } xp-robotaxi-api/src/main/java/com/xiaopeng/api/feignClient/maintenance/XpTaskClient.java
New file @@ -0,0 +1,32 @@ package com.xiaopeng.api.feignClient.maintenance; import com.xiaopeng.api.factory.maintenance.XpTaskClientFallbackFactory; import com.xiaopeng.api.factory.maintenance.XpTaskHandleDetailRoutineClientFallbackFactory; import com.xiaopeng.api.model.maintenance.XpTask; import com.xiaopeng.api.model.maintenance.XpTaskHandleDetailRoutine; import com.xiaopeng.common.core.domain.R; import com.xiaopeng.common.core.dto.ServiceNameConstantsEnum; import org.springframework.cloud.openfeign.FeignClient; import org.springframework.web.bind.annotation.GetMapping; import org.springframework.web.bind.annotation.RequestParam; /** * 打卡服务 Feign 客户端 * * @author mitao * @date 2026-02-14 */ @FeignClient( contextId = "XpTaskClient", value = ServiceNameConstantsEnum.XP_MAINTENANCE_SERVICE, fallbackFactory = XpTaskClientFallbackFactory.class ) public interface XpTaskClient { /** * 通过车辆id查询上一次保养记录 * @param vehicleId 车辆ID */ @GetMapping("/inner/xpTask/queryInfoByVehicleId") R<XpTask> queryInfoByVehicleId(@RequestParam("vehicleId") Long vehicleId); } xp-robotaxi-api/src/main/java/com/xiaopeng/api/feignClient/maintenance/XpTaskHandleDetailRoutineClient.java
New file @@ -0,0 +1,25 @@ package com.xiaopeng.api.feignClient.maintenance; import com.xiaopeng.api.factory.maintenance.XpClockInClientFallbackFactory; import com.xiaopeng.api.factory.maintenance.XpTaskHandleDetailRoutineClientFallbackFactory; import com.xiaopeng.api.model.maintenance.XpTaskHandleDetailRoutine; import com.xiaopeng.common.core.domain.R; import com.xiaopeng.common.core.dto.ServiceNameConstantsEnum; import org.springframework.cloud.openfeign.FeignClient; import org.springframework.web.bind.annotation.GetMapping; import org.springframework.web.bind.annotation.RequestParam; /** * 打卡服务 Feign 客户端 * * @author mitao * @date 2026-02-14 */ @FeignClient( contextId = "XpTaskHandleDetailRoutineClient", value = ServiceNameConstantsEnum.XP_MAINTENANCE_SERVICE, fallbackFactory = XpTaskHandleDetailRoutineClientFallbackFactory.class ) public interface XpTaskHandleDetailRoutineClient { } xp-robotaxi-api/src/main/java/com/xiaopeng/api/feignClient/maintenance/XpTaskRuleClient.java
New file @@ -0,0 +1,32 @@ package com.xiaopeng.api.feignClient.maintenance; import com.xiaopeng.api.factory.maintenance.XpTaskClientFallbackFactory; import com.xiaopeng.api.factory.maintenance.XpTaskRuleClientFallbackFactory; import com.xiaopeng.api.model.maintenance.XpTask; import com.xiaopeng.api.model.maintenance.XpTaskRule; import com.xiaopeng.api.model.maintenance.XpTaskRuleRole; import com.xiaopeng.common.core.domain.R; import com.xiaopeng.common.core.dto.ServiceNameConstantsEnum; import org.springframework.cloud.openfeign.FeignClient; import org.springframework.web.bind.annotation.GetMapping; import org.springframework.web.bind.annotation.RequestParam; /** * 打卡服务 Feign 客户端 * * @author mitao * @date 2026-02-14 */ @FeignClient( contextId = "XpTaskRuleClient", value = ServiceNameConstantsEnum.XP_MAINTENANCE_SERVICE, fallbackFactory = XpTaskRuleClientFallbackFactory.class ) public interface XpTaskRuleClient { /** * 查询运维规则 */ @GetMapping("/inner/xpTaskRule/queryDetail") R<XpTaskRule> queryDetail(); } xp-robotaxi-api/src/main/resources/META-INF/spring/org.springframework.boot.autoconfigure.AutoConfiguration.imports
@@ -30,4 +30,7 @@ com.xiaopeng.api.factory.automaticPilot.OrderMissionClientFallbackFactory com.xiaopeng.api.factory.maintenance.XpClockInClientFallbackFactory com.xiaopeng.api.factory.account.SysGroupMenuClientFallbackFactory com.xiaopeng.api.factory.order.XpCruiseOrderClientFallbackFactory com.xiaopeng.api.factory.order.XpCruiseOrderClientFallbackFactory com.xiaopeng.api.factory.maintenance.XpTaskHandleDetailRoutineClientFallbackFactory com.xiaopeng.api.factory.maintenance.XpTaskClientFallbackFactory com.xiaopeng.api.factory.maintenance.XpTaskRuleClientFallbackFactory xp-robotaxi-maintenance-boot/src/main/java/com/xiaopeng/maintenance/controller/XpTaskController.java
@@ -5,6 +5,8 @@ import com.xiaopeng.api.feignClient.vehicleConvoy.XpVehicleClient; import com.xiaopeng.api.model.account.XpOperationsUser; import com.xiaopeng.api.model.maintenance.XpErrorType; import com.xiaopeng.api.model.maintenance.XpTask; import com.xiaopeng.api.model.maintenance.XpTaskHandleDetailRoutine; import com.xiaopeng.api.model.vehicleConvoy.XpVehicle; import com.xiaopeng.api.vo.account.LoginOperationUser; import com.xiaopeng.common.core.domain.R; @@ -186,4 +188,14 @@ public R<List<XpErrorType>> errorTypeTreeList() { return xpErrorTypeService.errorTypeList(); } /** * 通过车辆id查询上一次保养记录 * @param vehicleId 车辆ID */ @GetMapping("/inner/xpTask/queryInfoByVehicleId") public R<XpTask> queryInfoByVehicleId(@RequestParam("vehicleId") Long vehicleId){ XpTask xpTask = xpTaskService.queryInfoByVehicleId(vehicleId); return R.ok(xpTask); } } xp-robotaxi-maintenance-boot/src/main/java/com/xiaopeng/maintenance/controller/XpTaskHandleDetailRoutineController.java
New file @@ -0,0 +1,51 @@ package com.xiaopeng.maintenance.controller; import com.xiaopeng.api.feignClient.vehicleConvoy.XpFleetOperationsClient; import com.xiaopeng.api.feignClient.vehicleConvoy.XpVehicleClient; import com.xiaopeng.api.model.account.XpOperationsUser; import com.xiaopeng.api.model.maintenance.XpErrorType; import com.xiaopeng.api.model.maintenance.XpTaskHandleDetailRoutine; import com.xiaopeng.api.model.vehicleConvoy.XpVehicle; import com.xiaopeng.api.vo.account.LoginOperationUser; import com.xiaopeng.common.core.domain.R; import com.xiaopeng.common.core.web.page.PageInfo; import com.xiaopeng.common.security.service.TokenService; import com.xiaopeng.maintenance.dto.HandleVehicleAccidentDto; import com.xiaopeng.maintenance.dto.SaveRoutineDetailDto; import com.xiaopeng.maintenance.dto.SaveVehicleAccidentDto; import com.xiaopeng.maintenance.model.query.TaskPageListQuery; import com.xiaopeng.maintenance.model.query.XpTaskRecordPageQuery; import com.xiaopeng.maintenance.model.vo.*; import com.xiaopeng.maintenance.service.IXpErrorTypeService; import com.xiaopeng.maintenance.service.IXpTaskHandleDetailRoutineService; import com.xiaopeng.maintenance.service.XpTaskService; import com.xiaopeng.maintenance.vo.VehicleListVO; import io.swagger.annotations.ApiOperation; import io.swagger.annotations.ApiParam; import lombok.extern.slf4j.Slf4j; import org.springframework.transaction.annotation.Transactional; import org.springframework.web.bind.annotation.*; import javax.annotation.Resource; import javax.validation.Valid; import java.util.ArrayList; import java.util.List; /** * <p> * 运维APP 任务中心 * </p> * * @author mitao * @since 2026-02-03 */ @RestController @Slf4j public class XpTaskHandleDetailRoutineController { @Resource private XpTaskService xpTaskService; @Resource private IXpTaskHandleDetailRoutineService xpTaskHandleDetailRoutineService; } xp-robotaxi-maintenance-boot/src/main/java/com/xiaopeng/maintenance/controller/XpTaskRuleController.java
@@ -1,6 +1,7 @@ package com.xiaopeng.maintenance.controller; import com.xiaopeng.api.model.maintenance.XpTaskRule; import com.xiaopeng.common.core.domain.R; import com.xiaopeng.maintenance.dto.TaskRuleDetailDto; import com.xiaopeng.maintenance.vo.TaskRuleDetailVO; @@ -25,21 +26,30 @@ @RestController @Slf4j @Api(tags = "管理后台-任务规则设置") @RequestMapping("/api/v1/taskRule") @RequestMapping("") public class XpTaskRuleController { @Resource private IXpTaskRuleService xpTaskRuleService; @Resource private IXpTaskRuleRoleService xpTaskRuleRoleService; @ApiOperation(value = "任务规则详情") @GetMapping("/taskRuleDetail") @GetMapping("/api/v1/taskRule/taskRuleDetail") @Transactional public R<TaskRuleDetailVO> taskRuleDetail() { return xpTaskRuleService.taskRuleDetail(); } /** * 查询运维规则 */ @GetMapping("/inner/xpTaskRule/queryDetail") public R<XpTaskRule> queryDetail(){ XpTaskRule taskRule = xpTaskRuleService.getOne(null); return R.ok(taskRule); } @ApiOperation(value = "保存或修改任务规则") @PostMapping("/saveOrUpdateTaskRule") @PostMapping("/api/v1/taskRule/saveOrUpdateTaskRule") public R saveOrUpdateTaskRule(@RequestBody TaskRuleDetailDto dto) { xpTaskRuleService.saveOrUpdateTaskRule(dto); return R.ok(); xp-robotaxi-maintenance-boot/src/main/java/com/xiaopeng/maintenance/mapper/XpTaskHandleDetailRoutineMapper.java
@@ -2,6 +2,7 @@ import com.xiaopeng.api.model.maintenance.XpTaskHandleDetailRoutine; import com.baomidou.mybatisplus.core.mapper.BaseMapper; import org.apache.ibatis.annotations.Param; /** * <p> xp-robotaxi-maintenance-boot/src/main/java/com/xiaopeng/maintenance/mapper/XpTaskMapper.java
@@ -31,4 +31,12 @@ List<TaskManagementPageListVO> pageListManagement(@Param("pageInfo")PageInfo<TaskManagementPageListVO> pageInfo,@Param("query") TaskManagementPageListQuery query); List<TaskManagementPageListVO> exportList(@Param("query")TaskManagementPageListQuery query); /** * 根据车辆ID查询任务信息 * @param vehicleId * @return */ XpTask queryInfoByVehicleId(@Param("vehicleId")Long vehicleId); } xp-robotaxi-maintenance-boot/src/main/java/com/xiaopeng/maintenance/service/XpTaskService.java
@@ -83,4 +83,12 @@ R<TaskManagementDetailVO> taskDetail(Long id); List<TaskManagementPageListVO> exportList(TaskManagementPageListQuery query); /** * 通过车辆id查询任务信息 * @param vehicleId * @return */ XpTask queryInfoByVehicleId(Long vehicleId); } xp-robotaxi-maintenance-boot/src/main/java/com/xiaopeng/maintenance/service/impl/XpTaskServiceImpl.java
@@ -749,6 +749,12 @@ List<TaskManagementPageListVO> list = this.baseMapper.exportList(query); return list; } @Override public XpTask queryInfoByVehicleId(Long vehicleId) { return this.baseMapper.queryInfoByVehicleId(vehicleId); } @Override public R assigneeTask(Long id, Long handlerUserId,Long assigneeUserId) { XpTask task = this.getById(id); xp-robotaxi-maintenance-boot/src/main/resources/mapper/maintenance/SysMenuClient.xml
@@ -1,5 +1,4 @@ <?xml version="1.0" encoding="UTF-8"?> <!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd"> <mapper namespace="com.xiaopeng.maintenance.mapper.XpTaskHandleDetailRoutineMapper"> </mapper> xp-robotaxi-maintenance-boot/src/main/resources/mapper/maintenance/XpTaskMapper.xml
@@ -163,4 +163,15 @@ order by t.status,t.task_urgency_level asc, t.create_time desc </select> <select id="queryInfoByVehicleId" resultType="com.xiaopeng.api.model.maintenance.XpTask"> SELECT <include refid="Base_Column_List"></include> FROM xp_task WHERE vehicle_id = #{vehicleId} AND task_category = 1 AND task_type_id = 6 AND status != 3 ORDER BY handle_time DESC limit 1 </select> </mapper> xp-robotaxi-map-boot/src/main/java/com/xiaopeng/map/controller/XpElectronicFenceController.java
@@ -21,7 +21,7 @@ @Slf4j @RestController @RequestMapping("/base/v1/mini-program") @RequestMapping("") @Api(tags = "电子围栏") public class XpElectronicFenceController extends BaseController { @@ -38,21 +38,30 @@ * @return */ @ApiOperation(value = "获取地图开放区域围栏",tags = {"小程序-获取地图开放区域围栏"},response = XpElectronicFenceVo.class) @GetMapping("/cities/list") @GetMapping("/base/v1/mini-program/cities/list") public R<List<XpElectronicFenceVo>> citiesList(@RequestParam String cityCode) { return R.ok(xpElectronicFenceAreaService.citiesList(cityCode)); } /** * 获取地图开放区域围栏 * @return */ @ApiOperation(value = "获取地图开放区域围栏",tags = {"运维APP-电子围栏"},response = XpElectronicFenceVo.class) @GetMapping("/api/v1/fence/listByCityCode") public R<List<XpElectronicFenceVo>> listByCityCode(@RequestParam String cityCode) { return R.ok(xpElectronicFenceAreaService.citiesList(cityCode)); } @ApiOperation(value = "判断当前位置是否在运营区域内",tags = {"小程序-判断当前位置是否在运营区域内"}) @PostMapping("/fence/check") @PostMapping("/base/v1/mini-program/fence/check") public R<IsInOperationAreaVo> isInOperationArea(@RequestBody @Valid LonLatDto dto) { return R.ok(xpElectronicFenceAreaService.isInOperationArea(dto)); } @ApiOperation(value = "根据点位获取步行时间和距离",tags = {"小程序-根据点位获取步行时间和距离"}) @PostMapping("/fence/walkTime") @PostMapping("/base/v1/mini-program/fence/walkTime") public R<WalkTimeVo> getWalkTime(@RequestBody @Valid WalkTimeDto dto) { return R.ok(xpElectronicFenceAreaService.getWalkTime(dto)); } @@ -64,7 +73,7 @@ * @param dto * @return */ @PostMapping("/fence/diagnosisArea") @PostMapping("/base/v1/mini-program/fence/diagnosisArea") public R<Boolean> diagnosisArea(@RequestBody RouteAndFareDto dto){ return R.ok(xpElectronicFenceAreaService.diagnosisArea(dto)); } xp-robotaxi-push-message-boot/pom.xml
@@ -118,6 +118,13 @@ <artifactId>snakeyaml</artifactId> <version>1.33</version> </dependency> <dependency> <groupId>com.aliyun</groupId> <artifactId>alibabacloud-push20160801</artifactId> <version>2.0.5</version> </dependency> </dependencies> <build> xp-robotaxi-vehicle-convoy-boot/src/main/java/com/xiaopeng/vehicleConvoy/controller/XpVehicleController.java
@@ -13,8 +13,12 @@ import com.xiaopeng.api.dto.vehicleConvoy.UpdateVehicleStateDto; import com.xiaopeng.api.dto.vehicleConvoy.VehicleTemperatureDto; import com.xiaopeng.api.feignClient.maintenance.XpChargingRecordClient; import com.xiaopeng.api.feignClient.maintenance.XpTaskClient; import com.xiaopeng.api.feignClient.maintenance.XpTaskRuleClient; import com.xiaopeng.api.feignClient.maintenance.XpVehiclePreparationClient; import com.xiaopeng.api.feignClient.order.XpOrderClient; import com.xiaopeng.api.model.maintenance.XpTask; import com.xiaopeng.api.model.maintenance.XpTaskRule; import com.xiaopeng.api.model.vehicleConvoy.XpVehicle; import com.xiaopeng.api.model.vehicleConvoy.XpVehicleAnnualRecord; import com.xiaopeng.api.vo.vehicleConvoy.VehiclesCommandCallbackVo; @@ -35,6 +39,7 @@ import lombok.extern.slf4j.Slf4j; import org.apache.commons.lang3.StringUtils; import org.apache.poi.ss.usermodel.Workbook; import org.springframework.beans.BeanUtils; import org.springframework.context.annotation.Lazy; import org.springframework.util.CollectionUtils; import org.springframework.web.bind.annotation.*; @@ -47,8 +52,11 @@ import java.io.IOException; import java.io.InputStream; import java.net.URLEncoder; import java.time.LocalDate; import java.time.LocalDateTime; import java.util.ArrayList; import java.util.List; import java.util.Objects; /** * <p> @@ -69,6 +77,8 @@ private final IXpVehicleAnnualRecordService xpVehicleAnnualRecordService; private final XpVehiclePreparationClient xpVehiclePreparationClient; private final XpChargingRecordClient xpChargingRecordClient; private final XpTaskClient xpTaskClient; private final XpTaskRuleClient xpTaskRuleClient; /** * 根据ID列表批量查询车辆信息(内部接口) * @@ -86,7 +96,6 @@ /** * 批量获取车辆列表 * * @param ids 车辆ID列表 * @return 车辆列表 */ @ApiOperation(value = "批量查询车辆信息", tags = {"内部接口"}) @@ -471,10 +480,52 @@ */ @ApiOperation(value = "车辆详情", tags = {"运维APP-车辆管理"}) @PostMapping("/api/v1/vehicle/vehicleDetail") public R<XpVehicle> vehicleDetail(@RequestParam Long id) { public R<XpVehicleVO> vehicleDetail(@RequestParam Long id) { // 查询车辆 XpVehicle xpVehicle = xpVehicleService.getById(id); return R.ok(xpVehicle); XpVehicleVO xpVehicleVO = new XpVehicleVO(); BeanUtils.copyProperties(xpVehicle, xpVehicleVO); // 查询运维规则 保养周期 XpTaskRule xpTaskRule = xpTaskRuleClient.queryDetail().getData(); if(Objects.isNull(xpTaskRule)){ return R.ok(xpVehicleVO); } Boolean maintenanceCycle = xpTaskRule.getMaintenanceCycle(); Integer maintenanceCycleTime = xpTaskRule.getMaintenanceCycleTime(); Integer maintenanceCycleTimeType = xpTaskRule.getMaintenanceCycleTimeType(); if(maintenanceCycle){ // 查询车辆上次保养记录 XpTask xpTask = xpTaskClient.queryInfoByVehicleId(id).getData(); if(Objects.nonNull(xpTask)){ // 存在保养记录 LocalDateTime handleTime = xpTask.getCreateTime(); switch (maintenanceCycleTimeType){ case 1: handleTime.plusDays(maintenanceCycleTime); break; default: handleTime.plusMonths(maintenanceCycleTime); break; } xpVehicleVO.setNextMaintenanceTime(handleTime.toLocalDate()); }else { // 没有保养记录 // 入库时间 LocalDateTime warehousingTime = xpVehicle.getWarehousingTime(); if(Objects.nonNull(warehousingTime)){ switch (maintenanceCycleTimeType){ case 1: warehousingTime.plusDays(maintenanceCycleTime); break; default: warehousingTime.plusMonths(maintenanceCycleTime); break; } xpVehicleVO.setNextMaintenanceTime(warehousingTime.toLocalDate()); } } } return R.ok(xpVehicleVO); } /** xp-robotaxi-vehicle-convoy-boot/src/main/java/com/xiaopeng/vehicleConvoy/model/vo/XpVehicleVO.java
@@ -1,10 +1,14 @@ package com.xiaopeng.vehicleConvoy.model.vo; import com.fasterxml.jackson.annotation.JsonFormat; import com.xiaopeng.api.model.vehicleConvoy.XpVehicle; import io.swagger.annotations.ApiModel; import io.swagger.annotations.ApiModelProperty; import lombok.Data; import lombok.EqualsAndHashCode; import java.time.LocalDate; import java.time.LocalDateTime; /** * @author MiTao @@ -18,4 +22,9 @@ @ApiModelProperty(value = "车队名称") private String fleetName; @ApiModelProperty(value = "下次保养时间") @JsonFormat(pattern = "yyyy-MM-dd",timezone = "GMT+8") private LocalDate nextMaintenanceTime; }