| | |
| | | |
| | | import cn.hutool.core.bean.BeanUtil; |
| | | import cn.hutool.core.collection.CollUtil; |
| | | import cn.hutool.core.lang.Snowflake; |
| | | import com.alibaba.fastjson2.JSON; |
| | | import com.alibaba.fastjson2.JSONArray; |
| | | import com.alibaba.fastjson2.JSONObject; |
| | |
| | | import com.xiaopeng.common.core.constant.CacheConstants; |
| | | import com.xiaopeng.common.core.constant.HttpStatus; |
| | | import com.xiaopeng.common.core.domain.R; |
| | | import com.xiaopeng.common.core.enums.OrderStatusEnum; |
| | | import com.xiaopeng.common.core.exception.ServiceException; |
| | | import com.xiaopeng.common.core.utils.DateUtils; |
| | | import com.xiaopeng.common.core.utils.GeodesyUtil; |
| | | import com.xiaopeng.common.core.utils.SensitiveDataCryptoUtil; |
| | | import com.xiaopeng.common.core.utils.StringUtils; |
| | | import com.xiaopeng.common.core.web.domain.BaseModel; |
| | | import com.xiaopeng.common.core.web.page.PageInfo; |
| | |
| | | import com.xiaopeng.order.job.base.QuartzManager; |
| | | import com.xiaopeng.order.job.base.TimeJobType; |
| | | import com.xiaopeng.order.job.jobs.EndTripJob; |
| | | import com.xiaopeng.order.job.jobs.OrderCancelJob; |
| | | import com.xiaopeng.order.mangodb.model.OrderTrajectory; |
| | | import com.xiaopeng.order.job.jobs.TestOrderCancelJob; |
| | | import com.xiaopeng.api.model.order.OrderTrajectory; |
| | | import com.xiaopeng.order.mapper.XpCruiseOrderMapper; |
| | | import com.xiaopeng.order.mapper.XpTestOrderDetailMapper; |
| | | import com.xiaopeng.order.mapper.XpTestOrderMapper; |
| | |
| | | import org.apache.shardingsphere.transaction.annotation.ShardingSphereTransactionType; |
| | | import org.apache.shardingsphere.transaction.core.TransactionType; |
| | | import org.springframework.beans.BeanUtils; |
| | | import org.springframework.beans.factory.annotation.Autowired; |
| | | import org.springframework.context.annotation.Lazy; |
| | | import org.springframework.data.domain.Sort; |
| | | import org.springframework.data.mongodb.core.MongoTemplate; |
| | |
| | | private final UserVehicleClient userVehicleClient; |
| | | private final IXpOrderEvaluateService xpOrderEvaluateService; |
| | | private final IXpTestOrderCancelService xpTestOrderCancelService; |
| | | private final IXpOrderReassignService xpOrderReassignService; |
| | | @Lazy |
| | | @Autowired |
| | | private IXpOrderReassignService xpOrderReassignService; |
| | | private final RedisService redisService; |
| | | private final XpPricingClient xpPricingClient; |
| | | private final XpSystemSettingClient xpSystemSettingClient; |
| | |
| | | |
| | | @Resource |
| | | private BootCommonService bootCommonService; |
| | | |
| | | @Resource |
| | | private XpTradingStrategyClient tradingStrategyClient; |
| | | |
| | | @Resource(name = "hutoolSnowflake") |
| | | private Snowflake snowflake; |
| | | |
| | | |
| | | |
| | |
| | | xpOrder.setTestPlanId(query.getTestPlanId()); |
| | | xpOrder.setOrderType(query.getOrderType()); |
| | | xpOrder.setMileageKilometers(0.0); |
| | | xpOrder.setOrderNumber("XP" + System.currentTimeMillis()); |
| | | xpOrder.setOrderNumber(getOrderNumber()); |
| | | xpOrder.setCityId(openCity.getId()); |
| | | xpOrder.setPlacementLat(xpPoint.getPointLat()); |
| | | xpOrder.setPlacementLon(xpPoint.getPointLon()); |
| | |
| | | xpOrder.setStatus(1); |
| | | xpOrder.setOrderSource(1); |
| | | xpOrder.setOpenTrunk(2); |
| | | xpOrder.setXpuStartTaskId(snowflake.nextId() + ""); |
| | | xpOrder.setXpuEndTaskId(snowflake.nextId() + ""); |
| | | |
| | | // 当前时段 |
| | | String currentTimeSlot = DateUtils.getCurrentTimeSlot(); |
| | |
| | | for (Long vehicleId : vehicleIds) { |
| | | xpOrder.setId(null); |
| | | XpVehicle xpVehicle = xpVehicleClient.queryById(vehicleId).getData(); |
| | | String vin = SensitiveDataCryptoUtil.decryptIfPossible(xpVehicle.getVehicleVin()); |
| | | xpOrder.setVehicleId(vehicleId); |
| | | xpOrder.setFleetId(xpVehicle.getFleetId()); |
| | | this.save(xpOrder); |
| | |
| | | redisService.setCacheObject("TEST_ORDER_NAVIGATION_END_DATA:" + vehicleId, JSON.toJSONString(routeVo), 24L, TimeUnit.HOURS); |
| | | //下发XPU消息 |
| | | PushOrderDto pushOrderDto = new PushOrderDto(); |
| | | pushOrderDto.setVin(xpVehicle.getVehicleVin()); |
| | | pushOrderDto.setStartTaskId(xpOrder.getXpuStartTaskId()); |
| | | pushOrderDto.setEndTaskId(xpOrder.getXpuEndTaskId()); |
| | | pushOrderDto.setVin(vin); |
| | | pushOrderDto.setOrderId("TEST" + xpOrder.getId()); |
| | | pushOrderDto.setStartWaypointId(xpOrder.getStartTestPointId()); |
| | | pushOrderDto.setEndWaypointId(xpOrder.getEndTestPointId()); |
| | | pushOrderDto.setStartLatitude(xpOrder.getStartLat()); |
| | | pushOrderDto.setStartLongitude(xpOrder.getStartLon()); |
| | | pushOrderDto.setEndLatitude(xpOrder.getEndLat()); |
| | |
| | | orderMissionClient.pushOrder(pushOrderDto); |
| | | } |
| | | } |
| | | |
| | | private String getOrderNumber(){ |
| | | int random = Double.valueOf(Math.random() * 1000).intValue(); |
| | | return "XP" + random + System.currentTimeMillis(); |
| | | } |
| | | |
| | | |
| | | private Boolean isInOperationTime(String operationStrategy) { |
| | | JSONArray jsonArray = JSONArray.parseArray(operationStrategy); |
| | |
| | | XpVehicle vehicle = vehicleMap.get(order.getVehicleId()); |
| | | if (Objects.nonNull(vehicle)) { |
| | | vo.setPlateNumber(vehicle.getPlateNumber()); |
| | | vo.setVehicleModel(vehicle.getVehicleModel()); |
| | | vo.setVehicleModel(vehicle.getVehicleModelName()); |
| | | } |
| | | } |
| | | |
| | |
| | | R<XpVehicle> xpVehicleR = xpVehicleClient.queryById(order.getVehicleId()); |
| | | if (xpVehicleR.getCode() == HttpStatus.SUCCESS && Objects.nonNull(xpVehicleR.getData())) { |
| | | XpVehicle xpVehicle = xpVehicleR.getData(); |
| | | String vin = SensitiveDataCryptoUtil.decryptIfPossible(xpVehicle.getVehicleVin()); |
| | | //还原车辆状态 |
| | | if(1 == xpVehicle.getState()){ |
| | | XpVehicle vehicle1 = new XpVehicle(); |
| | |
| | | |
| | | // 下发命令 |
| | | PushOrderDto pushOrderDto = new PushOrderDto(); |
| | | pushOrderDto.setEndTaskId(order.getStatus() < 6 ? order.getXpuStartTaskId() : order.getXpuEndTaskId()); |
| | | pushOrderDto.setOrderId("TEST" + order.getId().toString()); |
| | | pushOrderDto.setVin(xpVehicle.getVehicleVin()); |
| | | pushOrderDto.setVin(vin); |
| | | pushOrderDto.setOperation_type(OrderOperationType.CLOUD_CANCEL_ORDER); |
| | | orderMissionClient.cancelOrder(pushOrderDto); |
| | | log.info("运营人员取消订单成功,开始执行巡游订单 {}", order.getId()); |
| | |
| | | */ |
| | | private void closeOrder(XpTestOrder order) { |
| | | XpVehicle xpVehicle = xpVehicleClient.queryById(order.getVehicleId()).getData(); |
| | | String vin = SensitiveDataCryptoUtil.decryptIfPossible(xpVehicle.getVehicleVin()); |
| | | order.setStatus(7); |
| | | order.setGetoffTime(LocalDateTime.now()); |
| | | // 解析下车地点 |
| | | VehiclePosition vehiclePosition = mongoTemplate.findOne(new Query(Criteria.where("vin").is(xpVehicle.getVehicleVin())), VehiclePosition.class); |
| | | VehiclePosition vehiclePosition = mongoTemplate.findOne(new Query(Criteria.where("vin").is(vin)), VehiclePosition.class); |
| | | if(Objects.nonNull(vehiclePosition)){ |
| | | GeoJsonPoint point = vehiclePosition.getPoint(); |
| | | if(Objects.nonNull(point)){ |
| | |
| | | |
| | | //给XPU推送订单取消的报文 |
| | | PushOrderDto pushOrderDto = new PushOrderDto(); |
| | | pushOrderDto.setEndTaskId(order.getStatus() < 6 ? order.getXpuStartTaskId() : order.getXpuEndTaskId()); |
| | | pushOrderDto.setOrderId("TEST" + order.getId().toString()); |
| | | pushOrderDto.setVin(xpVehicle.getVehicleVin()); |
| | | pushOrderDto.setVin(vin); |
| | | pushOrderDto.setOperation_type(OrderOperationType.CLOUD_CANCEL_ORDER); |
| | | orderMissionClient.cancelOrder(pushOrderDto); |
| | | |
| | | //结束行程,修改状态和计算费用 |
| | | endTrip(order.getId()); |
| | | } |
| | | |
| | | |
| | | |
| | | public void carAbnormalUpdateOrderStatus(Long orderId) { |
| | | XpTestOrder order = this.getById(orderId); |
| | | XpVehicle xpVehicle = xpVehicleClient.queryById(order.getVehicleId()).getData(); |
| | | String vin = SensitiveDataCryptoUtil.decryptIfPossible(xpVehicle.getVehicleVin()); |
| | | order.setStatus(7); |
| | | order.setGetoffTime(LocalDateTime.now()); |
| | | // 解析下车地点 |
| | | VehiclePosition vehiclePosition = mongoTemplate.findOne(new Query(Criteria.where("vin").is(vin)), VehiclePosition.class); |
| | | if(Objects.nonNull(vehiclePosition)){ |
| | | GeoJsonPoint point = vehiclePosition.getPoint(); |
| | | if(Objects.nonNull(point)){ |
| | | double x = point.getX(); |
| | | double y = point.getY(); |
| | | Map<String, String> geocode = gdMapGeocodingUtil.geocode(String.valueOf(x), String.valueOf(y)); |
| | | order.setGetoffAddress(geocode.get("address")); |
| | | } |
| | | } |
| | | //计算行驶总距离和时长 |
| | | List<OrderTrajectory> orderTrajectoryList = mongoTemplate.find(new Query().addCriteria(Criteria.where("orderId").is(order.getId())), OrderTrajectory.class); |
| | | Double reduce = orderTrajectoryList.stream().map(OrderTrajectory::getDistance).reduce(0.0, Double::sum); |
| | | order.setMileageKilometers(new BigDecimal(reduce).divide(new BigDecimal(1000)).setScale(4, RoundingMode.HALF_EVEN).doubleValue()); |
| | | long duration = LocalDateTime.now().toEpochSecond(ZoneOffset.of("+8")) - order.getTripBegin().toEpochSecond(ZoneOffset.of("+8")); |
| | | order.setDuration(new BigDecimal(duration).divide(new BigDecimal(60), 2, RoundingMode.HALF_EVEN).doubleValue()); |
| | | order.setStartTestPointId(null); |
| | | this.updateById(order); |
| | | redisService.setCacheObject("TEST_ORDER_STATUS:" + order.getId(), 7, 24L, TimeUnit.HOURS); |
| | | |
| | | //给XPU推送订单取消的报文 |
| | | PushOrderDto pushOrderDto = new PushOrderDto(); |
| | | pushOrderDto.setEndTaskId(order.getStatus() < 6 ? order.getXpuStartTaskId() : order.getXpuEndTaskId()); |
| | | pushOrderDto.setOrderId("TEST" + order.getId().toString()); |
| | | pushOrderDto.setVin(vin); |
| | | pushOrderDto.setOperation_type(OrderOperationType.CLOUD_CANCEL_ORDER); |
| | | orderMissionClient.cancelOrder(pushOrderDto); |
| | | |
| | | //结束行程,修改状态和计算费用 |
| | | endTrip(order.getId()); |
| | | |
| | | //将支付金额修改成0 并将状态修改成 订单状态9 |
| | | setFree(order.getId()); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * 豁免 |
| | | */ |
| | | public void setFree(Long id) { |
| | | |
| | | //将支付金额修改成0 并将状态修改成 订单状态9 |
| | | XpTestOrder xpOrder1 = new XpTestOrder(); |
| | | xpOrder1.setId(id); |
| | | xpOrder1.setIsFree(true);//豁免 |
| | | xpOrder1.setPayMoney(BigDecimal.ZERO); |
| | | xpOrder1.setStatus(OrderStatusEnum.PENDING_PAYMENT.getCode()); |
| | | xpOrder1.setUpdateTime(LocalDateTime.now()); |
| | | baseMapper.updateById(xpOrder1); |
| | | } |
| | | |
| | | |
| | | /** |
| | | * 改派订单 |
| | |
| | | R<XpVehicle> oldVehicleResult = xpVehicleClient.queryById(oldVehicleId); |
| | | if (oldVehicleResult != null && oldVehicleResult.getCode() == HttpStatus.SUCCESS && oldVehicleResult.getData() != null) { |
| | | XpVehicle oldVehicle = oldVehicleResult.getData(); |
| | | String vin = SensitiveDataCryptoUtil.decryptIfPossible(oldVehicle.getVehicleVin()); |
| | | |
| | | // 6.1.1 取消原订单指令 |
| | | PushOrderDto cancelDto = new PushOrderDto(); |
| | | cancelDto.setOrderId("TEST" + order.getId().toString()); |
| | | cancelDto.setVin(oldVehicle.getVehicleVin()); |
| | | cancelDto.setVin(vin); |
| | | cancelDto.setOperation_type(OrderOperationType.CLOUD_CANCEL_ORDER); |
| | | orderMissionClient.cancelOrder(cancelDto); |
| | | log.info("已取消原车辆订单指令,订单ID: {}, VIN: {}", orderId, oldVehicle.getVehicleVin()); |
| | | log.info("已取消原车辆订单指令,订单ID: {}, VIN: {}", orderId, vin); |
| | | |
| | | // 6.1.3 修改原车辆状态为空闲 |
| | | XpVehicle vehicle1 = new XpVehicle(); |
| | |
| | | |
| | | // 11. 处理新车辆:绑定乘客、下发订单、更新状态 |
| | | try { |
| | | String vin = SensitiveDataCryptoUtil.decryptIfPossible(newVehicle.getVehicleVin()); |
| | | // 11.2 下发订单到新车辆 |
| | | PushOrderDto pushOrderDto = new PushOrderDto(); |
| | | pushOrderDto.setVin(newVehicle.getVehicleVin()); |
| | | pushOrderDto.setStartTaskId(order.getXpuStartTaskId()); |
| | | pushOrderDto.setEndTaskId(order.getXpuEndTaskId()); |
| | | pushOrderDto.setVin(vin); |
| | | pushOrderDto.setOrderId("TEST" + order.getId()); |
| | | pushOrderDto.setStartWaypointId(order.getStartTestPointId()); |
| | | pushOrderDto.setEndWaypointId(order.getEndTestPointId()); |
| | | pushOrderDto.setStartLatitude(order.getStartLat()); |
| | | pushOrderDto.setStartLongitude(order.getStartLon()); |
| | | pushOrderDto.setEndLatitude(order.getEndLat()); |
| | |
| | | // 调用推送服务 orderId + carVin |
| | | orderMissionClient.pushOrder(pushOrderDto); |
| | | |
| | | log.info("已下发订单到新车辆,订单ID: {}, VIN: {}", orderId, newVehicle.getVehicleVin()); |
| | | log.info("已下发订单到新车辆,订单ID: {}, VIN: {}", orderId, vin); |
| | | |
| | | // 11.3 更新新车辆状态为已接单 |
| | | XpVehicle vehicle1 = new XpVehicle(); |
| | |
| | | put("id", xpOrder.getId()) |
| | | .build(); |
| | | QuartzManager.addJob( |
| | | OrderCancelJob.class, |
| | | (OrderCancelJob.name + xpOrder.getId()).toUpperCase(), |
| | | TimeJobType.ORDER_CANCEL, |
| | | TestOrderCancelJob.class, |
| | | (TestOrderCancelJob.name + xpOrder.getId()).toUpperCase(), |
| | | TimeJobType.TEST_ORDER_CANCEL, |
| | | DateUtils.localDateTimeToDate(LocalDateTime.now().plusMinutes(xpPoint.getParkingTimeLimit())), |
| | | cancelJobMaps |
| | | ); |
| | |
| | | xpOrder.setBoardingTime(now); |
| | | xpOrder.setRideTime(now); |
| | | // 删除定时任务job |
| | | QuartzManager.removeJob((OrderCancelJob.name + xpOrder.getId()).toUpperCase(), TimeJobType.ORDER_CANCEL); |
| | | QuartzManager.removeJob((TestOrderCancelJob.name + xpOrder.getId()).toUpperCase(), TimeJobType.TEST_ORDER_CANCEL); |
| | | //乘客已上车,重新倒计时不开始行程取消订单 |
| | | XpTestPoint xpPoint1 = xpTestPointClient.queryById(xpOrder.getStartTestPointId()).getData(); |
| | | if(StringUtils.isEmpty(xpPoint1.getCityCode())){ |
| | | Map<String, String> geocode = gdMapGeocodingUtil.geocode(xpPoint1.getPointLon().toString(), xpPoint1.getPointLat().toString()); |
| | | if(null != geocode){ |
| | | xpPoint1.setCityCode(geocode.get("cityCode")); |
| | | xpPoint1.setCityName(geocode.get("address")); |
| | | xpTestPointClient.editXpPoint(xpPoint1); |
| | | } |
| | | } |
| | | XpTradingStrategy tradingStrategy = tradingStrategyClient.getTradingStrategyByCityCode(xpPoint1.getCityCode()).getData(); |
| | | if(null != tradingStrategy){ |
| | | Map<String, ? extends Object> cancelJobMaps1 = |
| | | new ImmutableMap.Builder<String, Long>() |
| | | .put("id", xpOrder.getId()) |
| | | .build(); |
| | | QuartzManager.addJob( |
| | | TestOrderCancelJob.class, |
| | | (TestOrderCancelJob.name + xpOrder.getId()).toUpperCase(), |
| | | TimeJobType.TEST_ORDER_CANCEL, |
| | | DateUtils.localDateTimeToDate(LocalDateTime.now().plusMinutes(tradingStrategy.getBdNotBoardedTime())), |
| | | cancelJobMaps1 |
| | | ); |
| | | } |
| | | break; |
| | | case 6: |
| | | // 删除定时任务job |
| | | QuartzManager.removeJob((TestOrderCancelJob.name + xpOrder.getId()).toUpperCase(), TimeJobType.TEST_ORDER_CANCEL); |
| | | // 行程开始时间 |
| | | xpOrder.setTripBegin(LocalDateTime.now()); |
| | | redisService.deleteObject("TEST_ORDER_NAVIGATION_START_DATA:" + xpOrder.getVehicleId()); |
| | | break; |
| | | case 7: |
| | | String vin = SensitiveDataCryptoUtil.decryptIfPossible(xpVehicle.getVehicleVin()); |
| | | xpOrder.setGetoffTime(LocalDateTime.now()); |
| | | // 解析下车地点 |
| | | VehiclePosition vehiclePosition = mongoTemplate.findOne(new Query(Criteria.where("vin").is(xpVehicle.getVehicleVin())), VehiclePosition.class); |
| | | VehiclePosition vehiclePosition = mongoTemplate.findOne(new Query(Criteria.where("vin").is(vin)), VehiclePosition.class); |
| | | if(Objects.nonNull(vehiclePosition)){ |
| | | GeoJsonPoint point = vehiclePosition.getPoint(); |
| | | if(Objects.nonNull(point)){ |
| | |
| | | xpTestOrder.setStartTestPointId(null); |
| | | this.updateById(xpTestOrder); |
| | | XpVehicle xpVehicle = xpVehicleClient.queryById(xpTestOrder.getVehicleId()).getData(); |
| | | String vin = SensitiveDataCryptoUtil.decryptIfPossible(xpVehicle.getVehicleVin()); |
| | | PushOrderDto pushOrderDto = new PushOrderDto(); |
| | | pushOrderDto.setVin(xpVehicle.getVehicleVin()); |
| | | pushOrderDto.setEndTaskId(xpTestOrder.getStatus() < 6 ? xpTestOrder.getXpuStartTaskId() : xpTestOrder.getXpuEndTaskId()); |
| | | pushOrderDto.setVin(vin); |
| | | pushOrderDto.setOrderId("TEST" + xpTestOrder.getId()); |
| | | pushOrderDto.setOperation_type(OrderOperationType.CLOUD_CANCEL_ORDER); |
| | | R<Boolean> booleanR = orderMissionClient.cancelOrder(pushOrderDto); |