暂无图片
暂无图片
暂无图片
暂无图片
暂无图片

为什么我推荐你使用 MongoDB 实现物流订单系统

哈喽沃德先生 2021-05-16
458

温馨提示:本案例图文并茂,代码齐全(包括前端)大家只需要跟着文章一步步学习即可实现。想要一步到位直接获取代码的同学,请关注微信公众号「哈喽沃德先生」回复 logistics
即可

电商购物或者快递发送相信每个人都经历过,每个订单的背后都关联着一连串的物流信息,每到达一个地点更新一次,直到用户签收为止。

普通人可能只享受收快递时的那种喜悦了,身为一名合格的程序员必须搞清楚其背后的实现原理。安排!

本文将通过 Spring Boot + MongoDB + Layui 实现一个简易版的物流订单管理系统,方便大家理解背后的原理。

案例分析


正好最近使用顺丰快递了一批东西回老家,参考顺丰的物流流程大致如下:

根据上图可以得知如果要实现这个功能,采用关系型数据库最起码要两张表:订单表和物流表。


MySQL


订单表 order


物流表 logistics


SQL

SELECT
 o.id,
 o.`status`,
 o.order_time,
 o.shipper,
 o.shipper_address,
 o.shipper_phone,
 o.ship_time,
 o.receiver,
 o.receiver_address,
 o.receiver_phone,
 l.operation,
 l.operator,
 l.phone,
 l.address,
 l.operation_time,
 l.details 
FROM
 `order` o
 LEFT JOIN logistics l ON o.id = l.order_id 
WHERE
 o.id = 1368198081836879872;

复制

通过分析发现关系型数据库完全可以胜任这个工作,但是随着物流运输的过程,订单表需要不断的更新,物流表需要不断的添加新的记录。眼光放长远去看,例如顺丰这样的公司,全国每天下单量总和可能会几百万甚至几千万(注意是每天),在这样的体量下,肯定会有性能瓶颈而需要优化,且存储在关系型数据库费钱(存储成本)又费力(优化成本)。


MongoDB


如果使用 MongoDB 来做这件事,上述问题都会迎刃而解:

  • 体量问题(支持单机、主从集群、副本集集群、分片集群,提供冗余及自动故障转移,可以动态添加或移除节点)
  • 成本问题(可以存储大尺寸、低价值数据)
  • 优化问题(完整的索引支持,BSON 结构对象存储,可以动态添加、修改、删除字段,操作更方便)
  • 性能问题(底层 C++ 编写,性能优秀)
  • 学习问题(部署简单,Java 程序员配合 Spring Data 轻松上手)


比如刚才两张表的数据,可以直接存储在一个集合中(嵌套文档)即可。假设后期市场需求变更需要添加字段,莫急,随时添加随时使用。数据越存越多,不慌,自动分片功能支持水平的数据库集群,可动态添加额外的机器。并且 MongoDB 支持 GIS 功能,非常适用于 MongoDB 来支撑物流业务。

综上所述,你懂的,废话不多说,下面进入实战环节。

下图来自:https://db-engines.com/en/ranking


准备工作


环境



MongoDB


为了方便省事,直接使用可视化客户端管理工具创建一个 example
数据库。


Spring Boot


创建项目


使用 Spring Initializr
初始化 Spring Boot 项目,添加 Spring Web
Spring Data MongoDB
Lombok

顺便再添加 hutool
工具集,方便根据雪花算法生成订单编号。

<dependency>
    <groupId>cn.hutool</groupId>
    <artifactId>hutool-all</artifactId>
    <version>5.5.9</version>
</dependency>

复制


配置文件


application.yml 配置 MongoDB 服务器的 example 数据库。

spring:
  data:
    mongodb:
      uri: mongodb://192.168.10.101:27017/example

复制


前端


使用 CDN 替换 CSS、JS 免去下载文件的过程。

<link href="//lib.baomitu.com/layui/2.5.7/css/layui.min.css" rel="stylesheet">
<script src="//lib.baomitu.com/layui/2.5.7/layui.min.js"></script>

复制


index.html


参考:https://www.layui.com/doc/element/layout.html#admin

index.html 最终修改如下,将该文件放入项目 resources
目录下的 static
目录中。

<!DOCTYPE html>
<html>
<head>
  <meta charset="utf-8">
  <meta name="viewport" content="width=device-width, initial-scale=1, maximum-scale=1">
  <title>物流订单管理系统</title>
  <link href="//lib.baomitu.com/layui/2.5.7/css/layui.min.css" rel="stylesheet">
</head>
<body class="layui-layout-body">
<div class="layui-layout layui-layout-admin">
  <div class="layui-header">
    <div class="layui-logo">物流订单管理系统</div>
    <!-- 头部区域(可配合layui已有的水平导航) -->
    <ul class="layui-nav layui-layout-right">
      <li class="layui-nav-item">
        <a href="javascript:;">
          <img src="https://mrhelloworld.com/resources/mrhelloworld/logo/avatar.jpg" class="layui-nav-img">
          哈喽沃德先生
        </a>
        <dl class="layui-nav-child">
          <dd><a href="">基本资料</a></dd>
          <dd><a href="">安全设置</a></dd>
        </dl>
      </li>
      <li class="layui-nav-item"><a href="">安全退出</a></li>
    </ul>
  </div>

  <div class="layui-side layui-bg-black">
    <div class="layui-side-scroll">
      <!-- 左侧导航区域(可配合layui已有的垂直导航) -->
      <ul class="layui-nav layui-nav-tree" lay-filter="test">
        <li class="layui-nav-item layui-nav-itemed">
          <a class="" href="javascript:;">订单管理</a>
          <dl class="layui-nav-child">
            <dd><a href="order-manage.html" target="container">订单管理</a></dd>
            <dd><a href="add-order.html" target="container">订单添加</a></dd>
            <dd><a href="add-logistics.html" target="container">物流添加</a></dd>
          </dl>
        </li>
      </ul>
    </div>
  </div>

  <div class="layui-body">
    <!-- 内容主体区域 -->
    <iframe src="add-order.html" name="container" width="100%" height="100%"></iframe>
  </div>

  <div class="layui-footer">
    <!-- 底部固定区域 -->
    https://mrhelloworld.com - 哈喽沃德先生
  </div>
</div>
<script src="//lib.baomitu.com/layui/2.5.7/layui.min.js"></script>
<script>
  //JavaScript代码区域
  layui.use('element'function ({
    var element = layui.element;

  });
</script>
</body>
</html>

复制


add-order.html


创建文件先写个订单添加等后续功能开发时再做处理。

将该文件放入项目 resources
目录下的 static
目录中。

订单添加

复制


add-logistics.html


创建文件先写个物流添加等后续功能开发时再做处理。

将该文件放入项目 resources
目录下的 static
目录中。

物流添加

复制


order-manage.html


创建文件先写个订单管理等后续功能开发时再做处理。

将该文件放入项目 resources
目录下的 static
目录中。

订单管理

复制


启动


访问:http://localhost:8080/index.html 效果如下:


功能开发


实体类


Order.java


package com.example.pojo;

import com.fasterxml.jackson.annotation.JsonFormat;
import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;

import java.io.Serializable;
import java.util.Date;
import java.util.List;

@Data
@NoArgsConstructor
@AllArgsConstructor
public class Order implements Serializable {

    private static final long serialVersionUID = 2298879574024937430L;
    private String id; // 订单编号
    private String status; // 订单状态
    @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss", timezone = "GMT+8")
    private Date orderTime; // 下单时间
    private String shipper; // 发货人
    private String shipperAddress; // 发货人地址
    private String shipperPhone; // 发货人电话
    @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss", timezone = "GMT+8")
    private Date shipTime; // 发货时间
    private String receiver; // 收货人
    private String receiverAddress; // 收货人地址
    private String receiverPhone; // 收货人电话
    private List<Logistics> logistics; // 物流信息

}

复制


Logistics.java


package com.example.pojo;

import com.fasterxml.jackson.annotation.JsonFormat;
import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;

import java.io.Serializable;
import java.util.Date;

@Data
@NoArgsConstructor
@AllArgsConstructor
public class Logistics implements Serializable {

    private static final long serialVersionUID = -7416584494933994605L;
    private String orderId; // 订单编号
    private String operation; // 操作名称
    private String operator; // 操作员
    private String phone; // 操作员电话
    @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss", timezone = "GMT+8")
    private Date operationTime; // 操作时间
    private String address; // 操作地址
    private String details; // 详细信息

}

复制


订单添加


OrderService.java


package com.example.service;

import cn.hutool.core.util.IdUtil;
import com.example.pojo.Order;
import org.springframework.data.mongodb.core.MongoTemplate;
import org.springframework.stereotype.Service;

import javax.annotation.Resource;
import java.util.Date;

/**
 * @author 哈喽沃德先生
 * @微信公众号 哈喽沃德先生
 * @website https://mrhelloworld.com
 * @wechat 124059770
 */

@Service
public class OrderService {

    @Resource
    private MongoTemplate mongoTemplate;

    /**
     * 添加订单至 MongoDB
     *
     * @param order
     */

    public void addOrder(Order order) {
        // 订单编号根据雪花算法生成
        order.setId(IdUtil.getSnowflake(11).nextIdStr());
        // 设置订单状态
        order.setStatus("已下单");
        // 设置下单时间
        order.setOrderTime(new Date());
        // 设置发货时间
        order.setShipTime(new Date());
        // 添加订单至 MongoDB
        mongoTemplate.insert(order, "order");
    }

}

复制


OrderController.java


package com.example.controller;

import com.example.pojo.Order;
import com.example.service.OrderService;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;

import javax.annotation.Resource;

/**
 * @author 哈喽沃德先生
 * @微信公众号 哈喽沃德先生
 * @website https://mrhelloworld.com
 * @wechat 124059770
 */

@RestController
@RequestMapping("order")
public class OrderController {

    @Resource
    private OrderService orderService;

    /**
     * 添加订单至 MongoDB
     *
     * @param order
     */

    @PostMapping("add")
    public String addOrder(Order order) {
        orderService.addOrder(order);
        return "订单添加成功";
    }

}

复制


add-order.html


参考:

  • https://www.layui.com/demo/form.html (表单)
  • https://www.layui.com/demo/panel.html (面板)

add-order.html 最终修改如下。

注意:form 表单中 input 标签的 name 属性值对应实体类 Order 的属性名。记得添加 jQuery。

<!DOCTYPE html>
<html>
<head>
  <meta charset="utf-8">
  <meta name="viewport" content="width=device-width, initial-scale=1, maximum-scale=1">
  <title>订单添加</title>
  <link href="//lib.baomitu.com/layui/2.5.7/css/layui.min.css" rel="stylesheet">
</head>
<body>
<fieldset class="layui-elem-field layui-field-title" style="margin-top: 20px;">
  <legend>订单添加</legend>
</fieldset>
<div class="layui-card">
  <div class="layui-card-body">
    <form class="layui-form" action="">
      <div class="layui-form-item">
        <label class="layui-form-label">发货人</label>
        <div class="layui-input-block">
          <input type="text" name="shipper" autocomplete="off" class="layui-input" value="">
        </div>
      </div>
      <div class="layui-form-item">
        <label class="layui-form-label">发货人地址</label>
        <div class="layui-input-block">
          <input type="text" name="shipperAddress" autocomplete="off" class="layui-input" value="">
        </div>
      </div>
      <div class="layui-form-item">
        <label class="layui-form-label">发货人电话</label>
        <div class="layui-input-block">
          <input type="text" name="shipperPhone" autocomplete="off" class="layui-input" value="">
        </div>
      </div>
      <div class="layui-form-item">
        <label class="layui-form-label">收货人</label>
        <div class="layui-input-block">
          <input type="text" name="receiver" autocomplete="off" class="layui-input" value="">
        </div>
      </div>
      <div class="layui-form-item">
        <label class="layui-form-label">收货人地址</label>
        <div class="layui-input-block">
          <input type="text" name="receiverAddress" autocomplete="off" class="layui-input" value="">
        </div>
      </div>
      <div class="layui-form-item">
        <label class="layui-form-label">收货人电话</label>
        <div class="layui-input-block">
          <input type="text" name="receiverPhone" autocomplete="off" class="layui-input" value="">
        </div>
      </div>

      <div class="layui-form-item">
        <div class="layui-input-block">
          <button class="layui-btn" lay-submit lay-filter="formDemo">提交</button>
          <button type="reset" class="layui-btn layui-btn-primary">重置</button>
        </div>
      </div>
    </form>
  </div>
</div>
<script src="//lib.baomitu.com/jquery/3.6.0/jquery.min.js"></script>
<script src="//lib.baomitu.com/layui/2.5.7/layui.min.js"></script>
<script>
  //Demo
  layui.use('form'function ({
    var form = layui.form;

    //监听提交
    form.on('submit(formDemo)'function (data{
      $.ajax({
        url'http://localhost:8080/order/add',
        type"POST",
        data: data.field,
        dataType"JSON",
        successfunction (result{
          layer.msg(result);
        }
      });
      return false;
    });
  });
</script>
</body>

复制


测试


访问:http://localhost:8080/index.html 填写表单信息并提交。

MongoDB 数据库。


物流添加(订单更新)


OrderService.java


/**
 * 更新订单信息
 * 追加物流信息
 *
 * @param logistics
 */

public void updateOrderAndAddLogistics(Logistics logistics) {
    // 获取操作名称
    String status = logistics.getOperation();
    // 设置操作时间
    logistics.setOperationTime(new Date());
    // 初始化 Query 对象,根据订单编号查询
    Query query = new Query(Criteria.where("_id").is(logistics.getOrderId()));
    // 初始化 Update 对象
    Update update = new Update();
    // 更新订单状态
    update.set("status", status);
    // 追加物流信息,物流信息由多个物流数据组成,使用 push() 追加
    update.push("logistics", logistics);
    // 更新订单信息
    mongoTemplate.upsert(query, update, Order.class, "order");
}

复制


OrderController.java


/**
 * 更新订单信息
 * 添加物流信息
 *
 * @param logistics
 */

@PostMapping("update")
public String updateOrderAndAddLogistics(Logistics logistics) {
    orderService.updateOrderAndAddLogistics(logistics);
    return "物流添加成功";
}

复制


add-logistics.html


参考:

  • https://www.layui.com/demo/form.html (表单)
  • https://www.layui.com/demo/panel.html (面板)

add-logistics.html 最终修改如下。

注意:form 表单中 input 标签的 name 属性值对应实体类 Logistics 的属性名。

<!DOCTYPE html>
<html>
<head>
  <meta charset="utf-8">
  <meta name="viewport" content="width=device-width, initial-scale=1, maximum-scale=1">
  <title>物流添加</title>
  <link href="//lib.baomitu.com/layui/2.5.7/css/layui.min.css" rel="stylesheet">
</head>
<body>
<fieldset class="layui-elem-field layui-field-title" style="margin-top: 20px;">
  <legend>物流添加</legend>
</fieldset>
<div class="layui-card">
  <div class="layui-card-body">
    <form class="layui-form" action="">
      <div class="layui-form-item">
        <label class="layui-form-label">订单编号</label>
        <div class="layui-input-block">
          <input type="text" name="orderId" autocomplete="off" class="layui-input" value="">
        </div>
      </div>
      <div class="layui-form-item">
        <label class="layui-form-label">操作名称</label>
        <div class="layui-input-block">
          <select name="operation" lay-filter="aihao">
            <option value="">请选择</option>
            <option value="已取件">已取件</option>
            <option value="运送中">运送中</option>
            <option value="派送中">派送中</option>
            <option value="已签收">已签收</option>
          </select>
        </div>
      </div>
      <div class="layui-form-item">
        <label class="layui-form-label">操作员</label>
        <div class="layui-input-block">
          <input type="text" name="operator" autocomplete="off" class="layui-input" value="">
        </div>
      </div>
      <div class="layui-form-item">
        <label class="layui-form-label">操作员电话</label>
        <div class="layui-input-block">
          <input type="text" name="phone" autocomplete="off" class="layui-input" value="">
        </div>
      </div>
      <div class="layui-form-item">
        <label class="layui-form-label">操作地址</label>
        <div class="layui-input-block">
          <input type="text" name="address" autocomplete="off" class="layui-input" value="">
        </div>
      </div>
      <div class="layui-form-item">
        <label class="layui-form-label">详细信息</label>
        <div class="layui-input-block">
          <input type="text" name="details" autocomplete="off" class="layui-input" value="">
        </div>
      </div>

      <div class="layui-form-item">
        <div class="layui-input-block">
          <button class="layui-btn" lay-submit lay-filter="formDemo">提交</button>
          <button type="reset" class="layui-btn layui-btn-primary">重置</button>
        </div>
      </div>
    </form>
  </div>
</div>
<script src="//lib.baomitu.com/jquery/3.6.0/jquery.min.js"></script>
<script src="//lib.baomitu.com/layui/2.5.7/layui.min.js"></script>
<script>
  // Demo
  layui.use('form'function ({
    var form = layui.form;

    //监听提交
    form.on('submit(formDemo)'function (data{
      $.ajax({
        url'http://localhost:8080/order/update',
        type"POST",
        data: data.field,
        dataType"JSON",
        successfunction (result{
          layer.msg(result);
        }
      });
      return false;
    });
  });
</script>
</body>

复制


测试


访问:http://localhost:8080/index.html 选择物流添加,填写表单信息并提交。

提示:操作员、操作员电话、操作地址是对物流信息的一个后台记录,用户界面无需展示。

MongoDB 数据库。


模拟真实物流


接下来让我们模拟真实物流,多添加一些物流信息。

  • 已取件:顺丰速运已收取快件
  • 运送中:快件在【北京市海淀区XX营业点】完成分拣,准备发往【北京海淀集散点】
  • 运送中:快件已发车
  • 运送中:快件到达【北京海淀集散点】
  • 运送中:快件在【北京海淀集散点】完成分拣,准备发往【北京中转场】
  • 运送中:快件已发车
  • 运送中:快件到达【北京中转场】
  • 运送中:快件在【北京中转场】完成分拣,准备发往【上海中转场】
  • 运送中:快件已发车
  • 运送中:快件到达【上海中转场】
  • 运送中:快件在【上海中转场】完成分拣,准备发往【上海浦东新区集散点】
  • 运送中:快件已发车
  • 运送中:快件到达【上海浦东新区集散点】
  • 运送中:快件在【上海浦东新区集散点】完成分拣,准备发往【上海市浦东新区集配站】
  • 运送中:快件已发车
  • 运送中:快件到达【上海市浦东新区集配站】
  • 派送中:快件交给小顺子,正在派送途中(联系电话:1300000000,顺丰已开启“安全呼叫”保护您的电话隐私,请放心接听!)
  • 已签收:您的快件已签收,如有疑问请电话联系快递员【小顺子,电话:1300000000】。疫情期间顺丰每日对网点消毒、快递员每日测温、佩戴口罩,感谢您使用顺丰,期待再次为您服务。


订单管理 - 查询


主要实现根据订单编号查询订单信息,前端展示订单信息和物流信息。


OrderService.java


/**
 * 通过订单编号查询
 *
 * @param id
 * @return
 */

public Order selectOrderById(String id) {
    // 初始化 Query 对象,根据订单编号查询
    Query query = new Query(Criteria.where("_id").is(id));
    return mongoTemplate.findOne(query, Order.class, "order");
}

复制


OrderController.java


/**
 * 通过订单编号查询
 *
 * @param id
 * @return
 */

@GetMapping("{id}")
public Order selectOrderById(@PathVariable String id) {
    return orderService.selectOrderById(id);
}

复制


order-manage.html


参考:

  • https://www.layui.com/demo/panel.html (面板)

  • https://www.layui.com/demo/timeline.html (时间线)

  • https://www.layui.com/demo/button.html (按钮)

  • https://www.layui.com/doc/element/icon.html (字体图标)

order-manage.html 最终修改如下。

<!DOCTYPE html>
<html>
<head>
  <meta charset="utf-8">
  <meta name="viewport" content="width=device-width, initial-scale=1, maximum-scale=1">
  <title>订单管理</title>
  <link href="//lib.baomitu.com/layui/2.5.7/css/layui.min.css" rel="stylesheet">
</head>
<body>
<fieldset class="layui-elem-field layui-field-title" style="margin-top: 20px;">
  <legend>订单管理</legend>
</fieldset>

<div class="layui-card">
  <div class="layui-card-body">
    <div class="layui-inline">
      <label class="layui-form-label">订单编号</label>
      <div class="layui-input-inline">
        <input type="text" id="orderId" name="orderId" autocomplete="off" class="layui-input" value="">
      </div>
      <button onclick="search();" type="button" class="layui-btn"><i class="layui-icon">&#xe615;</i></button>
    </div>
  </div>
</div>

<div style="padding: 20px; background-color: #F2F2F2;">
  <div class="layui-row layui-col-space15">
    <div class="layui-col-md12">
      <div class="layui-card">
        <div class="layui-card-header">订单信息</div>
        <div class="layui-card-body" id="order">

        </div>
      </div>
    </div>
    <div class="layui-col-md12">
      <div class="layui-card">
        <div class="layui-card-header">物流信息</div>
        <div class="layui-card-body">
          <ul class="layui-timeline" id="logistics">

          </ul>
        </div>
      </div>
    </div>
  </div>
</div>

<script src="//lib.baomitu.com/jquery/3.6.0/jquery.min.js"></script>
<script src="//lib.baomitu.com/layui/2.5.7/layui.min.js"></script>
<script type="text/javascript">
  // 搜索
  function search({
    // 获取订单编号
    var orderId = $("#orderId").val();
    // 每次查询前将订单信息和物流信息清空
    $("#order").html("");
    $("#logistics").html("");
    // 异步请求
    $.ajax({
      url"http://localhost:8080/order/" + orderId,
      type"GET",
      dataType"JSON",
      // 拼接处理返回结果
      successfunction (order{
        if (order == null || order == undefined || order == "") {
          layer.msg("订单不存在");
          return;
        }
        // 处理订单信息
        $("#order").append("订单编号:" + orderId + "(" + order["status"] + ")<hr/>")
            .append("发货人:" + order["shipper"] + "<br/>")
            .append("发货人地址:" + order["shipperAddress"] + "<br/>")
            .append("发货人电话:" + order["shipperPhone"] + "<br/>")
            .append("下单时间:" + order["orderTime"] + "<br/>")
            .append("发货时间:" + order["shipTime"] + "<hr/>")
            .append("收货人:" + order["receiver"] + "<br/>")
            .append("收获人地址:" + order['receiverAddress'] + "<br/>")
            .append("收获人手机:" + order["receiverPhone"]);
        // 获取物流信息
        let logistics = order['logistics'];
        // 倒序循环
        for (var i = logistics.length - 1; i >= 0; i--) {
          // 处理物流信息
          $("#logistics").append('<li class="layui-timeline-item">' +
              '<i class="layui-icon layui-timeline-axis"></i>' +
              '<div class="layui-timeline-content layui-text">' +
              '<h3 class="layui-timeline-title">' +
              '(' + logistics[i].operation + ')' +
              logistics[i].operationTime + '</h3>' +
              '<p>' + logistics[i].details + '</p>' +
              '<p>操作员:' + logistics[i].operator + '&nbsp;' +
              '操作员电话:' + logistics[i].phone + '&nbsp;' +
              '操作地址:' + logistics[i].address + '</p></div></li>');
        }
      },
      errorfunction (order{
        layer.msg(order);
      }
    });
  }
</script>
</body>

复制


测试


访问:http://localhost:8080/index.html 选择订单管理,填写订单编号进行搜索。

提示:操作员、操作员电话、操作地址是对物流信息的一个后台记录,用户界面无需展示。


订单管理 - 删除


先查询订单列表然后根据订单编号实现订单删除。


OrderService.java


/**
 * 查询所有订单
 *
 * @return
 */

public List<Order> selectOrderList() {
    return mongoTemplate.findAll(Order.class, "order");
}

/**
 * 根据订单编号删除订单记录
 *
 * @param id
 * @return
 */

public boolean deleteOrderById(String id) {
    Query query = new Query(Criteria.where("_id").is(id));
    DeleteResult result = mongoTemplate.remove(query, Order.class, "order");
    return result.getDeletedCount() > 0 ? true : false;
}

复制


OrderController.java


订单列表使用 Layui 数据表格展示,Layui 需要特定的 JSON 格式(下图为官方 DEMO),按照要求封装数据返回。

/**
 * 查询所有订单
 *
 * @return
 */

@GetMapping("list")
public Map<String, Object> selectOrderList() {
    List<Order> list = orderService.selectOrderList();
    Map<String, Object> map = new HashMap<>();
    map.put("code""0");
    map.put("count", list.size());
    map.put("data", list);
    return map;
}

/**
 * 根据订单编号删除订单记录
 *
 * @param id
 * @return
 */

@PostMapping("delete")
public String deleteById(String id) {
    orderService.deleteOrderById(id);
    return "删除成功";
}

复制


order-manage.html


参考:

  • https://www.layui.com/doc/modules/table.html (快速使用)
  • https://www.layui.com/doc/modules/table.html#ontoolbar (监听头工具栏事件)
  • https://www.layui.com/doc/modules/table.html#ontool (监听行工具事件)

order-manage.html 添加以下代码。

<!-- 数据表格 -->
<div class="layui-card">
  <div class="layui-card-header">订单列表</div>
  <div class="layui-card-body">
    <table class="layui-hide" id="orderList" lay-filter="orderTable"></table>
  </div>
</div>
<!-- 筛选/导出/打印 -->
<script type="text/html" id="toolbarDemo">
</script>
<!-- 编辑/删除 -->
<script type="text/html" id="barDemo">
  <div class="layui-btn-container">
    <button class="layui-btn layui-btn-sm" lay-event="update">编辑</button>
    <button class="layui-btn layui-btn-danger layui-btn-sm" lay-event="delete">删除</button>
  </div>
</script>

<script type="text/javascript">
// 表格
layui.use('table'function ({
  var table = layui.table;

  table.render({
    elem'#orderList',
    url'http://localhost:8080/order/list',
    cellMinWidth80// 全局定义常规单元格的最小宽度,layui 2.2.1 新增
    toolbar'#toolbarDemo'// 筛选/导出/打印
    cols: [[
      {field'id'title'订单编号'sorttruefixed'left'},
      {field'status'title'订单状态'},
      {field'orderTime'title'下单时间'sorttrue},
      {field'shipper'title'发货人'},
      {field'shipperAddress'title'发货地址'},
      {field'shipperPhone'title'发货人电话'},
      {field'receiver'title'收货人'edit'text'},
      {field'receiverAddress'title'收货地址'},
      {field'receiverPhone'title'收货人电话'},
      {fixed'right'title'操作'toolbar'#barDemo'// 编辑/删除
    ]]
  });
  // 监听事件
  // on() 监听 lay-event="" 的元素时触发(该事件为 layui 2.4.0 开始新增)
  // tool() 监听 lay-filter="" 的元素
  // 注:tool 是工具条事件名,orderTable 是 table 原始容器的属性 lay-filter="对应的值"
  table.on('tool(orderTable)'function (obj{
    var data = obj.data; // 获得当前行数据
    // 获得 lay-event 对应的值进行比较
    if (obj.event === 'delete') {
      layer.confirm('该操作不可逆,确定删除?'function (index{
        $.ajax({
          url'http://localhost:8080/order/delete',
          method'POST',
          data: {'id': data.id},
          dataType"JSON",
          traditionaltrue,
          successfunction (msg{
            layer.msg(msg);
            obj.del(); // 删除对应行(tr)的DOM结构,并更新缓存
          },
          errorfunction (msg{
            layer.msg(msg)
          }
        });
        layer.close(index);
      });
    }
  });
});
</script>

复制


测试


访问:http://localhost:8080/index.html 选择订单管理,点击表格中对应订单的删除按钮。

MongoDB 数据库。

结语


至此 MongoDB 的实战小项目《物流订单管理系统》就完成啦,本文讲解了 Spring Boot 整合 MongoDB 的 CRUD 操作,顺便结合前端 Layui 实现了简单的页面效果。作为一款非常热门的非关系型数据库,大家非常有必要进行更深入的学习,最后祝大家加薪!加薪!加薪!

温馨提示:本案例图文并茂,代码齐全(包括前端)大家只需要跟着文章一步步学习即可实现。想要一步到位直接获取代码的同学,请关注微信公众号「哈喽沃德先生」回复 logistics
即可


参考


  • https://docs.spring.io/spring-data/mongodb/docs/3.1.5/reference/html/#reference
  • https://docs.mongoing.com/
  • https://www.layui.com/doc/
  • https://www.layui.com/demo/
  • https://blog.csdn.net/qq_40693171/article/details/108229145

点击👇卡片关注我的公众号

文章转载自哈喽沃德先生,如果涉嫌侵权,请发送邮件至:contact@modb.pro进行举报,并提供相关证据,一经查实,墨天轮将立刻删除相关内容。

评论