| | |
| | | import com.alibaba.fastjson.JSONObject; |
| | | import com.alibaba.fastjson.TypeReference; |
| | | import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper; |
| | | import com.baomidou.mybatisplus.core.conditions.update.UpdateWrapper; |
| | | import com.doumee.biz.system.SystemDictDataBiz; |
| | | import com.doumee.core.constants.Constants; |
| | | import com.doumee.core.constants.ResponseStatus; |
| | | import com.doumee.core.exception.BusinessException; |
| | | import com.doumee.core.utils.DateUtil; |
| | | import com.doumee.core.utils.PositionUtil; |
| | | import com.doumee.core.utils.StringTools; |
| | | import com.doumee.core.wx.WxMiniUtilService; |
| | |
| | | import org.springframework.transaction.annotation.Transactional; |
| | | import org.springframework.web.bind.annotation.RequestBody; |
| | | import org.yzh.commons.model.APIResult; |
| | | import org.yzh.protocol.commons.transform.AttributeKey; |
| | | import org.yzh.protocol.commons.transform.attribute.Battery; |
| | | import org.yzh.protocol.t808.T0200; |
| | | import org.yzh.protocol.t808.T0201_0500; |
| | | import org.yzh.protocol.t808.T8500; |
| | | import reactor.core.publisher.Mono; |
| | | |
| | | import java.math.BigDecimal; |
| | | import java.util.ArrayList; |
| | | import java.util.Date; |
| | | import java.util.List; |
| | | import java.util.Objects; |
| | |
| | | private MessageManager messageManager; |
| | | @Autowired |
| | | private GoodsorderService goodsorderService; |
| | | @Autowired |
| | | private BikesMapper bikesMapper; |
| | | |
| | | @Autowired |
| | | private DiscountMemberMapper discountMemberMapper; |
| | |
| | | |
| | | @Transactional(rollbackFor = {BusinessException.class}) |
| | | public void backElecBike(BackElecBikeRequest param) { |
| | | if (param.getLatitude() == null || param.getLongitude() == null || StringUtils.isBlank(param.getMemberId())) { |
| | | throw new BusinessException(ResponseStatus.BAD_REQUEST.getCode(), "对不起,定位信息有误,请确认定位权限已开启!"); |
| | | } |
| | | Member member = memberMapper.selectById(param.getMemberId()); |
| | | if (member == null) { |
| | | throw new BusinessException(ResponseStatus.BAD_REQUEST.getCode(), "对不起,您的账号信息查询失败,请返回重新进入小程序再试!"); |
| | |
| | | } |
| | | //查询骑行记录 |
| | | List<MemberRides> memberRides = goodsorderService.getMemberRidesForClose(goodsorder.getId()); |
| | | List<String> backIds = new ArrayList<>(); |
| | | if(memberRides!=null && memberRides.size()>0){ |
| | | for (MemberRides rides : memberRides){ |
| | | if(Constants.equalsInteger(rides.getStatus(),Constants.MEMBER_RIDES_STATUS.RIDES_RUNNING.getKey())){ |
| | | if(StringUtils.isNotBlank(rides.getDeviceSn()) &&Constants.equalsInteger(rides.getType(),Constants.ONE) ){ |
| | | Sites site = getBackSiteByPostion(param);//查询停车站点信息 |
| | | //如果是电车并且是骑行中 进行关锁处理 |
| | | lockBikes(rides.getDeviceSn(),Constants.ZERO);//发起关锁指令请求 |
| | | if(Constants.equalsInteger(rides.getStatus(),Constants.MEMBER_RIDES_STATUS.RIDES_RUNNING.getKey()) |
| | | &&Constants.equalsInteger(rides.getType(),Constants.ONE)){ |
| | | //如果是电车并且是骑行中 进行关锁处理 |
| | | Bikes bike = getElecBikeByCode(rides.getBikeCode()); |
| | | //查询停车站点信息 |
| | | if(bike.getSiteId() ==null){ |
| | | throw new BusinessException(ResponseStatus.DATA_EMPTY.getCode(), "对不起,请按要求前往停车点停车!"); |
| | | } |
| | | lockBikes(bike.getDeviceSn(),Constants.ZERO);//发起关锁指令请求 |
| | | backIds.add(rides.getId()); |
| | | rides.setStatus(Constants.MEMBER_RIDES_STATUS.BACK_CYCLING.getKey());//已还车 |
| | | rides.setBackSiteId(bike.getSiteId());//还车站点 |
| | | rides.setBackDate(new Date()); |
| | | rides.setEditDate(rides.getBackDate()); |
| | | memberRidesJoinMapper.updateById(rides);//更新骑行状态为已还车 |
| | | } |
| | | } |
| | | } |
| | |
| | | goodsorder.setEditDate(date); |
| | | goodsorder.setEditor(null); |
| | | goodsorderService.dealCloseGoodsorderBiz( goodsorder,Constants.REFUND_TYPE.NORMAL.getKey(),memberRides); |
| | | } |
| | | |
| | | private Bikes getElecBikeByCode(String bikeCode) { |
| | | Bikes bike = bikesMapper.selectOne(new QueryWrapper<Bikes>().lambda() |
| | | .eq(Bikes::getType,Constants.ONE) |
| | | .eq(Bikes::getIsdeleted,Constants.ZERO) |
| | | .eq(Bikes::getCode,bikeCode) |
| | | ); |
| | | if(bike==null){ |
| | | throw new BusinessException(ResponseStatus.NOT_ALLOWED.getCode(),"车辆信息查询失败,请稍后重试或联系园区管理员处理!" ); |
| | | } |
| | | if(StringUtils.isBlank(bike.getDeviceSn()) || bike.getLongitude()==null ||bike.getLatitude() ==null){ |
| | | throw new BusinessException(ResponseStatus.NOT_ALLOWED.getCode(),"车辆位置信息查询失败,请稍后重试或联系园区管理员处理!" ); |
| | | } |
| | | if(StringUtils.isBlank(bike.getDeviceSn()) ){ |
| | | throw new BusinessException(ResponseStatus.NOT_ALLOWED.getCode(),"车辆控制器故障,请稍后重试或联系园区管理员处理!" ); |
| | | } |
| | | int expireTime = 10*1000;//默认10秒 |
| | | try { |
| | | expireTime = Integer.parseInt(systemDictDataBiz.queryByCode(Constants.MINI_PROGRAMME,Constants.HEART_TIME_EXPIRE_TIME).getCode())*1000; |
| | | }catch (Exception e){ |
| | | } |
| | | if(bike.getHeartDate() == null || System.currentTimeMillis() - bike.getHeartDate().getTime() >expireTime){ |
| | | //如果车辆上报时间超过30秒,则表示车辆控制器失效 |
| | | throw new BusinessException(ResponseStatus.NOT_ALLOWED.getCode(),"车辆控制器故障,获取定位信息失败,请稍后重试或联系园区管理员处理!" ); |
| | | } |
| | | return bike; |
| | | } |
| | | |
| | | /** |
| | | * 发起关锁、开锁指令请求 |
| | | * @param clientId |
| | | * @param type 控制标志:0.车门解锁 1.车门加锁 |
| | | */ |
| | | private void lockBikes(String clientId,int type) { |
| | | T8500 request = new T8500(); |
| | |
| | | APIResult<T0201_0500> data = result.block(); |
| | | if(!data.isSuccess()){ |
| | | //如果开锁失败,则返回异常 |
| | | throw new BusinessException(ResponseStatus.BAD_REQUEST.getCode(), "对不起,还车关锁失败,请稍后重试,或者联系园区管理人员!"); |
| | | throw new BusinessException(ResponseStatus.BAD_REQUEST.getCode(), "对不起,"+(type ==0?"车辆开锁":"车辆关锁")+"失败,请稍后重试,或者联系园区管理人员!"); |
| | | } |
| | | } |
| | | |
| | | /** |
| | | * 查询停车站点信息 |
| | | * @param param |
| | | * @return |
| | | */ |
| | | private Sites getBackSiteByPostion(BackElecBikeRequest param) { |
| | | private Sites getBackSiteByPostion(double lat,double lng) { |
| | | Sites site = null;//查询停车站点信息 |
| | | List<Sites> sitesList = sitesMapper.selectList(new QueryWrapper<Sites>().lambda() |
| | | .eq(Sites::getStatus,Constants.ZERO) |
| | | .eq(Sites::getIsdeleted,Constants.ZERO) |
| | | .eq(Sites::getType,Constants.ONE)); |
| | | if(sitesList ==null ||sitesList.size() ==0){ |
| | | throw new BusinessException(ResponseStatus.DATA_EMPTY.getCode(), "对不起,请按照要求前往停车点停车!"); |
| | | // throw new BusinessException(ResponseStatus.DATA_EMPTY.getCode(), "对不起,请按照要求前往停车点停车!"); |
| | | return null; |
| | | } |
| | | for(Sites sites :sitesList){ |
| | | TypeReference typeReference = new TypeReference<List<LocaltionDTO>>(){}; |
| | |
| | | if(array == null || array.size() ==0){ |
| | | continue; |
| | | } |
| | | if(PositionUtil.isInPolygon(param.getLongitude(),param.getLatitude(),array)){ |
| | | if(PositionUtil.isInPolygon(lat,lng,array)){ |
| | | //如果在停车点范围内; |
| | | site = sites; |
| | | break; |
| | | } |
| | | if(site ==null){ |
| | | /* if(site ==null){ |
| | | throw new BusinessException(ResponseStatus.DATA_EMPTY.getCode(), "对不起,请按照要求前往停车点停车!"); |
| | | } |
| | | }*/ |
| | | } |
| | | return site; |
| | | } |
| | | |
| | | /** |
| | | * 临时停车 |
| | | * @param param |
| | | */ |
| | | @Transactional(rollbackFor = {BusinessException.class}) |
| | | public void pauseElecBike(BackElecBikeRequest param) { |
| | | Member member = memberMapper.selectById(param.getMemberId()); |
| | | if (member == null) { |
| | | throw new BusinessException(ResponseStatus.BAD_REQUEST.getCode(), "对不起,您的账号信息查询失败,请返回重新进入小程序再试!"); |
| | | } |
| | | Goodsorder gparam = new Goodsorder(); |
| | | gparam.setMemberId(param.getMemberId()); |
| | | gparam.setStatus(Constants.goodsorderStatus.pay); |
| | | Goodsorder goodsorder = goodsorderService.findOne(gparam); |
| | | if(Objects.isNull(goodsorder)){ |
| | | throw new BusinessException(ResponseStatus.NO_UNCLOSEED_ORDER.getCode(),"对不起,未查询到您当前有骑行中订单记录"); |
| | | } |
| | | //查询所有骑行记录 |
| | | MemberRides memberRides = memberRidesJoinMapper.selectJoinOne(MemberRides.class,new MPJLambdaWrapper<MemberRides>() |
| | | .eq(MemberRides::getOrdreId,goodsorder.getId()) |
| | | .eq(MemberRides::getStatus,Constants.MEMBER_RIDES_STATUS.RIDES_RUNNING.getKey()) |
| | | .selectAll(MemberRides.class) |
| | | .last("limit 1")); |
| | | if(memberRides ==null || memberRides.getBikeCode() == null){ |
| | | throw new BusinessException(ResponseStatus.NO_UNCLOSEED_ORDER.getCode(),"对不起,未查询到您当前有骑行中记录"); |
| | | } |
| | | Bikes bike = getElecBikeByCode(memberRides.getBikeCode()); |
| | | //查询停车位置是否符合停车位置规范 |
| | | checkPausePostionBiz(bike); |
| | | memberRides.setPauseDate(new Date()); |
| | | memberRides.setEditDate(memberRides.getBackDate()); |
| | | memberRides.setStatus(Constants.MEMBER_RIDES_STATUS.RIDES_PAUSING.getKey()); |
| | | memberRidesJoinMapper.updateById(memberRides);//更新骑行状态为临停中 |
| | | } |
| | | |
| | | private void checkPausePostionBiz(Bikes bike) { |
| | | int ruleType = 0; |
| | | try { |
| | | ruleType =Integer.parseInt( systemDictDataBiz.queryByCode(Constants.MINI_PROGRAMME,Constants.PAUSE_BIKE_TYPE).getCode()); |
| | | }catch (Exception e){ |
| | | } |
| | | if(ruleType == 0){ |
| | | //如果仅限于园区临时停车 |
| | | List<LocaltionDTO> array = new ArrayList<>(); |
| | | try { |
| | | TypeReference typeReference = new TypeReference<List<LocaltionDTO>>(){}; |
| | | array = JSONObject.parseObject(systemDictDataBiz.queryByCode(Constants.MINI_PROGRAMME, Constants.PARK_LAT_LNG_LIST).getCode(), typeReference.getType()); |
| | | }catch (Exception e){ |
| | | } |
| | | if(array == null || array.size() ==0){ |
| | | throw new BusinessException(ResponseStatus.DATA_EMPTY.getCode(), "对不起,园区运营区域配置有误,请联系园区管理员处理!"); |
| | | } |
| | | if( !PositionUtil.isInPolygon(bike.getLatitude().doubleValue(),bike.getLongitude().doubleValue(),array)){ |
| | | //如果在停车点范围内; |
| | | throw new BusinessException(ResponseStatus.DATA_EMPTY.getCode(), "对不起,请按要求在园区运营区域范围内停车!"); |
| | | } |
| | | }else{ |
| | | //检查是否满足停车点停车 |
| | | if(bike.getSiteId() ==null){ |
| | | throw new BusinessException(ResponseStatus.DATA_EMPTY.getCode(), "对不起,请按要求前往停车点停车!"); |
| | | } |
| | | } |
| | | } |
| | | |
| | | public void updateBikesInfo(List<T0200> list) { |
| | | Date date = new Date(); |
| | | for(T0200 m : list){ |
| | | Bikes bike = new Bikes(); |
| | | bike.setDeviceSn(m.getClientId()); |
| | | if(m.getLatitude()!=0){ |
| | | bike.setLatitude(new BigDecimal(m.getLatitude()).divide(new BigDecimal(1000000),8,BigDecimal.ROUND_HALF_UP)); |
| | | } |
| | | if(m.getLongitude()!=0){ |
| | | bike.setLongitude(new BigDecimal(m.getLongitude()).divide(new BigDecimal(1000000),8,BigDecimal.ROUND_HALF_UP)); |
| | | } |
| | | bike.setHeartDate(DateUtil.getDateFromLocalDateTime(m.getDeviceTime())); |
| | | if(m.getAttributes()!=null ){ |
| | | Battery battery= (Battery) m.getAttributes().get(AttributeKey.Battery); |
| | | if(battery !=null && battery.getVoltage()!=null){ |
| | | bike.setVoltage(new BigDecimal(battery.getVoltage())); |
| | | } |
| | | } |
| | | if(StringUtils.isBlank(bike.getDeviceSn() )){ |
| | | return; |
| | | } |
| | | String tSn = StringTools.leftPad(bike.getDeviceSn(),12,'0') ; |
| | | Bikes bikes = bikesMapper.selectOne(new QueryWrapper<Bikes>().lambda() |
| | | .eq(Bikes::getDeviceSn,tSn) |
| | | .eq(Bikes::getIsdeleted,Constants.ZERO) |
| | | .eq(Bikes::getType,Constants.ONE) |
| | | .last("limit 1")); |
| | | if(bikes == null){ |
| | | return; |
| | | } |
| | | Sites site = null; |
| | | if(bikes.getLatitude()!=null && bikes.getLongitude()!=null){ |
| | | //根据定位信息查询所在站点 |
| | | site = getBackSiteByPostion(bikes.getLatitude().doubleValue(),bikes.getLongitude().doubleValue()); |
| | | } |
| | | bikesMapper.update(null,new UpdateWrapper<Bikes>().lambda() |
| | | .set(bike.getLatitude()!=null,Bikes::getLatitude,bike.getLatitude()) |
| | | .set(bike.getVoltage()!=null,Bikes::getVoltage,bike.getVoltage()) |
| | | .set(bike.getLongitude()!=null,Bikes::getLongitude,bike.getLongitude()) |
| | | .set(Bikes::getSiteId,site ==null?null:site.getId()) |
| | | .set( Bikes::getHeartDate,date) |
| | | .eq(Bikes::getId,bikes.getId())); |
| | | } |
| | | } |
| | | } |