1. 概述

本教程将指导如何在 Spring Boot 中集成 SAML2。SAML 是实现安全应用的成熟技术,但配置过程涉及多个参与方,相对复杂。我们需要在服务提供商(SP)和身份提供商(IdP)之间反复调整配置,因此需要耐心按步骤操作。下面我们将逐步创建一个可运行的 SAML2 应用。

2. 配置服务提供商(SP)

我们的 Spring Boot 应用将作为服务提供商。首先创建包含 Spring Security、Spring MVC 和 OpenSAML 依赖的 Spring Boot 应用。核心依赖是 Spring Security SAML2,Spring Security 框架通过以下单一依赖提供 SAML2 支持:

<dependency>
    <groupId>org.springframework.security</groupId>
    <artifactId>spring-security-saml2-service-provider</artifactId>
</dependency>

2.1. SAML 基础配置

application.yml 中添加 SAML2 必要配置。最关键的是身份提供商的元数据。虽然我们已添加 metadata-uri 配置,但此时元数据文件尚未生成:

spring:
  security:
    saml2:
      relyingparty:
        registration:
          okta:
            signing:
              credentials:
                - private-key-location: classpath:local.key
                  certificate-location: classpath:local.crt
            singlelogout:
              binding: POST
              response-url: "{baseUrl}/logout/saml2/slo"
            assertingparty:
              metadata-uri: "classpath:metadata/metadata-idp.xml"

singlelogout 配置定义了身份提供商在登出成功后的重定向接口。signing.credentials 配置指定了应用用于向身份提供商签名登出请求的密钥和证书。使用 OpenSSL 工具生成 local.keylocal.crt 文件:

openssl req -newkey rsa:2048 -nodes -keyout local.key -x509 -days 365 -out local.crt

2.2. 代码级安全配置

添加安全过滤器到过滤器链,该过滤器将身份提供商元数据注入安全上下文。同时在 http 对象上调用 saml2Login()saml2Logout() 启用登录/登出功能:

Saml2MetadataFilter filter = new Saml2MetadataFilter(relyingPartyRegistrationResolver, new OpenSamlMetadataResolver());

http.csrf(AbstractHttpConfigurer::disable).authorizeHttpRequests(authorize -> authorize.anyRequest()
  .authenticated())
  .saml2Login(withDefaults())
  .saml2Logout(withDefaults())
  .addFilterBefore(filter, Saml2WebSsoAuthenticationFilter.class);

return http.build();

使用 withDefaults() 方法配置默认行为,这正是 Spring Boot 平台的强大之处——仅需几行代码即可完成整个 SAML2 应用配置。接下来我们将配置 Okta 作为身份提供商。

3. 配置身份提供商(IdP)

本步骤将 Okta 设置为身份提供商。身份提供商负责用户认证并生成 SAML 断言,该断言将返回给用户代理(浏览器)。用户代理将断言提交给服务提供商进行验证,验证通过后即可访问资源。

注册 Okta 开发者账户 并登录后,在左侧导航栏进入 Applications 页面开始 SAML 应用集成:

Okta dashboard

3.1. 创建应用集成

点击 "Create App Integration" 打开创建向导,选择 SAML 2.0:

Okta create a new app integration

点击 "Next" 进入三步式 SAML 集成向导。

3.2. 通用设置

填写应用名称为 "Baeldung Spring Security SAML2 App":

Okta create SAML integration

3.3. SAML 核心配置

配置 SAML 应用的关键参数

  • 单点登录(SSO)URL:身份提供商接收 SSO 请求的地址
  • 受众 URI(Audience URI):SAML 断言接收方的标识符

Okta Create A New App Integration Configure

示例配置:

  • 受众 URI:http://localhost:8080/saml2/service-provider-metadata/okta
  • 单点登录 URL:http://localhost:8080/login/saml2/sso/okta

3.4. 高级设置与用户属性

展开 "Show Advanced Settings" 部分:

  1. 启用单点登出:上传 local.crt 证书(与服务提供商配置中的证书相同
  2. 配置单点登出 URLhttp://localhost:8080/logout/saml2/slo

Create SAML Integration

添加用户属性映射:

emailAddress -> Unspecified -> user.email  
firstName -> Unspecified -> user.firstName

通过 "Preview the SAML Assertion" 预览生成的断言:

Preview SAML

3.5. 反馈信息

选择 "I'm an Okta customer adding an internal app":

SAML integration feedback step

3.6. 获取 SAML 配置信息

完成向导后进入应用的 "Sign On" 标签页,点击右侧 "View SAML setup instructions":

SAML configuration sign in step

在配置页面底部找到 IdP 元数据:

SAML settings and certificate configurations

复制元数据并保存为 metadata-idp-okta.xml,放置于服务提供商的 resources/metadata 目录下,满足 application.ymlmetadata_uri 的要求:

Okta create a new app integration fetch IDP metadata

至此,服务提供商和身份提供商配置完成。接下来在 Okta 中创建用户并分配应用权限。

4. 创建用户主体

登录 Okta 开发者账户,在左侧 "Directory" 下进入 "People" 页面。填写表单创建新用户(可能需要刷新页面才能看到新用户):

Add a new Okta user

⚠️ 生产环境建议发送激活邮件或要求首次登录修改密码,此处我们直接激活用户。

点击 "Assign" 按钮将用户分配到 SAML 应用:

Okta user assignment

5. 测试应用

启动 Spring Boot 应用,访问 http://localhost:8080 将跳转到登录页面:

Okta User Login

登录成功后显示用户信息(包括 emailAddressfirstName):

Okta User Login Reset Password

最后测试登出功能。首先在 application.yml 中配置 <OKTA-ID>(从 URL 中获取):

spring:
  security:
    saml2:
      relyingparty:
        registration:
          okta:
            ...
            singlelogout:
              url: https://dev-<OKTA-ID>.okta.com/app/dev-56617222_springbootsaml_1/exk8b5jr6vYQqVXp45d7/slo/saml
              binding: POST
              response-url: "{baseUrl}/logout/saml2/slo"

点击登出按钮将清除所有 SAML 会话:

Okta User Logout Success

6. 总结

本文介绍了 Spring Boot Security SAML2 的集成方案。尽管 SAML2 配置复杂,但它是大型企业的首选方案。掌握 SAML2 后,可以充分利用其强大的安全特性,不仅保障应用安全,还能实现单点登录(SSO),避免用户记忆多套账号密码。

✅ 关键要点总结:

  1. 服务提供商需配置元数据、证书和安全过滤器
  2. 身份提供商需配置 SAML 断言参数和用户属性
  3. 单点登出需同步配置证书和重定向 URL
  4. 测试时需验证登录、用户属性展示和登出流程

完整示例代码请查看 GitHub 仓库


原始标题:SAML with Spring Boot and Spring Security