server/services/src/main/java/com/doumee/config/jwt/WebMvcConfig.java
@@ -10,6 +10,7 @@ import com.doumee.dao.business.model.Member; import com.doumee.dao.business.model.ShopInfo; import io.jsonwebtoken.JwtException; import lombok.extern.log4j.Log4j; import org.apache.commons.lang3.StringUtils; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.context.annotation.Bean; @@ -26,6 +27,7 @@ import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpServletResponse; import java.util.Objects; import java.util.logging.Logger; @Configuration public class WebMvcConfig implements WebMvcConfigurer { @@ -115,6 +117,7 @@ public Boolean checkMemberLogin(HttpServletRequest request, HttpServletResponse response){ String token = request.getHeader(JwtTokenUtil.HEADER_KEY); System.out.println("ä¼åtoken:=========>{}"+token); try { if(!token.startsWith(Constants.ZERO+"")){ throw new BusinessException(ResponseStatus.TOKEN_EXCEED_TIME); @@ -145,6 +148,7 @@ public Boolean checkShopLogin(String token,HttpServletRequest request, HttpServletResponse response){ System.out.println("é¨åºtoken:=========>{}"+token); try { if(!token.startsWith(Constants.TWO+"")){ throw new BusinessException(ResponseStatus.SHOP_TOKEN_EXCEED_TIME); @@ -185,6 +189,7 @@ public Boolean checkDriverLogin(HttpServletRequest request, HttpServletResponse response){ String token = request.getHeader(JwtTokenUtil.HEADER_KEY); System.out.println("叿ºtoken:=========>{}"+token); try { if(!token.startsWith(Constants.ONE+"")){ throw new BusinessException(ResponseStatus.TOKEN_EXCEED_TIME); server/services/src/main/java/com/doumee/dao/business/model/Orders.java
@@ -420,6 +420,14 @@ private String c2OtherField; @TableField(exist = false) @ApiModelProperty(value = "ç©åç级åç§°ï¼å ³èæ¥è¯¢ï¼") private String goodLevelName; @TableField(exist = false) @ApiModelProperty(value = "æ¯å¦åå¨ç¹å¤§å°ºå¯¸ï¼0=å¦ 1=æ¯ï¼å ³èæ¥è¯¢ï¼") private Integer hasOversized; @TableField(exist = false) @ApiModelProperty(value = "叿ºå§åï¼å ³èæ¥è¯¢ï¼") private String driverName; server/services/src/main/java/com/doumee/dao/dto/DriverOrderPageDTO.java
¶Ô±ÈÐÂÎļþ @@ -0,0 +1,19 @@ package com.doumee.dao.dto; import io.swagger.annotations.ApiModel; import io.swagger.annotations.ApiModelProperty; import lombok.Data; /** * 叿ºè®¢åå页æ¥è¯¢è¯·æ± * @author rk * @date 2026/04/25 */ @Data @ApiModel("叿ºè®¢åå页æ¥è¯¢è¯·æ±") public class DriverOrderPageDTO { @ApiModelProperty(value = "订åç¶æçéï¼null=å ¨é¨ï¼3=å¾ åä»¶ï¼4=é éä¸ï¼7=已宿") private Integer status; } server/services/src/main/java/com/doumee/dao/dto/DriverPickupDTO.java
@@ -25,4 +25,10 @@ @Size(min = 1, max = 3, message = "åä»¶å¾ç1-3å¼ ") @ApiModelProperty(value = "åä»¶å¾çåè¡¨ï¼æå¤3å¼ ï¼", required = true) private List<String> images; @ApiModelProperty(value = "夿³¨") private String remark; } server/services/src/main/java/com/doumee/dao/dto/ShopInfoMaintainDTO.java
@@ -20,6 +20,9 @@ @ApiModelProperty(value = "é¨åºå¤´å") private String coverImg; @ApiModelProperty(value = "é¨åºå¤´åï¼å ¨è·¯å¾ï¼") private String coverImgUrl; @ApiModelProperty(value = "é¨åºä»ç»") private String content; server/services/src/main/java/com/doumee/dao/vo/DriverActiveOrderCountVO.java
¶Ô±ÈÐÂÎļþ @@ -0,0 +1,21 @@ package com.doumee.dao.vo; import io.swagger.annotations.ApiModel; import io.swagger.annotations.ApiModelProperty; import lombok.Data; /** * 叿ºè¿è¡ä¸è®¢åæ°é * @author rk * @date 2026/04/25 */ @Data @ApiModel("叿ºè¿è¡ä¸è®¢åæ°é") public class DriverActiveOrderCountVO { @ApiModelProperty(value = "å·²æ¢åæ°é", example = "0") private Integer grabbedCount; @ApiModelProperty(value = "æ´¾é䏿°é", example = "0") private Integer deliveringCount; } server/services/src/main/java/com/doumee/dao/vo/DriverCancelLimitVO.java
¶Ô±ÈÐÂÎļþ @@ -0,0 +1,24 @@ package com.doumee.dao.vo; import io.swagger.annotations.ApiModel; import io.swagger.annotations.ApiModelProperty; import lombok.Data; /** * 叿ºä»æ¥åæ¶æ¬¡æ° * @author rk * @date 2026/04/25 */ @Data @ApiModel("叿ºä»æ¥åæ¶æ¬¡æ°") public class DriverCancelLimitVO { @ApiModelProperty(value = "æ¯æ¥åæ¶ä¸é", example = "3") private Integer limit; @ApiModelProperty(value = "仿¥å·²åæ¶æ¬¡æ°", example = "1") private Integer used; @ApiModelProperty(value = "仿¥å©ä½å¯åæ¶æ¬¡æ°", example = "2") private Integer remain; } server/services/src/main/java/com/doumee/dao/vo/DriverGrabOrderVO.java
@@ -37,8 +37,14 @@ @ApiModelProperty(value = "è·åä»¶é¨åºè·ç¦»ï¼å¦ 500mã1.2kmï¼") private String depositDistance; @ApiModelProperty(value = "åä»¶åç§°ï¼é¨åºåç§°æèªå®ä¹å°ç¹ï¼") @ApiModelProperty(value = "åä»¶é¨åºåç§°") private String takeName; @ApiModelProperty(value = "åä»¶å°å") private String takeAddress; @ApiModelProperty(value = "åä»¶é¨åºä¸»é®ï¼æåä»¶é¨åºæ¶è¿åï¼") private Integer takeShopId; @ApiModelProperty(value = "åä»¶è·ç¦»ï¼å¦ 500mã1.2kmï¼") private String takeDistance; @@ -58,6 +64,15 @@ @ApiModelProperty(value = "æ¯å¦è´µéç©å") private Boolean isValuable; @ApiModelProperty(value = "ç©åç级åç§°") private String goodLevelName; @ApiModelProperty(value = "æ¯å¦åå¨ç¹å¤§å°ºå¯¸ï¼0=å¦ 1=æ¯") private Integer hasOversized; @ApiModelProperty(value = "叿ºåè´§ç ï¼å¾ åè´§ç¶ææ¶è¿åï¼") private String driverVerifyCode; @Data @ApiModel("æ¢å大å ç©å项") public static class OrderItem implements Serializable { @@ -66,6 +81,9 @@ @ApiModelProperty(value = "æ°é") private Integer quantity; @ApiModelProperty(value = "æ¯å¦å¤§ä»¶ç©åï¼0=å¦ 1=æ¯") private Integer isOversized; } } server/services/src/main/java/com/doumee/dao/vo/DriverOrderDetailVO.java
@@ -47,6 +47,12 @@ @ApiModelProperty(value = "åä»¶åç§°ï¼é¨åºåç§°æèªå®ä¹å°ç¹ï¼") private String takeName; @ApiModelProperty(value = "åä»¶å°å") private String takeAddress; @ApiModelProperty(value = "åä»¶é¨åºä¸»é®ï¼æåä»¶é¨åºæ¶è¿åï¼") private Integer takeShopId; @ApiModelProperty(value = "åä»¶è·ç¦»ï¼å¦ 500mã1.2kmï¼") private String takeDistance; @@ -64,6 +70,15 @@ @ApiModelProperty(value = "æ¯å¦è´µéç©å") private Boolean isValuable; @ApiModelProperty(value = "ç©åç级åç§°") private String goodLevelName; @ApiModelProperty(value = "æ¯å¦åå¨ç¹å¤§å°ºå¯¸ï¼0=å¦ 1=æ¯") private Integer hasOversized; @ApiModelProperty(value = "叿ºåè´§ç ï¼å¾ åè´§ç¶ææ¶è¿åï¼") private String driverVerifyCode; @ApiModelProperty(value = "导èªçº¬åº¦ï¼status=2åä»¶é¨åºçº¬åº¦ï¼status=3/4å件纬度ï¼") private Double navigateLat; @@ -123,6 +138,9 @@ @ApiModelProperty(value = "æ°é") private Integer quantity; @ApiModelProperty(value = "æ¯å¦å¤§ä»¶ç©åï¼0=å¦ 1=æ¯") private Integer isOversized; } } server/services/src/main/java/com/doumee/dao/vo/ShopDetailVO.java
@@ -169,4 +169,7 @@ @ApiModelProperty(value = "ç»å®å¼æ·ä¼å头å") private String payMemberCoverImage; @ApiModelProperty(value = "é¨åºå¤´åï¼å ¨è·¯å¾ï¼") private String shopAvatar; } server/services/src/main/java/com/doumee/service/business/DriverInfoService.java
@@ -4,6 +4,7 @@ import com.doumee.core.model.PageWrap; import com.doumee.dao.dto.DriverActiveOrderDTO; import com.doumee.dao.dto.DriverGrabOrderDTO; import com.doumee.dao.dto.DriverOrderPageDTO; import com.doumee.dao.business.model.DriverInfo; import com.doumee.dao.dto.DriverLoginRequest; import com.doumee.dao.dto.DriverDeliverDTO; @@ -11,9 +12,10 @@ import com.doumee.dao.dto.DriverRegisterRequest; import com.doumee.dao.dto.DriverVerifyRequest; import com.doumee.dao.vo.AccountResponse; import com.doumee.dao.vo.DriverActiveOrderCountVO; import com.doumee.dao.vo.DriverGrabOrderVO; import java.util.List; import java.util.Map; /** * 叿ºæ³¨åä¿¡æ¯Serviceå®ä¹ @@ -269,8 +271,25 @@ * è·å叿ºè¿è¡ä¸è®¢åæ°é * * @param driverId 叿ºä¸»é® * @return [å·²æ¢åæ°é, æ´¾é䏿°é] * @return è¿è¡ä¸è®¢åæ°é */ Map<String, Integer> getActiveOrderCount(Integer driverId); DriverActiveOrderCountVO getActiveOrderCount(Integer driverId); /** * 叿ºè®¢åå页æ¥è¯¢ * * @param driverId 叿ºä¸»é® * @param pageWrap å页忰ï¼model.status: null=å ¨é¨, 3=å¾ åä»¶, 4=é éä¸, 7=å·²å®æï¼ * @return åé¡µç»æ */ PageData<DriverGrabOrderVO> driverOrderPage(Integer driverId, PageWrap<DriverOrderPageDTO> pageWrap); /** * æ¥è¯¢å¸æºä»æ¥å¯åæ¶æ¬¡æ° * * @param driverId 叿ºä¸»é® * @return DriverCancelLimitVO */ com.doumee.dao.vo.DriverCancelLimitVO getTodayCancelLimit(Integer driverId); } server/services/src/main/java/com/doumee/service/business/impl/DriverInfoServiceImpl.java
@@ -30,6 +30,8 @@ import com.doumee.dao.business.OrderLogMapper; import com.doumee.dao.dto.*; import com.doumee.dao.vo.AccountResponse; import com.doumee.dao.vo.DriverActiveOrderCountVO; import com.doumee.dao.vo.DriverCancelLimitVO; import com.doumee.dao.vo.DriverCenterVO; import com.doumee.dao.vo.DriverGrabOrderVO; import com.doumee.dao.vo.DriverOrderDetailVO; @@ -48,6 +50,7 @@ import org.springframework.util.CollectionUtils; import java.util.*; import java.util.concurrent.TimeUnit; import java.util.stream.Collectors; /** @@ -845,7 +848,7 @@ Long todayOrderCount = ordersMapper.selectCount(new QueryWrapper<Orders>().lambda() .eq(Orders::getAcceptDriver, driver.getId()) .eq(Orders::getDeleted, Constants.ZERO) .ge(Orders::getFinishTime, todayStart)); .ge(Orders::getAcceptTime, todayStart)); vo.setTodayOrderCount(todayOrderCount.intValue()); // å¾ åè´§ï¼å·²æ¥å=3ï¼ @@ -945,10 +948,8 @@ goodTypeIds = cats.stream().map(Category::getId).collect(Collectors.toList()); } // 3. Haversine SQLå ¬å¼ï¼å¸æºå°åä»¶é¨åºè·ç¦»(km)ï¼ä½¿ç¨Ordersèªå¸¦åæ String depositDist = "(6371 * acos(cos(radians(" + driverLat + ")) * cos(radians(t.DEPOSIT_LGT)) " + "* cos(radians(t.DEPOSIT_LAT) - radians(" + driverLng + ")) " + "+ sin(radians(" + driverLat + ")) * sin(radians(t.DEPOSIT_LGT))))"; // 3. ST_Distance_Sphere计ç®å¸æºå°åä»¶é¨åºè·ç¦»(km)ï¼ä½¿ç¨Ordersèªå¸¦åæ String depositDist = "(ST_Distance_Sphere(POINT(" + driverLng + ", " + driverLat + "), POINT(t.DEPOSIT_LGT, t.DEPOSIT_LAT)) / 1000)"; // 4. æé MPJæ¥è¯¢ IPage<Orders> page = new Page<>(pageWrap.getPage(), pageWrap.getCapacity()); @@ -963,6 +964,9 @@ .select("s2.link_phone as takeShopLinkPhone") // ç©åççº§è´µéæ è¯ .select("c2.other_field as c2OtherField") .select("c2.name as goodLevelName") // æ¯å¦åå¨ç¹å¤§å°ºå¯¸ .select("IF(EXISTS(SELECT 1 FROM orders_detail od JOIN category c3 ON c3.id = od.LUGGAGE_ID AND c3.TYPE = 4 AND c3.OTHER_FIELD = '1' WHERE od.ORDER_ID = t.ID AND od.DELETED = 0), 1, 0) as hasOversized") // JOIN .leftJoin("shop_info s1 on s1.id = t.DEPOSIT_SHOP_ID and s1.DELETED = 0") .leftJoin("shop_info s2 on s2.id = t.TAKE_SHOP_ID and s2.DELETED = 0") @@ -1062,13 +1066,15 @@ .select("s2.address", Orders::getTakeShopAddress) .select("s2.link_phone as takeShopLinkPhone") .select("c2.other_field as c2OtherField") .select("c2.name as goodLevelName") .select("IF(EXISTS(SELECT 1 FROM orders_detail od JOIN category c3 ON c3.id = od.LUGGAGE_ID AND c3.TYPE = 4 AND c3.OTHER_FIELD = '1' WHERE od.ORDER_ID = t.ID AND od.DELETED = 0), 1, 0) as hasOversized") .leftJoin("shop_info s1 on s1.id = t.DEPOSIT_SHOP_ID and s1.DELETED = 0") .leftJoin("shop_info s2 on s2.id = t.TAKE_SHOP_ID and s2.DELETED = 0") .leftJoin("category c1 on c1.id = t.GOOD_TYPE and c1.DELETED = 0") .leftJoin("category c2 on c2.id = c1.RELATION_ID and c2.DELETED = 0 and c2.TYPE = 3") .eq(Orders::getAcceptDriver, driver.getId()) .eq(Orders::getType, Constants.ONE) .eq(Orders::getStatus, dto.getStatus()) .eq(Objects.nonNull(dto.getStatus()),Orders::getStatus, dto.getStatus()) .eq(Orders::getDeleted, Constants.ZERO) .orderByAsc(Orders::getAcceptTime); @@ -1107,6 +1113,7 @@ .select("s2.address", Orders::getTakeShopAddress) .select("s2.link_phone as takeShopLinkPhone") .select("c2.other_field as c2OtherField") .select("IF(EXISTS(SELECT 1 FROM orders_detail od JOIN category c3 ON c3.id = od.LUGGAGE_ID AND c3.TYPE = 4 AND c3.OTHER_FIELD = '1' WHERE od.ORDER_ID = t.ID AND od.DELETED = 0), 1, 0) as hasOversized") .leftJoin("shop_info s1 on s1.id = t.DEPOSIT_SHOP_ID and s1.DELETED = 0") .leftJoin("shop_info s2 on s2.id = t.TAKE_SHOP_ID and s2.DELETED = 0") .leftJoin("category c1 on c1.id = t.GOOD_TYPE and c1.DELETED = 0") @@ -1164,11 +1171,17 @@ vo.setDepositShopAddress(base.getDepositShopAddress()); vo.setDepositDistance(base.getDepositDistance()); vo.setTakeName(base.getTakeName()); vo.setTakeAddress(base.getTakeAddress()); vo.setTakeShopId(base.getTakeShopId()); vo.setTakeDistance(base.getTakeDistance()); vo.setContactPhone(base.getContactPhone()); vo.setDriverFee(base.getDriverFee()); vo.setUrgentAmount(base.getUrgentAmount()); vo.setIsValuable(base.getIsValuable()); vo.setGoodLevelName(base.getGoodLevelName()); vo.setHasOversized(base.getHasOversized()); vo.setDriverVerifyCode(base.getDriverVerifyCode()); // ç©åæç»ï¼è½¬æ¢ç±»åï¼ List<DriverOrderDetailVO.OrderItem> detailItems = new ArrayList<>(); @@ -1177,6 +1190,7 @@ DriverOrderDetailVO.OrderItem item = new DriverOrderDetailVO.OrderItem(); item.setName(src.getName()); item.setQuantity(src.getQuantity()); item.setIsOversized(src.getIsOversized()); detailItems.add(item); } } @@ -1380,11 +1394,13 @@ // 5. ååæ´æ°ï¼å¸¦ status=2 æ¡ä»¶é²æ¢å¹¶åé夿¢å Date now = new Date(); String driverVerifyCode = generateVerifyCode(); int rows = ordersMapper.update(new UpdateWrapper<Orders>().lambda() .set(Orders::getAcceptDriver, driverId) .set(Orders::getAcceptTime, now) .set(Orders::getAcceptType, 0) // 0=æå¨æ¢å .set(Orders::getStatus, Constants.OrderStatus.accepted.getStatus()) .set(Orders::getDriverVerifyCode, driverVerifyCode) .set(Orders::getUpdateTime, now) .eq(Orders::getId, orderId) .eq(Orders::getStatus, Constants.TWO)); @@ -1486,6 +1502,7 @@ log.setOptUserId(driver.getMemberId()); log.setOptUserType(Constants.ONE); log.setOrderStatus(Constants.OrderStatus.delivering.getStatus()); log.setRemark(dto.getRemark()); log.setCreateTime(now); log.setDeleted(Constants.ZERO); orderLogMapper.insert(log); @@ -1636,6 +1653,22 @@ return String.format("%.1fkm", km); } /** * çæ6使°åæ ¸éç ï¼Redis SETNX ä¿è¯å¯ä¸ï¼ */ private String generateVerifyCode() { Random random = new Random(); String redisKey = Constants.REDIS_VERIFY_CODE_KEY; for (int i = 0; i < 200; i++) { String code = String.format("%06d", random.nextInt(1000000)); Boolean success = redisTemplate.opsForValue().setIfAbsent(redisKey + code, "1", 24, TimeUnit.HOURS); if (success != null && success) { return code; } } throw new BusinessException(ResponseStatus.BAD_REQUEST.getCode(), "æ ¸éç çæå¤±è´¥ï¼è¯·éè¯"); } private double haversine(double lat1, double lng1, double lat2, double lng2) { double R = 6371; double dLat = Math.toRadians(lat2 - lat1); @@ -1697,9 +1730,12 @@ boolean hasTakeShop = order.getTakeShopId() != null && StringUtils.isNotBlank(order.getTakeShopName()); if (hasTakeShop) { vo.setTakeName(order.getTakeShopName()); vo.setTakeAddress(order.getTakeShopAddress()); vo.setTakeShopId(order.getTakeShopId()); vo.setContactPhone(order.getTakeShopLinkPhone()); } else { vo.setTakeName(order.getTakeLocation()); vo.setTakeAddress(order.getTakeLocationRemark()); vo.setContactPhone(order.getTakePhone()); } if (driverLat != null && driverLng != null @@ -1711,14 +1747,36 @@ // è´µéç©å vo.setIsValuable("1".equals(order.getC2OtherField())); vo.setGoodLevelName(order.getGoodLevelName()); vo.setHasOversized(order.getHasOversized()); // å¾ åè´§ç¶æ(status=3)è¿å叿ºåè´§ç if (Constants.equalsInteger(order.getStatus(), Constants.THREE)||Constants.equalsInteger(order.getStatus(), Constants.FOUR)) { vo.setDriverVerifyCode(order.getDriverVerifyCode()); } // ç©åæç» List<OrdersDetail> details = detailMap.getOrDefault(order.getId(), Collections.emptyList()); // æ¹éæ¥è¯¢æ¶åå°ç luggageId 对åºç categoryï¼å¤ææ¯å¦å¤§ä»¶ Set<Integer> luggageIds = details.stream() .map(OrdersDetail::getLuggageId) .filter(Objects::nonNull) .collect(Collectors.toSet()); Set<Integer> oversizedIds = new HashSet<>(); if (!luggageIds.isEmpty()) { categoryMapper.selectList(new QueryWrapper<Category>().lambda() .in(Category::getId, luggageIds) .eq(Category::getType, Constants.FOUR) .eq(Category::getOtherField, "1") .eq(Category::getDeleted, Constants.ZERO)) .forEach(c -> oversizedIds.add(c.getId())); } List<DriverGrabOrderVO.OrderItem> items = new ArrayList<>(); for (OrdersDetail detail : details) { DriverGrabOrderVO.OrderItem item = new DriverGrabOrderVO.OrderItem(); item.setName(detail.getLuggageName()); item.setQuantity(detail.getNum()); item.setIsOversized(oversizedIds.contains(detail.getLuggageId()) ? Constants.ONE : Constants.ZERO); items.add(item); } vo.setItems(items); @@ -1804,7 +1862,7 @@ } @Override public Map<String, Integer> getActiveOrderCount(Integer driverId) { public DriverActiveOrderCountVO getActiveOrderCount(Integer driverId) { // å·²æ¢å(status=3)æ°é Long grabbed = ordersMapper.selectCount(new QueryWrapper<Orders>().lambda() .eq(Orders::getAcceptDriver, driverId) @@ -1815,10 +1873,121 @@ .eq(Orders::getAcceptDriver, driverId) .eq(Orders::getStatus, Constants.OrderStatus.delivering.getStatus()) .eq(Orders::getDeleted, Constants.ZERO)); Map<String, Integer> result = new HashMap<>(); result.put("grabbedCount", grabbed != null ? grabbed.intValue() : 0); result.put("deliveringCount", delivering != null ? delivering.intValue() : 0); return result; DriverActiveOrderCountVO vo = new DriverActiveOrderCountVO(); vo.setGrabbedCount(grabbed != null ? grabbed.intValue() : 0); vo.setDeliveringCount(delivering != null ? delivering.intValue() : 0); return vo; } @Override public PageData<DriverGrabOrderVO> driverOrderPage(Integer driverId, PageWrap<DriverOrderPageDTO> pageWrap) { DriverInfo driver = driverInfoMapper.selectById(driverId); if (driver == null) { throw new BusinessException(ResponseStatus.DATA_EMPTY.getCode(), "叿ºä¿¡æ¯ä¸åå¨"); } DriverOrderPageDTO model = pageWrap.getModel(); Integer status = model != null ? model.getStatus() : null; // åæ³ç¶ææ ¡éª List<Integer> validStatuses = Arrays.asList( Constants.OrderStatus.accepted.getStatus(), Constants.OrderStatus.delivering.getStatus(), Constants.OrderStatus.finished.getStatus()); if (status != null && !validStatuses.contains(status)) { throw new BusinessException(ResponseStatus.BAD_REQUEST.getCode(), "ç¶æåªè½ä¸º3(å¾ åä»¶)ã4(é éä¸)ã7(已宿)"); } IPage<Orders> p = new Page<>(pageWrap.getPage(), pageWrap.getCapacity()); MPJLambdaWrapper<Orders> wrapper = new MPJLambdaWrapper<>(); wrapper.selectAll(Orders.class) .select("s1.name", Orders::getDepositShopName) .select("s1.address", Orders::getDepositShopAddress) .select("s2.name", Orders::getTakeShopName) .select("s2.address", Orders::getTakeShopAddress) .select("s2.link_phone as takeShopLinkPhone") .select("c2.other_field as c2OtherField") .select("c2.name as goodLevelName") .select("IF(EXISTS(SELECT 1 FROM orders_detail od JOIN category c3 ON c3.id = od.LUGGAGE_ID AND c3.TYPE = 4 AND c3.OTHER_FIELD = '1' WHERE od.ORDER_ID = t.ID AND od.DELETED = 0), 1, 0) as hasOversized") .leftJoin("shop_info s1 on s1.id = t.DEPOSIT_SHOP_ID and s1.DELETED = 0") .leftJoin("shop_info s2 on s2.id = t.TAKE_SHOP_ID and s2.DELETED = 0") .leftJoin("category c1 on c1.id = t.GOOD_TYPE and c1.DELETED = 0") .leftJoin("category c2 on c2.id = c1.RELATION_ID and c2.DELETED = 0 and c2.TYPE = 3") .eq(Orders::getAcceptDriver, driverId) .in(status == null, Orders::getStatus, validStatuses) .eq(status != null, Orders::getStatus, status) .eq(Orders::getDeleted, Constants.ZERO) .orderByDesc(Orders::getAcceptTime); IPage<Orders> orderPage = ordersMapper.selectJoinPage(p, Orders.class, wrapper); List<DriverGrabOrderVO> voList = new ArrayList<>(); if (orderPage != null && orderPage.getRecords() != null) { // æ¹éæ¥ç©åæç» List<Integer> orderIds = orderPage.getRecords().stream().map(Orders::getId).collect(Collectors.toList()); Map<Integer, List<OrdersDetail>> detailMap = new HashMap<>(); if (!orderIds.isEmpty()) { List<OrdersDetail> allDetails = ordersDetailMapper.selectList( new QueryWrapper<OrdersDetail>().lambda() .in(OrdersDetail::getOrderId, orderIds)); for (OrdersDetail d : allDetails) { detailMap.computeIfAbsent(d.getOrderId(), k -> new ArrayList<>()).add(d); } } Double driverLat = driver.getLatitude(); Double driverLng = driver.getLongitude(); Date now = new Date(); for (Orders order : orderPage.getRecords()) { boolean needDepositDist = Constants.equalsInteger(order.getStatus(), Constants.OrderStatus.accepted.getStatus()); voList.add(buildDriverOrderVO(order, driverLat, driverLng, needDepositDist, now, detailMap)); } } IPage<DriverGrabOrderVO> vPage = new Page<>(pageWrap.getPage(), pageWrap.getCapacity()); PageData<DriverGrabOrderVO> pageData = PageData.from(vPage); pageData.setRecords(voList); if (orderPage != null) { pageData.setTotal(orderPage.getTotal()); pageData.setPage(orderPage.getCurrent()); pageData.setCapacity(orderPage.getSize()); } return pageData; } @Override public DriverCancelLimitVO getTodayCancelLimit(Integer driverId) { DriverInfo driver = driverInfoMapper.selectById(driverId); if (driver == null) { throw new BusinessException(ResponseStatus.DATA_EMPTY.getCode(), "叿ºä¿¡æ¯ä¸åå¨"); } // æ¯æ¥åæ¶ä¸é String limitStr = operationConfigBiz.getConfig().getDriverDailyCancelLimit(); int limit = 3; if (StringUtils.isNotBlank(limitStr)) { try { limit = Integer.parseInt(limitStr); } catch (NumberFormatException ignored) {} } // 仿¥å·²åæ¶æ¬¡æ° Calendar cal = Calendar.getInstance(); cal.set(Calendar.HOUR_OF_DAY, 0); cal.set(Calendar.MINUTE, 0); cal.set(Calendar.SECOND, 0); cal.set(Calendar.MILLISECOND, 0); Date todayStart = cal.getTime(); Long todayCancelCount = orderLogMapper.selectCount(new QueryWrapper<OrderLog>().lambda() .eq(OrderLog::getOptUserId, driver.getMemberId()) .eq(OrderLog::getObjType, Constants.OrderLogType.driverCancel.getStatus()) .eq(OrderLog::getOptUserType, Constants.ONE) .ge(OrderLog::getCreateTime, todayStart)); int used = todayCancelCount != null ? todayCancelCount.intValue() : 0; DriverCancelLimitVO vo = new DriverCancelLimitVO(); vo.setLimit(limit); vo.setUsed(used); vo.setRemain(Math.max(limit - used, 0)); return vo; } } server/services/src/main/java/com/doumee/service/business/impl/OrdersServiceImpl.java
@@ -1526,7 +1526,7 @@ wrapper.eq(status != null, Orders::getStatus, status) .in(statusList != null && !Constants.equalsInteger(combinedStatus, Constants.SEVEN), Orders::getStatus, statusList) .orderByDesc(Orders::getCreateTime); .orderByDesc(Orders::getId); IPage<Orders> orderPage = ordersMapper.selectJoinPage(p, Orders.class, wrapper); List<MyOrderVO> voList = new ArrayList<>(); @@ -1950,7 +1950,8 @@ .set(Orders::getTakeLocation, order.getDepositLocation()) .set(Orders::getTakeLocationRemark, order.getDepositLocationRemark()) .set(Orders::getTakeLat, order.getDepositLat()) .set(Orders::getTakeLgt, order.getDepositLgt()); .set(Orders::getTakeLgt, order.getDepositLgt()) .set(Orders::getExpectedTakeTime, new Date()); if (Constants.equalsInteger(status, Constants.OrderStatus.accepted.getStatus())) { updateWrapper.lambda() .set(Orders::getAcceptDriver, null) @@ -2665,7 +2666,7 @@ if (!shopId.equals(order.getDepositShopId())) { throw new BusinessException(ResponseStatus.BAD_REQUEST.getCode(), "该订åä¸å±äºå½åé¨åºï¼æ æ³æ ¸é"); } order.setStatus(Constants.OrderStatus.deposited.getStatus()); order.setStatus(Constants.equalsInteger(order.getType(),Constants.ZERO)?Constants.OrderStatus.arrived.getStatus():Constants.OrderStatus.deposited.getStatus()); order.setDepositTime(now); // éæ¾å½åæ ¸éç ï¼çææ°çæ ¸éç ä¾åä»¶æ¶ä½¿ç¨ String verifyCode = order.getMemberVerifyCode(); @@ -3544,26 +3545,20 @@ /** * å°±å°å¯å龿天æ°è®¡ç® * è¿äºé¢è®¡åä»¶æ¶é´å½å¤©ç24:00ï¼æ¬¡æ¥00:00ï¼åæç®ç¬¬ä¸å¤© * è¿äºé¢è®¡åä»¶æ¥æçæ¬¡æ¥ï¼åªæ¯è¾å¹´ææ¥ï¼åå¼å§è®¡é¾æå¤©æ° */ private int calcLocalOverdueDays(Date now, Date expectedTakeTime) { if (expectedTakeTime == null || !now.after(expectedTakeTime)) { if (expectedTakeTime == null) { return 0; } // åºåæ¶é´ = é¢è®¡åä»¶æ¥æçæ¬¡æ¥ 00:00ï¼å³å½å¤©24:00ï¼ // åªåå¹´ææ¥ Calendar baseCal = Calendar.getInstance(); baseCal.setTime(expectedTakeTime); baseCal.set(Calendar.HOUR_OF_DAY, 0); baseCal.set(Calendar.MINUTE, 0); baseCal.set(Calendar.SECOND, 0); baseCal.set(Calendar.MILLISECOND, 0); baseCal.add(Calendar.DAY_OF_MONTH, 1); // 次æ¥00:00 = å½å¤©24:00 Date baseTime = baseCal.getTime(); if (!now.after(baseTime)) { return 0; } // é¾æå¤©æ° = å½åæ¥æ - åºåæ¥æï¼æå¤©åå·®ï¼ Calendar nowCal = Calendar.getInstance(); nowCal.setTime(now); nowCal.set(Calendar.HOUR_OF_DAY, 0); @@ -3571,40 +3566,31 @@ nowCal.set(Calendar.SECOND, 0); nowCal.set(Calendar.MILLISECOND, 0); Calendar baseDateCal = Calendar.getInstance(); baseDateCal.setTime(baseTime); baseDateCal.set(Calendar.HOUR_OF_DAY, 0); baseDateCal.set(Calendar.MINUTE, 0); baseDateCal.set(Calendar.SECOND, 0); baseDateCal.set(Calendar.MILLISECOND, 0); long diffMs = nowCal.getTimeInMillis() - baseDateCal.getTimeInMillis(); int days = (int) (diffMs / (1000 * 60 * 60 * 24)); return Math.max(days, 0); // åºåæ¥æ = é¢è®¡åä»¶æ¥æçæ¬¡æ¥ï¼å½å¤©åä¹åä¸ç®é¾æ if (nowCal.before(baseCal)) { return 0; } // é¾æå¤©æ° = å½åæ¥æ - åºåæ¥æ long diffMs = nowCal.getTimeInMillis() - baseCal.getTimeInMillis(); return (int) (diffMs / (1000 * 60 * 60 * 24)); } /** * å¼å°å¯å龿天æ°è®¡ç® * è¿äºè½¬ç§»å°åºæ¶é´å½å¤©çæä¸12ç¹ï¼24:00ï¼åæç®ç¬¬ä¸å¤© * è¿äºè½¬ç§»å°åºæ¥æç次æ¥ï¼åªæ¯è¾å¹´ææ¥ï¼åå¼å§è®¡é¾æå¤©æ° */ private int calcRemoteOverdueDays(Date now, Date arriveTime) { if (arriveTime == null || !now.after(arriveTime)) { if (arriveTime == null) { return 0; } // åºåæ¶é´ = 转移å°åºæ¥æçæ¬¡æ¥ 00:00ï¼å³å½å¤©24:00ï¼ // åªåå¹´ææ¥ Calendar baseCal = Calendar.getInstance(); baseCal.setTime(arriveTime); baseCal.set(Calendar.HOUR_OF_DAY, 0); baseCal.set(Calendar.MINUTE, 0); baseCal.set(Calendar.SECOND, 0); baseCal.set(Calendar.MILLISECOND, 0); baseCal.add(Calendar.DAY_OF_MONTH, 1); // 次æ¥00:00 = å½å¤©24:00 Date baseTime = baseCal.getTime(); if (!now.after(baseTime)) { return 0; } // é¾æå¤©æ° = å½åæ¥æ - åºåæ¥æ Calendar nowCal = Calendar.getInstance(); nowCal.setTime(now); nowCal.set(Calendar.HOUR_OF_DAY, 0); @@ -3612,16 +3598,14 @@ nowCal.set(Calendar.SECOND, 0); nowCal.set(Calendar.MILLISECOND, 0); Calendar baseDateCal = Calendar.getInstance(); baseDateCal.setTime(baseTime); baseDateCal.set(Calendar.HOUR_OF_DAY, 0); baseDateCal.set(Calendar.MINUTE, 0); baseDateCal.set(Calendar.SECOND, 0); baseDateCal.set(Calendar.MILLISECOND, 0); long diffMs = nowCal.getTimeInMillis() - baseDateCal.getTimeInMillis(); int days = (int) (diffMs / (1000 * 60 * 60 * 24)); return Math.max(days, 0); // åºåæ¥æ = å°åºæ¥æç次æ¥ï¼å½å¤©åä¹åä¸ç®é¾æ baseCal.add(Calendar.DAY_OF_MONTH, 1); if (nowCal.before(baseCal)) { return 0; } // é¾æå¤©æ° = å½åæ¥æ - åºåæ¥æ long diffMs = nowCal.getTimeInMillis() - baseCal.getTimeInMillis(); return (int) (diffMs / (1000 * 60 * 60 * 24)); } @Override server/services/src/main/java/com/doumee/service/business/impl/ShopInfoServiceImpl.java
@@ -757,6 +757,13 @@ } } // é¨åºå¤´åï¼ä¼å ä½¿ç¨ coverImgï¼ä¸ºç©ºååé¨å¤´ç §ç¬¬ä¸å¼ if (StringUtils.isNotBlank(shopInfo.getCoverImg())) { vo.setShopAvatar(imgPrefix + shopInfo.getCoverImg()); } else if (!CollectionUtils.isEmpty(vo.getStoreFrontImgUrls())) { vo.setShopAvatar(vo.getStoreFrontImgUrls().get(0)); } return vo; } @@ -906,8 +913,8 @@ } @Override public ShopInfoMaintainDTO getShopMaintainInfo(Integer memberId) { ShopInfo shop = shopInfoMapper.selectById(memberId); public ShopInfoMaintainDTO getShopMaintainInfo(Integer shopId) { ShopInfo shop = shopInfoMapper.selectById(shopId); if (Objects.isNull(shop) || Constants.equalsInteger(shop.getDeleted(), Constants.ONE)) { return null; } @@ -919,6 +926,10 @@ dto.setDeliveryArea(shop.getDeliveryArea()); dto.setShopHours(shop.getShopHours()); dto.setBusinessType(shop.getBusinessType()); // 头åå ¨è·¯å¾ if (StringUtils.isNotBlank(shop.getCoverImg())) { dto.setCoverImgUrl(getShopPrefix() + shop.getCoverImg()); } return dto; } server/web/src/main/java/com/doumee/api/web/DriverInfoApi.java
@@ -12,10 +12,13 @@ import com.doumee.dao.dto.DriverGrabOrderDTO; import com.doumee.dao.dto.DriverLoginRequest; import com.doumee.dao.dto.DriverDeliverDTO; import com.doumee.dao.dto.DriverOrderPageDTO; import com.doumee.dao.dto.DriverPickupDTO; import com.doumee.dao.dto.DriverRegisterRequest; import com.doumee.dao.dto.DriverVerifyRequest; import com.doumee.dao.vo.AccountResponse; import com.doumee.dao.vo.DriverActiveOrderCountVO; import com.doumee.dao.vo.DriverCancelLimitVO; import com.doumee.dao.vo.DriverCenterVO; import com.doumee.dao.vo.DriverGrabOrderVO; import com.doumee.dao.vo.DriverOrderDetailVO; @@ -30,14 +33,13 @@ import javax.validation.Valid; import java.util.List; import java.util.Map; /** * 叿ºéªè¯ç ç»å½æ¥å£ * @author rk * @date 2026/04/08 */ @Api(tags = "叿ºéªè¯ç ç»å½") @Api(tags = "叿ºä¸å¡æ¥å£") @Trace(exclude = true) @RestController @RequestMapping("/web/driverInfo") @@ -158,7 +160,7 @@ @LoginDriverRequired @Trace @ApiOperation(value = "叿ºæ¢å", notes = "对已å¯å(status=2)çå¼å°å¯å订ååèµ·æ¢å") @PostMapping("/grabOrder") @GetMapping("/grabOrder") @ApiImplicitParams({ @ApiImplicitParam(paramType = "header", dataType = "String", name = "token", value = "ç¨æ·tokenå¼", required = true), @ApiImplicitParam(paramType = "query", dataType = "Integer", name = "orderId", value = "订å主é®", required = true) @@ -248,8 +250,30 @@ @ApiImplicitParams({ @ApiImplicitParam(paramType = "header", dataType = "String", name = "token", value = "ç¨æ·tokenå¼", required = true) }) public ApiResponse<Map<String, Integer>> activeOrderCount() { public ApiResponse<DriverActiveOrderCountVO> activeOrderCount() { return ApiResponse.success("æä½æå", driverInfoService.getActiveOrderCount(this.getDriverId())); } @LoginDriverRequired @Trace @ApiOperation(value = "叿ºè®¢åå页", notes = "æ¥è¯¢å¸æºçå ¨é¨/å¾ åä»¶/é éä¸/å·²å®æè®¢å") @PostMapping("/orderPage") @ApiImplicitParams({ @ApiImplicitParam(paramType = "header", dataType = "String", name = "token", value = "ç¨æ·tokenå¼", required = true) }) public ApiResponse<PageData<DriverGrabOrderVO>> orderPage(@RequestBody PageWrap<DriverOrderPageDTO> pageWrap) { return ApiResponse.success("æä½æå", driverInfoService.driverOrderPage(this.getDriverId(), pageWrap)); } @LoginDriverRequired @Trace @ApiOperation(value = "仿¥å¯åæ¶æ¬¡æ°", notes = "è¿å叿ºä»æ¥åæ¶æ¬¡æ°ä¸éãå·²åæ¶æ¬¡æ°ãå©ä½å¯åæ¶æ¬¡æ°") @GetMapping("/cancelLimit") @ApiImplicitParams({ @ApiImplicitParam(paramType = "header", dataType = "String", name = "token", value = "ç¨æ·tokenå¼", required = true) }) public ApiResponse<DriverCancelLimitVO> cancelLimit() { return ApiResponse.success("æä½æå", driverInfoService.getTodayCancelLimit(this.getDriverId())); } } server/web/src/main/java/com/doumee/api/web/PaymentCallback.java
@@ -22,6 +22,7 @@ import com.wechat.pay.java.service.payments.model.Transaction; import com.wechat.pay.java.service.refund.model.RefundNotification; import com.wechat.pay.java.service.refund.model.Status; import io.swagger.annotations.Api; import lombok.extern.slf4j.Slf4j; import org.apache.commons.lang3.StringUtils; import org.springframework.beans.factory.annotation.Autowired; @@ -36,6 +37,7 @@ * @Author : Rk * @create 2023/3/24 16:57 */ @Api(tags = "æ¯ä»åè°ä¸å¡æ¥å£") @Slf4j @RestController @CrossOrigin server/web/src/main/java/com/doumee/api/web/ShopInfoApi.java
@@ -33,7 +33,7 @@ * @author rk * @date 2026/04/10 */ @Api(tags = "é¨åºå ¥é©»") @Api(tags = "é¨åºä¸å¡æ¥å£") @RestController @RequestMapping("/web/shopInfo") public class ShopInfoApi extends ApiController { @@ -60,6 +60,7 @@ return ApiResponse.success(shopInfoService.getMyShop(this.getMemberId())); } @ApiOperation("éè¿é¨åºå页å表") @PostMapping("/nearby") public ApiResponse<PageData<ShopNearbyVO>> nearby(@RequestBody @Validated PageWrap<ShopNearbyDTO> pageWrap) { @@ -80,6 +81,16 @@ }) public ApiResponse<ShopCenterVO> getShopInfo() { return ApiResponse.success("æ¥è¯¢æå", shopInfoService.getShopCenterInfo(getShopId())); } @LoginShopRequired @ApiOperation("é¨åºç«¯æ¥è¯¢é¨åºè¯¦æ ") @GetMapping("/shopDetail") @ApiImplicitParams({ @ApiImplicitParam(paramType = "header", dataType = "String", name = "token", value = "é¨åºtokenå¼", required = true) }) public ApiResponse<ShopDetailVO> shopDetail() { return ApiResponse.success("æ¥è¯¢æå", shopInfoService.getShopDetail(getShopId())); } @LoginShopRequired @@ -105,7 +116,7 @@ @ApiOperation("æ¥è¯¢é¨åºç»´æ¤ä¿¡æ¯") @PostMapping("/maintainInfo") public ApiResponse<ShopInfoMaintainDTO> maintainInfo() { return ApiResponse.success(shopInfoService.getShopMaintainInfo(this.getMemberId())); return ApiResponse.success(shopInfoService.getShopMaintainInfo(this.getShopId())); } @LoginRequired