• 苍穹外卖 day12 Echats 营业台数据可视化整合


    苍穹外卖-day12

    课程内容

    • 工作台
    • Apache POI
    • 导出运营数据Excel报表

    功能实现:工作台数据导出

    工作台效果图:

    数据导出效果图:

    数据统计页面点击数据导出:生成Excel报表

    1. 工作台

    1.1 需求分析和设计

    1.1.1 产品原型

    工作台是系统运营的数据看板,并提供快捷操作入口,可以有效提高商家的工作效率。

    工作台展示的数据:

    • 今日数据
    • 订单管理
    • 菜品总览
    • 套餐总览
    • 订单信息

    原型图:

    名词解释:

    • 营业额:已完成订单的总金额
    • 有效订单:已完成订单的数量
    • 订单完成率:有效订单数 / 总订单数 * 100%
    • 平均客单价:营业额 / 有效订单数
    • 新增用户:新增用户的数量
    1.1.2 接口设计

    通过上述原型图分析,共包含6个接口。

    接口设计:

    • 今日数据接口
    • 订单管理接口
    • 菜品总览接口
    • 套餐总览接口
    • 订单搜索(已完成)
    • 各个状态的订单数量统计(已完成)

    1). 今日数据的接口设计

    2). 订单管理的接口设计

    3). 菜品总览的接口设计

    4). 套餐总览的接口设计

    1.2 代码导入

    直接导入课程资料中的工作台模块功能代码即可:

    1.2.1 Controller层

    添加WorkSpaceController.java

    1. package com.sky.controller.admin;
    2. import com.sky.result.Result;
    3. import com.sky.service.WorkspaceService;
    4. import com.sky.vo.BusinessDataVO;
    5. import com.sky.vo.DishOverViewVO;
    6. import com.sky.vo.OrderOverViewVO;
    7. import com.sky.vo.SetmealOverViewVO;
    8. import io.swagger.annotations.Api;
    9. import io.swagger.annotations.ApiOperation;
    10. import lombok.extern.slf4j.Slf4j;
    11. import org.springframework.beans.factory.annotation.Autowired;
    12. import org.springframework.web.bind.annotation.GetMapping;
    13. import org.springframework.web.bind.annotation.RequestMapping;
    14. import org.springframework.web.bind.annotation.RestController;
    15. import java.time.LocalDateTime;
    16. import java.time.LocalTime;
    17. /**
    18. * 工作台
    19. */
    20. @RestController
    21. @RequestMapping("/admin/workspace")
    22. @Slf4j
    23. @Api(tags = "工作台相关接口")
    24. public class WorkSpaceController {
    25. @Autowired
    26. private WorkspaceService workspaceService;
    27. /**
    28. * 工作台今日数据查询
    29. * @return
    30. */
    31. @GetMapping("/businessData")
    32. @ApiOperation("工作台今日数据查询")
    33. public Result businessData(){
    34. //获得当天的开始时间
    35. LocalDateTime begin = LocalDateTime.now().with(LocalTime.MIN);
    36. //获得当天的结束时间
    37. LocalDateTime end = LocalDateTime.now().with(LocalTime.MAX);
    38. BusinessDataVO businessDataVO = workspaceService.getBusinessData(begin, end);
    39. return Result.success(businessDataVO);
    40. }
    41. /**
    42. * 查询订单管理数据
    43. * @return
    44. */
    45. @GetMapping("/overviewOrders")
    46. @ApiOperation("查询订单管理数据")
    47. public Result orderOverView(){
    48. return Result.success(workspaceService.getOrderOverView());
    49. }
    50. /**
    51. * 查询菜品总览
    52. * @return
    53. */
    54. @GetMapping("/overviewDishes")
    55. @ApiOperation("查询菜品总览")
    56. public Result dishOverView(){
    57. return Result.success(workspaceService.getDishOverView());
    58. }
    59. /**
    60. * 查询套餐总览
    61. * @return
    62. */
    63. @GetMapping("/overviewSetmeals")
    64. @ApiOperation("查询套餐总览")
    65. public Result setmealOverView(){
    66. return Result.success(workspaceService.getSetmealOverView());
    67. }
    68. }
    1.2.2 Service层接口

    添加WorkspaceService.java

    1. package com.sky.service;
    2. import com.sky.vo.BusinessDataVO;
    3. import com.sky.vo.DishOverViewVO;
    4. import com.sky.vo.OrderOverViewVO;
    5. import com.sky.vo.SetmealOverViewVO;
    6. import java.time.LocalDateTime;
    7. public interface WorkspaceService {
    8. /**
    9. * 根据时间段统计营业数据
    10. * @param begin
    11. * @param end
    12. * @return
    13. */
    14. BusinessDataVO getBusinessData(LocalDateTime begin, LocalDateTime end);
    15. /**
    16. * 查询订单管理数据
    17. * @return
    18. */
    19. OrderOverViewVO getOrderOverView();
    20. /**
    21. * 查询菜品总览
    22. * @return
    23. */
    24. DishOverViewVO getDishOverView();
    25. /**
    26. * 查询套餐总览
    27. * @return
    28. */
    29. SetmealOverViewVO getSetmealOverView();
    30. }
    1.2.3 Service层实现类

    添加WorkspaceServiceImpl.java

    1. package com.sky.service.impl;
    2. import com.sky.constant.StatusConstant;
    3. import com.sky.entity.Orders;
    4. import com.sky.mapper.DishMapper;
    5. import com.sky.mapper.OrderMapper;
    6. import com.sky.mapper.SetmealMapper;
    7. import com.sky.mapper.UserMapper;
    8. import com.sky.service.WorkspaceService;
    9. import com.sky.vo.BusinessDataVO;
    10. import com.sky.vo.DishOverViewVO;
    11. import com.sky.vo.OrderOverViewVO;
    12. import com.sky.vo.SetmealOverViewVO;
    13. import lombok.extern.slf4j.Slf4j;
    14. import org.springframework.beans.factory.annotation.Autowired;
    15. import org.springframework.stereotype.Service;
    16. import java.time.LocalDateTime;
    17. import java.time.LocalTime;
    18. import java.util.HashMap;
    19. import java.util.Map;
    20. @Service
    21. @Slf4j
    22. public class WorkspaceServiceImpl implements WorkspaceService {
    23. @Autowired
    24. private OrderMapper orderMapper;
    25. @Autowired
    26. private UserMapper userMapper;
    27. @Autowired
    28. private DishMapper dishMapper;
    29. @Autowired
    30. private SetmealMapper setmealMapper;
    31. /**
    32. * 根据时间段统计营业数据
    33. * @param begin
    34. * @param end
    35. * @return
    36. */
    37. public BusinessDataVO getBusinessData(LocalDateTime begin, LocalDateTime end) {
    38. /**
    39. * 营业额:当日已完成订单的总金额
    40. * 有效订单:当日已完成订单的数量
    41. * 订单完成率:有效订单数 / 总订单数
    42. * 平均客单价:营业额 / 有效订单数
    43. * 新增用户:当日新增用户的数量
    44. */
    45. Map map = new HashMap();
    46. map.put("begin",begin);
    47. map.put("end",end);
    48. //查询总订单数
    49. Integer totalOrderCount = orderMapper.countByMap(map);
    50. map.put("status", Orders.COMPLETED);
    51. //营业额
    52. Double turnover = orderMapper.sumByMap(map);
    53. turnover = turnover == null? 0.0 : turnover;
    54. //有效订单数
    55. Integer validOrderCount = orderMapper.countByMap(map);
    56. Double unitPrice = 0.0;
    57. Double orderCompletionRate = 0.0;
    58. if(totalOrderCount != 0 && validOrderCount != 0){
    59. //订单完成率
    60. orderCompletionRate = validOrderCount.doubleValue() / totalOrderCount;
    61. //平均客单价
    62. unitPrice = turnover / validOrderCount;
    63. }
    64. //新增用户数
    65. Integer newUsers = userMapper.countByMap(map);
    66. return BusinessDataVO.builder()
    67. .turnover(turnover)
    68. .validOrderCount(validOrderCount)
    69. .orderCompletionRate(orderCompletionRate)
    70. .unitPrice(unitPrice)
    71. .newUsers(newUsers)
    72. .build();
    73. }
    74. /**
    75. * 查询订单管理数据
    76. *
    77. * @return
    78. */
    79. public OrderOverViewVO getOrderOverView() {
    80. Map map = new HashMap();
    81. map.put("begin", LocalDateTime.now().with(LocalTime.MIN));
    82. map.put("status", Orders.TO_BE_CONFIRMED);
    83. //待接单
    84. Integer waitingOrders = orderMapper.countByMap(map);
    85. //待派送
    86. map.put("status", Orders.CONFIRMED);
    87. Integer deliveredOrders = orderMapper.countByMap(map);
    88. //已完成
    89. map.put("status", Orders.COMPLETED);
    90. Integer completedOrders = orderMapper.countByMap(map);
    91. //已取消
    92. map.put("status", Orders.CANCELLED);
    93. Integer cancelledOrders = orderMapper.countByMap(map);
    94. //全部订单
    95. map.put("status", null);
    96. Integer allOrders = orderMapper.countByMap(map);
    97. return OrderOverViewVO.builder()
    98. .waitingOrders(waitingOrders)
    99. .deliveredOrders(deliveredOrders)
    100. .completedOrders(completedOrders)
    101. .cancelledOrders(cancelledOrders)
    102. .allOrders(allOrders)
    103. .build();
    104. }
    105. /**
    106. * 查询菜品总览
    107. *
    108. * @return
    109. */
    110. public DishOverViewVO getDishOverView() {
    111. Map map = new HashMap();
    112. map.put("status", StatusConstant.ENABLE);
    113. Integer sold = dishMapper.countByMap(map);
    114. map.put("status", StatusConstant.DISABLE);
    115. Integer discontinued = dishMapper.countByMap(map);
    116. return DishOverViewVO.builder()
    117. .sold(sold)
    118. .discontinued(discontinued)
    119. .build();
    120. }
    121. /**
    122. * 查询套餐总览
    123. *
    124. * @return
    125. */
    126. public SetmealOverViewVO getSetmealOverView() {
    127. Map map = new HashMap();
    128. map.put("status", StatusConstant.ENABLE);
    129. Integer sold = setmealMapper.countByMap(map);
    130. map.put("status", StatusConstant.DISABLE);
    131. Integer discontinued = setmealMapper.countByMap(map);
    132. return SetmealOverViewVO.builder()
    133. .sold(sold)
    134. .discontinued(discontinued)
    135. .build();
    136. }
    137. }
    1.2.4 Mapper层

    在SetmealMapper中添加countByMap方法定义

    1. /**
    2. * 根据条件统计套餐数量
    3. * @param map
    4. * @return
    5. */
    6. Integer countByMap(Map map);

    在SetmealMapper.xml中添加对应SQL实现

    1. <select id="countByMap" resultType="java.lang.Integer">
    2. select count(id) from setmeal
    3. <where>
    4. <if test="status != null">
    5. and status = #{status}
    6. </if>
    7. <if test="categoryId != null">
    8. and category_id = #{categoryId}
    9. </if>
    10. </where>
    11. </select>

    在DishMapper中添加countByMap方法定义

    1. /**
    2. * 根据条件统计菜品数量
    3. * @param map
    4. * @return
    5. */
    6. Integer countByMap(Map map);

    在DishMapper.xml中添加对应SQL实现

    1. <select id="countByMap" resultType="java.lang.Integer">
    2. select count(id) from dish
    3. <where>
    4. <if test="status != null">
    5. and status = #{status}
    6. </if>
    7. <if test="categoryId != null">
    8. and category_id = #{categoryId}
    9. </if>
    10. </where>
    11. </select>

    1.3 功能测试

    可以通过如下方式进行测试:

    • 通过接口文档测试
    • 前后端联调测试

    接下来我们使用上述两种方式分别测试。

    1.3.1 接口文档测试

    启动服务,访问http://localhost:8080/doc.html,进入工作台相关接口

    注意:使用admin用户登录重新获取token,在全局参数设置中添加,防止token失效

    1). 今日数据查询

    2). 菜品总览查询

    3). 订单管理数据查询

    4). 套餐总览查询

    1.3.2 前后端联调测试

    启动nginx,访问 http://localhost,进入工作台

    进入开发者模式,分别查看今日数据、订单管理、菜品总览、套餐总览

    1). 今日数据查询

    2). 订单管理数据查询

    3). 菜品总览查询

    4). 套餐总览查询

    1.4 代码提交

    后续步骤和其它功能代码提交一致,不再赘述。

  • 相关阅读:
    AM@2个极限存在准则及其应用
    RabbitMQ 高级特性
    计算机视觉与图形学-神经渲染专题-NeRF汇总大礼包-I
    [单片机框架][bsp层][N32G4FR][bsp_adc] ADC配置和使用
    React 组件
    分享几个常用的可以从外部攻击视角发现甲方公司安全问题的开源工具
    zookeeper整理:paxos算法学习
    阿里巴巴店铺的所有商品API接口(item_search_shop-获得店铺的所有商品接口),阿里巴巴API接口
    Java Spring Boot----ruoyi项目部署 前后端分离
    C#开发的OpenRA游戏之调试菜单2
  • 原文地址:https://blog.csdn.net/m0_67184231/article/details/132713674