【问题标题】:keycloak CORS Headers in 401401中的keycloak CORS标头
【发布时间】:2017-12-17 22:18:01
【问题描述】:

我有两个 keyclock 客户端,

  • Angular 4:使用访问类型凭据身份验证
  • 一个 JAX RS 应用程序(将是资源服务器):使用 bearer-only 身份验证!在这个客户端我们激活CORS,如下json所示。

{
  "realm": "demo-realm",
  "bearer-only": true,
  "auth-server-url": "http://demo-keycloack-server:8080/auth",
  "ssl-required": "external",
  "resource": "demo-server",
  "enable-cors": true
}

问题是 JAX-RS 应用程序的状态代码为 401(未授权)的 HTTP 响应没有将所需的 CORS 标头带到 javascript 客户端!

HTTP 状态为 401 时如何添加相应的 CORS Header?

【问题讨论】:

  • 你是如何发送令牌休息的?您通过哪种方法保护其余部分?
  • 下面这个答案可以帮助您解决问题:stackoverflow.com/questions/45921049/…
  • 我建议您按照上面/下面的建议,通过破解您的 keycloak JBOSS 服务器配置来启用 CORS。这很糟糕。
  • 当承载者/用户访问令牌的 iss 字段上标记的主机名与用于发布的 URL 中的主机名大小写不同(即小写与大写)时,我们不断收到 HTTP 401 状态代码响应对 keycloak 令牌端点的 HTTP 请求。

标签: keycloak


【解决方案1】:

(注意:此行为已在 keycloak tomcat Valve 6.0.1 中重现)

[已更新以包含解决方案]

经过大量实验,问题似乎是这样的:

Keycloak 向 CORS 预检 (OPTIONS) 请求发回 401 响应。无论您向预检添加什么标头,错误状态代码(即除了 200 系列响应之外的任何内容)都将被视为 CORS 失败。

解决办法:

1) 扩展 Keycloak-valve 的 CORS 支持以响应 204 到 OPTIONS,可能通过添加如下所示的代码。如果你想检查一下,弄清楚它迷宫般的架构,然后提交 PR,那就太好了。否则,

2) 禁用 keycloak 的 CORS 支持并在您的配置中添加一个 CORS 阀。

我通过设置“enable_cors: false”(或简单地删除条目)禁用了仅承载服务器中的 CORS 支持。然后我创建了一个小的 CORS 支持阀来发送 Access-Control-Allow- 标头。因为这是一个不记名令牌系统,所以允许“*”是相当安全的。 (此外,如果您允许来源“*”,现代浏览器将不会发送凭据。)

整个 CORS 支持阀大致如下:

public void invoke(Request rqst, Response rsp) throws ...
{
    HttpServletResponse response = rsp.getResponse();
    HttpServletRequest request = rqst.getRequest();

    if (null != request.getHeader("origin")) {
        response.setHeader("Access-Control-Allow-Origin", "*");

        String method = request.getMethod();
        if (method.equalsIgnoreCase("options")) { // preflight?
            rsp.reset();
            response.setHeader("Access-Control-Allow-Methods", "POST,GET,OPTIONS");
            response.setHeader("Access-Control-Max-Age", "10");
            response.setHeader("Access-Control-Allow-Headers", "Origin,Accept,Content-Type,Access-Control-Request-Method,Access-Control-Request-Headers,Your-Header-Here");
            rsp.setStatus(204);
            return;
        }
    }

    getNext().invoke(rqst, rsp);
}

但您可能想为您的应用程序编写一个功能更全面的阀门。

添加后,CORS preflight 返回 204,然后请求者正确接收到 401/403 响应。

分析

Keycloak 阀仅在与 Keycloak 身份验证服务器签入后发送 CORS 标头。这意味着承载令牌服务器端应用程序的任何联网、配置或令牌验证失败都会导致没有任何 Access-Control-Allow 标头的错误响应,因此没有任何错误详细信息可用。

Keycloak tomcat 阀确实为几乎所有故障提供详细的故障信息。对于 401 错误,它位于 WWW-Authenticate 响应标头中,与大多数标头一样,在 CORS 失败的情况下禁止使用该标头。但是,它会将此 401 错误返回给 OPTIONS 请求,即 CORS 预检,它将其隐藏在客户端代码中。由于任何配置错误(auth-server-url 的端口错误,或领域拼写错误)也会触发 CORS 失败,因此您的应用永远不会看到标头。

该错误在某些浏览器的网络调试窗格中可见,但对 Javascript 不可见。

【讨论】:

    猜你喜欢
    • 2020-03-16
    • 2016-07-04
    • 1970-01-01
    • 2014-08-11
    • 2015-08-10
    • 2022-11-13
    • 2019-04-08
    • 2013-04-05
    • 2017-09-26
    相关资源
    最近更新 更多