springboot使用拦截器返回格式化json给前端

背景:在拦截器中返回格式化json给前端

前提:

网上找了很多例子,都没有靠谱的解决方法,自己总结了这个文章。

1、 Web配置文件中注入拦截器

package com.example.jwtdemo.config;

import org.springframework.stereotype.Component;
import org.springframework.web.servlet.config.annotation.InterceptorRegistry;
import org.springframework.web.servlet.config.annotation.WebMvcConfigurer;

/**
 * Web配置文件中注入拦截器
 *     Spring Boot1.0的时候可以通过继承WebMvcConfigurerAdapter完成,但在Spring Boot2.0
 *     中这个适配类是被弃用了的,所以我们可以直接实现WebMvcConfigurer来完成拦截器的添加
 *
 * @author 任珏朋
 * @version V1.0.0 2023/6/2
 * @since V100R001
 */
@Component
public class InterceptorConfig implements WebMvcConfigurer {

    /**
     * 在实现WebMvcConfigurer之后可以选择你要重写的方法,这里重写addInterceptors这个方法来添加自定义的拦截器。
     *     addInterceptor用于添加你自定义的拦截器实例
     *     addPathPatterns用于添加要拦截的url,可以写多个。
     *     excludePathPatterns用于添加不需要拦截的url,可以写多个。
     */
    @Override
    public void addInterceptors(InterceptorRegistry registry) {
        registry.addInterceptor(new JWTInterceptor()).
                excludePathPatterns("/api/user/**") // 直接放行通过的rl
                .addPathPatterns("/**"); // 要拦截的url
    }
}



2、定义一个拦截器,返回格式化的json给前端

要想返回格式化的json给前端,下面代码中的2个注意点是关键!!!
我这边是写的jwt例子,每次收到前端请求时,都先从请求头中的Authorization字段中取出JWT字符串并进行验证。

代码中DecodedJWT不影响测试,小伙伴们不用关心,本文主要关注返回json如何格式化。

package com.example.jwtdemo.config;

import com.alibaba.fastjson.JSON;
import com.auth0.jwt.exceptions.AlgorithmMismatchException;
import com.auth0.jwt.exceptions.SignatureVerificationException;
import com.auth0.jwt.exceptions.TokenExpiredException;
import com.auth0.jwt.interfaces.DecodedJWT;
import com.example.jwtdemo.jwtUtils.JWTUtils;
import org.springframework.web.servlet.HandlerInterceptor;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.io.PrintWriter;
import java.util.HashMap;
import java.util.Map;

/**
 * 定义一个拦截器,每次收到前端请求时,都先从请求头中的Authorization字段中取出JWT字符串并进行验证
 *
 * 自定义拦截器HandlerInterceptor会实现三个方法
 *
 * preHandle:调用Controller某个方法之前
 * postHandle:Controller之后调用,视图渲染之前,如果控制器Controller出现了异常,则不会执行此方法
 * afterCompletion:不管有没有异常,这个afterCompletion都会被调用,用于资源清理
 *
 * @author 任珏朋
 * @version V1.0.0 2023/6/2
 * @since V100R001
 */
public class JWTInterceptor implements HandlerInterceptor {

    /**
     * 预处理回调方法,实现处理器预处理
     * 返回值:true表示继续流程;false表示流程中断,不会继续调用其他的拦截器或者处理器
     */
    @Override
    public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
        // 从http请求头key为Authorization中取出JWT
        String JWT = request.getHeader("Authorization");
        try {
            // 1.校验JWT字符串
            DecodedJWT decodedJWT = JWTUtils.decode(JWT);
            // 2.如果用到Redis存用户信息的话,那么取出JWT字符串载荷中的随机token,从Redis中获取用户信息
            // ...
            return true;
        }catch (SignatureVerificationException e){
            returnJson(response,"无效签名");
            e.printStackTrace();
        }catch (TokenExpiredException e){
            returnJson(response,"token已经过期");
            e.printStackTrace();
        }catch (AlgorithmMismatchException e){
            returnJson(response,"算法不一致");
            e.printStackTrace();
        }catch (Exception e){
            returnJson(response,"token无效");
            e.printStackTrace();
        }
        return false;
    }

    /**
     * 返回格式化后的json到前端页面
     *
     * @param response
     * @param message
     * @throws Exception
     */
    private void returnJson(HttpServletResponse response, String message) throws Exception{
        PrintWriter writer = null;
         // 注意点1:这边返回配置为josn格式
        response.setContentType("application/json;charset=UTF-8");
        try {
            Map<String, Object> result = new HashMap<>();
            result.put("state", "false");
            result.put("msg", message);
            writer = response.getWriter();
             // 注意点2,这样要用fastjson转换一下后,返回的前端才是格式化后的json格式
            writer.print(JSON.toJSONString(result));
        } catch (IOException e) {
        } finally {
            if (writer != null)
                writer.close();
        }
    }

}




3、定义一个controller,用来测试

package com.example.jwtdemo.controller;

import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RestController;

/**
 * @author 任珏朋
 * @version V1.0.0 2023/5/23
 * @since V100R001
 */
@RestController
public class TestController {


    /**
     * 模拟一个测试接口
     *
     * @return
     */
    @GetMapping("/testF1")
    public String test() {
        String r = "成功进入方法了";
        System.out.println(r);
        return r;
    }

}

4、postman中调用controller接口进行测试,当Authorization随便输入,请求接口可以看到返回的json是格式化的了,而不是就一行连在一起的。(如{“msg”:“token已经过期”,“state”:“false”})

springboot使用拦截器返回格式化json给前端_第1张图片

你可能感兴趣的:(spring,boot,前端,json,mvc)