0
点赞
收藏
分享

微信扫一扫

springcloud Feign调用拦截器(统一处理拷贝请求头实现透传信息、内部调用鉴权、打印feign调用)

覃榜言 2024-06-03 阅读 1

springcloud Feign调用拦截器(统一处理拷贝请求头实现透传信息、内部调用鉴权、打印feign调用日志)

实现接口Feign.RequestInterceptor

实现接口 feign.RequestInterceptor 并注入到IOC容器即可生效
在这里插入图片描述

示范代码如下

  1. 拷贝请求头,将原请求信息透传下去给被调用的feign服务,部分头不拷贝,例如content-length
  2. 内部调用鉴权标记,在发起feign调用时加上标记(每天一个token,64位随机字符,在redis记录了今天的和昨天的,都有效),让内部调用时有权限调用被调服务
  3. 打印feign调用目标的日志

/**
 * @author humorchen
 * date: 2024/5/27
 * description: feign 请求拦截器
 **/
@Slf4j
public class FeignInterceptor implements RequestInterceptor {


    /**
     * 跳过某些 header
     * 比对时会忽略大小写
     */
    private static final Set<String> SKIP_HEADER_NAMES = new HashSet<>(Arrays.asList("transfer-encoding", "content-length", "accept", "accept-encoding", "connection"));

    static {
        // 转换为小写,避免大小写不一致
        HashSet<String> lowCaseSet = new HashSet<>(SKIP_HEADER_NAMES.size());
        SKIP_HEADER_NAMES.forEach(name -> lowCaseSet.add(name.toLowerCase()));
        SKIP_HEADER_NAMES.clear();
        SKIP_HEADER_NAMES.addAll(lowCaseSet);
    }

    /**
     * Called for every request. Add data using methods on the supplied {@link RequestTemplate}.
     *
     * @param template
     */
    @Override
    public void apply(RequestTemplate template) {
        ServletRequestAttributes requestAttributes = (ServletRequestAttributes) RequestContextHolder.getRequestAttributes();
        // 拷贝请求头信息,透传信息
        if (requestAttributes != null) {
            HttpServletRequest request = requestAttributes.getRequest();
            Enumeration<String> headerNames = request.getHeaderNames();
            if (headerNames != null) {
                while (headerNames.hasMoreElements()) {
                    // 跳过某些 header
                    String name = headerNames.nextElement();
                    if (SKIP_HEADER_NAMES.contains(name.toLowerCase())) {
                        continue;
                    }
                    String values = request.getHeader(name);
                    template.header(name, values);
                }
            }
        }
        // 内部调用鉴权标记
        template.header(SaSameUtil.SAME_TOKEN, SaSameUtil.getToken());
        // 测试环境打印
        log.debug("【新版权限日志】FeignInterceptor 发起Feign调用({}),请求头已拷贝,same-token已颁发。", template.url());
    }
}
举报

相关推荐

0 条评论