rk
2026-04-10 dc0b51b8800a31da0701c3f31a0b1460ae3c3ad9
代码生成
已添加53个文件
已修改11个文件
6152 ■■■■■ 文件已修改
server/admin/src/main/java/com/doumee/api/business/AreasController.java 107 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/admin/src/main/java/com/doumee/api/business/BannerController.java 92 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/admin/src/main/java/com/doumee/api/business/DriverInfoController.java 103 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/admin/src/main/java/com/doumee/api/business/PricingRuleController.java 200 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/admin/src/main/java/com/doumee/api/business/ShopInfoController.java 93 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/admin/src/main/java/com/doumee/api/business/SmsrecordController.java 93 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/pom.xml 22 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/services/db/business.banner.permissions.sql 5 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/services/src/main/java/com/doumee/config/cache/RedisConfig.java 36 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/services/src/main/java/com/doumee/config/jwt/JwtTokenUtil.java 32 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/services/src/main/java/com/doumee/core/utils/FileDigest.java 69 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/services/src/main/java/com/doumee/core/utils/PinYinUtil.java 137 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/services/src/main/java/com/doumee/core/utils/aliyun/ALiYunUtil.java 553 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/services/src/main/java/com/doumee/dao/business/AreasMapper.java 12 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/services/src/main/java/com/doumee/dao/business/BannerMapper.java 13 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/services/src/main/java/com/doumee/dao/business/DriverInfoMapper.java 13 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/services/src/main/java/com/doumee/dao/business/PricingRuleMapper.java 13 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/services/src/main/java/com/doumee/dao/business/ShopInfoMapper.java 13 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/services/src/main/java/com/doumee/dao/business/SmsrecordMapper.java 13 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/services/src/main/java/com/doumee/dao/business/model/Areas.java 134 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/services/src/main/java/com/doumee/dao/business/model/Banner.java 74 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/services/src/main/java/com/doumee/dao/business/model/Category.java 23 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/services/src/main/java/com/doumee/dao/business/model/DriverInfo.java 145 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/services/src/main/java/com/doumee/dao/business/model/Member.java 21 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/services/src/main/java/com/doumee/dao/business/model/Multifile.java 5 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/services/src/main/java/com/doumee/dao/business/model/PricingRule.java 70 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/services/src/main/java/com/doumee/dao/business/model/ShopInfo.java 124 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/services/src/main/java/com/doumee/dao/business/model/Smsrecord.java 71 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/services/src/main/java/com/doumee/dao/dto/AreasDto.java 25 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/services/src/main/java/com/doumee/dao/dto/AuditDTO.java 3 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/services/src/main/java/com/doumee/dao/dto/DriverLoginRequest.java 27 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/services/src/main/java/com/doumee/dao/dto/DriverRegisterRequest.java 27 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/services/src/main/java/com/doumee/dao/dto/DriverVerifyRequest.java 75 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/services/src/main/java/com/doumee/dao/dto/EstimatedDeliverySaveDTO.java 33 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/services/src/main/java/com/doumee/dao/dto/LocalStoragePricingItemDTO.java 26 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/services/src/main/java/com/doumee/dao/dto/LocalStoragePricingSaveDTO.java 30 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/services/src/main/java/com/doumee/dao/dto/RemoteDeliveryPricingItemDTO.java 38 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/services/src/main/java/com/doumee/dao/dto/RemoteDeliveryPricingSaveDTO.java 30 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/services/src/main/java/com/doumee/dao/dto/RevenueShareItemDTO.java 26 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/services/src/main/java/com/doumee/dao/dto/RevenueShareSaveDTO.java 30 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/services/src/main/java/com/doumee/dao/dto/StoreDepositItemDTO.java 26 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/services/src/main/java/com/doumee/dao/dto/StoreDepositSaveDTO.java 30 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/services/src/main/java/com/doumee/dao/vo/EstimatedDeliveryVO.java 29 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/services/src/main/java/com/doumee/dao/vo/LocalStoragePricingVO.java 32 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/services/src/main/java/com/doumee/dao/vo/RemoteDeliveryPricingVO.java 41 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/services/src/main/java/com/doumee/dao/vo/RevenueShareVO.java 32 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/services/src/main/java/com/doumee/dao/vo/StoreDepositVO.java 32 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/services/src/main/java/com/doumee/service/business/AreasService.java 136 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/services/src/main/java/com/doumee/service/business/BannerService.java 37 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/services/src/main/java/com/doumee/service/business/DriverInfoService.java 149 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/services/src/main/java/com/doumee/service/business/MemberService.java 12 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/services/src/main/java/com/doumee/service/business/PricingRuleService.java 187 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/services/src/main/java/com/doumee/service/business/ShopInfoService.java 99 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/services/src/main/java/com/doumee/service/business/SmsrecordService.java 99 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/services/src/main/java/com/doumee/service/business/impl/AreasServiceImpl.java 521 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/services/src/main/java/com/doumee/service/business/impl/BannerServiceImpl.java 148 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/services/src/main/java/com/doumee/service/business/impl/DriverInfoServiceImpl.java 585 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/services/src/main/java/com/doumee/service/business/impl/MemberServiceImpl.java 127 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/services/src/main/java/com/doumee/service/business/impl/PricingRuleServiceImpl.java 602 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/services/src/main/java/com/doumee/service/business/impl/ShopInfoServiceImpl.java 171 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/services/src/main/java/com/doumee/service/business/impl/SmsrecordServiceImpl.java 159 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/web/src/main/java/com/doumee/api/web/AccountApi.java 20 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/web/src/main/java/com/doumee/api/web/DriverInfoApi.java 82 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/web/src/main/java/com/doumee/api/web/UserApi.java 140 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
server/admin/src/main/java/com/doumee/api/business/AreasController.java
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,107 @@
package com.doumee.api.business;
import com.doumee.api.BaseController;
import com.doumee.core.annotation.excel.ExcelExporter;
import com.doumee.core.annotation.pr.PreventRepeat;
import com.doumee.core.model.ApiResponse;
import com.doumee.core.model.PageData;
import com.doumee.core.model.PageWrap;
import com.doumee.dao.business.model.Areas;
import com.doumee.dao.dto.AreasDto;
import com.doumee.service.business.AreasService;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import org.apache.shiro.authz.annotation.RequiresPermissions;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.*;
import javax.servlet.http.HttpServletResponse;
import java.util.ArrayList;
import java.util.List;
/**
 * @author æ±Ÿè¹„蹄
 * @date 2023/02/15 08:55
 */
@Api(tags = "省市区信息表")
@RestController
@RequestMapping("/business/areas")
public class AreasController extends BaseController {
    @Autowired
    private AreasService areasService;
    @PreventRepeat
    @ApiOperation("新建")
    @PostMapping("/create")
    @RequiresPermissions("business:areas:create")
    public ApiResponse create(@RequestBody Areas areas) {
        return ApiResponse.success(areasService.create(areas));
    }
    @ApiOperation("根据ID删除")
    @GetMapping("/delete/{id}")
    @RequiresPermissions("business:areas:delete")
    public ApiResponse deleteById(@PathVariable Integer id) {
        areasService.deleteById(id);
        return ApiResponse.success(null);
    }
    @ApiOperation("批量删除")
    @GetMapping("/delete/batch")
    @RequiresPermissions("business:areas:delete")
    public ApiResponse deleteByIdInBatch(@RequestParam String ids) {
        String [] idArray = ids.split(",");
        List<Integer> idList = new ArrayList<>();
        for (String id : idArray) {
            idList.add(Integer.valueOf(id));
        }
        areasService.deleteByIdInBatch(idList);
        return ApiResponse.success(null);
    }
    @ApiOperation("根据ID修改")
    @PostMapping("/updateById")
    @RequiresPermissions("business:areas:update")
    public ApiResponse updateById(@RequestBody Areas areas) {
        areasService.updateById(areas);
        return ApiResponse.success(null);
    }
    @ApiOperation("分页查询")
    @PostMapping("/page")
//    @RequiresPermissions("business:areas:query")
    public ApiResponse<PageData<Areas>> findPage (@RequestBody PageWrap<Areas> pageWrap) {
        return ApiResponse.success(areasService.findPage(pageWrap));
    }
    @ApiOperation("全部树形查询")
    @PostMapping("/treeList")
//    @RequiresPermissions("business:areas:query")
    public ApiResponse<List<Areas>> treeList (@RequestBody AreasDto pageWrap) {
        Areas a = new Areas();
        BeanUtils.copyProperties(pageWrap,a);
        return ApiResponse.success(areasService.findList(a));
    }
    @ApiOperation("根据父节点和类型查询")
    @PostMapping("/listByParentId")
//    @RequiresPermissions("business:areas:query")
    public ApiResponse<List<Areas>> listByParentId (@RequestBody AreasDto pageWrap) {
        return ApiResponse.success(areasService.findByParentId(pageWrap.getParentId(),pageWrap.getType(),pageWrap.getFlag()) );
    }
    @ApiOperation("导出Excel")
    @PostMapping("/exportExcel")
    @RequiresPermissions("business:areas:exportExcel")
    public void exportExcel (@RequestBody PageWrap<Areas> pageWrap, HttpServletResponse response) {
        ExcelExporter.build(Areas.class).export(areasService.findPage(pageWrap).getRecords(), "省市区信息表", response);
    }
    @ApiOperation("根据ID查询")
    @GetMapping("/{id}")
    @RequiresPermissions("business:areas:query")
    public ApiResponse findById(@PathVariable Integer id) {
        return ApiResponse.success(areasService.findById(id));
    }
}
server/admin/src/main/java/com/doumee/api/business/BannerController.java
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,92 @@
package com.doumee.api.business;
import com.doumee.api.BaseController;
import com.doumee.core.annotation.excel.ExcelExporter;
import com.doumee.core.annotation.pr.PreventRepeat;
import com.doumee.core.model.ApiResponse;
import com.doumee.core.model.PageData;
import com.doumee.core.model.PageWrap;
import com.doumee.dao.business.model.Banner;
import com.doumee.service.business.BannerService;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import org.apache.shiro.authz.annotation.RequiresPermissions;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.*;
import javax.servlet.http.HttpServletResponse;
import java.util.ArrayList;
import java.util.List;
/**
 * è½®æ’­å›¾
 * @author rk
 * @date 2026/04/08
 */
@Api(tags = "轮播图")
@RestController
@RequestMapping("/business/banner")
public class BannerController extends BaseController {
    @Autowired
    private BannerService bannerService;
    @PreventRepeat
    @ApiOperation("新建")
    @PostMapping("/create")
    @RequiresPermissions("business:banner:create")
    public ApiResponse create(@RequestBody Banner banner) {
        return ApiResponse.success(bannerService.create(banner));
    }
    @ApiOperation("根据ID删除")
    @GetMapping("/delete/{id}")
    @RequiresPermissions("business:banner:delete")
    public ApiResponse deleteById(@PathVariable Integer id) {
        bannerService.deleteById(id);
        return ApiResponse.success(null);
    }
    @ApiOperation("批量删除")
    @GetMapping("/delete/batch")
    @RequiresPermissions("business:banner:delete")
    public ApiResponse deleteByIdInBatch(@RequestParam String ids) {
        String[] idArray = ids.split(",");
        List<Integer> idList = new ArrayList<>();
        for (String id : idArray) {
            idList.add(Integer.valueOf(id));
        }
        bannerService.deleteByIdInBatch(idList);
        return ApiResponse.success(null);
    }
    @ApiOperation("根据ID修改")
    @PostMapping("/updateById")
    @RequiresPermissions("business:banner:update")
    public ApiResponse updateById(@RequestBody Banner banner) {
        bannerService.updateById(banner);
        return ApiResponse.success(null);
    }
    @ApiOperation("分页查询")
    @PostMapping("/page")
    @RequiresPermissions("business:banner:query")
    public ApiResponse<PageData<Banner>> findPage(@RequestBody PageWrap<Banner> pageWrap) {
        return ApiResponse.success(bannerService.findPage(pageWrap));
    }
    @ApiOperation("导出Excel")
    @PostMapping("/exportExcel")
    @RequiresPermissions("business:banner:exportExcel")
    public void exportExcel(@RequestBody PageWrap<Banner> pageWrap, HttpServletResponse response) {
        List<Banner> bannerList = bannerService.findPage(pageWrap).getRecords();
        ExcelExporter.build(Banner.class).export(bannerList, "轮播图", response);
    }
    @ApiOperation("根据ID查询")
    @GetMapping("/{id}")
    @RequiresPermissions("business:banner:query")
    public ApiResponse findById(@PathVariable Integer id) {
        return ApiResponse.success(bannerService.findById(id));
    }
}
server/admin/src/main/java/com/doumee/api/business/DriverInfoController.java
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,103 @@
package com.doumee.api.business;
import com.doumee.api.BaseController;
import com.doumee.core.annotation.excel.ExcelExporter;
import com.doumee.core.annotation.pr.PreventRepeat;
import com.doumee.core.model.ApiResponse;
import com.doumee.core.model.PageData;
import com.doumee.core.model.PageWrap;
import com.doumee.dao.business.model.DriverInfo;
import com.doumee.dao.dto.AuditDTO;
import com.doumee.service.business.DriverInfoService;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import org.apache.shiro.authz.annotation.RequiresPermissions;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.*;
import javax.servlet.http.HttpServletResponse;
import java.util.ArrayList;
import java.util.List;
/**
 * å¸æœºæ³¨å†Œä¿¡æ¯
 * @author rk
 * @date 2026/04/08
 */
@Api(tags = "司机注册信息")
@RestController
@RequestMapping("/business/driverInfo")
public class DriverInfoController extends BaseController {
    @Autowired
    private DriverInfoService driverInfoService;
    @PreventRepeat
    @ApiOperation("新建")
    @PostMapping("/create")
    @RequiresPermissions("business:driverInfo:create")
    public ApiResponse create(@RequestBody DriverInfo driverInfo) {
        return ApiResponse.success(driverInfoService.create(driverInfo));
    }
    @ApiOperation("根据ID删除")
    @GetMapping("/delete/{id}")
    @RequiresPermissions("business:driverInfo:delete")
    public ApiResponse deleteById(@PathVariable Integer id) {
        driverInfoService.deleteById(id);
        return ApiResponse.success(null);
    }
    @ApiOperation("批量删除")
    @GetMapping("/delete/batch")
    @RequiresPermissions("business:driverInfo:delete")
    public ApiResponse deleteByIdInBatch(@RequestParam String ids) {
        String[] idArray = ids.split(",");
        List<Integer> idList = new ArrayList<>();
        for (String id : idArray) {
            idList.add(Integer.valueOf(id));
        }
        driverInfoService.deleteByIdInBatch(idList);
        return ApiResponse.success(null);
    }
    @ApiOperation("根据ID修改")
    @PostMapping("/updateById")
    @RequiresPermissions("business:driverInfo:update")
    public ApiResponse updateById(@RequestBody DriverInfo driverInfo) {
        driverInfoService.updateById(driverInfo);
        return ApiResponse.success(null);
    }
    @ApiOperation("分页查询")
    @PostMapping("/page")
    @RequiresPermissions("business:driverInfo:query")
    public ApiResponse<PageData<DriverInfo>> findPage(@RequestBody PageWrap<DriverInfo> pageWrap) {
        return ApiResponse.success(driverInfoService.findPage(pageWrap));
    }
    @ApiOperation("导出Excel")
    @PostMapping("/exportExcel")
    @RequiresPermissions("business:driverInfo:exportExcel")
    public void exportExcel(@RequestBody PageWrap<DriverInfo> pageWrap, HttpServletResponse response) {
        List<DriverInfo> driverInfoList = driverInfoService.findPage(pageWrap).getRecords();
        ExcelExporter.build(DriverInfo.class).export(driverInfoList, "司机注册信息", response);
    }
    @ApiOperation("根据ID查询")
    @GetMapping("/{id}")
    @RequiresPermissions("business:driverInfo:query")
    public ApiResponse findById(@PathVariable Integer id) {
        return ApiResponse.success(driverInfoService.findById(id));
    }
    @ApiOperation("审批司机实名认证")
    @PostMapping("/audit")
    @RequiresPermissions("business:driverInfo:audit")
    public ApiResponse audit(@RequestBody AuditDTO auditDTO) {
        auditDTO.setAuditUser(this.getLoginUser().getId());
        driverInfoService.auditVerify(auditDTO);
        return ApiResponse.success("审批成功");
    }
}
server/admin/src/main/java/com/doumee/api/business/PricingRuleController.java
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,200 @@
package com.doumee.api.business;
import com.doumee.api.BaseController;
import com.doumee.core.annotation.excel.ExcelExporter;
import com.doumee.core.annotation.pr.PreventRepeat;
import com.doumee.core.model.ApiResponse;
import com.doumee.core.model.PageData;
import com.doumee.core.model.PageWrap;
import com.doumee.dao.business.model.PricingRule;
import com.doumee.dao.dto.LocalStoragePricingSaveDTO;
import com.doumee.dao.dto.RemoteDeliveryPricingSaveDTO;
import com.doumee.dao.dto.EstimatedDeliverySaveDTO;
import com.doumee.dao.dto.StoreDepositSaveDTO;
import com.doumee.dao.dto.RevenueShareSaveDTO;
import com.doumee.dao.vo.LocalStoragePricingVO;
import com.doumee.dao.vo.RemoteDeliveryPricingVO;
import com.doumee.dao.vo.EstimatedDeliveryVO;
import com.doumee.dao.vo.StoreDepositVO;
import com.doumee.dao.vo.RevenueShareVO;
import com.doumee.service.business.PricingRuleService;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import org.apache.shiro.authz.annotation.RequiresPermissions;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.*;
import javax.servlet.http.HttpServletResponse;
import java.util.ArrayList;
import java.util.List;
/**
 * è®¡ä»·è§„则配置
 * @author rk
 * @date 2026/04/08
 */
@Api(tags = "计价规则配置")
@RestController
@RequestMapping("/business/pricingRule")
public class PricingRuleController extends BaseController {
    @Autowired
    private PricingRuleService pricingRuleService;
    @PreventRepeat
    @ApiOperation("新建")
    @PostMapping("/create")
    @RequiresPermissions("business:pricingRule:create")
    public ApiResponse create(@RequestBody PricingRule pricingRule) {
        return ApiResponse.success(pricingRuleService.create(pricingRule));
    }
    @ApiOperation("根据ID删除")
    @GetMapping("/delete/{id}")
    @RequiresPermissions("business:pricingRule:delete")
    public ApiResponse deleteById(@PathVariable Integer id) {
        pricingRuleService.deleteById(id);
        return ApiResponse.success(null);
    }
    @ApiOperation("批量删除")
    @GetMapping("/delete/batch")
    @RequiresPermissions("business:pricingRule:delete")
    public ApiResponse deleteByIdInBatch(@RequestParam String ids) {
        String[] idArray = ids.split(",");
        List<Integer> idList = new ArrayList<>();
        for (String id : idArray) {
            idList.add(Integer.valueOf(id));
        }
        pricingRuleService.deleteByIdInBatch(idList);
        return ApiResponse.success(null);
    }
    @ApiOperation("根据ID修改")
    @PostMapping("/updateById")
    @RequiresPermissions("business:pricingRule:update")
    public ApiResponse updateById(@RequestBody PricingRule pricingRule) {
        pricingRuleService.updateById(pricingRule);
        return ApiResponse.success(null);
    }
    @ApiOperation("分页查询")
    @PostMapping("/page")
    @RequiresPermissions("business:pricingRule:query")
    public ApiResponse<PageData<PricingRule>> findPage(@RequestBody PageWrap<PricingRule> pageWrap) {
        return ApiResponse.success(pricingRuleService.findPage(pageWrap));
    }
    @ApiOperation("导出Excel")
    @PostMapping("/exportExcel")
    @RequiresPermissions("business:pricingRule:exportExcel")
    public void exportExcel(@RequestBody PageWrap<PricingRule> pageWrap, HttpServletResponse response) {
        List<PricingRule> pricingRuleList = pricingRuleService.findPage(pageWrap).getRecords();
        ExcelExporter.build(PricingRule.class).export(pricingRuleList, "计价规则配置", response);
    }
    @ApiOperation("根据ID查询")
    @GetMapping("/{id}")
    @RequiresPermissions("business:pricingRule:query")
    public ApiResponse findById(@PathVariable Integer id) {
        return ApiResponse.success(pricingRuleService.findById(id));
    }
    @PreventRepeat
    @ApiOperation("批量保存就地存取规则")
    @PostMapping("/localStorage/batchSave")
    @RequiresPermissions("business:pricingRule:create")
    public ApiResponse batchSaveLocalStoragePricing(@RequestBody @Validated LocalStoragePricingSaveDTO request) {
        pricingRuleService.batchSaveLocalStoragePricing(request);
        return ApiResponse.success(null);
    }
    @ApiOperation("查询就地存取规则列表")
    @GetMapping("/localStorage/list")
    @RequiresPermissions("business:pricingRule:query")
    public ApiResponse<List<LocalStoragePricingVO>> listLocalStoragePricing(@RequestParam Integer cityId) {
        return ApiResponse.success(pricingRuleService.listLocalStoragePricing(cityId));
    }
    @PreventRepeat
    @ApiOperation("批量保存异地寄送规则")
    @PostMapping("/remoteDelivery/batchSave")
    @RequiresPermissions("business:pricingRule:create")
    public ApiResponse batchSaveRemoteDeliveryPricing(@RequestBody @Validated RemoteDeliveryPricingSaveDTO request) {
        pricingRuleService.batchSaveRemoteDeliveryPricing(request);
        return ApiResponse.success(null);
    }
    @ApiOperation("查询异地寄送规则列表")
    @GetMapping("/remoteDelivery/list")
    @RequiresPermissions("business:pricingRule:query")
    public ApiResponse<List<RemoteDeliveryPricingVO>> listRemoteDeliveryPricing(@RequestParam Integer cityId) {
        return ApiResponse.success(pricingRuleService.listRemoteDeliveryPricing(cityId));
    }
    @PreventRepeat
    @ApiOperation("新增预计时效配置")
    @PostMapping("/estimatedDelivery/create")
    @RequiresPermissions("business:pricingRule:create")
    public ApiResponse createEstimatedDelivery(@RequestBody @Validated EstimatedDeliverySaveDTO request) {
        return ApiResponse.success(pricingRuleService.createEstimatedDelivery(request));
    }
    @PreventRepeat
    @ApiOperation("修改预计时效配置")
    @PostMapping("/estimatedDelivery/update")
    @RequiresPermissions("business:pricingRule:update")
    public ApiResponse updateEstimatedDelivery(@RequestBody @Validated EstimatedDeliverySaveDTO request) {
        pricingRuleService.updateEstimatedDelivery(request);
        return ApiResponse.success(null);
    }
    @ApiOperation("删除预计时效配置")
    @GetMapping("/estimatedDelivery/delete/{id}")
    @RequiresPermissions("business:pricingRule:delete")
    public ApiResponse deleteEstimatedDelivery(@PathVariable Integer id) {
        pricingRuleService.deleteEstimatedDelivery(id);
        return ApiResponse.success(null);
    }
    @ApiOperation("查询预计时效配置列表")
    @GetMapping("/estimatedDelivery/list")
    @RequiresPermissions("business:pricingRule:query")
    public ApiResponse<List<EstimatedDeliveryVO>> listEstimatedDelivery(@RequestParam Integer cityId) {
        return ApiResponse.success(pricingRuleService.listEstimatedDelivery(cityId));
    }
    @PreventRepeat
    @ApiOperation("批量保存门店注册押金")
    @PostMapping("/storeDeposit/batchSave")
    @RequiresPermissions("business:pricingRule:create")
    public ApiResponse batchSaveStoreDeposit(@RequestBody @Validated StoreDepositSaveDTO request) {
        pricingRuleService.batchSaveStoreDeposit(request);
        return ApiResponse.success(null);
    }
    @ApiOperation("查询门店注册押金列表")
    @GetMapping("/storeDeposit/list")
    @RequiresPermissions("business:pricingRule:query")
    public ApiResponse<List<StoreDepositVO>> listStoreDeposit(@RequestParam Integer cityId) {
        return ApiResponse.success(pricingRuleService.listStoreDeposit(cityId));
    }
    @PreventRepeat
    @ApiOperation("批量保存分成比例")
    @PostMapping("/revenueShare/batchSave")
    @RequiresPermissions("business:pricingRule:create")
    public ApiResponse batchSaveRevenueShare(@RequestBody @Validated RevenueShareSaveDTO request) {
        pricingRuleService.batchSaveRevenueShare(request);
        return ApiResponse.success(null);
    }
    @ApiOperation("查询分成比例列表")
    @GetMapping("/revenueShare/list")
    @RequiresPermissions("business:pricingRule:query")
    public ApiResponse<List<RevenueShareVO>> listRevenueShare(@RequestParam Integer cityId) {
        return ApiResponse.success(pricingRuleService.listRevenueShare(cityId));
    }
}
server/admin/src/main/java/com/doumee/api/business/ShopInfoController.java
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,93 @@
package com.doumee.api.business;
import com.doumee.api.BaseController;
import com.doumee.core.annotation.excel.ExcelExporter;
import com.doumee.core.annotation.pr.PreventRepeat;
import com.doumee.core.model.ApiResponse;
import com.doumee.core.model.PageData;
import com.doumee.core.model.PageWrap;
import com.doumee.dao.business.model.ShopInfo;
import com.doumee.service.business.ShopInfoService;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import org.apache.shiro.authz.annotation.RequiresPermissions;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.*;
import javax.servlet.http.HttpServletResponse;
import java.util.ArrayList;
import java.util.List;
/**
 * é—¨åº—信息
 * @author rk
 * @date 2026/04/08
 */
@Api(tags = "门店信息")
@RestController
@RequestMapping("/business/shopInfo")
public class ShopInfoController extends BaseController {
    @Autowired
    private ShopInfoService shopInfoService;
    @PreventRepeat
    @ApiOperation("新建")
    @PostMapping("/create")
    @RequiresPermissions("business:shopInfo:create")
    public ApiResponse create(@RequestBody ShopInfo shopInfo) {
        return ApiResponse.success(shopInfoService.create(shopInfo));
    }
    @ApiOperation("根据ID删除")
    @GetMapping("/delete/{id}")
    @RequiresPermissions("business:shopInfo:delete")
    public ApiResponse deleteById(@PathVariable Integer id) {
        shopInfoService.deleteById(id);
        return ApiResponse.success(null);
    }
    @ApiOperation("批量删除")
    @GetMapping("/delete/batch")
    @RequiresPermissions("business:shopInfo:delete")
    public ApiResponse deleteByIdInBatch(@RequestParam String ids) {
        String[] idArray = ids.split(",");
        List<Integer> idList = new ArrayList<>();
        for (String id : idArray) {
            idList.add(Integer.valueOf(id));
        }
        shopInfoService.deleteByIdInBatch(idList);
        return ApiResponse.success(null);
    }
    @ApiOperation("根据ID修改")
    @PostMapping("/updateById")
    @RequiresPermissions("business:shopInfo:update")
    public ApiResponse updateById(@RequestBody ShopInfo shopInfo) {
        shopInfoService.updateById(shopInfo);
        return ApiResponse.success(null);
    }
    @ApiOperation("分页查询")
    @PostMapping("/page")
    @RequiresPermissions("business:shopInfo:query")
    public ApiResponse<PageData<ShopInfo>> findPage(@RequestBody PageWrap<ShopInfo> pageWrap) {
        return ApiResponse.success(shopInfoService.findPage(pageWrap));
    }
    @ApiOperation("导出Excel")
    @PostMapping("/exportExcel")
    @RequiresPermissions("business:shopInfo:exportExcel")
    public void exportExcel(@RequestBody PageWrap<ShopInfo> pageWrap, HttpServletResponse response) {
        List<ShopInfo> shopInfoList = shopInfoService.findPage(pageWrap).getRecords();
        ExcelExporter.build(ShopInfo.class).export(shopInfoList, "门店信息", response);
    }
    @ApiOperation("根据ID查询")
    @GetMapping("/{id}")
    @RequiresPermissions("business:shopInfo:query")
    public ApiResponse findById(@PathVariable Integer id) {
        return ApiResponse.success(shopInfoService.findById(id));
    }
}
server/admin/src/main/java/com/doumee/api/business/SmsrecordController.java
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,93 @@
package com.doumee.api.business;
import com.doumee.api.BaseController;
import com.doumee.core.annotation.excel.ExcelExporter;
import com.doumee.core.annotation.pr.PreventRepeat;
import com.doumee.core.model.ApiResponse;
import com.doumee.core.model.PageData;
import com.doumee.core.model.PageWrap;
import com.doumee.dao.business.model.Smsrecord;
import com.doumee.service.business.SmsrecordService;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import org.apache.shiro.authz.annotation.RequiresPermissions;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.*;
import javax.servlet.http.HttpServletResponse;
import java.util.ArrayList;
import java.util.List;
/**
 * çŸ­ä¿¡éªŒè¯ç 
 * @author rk
 * @date 2026/04/08
 */
@Api(tags = "短信验证码")
@RestController
@RequestMapping("/business/smsrecord")
public class SmsrecordController extends BaseController {
    @Autowired
    private SmsrecordService smsrecordService;
    @PreventRepeat
    @ApiOperation("新建")
    @PostMapping("/create")
    @RequiresPermissions("business:smsrecord:create")
    public ApiResponse create(@RequestBody Smsrecord smsrecord) {
        return ApiResponse.success(smsrecordService.create(smsrecord));
    }
    @ApiOperation("根据ID删除")
    @GetMapping("/delete/{id}")
    @RequiresPermissions("business:smsrecord:delete")
    public ApiResponse deleteById(@PathVariable Integer id) {
        smsrecordService.deleteById(id);
        return ApiResponse.success(null);
    }
    @ApiOperation("批量删除")
    @GetMapping("/delete/batch")
    @RequiresPermissions("business:smsrecord:delete")
    public ApiResponse deleteByIdInBatch(@RequestParam String ids) {
        String[] idArray = ids.split(",");
        List<Integer> idList = new ArrayList<>();
        for (String id : idArray) {
            idList.add(Integer.valueOf(id));
        }
        smsrecordService.deleteByIdInBatch(idList);
        return ApiResponse.success(null);
    }
    @ApiOperation("根据ID修改")
    @PostMapping("/updateById")
    @RequiresPermissions("business:smsrecord:update")
    public ApiResponse updateById(@RequestBody Smsrecord smsrecord) {
        smsrecordService.updateById(smsrecord);
        return ApiResponse.success(null);
    }
    @ApiOperation("分页查询")
    @PostMapping("/page")
    @RequiresPermissions("business:smsrecord:query")
    public ApiResponse<PageData<Smsrecord>> findPage(@RequestBody PageWrap<Smsrecord> pageWrap) {
        return ApiResponse.success(smsrecordService.findPage(pageWrap));
    }
    @ApiOperation("导出Excel")
    @PostMapping("/exportExcel")
    @RequiresPermissions("business:smsrecord:exportExcel")
    public void exportExcel(@RequestBody PageWrap<Smsrecord> pageWrap, HttpServletResponse response) {
        List<Smsrecord> smsrecordList = smsrecordService.findPage(pageWrap).getRecords();
        ExcelExporter.build(Smsrecord.class).export(smsrecordList, "短信验证码", response);
    }
    @ApiOperation("根据ID查询")
    @GetMapping("/{id}")
    @RequiresPermissions("business:smsrecord:query")
    public ApiResponse findById(@PathVariable Integer id) {
        return ApiResponse.success(smsrecordService.findById(id));
    }
}
server/pom.xml
@@ -35,6 +35,8 @@
    <poi.version>5.0.0</poi.version>
    <jjwt.version>0.9.1</jjwt.version>
    <weixin-java-pay.version>4.1.0</weixin-java-pay.version>
    <!-- é˜¿é‡Œäº‘OSS存储 -->
    <aliyun-oss.version>3.8.0</aliyun-oss.version>
  </properties>
  <dependencies>
    <!-- Spring Boot -->
@@ -238,10 +240,11 @@
      <version>0.2.15</version>
    </dependency>
    <!--  é˜¿é‡Œäº‘OSS-->
    <dependency>
      <groupId>com.aliyun</groupId>
      <artifactId>aliyun-java-sdk-core</artifactId>
      <version>3.5.0</version>
      <groupId>com.aliyun.oss</groupId>
      <artifactId>aliyun-sdk-oss</artifactId>
      <version>${aliyun-oss.version}</version>
    </dependency>
    <dependency>
@@ -249,7 +252,18 @@
      <artifactId>aliyun-java-sdk-dysmsapi</artifactId>
      <version>1.1.0</version>
    </dependency>
    <!-- aliyun sms SDK -->
    <dependency>
      <groupId>com.aliyun</groupId>
      <artifactId>aliyun-java-sdk-core</artifactId>
      <version>4.5.3</version>
    </dependency>
  <!-- æ‹¼éŸ³è½¬æ¢ -->
    <dependency>
      <groupId>com.belerweb</groupId>
      <artifactId>pinyin4j</artifactId>
      <version>2.5.1</version>
    </dependency>
 <!--   <dependency>
      <groupId>com.azure.spring</groupId>
      <artifactId>spring-cloud-azure-starter-storage-blob</artifactId>
server/services/db/business.banner.permissions.sql
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,5 @@
INSERT INTO `SYSTEM_PERMISSION`(`CODE`, `NAME`, `MODULE`, `REMARK`, `FIXED`, `CREATE_USER`, `CREATE_TIME`, `UPDATE_USER`, `UPDATE_TIME`, `DELETED`) VALUES ('business:banner:create', '新建轮播图', '轮播图', '', 0, 1, CURRENT_TIMESTAMP, NULL, NULL, 0);
INSERT INTO `SYSTEM_PERMISSION`(`CODE`, `NAME`, `MODULE`, `REMARK`, `FIXED`, `CREATE_USER`, `CREATE_TIME`, `UPDATE_USER`, `UPDATE_TIME`, `DELETED`) VALUES ('business:banner:delete', '删除轮播图', '轮播图', '', 0, 1, CURRENT_TIMESTAMP, NULL, NULL, 0);
INSERT INTO `SYSTEM_PERMISSION`(`CODE`, `NAME`, `MODULE`, `REMARK`, `FIXED`, `CREATE_USER`, `CREATE_TIME`, `UPDATE_USER`, `UPDATE_TIME`, `DELETED`) VALUES ('business:banner:update', '修改轮播图', '轮播图', '', 0, 1, CURRENT_TIMESTAMP, NULL, NULL, 0);
INSERT INTO `SYSTEM_PERMISSION`(`CODE`, `NAME`, `MODULE`, `REMARK`, `FIXED`, `CREATE_USER`, `CREATE_TIME`, `UPDATE_USER`, `UPDATE_TIME`, `DELETED`) VALUES ('business:banner:query', '查询轮播图', '轮播图', '', 0, 1, CURRENT_TIMESTAMP, NULL, NULL, 0);
INSERT INTO `SYSTEM_PERMISSION`(`CODE`, `NAME`, `MODULE`, `REMARK`, `FIXED`, `CREATE_USER`, `CREATE_TIME`, `UPDATE_USER`, `UPDATE_TIME`, `DELETED`) VALUES ('business:banner:exportExcel', '导出轮播图(Excel)', '轮播图', '', 0, 1, CURRENT_TIMESTAMP, NULL, NULL, 0);
server/services/src/main/java/com/doumee/config/cache/RedisConfig.java
@@ -1,9 +1,14 @@
package com.doumee.config.cache;
import com.fasterxml.jackson.annotation.JsonAutoDetect;
import com.fasterxml.jackson.annotation.PropertyAccessor;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.fasterxml.jackson.databind.jsontype.impl.LaissezFaireSubTypeValidator;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.data.redis.connection.RedisConnectionFactory;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.data.redis.serializer.Jackson2JsonRedisSerializer;
import org.springframework.data.redis.serializer.StringRedisSerializer;
import java.io.Serializable;
@@ -17,16 +22,25 @@
public class RedisConfig {
    @Bean
    public RedisTemplate<Serializable, Serializable> redisTemplate(RedisConnectionFactory redisConnectionFactory) {
        RedisTemplate<Serializable, Serializable> redisTemplate = new RedisTemplate<>();
        redisTemplate.setConnectionFactory(redisConnectionFactory);
        // é»˜è®¤åºåˆ—化方式
        redisTemplate.setDefaultSerializer(new StringRedisSerializer());
        // å€¼åºåˆ—化方式
        RedisValueDefaultSerializer<Object> serializer = new RedisValueDefaultSerializer<>(Object.class);
        redisTemplate.setValueSerializer(serializer);
        redisTemplate.setHashValueSerializer(serializer);
        redisTemplate.afterPropertiesSet();
        return redisTemplate;
    @SuppressWarnings("all")
    public RedisTemplate<String, Object> redisTemplate(RedisConnectionFactory factory) {
        RedisTemplate<String, Object> template = new RedisTemplate<String, Object>();
        template.setConnectionFactory(factory);
        Jackson2JsonRedisSerializer jackson2JsonRedisSerializer = new Jackson2JsonRedisSerializer(Object.class);
        ObjectMapper om = new ObjectMapper();
        om.setVisibility(PropertyAccessor.ALL, JsonAutoDetect.Visibility.ANY);
        om.activateDefaultTyping(LaissezFaireSubTypeValidator.instance, ObjectMapper.DefaultTyping.NON_FINAL);
        jackson2JsonRedisSerializer.setObjectMapper(om);
        StringRedisSerializer stringRedisSerializer = new StringRedisSerializer();
        // key采用String的序列化方式
        template.setKeySerializer(stringRedisSerializer);
        // hash的key也采用String的序列化方式
        template.setHashKeySerializer(stringRedisSerializer);
        // value序列化方式采用jackson
        template.setValueSerializer(jackson2JsonRedisSerializer);
        // hash的value序列化方式采用jackson
        template.setHashValueSerializer(jackson2JsonRedisSerializer);
        template.afterPropertiesSet();
        return template;
    }
}
server/services/src/main/java/com/doumee/config/jwt/JwtTokenUtil.java
@@ -18,10 +18,7 @@
import javax.annotation.Resource;
import java.io.IOException;
import java.util.Date;
import java.util.HashMap;
import java.util.Map;
import java.util.Objects;
import java.util.*;
import java.util.concurrent.TimeUnit;
@Component
@@ -40,6 +37,8 @@
    @Resource
    private JwtProperties jwtProperties;
    //redis过期时间
    private static final Integer redisExpire = 365;
    /**
     * ç”Ÿæˆtoken令牌
     *
@@ -67,6 +66,31 @@
    }
    /**
     * ç”Ÿæˆtoken信息(同一用户仅保留一个有效token)
     * @param userId
     * @param userType ç”¨æˆ·ç±»åž‹ 0=会员;1=司机;2=店铺
     * @param userInfo
     * @param redisTemplate
     * @return
     */
    public static String generateTokenForRedis(Integer userId, Integer userType, String userInfo, RedisTemplate<String,Object> redisTemplate) {
        // åˆ é™¤è¯¥ç”¨æˆ·ä¹‹å‰ç™»å½•çš„token
        String userTokenMappingKey = Constants.REDIS_TOKEN_KEY + "user_" + userType + "_" + userId;
        String oldToken = (String) redisTemplate.opsForValue().get(userTokenMappingKey);
        if (StringUtils.isNotBlank(oldToken)) {
            redisTemplate.delete(Constants.REDIS_TOKEN_KEY + oldToken);
        }
        // ç”Ÿæˆæ–°token
        String tokenKey = userType +""+ UUID.randomUUID() + "_" + userId;
        redisTemplate.opsForValue().set(Constants.REDIS_TOKEN_KEY + tokenKey, userInfo, redisExpire, TimeUnit.DAYS);
        // è®°å½•用户与token的映射关系
        redisTemplate.opsForValue().set(userTokenMappingKey, tokenKey, redisExpire, TimeUnit.DAYS);
        return tokenKey;
    }
    /**
     * åˆ·æ–°ä»¤ç‰Œ
     *
server/services/src/main/java/com/doumee/core/utils/FileDigest.java
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,69 @@
package com.doumee.core.utils;
import java.io.File;
import java.io.FileInputStream;
import java.math.BigInteger;
import java.security.MessageDigest;
import java.util.HashMap;
import java.util.Map;
public class FileDigest {
    /**
     * è®¡ç®—文件的MD5值
     *
     * @param file
     * @return
     */
    public static String getFileMD5(File file) {
        if (!file.isFile()) {
            return null;
        }
        MessageDigest digest = null;
        FileInputStream in = null;
        byte buffer[] = new byte[1024];
        int len;
        try {
            digest = MessageDigest.getInstance("MD5");
            in = new FileInputStream(file);
            while ((len = in.read(buffer, 0, 1024)) != -1) {
                digest.update(buffer, 0, len);
            }
            in.close();
        } catch (Exception e) {
            e.printStackTrace();
            return null;
        }
        BigInteger bigInt = new BigInteger(1, digest.digest());
        return bigInt.toString(16);
    }
    /**
     * è®¡ç®—文件夹的MD5值
     *
     * @param file
     * @param listChild
     * @return
     */
    public static Map<String, String> getDirMD5(File file, boolean listChild) {
        if (!file.isDirectory()) {
            return null;
        }
        // <filepath,md5>
        Map<String, String> map = new HashMap<String, String>();
        String md5;
        File files[] = file.listFiles();
        for (int i = 0; i < files.length; i++) {
            File f = files[i];
            if (f.isDirectory() && listChild) {
                map.putAll(getDirMD5(f, listChild));
            } else {
                md5 = getFileMD5(f);
                if (md5 != null) {
                    map.put(f.getPath(), md5);
                }
            }
        }
        return map;
    }
}
server/services/src/main/java/com/doumee/core/utils/PinYinUtil.java
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,137 @@
package com.doumee.core.utils;
import net.sourceforge.pinyin4j.PinyinHelper;
import net.sourceforge.pinyin4j.format.HanyuPinyinCaseType;
import net.sourceforge.pinyin4j.format.HanyuPinyinOutputFormat;
import net.sourceforge.pinyin4j.format.HanyuPinyinToneType;
import net.sourceforge.pinyin4j.format.exception.BadHanyuPinyinOutputFormatCombination;
import org.apache.commons.lang3.StringUtils;
import java.text.Collator;
import java.util.Arrays;
import java.util.Collections;
import java.util.Comparator;
import java.util.List;
/**
 * æ±‰è¯­æ‹¼éŸ³å¸®åŠ©ç±»
 *
 * @author yanglong
 *
 */
public class PinYinUtil {
    /**
     * æ¯”较两个汉字的首字母 <br>
     *
     * @param ch1
     * @param ch2
     * @return
     */
    public static int comparatorWord(String ch1, String ch2) {
        return getFirstSpell(ch2).compareTo(getFirstSpell(ch1));
    }
    public static void main(String[] args) {
        Comparator<Object> com=Collator.getInstance(java.util.Locale.CHINA);
        String[] newArray={"中山","汕头","广州","安庆","阳江","南京","武汉","北京","安阳","北方"};
        List<String> list = Arrays.asList(newArray);
        Collections.sort(list, com);
        for(String i:list){
            System.out.print(i+"  ");
        }
        //System.err.println(getFirstFirstSpell("很合适的积分很少看见"));
    }
    /**
     * èŽ·å–æ±‰å­—ä¸²æ‹¼éŸ³é¦–å­—æ¯ï¼Œè‹±æ–‡å­—ç¬¦ä¸å˜
     *
     * @param chinese
     *            æ±‰å­—串
     * @return æ±‰è¯­æ‹¼éŸ³é¦–字母
     */
    public static String getFirstSpell(String chinese) {
        StringBuffer pybf = new StringBuffer();
        char[] arr = chinese.toCharArray();
        HanyuPinyinOutputFormat defaultFormat = new HanyuPinyinOutputFormat();
        defaultFormat.setCaseType(HanyuPinyinCaseType.LOWERCASE);
        defaultFormat.setToneType(HanyuPinyinToneType.WITHOUT_TONE);
        for (int i = 0; i < arr.length; i++) {
            if (arr[i] > 128) {
                try {
                    String[] temp = PinyinHelper.toHanyuPinyinStringArray(
                            arr[i], defaultFormat);
                    if (temp != null) {
                        pybf.append(temp[0].charAt(0));
                    }
                } catch (BadHanyuPinyinOutputFormatCombination e) {
                    e.printStackTrace();
                }
            } else {
                pybf.append(arr[i]);
            }
        }
        return pybf.toString().replaceAll("\\W", "").trim();
    }
    /**
     * èŽ·å–æ±‰å­—ä¸²æ‹¼éŸ³é¦–å­—æ¯ï¼Œè‹±æ–‡å­—ç¬¦ä¸å˜
     *
     * @param chinese
     *            æ±‰å­—串
     * @return æ±‰è¯­æ‹¼éŸ³é¦–字母
     */
    public static String getFirstFirstSpell(String chinese) {
        if(StringUtils.isBlank(chinese)){
            return null;
        }
        StringBuffer pybf = new StringBuffer();
        chinese = chinese.substring(0,1);
        char[] arr = chinese.toCharArray();
        HanyuPinyinOutputFormat defaultFormat = new HanyuPinyinOutputFormat();
        defaultFormat.setCaseType(HanyuPinyinCaseType.LOWERCASE);
        defaultFormat.setToneType(HanyuPinyinToneType.WITHOUT_TONE);
        for (int i = 0; i < arr.length; i++) {
            if (arr[i] > 128) {
                try {
                    String[] temp = PinyinHelper.toHanyuPinyinStringArray(
                            arr[i], defaultFormat);
                    if (temp != null) {
                        pybf.append(temp[0].charAt(0));
                    }
                } catch (BadHanyuPinyinOutputFormatCombination e) {
                    e.printStackTrace();
                }
            } else {
                pybf.append(arr[i]);
            }
        }
        return pybf.toString().replaceAll("\\W", "").trim().toUpperCase();
    }
    /**
     * èŽ·å–æ±‰å­—ä¸²æ‹¼éŸ³ï¼Œè‹±æ–‡å­—ç¬¦ä¸å˜
     *
     * @param chinese
     *            æ±‰å­—串
     * @return æ±‰è¯­æ‹¼éŸ³
     */
    public static String getFullSpell(String chinese) {
        StringBuffer pybf = new StringBuffer();
        char[] arr = chinese.toCharArray();
        HanyuPinyinOutputFormat defaultFormat = new HanyuPinyinOutputFormat();
        defaultFormat.setCaseType(HanyuPinyinCaseType.LOWERCASE);
        defaultFormat.setToneType(HanyuPinyinToneType.WITHOUT_TONE);
        for (int i = 0; i < arr.length; i++) {
            if (arr[i] > 128) {
                try {
                    pybf.append(PinyinHelper.toHanyuPinyinStringArray(arr[i],
                            defaultFormat)[0]);
                } catch (BadHanyuPinyinOutputFormatCombination e) {
                    e.printStackTrace();
                }
            } else {
                pybf.append(arr[i]);
            }
        }
        return pybf.toString();
    }
}
server/services/src/main/java/com/doumee/core/utils/aliyun/ALiYunUtil.java
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,553 @@
package com.doumee.core.utils.aliyun;
import com.aliyun.oss.ClientException;
import com.aliyun.oss.OSSClient;
import com.aliyun.oss.OSSException;
import com.aliyun.oss.model.*;
import com.doumee.core.utils.FileDigest;
import org.apache.commons.lang3.StringUtils;
import org.springframework.web.multipart.MultipartFile;
import java.io.*;
import java.net.URL;
import java.util.ArrayList;
import java.util.List;
import java.util.Map;
public class ALiYunUtil {
    private OSSClient client;
    // public static final String ENDPOINT = "oss-cn-shanghai.aliyuncs.com";
    public ALiYunUtil(String endpoint, String ACCESS_ID, String ACCESS_KEY) {
        client = new OSSClient(endpoint, ACCESS_ID, ACCESS_KEY);
    }
    /**
     * ä¸Šä¼ æ–‡ä»¶
     *
     * @param bucketName äº‘端存放bucket名称
     * @param key        é‡æ–°å‘½åçš„æ–‡ä»¶å
     * @param filename   å°†è¦ä¸Šä¼ çš„æ–‡ä»¶åç§°
     * @param mime       è¶…文本标记语言文本 .html,.html text/html æ™®é€šæ–‡æœ¬ .txt text/plain RTF文本
     *                   .rtf application/rtf GIF图形 .gif image/gif JPEG图形 .ipeg,.jpg
     *                   image/jpeg au声音文件 .au audio/basic MIDI音乐文件 mid,.midi
     *                   audio/midi,audio/x-midi RealAudio音乐文件 .ra, .ram
     *                   audio/x-pn-realaudio MPEG文件 .mpg,.mpeg video/mpeg AVI文件 .avi
     *                   video/x-msvideo GZIP文件 .gz application/x-gzip TAR文件 .tar
     *                   application/x-tar
     * @throws OSSException
     * @throws ClientException
     * @throws FileNotFoundException
     */
    public void uploadObject(String bucketName, String key, String filename,
                             String mime) throws OSSException, ClientException,
            FileNotFoundException {
        File file = new File(filename);
        // åˆ¤æ–­æ˜¯å¦å­˜åœ¨ï¼Œä¸å­˜åœ¨åˆ›å»º
        isExistBucket(bucketName);
        ObjectMetadata objectMeta = new ObjectMetadata();
        objectMeta.setContentLength(file.length());
        // å¯ä»¥åœ¨metadata中标记文件类型
        if (StringUtils.isNotBlank(mime)) {
            objectMeta.setContentType(mime);
        }
        InputStream input = new FileInputStream(file);
        client.putObject(bucketName, key, input, objectMeta);
    }
    /**
     * å…³é—­
     *
     * @throws OSSException
     * @throws ClientException
     * @throws FileNotFoundException
     */
    public void shutDown()
            throws OSSException, ClientException, FileNotFoundException {
        if (client != null) {
            // å…³é—­client
            client.shutdown();
        }
    }
    /**
     * æ‰¹é‡åˆ é™¤æ–‡ä»¶
     *
     * @param bucketName
     * @param keys
     * @throws OSSException
     * @throws ClientException
     * @throws FileNotFoundException
     */
    public void deleteObjects(String bucketName, List<String> keys)
            throws OSSException, ClientException, FileNotFoundException {
        if (keys == null || keys.size() > 0) {
            return;
        }
        DeleteObjectsResult deleteObjectsResult = client
                .deleteObjects(new DeleteObjectsRequest(bucketName)
                        .withKeys(keys));
        List<String> deletedObjects = deleteObjectsResult.getDeletedObjects();
        // å…³é—­client
        client.shutdown();
    }
    /**
     * ä¸Šä¼ æ–‡ä»¶
     *
     * @param bucketName äº‘端存放bucket名称
     *                   å°†è¦ä¸Šä¼ çš„æ–‡ä»¶åç§°
     * @param mime       è¶…文本标记语言文本 .html,.html text/html æ™®é€šæ–‡æœ¬ .txt text/plain RTF文本
     *                   .rtf application/rtf GIF图形 .gif image/gif JPEG图形 .ipeg,.jpg
     *                   image/jpeg au声音文件 .au audio/basic MIDI音乐文件 mid,.midi
     *                   audio/midi,audio/x-midi RealAudio音乐文件 .ra, .ram
     *                   audio/x-pn-realaudio MPEG文件 .mpg,.mpeg video/mpeg AVI文件 .avi
     *                   video/x-msvideo GZIP文件 .gz application/x-gzip TAR文件 .tar
     *                   application/x-tar
     * @throws OSSException
     * @throws ClientException
     * @throws FileNotFoundException
     */
    public void uploadFiles(String bucketName, Map<String, File> ossFiles,
                            String mime) throws OSSException, ClientException,
            FileNotFoundException {
        // åˆ¤æ–­æ˜¯å¦å­˜åœ¨ï¼Œä¸å­˜åœ¨åˆ›å»º
        isExistBucket(bucketName);
        // å¯ä»¥åœ¨metadata中标记文件类型
        if (ossFiles != null && ossFiles.size() > 0) {
            for (Map.Entry<String, File> entry : ossFiles.entrySet()) {
                ObjectMetadata objectMeta = new ObjectMetadata();
                objectMeta.setContentLength(entry.getValue().length());
                if (StringUtils.isNotBlank(mime)) {
                    objectMeta.setContentType(mime);
                }
                InputStream input = new FileInputStream(entry.getValue());
                client.putObject(bucketName, entry.getKey(), input, objectMeta);
                // ä¸Šä¼ å›¾ç‰‡
            }
        }
        client.shutdown();
    }
    /**
     * ä¸Šä¼ æ–‡ä»¶
     *
     * @param bucketName äº‘端存放bucket名称
     * @param key        å°†è¦ä¸Šä¼ çš„æ–‡ä»¶åç§°
     * @param mime       è¶…文本标记语言文本 .html,.html text/html æ™®é€šæ–‡æœ¬ .txt text/plain RTF文本
     *                   .rtf application/rtf GIF图形 .gif image/gif JPEG图形 .ipeg,.jpg
     *                   image/jpeg au声音文件 .au audio/basic MIDI音乐文件 mid,.midi
     *                   audio/midi,audio/x-midi RealAudio音乐文件 .ra, .ram
     *                   audio/x-pn-realaudio MPEG文件 .mpg,.mpeg video/mpeg AVI文件 .avi
     *                   video/x-msvideo GZIP文件 .gz application/x-gzip TAR文件 .tar
     *                   application/x-tar
     * @throws OSSException
     * @throws ClientException
     * @throws FileNotFoundException
     */
    public void uploadFile(String bucketName, String key, File file, String mime)
            throws OSSException, ClientException, FileNotFoundException {
        // åˆ¤æ–­æ˜¯å¦å­˜åœ¨ï¼Œä¸å­˜åœ¨åˆ›å»º
        isExistBucket(bucketName);
        ObjectMetadata objectMeta = new ObjectMetadata();
        objectMeta.setContentLength(file.length());
        // å¯ä»¥åœ¨metadata中标记文件类型
        if (StringUtils.isNotBlank(mime)) {
            objectMeta.setContentType(mime);
        }
        InputStream input = new FileInputStream(file);
        client.putObject(bucketName, key, input, objectMeta);
    }
    /**
     * ä¸Šä¼ æ–‡ä»¶
     *
     * @param bucketName äº‘端存放bucket名称
     * @param key        å°†è¦ä¸Šä¼ çš„æ–‡ä»¶åç§°
     * @param mime       è¶…文本标记语言文本 .html,.html text/html æ™®é€šæ–‡æœ¬ .txt text/plain RTF文本
     *                   .rtf application/rtf GIF图形 .gif image/gif JPEG图形 .ipeg,.jpg
     *                   image/jpeg au声音文件 .au audio/basic MIDI音乐文件 mid,.midi
     *                   audio/midi,audio/x-midi RealAudio音乐文件 .ra, .ram
     *                   audio/x-pn-realaudio MPEG文件 .mpg,.mpeg video/mpeg AVI文件 .avi
     *                   video/x-msvideo GZIP文件 .gz application/x-gzip TAR文件 .tar
     *                   application/x-tar
     * @throws OSSException
     * @throws ClientException
     * @throws IOException
     */
    public boolean uploadObject(MultipartFile file, String bucketName,
                                String key, String mime) throws OSSException, ClientException,
            IOException {
        if (file != null) {
            // åˆ¤æ–­æ˜¯å¦å­˜åœ¨ï¼Œä¸å­˜åœ¨åˆ›å»º
            isExistBucket(bucketName);
            ObjectMetadata objectMeta = new ObjectMetadata();
            objectMeta.setContentLength(file.getSize());
            // å¯ä»¥åœ¨metadata中标记文件类型
            if (StringUtils.isNotBlank(mime)) {
                objectMeta.setContentType(mime);
            }
            PutObjectRequest putObjectRequest = new PutObjectRequest(
                    bucketName, key, file.getInputStream());
            // ä¸Šä¼ å›žè°ƒå‚æ•°
            /*
             * Callback callback = new Callback();
             * callback.setCallbackUrl("http://www.doumee.com");
             * callback.setCallbackHost("oss-cn-hangzhou.aliyuncs.com");
             * callback.setCallbackBody(
             * "{\\\"mimeType\\\":${mimeType},\\\"size\\\":${size}}"); //
             * callback.setCallbackBodyType(CallbackBodyType.JSON);
             * callback.addCallbackVar("x:var1", "value1");
             * callback.addCallbackVar("x:var2", "value2");
             * putObjectRequest.setCallback(callback);
             */
            try {
                PutObjectResult putObjectResult = client
                        .putObject(putObjectRequest);
                return true;
            } catch (Exception e) {
                // TODO: handle exception
                System.err.println(e.getMessage());
            }
            /*
             * // è¯»å–上传回调返回的消息内容 byte[] buffer = new byte[1024];
             * putObjectResult.getCallbackResponseBody().read(buffer);
             *
             * // ä¸€å®šè¦close,否则会造成连接资源泄漏
             * putObjectResult.getCallbackResponseBody().close();
             */
            file.getInputStream().close();
            client.shutdown();
        }
        return false;
    }
    /**
     * åˆ†å—上传文件
     *
     * @param bucketName
     * @param key
     * @param filename
     * @param mime
     * @throws IOException
     */
    public String partUploadObject(String bucketName, String key,
                                   String filename, String mime) throws IOException {
        // å¼€å§‹Multipart Upload
        InitiateMultipartUploadRequest initiateMultipartUploadRequest = new InitiateMultipartUploadRequest(
                bucketName, key);
        InitiateMultipartUploadResult initiateMultipartUploadResult = client
                .initiateMultipartUpload(initiateMultipartUploadRequest);
        // è®¾ç½®æ¯å—为 5M
        final int partSize = 1024 * 1024 * 5;
        File partFile = new File(filename);
        // è®¡ç®—分块数目
        int partCount = (int) (partFile.length() / partSize);
        if (partFile.length() % partSize != 0) {
            partCount++;
        }
        // æ–°å»ºä¸€ä¸ªList保存每个分块上传后的ETag和PartNumber
        List<PartETag> partETags = new ArrayList<PartETag>();
        for (int i = 0; i < partCount; i++) {
            // èŽ·å–æ–‡ä»¶æµ
            FileInputStream fis = new FileInputStream(partFile);
            // è·³åˆ°æ¯ä¸ªåˆ†å—的开头
            long skipBytes = partSize * i;
            fis.skip(skipBytes);
            // è®¡ç®—每个分块的大小
            long size = partSize < partFile.length() - skipBytes ? partSize
                    : partFile.length() - skipBytes;
            // åˆ›å»ºUploadPartRequest,上传分块
            UploadPartRequest uploadPartRequest = new UploadPartRequest();
            uploadPartRequest.setBucketName(bucketName);
            uploadPartRequest.setKey(key);
            uploadPartRequest.setUploadId(initiateMultipartUploadResult
                    .getUploadId());
            uploadPartRequest.setInputStream(fis);
            uploadPartRequest.setPartSize(size);
            uploadPartRequest.setPartNumber(i + 1);
            UploadPartResult uploadPartResult = client
                    .uploadPart(uploadPartRequest);
            // å°†è¿”回的PartETag保存到List中。
            partETags.add(uploadPartResult.getPartETag());
            // å…³é—­æ–‡ä»¶
            fis.close();
        }
        CompleteMultipartUploadRequest completeMultipartUploadRequest = new CompleteMultipartUploadRequest(
                bucketName, key, initiateMultipartUploadResult.getUploadId(),
                partETags);
        // å®Œæˆåˆ†å—上传
        CompleteMultipartUploadResult completeMultipartUploadResult = client
                .completeMultipartUpload(completeMultipartUploadRequest);
        // æ ¡éªŒMD5
        if (StringUtils.equals(FileDigest.getFileMD5(new File(filename)),
                completeMultipartUploadResult.getETag())) {
            // å¦‚果一致
            return "上传成功";
        }
        return "上传失败";
    }
    /**
     * åˆ¤æ–­æ˜¯å¦å­˜åœ¨bucket,如果不存在创建
     */
    @SuppressWarnings("deprecation")
    public void isExistBucket(String bucketName) {
        // èŽ·å–Bucket的存在信息
        boolean exists = client.doesBucketExist(bucketName);
        // è¾“出结果
        if (!exists) {
            // ä¸å­˜åœ¨åˆ›å»ºå®ƒ
            client.createBucket(bucketName);
            // ä¿®æ”¹æƒé™
            client.setBucketAcl(bucketName, CannedAccessControlList.PublicRead);
        }
        // åˆ—举bucket
        // List<Bucket> buckets = client.listBuckets();
        // for (Bucket bucket : buckets) {
        // System.out.println(" - " + bucket.getName());
        // }
    }
    /**
     * åˆ é™¤bucket
     *
     * @param bucketName
     * @return
     */
    @SuppressWarnings("deprecation")
    public boolean deleteBucket(String bucketName) {
        // åˆ¤æ–­æœ‰æ²¡æœ‰
        if (client.doesBucketExist(bucketName)) {
            // åˆ¤æ–­bucket是否为空
            ObjectListing listObjects = client.listObjects(bucketName);
            // éåŽ†æ‰€æœ‰Object
            for (OSSObjectSummary objectSummary : listObjects
                    .getObjectSummaries()) {
                // åˆ é™¤object
                client.deleteObject(bucketName, objectSummary.getKey());
            }
            // åˆ é™¤Bucket
            client.deleteBucket(bucketName);
        }
        return true;
    }
    /**
     * é€’归列出目录下所有文件
     *
     * @param bucketName
     * @return
     */
    public long getAllBuckets(String bucketName, String prefix) {
        long totalSize = 0;
        // æž„造ListObjectsRequest请求
        ListObjectsRequest listObjectsRequest = new ListObjectsRequest(
                bucketName);
        listObjectsRequest.setPrefix(prefix);
        listObjectsRequest.withMaxKeys(1000);
        // é€’归列出fun目录下的所有文件
        ObjectListing listing = null;
        String nextMarker = null;
        do {
            listObjectsRequest.withMarker(nextMarker);
            listing = client.listObjects(listObjectsRequest);
            for (OSSObjectSummary objectSummary : listing.getObjectSummaries()) {
                totalSize += objectSummary.getSize();
                System.out.println(objectSummary.getKey() + ":"
                        + objectSummary.getSize());
            }
            nextMarker = listing.getNextMarker();
        } while (listing.isTruncated());
        // éåŽ†æ‰€æœ‰Object
        System.out.println("Objects:");
        return totalSize;
    }
    /**
     * ä¸‹è½½æ–‡ä»¶
     *
     * @param bucketName äº‘端存放bucket名称
     * @param key        äº‘端已存在文件
     * @param filename   æœ¬åœ°å¾…写入文件
     * @throws OSSException
     * @throws ClientException
     * @throws IOException
     */
    public String downloadFile(String bucketName, String key, String filename)
            throws OSSException, ClientException, IOException {
        // é¦–先检查是否存在目录
        if (StringUtils.isBlank(filename)) {
            // å¾…写入文件为空
            return "ERROR_FILENAME_IS_NULL";
        }
        File file = new File(filename);
        if (!file.exists()) {
            file.createNewFile();
        }
        client.getObject(new GetObjectRequest(bucketName, key), file);
        return filename;
    }
    public static void main(String[] args) throws OSSException,
            ClientException, IOException {
        ALiYunUtil aLiYunUtil = new ALiYunUtil("", "uc4nnpsqep1i9fijqr37nokh",
                "/rp41xCx/XdGEVCptdH6v7xpc9w=");
        // aLiYunUtil.uploadObject("pongto", "work/li2.txt", "D://哈.txt",
        // ".html,.html text/html");D://装机软件/办公学习
        // aLiYunUtil.partUploadObject("pongto", "work/ps.exe",
        // "D://装机软件/办公学习/Adobe_Illustrator_CS6_XiaZaiBa.exe",
        // ".html,.html text/html");
        // aLiYunUtil.deleteBucket("pongto");
    }
    /**
     * ä¸Šä¼ ç½‘络文件
     *
     * @param bucketName äº‘端存放bucket名称
     * @param key        é‡æ–°å‘½åçš„æ–‡ä»¶å
     *                   å°†è¦ä¸Šä¼ çš„æ–‡ä»¶åç§°
     * @param mime       è¶…文本标记语言文本 .html,.html text/html æ™®é€šæ–‡æœ¬ .txt text/plain RTF文本
     *                   .rtf application/rtf GIF图形 .gif image/gif JPEG图形 .ipeg,.jpg
     *                   image/jpeg au声音文件 .au audio/basic MIDI音乐文件 mid,.midi
     *                   audio/midi,audio/x-midi RealAudio音乐文件 .ra, .ram
     *                   audio/x-pn-realaudio MPEG文件 .mpg,.mpeg video/mpeg AVI文件 .avi
     *                   video/x-msvideo GZIP文件 .gz application/x-gzip TAR文件 .tar
     *                   application/x-tar
     * @throws OSSException
     * @throws ClientException
     * @throws IOException
     */
    public boolean uploadOnlineObject(String url, String bucketName, String key,
                                      String mime) throws OSSException, ClientException, IOException {
        InputStream inputStream = new URL(url).openStream();
        if (inputStream != null) {
            // åˆ¤æ–­æ˜¯å¦å­˜åœ¨ï¼Œä¸å­˜åœ¨åˆ›å»º
            isExistBucket(bucketName);
            ObjectMetadata objectMeta = new ObjectMetadata();
            objectMeta.setContentLength(inputStream.available());
            // å¯ä»¥åœ¨metadata中标记文件类型
            if (StringUtils.isNotBlank(mime)) {
                objectMeta.setContentType(mime);
            }
            PutObjectRequest putObjectRequest = new PutObjectRequest(bucketName, key,
                    inputStream);
            // ä¸Šä¼ å›žè°ƒå‚æ•°
            /*    Callback callback = new Callback();
            callback.setCallbackUrl("http://www.doumee.com");
            callback.setCallbackHost("oss-cn-hangzhou.aliyuncs.com");
            callback.setCallbackBody("{\\\"mimeType\\\":${mimeType},\\\"size\\\":${size}}");
//            callback.setCallbackBodyType(CallbackBodyType.JSON);
            callback.addCallbackVar("x:var1", "value1");
            callback.addCallbackVar("x:var2", "value2");
            putObjectRequest.setCallback(callback);*/
            try {
                PutObjectResult putObjectResult = client.putObject(putObjectRequest);
                return true;
            } catch (Exception e) {
                // TODO: handle exception
            }
            /*// è¯»å–上传回调返回的消息内容
            byte[] buffer = new byte[1024];
            putObjectResult.getCallbackResponseBody().read(buffer);
            // ä¸€å®šè¦close,否则会造成连接资源泄漏
            putObjectResult.getCallbackResponseBody().close();*/
            inputStream.close();
            client.shutdown();
        }
        return false;
    }
    public boolean uploadOnlineObject(InputStream inputStream, String bucketName, String key,
                                      String mime) throws OSSException, ClientException, IOException {
        if (inputStream != null) {
            // åˆ¤æ–­æ˜¯å¦å­˜åœ¨ï¼Œä¸å­˜åœ¨åˆ›å»º
            isExistBucket(bucketName);
            ObjectMetadata objectMeta = new ObjectMetadata();
            objectMeta.setContentLength(inputStream.available());
            // å¯ä»¥åœ¨metadata中标记文件类型
            if (StringUtils.isNotBlank(mime)) {
                objectMeta.setContentType(mime);
            }
            PutObjectRequest putObjectRequest = new PutObjectRequest(bucketName, key,
                    inputStream);
            // ä¸Šä¼ å›žè°ƒå‚æ•°
            /*    Callback callback = new Callback();
            callback.setCallbackUrl("http://www.doumee.com");
            callback.setCallbackHost("oss-cn-hangzhou.aliyuncs.com");
            callback.setCallbackBody("{\\\"mimeType\\\":${mimeType},\\\"size\\\":${size}}");
//            callback.setCallbackBodyType(CallbackBodyType.JSON);
            callback.addCallbackVar("x:var1", "value1");
            callback.addCallbackVar("x:var2", "value2");
            putObjectRequest.setCallback(callback);*/
            try {
                PutObjectResult putObjectResult = client.putObject(putObjectRequest);
                return true;
            } catch (Exception e) {
                // TODO: handle exception
            }
            /*// è¯»å–上传回调返回的消息内容
            byte[] buffer = new byte[1024];
            putObjectResult.getCallbackResponseBody().read(buffer);
            // ä¸€å®šè¦close,否则会造成连接资源泄漏
            putObjectResult.getCallbackResponseBody().close();*/
            inputStream.close();
            client.shutdown();
        }
        return false;
    }
}
server/services/src/main/java/com/doumee/dao/business/AreasMapper.java
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,12 @@
package com.doumee.dao.business;
import com.doumee.dao.business.model.Areas;
import com.github.yulichang.base.MPJBaseMapper;
/**
 * @author æ±Ÿè¹„蹄
 * @date 2023/02/15 08:55
 */
public interface AreasMapper extends MPJBaseMapper<Areas> {
}
server/services/src/main/java/com/doumee/dao/business/BannerMapper.java
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,13 @@
package com.doumee.dao.business;
import com.doumee.dao.business.model.Banner;
import com.github.yulichang.base.MPJBaseMapper;
/**
 * è½®æ’­å›¾Mapper
 * @author rk
 * @date 2026/04/08
 */
public interface BannerMapper extends MPJBaseMapper<Banner> {
}
server/services/src/main/java/com/doumee/dao/business/DriverInfoMapper.java
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,13 @@
package com.doumee.dao.business;
import com.doumee.dao.business.model.DriverInfo;
import com.github.yulichang.base.MPJBaseMapper;
/**
 * å¸æœºæ³¨å†Œä¿¡æ¯Mapper
 * @author rk
 * @date 2026/04/08
 */
public interface DriverInfoMapper extends MPJBaseMapper<DriverInfo> {
}
server/services/src/main/java/com/doumee/dao/business/PricingRuleMapper.java
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,13 @@
package com.doumee.dao.business;
import com.doumee.dao.business.model.PricingRule;
import com.github.yulichang.base.MPJBaseMapper;
/**
 * è®¡ä»·è§„则配置Mapper
 * @author rk
 * @date 2026/04/08
 */
public interface PricingRuleMapper extends MPJBaseMapper<PricingRule> {
}
server/services/src/main/java/com/doumee/dao/business/ShopInfoMapper.java
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,13 @@
package com.doumee.dao.business;
import com.doumee.dao.business.model.ShopInfo;
import com.github.yulichang.base.MPJBaseMapper;
/**
 * é—¨åº—信息Mapper
 * @author rk
 * @date 2026/04/08
 */
public interface ShopInfoMapper extends MPJBaseMapper<ShopInfo> {
}
server/services/src/main/java/com/doumee/dao/business/SmsrecordMapper.java
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,13 @@
package com.doumee.dao.business;
import com.doumee.dao.business.model.Smsrecord;
import com.github.yulichang.base.MPJBaseMapper;
/**
 * çŸ­ä¿¡éªŒè¯ç Mapper
 * @author rk
 * @date 2026/04/08
 */
public interface SmsrecordMapper extends MPJBaseMapper<Smsrecord> {
}
server/services/src/main/java/com/doumee/dao/business/model/Areas.java
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,134 @@
package com.doumee.dao.business.model;
import com.baomidou.mybatisplus.annotation.IdType;
import com.baomidou.mybatisplus.annotation.TableField;
import com.baomidou.mybatisplus.annotation.TableId;
import com.baomidou.mybatisplus.annotation.TableName;
import com.doumee.core.annotation.excel.ExcelColumn;
import io.swagger.annotations.ApiModel;
import io.swagger.annotations.ApiModelProperty;
import lombok.Data;
import java.util.Date;
import java.util.List;
/**
 * çœå¸‚区信息表
 * @author æ±Ÿè¹„蹄
 * @date 2023/02/15 08:55
 */
@Data
@ApiModel("省市区信息表")
@TableName("`areas`")
public class Areas implements Cloneable,Comparable<Object>{
    @ApiModelProperty(value = "主键", example = "1")
    @ExcelColumn(name="主键")
    @TableId(value = "id",type = IdType.AUTO)
    private Integer id;
    @ApiModelProperty(value = "创建人编码", example = "1")
    @ExcelColumn(name="创建人编码")
    private Integer creator;
    @ApiModelProperty(value = "创建时间")
    @ExcelColumn(name="创建时间")
    private Date createDate;
    @ApiModelProperty(value = "更新人编码", example = "1")
    @ExcelColumn(name="更新人编码")
    private Integer editor;
    @ApiModelProperty(value = "更新时间")
    @ExcelColumn(name="更新时间")
    private Date editDate;
    @ApiModelProperty(value = "是否删除0否 1是", example = "1")
    @ExcelColumn(name="是否删除0否 1是")
    private Integer isdeleted;
    @ApiModelProperty(value = "名称")
    @ExcelColumn(name="名称")
    private String name;
    @ApiModelProperty(value = "备注")
    @ExcelColumn(name="备注")
    private String info;
    @ApiModelProperty(value = "行政区代码")
    @ExcelColumn(name="行政区代码")
    private String code;
    @ApiModelProperty(value = "父级编码(关联areas表)", example = "1")
    @ExcelColumn(name="父级编码(关联areas表)")
    private Integer parentId;
    @ApiModelProperty(value = "类型 0省 1市 2区县", example = "1")
    @ExcelColumn(name="类型 0省 1市 2区县")
    private Integer type;
    @ApiModelProperty(value = "排序码", example = "1")
    @ExcelColumn(name="排序码")
    private Integer sortnum;
    @ApiModelProperty(value = "是否开启使用:0=否;1=是;", example = "1")
    @ExcelColumn(name="是否开启使用:0=否;1=是;")
    private Integer status;
    @TableField(exist = false)
    private List<Areas> childList;
    @TableField(exist = false)
    private Integer provinceId;
    @TableField(exist = false)
    private String provinceName;
    @TableField(exist = false)
    private Integer cityId;
    @TableField(exist = false)
    private String cityName;
    @TableField(exist = false)
     private String fullspell;//全拼音;
    @TableField(exist = false)
     private String firstSpell;//首字母;
    //实现Cloneable的clone方法,将clone定义为public
    public Areas clone()   {
        try {
            return (Areas) super.clone();
        } catch (CloneNotSupportedException e) {
            e.printStackTrace();
        }
        return null;
    }
    @Override
    public String toString() {
        return "Areas{" +
            "id=" + id +
            ", creator=" + creator +
            ", createDate=" + createDate +
            ", editor=" + editor +
            ", editDate=" + editDate +
            ", isdeleted=" + isdeleted +
            ", name='" + name + '\'' +
            ", info='" + info + '\'' +
            ", code='" + code + '\'' +
            ", parentId=" + parentId +
            ", type=" + type +
            '}';
    }
    @Override
    public int compareTo(Object o) {
        if (this == o) {
            return 0;
        } else if (o != null && o instanceof Areas) {
            Areas u = (Areas) o;
            if (fullspell.compareTo(u.fullspell) < 0) {
                return -1;
            } else {
                return 1;
            }
        } else {
            return -1;
        }
    }
}
server/services/src/main/java/com/doumee/dao/business/model/Banner.java
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,74 @@
package com.doumee.dao.business.model;
import com.baomidou.mybatisplus.annotation.IdType;
import com.baomidou.mybatisplus.annotation.TableId;
import com.baomidou.mybatisplus.annotation.TableName;
import com.doumee.core.annotation.excel.ExcelColumn;
import com.fasterxml.jackson.annotation.JsonFormat;
import io.swagger.annotations.ApiModel;
import io.swagger.annotations.ApiModelProperty;
import lombok.Data;
import java.util.Date;
/**
 * è½®æ’­å›¾
 * @author rk
 * @date 2026/04/08
 */
@Data
@ApiModel("轮播图")
@TableName("`banner`")
public class Banner {
    @TableId(type = IdType.AUTO)
    @ApiModelProperty(value = "主键", example = "1")
    private Integer id;
    @ApiModelProperty(value = "是否已删除 0未删除 1已删除", example = "0")
    private Integer deleted;
    @ApiModelProperty(value = "创建人编码", example = "1")
    private Integer createUser;
    @ApiModelProperty(value = "创建时间")
    @ExcelColumn(name = "创建时间", index = 1, width = 16, dateFormat = "yyyy-MM-dd HH:mm:ss")
    private Date createTime;
    @ApiModelProperty(value = "更新人编码", example = "1")
    private Integer updateUser;
    @ApiModelProperty(value = "更新时间")
    @JsonFormat(pattern = "yyyy-MM-dd")
    private Date updateTime;
    @ApiModelProperty(value = "备注")
    private String remark;
    @ApiModelProperty(value = "活动主键")
    private Integer title;
    @ApiModelProperty(value = "排序号")
    private Integer sortnum;
    @ApiModelProperty(value = "状态 0正常 1停用", example = "0")
    @ExcelColumn(name = "状态", index = 2, width = 10, valueMapping = "0=正常;1=停用;")
    private Integer status;
    @ApiModelProperty(value = "列表图")
    private String imgurl;
    @ApiModelProperty(value = "跳转类型 0富文本 1外链", example = "0")
    @ExcelColumn(name = "跳转类型", index = 3, width = 10, valueMapping = "0=富文本;1=外链;")
    private Integer type;
    @ApiModelProperty(value = "位置 0首页 1店铺首页", example = "0")
    @ExcelColumn(name = "位置", index = 4, width = 10, valueMapping = "0=首页;1=店铺首页;")
    private Integer position;
    @ApiModelProperty(value = "店铺主键")
    private Integer shopId;
    @ApiModelProperty(value = "内容")
    private String content;
}
server/services/src/main/java/com/doumee/dao/business/model/Category.java
@@ -63,30 +63,39 @@
    @ExcelColumn(name="单位名称")
    private String name;
    @ApiModelProperty(value = "类型:0=品种配置;1=车辆类型配置;2=餐标配置;3=手续费配置;", example = "1")
    @ExcelColumn(name="类型:0=品种配置;1=车辆类型配置;2=餐标配置;3=手续费配置;")
    @ApiModelProperty(value = "类型:1=车辆类型;2=物品分类;3=物品等级;4=物品尺寸;", example = "1")
    @ExcelColumn(name="类型:1=车辆类型;2=物品分类;3=物品等级;4=物品尺寸;")
    private Integer type;
    @ApiModelProperty(value = "内容(车辆规格、餐标、手续费比例)")
    @ExcelColumn(name="内容(车辆规格、餐标、手续费比例)")
    @ApiModelProperty(value = "内容 ï¼ˆtype=1:通行方式; type=2:司机评级);")
    @ExcelColumn(name="内容")
    private String detail;
    @ApiModelProperty(value = "图标(车辆类型使用)")
    @ExcelColumn(name="图标(车辆类型使用)")
    private String icon;
    @ApiModelProperty(value = "排序码(升序)")
    @ExcelColumn(name="排序码(升序)")
    private Integer sortnum;
    @ApiModelProperty(value = "是否固定车辆(车辆类型使用):0=否;1=是;", example = "1")
    @ExcelColumn(name="是否固定车辆(车辆类型使用):0=否;1=是;")
    private Integer isFixed;
    @ApiModelProperty(value = "附属字段1 (type=1:是否需要上传驾驶证:0=不需要;1=需要;) ")
    @ExcelColumn(name="内容")
    private String otherField;
    @ApiModelProperty(value = "是否固定车辆", example = "1")
    @ExcelColumn(name="是否固定车辆")
    private Integer isFixed; // å¼ƒç”¨
    @ApiModelProperty(value = "是否固定车辆(车辆类型使用):0=否;1=是;", example = "1")
    @TableField(exist = false)
    private String updateUserName;
    @ApiModelProperty(value = "餐标等配置项集合", example = "1")
    @TableField(exist = false)
    private JSONArray detailList;
    @ApiModelProperty(value = "图标全路径")
    @TableField(exist = false)
    private String iconFull;
server/services/src/main/java/com/doumee/dao/business/model/DriverInfo.java
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,145 @@
package com.doumee.dao.business.model;
import com.baomidou.mybatisplus.annotation.IdType;
import com.baomidou.mybatisplus.annotation.TableField;
import com.baomidou.mybatisplus.annotation.TableId;
import com.baomidou.mybatisplus.annotation.TableName;
import com.doumee.core.annotation.excel.ExcelColumn;
import com.fasterxml.jackson.annotation.JsonFormat;
import io.swagger.annotations.ApiModel;
import io.swagger.annotations.ApiModelProperty;
import lombok.Data;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;
/**
 * å¸æœºæ³¨å†Œä¿¡æ¯
 * @author rk
 * @date 2026/04/08
 */
@Data
@ApiModel("司机注册信息")
@TableName("`driver_info`")
public class DriverInfo {
    @TableId(type = IdType.AUTO)
    @ApiModelProperty(value = "主键", example = "1")
    private Integer id;
    @ApiModelProperty(value = "是否已删除 0未删除 1已删除", example = "0")
    private Integer deleted;
    @ApiModelProperty(value = "创建人编码", example = "1")
    private Integer createUser;
    @ApiModelProperty(value = "创建时间")
    @ExcelColumn(name = "创建时间", index = 1, width = 16, dateFormat = "yyyy-MM-dd HH:mm:ss")
    private Date createTime;
    @ApiModelProperty(value = "更新人编码", example = "1")
    private Integer updateUser;
    @ApiModelProperty(value = "更新时间")
    @JsonFormat(pattern = "yyyy-MM-dd")
    private Date updateTime;
    @ApiModelProperty(value = "备注")
    private String remark;
    @ApiModelProperty(value = "姓名")
    @ExcelColumn(name = "姓名", index = 2, width = 10)
    private String name;
    @ApiModelProperty(value = "手机号")
    @ExcelColumn(name = "手机号", index = 3, width = 12)
    private String telephone;
    @ApiModelProperty(value = "身份证号码")
    @ExcelColumn(name = "身份证号码", index = 4, width = 18)
    private String idcard;
    @ApiModelProperty(value = "婚姻状态:0=未婚;1=已婚;2=离异;3=丧偶", example = "0")
    @ExcelColumn(name = "婚姻状态", index = 5, width = 10, valueMapping = "0=未婚;1=已婚;2=离异;3=丧偶;")
    private Integer maritalStatus;
    @ApiModelProperty(value = "区划主键", example = "1")
    private Integer areaId;
    @ApiModelProperty(value = "居住地址")
    private String livePlace;
    @ApiModelProperty(value = "头像图片")
    private String imgurl;
    @ApiModelProperty(value = "车辆类型", example = "1")
    private Integer carType;
    @ApiModelProperty(value = "车牌号")
    @ExcelColumn(name = "车牌号", index = 6, width = 10)
    private String carCode;
    @ApiModelProperty(value = "车辆颜色")
    private String carColor;
    @ApiModelProperty(value = "驾驶证有效期开始时间")
    @JsonFormat(pattern = "yyyy-MM-dd")
    private Date cardStartDate;
    @ApiModelProperty(value = "驾驶证有效期结束时间")
    @JsonFormat(pattern = "yyyy-MM-dd")
    private Date cardEndDate;
    @ApiModelProperty(value = "司机状态:0=注册;1=待审批;2=审批通过;3=审批驳回", example = "0")
    @ExcelColumn(name = "状态", index = 7, width = 10, valueMapping = "0=注册;1=待审批;2=审批通过;3=审批驳回;")
    private Integer status;
    @ApiModelProperty(value = "OPENID(APP)")
    private String openid;
    @ApiModelProperty(value = "UNIONID")
    private String unionid;
    @ApiModelProperty(value = "审批时间")
    @JsonFormat(pattern = "yyyy-MM-dd")
    private Date auditTime;
    @ApiModelProperty(value = "审批人", example = "1")
    private Integer auditUser;
    @ApiModelProperty(value = "审批备注")
    private String auditRemark;
    @ApiModelProperty(value = "会员主键", example = "1")
    private Integer memberId;
    @ApiModelProperty(value = "身份证正面照")
    private String idcardImg;
    @ApiModelProperty(value = "身份证反面照")
    private String idcardImgBack;
    @ApiModelProperty(value = "车辆照片列表")
    @TableField(exist = false)
    private List<Multifile> carImgList = new ArrayList<>();
    @ApiModelProperty(value = "驾驶证照片列表")
    @TableField(exist = false)
    private List<Multifile> licenseImgList = new ArrayList<>();
    @ApiModelProperty(value = "其他资料照片列表")
    @TableField(exist = false)
    private List<Multifile> otherImgList = new ArrayList<>();
    @ApiModelProperty(value = "是否需要上传驾驶证:0=不需要;1=需要")
    @TableField(exist = false)
    private Integer needLicense;
    @ApiModelProperty(value = "车辆类型名称")
    @TableField(exist = false)
    private String carTypeName;
}
server/services/src/main/java/com/doumee/dao/business/model/Member.java
@@ -67,13 +67,13 @@
    @ExcelColumn(name="真实姓名",index = 4,width = 10)
    private String name;
    @ApiModelProperty(value = "用工身份:0=未申请;1=申请中;2=已通过;3=未通过;", example = "1")
    @ApiModelProperty(value = "用工身份:0=未申请;1=申请中;2=已通过;3=未通过;", example = "1") //弃用
    private Integer workerIdentity;
    @ApiModelProperty(value = "货运身份:0=未申请;1=申请中;2=已通过;3=未通过;", example = "1")
    @ApiModelProperty(value = "货运身份:0=未申请;1=申请中;2=已通过;3=未通过;", example = "1") //弃用
    private Integer driverIdentity;
    @ApiModelProperty(value = "供餐身份:0=未申请;1=申请中;2=已通过;3=未通过;", example = "1")
    @ApiModelProperty(value = "供餐身份:0=未申请;1=申请中;2=已通过;3=未通过;", example = "1") //弃用
    private Integer chefIdentity;
    @ApiModelProperty(value = "当前余额(单位:分)", example = "1")
@@ -82,7 +82,7 @@
    @ApiModelProperty(value = "历史总金额(单位:分)", example = "1")
    private Long totalAmount;
    @ApiModelProperty(value = "状态", example = "1")
    @ApiModelProperty(value = "状态 0=正常;1=停用;2=已注销", example = "1")
    private Integer status;
    @ApiModelProperty(value = "最后登录时间")
@@ -134,6 +134,19 @@
    @ApiModelProperty(value = "当前使用身份:0=用工发布方;1=用工接单方;", example = "1")
    private Integer useIdentity;
    @ApiModelProperty(value = "用户类型:0=会员用户;1=司机;2=店铺人员;(司机与店铺均和会员表使用同主键值)", example = "1")
    private Integer userType;
    @ApiModelProperty(value = "业务状态:0=未认证;1=认证通过;2=认证未通过 ï¼›3=已支付押金", example = "1")
    private Integer businessStatus;
    @ApiModelProperty(value = "登录密码", example = "1")
    private String password;
    @ApiModelProperty(value = "密码盐", example = "1")
    private String salt;
    @ApiModelProperty(value = "我的 - æ•°æ®ä¿¡æ¯", example = "1")
    @TableField(exist = false)
    private UserCenterVO userCenterVO;
server/services/src/main/java/com/doumee/dao/business/model/Multifile.java
@@ -53,9 +53,8 @@
    @ApiModelProperty(value = "类型0图片 1视频 2其他", example = "1")
    private Integer type;
//    @ApiModelProperty(value = "关联对象类型 0SHE上报 1跌绊滑上报 2跌绊滑处理 3跌绊滑分配物业主管 4跌绊滑分配处理人 5DCA风险上报 6DCA风险处理 7DCA工单图片", example = "1")
//    @ExcelExportColumn(name="关联对象类型 0SHE上报 1跌绊滑上报 2跌绊滑处理 3跌绊滑分配物业主管 4跌绊滑分配处理人 5DCA风险上报 6DCA风险处理 7DCA工单图片")
    @ApiModelProperty(value = "关联对象类型 0身份申请资料 1订单附件", example = "1")
    @ApiModelProperty(value = "关联对象类型:0=门店其他材料;1=门店内部照片;2=订单寄存图片;3=订单取件图片;4=司机取件图片;5=司机完成图片;6=司机实名认证车辆照片;7=司机实名认证驾驶证照片;8=司机实名认证其他图片;" +
            "9=门店门头照;10=社保缴纳证明;11=有效劳动合同;", example = "1")
    private Integer objType;
    @ApiModelProperty(value = "文件地址")
server/services/src/main/java/com/doumee/dao/business/model/PricingRule.java
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,70 @@
package com.doumee.dao.business.model;
import com.baomidou.mybatisplus.annotation.IdType;
import com.baomidou.mybatisplus.annotation.TableId;
import com.baomidou.mybatisplus.annotation.TableName;
import com.doumee.core.annotation.excel.ExcelColumn;
import com.fasterxml.jackson.annotation.JsonFormat;
import io.swagger.annotations.ApiModel;
import io.swagger.annotations.ApiModelProperty;
import lombok.Data;
import java.util.Date;
/**
 * è®¡ä»·è§„则配置
 * @author rk
 * @date 2026/04/08
 */
@Data
@ApiModel("计价规则配置")
@TableName("`pricing_rule`")
public class PricingRule {
    @TableId(type = IdType.AUTO)
    @ApiModelProperty(value = "主键", example = "1")
    private Integer id;
    @ApiModelProperty(value = "是否已删除 0未删除 1已删除", example = "0")
    private Integer deleted;
    @ApiModelProperty(value = "创建人编码", example = "1")
    private Integer createUser;
    @ApiModelProperty(value = "创建时间")
    @ExcelColumn(name = "创建时间", index = 1, width = 16, dateFormat = "yyyy-MM-dd HH:mm:ss")
    private Date createTime;
    @ApiModelProperty(value = "更新人编码", example = "1")
    private Integer updateUser;
    @ApiModelProperty(value = "更新时间")
    @JsonFormat(pattern = "yyyy-MM-dd")
    private Date updateTime;
    @ApiModelProperty(value = "备注")
    private String remark;
    @ApiModelProperty(value = "城市主键(area_id)", example = "1")
    private Integer cityId;
    @ApiModelProperty(value = "类型:0=就地存取规则;1=异地存取规则;2=预计失效;3=门店注册押金;4=分成比例", example = "0")
    @ExcelColumn(name = "类型", index = 2, width = 10, valueMapping = "0=就地存取规则;1=异地存取规则;2=预计失效;3=门店注册押金;4=分成比例;")
    private Integer type;
    @ApiModelProperty(value = "参数1:type ï¼ˆ0/1)=  å…³è” ç‰©å“å°ºå¯¸ï¼ˆcategory type =4);type ï¼ˆ2)= é…é€é‡Œç¨‹ ï¼› type (3)  = ä¼ä¸šç±»åž‹ï¼ˆ0=企业;1=个人);type (4) = ç±»åž‹ï¼ˆ0-4 ä¼ä¸šå¯„/个人寄/企业取/个人取/配送员)")
    private String fieldA;
    @ApiModelProperty(value = "参数2:type ï¼ˆ0)=  æ”¶è´¹å•ä»· ;type ï¼ˆ1)= é…é€èµ·æ­¥é‡Œç¨‹å…¬é‡Œæ•° ï¼›type ï¼ˆ2)= é…é€æ—¶é•¿ ï¼› type (3)  = æŠ¼é‡‘ï¼›type (4) = åˆ†æˆæ¯”例")
    private String fieldB;
    @ApiModelProperty(value = "参数3:type ï¼ˆ1)= é…é€èµ·æ­¥é‡Œç¨‹æ¯å…¬é‡Œå•ä»· ï¼›")
    private String fieldC;
    @ApiModelProperty(value = "参数4:type=1  è¶…出首单里程公里数")
    private String fieldD;
    @ApiModelProperty(value = "参数5:type=1  è¶…出首单里程每公里 å•ä»·")
    private String fieldE;
}
server/services/src/main/java/com/doumee/dao/business/model/ShopInfo.java
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,124 @@
package com.doumee.dao.business.model;
import com.baomidou.mybatisplus.annotation.IdType;
import com.baomidou.mybatisplus.annotation.TableId;
import com.baomidou.mybatisplus.annotation.TableName;
import com.doumee.core.annotation.excel.ExcelColumn;
import com.fasterxml.jackson.annotation.JsonFormat;
import io.swagger.annotations.ApiModel;
import io.swagger.annotations.ApiModelProperty;
import lombok.Data;
import java.util.Date;
/**
 * é—¨åº—信息
 * @author rk
 * @date 2026/04/08
 */
@Data
@ApiModel("门店信息")
@TableName("`shop_info`")
public class ShopInfo {
    @TableId(type = IdType.AUTO)
    @ApiModelProperty(value = "主键", example = "1")
    private Integer id;
    @ApiModelProperty(value = "是否已删除 0未删除 1已删除", example = "0")
    private Integer deleted;
    @ApiModelProperty(value = "创建人编码", example = "1")
    private Integer createUser;
    @ApiModelProperty(value = "创建时间")
    @ExcelColumn(name = "创建时间", index = 1, width = 16, dateFormat = "yyyy-MM-dd HH:mm:ss")
    private Date createTime;
    @ApiModelProperty(value = "更新人编码", example = "1")
    private Integer updateUser;
    @ApiModelProperty(value = "更新时间")
    @JsonFormat(pattern = "yyyy-MM-dd")
    private Date updateTime;
    @ApiModelProperty(value = "备注")
    private String remark;
    @ApiModelProperty(value = "企业类型:0=个人;1=企业", example = "0")
    @ExcelColumn(name = "企业类型", index = 2, width = 10, valueMapping = "0=个人;1=企业;")
    private Integer companyType;
    @ApiModelProperty(value = "名称/店铺名称")
    @ExcelColumn(name = "店铺名称", index = 3, width = 15)
    private String name;
    @ApiModelProperty(value = "注册手机号")
    @ExcelColumn(name = "注册手机号", index = 4, width = 12)
    private String telephone;
    @ApiModelProperty(value = "登录密码")
    private String password;
    @ApiModelProperty(value = "密码盐")
    private String salt;
    @ApiModelProperty(value = "联系人名称")
    @ExcelColumn(name = "联系人", index = 5, width = 10)
    private String linkName;
    @ApiModelProperty(value = "联系人电话")
    @ExcelColumn(name = "联系电话", index = 6, width = 12)
    private String linkPhone;
    @ApiModelProperty(value = "联系人身份证号码")
    private String idcard;
    @ApiModelProperty(value = "区划主键", example = "1")
    private Integer areaId;
    @ApiModelProperty(value = "定位经度", example = "116.404")
    private Double longitude;
    @ApiModelProperty(value = "定位纬度", example = "39.915")
    private Double latitude;
    @ApiModelProperty(value = "详细地址")
    private String address;
    @ApiModelProperty(value = "法人姓名(企业类型使用)")
    private String legalPersonName;
    @ApiModelProperty(value = "法人电话(企业类型使用)")
    private String legalPersonPhone;
    @ApiModelProperty(value = "法人身份证号码(企业类型使用)")
    private String legalPersonCard;
    @ApiModelProperty(value = "身份证正面照")
    private String idcardImg;
    @ApiModelProperty(value = "身份证反面照")
    private String idcardImgBack;
    @ApiModelProperty(value = "营业执照")
    private String businessImg;
    @ApiModelProperty(value = "状态:0=待审批;1=审批通过;2=审批未通过", example = "0")
    @ExcelColumn(name = "状态", index = 7, width = 10, valueMapping = "0=待审批;1=审批通过;2=审批未通过;")
    private Integer status;
    @ApiModelProperty(value = "审批时间")
    @JsonFormat(pattern = "yyyy-MM-dd")
    private Date auditTime;
    @ApiModelProperty(value = "审批人", example = "1")
    private Integer auditUserId;
    @ApiModelProperty(value = "审批备注")
    private String auditRemark;
    @ApiModelProperty(value = "OPENID")
    private String openid;
}
server/services/src/main/java/com/doumee/dao/business/model/Smsrecord.java
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,71 @@
package com.doumee.dao.business.model;
import com.baomidou.mybatisplus.annotation.IdType;
import com.baomidou.mybatisplus.annotation.TableId;
import com.baomidou.mybatisplus.annotation.TableName;
import com.doumee.core.annotation.excel.ExcelColumn;
import com.fasterxml.jackson.annotation.JsonFormat;
import io.swagger.annotations.ApiModel;
import io.swagger.annotations.ApiModelProperty;
import lombok.Data;
import java.util.Date;
/**
 * çŸ­ä¿¡éªŒè¯ç 
 * @author rk
 * @date 2026/04/08
 */
@Data
@ApiModel("短信验证码")
@TableName("`smsrecord`")
public class Smsrecord {
    @TableId(type = IdType.AUTO)
    @ApiModelProperty(value = "主键", example = "1")
    private Integer id;
    @ApiModelProperty(value = "是否已删除 0未删除 1已删除", example = "0")
    private Integer deleted;
    @ApiModelProperty(value = "创建人编码", example = "1")
    private Integer createUser;
    @ApiModelProperty(value = "创建时间")
    @ExcelColumn(name = "创建时间", index = 1, width = 16, dateFormat = "yyyy-MM-dd HH:mm:ss")
    private Date createTime;
    @ApiModelProperty(value = "更新人编码", example = "1")
    private Integer updateUser;
    @ApiModelProperty(value = "更新时间")
    @JsonFormat(pattern = "yyyy-MM-dd")
    private Date updateTime;
    @ApiModelProperty(value = "备注")
    private String remark;
    @ApiModelProperty(value = "手机号")
    @ExcelColumn(name = "手机号", index = 2, width = 12)
    private String phone;
    @ApiModelProperty(value = "短信内容")
    @ExcelColumn(name = "短信内容", index = 3, width = 20)
    private String content;
    @ApiModelProperty(value = "短信类型:0=验证码", example = "0")
    @ExcelColumn(name = "短信类型", index = 4, width = 10, valueMapping = "0=验证码;")
    private Integer type;
    @ApiModelProperty(value = "有效期")
    @JsonFormat(pattern = "yyyy-MM-dd")
    private Date validDate;
    @ApiModelProperty(value = "关键字(验证码等)")
    private String code;
    @ApiModelProperty(value = "状态 0未使用 1已使用 2已过期", example = "0")
    @ExcelColumn(name = "状态", index = 5, width = 10, valueMapping = "0=未使用;1=已使用;2=已过期;")
    private Integer status;
}
server/services/src/main/java/com/doumee/dao/dto/AreasDto.java
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,25 @@
package com.doumee.dao.dto;
import io.swagger.annotations.ApiModel;
import io.swagger.annotations.ApiModelProperty;
import lombok.Data;
import java.io.Serializable;
/**
 * @author Eva.Caesar Liu
 * @date 2023/02/14 11:14
 */
@Data
@ApiModel("省市区查询参数")
public class AreasDto implements Serializable {
    @ApiModelProperty(value = "名称" )
    private String name;
    @ApiModelProperty(value = "类型 0省 1市 2区县", example = "1")
    private Integer type;
    @ApiModelProperty(value = "是否包含子节点 0不包含 1包含", example = "1")
    private int flag;
    @ApiModelProperty(value = "父节点编码", example = "1")
    private Integer parentId;
}
server/services/src/main/java/com/doumee/dao/dto/AuditDTO.java
@@ -23,4 +23,7 @@
    @ApiModelProperty(value = "审批描述")
    private String auditRemark;
    @ApiModelProperty(value = "审批人编码(服务端填充)", hidden = true)
    private Integer auditUser;
}
server/services/src/main/java/com/doumee/dao/dto/DriverLoginRequest.java
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,27 @@
package com.doumee.dao.dto;
import io.swagger.annotations.ApiModel;
import io.swagger.annotations.ApiModelProperty;
import lombok.Data;
import javax.validation.constraints.NotEmpty;
import java.io.Serializable;
/**
 * å¸æœºç™»å½•请求类
 * @author rk
 * @date 2026/04/08
 */
@Data
@ApiModel("司机登录请求类")
public class DriverLoginRequest implements Serializable {
    @NotEmpty(message = "手机号不能为空")
    @ApiModelProperty(value = "手机号", required = true)
    private String telephone;
    @NotEmpty(message = "密码不能为空")
    @ApiModelProperty(value = "登录密码", required = true)
    private String password;
}
server/services/src/main/java/com/doumee/dao/dto/DriverRegisterRequest.java
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,27 @@
package com.doumee.dao.dto;
import io.swagger.annotations.ApiModel;
import io.swagger.annotations.ApiModelProperty;
import lombok.Data;
import javax.validation.constraints.NotEmpty;
import java.io.Serializable;
/**
 * å¸æœºéªŒè¯ç ç™»å½•请求类
 * @author rk
 * @date 2026/04/08
 */
@Data
@ApiModel("司机验证码登录请求类")
public class DriverRegisterRequest implements Serializable {
    @NotEmpty(message = "手机号不能为空")
    @ApiModelProperty(value = "手机号", required = true)
    private String telephone;
    @NotEmpty(message = "验证码不能为空")
    @ApiModelProperty(value = "验证码", required = true)
    private String code;
}
server/services/src/main/java/com/doumee/dao/dto/DriverVerifyRequest.java
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,75 @@
package com.doumee.dao.dto;
import io.swagger.annotations.ApiModel;
import io.swagger.annotations.ApiModelProperty;
import lombok.Data;
import javax.validation.constraints.NotEmpty;
import javax.validation.constraints.NotNull;
import java.io.Serializable;
import java.util.Date;
import java.util.List;
/**
 * å¸æœºå®žåè®¤è¯è¯·æ±‚ç±»
 * @author rk
 * @date 2026/04/08
 */
@Data
@ApiModel("司机实名认证请求类")
public class DriverVerifyRequest implements Serializable {
    @NotEmpty(message = "姓名不能为空")
    @ApiModelProperty(value = "姓名", required = true)
    private String name;
    @NotEmpty(message = "身份证号不能为空")
    @ApiModelProperty(value = "身份证号码", required = true)
    private String idcard;
    @NotNull(message = "婚姻状态不能为空")
    @ApiModelProperty(value = "婚姻状态:0=未婚;1=已婚;2=离异;3=丧偶", required = true, example = "0")
    private Integer maritalStatus;
    @ApiModelProperty(value = "区划主键", example = "1")
    private Integer areaId;
    @NotEmpty(message = "居住地址不能为空")
    @ApiModelProperty(value = "居住地址", required = true)
    private String livePlace;
    @NotEmpty(message = "车牌号不能为空")
    @ApiModelProperty(value = "车牌号", required = true)
    private String carCode;
    @NotNull(message = "车辆类型不能为空")
    @ApiModelProperty(value = "车辆类型(关联category type=1)", required = true, example = "1")
    private Integer carType;
    @ApiModelProperty(value = "车辆颜色")
    private String carColor;
    @ApiModelProperty(value = "驾驶证有效期开始时间")
    private Date cardStartDate;
    @ApiModelProperty(value = "驾驶证有效期结束时间")
    private Date cardEndDate;
    @NotEmpty(message = "身份证正面照不能为空")
    @ApiModelProperty(value = "身份证正面照", required = true)
    private String idcardImg;
    @NotEmpty(message = "身份证反面照不能为空")
    @ApiModelProperty(value = "身份证反面照", required = true)
    private String idcardImgBack;
    @ApiModelProperty(value = "车辆照片(最多3张,mutifile objType=6)")
    private List<String> carImgUrls;
    @ApiModelProperty(value = "驾驶证照片(最多3张,mutifile objType=7)")
    private List<String> licenseImgUrls;
    @ApiModelProperty(value = "其他资料照片(最多3张,mutifile objType=8)")
    private List<String> otherImgUrls;
}
server/services/src/main/java/com/doumee/dao/dto/EstimatedDeliverySaveDTO.java
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,33 @@
package com.doumee.dao.dto;
import io.swagger.annotations.ApiModel;
import io.swagger.annotations.ApiModelProperty;
import lombok.Data;
import javax.validation.constraints.NotNull;
import java.io.Serializable;
/**
 * é¢„计时效配置保存请求
 * @author rk
 * @date 2026/04/08
 */
@Data
@ApiModel("预计时效配置保存请求")
public class EstimatedDeliverySaveDTO implements Serializable {
    @ApiModelProperty(value = "规则主键(修改时必传)")
    private Integer id;
    @ApiModelProperty(value = "城市主键", required = true, example = "1")
    @NotNull(message = "城市主键不能为空")
    private Integer cityId;
    @ApiModelProperty(value = "配送里程(公里)", required = true, example = "10")
    @NotNull(message = "配送里程不能为空")
    private String distance;
    @ApiModelProperty(value = "配送时长(小时)", required = true, example = "2")
    @NotNull(message = "配送时长不能为空")
    private String duration;
}
server/services/src/main/java/com/doumee/dao/dto/LocalStoragePricingItemDTO.java
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,26 @@
package com.doumee.dao.dto;
import io.swagger.annotations.ApiModel;
import io.swagger.annotations.ApiModelProperty;
import lombok.Data;
import javax.validation.constraints.NotNull;
import java.io.Serializable;
/**
 * å°±åœ°å­˜å–规则项
 * @author rk
 * @date 2026/04/08
 */
@Data
@ApiModel("就地存取规则项")
public class LocalStoragePricingItemDTO implements Serializable {
    @ApiModelProperty(value = "物品规格主键(category.id, type=4)", required = true, example = "1")
    @NotNull(message = "物品规格主键不能为空")
    private Integer categoryId;
    @ApiModelProperty(value = "收费单价", required = true, example = "10.50")
    @NotNull(message = "收费单价不能为空")
    private String unitPrice;
}
server/services/src/main/java/com/doumee/dao/dto/LocalStoragePricingSaveDTO.java
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,30 @@
package com.doumee.dao.dto;
import io.swagger.annotations.ApiModel;
import io.swagger.annotations.ApiModelProperty;
import lombok.Data;
import javax.validation.Valid;
import javax.validation.constraints.NotEmpty;
import javax.validation.constraints.NotNull;
import java.io.Serializable;
import java.util.List;
/**
 * å°±åœ°å­˜å–规则批量保存请求
 * @author rk
 * @date 2026/04/08
 */
@Data
@ApiModel("就地存取规则批量保存请求")
public class LocalStoragePricingSaveDTO implements Serializable {
    @ApiModelProperty(value = "城市主键", required = true, example = "1")
    @NotNull(message = "城市主键不能为空")
    private Integer cityId;
    @ApiModelProperty(value = "规则明细列表", required = true)
    @NotEmpty(message = "规则明细不能为空")
    @Valid
    private List<LocalStoragePricingItemDTO> items;
}
server/services/src/main/java/com/doumee/dao/dto/RemoteDeliveryPricingItemDTO.java
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,38 @@
package com.doumee.dao.dto;
import io.swagger.annotations.ApiModel;
import io.swagger.annotations.ApiModelProperty;
import lombok.Data;
import javax.validation.constraints.NotNull;
import java.io.Serializable;
/**
 * å¼‚地寄送规则项
 * @author rk
 * @date 2026/04/08
 */
@Data
@ApiModel("异地寄送规则项")
public class RemoteDeliveryPricingItemDTO implements Serializable {
    @ApiModelProperty(value = "物品规格主键(category.id, type=4)", required = true, example = "1")
    @NotNull(message = "物品规格主键不能为空")
    private Integer categoryId;
    @ApiModelProperty(value = "配送起步里程公里数", required = true, example = "5")
    @NotNull(message = "配送起步里程不能为空")
    private String startDistance;
    @ApiModelProperty(value = "配送起步里程每公里单价", required = true, example = "3.00")
    @NotNull(message = "配送起步里程每公里单价不能为空")
    private String startPrice;
    @ApiModelProperty(value = "超出首单里程公里数", required = true, example = "10")
    @NotNull(message = "超出首单里程不能为空")
    private String extraDistance;
    @ApiModelProperty(value = "超出首单里程每公里单价", required = true, example = "2.00")
    @NotNull(message = "超出首单里程每公里单价不能为空")
    private String extraPrice;
}
server/services/src/main/java/com/doumee/dao/dto/RemoteDeliveryPricingSaveDTO.java
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,30 @@
package com.doumee.dao.dto;
import io.swagger.annotations.ApiModel;
import io.swagger.annotations.ApiModelProperty;
import lombok.Data;
import javax.validation.Valid;
import javax.validation.constraints.NotEmpty;
import javax.validation.constraints.NotNull;
import java.io.Serializable;
import java.util.List;
/**
 * å¼‚地寄送规则批量保存请求
 * @author rk
 * @date 2026/04/08
 */
@Data
@ApiModel("异地寄送规则批量保存请求")
public class RemoteDeliveryPricingSaveDTO implements Serializable {
    @ApiModelProperty(value = "城市主键", required = true, example = "1")
    @NotNull(message = "城市主键不能为空")
    private Integer cityId;
    @ApiModelProperty(value = "规则明细列表", required = true)
    @NotEmpty(message = "规则明细不能为空")
    @Valid
    private List<RemoteDeliveryPricingItemDTO> items;
}
server/services/src/main/java/com/doumee/dao/dto/RevenueShareItemDTO.java
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,26 @@
package com.doumee.dao.dto;
import io.swagger.annotations.ApiModel;
import io.swagger.annotations.ApiModelProperty;
import lombok.Data;
import javax.validation.constraints.NotNull;
import java.io.Serializable;
/**
 * åˆ†æˆæ¯”例规则项
 * @author rk
 * @date 2026/04/08
 */
@Data
@ApiModel("分成比例规则项")
public class RevenueShareItemDTO implements Serializable {
    @ApiModelProperty(value = "类型(0=企业寄, 1=个人寄, 2=企业取, 3=个人取, 4=配送员)", required = true, example = "0")
    @NotNull(message = "类型不能为空")
    private Integer fieldType;
    @ApiModelProperty(value = "分成比例", required = true, example = "0.15")
    @NotNull(message = "分成比例不能为空")
    private String ratio;
}
server/services/src/main/java/com/doumee/dao/dto/RevenueShareSaveDTO.java
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,30 @@
package com.doumee.dao.dto;
import io.swagger.annotations.ApiModel;
import io.swagger.annotations.ApiModelProperty;
import lombok.Data;
import javax.validation.Valid;
import javax.validation.constraints.NotEmpty;
import javax.validation.constraints.NotNull;
import java.io.Serializable;
import java.util.List;
/**
 * åˆ†æˆæ¯”例批量保存请求
 * @author rk
 * @date 2026/04/08
 */
@Data
@ApiModel("分成比例批量保存请求")
public class RevenueShareSaveDTO implements Serializable {
    @ApiModelProperty(value = "城市主键", required = true, example = "1")
    @NotNull(message = "城市主键不能为空")
    private Integer cityId;
    @ApiModelProperty(value = "规则明细列表(企业寄/个人寄/企业取/个人取/配送员共5条)", required = true)
    @NotEmpty(message = "规则明细不能为空")
    @Valid
    private List<RevenueShareItemDTO> items;
}
server/services/src/main/java/com/doumee/dao/dto/StoreDepositItemDTO.java
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,26 @@
package com.doumee.dao.dto;
import io.swagger.annotations.ApiModel;
import io.swagger.annotations.ApiModelProperty;
import lombok.Data;
import javax.validation.constraints.NotNull;
import java.io.Serializable;
/**
 * é—¨åº—注册押金规则项
 * @author rk
 * @date 2026/04/08
 */
@Data
@ApiModel("门店注册押金规则项")
public class StoreDepositItemDTO implements Serializable {
    @ApiModelProperty(value = "企业类型(0=企业, 1=个人)", required = true, example = "0")
    @NotNull(message = "企业类型不能为空")
    private Integer fieldType;
    @ApiModelProperty(value = "押金金额", required = true, example = "5000.00")
    @NotNull(message = "押金金额不能为空")
    private String depositAmount;
}
server/services/src/main/java/com/doumee/dao/dto/StoreDepositSaveDTO.java
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,30 @@
package com.doumee.dao.dto;
import io.swagger.annotations.ApiModel;
import io.swagger.annotations.ApiModelProperty;
import lombok.Data;
import javax.validation.Valid;
import javax.validation.constraints.NotEmpty;
import javax.validation.constraints.NotNull;
import java.io.Serializable;
import java.util.List;
/**
 * é—¨åº—注册押金批量保存请求
 * @author rk
 * @date 2026/04/08
 */
@Data
@ApiModel("门店注册押金批量保存请求")
public class StoreDepositSaveDTO implements Serializable {
    @ApiModelProperty(value = "城市主键", required = true, example = "1")
    @NotNull(message = "城市主键不能为空")
    private Integer cityId;
    @ApiModelProperty(value = "规则明细列表(企业+个人共2条)", required = true)
    @NotEmpty(message = "规则明细不能为空")
    @Valid
    private List<StoreDepositItemDTO> items;
}
server/services/src/main/java/com/doumee/dao/vo/EstimatedDeliveryVO.java
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,29 @@
package com.doumee.dao.vo;
import io.swagger.annotations.ApiModel;
import io.swagger.annotations.ApiModelProperty;
import lombok.Data;
import java.io.Serializable;
/**
 * é¢„计时效配置列表返回
 * @author rk
 * @date 2026/04/08
 */
@Data
@ApiModel("预计时效配置(列表返回)")
public class EstimatedDeliveryVO implements Serializable {
    @ApiModelProperty(value = "规则主键")
    private Integer pricingRuleId;
    @ApiModelProperty(value = "城市主键")
    private Integer cityId;
    @ApiModelProperty(value = "配送里程(公里)")
    private String distance;
    @ApiModelProperty(value = "配送时长(小时)")
    private String duration;
}
server/services/src/main/java/com/doumee/dao/vo/LocalStoragePricingVO.java
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,32 @@
package com.doumee.dao.vo;
import io.swagger.annotations.ApiModel;
import io.swagger.annotations.ApiModelProperty;
import lombok.Data;
import java.io.Serializable;
/**
 * å°±åœ°å­˜å–规则列表返回
 * @author rk
 * @date 2026/04/08
 */
@Data
@ApiModel("就地存取规则项(列表返回)")
public class LocalStoragePricingVO implements Serializable {
    @ApiModelProperty(value = "规则主键")
    private Integer pricingRuleId;
    @ApiModelProperty(value = "物品尺寸主键")
    private Integer categoryId;
    @ApiModelProperty(value = "物品尺寸名称")
    private String categoryName;
    @ApiModelProperty(value = "收费单价")
    private String unitPrice;
    @ApiModelProperty(value = "城市主键")
    private Integer cityId;
}
server/services/src/main/java/com/doumee/dao/vo/RemoteDeliveryPricingVO.java
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,41 @@
package com.doumee.dao.vo;
import io.swagger.annotations.ApiModel;
import io.swagger.annotations.ApiModelProperty;
import lombok.Data;
import java.io.Serializable;
/**
 * å¼‚地寄送规则列表返回
 * @author rk
 * @date 2026/04/08
 */
@Data
@ApiModel("异地寄送规则项(列表返回)")
public class RemoteDeliveryPricingVO implements Serializable {
    @ApiModelProperty(value = "规则主键")
    private Integer pricingRuleId;
    @ApiModelProperty(value = "物品尺寸主键")
    private Integer categoryId;
    @ApiModelProperty(value = "物品尺寸名称")
    private String categoryName;
    @ApiModelProperty(value = "配送起步里程公里数")
    private String startDistance;
    @ApiModelProperty(value = "配送起步里程每公里单价")
    private String startPrice;
    @ApiModelProperty(value = "超出首单里程公里数")
    private String extraDistance;
    @ApiModelProperty(value = "超出首单里程每公里单价")
    private String extraPrice;
    @ApiModelProperty(value = "城市主键")
    private Integer cityId;
}
server/services/src/main/java/com/doumee/dao/vo/RevenueShareVO.java
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,32 @@
package com.doumee.dao.vo;
import io.swagger.annotations.ApiModel;
import io.swagger.annotations.ApiModelProperty;
import lombok.Data;
import java.io.Serializable;
/**
 * åˆ†æˆæ¯”例列表返回
 * @author rk
 * @date 2026/04/08
 */
@Data
@ApiModel("分成比例(列表返回)")
public class RevenueShareVO implements Serializable {
    @ApiModelProperty(value = "规则主键")
    private Integer pricingRuleId;
    @ApiModelProperty(value = "城市主键")
    private Integer cityId;
    @ApiModelProperty(value = "类型(0=企业寄, 1=个人寄, 2=企业取, 3=个人取, 4=配送员)")
    private Integer fieldType;
    @ApiModelProperty(value = "类型名称")
    private String fieldTypeName;
    @ApiModelProperty(value = "分成比例")
    private String ratio;
}
server/services/src/main/java/com/doumee/dao/vo/StoreDepositVO.java
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,32 @@
package com.doumee.dao.vo;
import io.swagger.annotations.ApiModel;
import io.swagger.annotations.ApiModelProperty;
import lombok.Data;
import java.io.Serializable;
/**
 * é—¨åº—注册押金列表返回
 * @author rk
 * @date 2026/04/08
 */
@Data
@ApiModel("门店注册押金(列表返回)")
public class StoreDepositVO implements Serializable {
    @ApiModelProperty(value = "规则主键")
    private Integer pricingRuleId;
    @ApiModelProperty(value = "城市主键")
    private Integer cityId;
    @ApiModelProperty(value = "企业类型(0=企业, 1=个人)")
    private Integer fieldType;
    @ApiModelProperty(value = "企业类型名称")
    private String fieldTypeName;
    @ApiModelProperty(value = "押金金额")
    private String depositAmount;
}
server/services/src/main/java/com/doumee/service/business/AreasService.java
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,136 @@
package com.doumee.service.business;
import com.doumee.core.model.PageData;
import com.doumee.core.model.PageWrap;
import com.doumee.dao.business.model.Areas;
import java.util.List;
/**
 * çœå¸‚区信息表Service定义
 * @author æ±Ÿè¹„蹄
 * @date 2023/02/15 08:55
 */
public interface AreasService {
    /**
     * åˆ›å»º
     *
     * @param areas å®žä½“对象
     * @return Integer
     */
    Integer create(Areas areas);
    /**
     * ä¸»é”®åˆ é™¤
     *
     * @param id ä¸»é”®
     */
    void deleteById(Integer id);
    /**
     * åˆ é™¤
     *
     * @param areas å®žä½“对象
     */
    void delete(Areas areas);
    /**
     * æ‰¹é‡ä¸»é”®åˆ é™¤
     *
     * @param ids ä¸»é”®é›†
     */
    void deleteByIdInBatch(List<Integer> ids);
    /**
     * ä¸»é”®æ›´æ–°
     *
     * @param areas å®žä½“对象
     */
    void updateById(Areas areas);
    /**
     * æ‰¹é‡ä¸»é”®æ›´æ–°
     *
     * @param areass å®žä½“集
     */
    void updateByIdInBatch(List<Areas> areass);
    /**
     * ä¸»é”®æŸ¥è¯¢
     *
     * @param id ä¸»é”®
     * @return Areas
     */
    Areas findById(Integer id);
    /**
     * æ ¹æ®id和type查询对象信息
     * @param id
     * @param type null æŸ¥è¯¢å…¨éƒ¨ 0省份 1城市 2区域
     * @return
     */
    Areas findById(Integer id,Integer type);
    Areas findByName(String name,Integer type);
    Areas findByNameAndParentId(String name,Integer type,Integer parentId);
    List<Areas> findByParentId(Integer parentId ,Integer type,int flag);
    List<Areas> findChildByParentId(Integer id,List<Areas>  list);
    boolean isAreaValid(String proName,String cityName,String areaName);
    /**
     * æ¡ä»¶æŸ¥è¯¢å•条记录
     *
     * @param areas å®žä½“对象
     * @return Areas
     */
    Areas findOne(Areas areas);
    /**
     * æ¡ä»¶æŸ¥è¯¢
     *
     * @param areas å®žä½“对象
     * @return List<Areas>
     */
    List<Areas> findList(Areas areas);
    /**
     * åˆ†é¡µæŸ¥è¯¢
     *
     * @param pageWrap åˆ†é¡µå¯¹è±¡
     * @return PageData<Areas>
     */
    PageData<Areas> findPage(PageWrap<Areas> pageWrap);
    /**
     * æ¡ä»¶ç»Ÿè®¡
     *
     * @param areas å®žä½“对象
     * @return long
     */
    long count(Areas areas);
    void cacheData();
    Areas findByCityAndArea(String cityName, String areasName);
    String getAddress(Integer cityId,Integer areaId);
    String getAddress(Integer areaId);
    List<Areas> listByParentId(Areas model);
    /**
     * èŽ·å–åŸŽå¸‚ä¿¡æ¯
     * @param areas
     * @return
     */
    List<Areas> getCityList(Areas areas);
}
server/services/src/main/java/com/doumee/service/business/BannerService.java
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,37 @@
package com.doumee.service.business;
import com.doumee.core.model.PageData;
import com.doumee.core.model.PageWrap;
import com.doumee.dao.business.model.Banner;
import java.util.List;
/**
 * è½®æ’­å›¾Service定义
 * @author rk
 * @date 2026/04/08
 */
public interface BannerService {
    Integer create(Banner banner);
    void deleteById(Integer id);
    void delete(Banner banner);
    void deleteByIdInBatch(List<Integer> ids);
    void updateById(Banner banner);
    void updateByIdInBatch(List<Banner> banners);
    Banner findById(Integer id);
    Banner findOne(Banner banner);
    List<Banner> findList(Banner banner);
    PageData<Banner> findPage(PageWrap<Banner> pageWrap);
    long count(Banner banner);
}
server/services/src/main/java/com/doumee/service/business/DriverInfoService.java
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,149 @@
package com.doumee.service.business;
import com.doumee.core.model.PageData;
import com.doumee.core.model.PageWrap;
import com.doumee.dao.business.model.DriverInfo;
import com.doumee.dao.dto.DriverLoginRequest;
import com.doumee.dao.dto.DriverRegisterRequest;
import com.doumee.dao.dto.DriverVerifyRequest;
import com.doumee.dao.vo.AccountResponse;
import java.util.List;
/**
 * å¸æœºæ³¨å†Œä¿¡æ¯Service定义
 * @author rk
 * @date 2026/04/08
 */
public interface DriverInfoService {
    /**
     * åˆ›å»º
     *
     * @param driverInfo å®žä½“对象
     * @return Integer
     */
    Integer create(DriverInfo driverInfo);
    /**
     * ä¸»é”®åˆ é™¤
     *
     * @param id ä¸»é”®
     */
    void deleteById(Integer id);
    /**
     * åˆ é™¤
     *
     * @param driverInfo å®žä½“对象
     */
    void delete(DriverInfo driverInfo);
    /**
     * æ‰¹é‡ä¸»é”®åˆ é™¤
     *
     * @param ids ä¸»é”®é›†
     */
    void deleteByIdInBatch(List<Integer> ids);
    /**
     * ä¸»é”®æ›´æ–°
     *
     * @param driverInfo å®žä½“对象
     */
    void updateById(DriverInfo driverInfo);
    /**
     * æ‰¹é‡ä¸»é”®æ›´æ–°
     *
     * @param driverInfos å®žä½“集
     */
    void updateByIdInBatch(List<DriverInfo> driverInfos);
    /**
     * ä¸»é”®æŸ¥è¯¢
     *
     * @param id ä¸»é”®
     * @return DriverInfo
     */
    DriverInfo findById(Integer id);
    /**
     * æ¡ä»¶æŸ¥è¯¢å•条记录
     *
     * @param driverInfo å®žä½“对象
     * @return DriverInfo
     */
    DriverInfo findOne(DriverInfo driverInfo);
    /**
     * æ¡ä»¶æŸ¥è¯¢
     *
     * @param driverInfo å®žä½“对象
     * @return List<DriverInfo>
     */
    List<DriverInfo> findList(DriverInfo driverInfo);
    /**
     * åˆ†é¡µæŸ¥è¯¢
     *
     * @param pageWrap åˆ†é¡µå¯¹è±¡
     * @return PageData<DriverInfo>
     */
    PageData<DriverInfo> findPage(PageWrap<DriverInfo> pageWrap);
    /**
     * æ¡ä»¶ç»Ÿè®¡
     *
     * @param driverInfo å®žä½“对象
     * @return long
     */
    long count(DriverInfo driverInfo);
    /**
     * å¸æœºéªŒè¯ç ç™»å½•(手机号+短信验证码,无账号自动注册)
     *
     * @param request éªŒè¯ç ç™»å½•请求
     * @return AccountResponse
     */
    AccountResponse register(DriverRegisterRequest request);
    /**
     * å‘送司机验证码登录验证码
     *
     * @param telephone æ‰‹æœºå·
     */
    void sendRegisterCode(String telephone);
    /**
     * å¸æœºæ‰‹æœºå·+密码登录
     *
     * @param request ç™»å½•请求
     * @return AccountResponse
     */
    AccountResponse login(DriverLoginRequest request);
    /**
     * æäº¤å®žåè®¤è¯ï¼ˆåˆæ¬¡æäº¤æˆ–驳回后修改)
     *
     * @param memberId ä¼šå‘˜ä¸»é”®
     * @param request  è®¤è¯è¯·æ±‚
     */
    void submitVerify(Integer memberId, DriverVerifyRequest request);
    /**
     * æŸ¥è¯¢å¸æœºå®žåè®¤è¯è¯¦æƒ…
     *
     * @param memberId ä¼šå‘˜ä¸»é”®
     * @return DriverInfo
     */
    DriverInfo getVerifyDetail(Integer memberId);
    /**
     * å®¡æ‰¹å¸æœºå®žåè®¤è¯ï¼ˆç®¡ç†ç«¯ï¼‰
     *
     * @param auditDTO å®¡æ‰¹å‚æ•°
     */
    void auditVerify(com.doumee.dao.dto.AuditDTO auditDTO);
}
server/services/src/main/java/com/doumee/service/business/MemberService.java
@@ -135,11 +135,11 @@
     */
    void editMemberInfo(Member member);
    /**
     * åˆ‡æ¢ç”¨å·¥èº«ä»½
     * @param member
     */
    void editUseIdentity(Member member);
//    /**
//     * åˆ‡æ¢ç”¨å·¥èº«ä»½
//     * @param member
//     */
//    void editUseIdentity(Member member);
    /**
     * ä¸ªäººä¿¡æ¯
@@ -150,5 +150,7 @@
    UserCenterVO getPlatformAboutUs();
    void logOut(String token,Integer memberId);
    void logOff(String token,Integer memberId);
}
server/services/src/main/java/com/doumee/service/business/PricingRuleService.java
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,187 @@
package com.doumee.service.business;
import com.doumee.core.model.PageData;
import com.doumee.core.model.PageWrap;
import com.doumee.dao.business.model.PricingRule;
import com.doumee.dao.dto.LocalStoragePricingSaveDTO;
import com.doumee.dao.dto.RemoteDeliveryPricingSaveDTO;
import com.doumee.dao.dto.EstimatedDeliverySaveDTO;
import com.doumee.dao.dto.StoreDepositSaveDTO;
import com.doumee.dao.dto.RevenueShareSaveDTO;
import com.doumee.dao.vo.LocalStoragePricingVO;
import com.doumee.dao.vo.RemoteDeliveryPricingVO;
import com.doumee.dao.vo.EstimatedDeliveryVO;
import com.doumee.dao.vo.StoreDepositVO;
import com.doumee.dao.vo.RevenueShareVO;
import java.util.List;
/**
 * è®¡ä»·è§„则配置Service定义
 * @author rk
 * @date 2026/04/08
 */
public interface PricingRuleService {
    /**
     * åˆ›å»º
     *
     * @param pricingRule å®žä½“对象
     * @return Integer
     */
    Integer create(PricingRule pricingRule);
    /**
     * ä¸»é”®åˆ é™¤
     *
     * @param id ä¸»é”®
     */
    void deleteById(Integer id);
    /**
     * åˆ é™¤
     *
     * @param pricingRule å®žä½“对象
     */
    void delete(PricingRule pricingRule);
    /**
     * æ‰¹é‡ä¸»é”®åˆ é™¤
     *
     * @param ids ä¸»é”®é›†
     */
    void deleteByIdInBatch(List<Integer> ids);
    /**
     * ä¸»é”®æ›´æ–°
     *
     * @param pricingRule å®žä½“对象
     */
    void updateById(PricingRule pricingRule);
    /**
     * æ‰¹é‡ä¸»é”®æ›´æ–°
     *
     * @param pricingRules å®žä½“集
     */
    void updateByIdInBatch(List<PricingRule> pricingRules);
    /**
     * ä¸»é”®æŸ¥è¯¢
     *
     * @param id ä¸»é”®
     * @return PricingRule
     */
    PricingRule findById(Integer id);
    /**
     * æ¡ä»¶æŸ¥è¯¢å•条记录
     *
     * @param pricingRule å®žä½“对象
     * @return PricingRule
     */
    PricingRule findOne(PricingRule pricingRule);
    /**
     * æ¡ä»¶æŸ¥è¯¢
     *
     * @param pricingRule å®žä½“对象
     * @return List<PricingRule>
     */
    List<PricingRule> findList(PricingRule pricingRule);
    /**
     * åˆ†é¡µæŸ¥è¯¢
     *
     * @param pageWrap åˆ†é¡µå¯¹è±¡
     * @return PageData<PricingRule>
     */
    PageData<PricingRule> findPage(PageWrap<PricingRule> pageWrap);
    /**
     * æ¡ä»¶ç»Ÿè®¡
     *
     * @param pricingRule å®žä½“对象
     * @return long
     */
    long count(PricingRule pricingRule);
    /**
     * æ‰¹é‡ä¿å­˜å°±åœ°å­˜å–规则
     * @param request æ‰¹é‡ä¿å­˜è¯·æ±‚
     */
    void batchSaveLocalStoragePricing(LocalStoragePricingSaveDTO request);
    /**
     * æŸ¥è¯¢å°±åœ°å­˜å–规则列表
     * @param cityId åŸŽå¸‚主键
     * @return å°±åœ°å­˜å–规则列表
     */
    List<LocalStoragePricingVO> listLocalStoragePricing(Integer cityId);
    /**
     * æ‰¹é‡ä¿å­˜å¼‚地寄送规则
     * @param request æ‰¹é‡ä¿å­˜è¯·æ±‚
     */
    void batchSaveRemoteDeliveryPricing(RemoteDeliveryPricingSaveDTO request);
    /**
     * æŸ¥è¯¢å¼‚地寄送规则列表
     * @param cityId åŸŽå¸‚主键
     * @return å¼‚地寄送规则列表
     */
    List<RemoteDeliveryPricingVO> listRemoteDeliveryPricing(Integer cityId);
    /**
     * æ–°å¢žé¢„计时效配置
     * @param request ä¿å­˜è¯·æ±‚
     * @return è§„则主键
     */
    Integer createEstimatedDelivery(EstimatedDeliverySaveDTO request);
    /**
     * ä¿®æ”¹é¢„计时效配置
     * @param request ä¿å­˜è¯·æ±‚
     */
    void updateEstimatedDelivery(EstimatedDeliverySaveDTO request);
    /**
     * åˆ é™¤é¢„计时效配置
     * @param id è§„则主键
     */
    void deleteEstimatedDelivery(Integer id);
    /**
     * æŸ¥è¯¢é¢„计时效配置列表
     * @param cityId åŸŽå¸‚主键
     * @return é¢„计时效配置列表
     */
    List<EstimatedDeliveryVO> listEstimatedDelivery(Integer cityId);
    /**
     * æ‰¹é‡ä¿å­˜é—¨åº—注册押金
     * @param request æ‰¹é‡ä¿å­˜è¯·æ±‚
     */
    void batchSaveStoreDeposit(StoreDepositSaveDTO request);
    /**
     * æŸ¥è¯¢é—¨åº—注册押金列表(固定返回2条)
     * @param cityId åŸŽå¸‚主键
     * @return é—¨åº—注册押金列表
     */
    List<StoreDepositVO> listStoreDeposit(Integer cityId);
    /**
     * æ‰¹é‡ä¿å­˜åˆ†æˆæ¯”例
     * @param request æ‰¹é‡ä¿å­˜è¯·æ±‚
     */
    void batchSaveRevenueShare(RevenueShareSaveDTO request);
    /**
     * æŸ¥è¯¢åˆ†æˆæ¯”例列表(固定返回5条)
     * @param cityId åŸŽå¸‚主键
     * @return åˆ†æˆæ¯”例列表
     */
    List<RevenueShareVO> listRevenueShare(Integer cityId);
}
server/services/src/main/java/com/doumee/service/business/ShopInfoService.java
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,99 @@
package com.doumee.service.business;
import com.doumee.core.model.PageData;
import com.doumee.core.model.PageWrap;
import com.doumee.dao.business.model.ShopInfo;
import java.util.List;
/**
 * é—¨åº—信息Service定义
 * @author rk
 * @date 2026/04/08
 */
public interface ShopInfoService {
    /**
     * åˆ›å»º
     *
     * @param shopInfo å®žä½“对象
     * @return Integer
     */
    Integer create(ShopInfo shopInfo);
    /**
     * ä¸»é”®åˆ é™¤
     *
     * @param id ä¸»é”®
     */
    void deleteById(Integer id);
    /**
     * åˆ é™¤
     *
     * @param shopInfo å®žä½“对象
     */
    void delete(ShopInfo shopInfo);
    /**
     * æ‰¹é‡ä¸»é”®åˆ é™¤
     *
     * @param ids ä¸»é”®é›†
     */
    void deleteByIdInBatch(List<Integer> ids);
    /**
     * ä¸»é”®æ›´æ–°
     *
     * @param shopInfo å®žä½“对象
     */
    void updateById(ShopInfo shopInfo);
    /**
     * æ‰¹é‡ä¸»é”®æ›´æ–°
     *
     * @param shopInfos å®žä½“集
     */
    void updateByIdInBatch(List<ShopInfo> shopInfos);
    /**
     * ä¸»é”®æŸ¥è¯¢
     *
     * @param id ä¸»é”®
     * @return ShopInfo
     */
    ShopInfo findById(Integer id);
    /**
     * æ¡ä»¶æŸ¥è¯¢å•条记录
     *
     * @param shopInfo å®žä½“对象
     * @return ShopInfo
     */
    ShopInfo findOne(ShopInfo shopInfo);
    /**
     * æ¡ä»¶æŸ¥è¯¢
     *
     * @param shopInfo å®žä½“对象
     * @return List<ShopInfo>
     */
    List<ShopInfo> findList(ShopInfo shopInfo);
    /**
     * åˆ†é¡µæŸ¥è¯¢
     *
     * @param pageWrap åˆ†é¡µå¯¹è±¡
     * @return PageData<ShopInfo>
     */
    PageData<ShopInfo> findPage(PageWrap<ShopInfo> pageWrap);
    /**
     * æ¡ä»¶ç»Ÿè®¡
     *
     * @param shopInfo å®žä½“对象
     * @return long
     */
    long count(ShopInfo shopInfo);
}
server/services/src/main/java/com/doumee/service/business/SmsrecordService.java
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,99 @@
package com.doumee.service.business;
import com.doumee.core.model.PageData;
import com.doumee.core.model.PageWrap;
import com.doumee.dao.business.model.Smsrecord;
import java.util.List;
/**
 * çŸ­ä¿¡éªŒè¯ç Service定义
 * @author rk
 * @date 2026/04/08
 */
public interface SmsrecordService {
    /**
     * åˆ›å»º
     *
     * @param smsrecord å®žä½“对象
     * @return Integer
     */
    Integer create(Smsrecord smsrecord);
    /**
     * ä¸»é”®åˆ é™¤
     *
     * @param id ä¸»é”®
     */
    void deleteById(Integer id);
    /**
     * åˆ é™¤
     *
     * @param smsrecord å®žä½“对象
     */
    void delete(Smsrecord smsrecord);
    /**
     * æ‰¹é‡ä¸»é”®åˆ é™¤
     *
     * @param ids ä¸»é”®é›†
     */
    void deleteByIdInBatch(List<Integer> ids);
    /**
     * ä¸»é”®æ›´æ–°
     *
     * @param smsrecord å®žä½“对象
     */
    void updateById(Smsrecord smsrecord);
    /**
     * æ‰¹é‡ä¸»é”®æ›´æ–°
     *
     * @param smsrecords å®žä½“集
     */
    void updateByIdInBatch(List<Smsrecord> smsrecords);
    /**
     * ä¸»é”®æŸ¥è¯¢
     *
     * @param id ä¸»é”®
     * @return Smsrecord
     */
    Smsrecord findById(Integer id);
    /**
     * æ¡ä»¶æŸ¥è¯¢å•条记录
     *
     * @param smsrecord å®žä½“对象
     * @return Smsrecord
     */
    Smsrecord findOne(Smsrecord smsrecord);
    /**
     * æ¡ä»¶æŸ¥è¯¢
     *
     * @param smsrecord å®žä½“对象
     * @return List<Smsrecord>
     */
    List<Smsrecord> findList(Smsrecord smsrecord);
    /**
     * åˆ†é¡µæŸ¥è¯¢
     *
     * @param pageWrap åˆ†é¡µå¯¹è±¡
     * @return PageData<Smsrecord>
     */
    PageData<Smsrecord> findPage(PageWrap<Smsrecord> pageWrap);
    /**
     * æ¡ä»¶ç»Ÿè®¡
     *
     * @param smsrecord å®žä½“对象
     * @return long
     */
    long count(Smsrecord smsrecord);
}
server/services/src/main/java/com/doumee/service/business/impl/AreasServiceImpl.java
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,521 @@
package com.doumee.service.business.impl;
import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONObject;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.conditions.update.UpdateWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.doumee.core.constants.Constants;
import com.doumee.core.constants.ResponseStatus;
import com.doumee.core.exception.BusinessException;
import com.doumee.core.model.PageData;
import com.doumee.core.model.PageWrap;
import com.doumee.core.utils.PinYinUtil;
import com.doumee.core.utils.Utils;
import com.doumee.dao.business.AreasMapper;
import com.doumee.dao.business.model.Areas;
import com.doumee.service.business.AreasService;
import com.github.yulichang.wrapper.MPJLambdaWrapper;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Service;
import org.springframework.util.CollectionUtils;
import org.springframework.web.client.RestTemplate;
import java.util.*;
import java.util.stream.Collectors;
/**
 * çœå¸‚区信息表Service实现
 * @author æ±Ÿè¹„蹄
 * @date 2023/02/15 08:55
 */
@Service
public class AreasServiceImpl implements AreasService {
    public static   List<Areas> ALL_AREA_LIST;
    public static   List<Areas> PROVINCE_LIST;
    public static   List<Areas> CITY_LIST;
    public static   List<Areas> AREA_LIST;
    public static   List<Areas> ALL_AREA_TREE;
    @Autowired
    private AreasMapper areasMapper;
    @Autowired
    RestTemplate restTemplate ;
    @Override
    public Integer create(Areas areas) {
/*
        if (Objects.isNull(areas.getParentId())){
            areas.setType(Constants.ZERO);
        }else {
            Areas parentArea = areasMapper.selectById(areas.getParentId());
            if (Objects.isNull(parentArea)){
                areas.setType(Constants.ZERO);
            }else {
                areas.setType(parentArea.getType()+Constants.ONE);
            }
        }*/
        areas.setIsdeleted(Constants.ZERO);
        areasMapper.insert(areas);
        areas.setCode(areas.getId().toString());
        areasMapper.updateById(areas);
        //刷新缓存数据
        cacheData();
        return areas.getId();
    }
    @Override
    public void deleteById(Integer id) {
        areasMapper.deleteById(id);
        //刷新缓存数据
        cacheData();
    }
    @Override
    public void delete(Areas areas) {
        UpdateWrapper<Areas> deleteWrapper = new UpdateWrapper<>(areas);
        areasMapper.delete(deleteWrapper);
        //刷新缓存数据
        cacheData();
    }
    @Override
    public void deleteByIdInBatch(List<Integer> ids) {
        if (CollectionUtils.isEmpty(ids)) {
            return;
        }
        areasMapper.deleteBatchIds(ids);
        //刷新缓存数据
        cacheData();
    }
    @Override
    public void updateById(Areas areas) {
        UpdateWrapper<Areas> wrapper = new UpdateWrapper<>();
        wrapper.lambda().eq(Areas::getId,areas.getId());
        Areas update = new Areas();
        update.setName(areas.getName());
        update.setSortnum(areas.getSortnum());
        areasMapper.update(update,wrapper);
        //刷新缓存数据
        cacheData();
    }
    @Override
    public void updateByIdInBatch(List<Areas> areass) {
        if (CollectionUtils.isEmpty(areass)) {
            return;
        }
        for (Areas areas: areass) {
            this.updateById(areas);
        }
        //刷新缓存数据
        cacheData();
    }
    @Override
    public Areas findById(Integer id) {
        if(ALL_AREA_LIST!=null){
            for(Areas a : ALL_AREA_LIST){
                if(Constants.equalsInteger(a.getId(),id)){
                    return a;
                }
            }
        }
   //     return areasMapper.selectById(id);
        return  null;
    }
    @Override
    public Areas findById(Integer id,Integer type) {
        List<Areas> list = null;
        if(type == null){
            list = ALL_AREA_LIST;
        }else if(Constants.equalsInteger(type,Constants.ZERO)){
            list = PROVINCE_LIST;
        }else  if(Constants.equalsInteger(type,Constants.ONE)){
            list = CITY_LIST;
        } else if (Constants.equalsInteger(type,Constants.TWO)){
            list =  AREA_LIST;
        }
        if(list!=null){
            for(Areas a : list){
                if(Constants.equalsInteger(a.getId(),id)){
                    return a;
                }
            }
        }
        return null;
    }
    @Override
    public Areas findByName(String name,Integer type){
        List<Areas> list = null;
        if(type == null){
            list = ALL_AREA_LIST;
        }else if(Constants.equalsInteger(type,Constants.ZERO)){
            list = PROVINCE_LIST;
        }else  if(Constants.equalsInteger(type,Constants.ONE)){
            list = CITY_LIST;
        } else if (Constants.equalsInteger(type,Constants.TWO)){
            list =  AREA_LIST;
        }
        if(list!=null){
            for(Areas a : list){
                if(StringUtils.equals(name,a.getName())){
                    return a;
                }
            }
        }
        return null;
    }
    @Override
    public Areas findByNameAndParentId(String name,Integer type,Integer parentId){
        List<Areas> list = null;
        if(type == null){
            list = ALL_AREA_LIST;
        }else if(Constants.equalsInteger(type,Constants.ZERO)){
            list = PROVINCE_LIST;
        }else  if(Constants.equalsInteger(type,Constants.ONE)){
            list = CITY_LIST;
        } else if (Constants.equalsInteger(type,Constants.TWO)){
            list =  AREA_LIST;
        }
        if(list!=null){
            for(Areas a : list){
                if(StringUtils.equals(name,a.getName()) && Constants.equalsInteger(parentId,a.getParentId())){
                    return a;
                }
            }
        }
        return null;
    }
    /**
     *
     * @param type
     * @param parentId
     * @param flag 0无子集 1包含子集县区
     * @return
     */
    @Override
    public List<Areas> findByParentId(Integer parentId,Integer type ,int flag) {
        List<Areas> list = null;
        if(type == null){
            list = ALL_AREA_LIST;
        }else if(Constants.equalsInteger(type,Constants.ZERO)){
            list = PROVINCE_LIST;
        }else  if(Constants.equalsInteger(type,Constants.ONE)){
            list = CITY_LIST;
        } else if (Constants.equalsInteger(type,Constants.TWO)){
            list =  AREA_LIST;
        }
        if(list!=null && Objects.nonNull(parentId)){
            list = list.stream().filter(s->Constants.equalsInteger(s.getParentId(),parentId))
                    .collect(Collectors.toList());
        }
        if(flag == 0){
            List<Areas> result = new ArrayList<>();
            for(Areas a : list){
                Areas r = new Areas();
                BeanUtils.copyProperties(a,r);
                r.setChildList(null);
                result.add(r);
            }
            return  result;
        }
        return list;
    }
    @Override
    public List<Areas> findChildByParentId(Integer id,List<Areas> list){
        List<Areas> result =null;
        if(list == null){
            list = ALL_AREA_LIST;
        }
        if(list!=null && list.size()>0){
            for(Areas model :list){
                if(Constants.equalsInteger(id,model.getParentId())){
                    if(result == null){
                        result = new ArrayList<>();
                    }
                    result.add(model );
                }
            }
        }
        return result;
    }
    @Override
    public boolean isAreaValid(String proName,String cityName,String areaName){
        Areas pro = findByName(proName,Constants.ZERO);
        if(pro == null){
            return  false;
        }
        Areas city = findByName(proName,Constants.ONE);
        if(city == null && !Constants.equalsInteger(city.getParentId(),pro.getId())){
            return  false;
        }
        Areas area = findByName(proName,Constants.TWO);
        if(area == null && !Constants.equalsInteger(area.getParentId(),city.getId())){
            return  false;
        }
        return false;
    }
    @Override
    public Areas findOne(Areas areas) {
        QueryWrapper<Areas> wrapper = new QueryWrapper<>(areas);
        return areasMapper.selectOne(wrapper);
    }
    @Override
    public List<Areas> findList(Areas areas) {
        List<Areas> list = null;
        Integer type =areas.getType();
        if(type == null){
            list = ALL_AREA_LIST;
        }else if(Constants.equalsInteger(type,Constants.ZERO)){
            list = PROVINCE_LIST;
        }else  if(Constants.equalsInteger(type,Constants.ONE)){
            list = CITY_LIST;
        } else if (Constants.equalsInteger(type,Constants.TWO)){
            list =  AREA_LIST;
        }
        List<Areas> result = null;
        if(StringUtils.isNotBlank(areas.getName())){
            for(Areas a : list){
                if(StringUtils.contains(a.getName(),areas.getName())){
                    if(result == null){
                        result = new ArrayList<>();
                    }
                    result.add(a);
                }
            }
            return  result;
        }
        return list;
    }
    @Override
    public  List<Areas> listByParentId(Areas areas) {
        List<Areas> list = null;
        Integer type =areas.getType();
        if(type == null){
            list = ALL_AREA_LIST;
        }else if(Constants.equalsInteger(type,Constants.ZERO)){
            list = PROVINCE_LIST;
        }else  if(Constants.equalsInteger(type,Constants.ONE)){
            list = CITY_LIST;
        } else if (Constants.equalsInteger(type,Constants.TWO)){
            list =  AREA_LIST;
        }
        List<Areas> result = null;
        if( areas.getParentId() !=null){
            for(Areas a : list){
                if(Constants.equalsInteger(a.getParentId(),areas.getParentId())){
                    if(result == null){
                        result = new ArrayList<>();
                    }
                    result.add(a);
                }
            }
            return  result;
        }
        return list;
    }
    @Override
    public  void cacheData() {
       Areas a = new Areas();
       a.setIsdeleted(Constants.ZERO);
       ALL_AREA_LIST = null;
       PROVINCE_LIST =null;
       CITY_LIST=null;
       AREA_LIST = null;
       ALL_AREA_TREE = null;
       ALL_AREA_LIST =  areasMapper.selectJoinList(Areas.class,new MPJLambdaWrapper<Areas>()
                .selectAll(Areas.class)
               .eq(Areas::getIsdeleted,Constants.ZERO)
               .orderByDesc(Areas::getSortnum));
       if(ALL_AREA_LIST!=null){
           for(Areas model : ALL_AREA_LIST){
                if(Constants.equalsInteger(model.getType(),Constants.ZERO)){
                    if(PROVINCE_LIST == null){
                        PROVINCE_LIST = new ArrayList<>();
                    }
                    PROVINCE_LIST.add(model);
                }else if(Constants.equalsInteger(model.getType(),Constants.ONE)){
                    if(CITY_LIST == null){
                        CITY_LIST = new ArrayList<>();
                    }
                    CITY_LIST.add(model);
                    if(model.getParentId() != null){
                        Areas p = findById(model.getParentId());
                        if(p!=null  ){
                            model.setProvinceId(p.getId());
                            model.setProvinceName(p.getName());
                        }
                    }
                }else if(Constants.equalsInteger(model.getType(),Constants.TWO)){
                    if(AREA_LIST == null){
                        AREA_LIST = new ArrayList<>();
                    }
                    AREA_LIST.add(model);
                    Areas city = findById(model.getParentId());
                    if(city!=null  ){
                        model.setCityId(city.getId());
                        model.setCityName(city.getName());
                        if(city!=null && city.getParentId()!=null){
                            Areas p = findById(city.getParentId());
                            if(p!=null  ){
                                model.setProvinceId(p.getId());
                                model.setProvinceName(p.getName());
                            }
                        }
                    }
                }
           }
       }
       if(CITY_LIST!=null){
           for(Areas aa : CITY_LIST){
               aa.setChildList(findChildByParentId(aa.getId(), AREA_LIST));
           }
       }
       if(PROVINCE_LIST!=null){
           for(Areas aa : PROVINCE_LIST){
               aa.setChildList(findChildByParentId(aa.getId(),CITY_LIST));
           }
       }
       System.out.println("=================");
    }
    @Override
    public PageData<Areas> findPage(PageWrap<Areas> pageWrap) {
        IPage<Areas> page = new Page<>(pageWrap.getPage(), pageWrap.getCapacity());
        QueryWrapper<Areas> queryWrapper = new QueryWrapper<>();
        Utils.MP.blankToNull(pageWrap.getModel());
        if (pageWrap.getModel().getId() != null) {
            queryWrapper.lambda().eq(Areas::getId, pageWrap.getModel().getId());
        }
        if (pageWrap.getModel().getCreator() != null) {
            queryWrapper.lambda().eq(Areas::getCreator, pageWrap.getModel().getCreator());
        }
        if (pageWrap.getModel().getCreateDate() != null) {
            queryWrapper.lambda().ge(Areas::getCreateDate, Utils.Date.getStart(pageWrap.getModel().getCreateDate()));
            queryWrapper.lambda().le(Areas::getCreateDate, Utils.Date.getEnd(pageWrap.getModel().getCreateDate()));
        }
        if (pageWrap.getModel().getEditor() != null) {
            queryWrapper.lambda().eq(Areas::getEditor, pageWrap.getModel().getEditor());
        }
        if (pageWrap.getModel().getEditDate() != null) {
            queryWrapper.lambda().ge(Areas::getEditDate, Utils.Date.getStart(pageWrap.getModel().getEditDate()));
            queryWrapper.lambda().le(Areas::getEditDate, Utils.Date.getEnd(pageWrap.getModel().getEditDate()));
        }
        if (pageWrap.getModel().getIsdeleted() != null) {
            queryWrapper.lambda().eq(Areas::getIsdeleted, pageWrap.getModel().getIsdeleted());
        }
        if (pageWrap.getModel().getName() != null) {
            queryWrapper.lambda().eq(Areas::getName, pageWrap.getModel().getName());
        }
        if (pageWrap.getModel().getInfo() != null) {
            queryWrapper.lambda().eq(Areas::getInfo, pageWrap.getModel().getInfo());
        }
        if (pageWrap.getModel().getCode() != null) {
            queryWrapper.lambda().eq(Areas::getCode, pageWrap.getModel().getCode());
        }
        if (pageWrap.getModel().getParentId() != null) {
            queryWrapper.lambda().eq(Areas::getParentId, pageWrap.getModel().getParentId());
        }
        if (pageWrap.getModel().getType() != null) {
            queryWrapper.lambda().eq(Areas::getType, pageWrap.getModel().getType());
        }
        for(PageWrap.SortData sortData: pageWrap.getSorts()) {
            if (sortData.getDirection().equalsIgnoreCase(PageWrap.DESC)) {
                queryWrapper.orderByDesc(sortData.getProperty());
            } else {
                queryWrapper.orderByAsc(sortData.getProperty());
            }
        }
        return PageData.from(areasMapper.selectPage(page, queryWrapper));
    }
    @Override
    public long count(Areas areas) {
        QueryWrapper<Areas> wrapper = new QueryWrapper<>(areas);
        return areasMapper.selectCount(wrapper);
    }
    @Override
    public Areas findByCityAndArea(String cityName, String areasName) {
        Areas city = findByName(cityName,Constants.ONE);
        if(city !=null){
           return  findByNameAndParentId(areasName,Constants.TWO,city.getId());
        }
        return null;
    }
    @Override
    public String getAddress(Integer cityId,Integer areaId){
        Areas cityAreas = findById(cityId, Constants.ONE);
        Areas areas = findById(areaId, Constants.TWO);
        String cityName = Optional.ofNullable(cityAreas)
                .map(s -> s.getProvinceName() + s.getName())
                .orElseThrow(() -> new BusinessException(ResponseStatus.BAD_REQUEST));
        String areaName = Optional.ofNullable(areas).map(s -> s.getName()).orElse("");
        return cityName+areaName;
    }
    @Override
    public String getAddress(Integer areaId) {
        Areas areas = findById(areaId, Constants.TWO);
        String cityName = Optional.ofNullable(areas)
                .map(s -> s.getProvinceName() + s.getCityName())
                .orElseThrow(() -> new BusinessException(ResponseStatus.BAD_REQUEST));
        String areaName = Optional.ofNullable(areas).map(s -> s.getName()).orElse("");
        return cityName+areaName;
    }
    public static Areas getAddressByAreaId(Integer areaId) {
        if(areaId ==null){
            return null;
        }
        if(AREA_LIST!=null){
            for(Areas a : AREA_LIST){
                if(Constants.equalsInteger(a.getId(),areaId)){
                    return a;
//                    return  StringUtils.defaultString(a.getProvinceName(),"")+StringUtils.defaultString(a.getCityName(),"")+StringUtils.defaultString(a.getName(),"")
                }
            }
        }
        return null;
    }
    @Override
    public List<Areas> getCityList(Areas areas)  {
        //查询全部城市数据
        List<Areas>  dataList = findByParentId(null,Constants.ONE,0);
        if (StringUtils.isNotBlank(areas.getCityName())){
            dataList = dataList.stream().filter(s -> s.getName().contains(areas.getCityName())).collect(Collectors.toList());
        }
        if(dataList != null){
            for(Areas c: dataList){
                c.setFullspell(PinYinUtil.getFullSpell(c.getName()));
                c.setFirstSpell(PinYinUtil.getFirstFirstSpell(c.getName()));
            }
            Collections.sort(dataList);
        }
        return dataList;
    }
}
server/services/src/main/java/com/doumee/service/business/impl/BannerServiceImpl.java
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,148 @@
package com.doumee.service.business.impl;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.conditions.update.UpdateWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.doumee.core.constants.Constants;
import com.doumee.core.constants.ResponseStatus;
import com.doumee.core.exception.BusinessException;
import com.doumee.core.model.PageData;
import com.doumee.core.model.PageWrap;
import com.doumee.core.utils.Utils;
import com.doumee.dao.business.BannerMapper;
import com.doumee.dao.business.model.Banner;
import com.doumee.service.business.BannerService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.util.CollectionUtils;
import java.util.List;
import java.util.Objects;
/**
 * è½®æ’­å›¾Service实现
 * @author rk
 * @date 2026/04/08
 */
@Service
public class BannerServiceImpl implements BannerService {
    @Autowired
    private BannerMapper bannerMapper;
    @Override
    public Integer create(Banner banner) {
        bannerMapper.insert(banner);
        return banner.getId();
    }
    @Override
    public void deleteById(Integer id) {
        bannerMapper.deleteById(id);
    }
    @Override
    public void delete(Banner banner) {
        UpdateWrapper<Banner> deleteWrapper = new UpdateWrapper<>(banner);
        bannerMapper.delete(deleteWrapper);
    }
    @Override
    public void deleteByIdInBatch(List<Integer> ids) {
        if (CollectionUtils.isEmpty(ids)) {
            return;
        }
        bannerMapper.deleteBatchIds(ids);
    }
    @Override
    public void updateById(Banner banner) {
        bannerMapper.updateById(banner);
    }
    @Override
    public void updateByIdInBatch(List<Banner> banners) {
        if (CollectionUtils.isEmpty(banners)) {
            return;
        }
        for (Banner banner : banners) {
            this.updateById(banner);
        }
    }
    @Override
    public Banner findById(Integer id) {
        Banner banner = bannerMapper.selectById(id);
        if (Objects.isNull(banner)) {
            throw new BusinessException(ResponseStatus.DATA_EMPTY);
        }
        return banner;
    }
    @Override
    public Banner findOne(Banner banner) {
        QueryWrapper<Banner> wrapper = new QueryWrapper<>(banner);
        return bannerMapper.selectOne(wrapper);
    }
    @Override
    public List<Banner> findList(Banner banner) {
        QueryWrapper<Banner> wrapper = new QueryWrapper<>(banner);
        return bannerMapper.selectList(wrapper);
    }
    @Override
    public PageData<Banner> findPage(PageWrap<Banner> pageWrap) {
        IPage<Banner> page = new Page<>(pageWrap.getPage(), pageWrap.getCapacity());
        QueryWrapper<Banner> queryWrapper = new QueryWrapper<>();
        Utils.MP.blankToNull(pageWrap.getModel());
        pageWrap.getModel().setDeleted(Constants.ZERO);
        if (pageWrap.getModel().getId() != null) {
            queryWrapper.lambda().eq(Banner::getId, pageWrap.getModel().getId());
        }
        if (pageWrap.getModel().getDeleted() != null) {
            queryWrapper.lambda().eq(Banner::getDeleted, pageWrap.getModel().getDeleted());
        }
        if (pageWrap.getModel().getCreateUser() != null) {
            queryWrapper.lambda().eq(Banner::getCreateUser, pageWrap.getModel().getCreateUser());
        }
        if (pageWrap.getModel().getCreateTime() != null) {
            queryWrapper.lambda().ge(Banner::getCreateTime, Utils.Date.getStart(pageWrap.getModel().getCreateTime()));
            queryWrapper.lambda().le(Banner::getCreateTime, Utils.Date.getEnd(pageWrap.getModel().getCreateTime()));
        }
        if (pageWrap.getModel().getUpdateUser() != null) {
            queryWrapper.lambda().eq(Banner::getUpdateUser, pageWrap.getModel().getUpdateUser());
        }
        if (pageWrap.getModel().getUpdateTime() != null) {
            queryWrapper.lambda().ge(Banner::getUpdateTime, Utils.Date.getStart(pageWrap.getModel().getUpdateTime()));
            queryWrapper.lambda().le(Banner::getUpdateTime, Utils.Date.getEnd(pageWrap.getModel().getUpdateTime()));
        }
        if (pageWrap.getModel().getStatus() != null) {
            queryWrapper.lambda().eq(Banner::getStatus, pageWrap.getModel().getStatus());
        }
        if (pageWrap.getModel().getType() != null) {
            queryWrapper.lambda().eq(Banner::getType, pageWrap.getModel().getType());
        }
        if (pageWrap.getModel().getPosition() != null) {
            queryWrapper.lambda().eq(Banner::getPosition, pageWrap.getModel().getPosition());
        }
        if (pageWrap.getModel().getShopId() != null) {
            queryWrapper.lambda().eq(Banner::getShopId, pageWrap.getModel().getShopId());
        }
        for (PageWrap.SortData sortData : pageWrap.getSorts()) {
            if (sortData.getDirection().equalsIgnoreCase(PageWrap.DESC)) {
                queryWrapper.orderByDesc(sortData.getProperty());
            } else {
                queryWrapper.orderByAsc(sortData.getProperty());
            }
        }
        return PageData.from(bannerMapper.selectPage(page, queryWrapper));
    }
    @Override
    public long count(Banner banner) {
        QueryWrapper<Banner> wrapper = new QueryWrapper<>(banner);
        return bannerMapper.selectCount(wrapper);
    }
}
server/services/src/main/java/com/doumee/service/business/impl/DriverInfoServiceImpl.java
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,585 @@
package com.doumee.service.business.impl;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.conditions.update.UpdateWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.doumee.core.constants.Constants;
import com.doumee.core.constants.ResponseStatus;
import com.doumee.core.exception.BusinessException;
import com.doumee.core.model.PageData;
import com.doumee.core.model.PageWrap;
import com.doumee.config.jwt.JwtTokenUtil;
import com.doumee.core.utils.Secure;
import com.doumee.core.utils.Utils;
import com.doumee.dao.business.DriverInfoMapper;
import com.doumee.dao.business.MemberMapper;
import com.doumee.dao.business.MultifileMapper;
import com.doumee.dao.business.SmsrecordMapper;
import com.doumee.dao.business.CategoryMapper;
import com.doumee.dao.business.model.Category;
import com.doumee.dao.business.model.DriverInfo;
import com.doumee.dao.business.model.Member;
import com.doumee.dao.business.model.Multifile;
import com.doumee.dao.business.model.Smsrecord;
import com.doumee.dao.vo.AccountResponse;
import com.doumee.dao.dto.AuditDTO;
import com.doumee.dao.dto.DriverLoginRequest;
import com.doumee.dao.dto.DriverRegisterRequest;
import com.doumee.dao.dto.DriverVerifyRequest;
import com.doumee.service.business.AliSmsService;
import com.doumee.service.business.DriverInfoService;
import com.alibaba.fastjson.JSONObject;
import org.apache.commons.lang3.RandomStringUtils;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.util.CollectionUtils;
import java.util.Calendar;
import java.util.Date;
import java.util.List;
import java.util.Objects;
/**
 * å¸æœºæ³¨å†Œä¿¡æ¯Service实现
 * @author rk
 * @date 2026/04/08
 */
@Service
public class DriverInfoServiceImpl implements DriverInfoService {
    @Autowired
    private DriverInfoMapper driverInfoMapper;
    @Autowired
    private MemberMapper memberMapper;
    @Autowired
    private SmsrecordMapper smsrecordMapper;
    @Autowired
    private JwtTokenUtil jwtTokenUtil;
    @Autowired
    private Secure secure;
    @Autowired
    private RedisTemplate<String, Object> redisTemplate;
    @Autowired
    private MultifileMapper multifileMapper;
    @Autowired
    private CategoryMapper categoryMapper;
    @Override
    public Integer create(DriverInfo driverInfo) {
        driverInfoMapper.insert(driverInfo);
        return driverInfo.getId();
    }
    @Override
    public void deleteById(Integer id) {
        driverInfoMapper.deleteById(id);
    }
    @Override
    public void delete(DriverInfo driverInfo) {
        UpdateWrapper<DriverInfo> deleteWrapper = new UpdateWrapper<>(driverInfo);
        driverInfoMapper.delete(deleteWrapper);
    }
    @Override
    public void deleteByIdInBatch(List<Integer> ids) {
        if (CollectionUtils.isEmpty(ids)) {
            return;
        }
        driverInfoMapper.deleteBatchIds(ids);
    }
    @Override
    public void updateById(DriverInfo driverInfo) {
        driverInfoMapper.updateById(driverInfo);
    }
    @Override
    public void updateByIdInBatch(List<DriverInfo> driverInfos) {
        if (CollectionUtils.isEmpty(driverInfos)) {
            return;
        }
        for (DriverInfo driverInfo : driverInfos) {
            this.updateById(driverInfo);
        }
    }
    @Override
    public DriverInfo findById(Integer id) {
        DriverInfo driverInfo = driverInfoMapper.selectById(id);
        if (Objects.isNull(driverInfo)) {
            throw new BusinessException(ResponseStatus.DATA_EMPTY);
        }
        return driverInfo;
    }
    @Override
    public DriverInfo findOne(DriverInfo driverInfo) {
        QueryWrapper<DriverInfo> wrapper = new QueryWrapper<>(driverInfo);
        return driverInfoMapper.selectOne(wrapper);
    }
    @Override
    public List<DriverInfo> findList(DriverInfo driverInfo) {
        QueryWrapper<DriverInfo> wrapper = new QueryWrapper<>(driverInfo);
        return driverInfoMapper.selectList(wrapper);
    }
    @Override
    public PageData<DriverInfo> findPage(PageWrap<DriverInfo> pageWrap) {
        IPage<DriverInfo> page = new Page<>(pageWrap.getPage(), pageWrap.getCapacity());
        QueryWrapper<DriverInfo> queryWrapper = new QueryWrapper<>();
        Utils.MP.blankToNull(pageWrap.getModel());
        pageWrap.getModel().setDeleted(Constants.ZERO);
        if (pageWrap.getModel().getId() != null) {
            queryWrapper.lambda().eq(DriverInfo::getId, pageWrap.getModel().getId());
        }
        if (pageWrap.getModel().getDeleted() != null) {
            queryWrapper.lambda().eq(DriverInfo::getDeleted, pageWrap.getModel().getDeleted());
        }
        if (pageWrap.getModel().getCreateUser() != null) {
            queryWrapper.lambda().eq(DriverInfo::getCreateUser, pageWrap.getModel().getCreateUser());
        }
        if (pageWrap.getModel().getCreateTime() != null) {
            queryWrapper.lambda().ge(DriverInfo::getCreateTime, Utils.Date.getStart(pageWrap.getModel().getCreateTime()));
            queryWrapper.lambda().le(DriverInfo::getCreateTime, Utils.Date.getEnd(pageWrap.getModel().getCreateTime()));
        }
        if (pageWrap.getModel().getUpdateUser() != null) {
            queryWrapper.lambda().eq(DriverInfo::getUpdateUser, pageWrap.getModel().getUpdateUser());
        }
        if (pageWrap.getModel().getUpdateTime() != null) {
            queryWrapper.lambda().ge(DriverInfo::getUpdateTime, Utils.Date.getStart(pageWrap.getModel().getUpdateTime()));
            queryWrapper.lambda().le(DriverInfo::getUpdateTime, Utils.Date.getEnd(pageWrap.getModel().getUpdateTime()));
        }
        if (pageWrap.getModel().getRemark() != null) {
            queryWrapper.lambda().eq(DriverInfo::getRemark, pageWrap.getModel().getRemark());
        }
        if (pageWrap.getModel().getName() != null) {
            queryWrapper.lambda().like(DriverInfo::getName, pageWrap.getModel().getName());
        }
        if (pageWrap.getModel().getTelephone() != null) {
            queryWrapper.lambda().like(DriverInfo::getTelephone, pageWrap.getModel().getTelephone());
        }
        if (pageWrap.getModel().getIdcard() != null) {
            queryWrapper.lambda().eq(DriverInfo::getIdcard, pageWrap.getModel().getIdcard());
        }
        if (pageWrap.getModel().getMaritalStatus() != null) {
            queryWrapper.lambda().eq(DriverInfo::getMaritalStatus, pageWrap.getModel().getMaritalStatus());
        }
        if (pageWrap.getModel().getCarType() != null) {
            queryWrapper.lambda().eq(DriverInfo::getCarType, pageWrap.getModel().getCarType());
        }
        if (pageWrap.getModel().getCarCode() != null) {
            queryWrapper.lambda().like(DriverInfo::getCarCode, pageWrap.getModel().getCarCode());
        }
        if (pageWrap.getModel().getCardStartDate() != null) {
            queryWrapper.lambda().ge(DriverInfo::getCardStartDate, Utils.Date.getStart(pageWrap.getModel().getCardStartDate()));
            queryWrapper.lambda().le(DriverInfo::getCardStartDate, Utils.Date.getEnd(pageWrap.getModel().getCardStartDate()));
        }
        if (pageWrap.getModel().getCardEndDate() != null) {
            queryWrapper.lambda().ge(DriverInfo::getCardEndDate, Utils.Date.getStart(pageWrap.getModel().getCardEndDate()));
            queryWrapper.lambda().le(DriverInfo::getCardEndDate, Utils.Date.getEnd(pageWrap.getModel().getCardEndDate()));
        }
        if (pageWrap.getModel().getStatus() != null) {
            queryWrapper.lambda().eq(DriverInfo::getStatus, pageWrap.getModel().getStatus());
        }
        if (pageWrap.getModel().getAuditTime() != null) {
            queryWrapper.lambda().ge(DriverInfo::getAuditTime, Utils.Date.getStart(pageWrap.getModel().getAuditTime()));
            queryWrapper.lambda().le(DriverInfo::getAuditTime, Utils.Date.getEnd(pageWrap.getModel().getAuditTime()));
        }
        if (pageWrap.getModel().getAuditUser() != null) {
            queryWrapper.lambda().eq(DriverInfo::getAuditUser, pageWrap.getModel().getAuditUser());
        }
        if (pageWrap.getModel().getMemberId() != null) {
            queryWrapper.lambda().eq(DriverInfo::getMemberId, pageWrap.getModel().getMemberId());
        }
        for (PageWrap.SortData sortData : pageWrap.getSorts()) {
            if (sortData.getDirection().equalsIgnoreCase(PageWrap.DESC)) {
                queryWrapper.orderByDesc(sortData.getProperty());
            } else {
                queryWrapper.orderByAsc(sortData.getProperty());
            }
        }
        return PageData.from(driverInfoMapper.selectPage(page, queryWrapper));
    }
    @Override
    public long count(DriverInfo driverInfo) {
        QueryWrapper<DriverInfo> wrapper = new QueryWrapper<>(driverInfo);
        return driverInfoMapper.selectCount(wrapper);
    }
    /***************司机验证码登录业务*************/
    @Override
    public void sendRegisterCode(String telephone) {
        if (StringUtils.isBlank(telephone)) {
            throw new BusinessException(ResponseStatus.BAD_REQUEST);
        }
        // ç”Ÿæˆ6位数字验证码
        String code = RandomStringUtils.randomNumeric(6);
        // å‘送短信
        String templateParam = "{\"code\":\"" + code + "\"}";
        AliSmsService.sendSms(telephone, "SMS_491325122", templateParam);
        // ä¿å­˜çŸ­ä¿¡è®°å½•
        Smsrecord smsrecord = new Smsrecord();
        smsrecord.setDeleted(Constants.ZERO);
        smsrecord.setCreateTime(new Date());
        smsrecord.setUpdateTime(new Date());
        smsrecord.setPhone(telephone);
        smsrecord.setContent("司机验证码登录:" + code);
        smsrecord.setType(Constants.ZERO);
        smsrecord.setCode(code);
        smsrecord.setStatus(Constants.ZERO);
        // æœ‰æ•ˆæœŸ15分钟
        Calendar calendar = Calendar.getInstance();
        calendar.setTime(new Date());
        calendar.add(Calendar.MINUTE, 15);
        smsrecord.setValidDate(calendar.getTime());
        smsrecordMapper.insert(smsrecord);
    }
    @Override
    @Transactional
    public AccountResponse register(DriverRegisterRequest request) {
        String telephone = request.getTelephone();
        String code = request.getCode();
        if (StringUtils.isAnyBlank(telephone, code)) {
            throw new BusinessException(ResponseStatus.BAD_REQUEST);
        }
        // 1. éªŒè¯çŸ­ä¿¡éªŒè¯ç 
        QueryWrapper<Smsrecord> smsWrapper = new QueryWrapper<>();
        smsWrapper.lambda().eq(Smsrecord::getPhone, telephone)
                .eq(Smsrecord::getCode, code)
                .eq(Smsrecord::getType, Constants.ZERO)
                .eq(Smsrecord::getStatus, Constants.ZERO)
                .ge(Smsrecord::getValidDate, new Date())
                .orderByDesc(Smsrecord::getCreateTime)
                .last("limit 1");
        Smsrecord smsrecord = smsrecordMapper.selectOne(smsWrapper);
        if (Objects.isNull(smsrecord)) {
            throw new BusinessException(ResponseStatus.NOT_ALLOWED.getCode(), "验证码错误或已过期");
        }
        // æ ‡è®°éªŒè¯ç å·²ä½¿ç”¨
        smsrecord.setStatus(Constants.ONE);
        smsrecord.setUpdateTime(new Date());
        smsrecordMapper.updateById(smsrecord);
        // 2. æŸ¥è¯¢æ˜¯å¦å·²æœ‰å¸æœºè´¦å·
        Member existMember = memberMapper.selectOne(new QueryWrapper<Member>().lambda()
                .eq(Member::getTelephone, telephone)
                .eq(Member::getUserType, Constants.ONE)
                .ne(Member::getStatus, Constants.TWO)
                .last("limit 1"));
        Date now = new Date();
        Member member;
        if (Objects.nonNull(existMember)) {
            // å·²æœ‰å¸æœºè´¦å·ï¼Œç›´æŽ¥ç™»å½•
            if (!Constants.equalsInteger(existMember.getStatus(), Constants.ZERO)) {
                throw new BusinessException(ResponseStatus.NOT_ALLOWED.getCode(), "账号已停用,请联系管理员");
            }
            // æ›´æ–°ç™»å½•信息
            memberMapper.update(new UpdateWrapper<Member>().lambda()
                    .set(Member::getLoginTime, now)
                    .setSql("login_times = login_times + 1")
                    .eq(Member::getId, existMember.getId()));
            // æ›´æ–°å†…存中的登录信息
            existMember.setLoginTime(now);
            existMember.setLoginTimes(existMember.getLoginTimes() + 1);
            member = existMember;
        } else {
            // æ²¡æœ‰å¸æœºè´¦å·ï¼Œæ³¨å†Œæ–°ç”¨æˆ·ï¼Œé»˜è®¤å¯†ç ä¸ºæ‰‹æœºå·åŽå…­ä½
            String salt = RandomStringUtils.randomAlphanumeric(6);
            String defaultPassword = telephone.substring(telephone.length() - 6);
            member = new Member();
            member.setDeleted(Constants.ZERO);
            member.setCreateTime(now);
            member.setUpdateTime(now);
            member.setTelephone(telephone);
            member.setNickName(telephone);
            member.setName(telephone);
            member.setUserType(Constants.ONE);
            member.setDriverStatus(Constants.ZERO);
            member.setPassword(secure.encryptPassword(defaultPassword, salt));
            member.setSalt(salt);
            member.setWorkerIdentity(Constants.ZERO);
            member.setDriverIdentity(Constants.ZERO);
            member.setChefIdentity(Constants.ZERO);
            member.setAmount(Constants.ZERO.longValue());
            member.setTotalAmount(Constants.ZERO.longValue());
            member.setStatus(Constants.ZERO);
            member.setLoginTime(now);
            member.setLoginTimes(Constants.ONE.longValue());
            member.setReceiveNum(Constants.ZERO.longValue());
            member.setPublishNum(Constants.ZERO.longValue());
            member.setAutoReceiveStatus(Constants.ONE);
            member.setUseIdentity(Constants.ZERO);
            memberMapper.insert(member);
            // åˆ›å»ºå¸æœºåŸºç¡€ä¿¡æ¯ï¼ˆstatus=0,注册状态)
            DriverInfo driverInfo = new DriverInfo();
            driverInfo.setDeleted(Constants.ZERO);
            driverInfo.setCreateTime(now);
            driverInfo.setUpdateTime(now);
            driverInfo.setTelephone(telephone);
            driverInfo.setMemberId(member.getId());
            driverInfo.setStatus(Constants.ZERO);
            driverInfoMapper.insert(driverInfo);
        }
        // 3. ç”Ÿæˆtoken返回
        AccountResponse accountResponse = new AccountResponse();
        accountResponse.setToken(JwtTokenUtil.generateTokenForRedis(member.getId(), Constants.ONE, JSONObject.toJSONString(member), redisTemplate));
        accountResponse.setMember(member);
        return accountResponse;
    }
    @Override
    public AccountResponse login(DriverLoginRequest request) {
        String telephone = request.getTelephone();
        String password = request.getPassword();
        if (StringUtils.isAnyBlank(telephone, password)) {
            throw new BusinessException(ResponseStatus.BAD_REQUEST);
        }
        // æŸ¥è¯¢å¸æœºä¼šå‘˜
        Member member = memberMapper.selectOne(new QueryWrapper<Member>().lambda()
                .eq(Member::getTelephone, telephone)
                .eq(Member::getUserType, Constants.ONE)
                .ne(Member::getStatus, Constants.TWO)
                .last("limit 1"));
        if (Objects.isNull(member)) {
            throw new BusinessException(ResponseStatus.NOT_ALLOWED.getCode(), "账号不存在");
        }
        if (!Constants.equalsInteger(member.getStatus(), Constants.ZERO)) {
            throw new BusinessException(ResponseStatus.NOT_ALLOWED.getCode(), "账号已停用,请联系管理员");
        }
        // æ ¡éªŒå¯†ç 
        String encryptPwd = secure.encryptPassword(password, member.getSalt());
        if (!encryptPwd.equals(member.getPassword())) {
            throw new BusinessException(ResponseStatus.NOT_ALLOWED.getCode(), "密码错误");
        }
        // æ›´æ–°ç™»å½•信息
        memberMapper.update(new UpdateWrapper<Member>().lambda()
                .set(Member::getLoginTime, new Date())
                .setSql("login_times = login_times + 1")
                .eq(Member::getId, member.getId()));
        AccountResponse accountResponse = new AccountResponse();
        accountResponse.setToken(JwtTokenUtil.generateTokenForRedis(member.getId(), Constants.ONE, JSONObject.toJSONString(member), redisTemplate));
        accountResponse.setMember(member);
        return accountResponse;
    }
    /***************司机实名认证业务*************/
    @Override
    @Transactional
    public void submitVerify(Integer memberId, DriverVerifyRequest request) {
        // å‚数基础校验
        if (StringUtils.isAnyBlank(request.getName(), request.getIdcard(), request.getLivePlace(),
                request.getCarCode(), request.getIdcardImg(), request.getIdcardImgBack())) {
            throw new BusinessException(ResponseStatus.BAD_REQUEST);
        }
        if (request.getMaritalStatus() == null || request.getCarType() == null) {
            throw new BusinessException(ResponseStatus.BAD_REQUEST);
        }
        // èº«ä»½è¯å·æ ¼å¼æ ¡éªŒï¼ˆ18位,最后一位可为X)
        if (!request.getIdcard().matches("^[1-9]\\d{5}(18|19|20)\\d{2}(0[1-9]|1[0-2])(0[1-9]|[12]\\d|3[01])\\d{3}[\\dXx]$")) {
            throw new BusinessException(ResponseStatus.NOT_ALLOWED.getCode(), "身份证号格式不正确");
        }
        // æŸ¥è¯¢å¸æœºä¿¡æ¯
        DriverInfo driverInfo = driverInfoMapper.selectOne(new QueryWrapper<DriverInfo>().lambda()
                .eq(DriverInfo::getMemberId, memberId)
                .eq(DriverInfo::getDeleted, Constants.ZERO)
                .last("limit 1"));
        if (Objects.isNull(driverInfo)) {
            throw new BusinessException(ResponseStatus.DATA_EMPTY);
        }
        // çŠ¶æ€æ ¡éªŒï¼šstatus=0(注册)或status=3(审批驳回)可提交认证
        if (driverInfo.getStatus() != null
                && !Constants.equalsInteger(driverInfo.getStatus(), Constants.ZERO)
                && !Constants.equalsInteger(driverInfo.getStatus(), Constants.THREE)) {
            throw new BusinessException(ResponseStatus.NOT_ALLOWED.getCode(), "当前状态不允许提交认证");
        }
        // æ ¹æ®è½¦è¾†ç±»åž‹åˆ¤æ–­æ˜¯å¦éœ€è¦é©¾é©¶è¯
        Category category = categoryMapper.selectById(request.getCarType());
        if (Objects.isNull(category) || !Constants.equalsInteger(category.getType(), Constants.ONE)) {
            throw new BusinessException(ResponseStatus.NOT_ALLOWED.getCode(), "车辆类型不存在");
        }
        boolean needLicense = Constants.equalsInteger(Integer.valueOf(category.getOtherField()), Constants.ONE);
        if (needLicense) {
            if (request.getCardStartDate() == null || request.getCardEndDate() == null) {
                throw new BusinessException(ResponseStatus.NOT_ALLOWED.getCode(), "该车辆类型需要填写驾驶证有效期");
            }
            if (request.getLicenseImgUrls() == null || request.getLicenseImgUrls().isEmpty()) {
                throw new BusinessException(ResponseStatus.NOT_ALLOWED.getCode(), "该车辆类型需要上传驾驶证照片");
            }
        }
        // è½¦è¾†ç…§ç‰‡å¿…å¡«
        if (request.getCarImgUrls() == null || request.getCarImgUrls().isEmpty()) {
            throw new BusinessException(ResponseStatus.NOT_ALLOWED.getCode(), "请上传车辆照片");
        }
        // ç…§ç‰‡æ•°é‡æ ¡éªŒ
        if (request.getCarImgUrls().size() > 3) {
            throw new BusinessException(ResponseStatus.NOT_ALLOWED.getCode(), "车辆照片最多上传3å¼ ");
        }
        if (request.getLicenseImgUrls() != null && request.getLicenseImgUrls().size() > 3) {
            throw new BusinessException(ResponseStatus.NOT_ALLOWED.getCode(), "驾驶证照片最多上传3å¼ ");
        }
        if (request.getOtherImgUrls() != null && request.getOtherImgUrls().size() > 3) {
            throw new BusinessException(ResponseStatus.NOT_ALLOWED.getCode(), "其他资料照片最多上传3å¼ ");
        }
        // æ›´æ–°å¸æœºä¿¡æ¯
        Date now = new Date();
        driverInfoMapper.update(new UpdateWrapper<DriverInfo>().lambda()
                .set(DriverInfo::getName, request.getName())
                .set(DriverInfo::getIdcard, request.getIdcard())
                .set(DriverInfo::getMaritalStatus, request.getMaritalStatus())
                .set(DriverInfo::getAreaId, request.getAreaId())
                .set(DriverInfo::getLivePlace, request.getLivePlace())
                .set(DriverInfo::getCarCode, request.getCarCode())
                .set(DriverInfo::getCarType, request.getCarType())
                .set(DriverInfo::getCarColor, request.getCarColor())
                .set(DriverInfo::getCardStartDate, request.getCardStartDate())
                .set(DriverInfo::getCardEndDate, request.getCardEndDate())
                .set(DriverInfo::getIdcardImg, request.getIdcardImg())
                .set(DriverInfo::getIdcardImgBack, request.getIdcardImgBack())
                .set(DriverInfo::getStatus, Constants.ONE)
                .set(DriverInfo::getUpdateTime, now)
                .set(DriverInfo::getAuditRemark, null)
                .set(DriverInfo::getAuditTime, null)
                .eq(DriverInfo::getId, driverInfo.getId()));
        // åˆ é™¤æ—§çš„照片记录
        multifileMapper.delete(new QueryWrapper<Multifile>().lambda()
                .eq(Multifile::getObjId, driverInfo.getId())
                .in(Multifile::getObjType, 6, 7, 8));
        // ä¿å­˜è½¦è¾†ç…§ç‰‡ objType=6
        saveMultifileList(driverInfo.getId(), 6, request.getCarImgUrls(), now);
        // ä¿å­˜é©¾é©¶è¯ç…§ç‰‡ objType=7
        if (!CollectionUtils.isEmpty(request.getLicenseImgUrls())) {
            saveMultifileList(driverInfo.getId(), 7, request.getLicenseImgUrls(), now);
        }
        // ä¿å­˜å…¶ä»–资料照片 objType=8
        if (!CollectionUtils.isEmpty(request.getOtherImgUrls())) {
            saveMultifileList(driverInfo.getId(), 8, request.getOtherImgUrls(), now);
        }
        // æ›´æ–°ä¼šå‘˜å¸æœºè®¤è¯çŠ¶æ€ä¸ºè®¤è¯ä¸­
        memberMapper.update(new UpdateWrapper<Member>().lambda()
                .set(Member::getDriverStatus, Constants.ONE)
                .set(Member::getUpdateTime, now)
                .eq(Member::getId, memberId));
    }
    @Override
    public DriverInfo getVerifyDetail(Integer memberId) {
        DriverInfo driverInfo = driverInfoMapper.selectOne(new QueryWrapper<DriverInfo>().lambda()
                .eq(DriverInfo::getMemberId, memberId)
                .eq(DriverInfo::getDeleted, Constants.ZERO)
                .last("limit 1"));
        if (Objects.isNull(driverInfo)) {
            throw new BusinessException(ResponseStatus.DATA_EMPTY);
        }
        // æŸ¥è¯¢è½¦è¾†ç±»åž‹åç§°å’Œæ˜¯å¦éœ€è¦é©¾é©¶è¯
        if (driverInfo.getCarType() != null) {
            Category category = categoryMapper.selectById(driverInfo.getCarType());
            if (Objects.nonNull(category)) {
                driverInfo.setCarTypeName(category.getName());
                driverInfo.setNeedLicense(Constants.equalsInteger(Integer.valueOf(category.getOtherField()), Constants.ONE) ? Constants.ONE : Constants.ZERO);
            }
        }
        // æŸ¥è¯¢ç…§ç‰‡åˆ—表
        List<Multifile> multifileList = multifileMapper.selectList(new QueryWrapper<Multifile>().lambda()
                .eq(Multifile::getObjId, driverInfo.getId())
                .in(Multifile::getObjType, 6, 7, 8)
                .orderByAsc(Multifile::getSortnum));
        if (!CollectionUtils.isEmpty(multifileList)) {
            for (Multifile mf : multifileList) {
                if (Constants.equalsInteger(mf.getObjType(), 6)) {
                    driverInfo.getCarImgList().add(mf);
                } else if (Constants.equalsInteger(mf.getObjType(), 7)) {
                    driverInfo.getLicenseImgList().add(mf);
                } else if (Constants.equalsInteger(mf.getObjType(), 8)) {
                    driverInfo.getOtherImgList().add(mf);
                }
            }
        }
        return driverInfo;
    }
    @Override
    @Transactional
    public void auditVerify(AuditDTO auditDTO) {
        if (Objects.isNull(auditDTO.getId()) || Objects.isNull(auditDTO.getAuditStatus())) {
            throw new BusinessException(ResponseStatus.BAD_REQUEST);
        }
        DriverInfo driverInfo = driverInfoMapper.selectById(auditDTO.getId());
        if (Objects.isNull(driverInfo)) {
            throw new BusinessException(ResponseStatus.DATA_EMPTY);
        }
        // åªæœ‰çŠ¶æ€ä¸º1(待审批)且已填写认证信息才能审批
        if (!Constants.equalsInteger(driverInfo.getStatus(), Constants.ONE)
                || StringUtils.isBlank(driverInfo.getIdcard())) {
            throw new BusinessException(ResponseStatus.NOT_ALLOWED.getCode(), "当前状态不允许审批");
        }
        Date now = new Date();
        // å®¡æ‰¹ç»“果:auditDTO.auditStatus 0=通过→driverInfo.status=2,1=拒绝→driverInfo.status=3
        Integer newStatus;
        if (Constants.equalsInteger(auditDTO.getAuditStatus(), Constants.ZERO)) {
            newStatus = Constants.TWO;  // å®¡æ‰¹é€šè¿‡
        } else if (Constants.equalsInteger(auditDTO.getAuditStatus(), Constants.ONE)) {
            newStatus = Constants.THREE;  // å®¡æ‰¹é©³å›ž
        } else {
            throw new BusinessException(ResponseStatus.NOT_ALLOWED.getCode(), "审批状态参数错误");
        }
        // æ›´æ–°å¸æœºçŠ¶æ€
        driverInfoMapper.update(new UpdateWrapper<DriverInfo>().lambda()
                .set(DriverInfo::getStatus, newStatus)
                .set(DriverInfo::getAuditTime, now)
                .set(DriverInfo::getAuditRemark, auditDTO.getAuditRemark())
                .set(DriverInfo::getAuditUser, auditDTO.getAuditUser())
                .set(DriverInfo::getUpdateTime, now)
                .eq(DriverInfo::getId, auditDTO.getId()));
        // æ›´æ–°ä¼šå‘˜å¸æœºè®¤è¯çŠ¶æ€ï¼šé€šè¿‡=2,驳回=3
        Integer driverStatus = Constants.equalsInteger(newStatus, Constants.TWO) ? Constants.TWO : Constants.THREE;
        memberMapper.update(new UpdateWrapper<Member>().lambda()
                .set(Member::getDriverStatus, driverStatus)
                .set(Member::getUpdateTime, now)
                .eq(Member::getId, driverInfo.getMemberId()));
    }
    /**
     * æ‰¹é‡ä¿å­˜é™„件记录
     */
    private void saveMultifileList(Integer objId, Integer objType, List<String> urls, Date now) {
        int sortNum = 0;
        for (String url : urls) {
            Multifile multifile = new Multifile();
            multifile.setObjId(objId);
            multifile.setObjType(objType);
            multifile.setType(Constants.ZERO);
            multifile.setFileurl(url);
            multifile.setIsdeleted(Constants.ZERO);
            multifile.setCreateDate(now);
            multifile.setSortnum(sortNum++);
            multifileMapper.insert(multifile);
        }
    }
}
server/services/src/main/java/com/doumee/service/business/impl/MemberServiceImpl.java
@@ -69,6 +69,10 @@
    @Autowired
    private SystemDictDataBiz systemDictDataBiz;
    @Autowired
    private RedisTemplate<String,Object> redisTemplate;
    @Override
    public Integer create(Member member) {
        memberMapper.insert(member);
@@ -271,13 +275,18 @@
            if (StringUtils.isBlank(openId)) {
                throw new BusinessException(ResponseStatus.NOT_ALLOWED.getCode(), "获取openid失败!请联系管理员");
            }
            Member member = memberMapper.selectOne(new QueryWrapper<Member>().eq("openid", openId).eq("DELETED", Constants.ZERO).last("limit 1"));
            Member member = memberMapper.selectOne(new QueryWrapper<Member>().lambda().eq(Member::getOpenid, openId).eq(Member::getUserType,Constants.ZERO)
                    .eq(Member::getDeleted, Constants.ZERO).ne(Member::getStatus, Constants.TWO).last("limit 1"));
            AccountResponse accountResponse = new AccountResponse();
            accountResponse.setOpenid(openId);
            if(Objects.isNull(member)){
                return accountResponse;
            }
            accountResponse.setToken(jwtTokenUtil.generateToken(member));
            if(!Constants.equalsInteger(member.getStatus(),Constants.ZERO)){
                throw new BusinessException(ResponseStatus.NOT_ALLOWED.getCode(), "对不起,账号已禁用,请联系管理员!");
            }
            String token = JwtTokenUtil.generateTokenForRedis(member.getId(), Constants.ZERO, JSONObject.toJSONString(member), redisTemplate);
            accountResponse.setToken(token);
            accountResponse.setMember(member);
            return accountResponse;
        } catch (WxErrorException e) {
@@ -301,8 +310,12 @@
            if(Objects.isNull(mobile)){
                throw new BusinessException(ResponseStatus.NOT_ALLOWED.getCode(),"未获取到手机号");
            }
            Member member =  memberMapper.selectOne(new QueryWrapper<Member>().lambda().eq(Member::getTelephone,mobile).last("limit 1"));
            Member member =  memberMapper.selectOne(new QueryWrapper<Member>().lambda().eq(Member::getTelephone,mobile).eq(Member::getUserType,Constants.ZERO)
                    .ne(Member::getStatus, Constants.TWO).last("limit 1"));
            if(Objects.nonNull(member)){
                if(!Constants.equalsInteger(member.getStatus(),Constants.ZERO)){
                    throw new BusinessException(ResponseStatus.NOT_ALLOWED.getCode(), "对不起,账号已禁用,请联系管理员!");
                }
                memberMapper.update(new UpdateWrapper<Member>().lambda().set(Member::getTelephone,mobile)
                        .set(Member::getOpenid,wxPhoneRequest.getOpenid()).set(Member::getUpdateTime,new Date()).eq(Member::getId,member.getId()));
            }else{
@@ -328,8 +341,9 @@
                member.setUseIdentity(Constants.ZERO);
                memberMapper.insert(member);
            }
            String token = JwtTokenUtil.generateTokenForRedis(member.getId(), Constants.ZERO, JSONObject.toJSONString(member), redisTemplate);
            AccountResponse accountResponse = new AccountResponse();
            accountResponse.setToken(jwtTokenUtil.generateToken(member));
            accountResponse.setToken(token);
            accountResponse.setMember(member);
            return accountResponse;
        } catch (Exception e) {
@@ -359,25 +373,25 @@
    }
    @Override
    public void editUseIdentity(Member member){
        if(Objects.isNull(member)
                || Objects.isNull(member.getUseIdentity())){
            throw new BusinessException(ResponseStatus.BAD_REQUEST);
        }
        if(Constants.equalsInteger(member.getUseIdentity(),Constants.ZERO)){
            member.setUseIdentity(Constants.ZERO);
            memberMapper.update(new UpdateWrapper<Member>().lambda().set(Member::getUseIdentity,Constants.ZERO).eq(Member::getId,member.getId()));
        }else{
            if(identityInfoMapper.selectCount(new QueryWrapper<IdentityInfo>().lambda().eq(IdentityInfo::getDeleted,Constants.ZERO)
                    .eq(IdentityInfo::getMemberId,member.getId())
                    .eq(IdentityInfo::getAuditStatus,Constants.TWO))>Constants.ZERO){
                memberMapper.update(new UpdateWrapper<Member>().lambda().set(Member::getUseIdentity,Constants.ONE).eq(Member::getId,member.getId()));
            }else{
                throw new BusinessException(ResponseStatus.NOT_ALLOWED.getCode(),"当前无可用接单身份!");
            }
        }
    }
//    @Override
//    public void editUseIdentity(Member member){
//        if(Objects.isNull(member)
//                || Objects.isNull(member.getUseIdentity())){
//            throw new BusinessException(ResponseStatus.BAD_REQUEST);
//        }
//        if(Constants.equalsInteger(member.getUseIdentity(),Constants.ZERO)){
//            member.setUseIdentity(Constants.ZERO);
//            memberMapper.update(new UpdateWrapper<Member>().lambda().set(Member::getUseIdentity,Constants.ZERO).eq(Member::getId,member.getId()));
//        }else{
//            if(identityInfoMapper.selectCount(new QueryWrapper<IdentityInfo>().lambda().eq(IdentityInfo::getDeleted,Constants.ZERO)
//                    .eq(IdentityInfo::getMemberId,member.getId())
//                    .eq(IdentityInfo::getAuditStatus,Constants.TWO))>Constants.ZERO){
//                memberMapper.update(new UpdateWrapper<Member>().lambda().set(Member::getUseIdentity,Constants.ONE).eq(Member::getId,member.getId()));
//            }else{
//                throw new BusinessException(ResponseStatus.NOT_ALLOWED.getCode(),"当前无可用接单身份!");
//            }
//        }
//    }
    @Override
@@ -391,29 +405,29 @@
                    +systemDictDataBiz.queryByCode(Constants.SYSTEM,Constants.MEMBER_FILES).getCode();
            member.setFullCoverImage(path + member.getCoverImage());
        }
        UserCenterVO userCenterVO = new UserCenterVO();
        userCenterVO.setReleaseTaskTotal(Constants.ZERO);
        userCenterVO.setWaitReceiveTotal(Constants.ZERO);
        userCenterVO.setDoingTotal(Constants.ZERO);
        userCenterVO.setWaitCommentTotal(Constants.ZERO);
        userCenterVO.setTaskingTotal(Constants.ZERO);
        userCenterVO.setDoneTotal(Constants.ZERO);
        userCenterVO.setReceiveTotal(Constants.ZERO);
        List<Orders> releaseOrders = ordersMapper.selectList(new QueryWrapper<Orders>().lambda().eq(Orders::getDeleted,Constants.ZERO)
                .eq(Orders::getReleaseMemberId,member.getId()));
        if(com.github.xiaoymin.knife4j.core.util.CollectionUtils.isNotEmpty(releaseOrders)){
            userCenterVO.setReleaseTaskTotal(releaseOrders.size());
            userCenterVO.setWaitCommentTotal(releaseOrders.stream().filter(i->Constants.equalsInteger(i.getStatus(),Constants.ordersStatus.done.getKey())&&Constants.equalsInteger(i.getCommentStatus(),Constants.ZERO)).collect(Collectors.toList()).size());
            userCenterVO.setDoingTotal(releaseOrders.stream().filter(i->Constants.equalsInteger(i.getStatus(),Constants.ordersStatus.doing.getKey())).collect(Collectors.toList()).size());
            userCenterVO.setWaitReceiveTotal(releaseOrders.stream().filter(i->Constants.equalsInteger(i.getStatus(),Constants.ordersStatus.wait.getKey())).collect(Collectors.toList()).size());
        }
        List<Orders> acceptOrders = ordersMapper.selectList(new QueryWrapper<Orders>().lambda().eq(Orders::getDeleted,Constants.ZERO).eq(Orders::getAcceptMemberId,member.getId()));
        if(com.github.xiaoymin.knife4j.core.util.CollectionUtils.isNotEmpty(acceptOrders)){
            userCenterVO.setReceiveTotal(acceptOrders.size());
            userCenterVO.setTaskingTotal(acceptOrders.stream().filter(i->Constants.equalsInteger(i.getStatus(),Constants.ordersStatus.doing.getKey())).collect(Collectors.toList()).size());
            userCenterVO.setDoneTotal(acceptOrders.stream().filter(i->Constants.equalsInteger(i.getStatus(),Constants.ordersStatus.done.getKey())).collect(Collectors.toList()).size());
        }
        member.setUserCenterVO(userCenterVO);
//        UserCenterVO userCenterVO = new UserCenterVO();
//        userCenterVO.setReleaseTaskTotal(Constants.ZERO);
//        userCenterVO.setWaitReceiveTotal(Constants.ZERO);
//        userCenterVO.setDoingTotal(Constants.ZERO);
//        userCenterVO.setWaitCommentTotal(Constants.ZERO);
//        userCenterVO.setTaskingTotal(Constants.ZERO);
//        userCenterVO.setDoneTotal(Constants.ZERO);
//        userCenterVO.setReceiveTotal(Constants.ZERO);
//        List<Orders> releaseOrders = ordersMapper.selectList(new QueryWrapper<Orders>().lambda().eq(Orders::getDeleted,Constants.ZERO)
//                .eq(Orders::getReleaseMemberId,member.getId()));
//        if(com.github.xiaoymin.knife4j.core.util.CollectionUtils.isNotEmpty(releaseOrders)){
//            userCenterVO.setReleaseTaskTotal(releaseOrders.size());
//            userCenterVO.setWaitCommentTotal(releaseOrders.stream().filter(i->Constants.equalsInteger(i.getStatus(),Constants.ordersStatus.done.getKey())&&Constants.equalsInteger(i.getCommentStatus(),Constants.ZERO)).collect(Collectors.toList()).size());
//            userCenterVO.setDoingTotal(releaseOrders.stream().filter(i->Constants.equalsInteger(i.getStatus(),Constants.ordersStatus.doing.getKey())).collect(Collectors.toList()).size());
//            userCenterVO.setWaitReceiveTotal(releaseOrders.stream().filter(i->Constants.equalsInteger(i.getStatus(),Constants.ordersStatus.wait.getKey())).collect(Collectors.toList()).size());
//        }
//        List<Orders> acceptOrders = ordersMapper.selectList(new QueryWrapper<Orders>().lambda().eq(Orders::getDeleted,Constants.ZERO).eq(Orders::getAcceptMemberId,member.getId()));
//        if(com.github.xiaoymin.knife4j.core.util.CollectionUtils.isNotEmpty(acceptOrders)){
//            userCenterVO.setReceiveTotal(acceptOrders.size());
//            userCenterVO.setTaskingTotal(acceptOrders.stream().filter(i->Constants.equalsInteger(i.getStatus(),Constants.ordersStatus.doing.getKey())).collect(Collectors.toList()).size());
//            userCenterVO.setDoneTotal(acceptOrders.stream().filter(i->Constants.equalsInteger(i.getStatus(),Constants.ordersStatus.done.getKey())).collect(Collectors.toList()).size());
//        }
//        member.setUserCenterVO(userCenterVO);
        return member;
    }
@@ -424,20 +438,33 @@
    public UserCenterVO getPlatformAboutUs(){
        UserCenterVO userCenterVO = new UserCenterVO();
        userCenterVO.setAboutUs(StringUtils.trimToNull(systemDictDataBiz.queryByCode(Constants.SYSTEM,Constants.ABOUT_US).getCode()));
        userCenterVO.setFeeStandards(StringUtils.trimToNull(systemDictDataBiz.queryByCode(Constants.SYSTEM,Constants.FEE_STANDARDS).getCode()));
        userCenterVO.setServerIntroduce(StringUtils.trimToNull(systemDictDataBiz.queryByCode(Constants.SYSTEM,Constants.SERVER_INTRODUCE).getCode()));
        userCenterVO.setServerPhone(StringUtils.trimToNull(systemDictDataBiz.queryByCode(Constants.SYSTEM,Constants.SERVER_PHONE).getCode()));
        userCenterVO.setUserAgreement(StringUtils.trimToNull(systemDictDataBiz.queryByCode(Constants.SYSTEM,Constants.USER_AGREEMENT).getCode()));
        userCenterVO.setPrivacyAgreement(StringUtils.trimToNull(systemDictDataBiz.queryByCode(Constants.SYSTEM,Constants.PRIVACY_AGREEMENT).getCode()));
//        userCenterVO.setFeeStandards(StringUtils.trimToNull(systemDictDataBiz.queryByCode(Constants.SYSTEM,Constants.FEE_STANDARDS).getCode()));
//        userCenterVO.setServerIntroduce(StringUtils.trimToNull(systemDictDataBiz.queryByCode(Constants.SYSTEM,Constants.SERVER_INTRODUCE).getCode()));
//        userCenterVO.setServerPhone(StringUtils.trimToNull(systemDictDataBiz.queryByCode(Constants.SYSTEM,Constants.SERVER_PHONE).getCode()));
        return userCenterVO;
    }
    @Override
    public void logOff(String token,Integer memberId){
    public void logOut(String token,Integer memberId){
        memberMapper.update(new UpdateWrapper<Member>().lambda().setSql(" openid = null ").eq(Member::getId,memberId));
        jwtTokenUtil.logoutForH5(token);
    }
    @Override
    public void logOff(String token,Integer memberId){
        Member  member = memberMapper.selectById(memberId);
        if(Objects.nonNull(member)){
            memberMapper.update(new UpdateWrapper<Member>().lambda()
//                    .set(Member::getOpenId,null)
                            .set(Member::getStatus,Constants.TWO)
                            .eq(Member::getId,member.getId())
            );
        }
        redisTemplate.delete(token);
    }
}
server/services/src/main/java/com/doumee/service/business/impl/PricingRuleServiceImpl.java
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,602 @@
package com.doumee.service.business.impl;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.conditions.update.UpdateWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.doumee.core.constants.Constants;
import com.doumee.core.constants.ResponseStatus;
import com.doumee.core.exception.BusinessException;
import com.doumee.core.model.PageData;
import com.doumee.core.model.PageWrap;
import com.doumee.core.utils.Utils;
import com.doumee.dao.business.CategoryMapper;
import com.doumee.dao.business.PricingRuleMapper;
import com.doumee.dao.business.model.Category;
import com.doumee.dao.business.model.PricingRule;
import com.doumee.dao.dto.LocalStoragePricingItemDTO;
import com.doumee.dao.dto.LocalStoragePricingSaveDTO;
import com.doumee.dao.dto.RemoteDeliveryPricingItemDTO;
import com.doumee.dao.dto.RemoteDeliveryPricingSaveDTO;
import com.doumee.dao.dto.EstimatedDeliverySaveDTO;
import com.doumee.dao.dto.StoreDepositItemDTO;
import com.doumee.dao.dto.StoreDepositSaveDTO;
import com.doumee.dao.dto.RevenueShareItemDTO;
import com.doumee.dao.dto.RevenueShareSaveDTO;
import com.doumee.dao.vo.LocalStoragePricingVO;
import com.doumee.dao.vo.RemoteDeliveryPricingVO;
import com.doumee.dao.vo.EstimatedDeliveryVO;
import com.doumee.dao.vo.StoreDepositVO;
import com.doumee.dao.vo.RevenueShareVO;
import com.doumee.service.business.PricingRuleService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.util.CollectionUtils;
import java.util.*;
import java.util.stream.Collectors;
/**
 * è®¡ä»·è§„则配置Service实现
 * @author rk
 * @date 2026/04/08
 */
@Service
public class PricingRuleServiceImpl implements PricingRuleService {
    @Autowired
    private PricingRuleMapper pricingRuleMapper;
    @Autowired
    private CategoryMapper categoryMapper;
    @Override
    public Integer create(PricingRule pricingRule) {
        pricingRuleMapper.insert(pricingRule);
        return pricingRule.getId();
    }
    @Override
    public void deleteById(Integer id) {
        pricingRuleMapper.deleteById(id);
    }
    @Override
    public void delete(PricingRule pricingRule) {
        UpdateWrapper<PricingRule> deleteWrapper = new UpdateWrapper<>(pricingRule);
        pricingRuleMapper.delete(deleteWrapper);
    }
    @Override
    public void deleteByIdInBatch(List<Integer> ids) {
        if (CollectionUtils.isEmpty(ids)) {
            return;
        }
        pricingRuleMapper.deleteBatchIds(ids);
    }
    @Override
    public void updateById(PricingRule pricingRule) {
        pricingRuleMapper.updateById(pricingRule);
    }
    @Override
    public void updateByIdInBatch(List<PricingRule> pricingRules) {
        if (CollectionUtils.isEmpty(pricingRules)) {
            return;
        }
        for (PricingRule pricingRule : pricingRules) {
            this.updateById(pricingRule);
        }
    }
    @Override
    public PricingRule findById(Integer id) {
        PricingRule pricingRule = pricingRuleMapper.selectById(id);
        if (Objects.isNull(pricingRule)) {
            throw new BusinessException(ResponseStatus.DATA_EMPTY);
        }
        return pricingRule;
    }
    @Override
    public PricingRule findOne(PricingRule pricingRule) {
        QueryWrapper<PricingRule> wrapper = new QueryWrapper<>(pricingRule);
        return pricingRuleMapper.selectOne(wrapper);
    }
    @Override
    public List<PricingRule> findList(PricingRule pricingRule) {
        QueryWrapper<PricingRule> wrapper = new QueryWrapper<>(pricingRule);
        return pricingRuleMapper.selectList(wrapper);
    }
    @Override
    public PageData<PricingRule> findPage(PageWrap<PricingRule> pageWrap) {
        IPage<PricingRule> page = new Page<>(pageWrap.getPage(), pageWrap.getCapacity());
        QueryWrapper<PricingRule> queryWrapper = new QueryWrapper<>();
        Utils.MP.blankToNull(pageWrap.getModel());
        pageWrap.getModel().setDeleted(Constants.ZERO);
        if (pageWrap.getModel().getId() != null) {
            queryWrapper.lambda().eq(PricingRule::getId, pageWrap.getModel().getId());
        }
        if (pageWrap.getModel().getDeleted() != null) {
            queryWrapper.lambda().eq(PricingRule::getDeleted, pageWrap.getModel().getDeleted());
        }
        if (pageWrap.getModel().getCreateUser() != null) {
            queryWrapper.lambda().eq(PricingRule::getCreateUser, pageWrap.getModel().getCreateUser());
        }
        if (pageWrap.getModel().getCreateTime() != null) {
            queryWrapper.lambda().ge(PricingRule::getCreateTime, Utils.Date.getStart(pageWrap.getModel().getCreateTime()));
            queryWrapper.lambda().le(PricingRule::getCreateTime, Utils.Date.getEnd(pageWrap.getModel().getCreateTime()));
        }
        if (pageWrap.getModel().getUpdateUser() != null) {
            queryWrapper.lambda().eq(PricingRule::getUpdateUser, pageWrap.getModel().getUpdateUser());
        }
        if (pageWrap.getModel().getUpdateTime() != null) {
            queryWrapper.lambda().ge(PricingRule::getUpdateTime, Utils.Date.getStart(pageWrap.getModel().getUpdateTime()));
            queryWrapper.lambda().le(PricingRule::getUpdateTime, Utils.Date.getEnd(pageWrap.getModel().getUpdateTime()));
        }
        if (pageWrap.getModel().getRemark() != null) {
            queryWrapper.lambda().eq(PricingRule::getRemark, pageWrap.getModel().getRemark());
        }
        if (pageWrap.getModel().getCityId() != null) {
            queryWrapper.lambda().eq(PricingRule::getCityId, pageWrap.getModel().getCityId());
        }
        if (pageWrap.getModel().getType() != null) {
            queryWrapper.lambda().eq(PricingRule::getType, pageWrap.getModel().getType());
        }
        if (pageWrap.getModel().getFieldA() != null) {
            queryWrapper.lambda().eq(PricingRule::getFieldA, pageWrap.getModel().getFieldA());
        }
        if (pageWrap.getModel().getFieldB() != null) {
            queryWrapper.lambda().eq(PricingRule::getFieldB, pageWrap.getModel().getFieldB());
        }
        if (pageWrap.getModel().getFieldC() != null) {
            queryWrapper.lambda().eq(PricingRule::getFieldC, pageWrap.getModel().getFieldC());
        }
        if (pageWrap.getModel().getFieldD() != null) {
            queryWrapper.lambda().eq(PricingRule::getFieldD, pageWrap.getModel().getFieldD());
        }
        if (pageWrap.getModel().getFieldE() != null) {
            queryWrapper.lambda().eq(PricingRule::getFieldE, pageWrap.getModel().getFieldE());
        }
        for (PageWrap.SortData sortData : pageWrap.getSorts()) {
            if (sortData.getDirection().equalsIgnoreCase(PageWrap.DESC)) {
                queryWrapper.orderByDesc(sortData.getProperty());
            } else {
                queryWrapper.orderByAsc(sortData.getProperty());
            }
        }
        return PageData.from(pricingRuleMapper.selectPage(page, queryWrapper));
    }
    @Override
    public long count(PricingRule pricingRule) {
        QueryWrapper<PricingRule> wrapper = new QueryWrapper<>(pricingRule);
        return pricingRuleMapper.selectCount(wrapper);
    }
    @Override
    @Transactional(rollbackFor = Exception.class)
    public void batchSaveLocalStoragePricing(LocalStoragePricingSaveDTO request) {
        // æ ¡éªŒåˆ†ç±»æ•°æ®å®Œæ•´æ€§
        Set<Integer> requestCategoryIds = request.getItems().stream()
                .map(LocalStoragePricingItemDTO::getCategoryId)
                .collect(Collectors.toSet());
        validateCategoryType4(requestCategoryIds);
        // é€é¡¹ upsert
        Date now = new Date();
        for (LocalStoragePricingItemDTO item : request.getItems()) {
            // æŸ¥è¯¢å·²æœ‰è§„则
            QueryWrapper<PricingRule> qw = new QueryWrapper<>();
            qw.lambda()
                    .eq(PricingRule::getType, Constants.ZERO)
                    .eq(PricingRule::getFieldA, String.valueOf(item.getCategoryId()))
                    .eq(PricingRule::getCityId, request.getCityId())
                    .eq(PricingRule::getDeleted, Constants.ZERO)
                    .last("limit 1");
            PricingRule existing = pricingRuleMapper.selectOne(qw);
            if (existing != null) {
                // æ›´æ–°
                existing.setFieldB(item.getUnitPrice());
                existing.setUpdateTime(now);
                pricingRuleMapper.updateById(existing);
            } else {
                // æ–°å»º
                PricingRule rule = new PricingRule();
                rule.setType(Constants.ZERO);
                rule.setFieldA(String.valueOf(item.getCategoryId()));
                rule.setFieldB(item.getUnitPrice());
                rule.setCityId(request.getCityId());
                rule.setDeleted(Constants.ZERO);
                rule.setCreateTime(now);
                rule.setUpdateTime(now);
                pricingRuleMapper.insert(rule);
            }
        }
    }
    @Override
    public List<LocalStoragePricingVO> listLocalStoragePricing(Integer cityId) {
        // 1. æŸ¥è¯¢æ‰€æœ‰ Category type=4, deleted=0
        Category categoryQuery = new Category();
        categoryQuery.setType(Constants.FOUR);
        categoryQuery.setDeleted(Constants.ZERO);
        List<Category> allCategories = categoryMapper.selectList(new QueryWrapper<>(categoryQuery));
        Map<Integer, String> categoryNameMap = allCategories.stream()
                .collect(Collectors.toMap(Category::getId, Category::getName));
        // 2. æŸ¥è¯¢å·²æœ‰è§„则
        QueryWrapper<PricingRule> qw = new QueryWrapper<>();
        qw.lambda()
                .eq(PricingRule::getType, Constants.ZERO)
                .eq(PricingRule::getCityId, cityId)
                .eq(PricingRule::getDeleted, Constants.ZERO);
        List<PricingRule> rules = pricingRuleMapper.selectList(qw);
        Map<String, PricingRule> existingMap = rules.stream()
                .collect(Collectors.toMap(PricingRule::getFieldA, r -> r));
        // 3. åŸºäºŽæ‰€æœ‰åˆ†ç±»ç»„装 VO,无规则则返回空记录
        return allCategories.stream().map(category -> {
            LocalStoragePricingVO vo = new LocalStoragePricingVO();
            vo.setCategoryId(category.getId());
            vo.setCategoryName(category.getName());
            vo.setCityId(cityId);
            PricingRule rule = existingMap.get(String.valueOf(category.getId()));
            if (rule != null) {
                vo.setPricingRuleId(rule.getId());
                vo.setUnitPrice(rule.getFieldB());
            }
            return vo;
        }).collect(Collectors.toList());
    }
    @Override
    @Transactional(rollbackFor = Exception.class)
    public void batchSaveRemoteDeliveryPricing(RemoteDeliveryPricingSaveDTO request) {
        // æ ¡éªŒåˆ†ç±»æ•°æ®å®Œæ•´æ€§
        Set<Integer> requestCategoryIds = request.getItems().stream()
                .map(RemoteDeliveryPricingItemDTO::getCategoryId)
                .collect(Collectors.toSet());
        Map<Integer, String> categoryMap = validateCategoryType4(requestCategoryIds);
        // é€é¡¹ upsert
        Date now = new Date();
        for (RemoteDeliveryPricingItemDTO item : request.getItems()) {
            QueryWrapper<PricingRule> qw = new QueryWrapper<>();
            qw.lambda()
                    .eq(PricingRule::getType, Constants.ONE)
                    .eq(PricingRule::getFieldA, String.valueOf(item.getCategoryId()))
                    .eq(PricingRule::getCityId, request.getCityId())
                    .eq(PricingRule::getDeleted, Constants.ZERO)
                    .last("limit 1");
            PricingRule existing = pricingRuleMapper.selectOne(qw);
            if (existing != null) {
                existing.setFieldB(item.getStartDistance());
                existing.setFieldC(item.getStartPrice());
                existing.setFieldD(item.getExtraDistance());
                existing.setFieldE(item.getExtraPrice());
                existing.setUpdateTime(now);
                pricingRuleMapper.updateById(existing);
            } else {
                PricingRule rule = new PricingRule();
                rule.setType(Constants.ONE);
                rule.setFieldA(String.valueOf(item.getCategoryId()));
                rule.setFieldB(item.getStartDistance());
                rule.setFieldC(item.getStartPrice());
                rule.setFieldD(item.getExtraDistance());
                rule.setFieldE(item.getExtraPrice());
                rule.setCityId(request.getCityId());
                rule.setDeleted(Constants.ZERO);
                rule.setCreateTime(now);
                rule.setUpdateTime(now);
                pricingRuleMapper.insert(rule);
            }
        }
    }
    @Override
    public List<RemoteDeliveryPricingVO> listRemoteDeliveryPricing(Integer cityId) {
        // 1. æŸ¥è¯¢æ‰€æœ‰ Category type=4, deleted=0
        Category categoryQuery = new Category();
        categoryQuery.setType(Constants.FOUR);
        categoryQuery.setDeleted(Constants.ZERO);
        List<Category> allCategories = categoryMapper.selectList(new QueryWrapper<>(categoryQuery));
        Map<Integer, String> categoryNameMap = allCategories.stream()
                .collect(Collectors.toMap(Category::getId, Category::getName));
        // 2. æŸ¥è¯¢å·²æœ‰è§„则
        QueryWrapper<PricingRule> qw = new QueryWrapper<>();
        qw.lambda()
                .eq(PricingRule::getType, Constants.ONE)
                .eq(PricingRule::getCityId, cityId)
                .eq(PricingRule::getDeleted, Constants.ZERO);
        List<PricingRule> rules = pricingRuleMapper.selectList(qw);
        Map<String, PricingRule> existingMap = rules.stream()
                .collect(Collectors.toMap(PricingRule::getFieldA, r -> r));
        // 3. åŸºäºŽæ‰€æœ‰åˆ†ç±»ç»„装 VO,无规则则返回空记录
        return allCategories.stream().map(category -> {
            RemoteDeliveryPricingVO vo = new RemoteDeliveryPricingVO();
            vo.setCategoryId(category.getId());
            vo.setCategoryName(category.getName());
            vo.setCityId(cityId);
            PricingRule rule = existingMap.get(String.valueOf(category.getId()));
            if (rule != null) {
                vo.setPricingRuleId(rule.getId());
                vo.setStartDistance(rule.getFieldB());
                vo.setStartPrice(rule.getFieldC());
                vo.setExtraDistance(rule.getFieldD());
                vo.setExtraPrice(rule.getFieldE());
            }
            return vo;
        }).collect(Collectors.toList());
    }
    /**
     * æ ¡éªŒè¯·æ±‚中的 categoryId ä¸Žåˆ†ç±»è¡¨ type=4 æ•°æ®å®Œå…¨åŒ¹é…
     * @param requestCategoryIds è¯·æ±‚中的 categoryId é›†åˆ
     * @return åˆ†ç±»è¡¨ id->name æ˜ å°„
     */
    private Map<Integer, String> validateCategoryType4(Set<Integer> requestCategoryIds) {
        Category categoryQuery = new Category();
        categoryQuery.setType(Constants.FOUR);
        categoryQuery.setDeleted(Constants.ZERO);
        List<Category> allType4Categories = categoryMapper.selectList(new QueryWrapper<>(categoryQuery));
        Map<Integer, String> categoryMap = allType4Categories.stream()
                .collect(Collectors.toMap(Category::getId, Category::getName));
        Set<Integer> allCategoryIds = categoryMap.keySet();
        // æ ¡éªŒï¼šè¯·æ±‚中存在但分类表中不存在的 categoryId
        List<String> invalidIds = requestCategoryIds.stream()
                .filter(id -> !allCategoryIds.contains(id))
                .map(String::valueOf)
                .collect(Collectors.toList());
        if (!invalidIds.isEmpty()) {
            throw new BusinessException(ResponseStatus.BAD_REQUEST.getCode(),
                    "以下物品规格不存在: " + String.join(", ", invalidIds));
        }
        // æ ¡éªŒï¼šåˆ†ç±»è¡¨ä¸­å­˜åœ¨ä½†è¯·æ±‚中缺失的 categoryId
        List<String> missingNames = allCategoryIds.stream()
                .filter(id -> !requestCategoryIds.contains(id))
                .map(id -> categoryMap.get(id) + "(" + id + ")")
                .collect(Collectors.toList());
        if (!missingNames.isEmpty()) {
            throw new BusinessException(ResponseStatus.BAD_REQUEST.getCode(),
                    "缺少以下物品规格的定价配置: " + String.join(", ", missingNames));
        }
        return categoryMap;
    }
    @Override
    public Integer createEstimatedDelivery(EstimatedDeliverySaveDTO request) {
        PricingRule rule = new PricingRule();
        rule.setType(Constants.TWO);
        rule.setCityId(request.getCityId());
        rule.setFieldA(request.getDistance());
        rule.setFieldB(request.getDuration());
        rule.setDeleted(Constants.ZERO);
        rule.setCreateTime(new Date());
        rule.setUpdateTime(new Date());
        pricingRuleMapper.insert(rule);
        return rule.getId();
    }
    @Override
    public void updateEstimatedDelivery(EstimatedDeliverySaveDTO request) {
        if (request.getId() == null) {
            throw new BusinessException(ResponseStatus.BAD_REQUEST.getCode(), "主键不能为空");
        }
        PricingRule existing = pricingRuleMapper.selectById(request.getId());
        if (Objects.isNull(existing) || !Constants.equalsInteger(existing.getType(), Constants.TWO)) {
            throw new BusinessException(ResponseStatus.DATA_EMPTY);
        }
        existing.setFieldA(request.getDistance());
        existing.setFieldB(request.getDuration());
        existing.setCityId(request.getCityId());
        existing.setUpdateTime(new Date());
        pricingRuleMapper.updateById(existing);
    }
    @Override
    public void deleteEstimatedDelivery(Integer id) {
        PricingRule existing = pricingRuleMapper.selectById(id);
        if (Objects.isNull(existing) || !Constants.equalsInteger(existing.getType(), Constants.TWO)) {
            throw new BusinessException(ResponseStatus.DATA_EMPTY);
        }
        existing.setDeleted(Constants.ONE);
        existing.setUpdateTime(new Date());
        pricingRuleMapper.updateById(existing);
    }
    @Override
    public List<EstimatedDeliveryVO> listEstimatedDelivery(Integer cityId) {
        QueryWrapper<PricingRule> qw = new QueryWrapper<>();
        qw.lambda()
                .eq(PricingRule::getType, Constants.TWO)
                .eq(PricingRule::getCityId, cityId)
                .eq(PricingRule::getDeleted, Constants.ZERO)
                .orderByAsc(PricingRule::getFieldA);
        List<PricingRule> rules = pricingRuleMapper.selectList(qw);
        if (CollectionUtils.isEmpty(rules)) {
            return new ArrayList<>();
        }
        return rules.stream().map(rule -> {
            EstimatedDeliveryVO vo = new EstimatedDeliveryVO();
            vo.setPricingRuleId(rule.getId());
            vo.setCityId(rule.getCityId());
            vo.setDistance(rule.getFieldA());
            vo.setDuration(rule.getFieldB());
            return vo;
        }).collect(Collectors.toList());
    }
    @Override
    @Transactional(rollbackFor = Exception.class)
    public void batchSaveStoreDeposit(StoreDepositSaveDTO request) {
        // æ ¡éªŒï¼šå¿…须包含 fieldType=0(企业) å’Œ fieldType=1(个人) å„一条
        Set<Integer> fieldTypes = request.getItems().stream()
                .map(StoreDepositItemDTO::getFieldType)
                .collect(Collectors.toSet());
        if (!fieldTypes.contains(Constants.ZERO) || !fieldTypes.contains(Constants.ONE)) {
            throw new BusinessException(ResponseStatus.BAD_REQUEST.getCode(),
                    "必须包含企业(0)和个人(1)两条数据");
        }
        if (request.getItems().size() != 2) {
            throw new BusinessException(ResponseStatus.BAD_REQUEST.getCode(),
                    "有且仅有2条数据");
        }
        Date now = new Date();
        for (StoreDepositItemDTO item : request.getItems()) {
            QueryWrapper<PricingRule> qw = new QueryWrapper<>();
            qw.lambda()
                    .eq(PricingRule::getType, Constants.THREE)
                    .eq(PricingRule::getFieldA, String.valueOf(item.getFieldType()))
                    .eq(PricingRule::getCityId, request.getCityId())
                    .eq(PricingRule::getDeleted, Constants.ZERO)
                    .last("limit 1");
            PricingRule existing = pricingRuleMapper.selectOne(qw);
            if (existing != null) {
                existing.setFieldB(item.getDepositAmount());
                existing.setUpdateTime(now);
                pricingRuleMapper.updateById(existing);
            } else {
                PricingRule rule = new PricingRule();
                rule.setType(Constants.THREE);
                rule.setFieldA(String.valueOf(item.getFieldType()));
                rule.setFieldB(item.getDepositAmount());
                rule.setCityId(request.getCityId());
                rule.setDeleted(Constants.ZERO);
                rule.setCreateTime(now);
                rule.setUpdateTime(now);
                pricingRuleMapper.insert(rule);
            }
        }
    }
    @Override
    public List<StoreDepositVO> listStoreDeposit(Integer cityId) {
        // æŸ¥è¯¢å·²æœ‰è§„则
        QueryWrapper<PricingRule> qw = new QueryWrapper<>();
        qw.lambda()
                .eq(PricingRule::getType, Constants.THREE)
                .eq(PricingRule::getCityId, cityId)
                .eq(PricingRule::getDeleted, Constants.ZERO);
        List<PricingRule> rules = pricingRuleMapper.selectList(qw);
        // æž„建已存在数据的映射 fieldA -> rule
        Map<String, PricingRule> existingMap = rules.stream()
                .collect(Collectors.toMap(PricingRule::getFieldA, r -> r));
        // å›ºå®šè¿”回2条:企业(0)、个人(1)
        List<StoreDepositVO> result = new ArrayList<>();
        String[] typeNames = {"企业", "个人"};
        for (int i = 0; i <= 1; i++) {
            StoreDepositVO vo = new StoreDepositVO();
            vo.setFieldType(i);
            vo.setFieldTypeName(typeNames[i]);
            vo.setCityId(cityId);
            PricingRule rule = existingMap.get(String.valueOf(i));
            if (rule != null) {
                vo.setPricingRuleId(rule.getId());
                vo.setDepositAmount(rule.getFieldB());
            }
            result.add(vo);
        }
        return result;
    }
    @Override
    @Transactional(rollbackFor = Exception.class)
    public void batchSaveRevenueShare(RevenueShareSaveDTO request) {
        // æ ¡éªŒï¼šå¿…须包含 fieldType 0-4 å„一条
        Set<Integer> fieldTypes = request.getItems().stream()
                .map(RevenueShareItemDTO::getFieldType)
                .collect(Collectors.toSet());
        if (fieldTypes.size() != Constants.FIVE) {
            throw new BusinessException(ResponseStatus.BAD_REQUEST.getCode(),
                    "必须包含企业寄(0)、个人寄(1)、企业取(2)、个人取(3)、配送员(4)共5条数据");
        }
        for (int i = 0; i <= Constants.FOUR; i++) {
            if (!fieldTypes.contains(i)) {
                throw new BusinessException(ResponseStatus.BAD_REQUEST.getCode(),
                        "缺少类型" + i + "的数据");
            }
        }
        Date now = new Date();
        for (RevenueShareItemDTO item : request.getItems()) {
            QueryWrapper<PricingRule> qw = new QueryWrapper<>();
            qw.lambda()
                    .eq(PricingRule::getType, Constants.FOUR)
                    .eq(PricingRule::getFieldA, String.valueOf(item.getFieldType()))
                    .eq(PricingRule::getCityId, request.getCityId())
                    .eq(PricingRule::getDeleted, Constants.ZERO)
                    .last("limit 1");
            PricingRule existing = pricingRuleMapper.selectOne(qw);
            if (existing != null) {
                existing.setFieldB(item.getRatio());
                existing.setUpdateTime(now);
                pricingRuleMapper.updateById(existing);
            } else {
                PricingRule rule = new PricingRule();
                rule.setType(Constants.FOUR);
                rule.setFieldA(String.valueOf(item.getFieldType()));
                rule.setFieldB(item.getRatio());
                rule.setCityId(request.getCityId());
                rule.setDeleted(Constants.ZERO);
                rule.setCreateTime(now);
                rule.setUpdateTime(now);
                pricingRuleMapper.insert(rule);
            }
        }
    }
    @Override
    public List<RevenueShareVO> listRevenueShare(Integer cityId) {
        // æŸ¥è¯¢å·²æœ‰è§„则
        QueryWrapper<PricingRule> qw = new QueryWrapper<>();
        qw.lambda()
                .eq(PricingRule::getType, Constants.FOUR)
                .eq(PricingRule::getCityId, cityId)
                .eq(PricingRule::getDeleted, Constants.ZERO);
        List<PricingRule> rules = pricingRuleMapper.selectList(qw);
        // æž„建已存在数据的映射 fieldA -> rule
        Map<String, PricingRule> existingMap = rules.stream()
                .collect(Collectors.toMap(PricingRule::getFieldA, r -> r));
        // å›ºå®šè¿”回5条:企业寄(0)、个人寄(1)、企业取(2)、个人取(3)、配送员(4)
        List<RevenueShareVO> result = new ArrayList<>();
        String[] typeNames = {"企业寄", "个人寄", "企业取", "个人取", "配送员"};
        for (int i = 0; i <= Constants.FOUR; i++) {
            RevenueShareVO vo = new RevenueShareVO();
            vo.setFieldType(i);
            vo.setFieldTypeName(typeNames[i]);
            vo.setCityId(cityId);
            PricingRule rule = existingMap.get(String.valueOf(i));
            if (rule != null) {
                vo.setPricingRuleId(rule.getId());
                vo.setRatio(rule.getFieldB());
            }
            result.add(vo);
        }
        return result;
    }
}
server/services/src/main/java/com/doumee/service/business/impl/ShopInfoServiceImpl.java
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,171 @@
package com.doumee.service.business.impl;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.conditions.update.UpdateWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.doumee.core.constants.Constants;
import com.doumee.core.constants.ResponseStatus;
import com.doumee.core.exception.BusinessException;
import com.doumee.core.model.PageData;
import com.doumee.core.model.PageWrap;
import com.doumee.core.utils.Utils;
import com.doumee.dao.business.ShopInfoMapper;
import com.doumee.dao.business.model.ShopInfo;
import com.doumee.service.business.ShopInfoService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.util.CollectionUtils;
import java.util.List;
import java.util.Objects;
/**
 * é—¨åº—信息Service实现
 * @author rk
 * @date 2026/04/08
 */
@Service
public class ShopInfoServiceImpl implements ShopInfoService {
    @Autowired
    private ShopInfoMapper shopInfoMapper;
    @Override
    public Integer create(ShopInfo shopInfo) {
        shopInfoMapper.insert(shopInfo);
        return shopInfo.getId();
    }
    @Override
    public void deleteById(Integer id) {
        shopInfoMapper.deleteById(id);
    }
    @Override
    public void delete(ShopInfo shopInfo) {
        UpdateWrapper<ShopInfo> deleteWrapper = new UpdateWrapper<>(shopInfo);
        shopInfoMapper.delete(deleteWrapper);
    }
    @Override
    public void deleteByIdInBatch(List<Integer> ids) {
        if (CollectionUtils.isEmpty(ids)) {
            return;
        }
        shopInfoMapper.deleteBatchIds(ids);
    }
    @Override
    public void updateById(ShopInfo shopInfo) {
        shopInfoMapper.updateById(shopInfo);
    }
    @Override
    public void updateByIdInBatch(List<ShopInfo> shopInfos) {
        if (CollectionUtils.isEmpty(shopInfos)) {
            return;
        }
        for (ShopInfo shopInfo : shopInfos) {
            this.updateById(shopInfo);
        }
    }
    @Override
    public ShopInfo findById(Integer id) {
        ShopInfo shopInfo = shopInfoMapper.selectById(id);
        if (Objects.isNull(shopInfo)) {
            throw new BusinessException(ResponseStatus.DATA_EMPTY);
        }
        return shopInfo;
    }
    @Override
    public ShopInfo findOne(ShopInfo shopInfo) {
        QueryWrapper<ShopInfo> wrapper = new QueryWrapper<>(shopInfo);
        return shopInfoMapper.selectOne(wrapper);
    }
    @Override
    public List<ShopInfo> findList(ShopInfo shopInfo) {
        QueryWrapper<ShopInfo> wrapper = new QueryWrapper<>(shopInfo);
        return shopInfoMapper.selectList(wrapper);
    }
    @Override
    public PageData<ShopInfo> findPage(PageWrap<ShopInfo> pageWrap) {
        IPage<ShopInfo> page = new Page<>(pageWrap.getPage(), pageWrap.getCapacity());
        QueryWrapper<ShopInfo> queryWrapper = new QueryWrapper<>();
        Utils.MP.blankToNull(pageWrap.getModel());
        pageWrap.getModel().setDeleted(Constants.ZERO);
        if (pageWrap.getModel().getId() != null) {
            queryWrapper.lambda().eq(ShopInfo::getId, pageWrap.getModel().getId());
        }
        if (pageWrap.getModel().getDeleted() != null) {
            queryWrapper.lambda().eq(ShopInfo::getDeleted, pageWrap.getModel().getDeleted());
        }
        if (pageWrap.getModel().getCreateUser() != null) {
            queryWrapper.lambda().eq(ShopInfo::getCreateUser, pageWrap.getModel().getCreateUser());
        }
        if (pageWrap.getModel().getCreateTime() != null) {
            queryWrapper.lambda().ge(ShopInfo::getCreateTime, Utils.Date.getStart(pageWrap.getModel().getCreateTime()));
            queryWrapper.lambda().le(ShopInfo::getCreateTime, Utils.Date.getEnd(pageWrap.getModel().getCreateTime()));
        }
        if (pageWrap.getModel().getUpdateUser() != null) {
            queryWrapper.lambda().eq(ShopInfo::getUpdateUser, pageWrap.getModel().getUpdateUser());
        }
        if (pageWrap.getModel().getUpdateTime() != null) {
            queryWrapper.lambda().ge(ShopInfo::getUpdateTime, Utils.Date.getStart(pageWrap.getModel().getUpdateTime()));
            queryWrapper.lambda().le(ShopInfo::getUpdateTime, Utils.Date.getEnd(pageWrap.getModel().getUpdateTime()));
        }
        if (pageWrap.getModel().getRemark() != null) {
            queryWrapper.lambda().eq(ShopInfo::getRemark, pageWrap.getModel().getRemark());
        }
        if (pageWrap.getModel().getCompanyType() != null) {
            queryWrapper.lambda().eq(ShopInfo::getCompanyType, pageWrap.getModel().getCompanyType());
        }
        if (pageWrap.getModel().getName() != null) {
            queryWrapper.lambda().like(ShopInfo::getName, pageWrap.getModel().getName());
        }
        if (pageWrap.getModel().getTelephone() != null) {
            queryWrapper.lambda().like(ShopInfo::getTelephone, pageWrap.getModel().getTelephone());
        }
        if (pageWrap.getModel().getLinkName() != null) {
            queryWrapper.lambda().like(ShopInfo::getLinkName, pageWrap.getModel().getLinkName());
        }
        if (pageWrap.getModel().getLinkPhone() != null) {
            queryWrapper.lambda().like(ShopInfo::getLinkPhone, pageWrap.getModel().getLinkPhone());
        }
        if (pageWrap.getModel().getAreaId() != null) {
            queryWrapper.lambda().eq(ShopInfo::getAreaId, pageWrap.getModel().getAreaId());
        }
        if (pageWrap.getModel().getStatus() != null) {
            queryWrapper.lambda().eq(ShopInfo::getStatus, pageWrap.getModel().getStatus());
        }
        if (pageWrap.getModel().getAuditTime() != null) {
            queryWrapper.lambda().ge(ShopInfo::getAuditTime, Utils.Date.getStart(pageWrap.getModel().getAuditTime()));
            queryWrapper.lambda().le(ShopInfo::getAuditTime, Utils.Date.getEnd(pageWrap.getModel().getAuditTime()));
        }
        if (pageWrap.getModel().getAuditUserId() != null) {
            queryWrapper.lambda().eq(ShopInfo::getAuditUserId, pageWrap.getModel().getAuditUserId());
        }
        if (pageWrap.getModel().getOpenid() != null) {
            queryWrapper.lambda().like(ShopInfo::getOpenid, pageWrap.getModel().getOpenid());
        }
        for (PageWrap.SortData sortData : pageWrap.getSorts()) {
            if (sortData.getDirection().equalsIgnoreCase(PageWrap.DESC)) {
                queryWrapper.orderByDesc(sortData.getProperty());
            } else {
                queryWrapper.orderByAsc(sortData.getProperty());
            }
        }
        return PageData.from(shopInfoMapper.selectPage(page, queryWrapper));
    }
    @Override
    public long count(ShopInfo shopInfo) {
        QueryWrapper<ShopInfo> wrapper = new QueryWrapper<>(shopInfo);
        return shopInfoMapper.selectCount(wrapper);
    }
}
server/services/src/main/java/com/doumee/service/business/impl/SmsrecordServiceImpl.java
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,159 @@
package com.doumee.service.business.impl;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.conditions.update.UpdateWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.doumee.core.constants.Constants;
import com.doumee.core.constants.ResponseStatus;
import com.doumee.core.exception.BusinessException;
import com.doumee.core.model.PageData;
import com.doumee.core.model.PageWrap;
import com.doumee.core.utils.Utils;
import com.doumee.dao.business.SmsrecordMapper;
import com.doumee.dao.business.model.Smsrecord;
import com.doumee.service.business.SmsrecordService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.util.CollectionUtils;
import java.util.List;
import java.util.Objects;
/**
 * çŸ­ä¿¡éªŒè¯ç Service实现
 * @author rk
 * @date 2026/04/08
 */
@Service
public class SmsrecordServiceImpl implements SmsrecordService {
    @Autowired
    private SmsrecordMapper smsrecordMapper;
    @Override
    public Integer create(Smsrecord smsrecord) {
        smsrecordMapper.insert(smsrecord);
        return smsrecord.getId();
    }
    @Override
    public void deleteById(Integer id) {
        smsrecordMapper.deleteById(id);
    }
    @Override
    public void delete(Smsrecord smsrecord) {
        UpdateWrapper<Smsrecord> deleteWrapper = new UpdateWrapper<>(smsrecord);
        smsrecordMapper.delete(deleteWrapper);
    }
    @Override
    public void deleteByIdInBatch(List<Integer> ids) {
        if (CollectionUtils.isEmpty(ids)) {
            return;
        }
        smsrecordMapper.deleteBatchIds(ids);
    }
    @Override
    public void updateById(Smsrecord smsrecord) {
        smsrecordMapper.updateById(smsrecord);
    }
    @Override
    public void updateByIdInBatch(List<Smsrecord> smsrecords) {
        if (CollectionUtils.isEmpty(smsrecords)) {
            return;
        }
        for (Smsrecord smsrecord : smsrecords) {
            this.updateById(smsrecord);
        }
    }
    @Override
    public Smsrecord findById(Integer id) {
        Smsrecord smsrecord = smsrecordMapper.selectById(id);
        if (Objects.isNull(smsrecord)) {
            throw new BusinessException(ResponseStatus.DATA_EMPTY);
        }
        return smsrecord;
    }
    @Override
    public Smsrecord findOne(Smsrecord smsrecord) {
        QueryWrapper<Smsrecord> wrapper = new QueryWrapper<>(smsrecord);
        return smsrecordMapper.selectOne(wrapper);
    }
    @Override
    public List<Smsrecord> findList(Smsrecord smsrecord) {
        QueryWrapper<Smsrecord> wrapper = new QueryWrapper<>(smsrecord);
        return smsrecordMapper.selectList(wrapper);
    }
    @Override
    public PageData<Smsrecord> findPage(PageWrap<Smsrecord> pageWrap) {
        IPage<Smsrecord> page = new Page<>(pageWrap.getPage(), pageWrap.getCapacity());
        QueryWrapper<Smsrecord> queryWrapper = new QueryWrapper<>();
        Utils.MP.blankToNull(pageWrap.getModel());
        pageWrap.getModel().setDeleted(Constants.ZERO);
        if (pageWrap.getModel().getId() != null) {
            queryWrapper.lambda().eq(Smsrecord::getId, pageWrap.getModel().getId());
        }
        if (pageWrap.getModel().getDeleted() != null) {
            queryWrapper.lambda().eq(Smsrecord::getDeleted, pageWrap.getModel().getDeleted());
        }
        if (pageWrap.getModel().getCreateUser() != null) {
            queryWrapper.lambda().eq(Smsrecord::getCreateUser, pageWrap.getModel().getCreateUser());
        }
        if (pageWrap.getModel().getCreateTime() != null) {
            queryWrapper.lambda().ge(Smsrecord::getCreateTime, Utils.Date.getStart(pageWrap.getModel().getCreateTime()));
            queryWrapper.lambda().le(Smsrecord::getCreateTime, Utils.Date.getEnd(pageWrap.getModel().getCreateTime()));
        }
        if (pageWrap.getModel().getUpdateUser() != null) {
            queryWrapper.lambda().eq(Smsrecord::getUpdateUser, pageWrap.getModel().getUpdateUser());
        }
        if (pageWrap.getModel().getUpdateTime() != null) {
            queryWrapper.lambda().ge(Smsrecord::getUpdateTime, Utils.Date.getStart(pageWrap.getModel().getUpdateTime()));
            queryWrapper.lambda().le(Smsrecord::getUpdateTime, Utils.Date.getEnd(pageWrap.getModel().getUpdateTime()));
        }
        if (pageWrap.getModel().getRemark() != null) {
            queryWrapper.lambda().eq(Smsrecord::getRemark, pageWrap.getModel().getRemark());
        }
        if (pageWrap.getModel().getPhone() != null) {
            queryWrapper.lambda().like(Smsrecord::getPhone, pageWrap.getModel().getPhone());
        }
        if (pageWrap.getModel().getContent() != null) {
            queryWrapper.lambda().like(Smsrecord::getContent, pageWrap.getModel().getContent());
        }
        if (pageWrap.getModel().getType() != null) {
            queryWrapper.lambda().eq(Smsrecord::getType, pageWrap.getModel().getType());
        }
        if (pageWrap.getModel().getValidDate() != null) {
            queryWrapper.lambda().ge(Smsrecord::getValidDate, Utils.Date.getStart(pageWrap.getModel().getValidDate()));
            queryWrapper.lambda().le(Smsrecord::getValidDate, Utils.Date.getEnd(pageWrap.getModel().getValidDate()));
        }
        if (pageWrap.getModel().getCode() != null) {
            queryWrapper.lambda().eq(Smsrecord::getCode, pageWrap.getModel().getCode());
        }
        if (pageWrap.getModel().getStatus() != null) {
            queryWrapper.lambda().eq(Smsrecord::getStatus, pageWrap.getModel().getStatus());
        }
        for (PageWrap.SortData sortData : pageWrap.getSorts()) {
            if (sortData.getDirection().equalsIgnoreCase(PageWrap.DESC)) {
                queryWrapper.orderByDesc(sortData.getProperty());
            } else {
                queryWrapper.orderByAsc(sortData.getProperty());
            }
        }
        return PageData.from(smsrecordMapper.selectPage(page, queryWrapper));
    }
    @Override
    public long count(Smsrecord smsrecord) {
        QueryWrapper<Smsrecord> wrapper = new QueryWrapper<>(smsrecord);
        return smsrecordMapper.selectCount(wrapper);
    }
}
server/web/src/main/java/com/doumee/api/web/AccountApi.java
@@ -62,8 +62,26 @@
    })
    public ApiResponse logOff() {
        String token = this.getRequest().getHeader(JwtTokenUtil.HEADER_KEY);
        memberService.logOff(token,getMemberId());
        memberService.logOut(token,getMemberId());
        return  ApiResponse.success("操作成功");
    }
    @LoginRequired
    @ApiOperation(value = "用户注销", notes = "小程序端")
    @GetMapping("/logOut")
    @ApiImplicitParams({
            @ApiImplicitParam(paramType = "header", dataType = "String", name = "token", value = "用户token值", required = true),
    })
    public ApiResponse logOut() {
        String token = this.getRequest().getHeader(JwtTokenUtil.HEADER_KEY);
        memberService.logOut(token,getMemberId());
        return  ApiResponse.success("操作成功");
    }
}
server/web/src/main/java/com/doumee/api/web/DriverInfoApi.java
¶Ô±ÈÐÂÎļþ
@@ -0,0 +1,82 @@
package com.doumee.api.web;
import com.doumee.core.annotation.LoginRequired;
import com.doumee.core.annotation.trace.Trace;
import com.doumee.core.model.ApiResponse;
import com.doumee.dao.dto.DriverLoginRequest;
import com.doumee.dao.dto.DriverRegisterRequest;
import com.doumee.dao.dto.DriverVerifyRequest;
import com.doumee.dao.vo.AccountResponse;
import com.doumee.service.business.DriverInfoService;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiImplicitParam;
import io.swagger.annotations.ApiImplicitParams;
import io.swagger.annotations.ApiOperation;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.*;
/**
 * å¸æœºéªŒè¯ç ç™»å½•接口
 * @author rk
 * @date 2026/04/08
 */
@Api(tags = "司机验证码登录")
@Trace(exclude = true)
@RestController
@RequestMapping("/web/driverInfo")
@Slf4j
public class DriverInfoApi extends ApiController {
    @Autowired
    private DriverInfoService driverInfoService;
    @Trace
    @ApiOperation(value = "发送验证码", notes = "司机验证码登录")
    @GetMapping("/sendCode")
    @ApiImplicitParams({
            @ApiImplicitParam(paramType = "query", dataType = "String", name = "telephone", value = "手机号", required = true)
    })
    public ApiResponse sendCode(@RequestParam String telephone) {
        driverInfoService.sendRegisterCode(telephone);
        return ApiResponse.success("验证码发送成功");
    }
    @Trace
    @ApiOperation(value = "司机验证码登录", notes = "手机号+验证码,无账号自动注册并登录")
    @PostMapping("/register")
    public ApiResponse<AccountResponse> register(@RequestBody DriverRegisterRequest request) {
        return ApiResponse.success("注册成功", driverInfoService.register(request));
    }
    @Trace
    @ApiOperation(value = "司机登录", notes = "手机号+密码登录")
    @PostMapping("/login")
    public ApiResponse<AccountResponse> login(@RequestBody DriverLoginRequest request) {
        return ApiResponse.success("登录成功", driverInfoService.login(request));
    }
    @LoginRequired
    @Trace
    @ApiOperation(value = "提交实名认证", notes = "初次提交或驳回后修改")
    @PostMapping("/submitVerify")
    @ApiImplicitParams({
            @ApiImplicitParam(paramType = "header", dataType = "String", name = "token", value = "用户token值", required = true)
    })
    public ApiResponse submitVerify(@RequestBody DriverVerifyRequest request) {
        driverInfoService.submitVerify(this.getMemberId(), request);
        return ApiResponse.success("提交成功");
    }
    @LoginRequired
    @Trace
    @ApiOperation(value = "查询实名认证详情", notes = "司机端查询")
    @GetMapping("/verifyDetail")
    @ApiImplicitParams({
            @ApiImplicitParam(paramType = "header", dataType = "String", name = "token", value = "用户token值", required = true)
    })
    public ApiResponse verifyDetail() {
        return ApiResponse.success(driverInfoService.getVerifyDetail(this.getMemberId()));
    }
}
server/web/src/main/java/com/doumee/api/web/UserApi.java
@@ -43,14 +43,14 @@
    @Autowired
    private MemberService memberService;
    @Autowired
    private IdentityInfoService identityInfoService;
//    @Autowired
//    private IdentityInfoService identityInfoService;
    @Autowired
    private MemberRevenueService memberRevenueService;
    @Autowired
    private WithdrawalOrdersService withdrawalOrdersService;
//    @Autowired
//    private MemberRevenueService memberRevenueService;
//
//    @Autowired
//    private WithdrawalOrdersService withdrawalOrdersService;
    @ApiOperation(value = "获取系统配置", notes = "小程序端")
@@ -83,80 +83,80 @@
        return  ApiResponse.success("操作成功");
    }
    @LoginRequired
    @ApiOperation(value = "切换用工身份", notes = "小程序端")
    @PostMapping("/editUseIdentity")
    @ApiImplicitParams({
            @ApiImplicitParam(paramType = "header", dataType = "String", name = "token", value = "用户token值", required = true),
    })
    public ApiResponse editUseIdentity(@RequestBody Member member) {
        member.setId(getMemberId());
        memberService.editUseIdentity(member);
        return  ApiResponse.success("操作成功");
    }
//    @LoginRequired
//    @ApiOperation(value = "切换用工身份", notes = "小程序端")
//    @PostMapping("/editUseIdentity")
//    @ApiImplicitParams({
//            @ApiImplicitParam(paramType = "header", dataType = "String", name = "token", value = "用户token值", required = true),
//    })
//    public ApiResponse editUseIdentity(@RequestBody Member member) {
//        member.setId(getMemberId());
//        memberService.editUseIdentity(member);
//        return  ApiResponse.success("操作成功");
//    }
    @LoginRequired
    @ApiOperation(value = "获取身份认证信息", notes = "小程序端")
    @GetMapping("/getIdentityInfo")
    @ApiImplicitParams({
            @ApiImplicitParam(paramType = "header", dataType = "String", name = "token", value = "用户token值", required = true),
    })
    public ApiResponse<IdentityInfo> getIdentityInfo(@RequestParam Integer type) {
        return  ApiResponse.success("查询成功",identityInfoService.findByMemberType(type,getMemberId()));
    }
//    @LoginRequired
//    @ApiOperation(value = "获取身份认证信息", notes = "小程序端")
//    @GetMapping("/getIdentityInfo")
//    @ApiImplicitParams({
//            @ApiImplicitParam(paramType = "header", dataType = "String", name = "token", value = "用户token值", required = true),
//    })
//    public ApiResponse<IdentityInfo> getIdentityInfo(@RequestParam Integer type) {
//        return  ApiResponse.success("查询成功",identityInfoService.findByMemberType(type,getMemberId()));
//    }
    @LoginRequired
    @ApiOperation(value = "申请身份信息", notes = "小程序端")
    @PostMapping("/applyForIdentity")
    @ApiImplicitParams({
            @ApiImplicitParam(paramType = "header", dataType = "String", name = "token", value = "用户token值", required = true),
    })
    public ApiResponse applyForIdentity(@RequestBody IdentityInfo identityInfo) {
        identityInfo.setMemberId(getMemberId());
        identityInfoService.create(identityInfo);
        return  ApiResponse.success("操作成功");
    }
//    @LoginRequired
//    @ApiOperation(value = "申请身份信息", notes = "小程序端")
//    @PostMapping("/applyForIdentity")
//    @ApiImplicitParams({
//            @ApiImplicitParam(paramType = "header", dataType = "String", name = "token", value = "用户token值", required = true),
//    })
//    public ApiResponse applyForIdentity(@RequestBody IdentityInfo identityInfo) {
//        identityInfo.setMemberId(getMemberId());
//        identityInfoService.create(identityInfo);
//        return  ApiResponse.success("操作成功");
//    }
    @LoginRequired
    @ApiOperation(value = "修改身份信息(认证失败后使用)", notes = "小程序端")
    @PostMapping("/updateIdentity")
    @ApiImplicitParams({
            @ApiImplicitParam(paramType = "header", dataType = "String", name = "token", value = "用户token值", required = true),
    })
    public ApiResponse updateIdentity(@RequestBody IdentityInfo identityInfo) {
        identityInfo.setMemberId(getMemberId());
        identityInfoService.updateById(identityInfo);
        return  ApiResponse.success("操作成功");
    }
//    @LoginRequired
//    @ApiOperation(value = "修改身份信息(认证失败后使用)", notes = "小程序端")
//    @PostMapping("/updateIdentity")
//    @ApiImplicitParams({
//            @ApiImplicitParam(paramType = "header", dataType = "String", name = "token", value = "用户token值", required = true),
//    })
//    public ApiResponse updateIdentity(@RequestBody IdentityInfo identityInfo) {
//        identityInfo.setMemberId(getMemberId());
//        identityInfoService.updateById(identityInfo);
//        return  ApiResponse.success("操作成功");
//    }
    @LoginRequired
    @ApiOperation(value = "修改身份信息位置(认证成功后使用)", notes = "小程序端")
    @PostMapping("/updateLocation")
    @ApiImplicitParams({
            @ApiImplicitParam(paramType = "header", dataType = "String", name = "token", value = "用户token值", required = true),
    })
    public ApiResponse updateLocation(@RequestBody IdentityInfo identityInfo) {
        identityInfo.setMemberId(getMemberId());
        identityInfoService.updateLocation(identityInfo);
        return  ApiResponse.success("操作成功");
    }
//    @LoginRequired
//    @ApiOperation(value = "修改身份信息位置(认证成功后使用)", notes = "小程序端")
//    @PostMapping("/updateLocation")
//    @ApiImplicitParams({
//            @ApiImplicitParam(paramType = "header", dataType = "String", name = "token", value = "用户token值", required = true),
//    })
//    public ApiResponse updateLocation(@RequestBody IdentityInfo identityInfo) {
//        identityInfo.setMemberId(getMemberId());
//        identityInfoService.updateLocation(identityInfo);
//        return  ApiResponse.success("操作成功");
//    }
    @LoginRequired
    @ApiOperation("余额明细")
    @PostMapping("/revenuePage")
    @ApiImplicitParams({
            @ApiImplicitParam(paramType = "header", dataType = "String", name = "token", value = "用户token值", required = true),
    })
    public ApiResponse<PageData<MemberRevenue>> revenuePage (@RequestBody PageWrap<MemberRevenue> pageWrap) {
        pageWrap.getModel().setMemberId(this.getMemberId());
        return ApiResponse.success(memberRevenueService.findPage(pageWrap));
    }
//    @LoginRequired
//    @ApiOperation("余额明细")
//    @PostMapping("/revenuePage")
//    @ApiImplicitParams({
//            @ApiImplicitParam(paramType = "header", dataType = "String", name = "token", value = "用户token值", required = true),
//    })
//    public ApiResponse<PageData<MemberRevenue>> revenuePage (@RequestBody PageWrap<MemberRevenue> pageWrap) {
//        pageWrap.getModel().setMemberId(this.getMemberId());
//        return ApiResponse.success(memberRevenueService.findPage(pageWrap));
//    }