一. 开源算法Snowflake生成分布式id
1. 原因: 数据量庞大 ->分库分表 -> 数据库多实例部署 -> 唯一的全局ID
2. UUID: universe unique ID -> 32位长度字符串
(1) 缺点: 无排序, 无递增; 字符串存储查询效率低; 存储量大; 传输数据量大; 不可读
3. Redis:
(1) 单线程特点 -> 原子性 -> INCR / INCRBY
(2) 优点: 不依赖数据库, 性能优于数据库; 天然排序
(3) 缺点: 引入Redis组件增加系统复杂度; 编码和配置工作量大; 网络传输性能下降
4. Snowflake: Twitter开源算法
(1) Long型ID, 本机算法生成ID, 可排序
(2) 组成: 64位(1位不用+41位毫秒时间戳+10位手动机器ID+12位序列号)
(3) 工具类IdWorker: 放到公共模块changgou_common/util
(4)测试: long id = new IdWorker(workerId, DatacenterId).nextId();
(5)使用步骤:
1) application.yml中配置: workerId: 0 ; datacenterId: 0
2) 启动类注入: @Bean IdWorker(){}
3) 取值: @Value("${workerId}")
二. SPU & SKU
1. SPU: standard product unit 商品信息集合最小单位 -> 例: 京东商品详情页, 多个属性规格
2. SKU: stock keep unit 库存量单位 -> 京东购物车添加的单位商品
3.前端 传递的数据格式: 一个spu对象+sku列表
(1). {"spu":{"name":"value1",
"brand":{"value1","value2",.....},
.....},
"skuList":[{"sn":"value1", "num":"value2",...},
{},{},......]}
三. 新增和修改商品功能
1. Plain Ordinary Java Object类: changgou_service_goods_api / pojo/Goods: spu+skuList
2. changgou_service_goods/SpuService业务接口: add(Goods goods)方法
3.业务层实现类SpuServiceImpl:
(1) 商品ID: long spuId = IdWorker.nextId();
(2) 删除状态 / 上架状态 / 审核转态: spu.setXXX("0");
(3)添加spu: spuMapper.insertSelective(spu);
4.添加SKU数据:
(1) Llist skuList = goods.getSkuList();
(2) !=null则比遍历集合
(3) sku.setId(String.valueOf(idWorker.nextId()); //设置skuId
(4) sku.name(spu名称+规格)
1) JSON格式的规格转换为map格式: JSON.parseObject(sku.getSpec(), Map.class);
2) 遍历map得到规格: name+=" "+value;
(5) 设置spuId / 创建时间 / 修改时间 / 分类ID / 商品分类名称 /品牌名称
(6) 添加到数据库: skuMapper.insertSelective(sku);
5. SpuController数据控制层:
四. 品牌Brand和商品分类Category关联:
1. CategoryBrand实体类: (1). @Table(name="tb_category_brand") (2). 联合主键:@Id categoryId / brandId 2. SpuServiceImpl实现类: (1) @Autowired categoryBrandMapper (2) categoryBrand.setBrandId() (3) categoryBrand.setCategoryId() (4) 查询关联表: int count = categoryBrandMapper.selectCount(categoryBrand); (5) count==0, 则brand和category无关联 (6) 插入关联表: categoryBrandMapper.insert(categoryBrand)
五. 根据ID查询商品:
1. Spu spu = spuMapper.selectByPrimaryKey(id);
2. 查询example对象的准则: Example.Criteria criteria = new Example(Sku.class).createCriteria();
3. 查询条件: citeria.andEqualTo("spuId");
4. 查询: List skuList = skuMapper.selectByExample(example);
5. 表现层SpuController: @GetMapping("/{id}") findById(@PathVariable String id){};
六. 修改商品:
1. 修改spu; spuMapper.updateByPrimaryKey(goods.getSpu());
2. 删除原有skuList: skuMapper.deleteByExample(new Example(Sku.class).createCriteria()));
3. 添加新的skuList: this.saveSkuList(goods);
4. 表现层: @PutMapping(value="/{id}") update(@RequestBody Goods goods) {};
七. 商品审核和上下架
1. 审核 -> 是否删除 -> "0"为否 ->则审核状态"1", 上架状态"1"
(1)业务层: spuMapper.updateByPrimaryKeySelective(spu.setIsMarketable("1"));
(2)控制层: @PutMapping("audit/{id}") audit(@PathVariable("id") String id){};
2.下架 -> 是否删除 ->"0"为否 -> 修改为下架状态"0"
(1) SpuServiceImpl: suMapper.updateByPrimaryKeySelective(spu.setIsMarketable("0"));
(2) SpuController: @PutMapping("/pull/{id}") pull(@PathVariable("id") String id){};
3. 上架 -> 是否为空 -> 是否已审核 -> "1"为是 ->
(1) 业务层: spu.setIsMarketabe("1")
(2) 控制层: @PutMapping("/put/{id}") put(@PathVariable("id") String id){};
八. 删除与还原商品
1. 删除: 不是物理删除, 而是逻辑删除, isDelete字段设置为"1"
(1) 查询spu -> 是否下架 -> 是则修改isDelete标记位
(2) Spu spu = spuMapper.selectByPrimaryKey(id);
(3) spu.setIsDelete("1")
(4) spu.setStatus("0")
(5) spuMapper.updateByPrimaryKeySelective(spu);
2. 回收站 -> 删除 -> 物理删除
(1) SpuService接口: void realDel(String id);
(2) 业务层: 查询spu -> 是否已删除 -> 是则删除
1) Spu spu = spuMapper.selectByPrimaryKey(id);
2) spuMapper.deleteByPrimaryKey(id);
(3)控制层: @DeleteMapping("/realDel/{id}") realDel(@PathVariable("id") String id){};
3. 回收站 -> 还原 -> isDelete字段设置"0"
(1) SpuService接口: void restart(String id);
(2) 业务层: 查询spu -> 判断是否删除 -> 是则修改IsDelete字段 -> 保存
1) 设置未删除: setIsDelete("0")
1) 设置未审核: setStatus("0")
(3) SpuController: @PutMapping("/erstore/{id}") restore(@PathVariable("id") String id){};



