购物车数据2种形态:

登录态:保存到服务器端的redis中

没登录:保存在浏览器端 localStorage 中

搭建购物车服务:8095

步骤一:创建changgou4-service-cart 项目

步骤二:修改pom.xml文件,添加坐标

<dependencies><!--自定义项目--><dependency><groupId>com.czxy.changgou</groupId><artifactId>changgou4-common-auth</artifactId></dependency><dependency><groupId>com.czxy.changgou</groupId><artifactId>changgou4-pojo</artifactId></dependency><!--web起步依赖--><dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-web</artifactId></dependency><!--redis--><dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-data-redis</artifactId></dependency><dependency><groupId>redis.clients</groupId><artifactId>jedis</artifactId></dependency><!-- nacos 客户端 --><dependency><groupId>com.alibaba.nacos</groupId><artifactId>nacos-client</artifactId></dependency><!-- nacos 服务发现 --><dependency><groupId>com.alibaba.cloud</groupId><artifactId>spring-cloud-starter-alibaba-nacos-discovery</artifactId></dependency><!-- openfeign 远程调用 --><dependency><groupId>org.springframework.cloud</groupId><artifactId>spring-cloud-starter-openfeign</artifactId></dependency><!--swagger2--><dependency><groupId>io.springfox</groupId><artifactId>springfox-swagger2</artifactId></dependency><dependency><groupId>io.springfox</groupId><artifactId>springfox-swagger-ui</artifactId></dependency><!--fastjson--><dependency><groupId>com.alibaba</groupId><artifactId>fastjson</artifactId></dependency></dependencies>

步骤三:创建yml文件,

#端口号
server:port: 8095
spring:application:name: cart-serviceredis:host: 127.0.0.1cloud:nacos:discovery:server-addr: 127.0.0.1:8848   #nacos服务地址
#自定义内容
sc:jwt:secret: sc@Login(Auth}*^31)&czxy% # 登录校验的密钥pubKeyPath: D:/rsa/rsa.pub # 公钥地址priKeyPath: D:/rsa/rsa.pri # 私钥地址expire: 360 # 过期时间,单位分钟

步骤四:拷贝JWT配合类 + Swagger + Redis

步骤五:启动类


package com.czxy.changgou4;import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.cloud.client.discovery.EnableDiscoveryClient;
import org.springframework.cloud.openfeign.EnableFeignClients;/*** @author 桐叔* @email liangtong@itcast.cn*/
@SpringBootApplication
@EnableDiscoveryClient
@EnableFeignClients
public class CGCartServiceApplication {public static void main(String[] args) {SpringApplication.run(CGCartServiceApplication.class, args);}
}

添加到购物车

整体分析

接口

POST http://localhost:10010/cart-service/carts
{"skuid": 2600242,"count": 5,"checked": true
}

后端实现:JavaBean

购物车列表项对象:CartItem (某一件商品的购买情况:商品、购买数量 等)

package com.czxy.changgou4.cart;import com.fasterxml.jackson.annotation.JsonProperty;
import lombok.Data;/*** @author 桐叔* @email liangtong@itcast.cn*/
@Data
public class CartItem {private Integer skuid;private Integer spuid;@JsonProperty("goods_name")private String goodsName;private Double price;private Integer count;//购买数量private Boolean checked;private String midlogo;@JsonProperty("spec_info")private String specInfo;}

购物车对象:Cart

package com.czxy.changgou4.cart;import lombok.Data;import java.util.HashMap;
import java.util.Map;/*** @author 桐叔* @email liangtong@itcast.cn*/
@Data
public class Cart {private Map<Integer , CartItem > data = new HashMap<>();private Double total;public Double getTotal() {double sum = 0.0;for (CartItem cartItem : data.values()) {//只统计勾选的价格if(cartItem.getChecked()){sum += ( cartItem.getPrice() * cartItem.getCount());}}return sum;}public void addCart(CartItem cartItem) {CartItem temp = data.get(cartItem.getSkuid());if(temp == null) {data.put( cartItem.getSkuid() , cartItem);} else {temp.setCount( cartItem.getCount() + temp.getCount() );}}public void updateCart(Integer skuid, Integer count , Boolean checked) {CartItem temp = data.get(skuid);if(temp != null) {temp.setCount( count );temp.setChecked(checked);}}public void deleteCart(Integer skuid) {data.remove( skuid );}}

购物车专门定制的对象

CartCategory

package com.czxy.changgou4.vo;import com.fasterxml.jackson.annotation.JsonInclude;
import com.fasterxml.jackson.annotation.JsonProperty;
import lombok.Data;import java.util.ArrayList;
import java.util.List;/*** @author 桐叔* @email liangtong@itcast.cn*/
@Data
public class CartCategory {private Integer id;@JsonProperty("cat_name")private String catName;@JsonProperty("parent_id")private Integer parentId;@JsonProperty("is_parent")private Boolean isParent;//当前分类具有的所有孩子@JsonInclude(JsonInclude.Include.NON_EMPTY)private List<CartCategory> children = new ArrayList<>();}

CartSpecificationOption

package com.czxy.changgou4.vo;import com.fasterxml.jackson.annotation.JsonProperty;
import lombok.Data;/*** @author 桐叔* @email liangtong@itcast.cn*/
@Data
public class CartSpecificationOption {private Integer id;@JsonProperty("spec_id")private Integer specId;                //外键,规格IDprivate CartSpecification specification; //外键对应对象@JsonProperty("option_name")private String optionName;             //选项名称}

CartSpecification

package com.czxy.changgou4.vo;import com.fasterxml.jackson.annotation.JsonProperty;
import lombok.Data;import java.util.List;/*** @author 桐叔* @email liangtong@itcast.cn*/
@Data
public class CartSpecification {private Integer id;@JsonProperty("spec_name")private String specName;                    //规格名称private Integer categoryId;                     //分类外键private CartCategory category;                      //分类外键对应对象private List<CartSpecificationOption> options;      //一个规格,具有多个规格选项}

CartOneSkuResult

package com.czxy.changgou4.vo;import com.fasterxml.jackson.annotation.JsonProperty;
import lombok.Data;import java.util.Date;
import java.util.List;
import java.util.Map;/*** @author 桐叔* @email liangtong@itcast.cn*/
@Data
public class CartOneSkuResult {private Integer skuid;private Integer spuid;@JsonProperty("goods_name")private String goodsName;private Double price;@JsonProperty("on_sale_date")private Date onSaleDate;@JsonProperty("comment_count")private Integer commentCount;@JsonProperty("comment_level")private Integer commentLevel;@JsonProperty("cat1_info")private CartCategory cat1Info;@JsonProperty("cat2_info")private CartCategory cat2Info;@JsonProperty("cat3_info")private CartCategory cat3Info;private Map<String, String> logo;private List<Map> photos;private String description;private String aftersale;private Integer stock;@JsonProperty("spec_list")private List<CartSpecification> specList;// id_list:'规格ID:选项ID|规格ID:选项ID|...',// id_txt:'规格名称:选项名称|规格名称:选项名称|...'@JsonProperty("spec_info")private Map<String, String> specInfo;@JsonProperty("sku_list")private List<Map<String, String>> skuList;}

​​​​​​​后端实现

步骤一:创建CartVo,用于封装请求参数

package com.czxy.changgou4.vo;import lombok.Data;/*** @author 桐叔* @email liangtong@itcast.cn*/
@Data
public class CartVo {private Integer skuid ;     //"SKUID",private Integer count;      //"购买数量"private Boolean checked;    //"是否选中"}

步骤二:创建SkuClient,用于查询详情

package com.czxy.changgou4.feign;import com.czxy.changgou4.vo.BaseResult;
import com.czxy.changgou4.vo.OneSkuResult;
import org.springframework.cloud.openfeign.FeignClient;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;/*** @author 桐叔* @email liangtong@itcast.cn*/
@FeignClient(value="web-service",path = "/sku")
public interface SkuClient {@GetMapping("/goods/{skuid}")public BaseResult<OneSkuResult> findSkuById(@PathVariable("skuid") Integer skuid);}

步骤三:创建CartService接口,用于完成添加业务逻辑

package com.czxy.changgou4.service;import com.czxy.changgou4.pojo.User;
import com.czxy.changgou4.vo.CartVo;/*** @author 桐叔* @email liangtong@itcast.cn*/
public interface CartService {/*** 给指定用户添加商品* @param user* @param cartVo*/public void addCart(User user , CartVo cartVo);
}

步骤四:创建CartService实现类

package com.czxy.changgou4.service.impl;import com.alibaba.fastjson.JSON;
import com.czxy.changgou4.cart.Cart;
import com.czxy.changgou4.cart.CartItem;
import com.czxy.changgou4.feign.SkuClient;
import com.czxy.changgou4.pojo.User;
import com.czxy.changgou4.service.CartService;
import com.czxy.changgou4.vo.BaseResult;
import com.czxy.changgou4.vo.CartOneSkuResult;
import com.czxy.changgou4.vo.CartVo;
import com.czxy.changgou4.vo.OneSkuResult;
import org.springframework.data.redis.core.StringRedisTemplate;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;import javax.annotation.Resource;/*** @author 桐叔* @email liangtong@itcast.cn*/
@Service
@Transactional
public class CartServiceImpl implements CartService {@Resourceprivate StringRedisTemplate stringRedisTemplate;@Resourceprivate SkuClient skuClient;@Overridepublic void addCart(User user, CartVo cartVo) {//1 获得购物车Cart cart;String key = "cart" + user.getId();String cartStr = stringRedisTemplate.opsForValue().get(key);// 处理是否有购物车,没有创建,有转换(jsonStr --> java对象 )if(cartStr != null){//如果有,将json字符串转换购物车对象cart = JSON.parseObject( cartStr , Cart.class);} else {//如果没有创建一个cart = new Cart();}//2 保存商品// 2.1 确定购物买商品BaseResult<CartOneSkuResult> entity = skuClient.findSkuById(cartVo.getSkuid());CartOneSkuResult oneSkuResult = entity.getData();// * 将OneSkuResult 转换成 CartItemCartItem cartItem = new CartItem();cartItem.setSkuid( oneSkuResult.getSkuid() );cartItem.setSpuid( oneSkuResult.getSpuid() );cartItem.setGoodsName( oneSkuResult.getGoodsName() );cartItem.setPrice( oneSkuResult.getPrice() );cartItem.setCount( cartVo.getCount() );        //购买数量,用户传递的cartItem.setChecked(true);cartItem.setMidlogo( oneSkuResult.getLogo().get("biglogo"));cartItem.setSpecInfo( JSON.toJSONString( oneSkuResult.getSpecInfo() ) );   //将对象转换json字符串// 2.2 添加到购物车cart.addCart( cartItem );System.out.println(JSON.toJSONString(cart) );//3 保存购物车stringRedisTemplate.opsForValue().set( key , JSON.toJSONString(cart) );}
}

步骤五:创建CartController

package com.czxy.changgou4.controller;import com.czxy.changgou4.config.JwtProperties;
import com.czxy.changgou4.pojo.User;
import com.czxy.changgou4.service.CartService;
import com.czxy.changgou4.utils.JwtUtils;
import com.czxy.changgou4.vo.BaseResult;
import com.czxy.changgou4.vo.CartVo;
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;import javax.annotation.Resource;
import javax.servlet.http.HttpServletRequest;/*** @author 桐叔* @email liangtong@itcast.cn*/
@RestController
@RequestMapping("/carts")
public class CartController {@Resourceprivate CartService cartService;@Resourceprivate HttpServletRequest request;@Resourceprivate JwtProperties jwtProperties;@PostMappingpublic BaseResult addCart(@RequestBody CartVo cartVo){//1 获得用户信息// 1.1 获得tokenString token = request.getHeader("Authorization");// 1.2 解析tokenUser loginUser = null;try {loginUser = JwtUtils.getObjectFromToken(token, jwtProperties.getPublicKey(),User.class);} catch (Exception e) {return BaseResult.error("token失效或未登录");}//2 添加操作cartService.addCart( loginUser , cartVo );//3 提示return BaseResult.ok("添加成功");}}

步骤六:测试

​​​​​​​前端实现:购买数量

步骤一:修改Goods.vue ,为文本框添加键盘事件,用于校验输入的数据

<input type="text" name="amount" v-model="buyCount" @keyup.prevent="updateCount($event)" value="1" class="amount"/>

步骤二:修改Goods.vue ,完成updateCount函数

 updateCount : function(e){// e.target.value 获得用户输入的数据//使用正则处理数字if( /^\d+$/.test(e.target.value) ){//如果是数字,小于1,默认为1if( e.target.value < 1) {this.buyCount = 1;}} else {//默认为1this.buyCount = 1;}},

步骤三:检查+和-已完成功能

前端实现

步骤一:修改 api.js ,完成“添加到购物车”方法

  //添加到购物车addToCart : ( params ) => {return axios.post("/cart-service/carts", params )},

步骤二:修改Goods.vue,给“加入购物车”绑定点击事件 addToCartFn

<input type="submit" value="" class="add_btn" @click.prevent="addToCartFn"  />

步骤三:修改Goods.vue,完成addToCartFn功能

未登录:保存到sessionStorage

登录:保存到redis

待完善功能:用户登录时,将sessionStorage保存的商品信息合并到redis中

async addToCartFn(){//获得登录标识let token = sessionStorage.getItem("token");if(token != null){//登录:发送ajax进行添加let newGoods = {skuid: this.$route.query.id,count:this.buyCount};//登录状态下的添加商品到购物车操作let {data} = await this.$request.addToCart(newGoods)if(data.code == 20000){//location.href = "flow1"this.$router.push('flow1')} else {alert(data.data.errmsg);}return;}//未登录:在浏览器保存//1 准备添加物品数据var newGoods = {skuid: this.goodsInfo.skuid,goods_name:this.goodsInfo.goods_name,price:this.goodsInfo.price,count:this.buyCount,checked:true,midlogo:this.goodsInfo.logo.smlogo,spec_info: JSON.stringify(this.goodsInfo.spec_info)};//2 维护数据:本地已经存储信息 和 新添加信息 合并var cartStr = localStorage.getItem("cart");var cart;if(cartStr == null) {// 2.1 第一次添加,直接已数组方式添加cart = [newGoods];} else {//判断是否存在(将字符串转换数组、依次遍历)cart = JSON.parse(cartStr);//是否为新物品,默认为新的let isNew = true;cart.forEach( g => {//已有数据的id 和 新物品id 是否一样if(g.skuid == newGoods.skuid){//不是新物品isNew = false;// 2.3 已有,重复,先获得对应,修改数量g.count += parseInt(newGoods.count);}});if(isNew == true){// 2.2 已有,不重复,先获得数组,后追加cart.push(newGoods);}}//3 存放到浏览器var cartStr = JSON.stringify(cart);localStorage.setItem("cart" , cartStr );//4 跳转页面location.href = "flow1"}

步骤四:编写flow1页面

<template><div>购物车</div>
</template><script>
export default {}
</script><style></style>

【畅购商城】购物车模块之添加购物车相关推荐

  1. 畅购商城-添加订单实现(一)

    观前提示: 详细资料观看黑马程序员的畅购商城. 该博客尝试用解题思路说明代码实现. 笔者当前水平有限,因此该博客质量不高. 已知: Idworke:一个分布式的ID生成工具. 可以理解为帮助生成数据库 ...

  2. Java毕业设计项目【畅购商城】

    为了帮助更多的铁汁们,快速进步,完成毕业设计,挺近大厂,我前面已经分享了很多项目 但是有铁汁们觉得实战项目不够,为了给支持我的朋友吧 此次分享的是商城项目,里面包含视频和代码,涉及到SSM.Sprin ...

  3. 畅购商城4.0 微信支付

    畅购商城4.0 1.微信支付 1.1流程分析 1.2微信支付概述 1.2.1账号申请 步骤一:注册公众号,根据自身主体类型注册对应的公众号 只能申请服务号,订阅号没有办法申请支付 https:// ...

  4. 畅购商城(三):商品管理

    好好学习,天天向上 本文已收录至我的Github仓库DayDayUP:github.com/RobodLee/DayDayUP,欢迎Star,更多文章请前往:目录导航 畅购商城(一):环境搭建 畅购商 ...

  5. 商品品牌信息的增删改查操作步骤_畅购商城(三):商品管理

    好好学习,天天向上 本文已收录至我的Github仓库 DayDayUP:github.com/RobodLee/DayDayUP,欢迎Star 畅购商城(一):环境搭建 畅购商城(二):分布式文件系统 ...

  6. 畅购商城(五):Elasticsearch实现商品搜索

    好好学习,天天向上 本文已收录至我的Github仓库DayDayUP:github.com/RobodLee/DayDayUP,欢迎Star,更多文章请前往:目录导航 畅购商城(一):环境搭建 畅购商 ...

  7. 畅购商城_第11章_ 订单

    畅购商城_第11章_ 订单 文章目录 畅购商城_第11章_ 订单 第11章 订单 课程内容 1 订单结算页 1.1 收件地址分析 1.2 实现用户收件地址查询 1.2.1 代码实现 1.2.2 测试 ...

  8. 畅购商城(十三):秒杀系统「上」

    好好学习,天天向上 本文已收录至我的Github仓库DayDayUP:github.com/RobodLee/DayDayUP,欢迎Star 畅购商城(一):环境搭建 畅购商城(二):分布式文件系统F ...

  9. 畅购商城六:微服务网关与jwt令牌

    微服务网关 基本概念 对于微服务的各个服务一般会有不同的地址,外部客户端的一个服务可能要调用诸多的接口,这会带来以下的问题 客户端会多次请求不同的微服务,地址复杂 存在跨域请求,处理复杂 认证复杂 难 ...

最新文章

  1. 汇编: 在代码中安排自己定义的数据,栈空间
  2. 人工智能一定要用python吗_学人工智能一定要学Python吗?
  3. 【CentOS】磁盘管理与vim编译器
  4. php的主要架构,php运行原理与基本结构
  5. Spring管理session的一些认识和用法心得
  6. asp.net core的文件下载
  7. jboss配置ejb容器_JBoss AS 7 EJB3池配置
  8. 使用Maven设置您的应用服务器
  9. 学云计算能干什么_陌陌主播等级计算?陌陌主播升级明细表?
  10. 确保VDI顺利部署 试点项目是关键
  11. java中redis存储map集合_使用RedisTemplate存储Map集合的一点注意
  12. Mac中如何卸载pkg包
  13. 魔兽世界单机(芒果3.3.5a)机器人操作命令大全
  14. 由对称性知定点一定在x轴上_2021版江苏高考数学一轮复习讲义:第8章 第10节 圆锥曲线中的证明、探索性问题 Word版含答案...
  15. 浅析API网关——Ocelot[网关]+Consul[服务发现负载均衡]+Polly[服务熔断]+Ids4[服务认证]
  16. 北京信息科技大学计算机学院官网,北京信息科技大学教务处官网入口地址
  17. 接口测试必知必会知识点
  18. 企鹅杏仁集团完成2.5亿美元融资,投后估值超过10亿美元...
  19. 正确打开/解读Logit模型系数的方式——离散选择模型之四
  20. 已有项目依赖cordovaLib打包后调用插件崩溃问题

热门文章

  1. 学习WEB前端第四天(3)-背景图像
  2. 程序员为什么不会修电脑
  3. 关于程序员的职业规划分析
  4. 深度了解自监督学习,就看这篇解读 !何恺明新作MAE:通向CV大模型
  5. ROS暑期学校与ROSCon 2018
  6. kotlin读取文件算法
  7. 抖音V1.7.9调研报告
  8. 锐捷交换机的环路检测
  9. 企业上云要几步?中拓互联奉送企业上云全攻略
  10. django模型类中,为什不是user_id而是user?