Spring boot zuul错误重定向请求

Posted

技术标签:

【中文标题】Spring boot zuul错误重定向请求【英文标题】:Spring boot zuul wrong redirection of request 【发布时间】:2020-03-18 12:53:41 【问题描述】:

我正在开发一个 API 网关来将请求重定向到某个微服务。 这是 application.properties 文件的一部分:

#     _____                                       _____.__
#    /  _  \ ______ ______     ____  ____   _____/ ____\__| ____
#   /  /_\  \\____ \\____ \  _/ ___\/  _ \ /    \   __\|  |/ ___\
#  /    |    \  |_> >  |_> > \  \__(  <_> )   |  \  |  |  / /_/  >
#  \____|__  /   __/|   __/   \___  >____/|___|  /__|  |__\___  /
#          \/|__|   |__|          \/           \/        /_____/

server.port=8088
server.servlet.context-path=/PetApp

#  __________           .__    _________                _____.__
#  \____    /__ __ __ __|  |   \_   ___ \  ____   _____/ ____\__| ____
#    /     /|  |  \  |  \  |   /    \  \/ /  _ \ /    \   __\|  |/ ___\
#   /     /_|  |  /  |  /  |__ \     \___(  <_> )   |  \  |  |  / /_/  >
#  /_______ \____/|____/|____/  \______  /\____/|___|  /__|  |__\___  /
#          \/                          \/            \/        /_____/

#Routes for Auth
zuul.routes.tokenGenerator.path=/auth/login
zuul.routes.tokenGenerator.url=http://localhost:8086/PetApp_Auth/auth/generateToken
zuul.routes.tokenGenerator.stripPrefix=false

我正在尝试将请求从 API 网关 (http://localhost:8080/PetApp/auth/login) 重定向到在 (http://localhost:8086/PetApp_Auth/auth/generateToken) 中运行的服务 我已经通过邮递员将请求直接发送到微服务,并且效果很好。

重要提示:我没有添加任何授权标头,因为此端点没有被证券化(而且它工作得很好),但我的身份验证微服务中的其余 API 被证券化了

但是当我尝试通过 API 网关发送请求时,我得到以下信息:

可以看出,请求被重定向到正确的微服务(身份验证服务)而不是正确的 URL,因为我对正在显示的其余端点和 URL 有一个例外。

我也尝试将之前生成的授权令牌放入标头中发送,但我得到相同的未授权

我做错了什么?

【问题讨论】:

为什么不使用 nginx 或 varnish 来实现这个目的?您无需任何编码即可设置平衡、ESI 等。您正在做的是复制现有软件的功能,同时在系统中创建额外的引导项。如果您的 API 网关除了转发请求之外还做了一些额外的事情,那么只需使其成为您的微服务军队的一部分,它位于反向代理后面,负责平衡和路由工作。 【参考方案1】:

也许您需要在 zuul 或 auth 微服务中禁用 Spring 安全性。只需删除 spring 安全依赖项,确保令牌从 zuul 传递到 auth...

【讨论】:

那不是问题。我已经解决了,但谢谢!【参考方案2】:

我已经通过添加过滤器来解决它。 Zuul 像服务服务定义的 URL + PATH 一样构建完整的 URL,所以我实现了一个删除路径的过滤器,现在请求在其他微服务中完美接收。 无论如何,我计划将端点定义更改为具有与微服务中定义的端点路径相同的端点路径,因为对于可变路径,我认为不可能解决这个问题。 我还将检查是否使用 @Maxim Sagaydachny 建议的其他解决方案,如 nginx 或 varnish

@Component
public class PathConfigFilter extends ZuulFilter 

    @Autowired
    private ZuulProperties zuulProperties;

    @Override
    public String filterType() 
        return FilterConstants.PRE_TYPE;
    

    @Override
    public int filterOrder() 
        return FilterConstants.PRE_DECORATION_FILTER_ORDER + 1;
    

    @Override
    public boolean shouldFilter() 
        return RequestContext.getCurrentContext().getFilterExecutionSummary().toString()
            .contains( "PreDecorationFilter[SUCCESS]" );
    

    @Override
    public Object run() 

        RequestContext context = RequestContext.getCurrentContext();

        String originalRequestPath = (String) context.get(FilterConstants.REQUEST_URI_KEY);

        //PathVariable change
        URL routeHost = (URL) context.get( "routeHost");
        String modifiedPathVariable = processPathVariableRoutes( routeHost.getPath(), originalRequestPath );
        if(modifiedPathVariable != null)
            try 
                URL newUrl = new URL(routeHost,modifiedPathVariable);
                context.put("routeHost", newUrl);
             catch (MalformedURLException e) 
                throw new ApiGatewayException( ApiGatewayErrorCodes.PATH_VARIABLE_ERROR );
            
        

        //Delete the path because the full path is defined in properties
        context.put(FilterConstants.REQUEST_URI_KEY, "");

        return null;
    

    private String processPathVariableRoutes(String routeHost, String requestPath)

        if(!routeHost.contains( "*" ))
            return null;
        

        ArrayList<String> splitedRoute = new ArrayList<>(Arrays.asList(routeHost.split( "/" )));
        splitedRoute.remove( 0 );
        String context = "/" + splitedRoute.get( 0 );
        String realPath = context + requestPath;

        return realPath;
    

非常感谢。

【讨论】:

以上是关于Spring boot zuul错误重定向请求的主要内容,如果未能解决你的问题,请参考以下文章

Zuul 代理和 Spring OAuth 重定向问题

Angular Spring Boot:重定向错误:预检响应中的 Access-Control-Allow-Headers 不允许请求标头字段 Content-Type

登录后 Spring Boot 重定向到请求的 URL

在 Zuul 代理后面时出现 Spring 重定向 url 问题

Linux 第三天 重定负管道符环境变量

在 Spring Boot 中将未知请求重定向到 index.html