预检响应具有无效的 HTTP 状态代码:401 角度

Posted

技术标签:

【中文标题】预检响应具有无效的 HTTP 状态代码:401 角度【英文标题】:Response for preflight has invalid HTTP status code: 401 angular 【发布时间】:2017-07-02 11:22:58 【问题描述】:

使用 Angular 和 Spring Boot,我们尝试向我们的服务添加身份验证,但由于某种原因,我们无法“打开”并从我们知道有效的 url 获取数据

角度:

this.getMismatches = function () 
    return $http(
            "async": true,
            "crossDomain": true,
            "url": GLOBALS.mismatchUrl,
            "method": "GET",
            "headers": 
                "authorization": "Basic YWRtaW46USNROawdNmY3UWhxQDlQA1VoKzU="
        
    );

(目前登录令牌是硬编码用于测试目的)

休息服务:

@CrossOrigin(origins = "*")
@RequestMapping("/api/mismatch")
public List<Mismatch> home() 
    return service.getAll();

CrossOrigin = * 应该解决 CORS 问题,但是这个失败的 URL 调用真的很奇怪。

我们尝试过的其他事情:

'Access-Control-Allow-Methods', 'GET, POST, OPTIONS'
'Access-Control-Allow-Origin', '*'
'Content-Type', json plaintext jsonp etc

App.js:
    $httpProvider.defaults.headers.common = ;
    $httpProvider.defaults.headers.post = ;
    $httpProvider.defaults.headers.put = ;
    $httpProvider.defaults.headers.patch = ;

【问题讨论】:

GLOBALS.mismatchUrl 设置为什么?我想它根本没有说“无效的 URL”...... 我的错,发布了错误的错误信息。 你能得到邮递员的回复吗? 是的,这很奇怪。 你能给'GLOBALS.mismatchUrl'的值吗? 【参考方案1】:

您在您的 cmets 中提到,通过使用邮递员,您可以获得预期的响应。这是一个很好的起点。我怀疑通过从终端使用 curl 命令curl -i -X URL 也会返回正确的响应。

如果邮递员工作正常,你必须知道,在发出请求之前,angular 会发送另一个请求,称为 pre-flight 请求,它会对位于服务器端。

此请求是 OPTIONS 类型的请求。

首先,您必须确保您的 dispatcherServlet 接受 OPTIONS 请求。您可以通过在*.properties 配置文件中指定它来实现这一点,例如:

spring.mvc.dispatch-options-request=true

或者通过配置web.xml

<servlet>
    <!--content eluded for clarity-->
    <init-param>
        <param-name>dispatchOptionsRequest</param-name>
        <param-value>true</param-value>
    </init-param>
</servlet>

将其配置为接受 OPTIONS 请求后,创建Filter.java 并配置 CORS 过滤器。

您可以通过以下示例进行指导:

public class CorsFilter implements Filter

@Override
public void doFilter(ServletRequest request, ServletResponse response,
                     FilterChain filterChain) throws IOException, ServletException 

    if(response instanceof HttpServletResponse)
        HttpServletResponse alteredResponse = ((HttpServletResponse)response);
        addCorsHeader(alteredResponse);
    

    filterChain.doFilter(request, response);


private void addCorsHeader(HttpServletResponse response)
    //TODO: externalize the Allow-Origin
    response.addHeader("Access-Control-Allow-Origin", "*");
    response.addHeader("Access-Control-Allow-Methods", "POST, GET, OPTIONS, PUT, DELETE, HEAD");
    response.addHeader("Access-Control-Allow-Headers", "Authorization, X-PINGOTHER, Origin, X-Requested-With, Content-Type, Accept");
    response.addHeader("Access-Control-Max-Age", "1728000");


@Override
public void destroy() 

@Override
public void init(FilterConfig filterConfig)throws ServletException

最后,不要忘记在web.xml 中添加此过滤器以及以下init-params。

<filter>
    <filter-name>cors-filter</filter-name>
    <filter-class>ai.surge.usrmngmtservice.util.cors.CorsFilter</filter-class>
    <init-param>
        <param-name>cors.allowed.origins</param-name>
        <param-value>*</param-value>
    </init-param>
    <init-param>
        <param-name>cors.allowed.methods</param-name>
        <param-value>GET,POST,OPTIONS,PUT</param-value>
    </init-param>
    <init-param>
        <param-name>cors.exposed.headers</param-name>
        <param-value>Authorization,Access-Control-Allow-Origin,Access-Control-Allow-Credentials</param-value>
    </init-param>
    <!--<init-param>-->
        <!--<param-name>cors.preflight.maxage</param-name>-->
        <!--<param-value>1800</param-value>-->
    <!--</init-param>-->
</filter>

你现在应该准备好了。

【讨论】:

以上是关于预检响应具有无效的 HTTP 状态代码:401 角度的主要内容,如果未能解决你的问题,请参考以下文章

预检响应具有无效的 HTTP 状态代码 401 - Spring

Angular 2 - 预检响应具有无效的 HTTP 状态代码 401

通过基本身份验证访问 REST 的 Angular2 抛出“预检响应具有无效的 HTTP 状态代码 401”

无法加载 http://localhost:9999/auth-service/oauth/token:预检响应具有无效的 HTTP 状态代码 401

Yii2 和 reactjs CORS 过滤器给出错误:预检响应具有无效的 HTTP 状态代码 401

预检响应具有无效的 HTTP 状态代码 404”