WSO2 和 Spring SAML 单次注销问题

Posted

技术标签:

【中文标题】WSO2 和 Spring SAML 单次注销问题【英文标题】:WSO2 and Spring SAML single logout issue 【发布时间】:2017-06-10 19:52:42 【问题描述】:

我遇到的这个问题已经在这个网站上讨论过好几次了,但是大多数帖子都很老了。这是我正在经历的something similar。我使用 WSO2 IS 5.2 作为我的 IdP,并且我有 2 个基于 Java 的 Web 应用程序托管在参与 SSO 的不同服务器上。每个 webapp (SP) 都实现了 Spring-SAML 扩展。单点登录完美运行,但单点注销仅部分有效。这是测试用例:

    访问 webapp1 上的安全资源 显示来自 Idp (WSO2) 的登录页面并且用户登录 提供来自 webapp1 的安全资源 访问 webapp2 上的安全资源 SAML 请求发送到 Idp,Idp 响应并且用户通过身份验证 提供来自 webapp2 的安全资源,结束 SSO 从 webapp2 发起单次注销 Webapp2 向 Idp 发送 saml 请求(通过浏览器)并返回 saml 响应 用户在 webapp2 上本地注销并且 Idp 会话终止 IdP 直接向 webapp1 发送注销请求(反向通道类型) 对 webapp1 的注销请求失败(日志显示 SamlStatusException: 没有用户登录)

所以最终结果是我在 webapp1 上仍然有一个本地会话。如果我更改顺序并从 webapp1 启动 SLO,那么 webapp1 将被注销并且 webapp2 的本地会话将继续存在。 WSO2 服务器能够在 SLO 期间确定第二个会话参与者,但是从 Idp 发送到第二个会话参与者的 HTTP 请求没有 Spring 安全上下文。这将是一个无状态的 HTTP 请求,因此不会有登录用户。这就是为什么我认为它失败了。

我发现this 讨论。它大约2岁。这个问题有什么新的吗?也许我在 WSO2 或 Spring-saml 配置中错过了一个配置步骤。

这是我的 SP 元数据的相关部分:

<md:SingleLogoutService Location="https://tpap10-wwwdev04.arbfile.org:443/webapp/saml/SingleLogout" Binding="urn:oasis:names:tc:SAML:2.0:bindings:HTTP-POST"/>
<md:SingleLogoutService Location="https://tpap10-wwwdev04.arbfile.org:443/webapp/saml/SingleLogout" Binding="urn:oasis:names:tc:SAML:2.0:bindings:HTTP-Redirect"/>
<md:NameIDFormat>urn:oasis:names:tc:SAML:1.1:nameid-format:emailAddress</md:NameIDFormat>
<md:NameIDFormat>urn:oasis:names:tc:SAML:2.0:nameid-format:transient</md:NameIDFormat>
<md:NameIDFormat>urn:oasis:names:tc:SAML:2.0:nameid-format:persistent</md:NameIDFormat>
<md:NameIDFormat>urn:oasis:names:tc:SAML:1.1:nameid-format:unspecified</md:NameIDFormat>
<md:NameIDFormat>urn:oasis:names:tc:SAML:1.1:nameid-format:X509SubjectName</md:NameIDFormat>
<md:AssertionConsumerService Location="https://tpap10-wwwdev04.arbfile.org:443/webapp/saml/SSO" Binding="urn:oasis:names:tc:SAML:2.0:bindings:HTTP-POST" isDefault="true" index="0"/>
<md:AssertionConsumerService Location="https://tpap10-wwwdev04.arbfile.org:443/webapp/saml/SSO" Binding="urn:oasis:names:tc:SAML:2.0:bindings:HTTP-Artifact" index="1"/>

SP 上的一些相关 Spring-Saml 配置:

  <bean id="metadataGeneratorFilter" class="org.springframework.security.saml.metadata.MetadataGeneratorFilter">
<constructor-arg>
  <bean class="org.springframework.security.saml.metadata.MetadataGenerator">
    <property name="entityId" value="urn:webapp1:mycity"/>
    <property name="entityBaseURL" value="https://wwwdev04.domain.org:443/webapp" />
    <property name="extendedMetadata">
      <bean class="org.springframework.security.saml.metadata.ExtendedMetadata">
        <!-- <property name="signMetadata" value="false"/> -->
        <property name="idpDiscoveryEnabled" value="false"/>
      </bean>
    </property>
  </bean>
</constructor-arg>
</bean>

【问题讨论】:

【参考方案1】:

WSO2 未正确实施 SAML 2.0 规范。该规范要求使用前端通道(=通过用户的浏览器)完成带有 HTTP-* 绑定的单点注销 - 这使得 HTTP 会话可用并允许 Spring SAML 正确终止它。我相信这个问题在 WSO2 中从未得到解决。

Spring SAML 默认使用 HttpSession 来存储用户的状态。这也是 Spring SAML 不支持开箱即用的 SOAP 绑定单点注销的原因。可以实现 Spring Security 会话的应用程序范围的存储,该会话可以独立于 HttpSession 失效(因此可以解决 WSO2 的限制),但默认情况下没有配置(我从未尝试过)。

【讨论】:

你好弗拉基米尔,我知道你是春天的专家。你能帮我解决我的问题吗?

以上是关于WSO2 和 Spring SAML 单次注销问题的主要内容,如果未能解决你的问题,请参考以下文章

ITfoxtec SAML 2.0 - 单次注销

使用 SAML 单次注销 (SLO) 调用注销 URL 后如何清除 Android 网络视图 cookie?

SAML 2.0 单次注销问题 - IdP 应如何终止在不同用户代理中运行的 SP 会话?

SAML SLO(单次注销)是不是从所有 SP(服务提供商)注销?

Spring SAML SSO 不共享会话

Spring SAML 与 WSO2 身份服务器集成,无法识别 SAML 消息