天天看点

汽车后端框架搭建(下)

后端框架的搭建临近尾声,在项目搭建的一些工作做了细化,配置了一个全局异常处理器,用来捕捉所有程序发生的异常,数据校验器用来对前端传来的数据做一些检查工作,避免脏数据入库,还要一个常量接口,主要用来保存我们用到的一些常量.还有一个就是自定义业务异常类,用来细分到底是哪个业务出了问题,这样找起来也好找.

1.全局异常处理器(GlobeExceptionHandler)

只要出现异常,就会走全局异常处理器

当程序抛出异常时,对异常进行拦截处理,根据异常的对象的信息,将这些信息转化为JSON数据返回给客户端

package com.zw.common.handler;

/**
 * 只要出现异常,就会走全局异常处理器
 * 当程序抛出异常时,对异常进行拦截处理,根据异常的对象的信息,将这些信息转化为JSON数据返回给客户端
 */

import com.zw.common.CodeMsg;
import com.zw.common.Result;
import com.zw.common.exception.BussiException;
import org.springframework.web.bind.annotation.ControllerAdvice;
import org.springframework.web.bind.annotation.ExceptionHandler;
import org.springframework.web.bind.annotation.ResponseBody;

/**
 * @ClassName:GlobeExceptionHandler
 * @Description: 全局异常处理器
 * @Author: KevinZeng
 * @Date 2020/1/8 下午 9:44
 */
@ControllerAdvice
public class GlobeExceptionHandler {
    /**
     * 处理异常
     * @param exception 发生异常的对象
     * @return
     */
    @ExceptionHandler
    @ResponseBody
    public Result bussiExceptionHandler(Exception exception){
        System.err.println(exception.getMessage());
        //判断抛出的异常是否是程序员自定义的业务异常
        if(exception instanceof BussiException){
            BussiException bussiException = (BussiException) exception;
            Result rs = new Result();
            rs.setCode(bussiException.getCode());
            rs.setMsg(bussiException.getMsg());

            System.out.println(rs);
            return rs;
        }
        //是程序报错
        return new Result(CodeMsg.ERROR);
    }
}

           

2.自定义业务异常类

package com.zw.common.exception;

/**
 * 当程序出现数据异常时就抛出异常信息
 * 两种情况:
 * 1.当数据校验不通过时,抛出异常信息
 * 2.当数据操作出现异常时,抛出异常信息,也是为了数据回滚
 */

/**
 * @ClassName:BussiException
 * @Description: 自定义业务异常类:
 * @Author: KevinZeng
 * @Date 2020/1/8 下午 9:39
 */
public class BussiException extends RuntimeException{
    /**
     * 异常编码
     */
    private  Integer code;
    /**
     * 异常信息
     */
    private String msg;

    public BussiException() {
    }
    public BussiException(Integer code, String msg) {
        super(code+":"+msg);
        this.code = code;
        this.msg = msg;
    }
//getters and setters 略
}

           

3.数据校验器

package com.zw.common.validator;
/**
 * 用于校验请求的数据
 * 请求的参数,有各种类型,各种类别,有一样存在公共点,例如:
 * 请求的参数不能为空
 * 请求的参数 最大 最小值
 * 请求的数据的字符串长度
 * 用户名:不能为空 长度
 */

import java.util.Set;

import com.zw.common.Constant;
import com.zw.common.exception.BussiException;

import javax.validation.ConstraintViolation;
import javax.validation.Validation;
import javax.validation.Validator;

/**
 * @ClassName:Validator
 * @Description: 数据校验器
 * @Author: KevinZeng
 * @Date 2020/1/9 下午 6:00
 */
public class ValidatorUtil {
    /**
     * 数据校验器
     */
    static final Validator validator;

    static {
        //获取一个数据校验器
        validator = Validation.buildDefaultValidatorFactory().getValidator();
    }

    public static void validator(Object form) {
        Set<ConstraintViolation<Object>> validate = validator.validate(form);
        for (ConstraintViolation<Object> constraintValidation : validate) {
            //校验不通过的信息
            String message = constraintValidation.getMessage();
            //校验不通过  抛出异常
            throw new BussiException(Constant.FORM_DATA_CHECK_ERROR_CODE, message);
        }
    }
}
           

4.常量接口

package com.zw.common;


/**
 * 常量接口
 */
public interface Constant {
    /**
     * 表单数据校验错误码
     */
    Integer FORM_DATA_CHECK_ERROR_CODE = 4001001;

}
           

5.对form类进行修改不用继承了,直接使用里面的属性就够了,在form里面可以进行数据的一些约束.

package com.zw.sys.form;
/**
 * 比如insert操作,以前的数据都是将前端传来的数据封装成user对象,现在用form包下的对象去接收,
 * 于是我们的SysUsersForm去继承SysUsers,
 */


import org.hibernate.validator.constraints.Length;

import javax.validation.constraints.NotBlank;

/**
 * @ClassName:SysUsersForm
 * @Description: 用于接收更新user表的数据的类
 * @Author: KevinZeng
 * @Date 2020/1/8 下午 11:01
 */
public class SysUsersForm {
    /**
     * 用户编号
     */
    private Integer id;

    /**
     * 登录名
     */
    @NotBlank(message = "用户登录名不能为空")
    @Length(min = 6, max = 15, message = "用户登录名只能为6-15个字符")
    private String loginName;

    /**
     * 登录密码
     */
    private String password;

    /**
     * 身份证号码
     */
    private String idCard;

    /**
     * 真实名称
     */
    private String realName;

    /**
     * 性别 1男 2女
     */
    private Integer sex;

    /**
     * 地址
     */
    private String address;

    /**
     * 电话
     */
    private String phone;

    /**
     * 用户头像
     */
    private String img;

    public Integer getId() {
        return id;
    }

    public void setId(Integer id) {
        this.id = id;
    }

    public String getLoginName() {
        return loginName;
    }

    public void setLoginName(String loginName) {
        this.loginName = loginName;
    }

    public String getPassword() {
        return password;
    }

    public void setPassword(String password) {
        this.password = password;
    }

    public String getIdCard() {
        return idCard;
    }

    public void setIdCard(String idCard) {
        this.idCard = idCard;
    }

    public String getRealName() {
        return realName;
    }

    public void setRealName(String realName) {
        this.realName = realName;
    }

    public Integer getSex() {
        return sex;
    }

    public void setSex(Integer sex) {
        this.sex = sex;
    }

    public String getAddress() {
        return address;
    }

    public void setAddress(String address) {
        this.address = address;
    }

    public String getPhone() {
        return phone;
    }

    public void setPhone(String phone) {
        this.phone = phone;
    }

    public String getImg() {
        return img;
    }

    public void setImg(String img) {
        this.img = img;
    }
}
           

5.我出现的问题

​ 在编写的过程中遇到一个问题,就是不能将null数据转化为json数据,输出到页面上,使用postman工具也没有成功.

第一次出现这个问题

结果是这样的

{
    "code": 1001,
    "msg":"程序员进ICU了"
}
           

正常来说,是应该要有

"data:null",

刚开始没有注意问题的所在,于是到处调试,

后来我想到将msg设置为null还会有吗?

结果是这样子的,

{
    "code": 1001
}
           

看来的确value为null的键值对,确实在后端传送到前端时被过滤到了,

于是我到处去网上翻贴,搜索返回json数据,属性值为null或空被省略的问题。

解决了,真的解决了,解决方案有很多,我的原因是包到导入问题,后来导入jack_json的相关jar包就好了,在其中也了解到了fastjson可以在springmvc.xml配置文件中配置json转换器.

6.系统流程

分析:

客户端在通过url访问服务器返回的页面之前,首先有一个拦截器,比如登录拦截器,登录拦截器如何实现以后在写,不难,拦截过后,会走controller层处理前端传过来的数据,这个数据应该是form对象,首先我们在controller层会进行一个数据的校验,这里主要就是数据的规范性,如果不合法,我们抛出异常,让异常处理器去处理,然后将经过处理的异常信息返回给客户端,如果没有发生异常,controller层的crud操作的数据传到service层,这里面也有一些验证的过程,不细说了,也是和controller层的一些校验道理差不多,只不过数据校验的可能侧重于数据的合法性(比如不能有相同的手机号等),之后就是service将CRUD操作的数据传到mapper层,由mapper层对数据库进行增删改查等操作.

汽车后端框架搭建(下)