栏目分类:
子分类:
返回
名师互学网用户登录
快速导航关闭
当前搜索
当前分类
子分类
实用工具
热门搜索
名师互学网 > IT > 软件开发 > 后端开发 > Java

谷粒商城-学习笔记-基础篇-商品服务1(P45-P58)

Java 更新时间: 发布时间: IT归档 最新发布 模块sitemap 名妆网 法律咨询 聚返吧 英语巴士网 伯小乐 网商动力

谷粒商城-学习笔记-基础篇-商品服务1(P45-P58)

谷粒商城-基础篇2
  • 一、商品服务-API-三级分类
    • 1、三级分类
    • 2、查出所有分类以及子分类
    • 2、配置网关路由与路径重写
    • 3、网关统一配置跨域
    • 4、查询-树形展示三级分类数据
    • 5、删除
    • 6、新增
    • 7、修改
    • 8、修改拖拽效果
    • 9、批量删除


商品服务-三级分类

一、商品服务-API-三级分类 1、三级分类
  • pms_category 表代表商品的分类
cat_id:分类id,cat代表分类,bigint(20)
name:分类名称
parent_cid:在哪个父目录下
cat_level:分类层级
show_status:是否显示,用于逻辑删除
sort:同层级同父目录下显示顺序
ico图标,product_unit商品计量单位,
InnoDB表,自增大小1437,utf编码,动态行格式
2、查出所有分类以及子分类

1.在product服务的package com.ljn.gulimall.product.controller中打开CategoryController,添加方法:

@RestController
@RequestMapping("product/category")
public class CategoryController {
    @Autowired
    private CategoryService categoryService;

    
    @RequestMapping("/list/tree")
    public R list(){
        List entities = categoryService.listWithTree();
        return R.ok().put("data", entities);
    }

2…在product服务的package com.ljn.gulimall.product.service;中打开CategoryService,添加方法:

public interface CategoryService extends IService {

    PageUtils queryPage(Map params);

    List listWithTree();
}

3.在product服务的package com.ljn.gulimall.product.service.impl;中打开CategoryServiceImpl实现方法:

package com.ljn.gulimall.product.service.impl;

@Service("categoryService")
public class CategoryServiceImpl extends ServiceImpl implements CategoryService {

    // 注入CategoryDao
    @Autowired
    CategoryDao categoryDao;

    @Override
    public PageUtils queryPage(Map params) {
        IPage page = this.page(
                new Query().getPage(params),
                new QueryWrapper()
        );

        return new PageUtils(page);
    }

    // 实现方法
    @Override
    public List listWithTree() {
        // 1.查出所有分类
        List entities = categoryDao.selectList(null);

        // 2.组装成父子的树形结构
        //  2.1 找到所有一级分类,一级分类父id=0,并返回为一个集合
        List Level1Menus = entities.stream().filter(categoryEntity -> {
            //  一级分类
            return categoryEntity.getParentCid() == 0;
        }).map((menu) -> {
            // 将查找到的子菜单放入
            menu.setChildren(getChildrens(menu, entities));
            return menu;
        }).sorted((menu1, menu2) -> {
            // 排序
            return (menu1.getSort() == null ? 0 : menu1.getSort()) - (menu2.getSort() == null ? 0 : menu2.getSort());
        }).collect(Collectors.toList());

        return Level1Menus;
    }

    // 递归查找所有菜单的子菜单,root:当前菜单    all:所有菜单
    private List getChildrens(CategoryEntity root, List all) {

        // 从所有菜单中过滤出子菜单
        List children = all.stream().filter(categoryEntity -> {
            // 当前菜单的父ID=指定菜单的id  也就是判断在哪个父目录下
            return categoryEntity.getParentCid().equals(root.getCatId());
        }).map(categoryEntity -> {
            // 当前菜单还可能有子菜单
            categoryEntity.setChildren(getChildrens(categoryEntity, all));
            return categoryEntity;
        }).sorted((menu1, menu2) -> {
            // 排序
            return (menu1.getSort() == null ? 0 : menu1.getSort()) - (menu2.getSort() == null ? 0 : menu2.getSort());
        }).collect(Collectors.toList());

        return children;
    }

}

4.结果

2、配置网关路由与路径重写

启动renren-fast 前后端项目:

  • 点击系统管理,菜单管理,新增

    刷新,看到左侧多了商品系统,添加的这个菜单其实是添加到了guli-admin.sys_menu表里.

  • 继续新增:分类维护菜单

在左侧点击【分类维护】,希望在此展示3级分类

注意地址栏http://localhost:8001/#/product-category 可以注意到product-category我们的/被替换为了-

比如sys-role具体的视图在renren-fast-vue/views/modules/sys/role.vue

  • 所以要自定义我们的product/category视图的话,就是创建mudules/product/category.vue






网关88配置

  • 在登录管理后台的时候,我们会发现,他要请求localhost:8080/renren-fast/product/category/list/tree这个url
  • 他要给8080发请求读取数据,但是数据是在10000端口上,如果找到了这个请求改端口那改起来很麻烦。
  • 方法1是改vue项目里的全局配置.
  • 方法2是搭建个网关,让网关路由到10000(即将vue项目里的请求都给网关,网关经过url处理后,去nacos里找到管理后台的微服务,就可以找到对应的端口了,这样我们就无需管理端口,统一交给网关管理端口接口)

1.在vue项目的 static/config/index.js里修改

 window.SITE_CONFIG['baseUrl'] = 'http://localhost:88/api';
// 意思是说本vue项目中要请求的资源url都发给88/api,那么我们就让网关端口为88,然后匹配到/api请求即可,
// 网关可以通过过滤器处理url后指定给某个微服务
// renren-fast服务已经注册到了nacos中

刷新后需要重新登录,此时验证码不显示,因为此时验证码是请求88的,所以不显示。而验证码是来源于fast后台即8080端口的的。

解决:将renren-fast 注册到nacos注册中心,这样请求88网关转发到8080fast。

2.让fast里加入注册中心的依赖:

 
        
            com.alibaba.cloud
            spring-cloud-starter-alibaba-nacos-config
            2.1.0.RELEASE
        


        
        
            com.alibaba.cloud
            spring-cloud-starter-alibaba-nacos-discovery
            2.1.0.RELEASE
        

3.在renren-fast项目的application.yml中添加:

spring:
  application:
    name: renren-fast  # 意思是把renren-fast项目也注册到nacos中,这样网关才能转发给
  cloud:
    nacos:
      discovery:
        server-addr: localhost:8848 # nacos
        

4.开启服务注册与发现

@EnableDiscoveryClient
@SpringBootApplication
public class RenrenApplication {

	public static void main(String[] args) {
		SpringApplication.run(RenrenApplication.class, args);
	}
}

5.在gateway服务中按格式加入

          - id: admin_route
            #            lb 代表负载均衡
            uri: lb://renren-fast       # 路由给renren-fast
            predicates:                 # 什么情况下路由给它
              - Path=/api*.xml
  global-config:
    db-config:
      id-type: auto
      logic-delete-value: 1   
      logic-not-delete-value: 0
  • 修改product.entity.CategoryEntity实体类,添加上@TableLogic,表明使用逻辑删除
	
	@TableLogic(value = "1",delval = "0")
	private Integer showStatus;

3、apifox测试请求

4、前端请求处理

发送的请求:delete
发送的数据:this.$http.adornData(ids, false)
util/httpRequest.js中,封装了一些拦截器
http.adornParams是封装get请求的数据
http.adornData封装post请求的数据
ajax的get请求会被缓存,就不会请求服务器了。
所以我们在url后面拼接个date时间戳,让他每次都请求服务器

  • 发送请求
 // 2. 删除分类的方法
remove(node, data) {
  // 1. 获取当前节点id
  var ids = [data.catId]

  // 2. 发送请求前弹框提示
  this.$confirm(`是否删除${data.name}菜单?`, '提示', {
    confirmButtonText: '确定',
    cancelButtonText: '取消',
    type: 'warning'
  }).then(() => {
    // 3. 确认删除,发送post请求
    this.$http({
      url: this.$http.adornUrl('/product/category/delete'),
      method: 'post',
      data: this.$http.adornData(ids, false)
    }).then(({ data }) => {
      // 4. 删除成功提示消息
      this.$message({
        type: "success",
        message: "菜单删除成功!",
      });
      // 5. 删除成功后重新请求菜单
      this.getMenus();
      // 6. 设置默认展开菜单
      this.expandedKey=[node.parent.data.catId]
    })
  }).catch(() => {

  });

  console.log("delete", node, data)
},

  • 删除后展开标准


 data() {
    return {
      expandedKey: [], // 展开基准
    };
  },
6、新增
  1. 点击append按钮的时候打开对话框
  • 用到属性 visible.sync,动态绑定,:visible.sync="dialogVisible"
  
    
      
        取 消
        确 定
      
    

	 data() {
    	return {
      	dialogVisible: false, // 是否打开对话框,默认为false
    };
  },
 	methods: {
    	append(data) {
      	// 1. 点击append 按钮打开对话框
      	this.dialogVisible = true;
      	console.log("append", data)
    },
  1. 对话框中添加表单
  • 属性
    

      
      
        
          
          
        
      

      
      
        取 消
        确 定
      

    
  1. 定义添加菜单的方法addCategory,并在append方法中设置默认值
 // 4. 添加三级分类的方法
    addCategory() {
      console.log("提交的三级分类数据", this.category)
      // 1. 发送保存请求,提交
      this.$http({
        url: this.$http.adornUrl('/product/category/save'),
        method: 'post',
        data: this.$http.adornData(this.category, false)  // 要发送的数据
      }).then(({ data }) => {
        // 2. 保存成功提示消息
        this.$message({
          type: "success",
          message: "菜单保存成功!",
        });
        // 3. 保存成功后关闭对话框
        this.dialogVisible = false;
        // 4. 刷新出新菜单
        this.getMenus();
        // 5. 设置默认展示的菜单
        this.expandedKey = [this.category.parentCid];

      })

    },

	 append(data) {
      console.log("append", data)
      // 1. 点击append 按钮打开对话框
      this.dialogVisible = true;
      // 2. 点击按钮为category获取默认值
      //    2.1 父id,当前点击append的catId
      this.category.parentCid = data.catId;
      //    2.2 层级catLevel 当前点击append 的层级+1
      this.category.catLevel = data.catLevel * 1 + 1;
    },
7、修改
  1. 增加修改按钮edit
         
           Edit
         

	 methods: {
		// 5. 点击修改分类按钮
	    edit(node, data){
	    // 显示对话框
     	 this.dialogVisible=true;
     	 // 回显数据
     	 this.category.name=data.name;
	      console.log(node,data)
	    },
	}

  1. 复用对话框
  • 定义对话框类型:dialogType
  • 修改对话框确认按钮绑定的事件:submitDate (提交数据)
  • 根据对话框类型动态提交数据
  • 修改完后,在append中清除回显信息
    
    

      
      
        
          
          
        

        
          
        

        
          
        

      

      
      
        取 消
        确 定