springcloud版本:Finchley SR2
1、引入依赖
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-netflix-eureka-client</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-netflix-zuul</artifactId>
</dependency>
2、zuul配置
zuul:
routes:
app-user:
path: /user/**
serviceId: app-user
3、过滤器
@Component
public class WebFilter extends ZuulFilter {
@Override
public String filterType() {
return "pre";
}
@Override
public int filterOrder() {
return 0;
}
@Override
public boolean shouldFilter() {
return true;
}
@Override
public Object run() throws ZuulException {
System.out.println("zuul过滤器...");
//向header中添加鉴权令牌
RequestContext requestContext = RequestContext.getCurrentContext();
//获取header
HttpServletRequest request = requestContext.getRequest();
String authorization = request.getHeader("Authorization");
if(authorization != null) {
System.out.println("authorization: " + authorization);
requestContext.addZuulRequestHeader("Authorization", authorization);
}
return null;
}
}
4、在app-user服务的controller里面测试能否获取到
@Autowired
private HttpServletRequest request;
/**
* 查询全部数据
* @return
*/
@RequestMapping(method= RequestMethod.GET)
public Result findAll(){
String header = request.getHeader("Authorization");
System.out.println("authHeader: " + header);
return new Result(true,StatusCode.OK,"查询成功",userService.findAll());
}
5、结果
1)、在过滤器里面能拿到,并且打印有值;
2)、在controller里面测试获取不到,打印为null。
PS:
不知道为什么在过滤器里这个addZuulRequestHeader没起作用,折腾半天没找原因,甚至查找了一些博客,写法都一样的,就那么几步,有哪位大佬遇到过这问题的,可以给点思路吗……┭┮﹏┭┮
经过无数次测试,终于找到问题了,罪魁祸首就是Authorization这个单词,不论大写小写,都获取不到,但是改成Authorization1就能获取到,我直接换成了其它的单词如token,就OK了,还专门试了试各种单词以及大小写,发现就是Authorization这个单词的问题,不知道是敏感词汇还是怎么的,zuul转发时子服务就是拿不到。
顺便查看了下zuul过滤器里面自带的requestContext.addZuulRequestHeader("xx")的源码,里面是这样写的:
public void addZuulRequestHeader(String name, String value) {
this.getZuulRequestHeaders().put(name.toLowerCase(), value);
}
是会自己转成小写的,所以保险起见以后header命名最好都是小写,以免引起未知的问题。
敏感头信息Authorization,Cookie,Set-Cookie默认是不转发的,也就获取不到
在配置文件里设置zuul.sensitiveHeaders为空,就可以获取到了
特意登录感谢,搞了我一晚上
谢谢找了好久,终于找到了
public Object run() throws ZuulException {//表示我们具体的过滤执行操作
RequestContext currentRequestContext = RequestContext.getCurrentContext();//获取当前请求的上下文
String auth = "admin:123456"; // 认证的原始信息
byte[] encodedAuth = Base64.getEncoder()
.encode(auth.getBytes(Charset.forName("US-ASCII"))); // 进行一个加密的处理
// 在进行授权的头信息内容配置的时候加密的信息一定要与“Basic”之间有一个空格
String authHeader = "Basic " + new String(encodedAuth);
currentRequestContext.addZuulRequestHeader("Authorization", authHeader);
return null;
}
#例如:zuul.sensitiveHeaders=Cookie,Set-Cookie
#如果客户端在发请求是带了Cookie,那么Cookie不会传递给下游服务。
#默认:zuul.sensitiveHeaders=
#什么都不设置代表不过滤任何信息,但 zuul.sensitiveHeaders= 一定要附上 。
zuul.sensitiveHeaders=
感谢,昨天困扰了一整天,现在解决了
不是啊。如果添加了 zuul.sensitiveHeaders=
那么所有请求头的信息都不会被过滤,直接可以转发。
那我还要这个addZuulRequestHeader()方法干嘛,不用它也直接转发了。
我还是觉得默认情况下zuul.sensitiveHeaders中有Authorization,默认不转发。
在zuulfilter中添加了addZuulRequestHeader(),应该会把这个默认不转发的东西,转发出去。不然要这个add方法干啥。???