黑马苍穹外卖项目思路09_用户端历史订单、商家端订单管理

本文详细描述了电商平台用户端的历史订单功能,如查询、取消和再来一单,以及商家端的订单管理模块,包括订单搜索、状态统计、接单拒单等。重点介绍了商家端如何通过地址编码API和轻量级路线规划服务校验订单配送范围。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >


一.用户端历史订单

1. 查询历史订单

产品原型:
在这里插入图片描述

业务规则:

  • 分页查询历史订单
  • 可以根据订单状态查询
  • 展示订单数据时,需要展示的数据包括:下单时间、订单状态、订单金额、订单明细(商品名称、图片)

接口设计:
在这里插入图片描述
url传参为:page,pageSize,status
返回数据为:PageResult

思路:
1.需要注意的是,返回给页面的数据为集合嵌套了集合(历史订单有多个订单数据,一个订单数据又有多个菜品或者套餐数据)

2.需要明确的是PageResult中的集合属性应为OrderVO集合,其中一个OrderVO中封装了OrderDetail集合,故只需要针对OrderVO集合中的每一个OrderVO对象封装每个订单的菜品或者套餐数据即可,明确了思路代码实现不难

2. 查询订单详情

产品原型:
在这里插入图片描述
接口设计:
在这里插入图片描述
路径参数为:id
返回数据为:OrderVO类

思路:

1.首先需要明确的是OrderVO其实是继承自Orders对象,故OrderVO类中也有Orders的属性,所以说只需要返回一个OrderVO对象即可拥有查询订单详情所需的数据

2.明白了继承关系后,其实通过id将Orders对象查询出来后进行对象属性拷贝到OrderVO对象,再通过id将orderDetail中的菜品或套餐数据查询出来赋值给OrderVO对象即可.

3. 取消订单

产品原型:
在这里插入图片描述
接口设计:
在这里插入图片描述
路径参数为:id
不需要返回数据,只需返回成功与否

业务规则:

  • 待支付和待接单状态下,用户可直接取消订单
  • 商家已接单状态下,用户取消订单需电话沟通商家
  • 派送中状态下,用户取消订单需电话沟通商家
  • 如果在待接单状态下取消订单,需要给用户退款
  • 取消订单后需要将订单状态修改为“已取消”

思路:

根据业务规则对应实现即可

4. 再来一单

产品原型:
在这里插入图片描述
接口设计:
在这里插入图片描述
路径参数为:id
不需要返回数据,只需返回成功与否

思路:
1.再来一单就是将原订单中的商品重新加入到购物车中

2.通过id将查询OrderDetail表,将相应的菜品或者套餐数据查询出来,重新通过用户id添加到购物车表中即可

3.通过订单id查询出来的肯定为集合数据,通过new一个购物车集合对象,然后对象属性拷贝到单个购物车对象即可,最后需要注意的是不能将orderDetail表中的菜品或者套餐的id拷贝到ShoppingCart对象中

二.商家端订单管理模块

1. 订单搜索

产品原型:
在这里插入图片描述
接口设计:
在这里插入图片描述
url传参为:
在这里插入图片描述

返回数据为:PageResult

业务规则:

  • 输入订单号/手机号进行搜索,支持模糊搜索
  • 根据订单状态进行筛选
  • 下单时间进行时间筛选
  • 搜索内容为空,提示未找到相关订单
  • 搜索结果页,展示包含搜索关键词的内容
  • 分页展示搜索到的订单数据

思路:

1.需要注意的是部分订单状态,需要额外返回订单菜品信息,即OrderVO中的订单菜品信息private String orderDishes属性,故传入PageResult中的为OrderVO集合

2.明确了第一点思路后,后面的实现和用户端的查询历史订单业务相似,首先对page对象中的Orders集合进行依次遍历,将其中的数据封装到OrderVO集合中,遍历过程中需要封装orderDishes属性的值.

3.接着第二点末尾,将每一条订单菜品信息拼接为字符串(格式:宫保鸡丁*3;),则需要根据Orders中的id查询到OrderDetail集合,其中封装了菜品和套餐数据,然后将集合拼接成字符串返回即可

2. 各个状态的订单数量统计

产品原型:
在这里插入图片描述
接口设计:
在这里插入图片描述
get方式不需要传参
返回数据为:OrderStatisticsVO类

思路:
使用count(id)和where status = #{status}"查询统计不同的status的id数量

3. 查询订单详情

此功能在用户端已经进行了实现,调用实现类的方法即可

4. 接单

产品原型:
商家端点击接单
接口设计:
在这里插入图片描述
请求体传参:封装了id和status的OrdersConfirmDTO类(只有id有值)

业务规则:

  • 商家接单其实就是将订单的状态修改为“已接单”

思路:
修改状态即可

5. 拒单

产品原型:
商家端点击拒单
接口设计:
在这里插入图片描述
请求体传参:封装了id和订单拒绝原因rejectionReason的OrdersRejectionDTO类

业务规则:

  • 商家拒单其实就是将订单状态修改为“已取消”
  • 只有订单处于“待接单”状态时可以执行拒单操作
  • 商家拒单时需要指定拒单原因
  • 商家拒单时,如果用户已经完成了支付,需要为用户退款

思路:
根据业务规则依次实现即可

6. 取消订单

产品原型:
商家端点击取消订单
接口设计:
在这里插入图片描述
请求体传参:封装了id和订单取消原因cancelReason的OrdersCancelDTO类

业务规则:

  • 取消订单其实就是将订单状态修改为“已取消”
  • 商家取消订单时需要指定取消原因
  • 商家取消订单时,如果用户已经完成了支付,需要为用户退款

思路:
根据业务规则依次实现即可

7. 派送订单

产品原型:
商家端点击派送订单
接口设计:
在这里插入图片描述
url传参:id

业务规则:

  • 派送订单其实就是将订单状态修改为“派送中”
  • 只有状态为“待派送”的订单可以执行派送订单操作

思路:
根据业务规则依次实现即可

8. 完成订单

产品原型:
商家端点击完成订单
接口设计:
在这里插入图片描述
url传参:id

业务规则:

  • 完成订单其实就是将订单状态修改为“已完成”
  • 只有状态为“派送中”的订单可以执行订单完成操作

思路:
根据业务规则依次实现即可

三.重点:校验收货地址是否超出配送范围

思路:调用百度地图的API,将商家的地址和用户的收货地址转换为经纬值,计算两者之间的距离,若小于某个距离则可以进行下单操作,反之抛出错误异常信息

实现思路:
1.地址连接:百度地图开发平台

2.找到Web服务API总览:
在这里插入图片描述
实现方式就是调用其中的两个API接口
在这里插入图片描述

1.地址编码API

地址编码的开发文档中可以找到API服务地址,请求参数和返回参数
在这里插入图片描述
请求参数和返回参数中重要的参数如下:
在这里插入图片描述
在这里插入图片描述
通过观察文档可知,给地址编码的API一个地址就能返回这个地址所对应的经纬值

2.轻量级路线规划服务

轻量级路线规划服务的开发文档中可以找到API服务地址,请求参数和返回参数
在这里插入图片描述
请求参数中重要的参数如下:
在这里插入图片描述
返回参数中重要的参数如下:
在这里插入图片描述
通过观察文档可知,通过传入起点和终点的经纬值就可以返回方案的距离,获得距离就可以判断是否满足配送距离要求

代码实现:
1.配置商家端的地址信息在配置文件(yml)中
2.在OrderServiceImpl中注入商家的地址和调用API所需的ak属性值

	@Value("${sky.shop.address}")
    private String shopAddress;

	@Value("${sky.baidu.ak}")
    private String ak;

在OrderServiceImpl中提供校验方法:

/**
     * 检查客户的收货地址是否超出配送范围
     * @param address
     */
    private void checkOutOfRange(String address) {
        Map map = new HashMap();
        map.put("address",shopAddress);
        map.put("output","json");
        map.put("ak",ak);

        //获取店铺的经纬度坐标
        String shopCoordinate = HttpClientUtil.doGet("https://api.map.baidu.com/geocoding/v3", map);

        JSONObject jsonObject = JSON.parseObject(shopCoordinate);
        if(!jsonObject.getString("status").equals("0")){
            throw new OrderBusinessException("店铺地址解析失败");
        }

        //数据解析
        JSONObject location = jsonObject.getJSONObject("result").getJSONObject("location");
        String lat = location.getString("lat");
        String lng = location.getString("lng");
        //店铺经纬度坐标
        String shopLngLat = lat + "," + lng;

        map.put("address",address);
        //获取用户收货地址的经纬度坐标
        String userCoordinate = HttpClientUtil.doGet("https://api.map.baidu.com/geocoding/v3", map);

        jsonObject = JSON.parseObject(userCoordinate);
        if(!jsonObject.getString("status").equals("0")){
            throw new OrderBusinessException("收货地址解析失败");
        }

        //数据解析
        location = jsonObject.getJSONObject("result").getJSONObject("location");
        lat = location.getString("lat");
        lng = location.getString("lng");
        //用户收货地址经纬度坐标
        String userLngLat = lat + "," + lng;

        map.put("origin",shopLngLat);
        map.put("destination",userLngLat);
        map.put("steps_info","0");

        //路线规划
        String json = HttpClientUtil.doGet("https://api.map.baidu.com/directionlite/v1/driving", map);

        jsonObject = JSON.parseObject(json);
        if(!jsonObject.getString("status").equals("0")){
            throw new OrderBusinessException("配送路线规划失败");
        }

        //数据解析
        JSONObject result = jsonObject.getJSONObject("result");
        JSONArray jsonArray = (JSONArray) result.get("routes");
        Integer distance = (Integer) ((JSONObject) jsonArray.get(0)).get("distance");

        if(distance > 5000){
            //配送距离超过5000米
            throw new OrderBusinessException("超出配送范围");
        }
    }

前面的课程中使用HttpClient次数很多了,代码并不复杂,难点是自己能分析出请求参数和返回参数和逻辑方面的判断

在OrderServiceImpl的submitOrder方法中调用上面的校验方法完成校验:

checkOutOfRange(addressBook.getCityName()+addressBook.getDistrictName()+addressBook.getDetail());
<think>好的,我现在需要帮助用户了解如何在苍穹外卖小程序中查看历史订单的功能实现。首先,我得仔细看看用户提供的引用内容,里面提到了用户端历史订单的查询、取消订单、再来一单等操作,还有一些接口设计和业务规则。 根据引用1、2、3,用户端历史订单查询支持分页,并且可以根据订单状态筛选。展示的数据包括下单时间、订单状态、金额以及订单明细中的商品名称和图片。接口设计中的参数有页码、每页数量、状态码,其中状态码对应不同的订单状态,比如1是待付款,2是待接单等。此外,后有一个Controller方法处理这个请求,调用Service层的pageQuery4User方法返回分页结果。 用户还提到引用4,指出订单不显示的问题可能与日期格式处理有关,需要在WebMvcConfiguration中扩展消息转换器。这说明前端在显示订单时,后必须正确格式化日期字段,否则可能导致前端无法解析,从而不显示订单。 现在需要把这些信息整合成一个清晰的步骤说明。首先,用户需要进入历史订单页面,然后选择状态筛选或直接查看全部订单。系统分页加载数据,每个订单显示关键信息。后处理分页参数,查询数据库,并格式化日期,最后返回给前端展示。 可能需要注意的点包括分页逻辑的实现、状态参数的传递和转换、日期格式化处理,以及订单明细的数据结构如何包含商品名称和图片。此外,前端可能需要处理图片的加载和显示,确保图片路径正确。 还要考虑用户可能遇到的问题,比如订单不显示的情况,可能的原因包括日期格式不正确、分页参数错误、状态参数未正确传递等。根据引用4,日期格式化是常见问题,需要检查后的消息转换器配置是否正确。 最后,生成相关问题需要考虑用户可能进一步想了解的,比如如何取消订单、再来一单的实现逻辑,或者如何处理不同状态订单的显示差异。此外,性能优化方面,比如分页查询的效率,或者图片加载的优化也可能被问到。</think>### 苍穹外卖小程序查看历史订单功能实现步骤 #### 1. **用户端入口设计** - 在小程序个人中心页面设置“历史订单”入口,触发`/historyOrders`接口请求[^3]。 - 支持按订单状态筛选(如待付款、已完成等),状态参数对应关系为:`1`待付款,`2`待接单,`3`已接单,`4`派送中,`5`已完成,`6`已取消。 #### 2. **分页查询实现** - **参数传递**:前端传递`page`(页码)、`pageSize`(每页数量)、`status`(可选状态码)至后。 - **SQL处理**:后通过`PageHelper`等工具实现分页查询,筛选符合条件的订单数据[^3]。 - **示例查询逻辑**: ```sql SELECT order_id, create_time, status, amount FROM orders WHERE user_id = #{userId} AND (status = #{status} OR #{status} IS NULL) ORDER BY create_time DESC ``` #### 3. **数据展示规则** - **关键字段**:展示下单时间(格式化为`yyyy-MM-dd HH:mm`)、订单状态(映射为中文)、订单金额、订单明细(含商品名称和图片)[^1][^2]。 - **日期格式化**:后需统一处理日期格式,避免前端显示异常(通过`WebMvcConfiguration`配置`Jackson`的日期格式)[^4]。 #### 4. **接口设计与实现** - **Controller层**:定义RESTful接口接收参数,调用Service层逻辑。 ```java @GetMapping("/historyOrders") public Result<PageResult> queryHistoryOrders( @RequestParam int page, @RequestParam int pageSize, @RequestParam(required = false) Integer status) { PageResult result = orderService.pageQuery4User(page, pageSize, status); return Result.success(result); } ``` - **Service层**:处理业务逻辑,关联查询订单明细表获取商品信息。 #### 5. **关联数据查询** - **订单明细加载**:通过`JOIN`查询获取商品名称和图片URL。 ```sql SELECT o.*, od.name AS dish_name, od.image FROM orders o LEFT JOIN order_detail od ON o.id = od.order_id WHERE o.user_id = #{userId} ``` #### 6. **前端渲染** - 使用滚动加载(或分页器)实现分页交互。 - 图片显示需通过`<image>`组件绑定查询结果中的`image`字段URL。
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值