在 foodie-dev-pojo 模块中的 com.imooc.pojo.vo 包内创建 SearchItemsVO 类

    1. package com.imooc.pojo.vo;
    2. /**
    3. * 用于展示商品搜索列表结果的 VO
    4. * Created by 92578 on 2020/8/22 21:28
    5. **/
    6. public class SearchItemsVO {
    7. private String itemId;
    8. private String itemName;
    9. private int sellCounts;
    10. private String imgUrl;
    11. private int price;
    12. public String getItemId() {
    13. return itemId;
    14. }
    15. public void setItemId(String itemId) {
    16. this.itemId = itemId;
    17. }
    18. public String getItemName() {
    19. return itemName;
    20. }
    21. public void setItemName(String itemName) {
    22. this.itemName = itemName;
    23. }
    24. public int getSellCounts() {
    25. return sellCounts;
    26. }
    27. public void setSellCounts(int sellCounts) {
    28. this.sellCounts = sellCounts;
    29. }
    30. public String getImgUrl() {
    31. return imgUrl;
    32. }
    33. public void setImgUrl(String imgUrl) {
    34. this.imgUrl = imgUrl;
    35. }
    36. public int getPrice() {
    37. return price;
    38. }
    39. public void setPrice(int price) {
    40. this.price = price;
    41. }
    42. }

    【注意】
    涉及到金额都是以“分”为单位,保证金额不会有任何差错,因为以“元”为单位在计算的时候会有四舍五入的问题
    在 foodie-dev-mapper 模块中完善 ItemsMapperCustom.xml,添加 searchItems 查询语句
    k:默认,代表默认排序,根据 name
    c:根据销量排序
    p:根据价格排序

    <?xml version="1.0" encoding="UTF-8"?>
    <!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
    <mapper namespace="com.imooc.mapper.ItemsMapperCustom">
        <select id="queryItemComments" parameterType="Map" resultType="com.imooc.pojo.vo.ItemCommentVO">
            select ic.comment_level as commentLevel,
            ic.content as content,
            ic.sepc_name as sepcName,
            ic.created_time as createdTime,
            u.face as userFace,
            u.nickname as nickname
            from items_comments as ic
            left join users as u on ic.user_id = u.id
            where ic.item_id = #{paramsMap.itemId}
            <if test=" paramsMap.level != null and paramsMap.level != '' ">
                and ic.comment_level = #{paramsMap.level}
            </if>
        </select>
        <select id="searchItems" parameterType="Map" resultType="com.imooc.pojo.vo.SearchItemsVO">
            SELECT
                i.id AS itemId,
                i.item_name AS itemName,
                i.sell_counts AS sellCounts,
                ii.url AS imgUrl,
                tempSpec.price_discount AS price
            FROM
                items i
                LEFT JOIN items_img ii ON i.id = ii.item_id
                LEFT JOIN ( SELECT item_id, MIN( price_discount ) AS price_discount FROM items_spec GROUP BY item_id ) tempSpec ON i.id = tempSpec.item_id
            WHERE
                ii.is_main = 1
                <if test=" paramsMap.keywords != null and paramsMap.keywords != '' ">
                    and i.item_name like '%${paramsMap.keywords}%'
                </if>
                order by
                <choose>
                    <when test=" paramsMap.sort == &quot;c&quot; ">
                        i.sell_counts desc
                    </when>
                    <when test=" paramsMap.sort == &quot;p&quot; ">
                        tempSpec.price_discount asc
                    </when>
                    <otherwise>
                        i.item_name asc
                    </otherwise>
                </choose>
        </select>
    </mapper>
    

    【注意】
    如果单引号识别不了,需要对其进行转义
    在 foodie-dev-service 模块中完善 ItemService 接口,添加 searchItems 方法

    package com.imooc.service;
    
    import com.imooc.pojo.Items;
    import com.imooc.pojo.ItemsImg;
    import com.imooc.pojo.ItemsParam;
    import com.imooc.pojo.ItemsSpec;
    import com.imooc.pojo.vo.CommentLevelCountsVO;
    import com.imooc.utils.PagedGridResult;
    
    import java.util.List;
    
    /**
     * Created by 92578 on 2020/8/22 16:17
     **/
    public interface ItemService {
    
        /**
         * 根据商品 id 查询详情
         *
         * @param itemId
         * @return
         */
        public Items queryItemById(String itemId);
    
        /**
         * 根据商品 id 查询商品图片列表
         *
         * @param itemId
         * @return
         */
        public List<ItemsImg> queryItemImgList(String itemId);
    
        /**
         * 根据商品 id 查询商品规格
         *
         * @param itemId
         * @return
         */
        public List<ItemsSpec> queryItemSpecList(String itemId);
    
        /**
         * 根据商品 id 查询商品参数
         *
         * @param itemId
         * @return
         */
        public ItemsParam queryItemsParam(String itemId);
    
        /**
         * 根据商品 id 查询商品的评价等级数量
         *
         * @param itemId
         */
        public CommentLevelCountsVO queryCommentCounts(String itemId);
    
        /**
         * 根据商品 id 查询商品的评价(分页)
         *
         * @param itemId
         * @param level
         * @return
         */
        public PagedGridResult queryPagedComments(String itemId, Integer level, Integer page, Integer pageSize);
    
        /**
         * 搜索商品列表
         * @param keywords
         * @param sort
         * @param page
         * @param pageSize
         * @return
         */
        public PagedGridResult searchItems(String keywords, String sort, Integer page, Integer pageSize);
    }
    

    在 foodie-dev-mapper 模块中完善 ItemsMapperCustom 接口,添加 searchItems 方法

    package com.imooc.mapper;
    
    import com.imooc.pojo.vo.ItemCommentVO;
    import com.imooc.pojo.vo.SearchItemsVO;
    import org.apache.ibatis.annotations.Param;
    
    import java.util.List;
    import java.util.Map;
    
    public interface ItemsMapperCustom {
        public List<ItemCommentVO> queryItemComments(@Param("paramsMap") Map<String, Object> map);
    
        public List<SearchItemsVO> searchItems(@Param("paramsMap") Map<String, Object> map);
    }
    

    在 foodie-dev-service 模块中完善 ItemServiceImpl 类,添加 searchItems 方法

    package com.imooc.service.impl;
    
    import com.github.pagehelper.PageHelper;
    import com.github.pagehelper.PageInfo;
    import com.imooc.enums.CommentLevel;
    import com.imooc.mapper.*;
    import com.imooc.pojo.*;
    import com.imooc.pojo.vo.CommentLevelCountsVO;
    import com.imooc.pojo.vo.ItemCommentVO;
    import com.imooc.pojo.vo.SearchItemsVO;
    import com.imooc.service.ItemService;
    import com.imooc.utils.DesensitizationUtil;
    import com.imooc.utils.PagedGridResult;
    import org.springframework.beans.factory.annotation.Autowired;
    import org.springframework.stereotype.Service;
    import org.springframework.transaction.annotation.Propagation;
    import org.springframework.transaction.annotation.Transactional;
    import tk.mybatis.mapper.entity.Example;
    
    import java.util.HashMap;
    import java.util.List;
    import java.util.Map;
    
    /**
     * Created by 92578 on 2020/8/22 16:18
     **/
    @Service
    public class ItemServiceImpl implements ItemService {
    
        @Autowired
        private ItemsMapper itemsMapper;
    
        @Autowired
        private ItemsImgMapper itemsImgMapper;
    
        @Autowired
        private ItemsSpecMapper itemsSpecMapper;
    
        @Autowired
        private ItemsParamMapper itemsParamMapper;
    
        @Autowired
        private ItemsCommentsMapper itemsCommentsMapper;
    
        @Autowired
        private ItemsMapperCustom itemsMapperCustom;
    
        /**
         * 根据商品 id 查询详情
         *
         * @param itemId
         * @return
         */
        @Transactional(propagation = Propagation.SUPPORTS)
        @Override
        public Items queryItemById(String itemId) {
            return itemsMapper.selectByPrimaryKey(itemId);
        }
    
        /**
         * 根据商品 id 查询商品图片列表
         *
         * @param itemId
         * @return
         */
        @Transactional(propagation = Propagation.SUPPORTS)
        @Override
        public List<ItemsImg> queryItemImgList(String itemId) {
            Example itemsImgExp = new Example(ItemsImg.class);
            Example.Criteria criteria = itemsImgExp.createCriteria();
            criteria.andEqualTo("itemId", itemId);
    
            return itemsImgMapper.selectByExample(itemsImgExp);
        }
    
        /**
         * 根据商品 id 查询商品规格
         *
         * @param itemId
         * @return
         */
        @Transactional(propagation = Propagation.SUPPORTS)
        @Override
        public List<ItemsSpec> queryItemSpecList(String itemId) {
            Example itemsSpecExp = new Example(ItemsSpec.class);
            Example.Criteria criteria = itemsSpecExp.createCriteria();
            criteria.andEqualTo("itemId", itemId);
    
            return itemsSpecMapper.selectByExample(itemsSpecExp);
        }
    
        /**
         * 根据商品 id 查询商品参数
         *
         * @param itemId
         * @return
         */
        @Transactional(propagation = Propagation.SUPPORTS)
        @Override
        public ItemsParam queryItemsParam(String itemId) {
            Example itemsParamExp = new Example(ItemsParam.class);
            Example.Criteria criteria = itemsParamExp.createCriteria();
            criteria.andEqualTo("itemId", itemId);
    
            return itemsParamMapper.selectOneByExample(itemsParamExp);
        }
    
        /**
         * 根据商品 id 查询商品的评价等级数量
         *
         * @param itemId
         */
        @Transactional(propagation = Propagation.SUPPORTS)
        @Override
        public CommentLevelCountsVO queryCommentCounts(String itemId) {
            Integer goodCounts = getCommentCounts(itemId, CommentLevel.GOOD.type);
            Integer normalCounts = getCommentCounts(itemId, CommentLevel.NORMAL.type);
            Integer badCounts = getCommentCounts(itemId, CommentLevel.BAD.type);
            Integer totalCounts = goodCounts + normalCounts + badCounts;
    
            CommentLevelCountsVO countsVO = new CommentLevelCountsVO();
            countsVO.setTotalCounts(totalCounts);
            countsVO.setGoodCounts(goodCounts);
            countsVO.setNormalCounts(normalCounts);
            countsVO.setBadCounts(badCounts);
    
            return countsVO;
        }
    
        /**
         * 根据商品 id 查询商品的评价(分页)
         *
         * @param itemId
         * @param level
         * @return
         */
        @Transactional(propagation = Propagation.SUPPORTS)
        @Override
        public PagedGridResult queryPagedComments(String itemId, Integer level, Integer page, Integer pageSize) {
            Map<String, Object> map = new HashMap<>();
            map.put("itemId", itemId);
            map.put("level", level);
    
            /**
             * page: 第几页
             * pageSize: 每页显示条数
             */
            PageHelper.startPage(page, pageSize);
    
            List<ItemCommentVO> list = itemsMapperCustom.queryItemComments(map);
            for (ItemCommentVO vo : list) {
                vo.setNickname(DesensitizationUtil.commonDisplay(vo.getNickname()));
            }
    
            return setterPagedGrid(list, page);
        }
    
        /**
         * 搜索商品列表
         *
         * @param keywords
         * @param sort
         * @param page
         * @param pageSize
         * @return
         */
        @Transactional(propagation = Propagation.SUPPORTS)
        @Override
        public PagedGridResult searchItems(String keywords, String sort, Integer page, Integer pageSize) {
            Map<String, Object> map = new HashMap<>();
            map.put("keywords", keywords);
            map.put("sort", sort);
    
            PageHelper.startPage(page, pageSize);
            List<SearchItemsVO> list = itemsMapperCustom.searchItems(map);
    
            return setterPagedGrid(list, page);
        }
    
        private PagedGridResult setterPagedGrid(List<?> list, Integer page) {
            PageInfo<?> pageList = new PageInfo<>(list);
            PagedGridResult grid = new PagedGridResult();
            grid.setPage(page);
            grid.setRows(list);
            grid.setTotal(pageList.getPages());
            grid.setRecords(pageList.getTotal());
            return grid;
        }
    
        @Transactional(propagation = Propagation.SUPPORTS)
        Integer getCommentCounts(String itemId, Integer level) {
            ItemsComments condition = new ItemsComments();
            condition.setItemId(itemId);
            if (level != null) {
                condition.setCommentLevel(level);
            }
    
            return itemsCommentsMapper.selectCount(condition);
        }
    }
    

    在 foodie-dev-api 模块中完善 ItemsController 类,添加 search 方法

    package com.imooc.controller;
    
    import com.imooc.pojo.Items;
    import com.imooc.pojo.ItemsImg;
    import com.imooc.pojo.ItemsParam;
    import com.imooc.pojo.ItemsSpec;
    import com.imooc.pojo.vo.CommentLevelCountsVO;
    import com.imooc.pojo.vo.ItemInfoVO;
    import com.imooc.service.ItemService;
    import com.imooc.utils.IMOOCJSONResult;
    import com.imooc.utils.PagedGridResult;
    import io.swagger.annotations.Api;
    import io.swagger.annotations.ApiOperation;
    import io.swagger.annotations.ApiParam;
    import org.apache.commons.lang3.StringUtils;
    import org.springframework.beans.factory.annotation.Autowired;
    import org.springframework.web.bind.annotation.*;
    
    import java.util.List;
    
    /**
     * Created by 92578 on 2020/8/22 16:30
     **/
    @Api(value = "商品接口", tags = {"商品信息展示的相关接口"})
    @RestController
    @RequestMapping("items")
    public class ItemsController extends BaseController {
    
        @Autowired
        private ItemService itemService;
    
        @ApiOperation(value = "查询商品详情", notes = "查询商品详情", httpMethod = "GET")
        @GetMapping("/info/{itemId}")
        public IMOOCJSONResult info(
                @ApiParam(name = "itemId", value = "商品 id", required = true)
                @PathVariable String itemId) {
            if (StringUtils.isBlank(itemId)) {
                return IMOOCJSONResult.errorMsg(null);
            }
    
            Items item = itemService.queryItemById(itemId);
            List<ItemsImg> itemsImgList = itemService.queryItemImgList(itemId);
            List<ItemsSpec> itemsSpecList = itemService.queryItemSpecList(itemId);
            ItemsParam itemsParam = itemService.queryItemsParam(itemId);
    
            ItemInfoVO itemInfoVO = new ItemInfoVO();
            itemInfoVO.setItem(item);
            itemInfoVO.setItemImgList(itemsImgList);
            itemInfoVO.setItemSpecList(itemsSpecList);
            itemInfoVO.setItemParams(itemsParam);
    
            return IMOOCJSONResult.ok(itemInfoVO);
        }
    
        @ApiOperation(value = "查询商品评价等级", notes = "查询商品评价等级", httpMethod = "GET")
        @GetMapping("/commentLevel")
        public IMOOCJSONResult commentLevel(
                @ApiParam(name = "itemId", value = "商品 id", required = true)
                @RequestParam String itemId) {
            if (StringUtils.isBlank(itemId)) {
                return IMOOCJSONResult.errorMsg(null);
            }
    
            CommentLevelCountsVO countsVO = itemService.queryCommentCounts(itemId);
    
            return IMOOCJSONResult.ok(countsVO);
        }
    
        @ApiOperation(value = "查询商品评论", notes = "查询商品评论", httpMethod = "GET")
        @GetMapping("/comments")
        public IMOOCJSONResult comments(
                @ApiParam(name = "itemId", value = "商品 id", required = true)
                @RequestParam String itemId,
                @ApiParam(name = "level", value = "评价等级", required = false)
                @RequestParam Integer level,
                @ApiParam(name = "page", value = "查询下一页的第几页", required = false)
                @RequestParam Integer page,
                @ApiParam(name = "pageSize", value = "分页的每一页显示的条数", required = false)
                @RequestParam Integer pageSize) {
            if (StringUtils.isBlank(itemId)) {
                return IMOOCJSONResult.errorMsg(null);
            }
    
            if (page == null) {
                page = 1;
            }
    
            if (pageSize == null) {
                pageSize = COMMENT_PAGE_SIZE;
            }
    
            PagedGridResult grid = itemService.queryPagedComments(itemId, level, page, pageSize);
    
            return IMOOCJSONResult.ok(grid);
        }
    
        @ApiOperation(value = "搜索商品列表", notes = "搜索商品列表", httpMethod = "GET")
        @GetMapping("/search")
        public IMOOCJSONResult search(
                @ApiParam(name = "keywords", value = "关键字", required = true)
                @RequestParam String keywords,
                @ApiParam(name = "sort", value = "排序", required = false)
                @RequestParam String sort,
                @ApiParam(name = "page", value = "查询下一页的第几页", required = false)
                @RequestParam Integer page,
                @ApiParam(name = "pageSize", value = "分页的每一页显示的条数", required = false)
                @RequestParam Integer pageSize) {
            if (StringUtils.isBlank(keywords)) {
                return IMOOCJSONResult.errorMsg(null);
            }
    
            if (page == null) {
                page = 1;
            }
    
            if (pageSize == null) {
                pageSize = PAGE_SIZE;
            }
    
            PagedGridResult grid = itemService.searchItems(keywords, sort, page, pageSize);
    
            return IMOOCJSONResult.ok(grid);
        }
    }
    

    在 foodie-dev-api 模块中完善 BaseController 类,添加 PAGE_SIZE 常量

    package com.imooc.controller;
    
    import org.springframework.stereotype.Controller;
    
    /**
     * @author 92578
     * @since 1.0
     */
    @Controller
    public class BaseController {
        public static final Integer COMMENT_PAGE_SIZE = 10;
        public static final Integer PAGE_SIZE = 20;
    }
    

    启动项目,访问 http://localhost:8088/doc.html
    找到商品信息展示的相关接口——搜索商品列表
    image.png
    访问 http://localhost:8080/foodie-shop/
    搜索“好吃”
    image.png
    点击“销量排序”
    image.png
    点击“价格排序”
    image.png
    搜索“网红”
    image.png