写在前面
本篇我们来介绍后台商品详细信息获取的功能,这里面有几个字段的获取比较特殊,需要格外注意。
获取商品详情
首先打开ProductManageController.java文件,在里面新增以下代码:
/*** * * 后台管理员获取商品的详情 * */ @RequestMapping("detail.do") @ResponseBody //自动序列化json功能 public ServerResponse getDetail(HttpSession session, Integer productId){ //判断一下登录情况 User user=(User) session.getAttribute(Const.CURRENT_USER); if(user ==null){ return ServerResponse.createByErrorCodeMessage(ResponseCode.NEED_LOGIN.getCode(),"用户未登录,请登录"); } //判断一下是不是管理员身份 if(iUserService.checkAdminRole(user).isSuccess()){ //如果是管理员就增加我们获取商品详情的逻辑 return iProductService.manageGetDetail(productId); }else{ return ServerResponse.createByErrorMessage("无权限操作,需要管理员权限"); } }
接着打开ProductServiceImpl.java文件,里面写入以下代码:
/*** * * 后台管理员获取商品的详情 * */ public ServerResponse<ProductDetailVo> manageGetDetail(Integer productId) { //判断商品是否存在 if (productId == null) { //商品id不存在 return ServerResponse.createByErrorCodeMessage(ResponseCode.ILLEGAL_ARGUMENT.getCode(), ResponseCode.ILLEGAL_ARGUMENT.getDesc()); } Product product = productMapper.selectByPrimaryKey(productId); if (product == null) { return ServerResponse.createByErrorMessage("该商品已下架或者删除!"); } // vo对象--value object //pojo -->bo(business object)--->vo(view object) //我们这里还是先按照技术结构的演变,使用vo等到后面升级的时候再进行替换 //商品存在,我们现在是进行信息的传递 ProductDetailVo productDetailVo =assembleProductDetailVo(product); return ServerResponse.createBySuccess(productDetailVo); }
我们知道现在是要获取商品的详细信息,那么我们可以使用不同的架构来完成,有两种架构可供选择:pojo -->vo对象(value object)和pojo -->bo(business object)--->vo(view object),考虑到技术的演变,我们这里还是使用vo等到后面升级的时候再进行替换。前面我们进行了商品信息是否存在的判断,现在是有商品,那么如何获取商品呢?
这里我们写了一个方法,用于获取商品信息(在ProductServiceImpl.java文件里面继续写入以下代码:):
private ProductDetailVo assembleProductDetailVo(Product product) { ProductDetailVo productDetailVo = new ProductDetailVo(); productDetailVo.setId(product.getId()); productDetailVo.setSubtitle(product.getSubtitle()); productDetailVo.setPrice(product.getPrice()); productDetailVo.setMainImage(product.getMainImage()); productDetailVo.setSubImages(product.getSubImages()); productDetailVo.setCategoryId(product.getCategoryId()); productDetailVo.setDetail(product.getDetail()); productDetailVo.setName(product.getName()); productDetailVo.setStatus(product.getStatus()); productDetailVo.setStock(product.getStock()); //imageHost:这个我们需要进行单独的配置,这样便于后面的维护 productDetailVo.setImageHost(PropertiesUtil.getProperty("ftp.server.http.prefix", "http://img.licheetools.top/")); //parentCategoryId Category category = categoryMapper.selectByPrimaryKey(product.getId()); if (category ==null) { productDetailVo.setParentCategoryId(0); //没有父节点就默认该节点为0 }else { productDetailVo.setParentCategoryId(category.getParentId()); //存在就赋值给它 } //createTime在mybatis里面都是毫秒数,不利于我们的展示,我们需要进行配置 productDetailVo.setCreateTime(DateTimeUtil.dateToStr(product.getCreateTime())); //updateTime在mybatis里面都是毫秒数,不利于我们的展示,我们需要进行配置 productDetailVo.setUpdateTime(DateTimeUtil.dateToStr(product.getUpdateTime())); return productDetailVo; }
既然我们使用了vo那么我们就要去vo包里面新建一个ProductDetailVo.java,在里面写入以下代码,这个文件里面就是定义一些你需要查询的商品字段:
package top.store.vo; import java.math.BigDecimal; public class ProductDetailVo { private Integer id; private Integer categoryId; private String name; private String subtitle; private String mainImage; private String subImages; private String detail; private BigDecimal price; private Integer stock; private Integer status; private String createTime; private String updateTime; private String imageHost; //这个是图片服务器的前缀,我们后面通过这个前缀和图片进行拼接从而形成url进行访问 private Integer parentCategoryId; public Integer getId() { return id; } public void setId(Integer id) { this.id = id; } public Integer getCategoryId() { return categoryId; } public void setCategoryId(Integer categoryId) { this.categoryId = categoryId; } public String getName() { return name; } public void setName(String name) { this.name = name; } public String getSubtitle() { return subtitle; } public void setSubtitle(String subtitle) { this.subtitle = subtitle; } public String getMainImage() { return mainImage; } public void setMainImage(String mainImage) { this.mainImage = mainImage; } public String getSubImages() { return subImages; } public void setSubImages(String subImages) { this.subImages = subImages; } public String getDetail() { return detail; } public void setDetail(String detail) { this.detail = detail; } public BigDecimal getPrice() { return price; } public void setPrice(BigDecimal price) { this.price = price; } public Integer getStock() { return stock; } public void setStock(Integer stock) { this.stock = stock; } public Integer getStatus() { return status; } public void setStatus(Integer status) { this.status = status; } public String getCreateTime() { return createTime; } public void setCreateTime(String createTime) { this.createTime = createTime; } public String getUpdateTime() { return updateTime; } public void setUpdateTime(String updateTime) { this.updateTime = updateTime; } public String getImageHost() { return imageHost; } public void setImageHost(String imageHost) { this.imageHost = imageHost; } public Integer getParentCategoryId() { return parentCategoryId; } public void setParentCategoryId(Integer parentCategoryId) { this.parentCategoryId = parentCategoryId; } }
里面我们有一个imageHost字段,它是图片服务器的前缀,我们后面通过这个前缀和图片进行拼接从而形成url进行访问。继续回到我们的ProductServiceImpl.java文件,不知道细心的你发现没有,有4个字段的获取我们是使用了特殊的方法。其实也正是因为这个原因,我们并没有直接从product对象里面直接获取信息,因为那样获取的信息有可能不是我们所需要的格式,所以我们这里就重新定义了一个ProductDetailVo类,它的实例对象都是来源于product对象但是又进行了更深层次的处理,因此它就是我们想要的。
那么这4个特殊字段的获取应该怎么操作呢?接下来一一为你介绍。
imageHost字段获取
前面说过因为imageHost是图片服务器的前缀,我们后面通过这个前缀和图片进行拼接从而形成url进行访问,所以肯定会涉及到一些服务器属性的配置,这样我们把与服务器属性相关的利用配置文件来处理,这样一旦服务器发送变动,你只需要修改一下配置文件即可,不需要进行很多代码的修改,无形中提高了代码的可维护性。
打开util包,在里面新建一个PropertiesUtil.java文件,里面写入以下代码:
package top.store.util; import org.apache.commons.lang.StringUtils; import org.slf4j.Logger; import org.slf4j.LoggerFactory; import java.io.IOException; import java.io.InputStreamReader; import java.util.Properties; public class PropertiesUtil { //定义日志 private static Logger logger = LoggerFactory.getLogger(PropertiesUtil.class); private static Properties properties; static { String fileName ="store.properties"; properties =new Properties(); try { properties.load(new InputStreamReader(PropertiesUtil.class.getClassLoader().getResourceAsStream(fileName),"UTF-8")); } catch (IOException e) { logger.info("配置文件读取异常",e); } } //定义方法用于从store.properties文件中读取信息 public static String getProperty(String key){ //可能我们写的property文件存在空格,需要去掉key包含的空格 String value =properties.getProperty(key.trim()); if(StringUtils.isBlank(value)){ //注意这里使用isBlank,就算是空格和制表符也是为空 return null; } return value.trim(); //有可能后面的值也存在空值 } //定义方法用于从store.properties文件中读取信息,添加默认参数 public static String getProperty(String key,String defaultValue){ //可能我们写的property文件存在空格,需要去掉key包含的空格 String value =properties.getProperty(key.trim()); if(StringUtils.isBlank(value)){ //注意这里使用isBlank,就算是空格和制表符也是为空 value= defaultValue; } return value.trim(); //有可能后面的值也存在空值 } }
我们这里利用的就是静态代码块,因为它只在类被加载时执行,而且只执行一次。这里我们重载了两个方法,目的就是适应不同的业务需求。同时为了能及时发现问题,我们定义了日志,用于相关信息的输出。
parentCategoryId字段获取
因为我们这里是通过商品的Id来获取其详细信息的,这样就可能会存在一个情况就是没有父节点,所以这个字段我们需要格外注意:
//parentCategoryId Category category = categoryMapper.selectByPrimaryKey(product.getId()); if (category ==null) { productDetailVo.setParentCategoryId(0); //没有父节点就默认该节点为0 }else { productDetailVo.setParentCategoryId(category.getParentId()); //存在就赋值给它 }
时间字段获取
在这里我们有两个关于时间的字段:createTime和updateTime,我们知道在mybatis里面时间单位都是毫秒数,这是不利于我们展示的,所以需要进行配置。我们可以自己定义一个专门用于处理时间的工具类。打开util包,在里面新建一个工具类DateTimeUtil,我们知道一般时间处理就两种格式:str->Date或者是Date->str。这里我们使用了joda-time这个专门用于处理时间的工具,具体的可以参考这里:Joda-Time的使用。DateTimeUtil文件写入以下信息:
package top.store.util; import org.apache.commons.lang3.StringUtils; import org.joda.time.DateTime; import org.joda.time.format.DateTimeFormat; import org.joda.time.format.DateTimeFormatter; import java.util.Date; public class DateTimeUtil { //我们使用joda-time //定义一下我们的日期格式 public static final String STANDARD_FORMAT = "yyyy-MM-dd HH:mm:ss"; //主要完成两种类型的转换 //str->Date //Date->str //str->Date,使用前面定义的默认的日期格式 public static Date strToDate(String dateTimeStr){ DateTimeFormatter dateTimeFormatter = DateTimeFormat.forPattern(STANDARD_FORMAT); DateTime dateTime = dateTimeFormatter.parseDateTime(dateTimeStr); return dateTime.toDate(); } //str->Date public static Date strToDate(String dateTimeStr,String formatStr){ DateTimeFormatter dateTimeFormatter = DateTimeFormat.forPattern(formatStr); DateTime dateTime = dateTimeFormatter.parseDateTime(dateTimeStr); return dateTime.toDate(); } //Date->str,使用前面定义的默认的日期格式 public static String dateToStr(Date date){ if(date == null){ return StringUtils.EMPTY; } DateTime dateTime = new DateTime(date); return dateTime.toString(STANDARD_FORMAT); } //Date->str public static String dateToStr(Date date,String formatStr){ if(date == null){ return StringUtils.EMPTY; } DateTime dateTime = new DateTime(date); return dateTime.toString(formatStr); } //测试上面方法有没有问题的方法 public static void main(String[] args) { System.out.println(DateTimeUtil.dateToStr(new Date(),"yyyy-MM-dd HH:mm:ss")); System.out.println(DateTimeUtil.strToDate("2008-08-08 20:08:08","yyyy-MM-dd HH:mm:ss")); } }
然后回到ProductServiceImpl.java文件,添加以下代码(实际上前面已经写过了):
//createTime在mybatis里面都是毫秒数,不利于我们的展示,我们需要进行配置 productDetailVo.setCreateTime(DateTimeUtil.dateToStr(product.getCreateTime())); //updateTime在mybatis里面都是毫秒数,不利于我们的展示,我们需要进行配置 productDetailVo.setUpdateTime(DateTimeUtil.dateToStr(product.getUpdateTime()));
最后打开IProductService.java文件,里面写入以下代码:
ServerResponse<ProductDetailVo> manageGetDetail(Integer productId); //后台管理员获取商品的详情
这样我们本篇,关于后台商品详细信息获取功能的介绍就到此为止了,感谢你的赏阅!