【问题标题】:SockJS not passing credential information when on a different domain(CORS)在不同的域(CORS)上时,SockJS 不传递凭据信息
【发布时间】:2014-12-17 12:27:53
【问题描述】:

我们有一个使用 spring 4 的 websocket 服务器端实现。它已被配置为使用 spring 安全性进行 auth/authz。在客户端,我们使用 sockJS,当客户端与服务器在同一个域时,它可以完美运行。

通过这种方式调用 websocket……

socket = new SockJS("http://guest:guest@mydomain.org/MyWebSocketApp/tracker")

这最终会调用http://guest:guest@myinterestingdomain.org/MyWebSocketApp/tracker/info 来决定要使用的传输。这一切都很好。

但是,当使用来自不同域的客户端时,我看到凭据被删除了。所以,当这个客户端在不同的域上时,我看到正在进行的调用是: http://myinterestingdomain.com/MyWebSocketApp/tracker/info。我没有看到正在传递的凭据。因此,我收到 401 错误(未经授权)用户。我们在服务器端有 CORS 配置,并且还有:

Access-Control-Allow-Credentials "true"

有人可以帮帮我吗?我没有选择,我不明白为什么凭证被剥夺?这可能与CORS有关吗?

【问题讨论】:

    标签: spring-security cors sockjs spring-websocket


    【解决方案1】:

    即使XmlHttpRequest.withCredentials=true(由 SockJS 客户端完成)和Access-Control-Allow-Credentials=true,您也无法在跨域请求的 URL 中传递用户名和密码。

    为了使用基本身份验证,您需要自己创建Authorization 标头,但目前 SockJS 客户端似乎不允许这样做。有一个问题需要这种支持,我添加了a new comment 解释我们需要这个来支持基本身份验证。

    由于 Authorization 标头不是 simple header,因此将在实际请求之前发送 CORS preflight request。但是 Spring Framework 目前默认does not dispatch OPTIONS requests,所以即使在客户端设置了 Authorization 标头,您也需要在 Spring Framework 中启用 OPTIONS 请求调度。

    web.xml:

    <servlet>
    <servlet-name>dispatcherServlet</servlet-name>
    <servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
    <init-param>
      <param-name>dispatchOptionsRequest</param-name>
      <param-value>true</param-value>
    </init-param>
    <load-on-startup>1</load-on-startup>
    

    或者,如果您使用没有 web.xml 的 Servlet 3,请将其添加到扩展 AbstractAnnotationConfigDispatcherServletInitializer 的类中:

    @Override
    protected void customizeRegistration(Dynamic registration) {
        registration.setInitParameter("dispatchOptionsRequest", "true");
    }
    

    【讨论】:

    • 非常感谢您提供建议。它澄清了很多。因此,听起来端到端的功能要正常工作,我们必须等待 SockJS 社区的修复。我的理解正确吗?同时,我们决定使用 Spring 的“纯”websocket 支持。这意味着,从 WebSocketConfigurer impl 中删除 .withSockJS() 方法。我们已经验证它在使用基于 java 的纯 websocket 客户端时可以正常工作。是否有浏览器客户端(使用纯 websocket JS)跨域传递凭据的解决方法?
    猜你喜欢
    • 2013-07-07
    • 2018-07-20
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2012-01-01
    • 1970-01-01
    • 2014-11-04
    • 1970-01-01
    相关资源
    最近更新 更多