Java-springboot生鲜电商项目(六)订单模块

java电商项目技术亮点难点,原理+实战+视频+源码 第1部分:基础篇 第2部分:开发篇 第3部分:优化篇 第4部分:管理维护篇 最后 毕竟工作也这么久了 ,除了途虎一轮,也七七八八面试了不少大厂,像阿里、饿了么、美团、滴滴这些面试过程就不一一写在这篇文章上了。我会整理一份详细的面试过程及大家想知道的一些问题细节 美团面试经验 字节面试经验 菜鸟面试经验 蚂蚁金服面试经验 唯品会面试经验 因篇幅有限,图文无法详细发出,感兴趣的朋友可以点击这里前往我的腾讯文档免费获取上述资料! cs.qq.com/doc/DSmxTbFJ1cmN 阅读详情

订单开发思路

  1. 登录
  2. 浏览商品
  3. 加入购物车
  4. 下单,取消订单
  5. 扫描支付
  6. 发货
  7. 收货

涉及到的接口

  1. 前台:创建订单
  2. 前台:订单详情
  3. 前台:订单列表
  4. 前台:取消订单
  5. 生成支付二维码
  6. 前台:支付订单
  7. 后台:订单列表
  8. 后台:订单发货
  9. 订单完结

重难点

  1. VO的封装还裁剪
  2. 一个订单内包含多个商品
  3. 订单状态流转
  4. 二维码生成

(一)创建订单

新建一个创建订单的请求类

package com.hyb.mall.model.request;

import javax.validation.constraints.NotNull;

public class CreateOrderReq {

    @NotNull(message = "接收人名字不能不为空")
    private String receiverName;

    @NotNull(message = "接收人电话不能不为空")
    private String receiverMobile;

    @NotNull(message = "接收人地址不能不为空")
    private String receiverAddress;

    private Integer postage = 0;

    private Integer paymentType = 1;

    public String getReceiverName() {
        return receiverName;
    }

    public void setReceiverName(String receiverName) {
        this.receiverName = receiverName;
    }

    public String getReceiverMobile() {
        return receiverMobile;
    }

    public void setReceiverMobile(String receiverMobile) {
        this.receiverMobile = receiverMobile;
    }

    public String getReceiverAddress() {
        return receiverAddress;
    }

    public void setReceiverAddress(String receiverAddress) {
        this.receiverAddress = receiverAddress;
    }

    public Integer getPostage() {
        return postage;
    }

    public void setPostage(Integer postage) {
        this.postage = postage;
    }

    public Integer getPaymentType() {
        return paymentType;
    }

    public void setPaymentType(Integer paymentType) {
        this.paymentType = paymentType;
    }
}

添加异常

CART_EMPTY(10018,"购物车已勾选的商品为空"),
NO_ENUM(10019,"未找到对应的枚举类"),

在Constant添加

    /**
     * 订单状态
     */
    public enum OrderStatusEnum{
        CANCELED(0,"用户已取消"),
        NOT_PAID(10,"未付款"),
        PAID(20,"已付款"),
        DELIVERED(30,"已发货"),
        FINISHED(40,"交易完成");
        private String value;
        private int code;

        OrderStatusEnum(int code,String value) {
            this.value = value;
            this.code = code;
        }

        public String getValue() {
            return value;
        }

        public void setValue(String value) {
            this.value = value;
        }

        public int getCode() {
            return code;
        }

        public void setCode(int code) {
            this.code = code;
        }

        //通过code返回意思
        public static OrderStatusEnum cedeOf(int code){
            for(OrderStatusEnum orderStatusEnum:values()){
                if (orderStatusEnum.getCode() == code){
                    return orderStatusEnum;
                }
            }
            throw new MallException(MallExceptionEnum.NO_ENUM);
        }
    }

在service添加创建订单方法

package com.hyb.mall.service.impl;

import com.hyb.mall.common.Constant;
import com.hyb.mall.exception.MallException;
import com.hyb.mall.exception.MallExceptionEnum;
import com.hyb.mall.filter.UserFilter;
import com.hyb.mall.model.dao.CartMapper;
import com.hyb.mall.model.dao.OrderItemMapper;
import com.hyb.mall.model.dao.OrderMapper;
import com.hyb.mall.model.dao.ProductMapper;
import com.hyb.mall.model.pojo.Order;
import com.hyb.mall.model.pojo.OrderItem;
import com.hyb.mall.model.pojo.Product;
import com.hyb.mall.model.request.CreateOrderReq;
import com.hyb.mall.model.vo.CartVO;
import com.hyb.mall.service.CartSrvice;
import com.hyb.mall.service.OrderSrvice;
import com.hyb.mall.util.OrderCodeFactory;
import io.swagger.models.auth.In;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.util.CollectionUtils;

import java.util.ArrayList;
import java.util.List;

/**
 * 描述:订单Service实现类
 */
@Service
public class OrderSrviceImpl implements OrderSrvice {
    @Autowired
    CartSrvice cartSrvice;

    @Autowired
    ProductMapper productMapper;

    @Autowired
    CartMapper cartMapper;

    @Autowired
    OrderMapper orderMapper;

    @Autowired
    OrderItemMapper orderItemMapper;

    @Override
    //数据库事务
    @Transactional(rollbackFor = Exception.class)
    public String create(CreateOrderReq createOrderReq) {
        //拿到用户ID
        Integer userId = UserFilter.currentUser.getId();

        //从购物车查找已经勾选的商品
        List<CartVO> cartVOList = cartSrvice.list(userId);
        ArrayList<CartVO> cartVOListTemp = new ArrayList<>();
        for (int i = 0; i < cartVOList.size(); i++) {
            CartVO cartVO = cartVOList.get(i);
            if (cartVO.getSelected().equals(Constant.Cart.CHCKED)) {
                cartVOListTemp.add(cartVO);
            }
        }
        cartVOList = cartVOListTemp;

        //如果购物车已勾选为空,报错
        if (CollectionUtils.isEmpty(cartVOList)) {
            throw new MallException(MallExceptionEnum.CART_EMPTY);
        }

        //判断商品是否存在,上下架状态,库存
        validSaleStatusAndStock(cartVOList);

        //把购物车对象转化为订单item对象
        List<OrderItem> orderItemList = cartVOListOrderItemList(cartVOList);

        //扣库存
        for (int i = 0; i < orderItemList.size(); i++) {
            OrderItem orderItem = orderItemList.get(i);
            Product product = productMapper.selectByPrimaryKey(orderItem.getProductId());
            int stock = product.getStock() - orderItem.getQuantity();
            if (stock < 0) {
                throw new MallException(MallExceptionEnum.NOT_ENOUGH);
            }
            product.setStock(stock);
            productMapper.updateByPrimaryKeySelective(product);
        }

        //把购物车中的已勾选商品删除
        cleanCart(cartVOList);

        //生成订单
        Order order = new Order();

        //生成订单号,有独立的规则
        String orderNo = OrderCodeFactory.getOrderCode(Long.valueOf(userId));
        order.setOrderNo(orderNo);
        order.setUserId(userId);
        order.setTotalPrice(totalPrice(orderItemList));
        order.setReceiverName(createOrderReq.getReceiverName());
        order.setReceiverMobile(createOrderReq.getReceiverMobile());
        order.setReceiverAddress(createOrderReq.getReceiverAddress());
        order.setOrderStatus(Constant.OrderStatusEnum.NOT_PAID.getCode());
        order.setPostage(0);
        order.setPaymentType(1);

        //插入到order表
        orderMapper.insertSelective(order);

        //循环保存每个商品到order_item表
        for (int i = 0; i < orderItemList.size(); i++) {
            OrderItem orderItem = orderItemList.get(i);
            orderItem.setOrderNo(order.getOrderNo());
            orderItemMapper.insertSelective(orderItem);
        }

        //把结果返回
        return orderNo;
    }

    private Integer totalPrice(List<OrderItem> orderItemList) {
        Integer totalPrice = 0;
        for (int i = 0; i < orderItemList.size(); i++) {
            OrderItem orderItem = orderItemList.get(i);
            totalPrice += orderItem.getTotalPrice();
        }
        return totalPrice;
    }

    private void cleanCart(List<CartVO> cartVOList) {
        for (int i = 0; i < cartVOList.size(); i++) {
            CartVO cartVO = cartVOList.get(i);
            cartMapper.deleteByPrimaryKey(cartVO.getId());
        }
    }

    private List<OrderItem> cartVOListOrderItemList(List<CartVO> cartVOList) {
        List<OrderItem> orderItemList = new ArrayList<>();
        for (int i = 0; i < cartVOList.size(); i++) {
            CartVO cartVO = cartVOList.get(i);
            OrderItem orderItem = new OrderItem();
            orderItem.setProductId(cartVO.getProductId());
            //记录商品快照信息
            orderItem.setProductName(cartVO.getProductName());
            orderItem.setProductImg(cartVO.getProductImage());
            orderItem.setUnitPrice(cartVO.getPrice());
            orderItem.setQuantity(cartVO.getQuantity());
            orderItem.setTotalPrice(cartVO.getTotalPrice());
            orderItemList.add(orderItem);

        }
        return orderItemList;
    }

    private void validSaleStatusAndStock(List<CartVO> cartVOList) {
        for (int i = 0; i < cartVOList.size(); i++) {
            CartVO cartVO = cartVOList.get(i);
            Product product = productMapper.selectByPrimaryKey(cartVO.getProductId());
            //判断商品是否存在,商品是否上架
            if (product == null || product.getStatus().equals(Constant.SaleStatus.NOT_SALE)) {
                throw new MallException(MallExceptionEnum.NOT_SALE);
            }
            //判断商品库存
            if (cartVO.getQuantity() > product.getStock()) {
                throw new MallException(MallExceptionEnum.NOT_ENOUGH);
            }
        }

    }
}

controller实现

package com.hyb.mall.controller;

import com.hyb.mall.common.ApiRestResponse;
import com.hyb.mall.model.request.CreateOrderReq;
import com.hyb.mall.service.OrderSrvice;
import io.swagger.annotations.ApiOperation;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;

/**
 * 描述:订单控制器
 */
@RestController
@RequestMapping("/order")
public class OrderController {

    @Autowired
    OrderSrvice orderSrvice;

    @PostMapping("/create")
    @ApiOperation("创建订单")
    public ApiRestResponse create(@RequestBody CreateOrderReq createOrderReq){
        String orderNo = orderSrvice.create(createOrderReq);
        return ApiRestResponse.success(orderNo);
    }
}

在postman进行测试

在这里插入图片描述

(二)订单详情

定义异常

NO_ORDER(10020,"订单不存在"),
NO_YOU_ORDER(10020,"订单不属于你"),

先在dao创建接口

orderMpper

Order selectByOrderNo(String orderNo);

Mapper

  <select id="selectByOrderNo" parameterType="java.lang.String" resultMap="BaseResultMap">
    select
    <include refid="Base_Column_List"/>
    from imooc_mall_order
    where order_no = #{orderNo}
  </select>

先在dao创建接口

dao

List<OrderItem> selectByOrderNo(String orderNo);

Mapper

  <select id="selectByOrderNo" parameterType="java.lang.String" resultMap="BaseResultMap">
    select
    <include refid="Base_Column_List"/>
    from imooc_mall_order_item
    where order_no=#{orderNo}
  </select>

service,主要还是在拼接信息上

    //查询订单详情
    @Override
    public OrderVO detail(String orderNo){
        Order order = orderMapper.selectByOrderNo(orderNo);
        //订单不存在,则报错
        if (order == null) {
            throw new MallException(MallExceptionEnum.NO_ORDER);
        }
        //订单存在,则判断所属
        Integer userId = UserFilter.currentUser.getId();
        if (!order.getUserId().equals(userId)){
            throw new MallException(MallExceptionEnum.NO_YOU_ORDER);
        }
        //拼接信息,将order转成orderVO
        OrderVO orderVO = getOrder(order);
        return orderVO;
    }

    private OrderVO getOrder(Order order) {
        OrderVO orderVO = new OrderVO();
        BeanUtils.copyProperties(order,orderVO);
        //获取订单对应的orderItemVOList
        List<OrderItem> orderItemList = orderItemMapper.selectByOrderNo(order.getOrderNo());
        List<OrderItemVO> orderItemVOList = new ArrayList<>();
        for (int i = 0; i < orderItemList.size(); i++) {
            OrderItem orderItem = orderItemList.get(i);
            OrderItemVO orderItemVO = new OrderItemVO();
            BeanUtils.copyProperties(orderItem,orderItemVO);
            orderItemVOList.add(orderItemVO);
        }
        orderVO.setOrderItemVOList(orderItemVOList);
        orderVO.setOrderStatusName(Constant.OrderStatusEnum.cedeOf(orderVO.getOrderStatus()).getValue());
        return orderVO;
    }

controller

    @GetMapping("/detail")
    @ApiOperation("前台订单详情")
    public ApiRestResponse detail(@RequestParam String orderNo){
        OrderVO orderVO = orderSrvice.detail(orderNo);
        return ApiRestResponse.success(orderVO);
    }

(三)订单列表

dao

List<Order> selectForCustomer(Integer userId);

mapper

  <select id="selectForCustomer" resultMap="BaseResultMap" parameterType="integer">
    select
    <include refid="Base_Column_List"/>
    from imooc_mall_order
    where user_id = #{userId}
    order by create_time desc
  </select>

service

    @Override
    public PageInfo listForCustomer(Integer pageNum,Integer pageSize){
        Integer userId = UserFilter.currentUser.getId();
        PageHelper.startPage(pageNum,pageSize);
        List<Order> orderList = orderMapper.selectForCustomer(userId);
        //将order转化为orderVO
        List<OrderVO> orderVOList = orderListToOrderVOList(orderList);
        //包装成pageInfo进行返回
        PageInfo pageInfo = new PageInfo<>(orderList);
        pageInfo.setList(orderVOList);
        return pageInfo;
    }

    private List<OrderVO> orderListToOrderVOList(List<Order> orderList) {
        List<OrderVO> orderVOList = new ArrayList<>();
        for (int i = 0; i < orderList.size(); i++) {
            Order order = orderList.get(i);
            OrderVO orderVO = getOrder(order);
            orderVOList.add(orderVO);
        }
        return orderVOList;
    }

controller

    @GetMapping("/list")
    @ApiOperation("前台订单列表")
    public ApiRestResponse list(@RequestParam Integer pageNum ,@RequestParam Integer pageSize){
        PageInfo pageInfo = orderSrvice.listForCustomer(pageNum, pageSize);
        return ApiRestResponse.success(pageInfo);
    }

postman测试

在这里插入图片描述

(四)取消订单

添加异常

WRONG_ORDER(10022,"订单状态不符"),

service

    @Override
    public void cancel(String orderNo){
        //查不到订单,报错
        Order order = orderMapper.selectByOrderNo(orderNo);
        if (order == null) {
            throw new MallException(MallExceptionEnum.NO_ORDER);
        }
        //验证用户身份
        //订单存在,则判断所属
        Integer userId = UserFilter.currentUser.getId();
        if (!order.getUserId().equals(userId)){
            throw new MallException(MallExceptionEnum.NO_YOU_ORDER);
        }
        //没有付款才取消
        if (order.getOrderStatus().equals(Constant.OrderStatusEnum.NOT_PAID.getCode())) {
            //将订单状态设置成取消
            order.setOrderStatus(Constant.OrderStatusEnum.CANCELED.getCode());
            order.setEndTime(new Date());
            //将订单传到数据库,来更新数据库的状态
            orderMapper.updateByPrimaryKeySelective(order);
        }else{
            throw new MallException(MallExceptionEnum.WRONG_ORDER_STATUS);
        }
    }

controller

    @PostMapping("/cancel")
    @ApiOperation("前台取消订单")
    public ApiRestResponse cancel(@RequestParam String orderNo){
        orderSrvice.cancel(orderNo);
        return ApiRestResponse.success();
    }

postman

在这里插入图片描述

(五)后台管理员列表开发

dao

List<Order> selectForAdmin();

mapper

  <select id="selectForAdmin" resultMap="BaseResultMap">
    select
    <include refid="Base_Column_List"/>
    from imooc_mall_order
    order by create_time desc
  </select>

service

    @Override
    public PageInfo listForAdmin(Integer pageNum, Integer pageSize){
        PageHelper.startPage(pageNum,pageSize);
        List<Order> orderList = orderMapper.selectForAdmin();
        //将order转化为orderVO
        List<OrderVO> orderVOList = orderListToOrderVOList(orderList);
        //包装成pageInfo进行返回
        PageInfo pageInfo = new PageInfo<>(orderList);
        pageInfo.setList(orderVOList);
        return pageInfo;
    }

controller

package com.hyb.mall.controller;

import com.github.pagehelper.PageInfo;
import com.hyb.mall.common.ApiRestResponse;
import com.hyb.mall.service.OrderSrvice;
import io.swagger.annotations.ApiOperation;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.RestController;

@RestController
public class OrderAdminController {
    @Autowired
    OrderSrvice orderSrvice;
    @GetMapping("/admin/order/list")
    @ApiOperation("管理员订单列表")
    public ApiRestResponse listForAdmin(@RequestParam Integer pageNum,@RequestParam Integer pageSize){
        PageInfo pageInfo = orderSrvice.listForAdmin(pageNum, pageSize);
        return ApiRestResponse.success(pageInfo);
    }
}

(六)支付相关的二维码接口

引入生成二维码的依赖

        <dependency>
            <groupId>com.google.zxing</groupId>
            <artifactId>javase</artifactId>
            <version>3.3.0</version>
        </dependency>

在工具类中添加生成二维码的类

package com.hyb.mall.util;

import com.google.zxing.BarcodeFormat;
import com.google.zxing.WriterException;
import com.google.zxing.client.j2se.MatrixToImageWriter;
import com.google.zxing.common.BitMatrix;
import com.google.zxing.qrcode.QRCodeWriter;
import com.hyb.mall.common.Constant;
import java.io.File;
import java.io.IOException;
import java.nio.file.FileSystems;
import java.nio.file.Path;

/**
 * 描述:     生成二维码工具
 */
public class QRCodeGenerator {


    public static void generateQRCodeImage(String text, int width, int height, String filePath)
            throws WriterException, IOException {
        QRCodeWriter qrCodeWriter = new QRCodeWriter();
        BitMatrix bitMatrix = qrCodeWriter.encode(text, BarcodeFormat.QR_CODE, width, height);
        Path path = FileSystems.getDefault().getPath(filePath);
        MatrixToImageWriter.writeToPath(bitMatrix, "PNG", path);
    }

    public static void main(String[] args) {
        try {
            generateQRCodeImage("Hello World", 350, 350, "/Users/hyb/Desktop/Pfile/二维码/QRTest.png");
        } catch (WriterException e) {
            e.printStackTrace();
        } catch (IOException e) {
            e.printStackTrace();
        }
    }
}

生成后的图片

在这里插入图片描述

service

    @Value("${file.upload.ip}")
    String ip;
    @Override
    public String qrcode(String orderNo){
        ServletRequestAttributes attributes = (ServletRequestAttributes)RequestContextHolder.getRequestAttributes();
        HttpServletRequest request = attributes.getRequest();
        String address = ip+":"+request.getLocalPort();
        //支付URL
        String payUrl = "http://"+address+"/pay?orderNo="+orderNo;
        try {
            QRCodeGenerator.generateQRCodeImage(payUrl,350,350,
                    Constant.FILE_UPLOAD_DIR+orderNo+".PNG");
        } catch (WriterException e) {
            e.printStackTrace();
        } catch (IOException e) {
            e.printStackTrace();
        }
        String pngAddress= "http://"+address+"/images/"+orderNo+".png";
        return pngAddress;
    }

controller

    @PostMapping("/admin/qrcode")
    @ApiOperation("生成二维码")
    public ApiRestResponse listForAdmin(@RequestParam String orderNo){
        String pngAddress = orderSrvice.qrcode(orderNo);
        return ApiRestResponse.success(pngAddress);
    }

(七)支付接口

service

    @Override
    public void pay(String orderNo){
        Order order = orderMapper.selectByOrderNo(orderNo);
        //查不到订单,报错
        if (order == null){
            throw new MallException(MallExceptionEnum.NO_ORDER);
        }
        if (order.getOrderStatus() == Constant.OrderStatusEnum.NOT_PAID.getCode()){
            order.setOrderStatus(Constant.OrderStatusEnum.PAID.getCode());
            order.setPayTime(new Date());
            orderMapper.updateByPrimaryKeySelective(order);
        }else {
            throw new MallException(MallExceptionEnum.WRONG_ORDER_STATUS);
        }
    }

controller

    @GetMapping("/pay")
    @ApiOperation("前台:支付订单")
    public ApiRestResponse pay(@RequestParam String orderNo){
        orderSrvice.pay(orderNo);
        return ApiRestResponse.success();
    }

postman

在这里插入图片描述

(八)发货订单

service

    @Override
    public void delivered(String orderNo){
        Order order = orderMapper.selectByOrderNo(orderNo);
        //查不到订单,报错
        if (order == null){
            throw new MallException(MallExceptionEnum.NO_ORDER);
        }
        //订单状态是不是付款的
        if (order.getOrderStatus() == Constant.OrderStatusEnum.NOT_PAID.getCode()){
            order.setOrderStatus(Constant.OrderStatusEnum.DELIVERED.getCode());
            order.setDeliveryTime(new Date());
            orderMapper.updateByPrimaryKeySelective(order);
        }else {
            throw new MallException(MallExceptionEnum.WRONG_ORDER_STATUS);
        }
    }

controller

    @PostMapping("/admin/order/delivered")
    @ApiOperation("后台:订单发货")
    public ApiRestResponse delivered(@RequestParam String orderNo){
        orderSrvice.delivered(orderNo);
        return ApiRestResponse.success();
    }

postman

在这里插入图片描述

(九)完结订单接口

service

    @Override
    public void finish(String orderNo){
        Order order = orderMapper.selectByOrderNo(orderNo);
        //查不到订单,报错
        if (order == null){
            throw new MallException(MallExceptionEnum.NO_ORDER);
        }
        //如果是普通用户,就要校验订单的所属
        if (!userService.checkAdminRole(UserFilter.currentUser) && !order.getUserId().equals(UserFilter.currentUser.getId())) {
            throw new MallException(MallExceptionEnum.NO_YOU_ORDER);
        }
        //发货后可以完结订单
        //订单状态是不是付款的
        if (order.getOrderStatus() == Constant.OrderStatusEnum.DELIVERED.getCode()){
            order.setOrderStatus(Constant.OrderStatusEnum.FINISHED.getCode());
            order.setEndTime(new Date());
            orderMapper.updateByPrimaryKeySelective(order);
        }else {
            throw new MallException(MallExceptionEnum.WRONG_ORDER_STATUS);
        }
    }

controller

    @PostMapping("/order/finish")
    @ApiOperation("订单完结")
    public ApiRestResponse finish(@RequestParam String orderNo){
        orderSrvice.finish(orderNo);
        return ApiRestResponse.success();
    }

postman

在这里插入图片描述

Java开发实战讲解!java小游戏毕业论文 Cache aside Cache aside也就是旁路缓存,是比较常用的缓存策略。 (1)读请求常见流程 应用首先会判断缓存是否有该数据,缓存命中直接返回数据,缓存未命中即缓存穿透到数据库,从数据库查询数据然后回写到缓存中,最后返回数据给客户端。 (2)写请求常见流程 首先更新数据库,然后从缓存中删除该数据。 看了写请求的图之后,有些同学可能要问了:为什么要删除缓存,直接更新不就行了?这里涉及到几个坑,我们一步一步踩下去。 Cache aside踩坑 Cache aside策略如果用错就会遇到深坑,下 阅读详情

相关推荐

Java电商项目面试--商品模块

面试:商品模块技术要点 1、POJO、BO、VO抽象模型 2、高效分页及动态排序 3、FTP服务对接、富文本上传 一、商品模块功能 前台功能: 1、产品搜索 2、动态排序列表 3、商品详情 后台功能: 1、商品列表 2、商品搜索 3、图片上传 4、增加商品、更新商品、商品上下架 二、后台新增和更新商品 Controller: @Controlle...

小刺猬 1万+

Java面试题-day28 项目合集之项目中你需要知道的事儿~

之前 我们讲了在项目开发前,作为开发人员我们必须要知道的项目常识,接下来我们继续讲解项目中要注意的事儿! 1. 项目的周期大概是多长? 这个要看项目的规模及投入的人力,物力的多少。 一般java项目,可以回答半年左右,但这半年不全是开发,集中开发可能只有两个月时间,其它时间是做需求,设计,测试,部署等。 还有的项目做个一,两年都正常。 2. 核心开发人员负责多少模块合适? 架构师将项目根据需求分解为各个模块,会将比较难的,复杂的交给核心开发人员。具体多少个模块也要看这个模块涉及到的功能点及复杂程度。 .

风归去. 3482

JAVA项目实战开发电商项目案例(十)订单与支付模块

电商项目PC端网页支付,采用支付宝支付,用户登录成功,购买商品支付宝支付付款成功跳转到网站首页。

HP-MN 1万+

java电商面试介绍

写博客 前两个项目采用的是ssh框架搭建的,最近的项目采用的是ssm框架搭建的。在实际开发中,我觉得这两个框架,他们最大的区别在于hibernate与mybatis的区别。 Hibernate与mybatis相比较,mybatis更为轻便、灵活,容易掌握。mybatis可以把sql语句从java代码中分离了出来,放在了配置文件中书写,大大降低里java代码与SQL语句的耦合度,更容易对sql...

易的博客 3268

(一)利用Python实现数据集读取,Python基本文件操作介绍

机器学习是计算机对大量数据的分析过程,在机器学习的实际项目中,通常都需要准备数据集,数据集通常包含的数据数量是庞大的。例如,在处理计算机视觉领域的项目时,每一张图片都是一个单独的文件,为了提高模型训练的效果,图片数量通常会比较多,因此需要合理且高效的操作将所有的图片数据读取。本篇旨在介绍如何用Python对海量文件进行遍历,也是机器学习实践的第一步。.........

ZZR2631574030的博客 6356

【DICOM后处理】qt+vs 实现DICOM数据四视图显示

方法用于 设置 2D 视图的“向上”方向,即定义图像在屏幕坐标系中的朝向。该方法直接影响影像的显示方向,尤其在多平面重建(MPR)或非标准切面显示时至关重要。:方法用于 设置渲染窗口在屏幕上的显示位置(以像素为单位)。它控制的是 VTK 渲染窗口的左上角在屏幕坐标系中的坐标位置。DICOM四视图通常指同时显示医学影像的四个不同平面或视角,用于全面分析三维数据(如CT、MRI等)。:基于 标量值 设置不透明度(控制不同组织的显示),显示骨骼or显示高密度流体等。默认朝向原点 (0, 0, 0)

weixin_41804847的博客 1325

Java-springboot生鲜电商项目(零)开发前言

springboot生鲜电商项目项目亮点1.最新的业界互联网企业级的优质技术。2.代码规范简介,充分优化。3.流程完整,电商功能丰富。4.前后端彻底分离,符合未来趋势。项目功能模块介绍前台模块:后台模块:工具准备:技术选型: 前言:开发的是一款基于springboot为主的销售生鲜网站,该网站主要是涉及到前端展示和后端管理的开发,开发的目的是为了将Java的所学做一次系统的汇总,并将技术落地到实际的项目开发中,从零到一的打造一个属于自己的优质网站。 该博客将会分模块的进行知识梳理,开发流程进行梳理,尽量将思

bingbign0607的博客 1857

Mathtype公式下标深度调整技巧:解决固定行距下的显示不全问题

本文针对在Word等文档中设置固定行距时,Mathtype公式下标显示不全的问题,提供了专业解决方案。核心在于调整Mathtype软件内部的“下标深度”参数,通过修改单个公式或批量格式化全文,使公式完美适配固定行距,确保下标清晰完整,且不影响文档整体排版。

pepsi的博客 1498

Java-springboot生鲜电商项目(五)购物车模块

Java-springboot生鲜电商项目(五)购物车模块购物车功能业务流程(一)购物车列表daomapperservice(二)添加商品到购物车对用户的过滤器开发:因为购物车的功能是用户的行为操作,所以在添加商品到购物车的时候,先判断是否是用户,可以借鉴管理员过滤器的开发filter包中创建UserFilter对过滤器进行config配置coding到这里,我发现有个小小的笔误,我在controller中@PostMapping("")注解中,映射的地址开头有些有“/”有些没有,然后我进行统一处理,全加上

bingbign0607的博客 3588

uniapp [全端兼容] - 实现接入使用天地图及卫星视图切换功能,在国家天地图上自由切换地图显示类型(卫星视图/地形视图/卫星混合/地形混合/普通视图)天地图切换视图显示改成卫星风格,切换地图图层

uni-app,h5移动端网页,微信小程序,支付宝小程序,Android安卓,苹果ios,app,nvue,天地图,视图,卫星,地图类型切换,uniAPP天地图,改成卫星视角,在线地图切换,来回切换卫星图,天地图如何实现来回切换卫星图,地形图,卫星视图,VUE3引入天地图卫星版,详细教程示例源码代码,天地图切换卫星用什么api,卫星视角API方法,vue3卫星天地图,能改地图的显示方式,vue3中使用天地图自定义样式切换地图图层,切换报错,加载出错,卫星图太卡,地图图层更换,vue3安装集成天地图详细示例源

🏆 前端领域优质创作者 1万+

UNet 改进(27):结合SCSE注意力机制的UNet网络实现

本文介绍了一种结合SCSE注意力机制的改进UNet网络架构。该网络在保持UNet经典编码器-解码器结构基础上,通过在每层添加SCSEBlock模块,融合了通道注意力和空间注意力机制。通道注意力通过全局池化和1×1卷积生成通道权重,空间注意力则产生空间权重图,二者相加增强关键特征响应。该设计具有以下优势:1)保持原始UNet的多尺度特征提取能力;2)通过注意力机制提升对重要区域的关注度;3)计算效率高,仅增加少量参数。测试显示网络能保持输入输出分辨率不变,适用于医学图像分割等像素级预测任务。完整代码实现了5层

2401_82355416的博客 415

Java-springboot生鲜电商项目(四)商品模块

Java-springboot生鲜电商项目(四)商品模块商品模块这个模块的难点常见错误(一)后台的新增商品在request创建AddProduct类,目的是为了修改product不会污染pojo下的product类在productMapper创建查询商品名的接口,用于之后的重名判断在productMapper.xml编写SQL语句在productServiceImpl实现商品插入的业务逻辑写到这里,会出现一个问题,就是图片上传问题,处理步骤如下:UUID在Constant常量类中编写图片文件保存的地址并在类

bingbign0607的博客 2277

2023华为OD机试真题B卷 Python 实现【最长的元音子串长度】

定义当一个字符串只有元音字母(a,e,i,o,u,A,E,I,O,U)组成,称为元音字符串,现给定一个字符串,请找出其中最长的元音字符串,并返回其长度,如果找不到请返回0, 字符串中任意一个连续字符组成的子序列称为该字符串的子串

MISAYAONE的博客 900

Java-springboot生鲜电商项目(二)用户模块

Java-springboot生鲜电商项目(二)用户模块用户模块开发开发涉及到内容:(一)用户注册用户注册的开发思路:根据文档,创建common包下ApiResponse类来处理响应对象定义controller返回的异常枚举在exception包中定义统一异常处理1.在dao层先定义查询用户的接口,并且返回User查询对象2.在UserMapper映射中添加SQL查询语句3.在UserService定义用户注册接口,并在Service实现接口4.在controller实现调用5.使用postman进行测试,

bingbign0607的博客 1548

【2026 Science Robotics】Learning realistic lip motions for humanoid face robots

哥伦比亚大学Yuhang Hu团队提出了一种创新方法,通过10自由度软体嘴唇设计和自监督学习算法解决仿人机器人嘴唇动作僵硬问题。研究采用变分自编码器(VAE)和面部动作Transformer(FAT)模型,将语音信号转化为机器人可执行的电机指令。实验表明,该方法在多语言测试中表现优异,用户偏好率达62.5%,显著提升了口型同步的真实感和流畅度。该成果突破了传统机械结构的限制,为跨越"恐怖谷效应"提供了有效解决方案。

志在山顶的人,不会贪念山腰的风景 308

CS 188 Project3(RL) Q10:Approximate Q-Learning

实现一个近似的Q-learning学习代理,它学习状态特征的权重,其中许多状态可能共享相同的特征。在qlearningAgents.py中的ApproximateQAgent类中编写实现,它是PacmanQAgent的子类。 注:近似Q-learning学习假设在状态和动作对上存在一个特征函数f(s,a),它产生一个向量f1(s,a) .. fi(s,a) .. fn(s,a)特征值。我们在fe...

大模型与Agent智能体 2655

计算机毕业设计springboot基于Java的网上生鲜超市 基于SpringBoot的社区生鲜电商订购平台设计与实现 融合SpringBoot的产地直供冷链商城系统开发

本文介绍了一个基于SpringBoot的网上生鲜超市系统设计,采用Java+Vue+MySQL技术栈实现B/S架构。系统包含用户端、卖家端和管理员端三大模块:用户可浏览商品、下单购买;卖家可管理商品和订单;管理员负责用户权限和系统维护。通过数字化管理生鲜供应链,实现从采摘到配送的全流程追踪,解决传统生鲜销售信息不对称问题。系统具有完整的电商功能,包括商品管理、订单处理、支付系统等,并支持多平台访问。开发环境为IDEA/Eclipse+MySQL+JDK1.8+Tomcat7.0,系统界面简洁,操作便捷,旨在

毕设源码_谢师姐 1276

汉书HE8,好用的汇编代码编写工具

汉书HE8,好用的汇编代码编写工具早期编写汇编代码所用功能强大

Java-springboot生鲜电商项目(七)上线阿里云的部署准备

Java-springboot生鲜电商项目(七)上线阿里云的部署准备1.将request包下的所有类加上toString()方法,因为在filter里面有个weblogaspect类会打印出一个一个的参数,入参是个对象的话,需要将toSring()字段的内容打印出来。2.规范get和post:列表类的请求可以用GetMapping例如3.准备线上数据库文件,提供给线上数据库的4.多环境配置,创建多一份application-prod.properties写上线上环境的配置信息,例如 1.将request包下

bingbign0607的博客 495

假人有限元模型

假人模型,车辆碰撞假人有限元模型,适合做乘员安全的研究者利用

Probability and Statistics - 4th edition

Probability and Statistics - 4th edition

Java项目:156SpringBoot Vue的生鲜商城系统

基于SpringBoot Vue的生鲜交易系统 角色:管理员、用户、商家 用户:用户系统,在系统首页可以查看首页,生鲜信息,公告信息,个人中心,后台管理,购物车等内容 商家:商家登录系统后,可以对首页,个人中心,生鲜信息管理,广告信息管理,生鲜仓库管理,生鲜出库管理,订单管理等 管理员:管理员登录进入系统可以对首页,个人中心,用户管理,商家管理,生鲜信息管理,生鲜分类管理,广告信息管理,生鲜仓库管理,生鲜出库管理,系统管理等进行相应操作 使用人群: 正在做毕设的学生,或者需要项目实战练习的Java

1287

efm32 入门.pdf

本PDF共计22页,介绍的是操作驱动API,下载与否自己斟酌。

java-springboot基于Java的网上生鲜超市 基于SpringBoot的Java生鲜电商购物平台 B/S架构下Java农产品在线订购配送系统计算机毕业设计

本文介绍了一个基于Java SpringBoot框架开发的网上生鲜超市系统。该系统采用B/S架构,整合了用户管理、商品展示、购物车、订单处理、支付结算、物流跟踪等核心功能模块,实现了从商品上架到配送评价的完整生鲜电商流程。系统使用MySQL数据库存储数据,通过SpringBoot+MyBatis技术栈实现前后端分离开发,具有用户注册登录、商品分类管理、库存预警、销售统计等特色功能。论文详细分析了系统的可行性、需求规格、技术架构和数据库设计,并展示了主要功能界面截图。该系统旨在解决传统生鲜购买中的时效性、新鲜

毕设源码_谢师姐 1775

电商项目介绍

电商项目介绍

HelloWouldH的博客 6985

springboot基于Java的社区生鲜团购系统

该系统广泛应用于生鲜、日用品等领域,凭借强大的社交裂变和本地化特性,解决了传统电商配送成本高、用户获取难等问题,同时优化了社区居民的购物体验。通过团长(通常是社区中有影响力的人)组织用户拼团购买商品,实现了低成本高效率的商品销售模式。综上所述,SpringBoot基于Java的社区生鲜团购系统是一种功能强大、易于使用且适应性强的电商系统。它可以满足用户、商家和管理员的不同需求,提高运营效率并优化用户体验。开发语言:Java框架:springbootJDK版本:JDK1.8。

QQ1039692211的博客 722

SpringBoot基于Java Web 的生鲜团购销售系统-SpringBoot828

一、系统概述该系统采用SpringBoot框架,结合JavaWeb技术栈,利用MySQL数据库进行数据存储与管理,构建了一个功能完善、性能稳定的生鲜团购销售平台。它主要面向社区居民,提供生鲜蔬果、农产品等商品的团购服务,旨在通过高效的供应链管理和营销策略,为用户提供优质、便捷的购物体验。二、技术架构1.后端:使用SpringBoot框架,提供RESTful API接口,支持快速开发和部署。同时,利用Spring Security等模块,确保系统的安全性。

qq_1406299528的博客 1141

计算机毕业设计springboot的小岛生鲜网站 鲜果生鲜电商平台开发 生鲜食品在线销售系统

小岛生鲜网站通过Spring Boot框架构建了一个高效、便捷的生鲜电商平台。它不仅涵盖了用户从浏览商品到下单支付的全流程,还通过后台管理功能为运营者提供了强大的支持。系统的设计充分考虑了用户体验和运营效率,无论是前端的交互设计还是后端的管理功能,都旨在提升生鲜电商的运营质量,满足消费者对新鲜、健康、便捷的生鲜产品的需求。注:完成的毕业设计程序以下面的的环境软件、功能图和界面为准。系统所需要的环境软件:idea、eclipse+mysql5.7、8.0+Navicat+JDK1.8+tomcat7.0。

Django计算机程序 1008

基于springboot的社区生鲜电商平台毕设源码

然而,要实现这一目标,还需要不断优化和完善系统的功能和性能,以满足日益增长的市场需求。社区生鲜电商平台应运而生,它通过整合线上线下资源,为消费者提供新鲜、优质的食品和农产品,满足人们对健康生活的需求。同时,通过建立溯源体系,用户可以更加了解商品的来源和质量,增强对食品安全的信任感。此外,社区生鲜电商平台还可以为消费者提供更多的选择和便利,满足人们对健康生活的需求。3. 商品详情与评价:每个商品都有详细的描述信息,包括价格、产地、规格等,同时用户可以对已购买的商品进行评价和查看其他用户的评价。

608

基于JAVA电子商务电商网上生鲜购物商城系统设计与实现(Springboot框架)研究背景和意义、国内外现状

基于JAVA电子商务电商网上生鲜购物商城系统设计与实现(Springboot框架)研究背景和意义: 随着互联网的快速发展和消费者对健康、安全食品需求的增加,电子商务电商网上生鲜购物市场呈现出蓬勃发展的态势。传统的实体超市购物方式存在着时间成本高、交通成本高、产品选择有限等问题,而电商平台通过网络销售生鲜食品,解决了传统购物方式的种种局限性,成为了一种便捷、高效的购物方式。因此,基于JAVA电子商务电商网上生鲜购物商城系统的设计与实现,对于解决上述问题,提升生鲜电商市场竞争力具有重要的研究意义和实际应用价值。

杭州.黄老师 2240
上一篇: Java-springboot生鲜电商项目(五)购物车模块
下一篇: Java-springboot生鲜电商项目(七)上线阿里云的部署准备
bingbing0607
博客等级 码龄9年 74粉丝 26原创
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

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

抵扣说明:

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

余额充值