SAML 2.0 ログイン、saml2Login()
機能は、SAML 2.0 ID プロバイダー(Okta、ADFS など)で既存のアカウントを使用してユーザーがアプリケーションにログインできるようにする機能をアプリケーションに提供します。
![]() | メモ |
---|---|
SAML 2.0 ログインは、SAML 2 プロファイル (英語) で指定されている Web ブラウザー SSO プロファイルを使用して実装されます。現在、実装は単純な認証スキームに制限されています。 |
SAML 2 サービスプロバイダー、SP (依存パーティ) のサポートは 2009 年から独立プロジェクト: GitHub (英語) として存在していました。1.0.x ブランチはまだ使用されていますが、SP 実装に基づいて SAML 2.0 ID プロバイダー実装も作成した Cloud Foundry ユーザーアカウントと認証サーバー: GitHub (英語) に含まれます。
2018 年に、サービスプロバイダーとアイデンティティプロバイダー: GitHub (英語) とスタンドアロンライブラリの両方の更新された実装を作成する実験を行いました。Spring Security チームである私たち Spring Security は、慎重かつ長期にわたる審議の結果、その努力を中止することにしました。この取り組みにより、そのスタンドアロン 1.0.x ライブラリの代替が作成されましたが、別のライブラリの上にライブラリを構築する必要はないと感じました。
代わりに、コア Spring Security: GitHub (英語) の一部として SAML 2 認証のフレームワークサポートを提供することを選択しました。
saml2Login()
は、認証プロバイダー、別名アサーティングパーティーから XML アサーションを受信するサービスプロバイダー、SP、依存パーティーである認証に焦点を当てて、SAML 2 機能セット (英語) の一部をサポートすることを目的としています。
SAML 2 ログインまたは認証は、SP が IDP からアサーションと呼ばれる XML メッセージを受信して検証するという概念です。
現在、2 つのサポートされている認証フローがあります
entityId = {baseUrl}/saml2/service-provider-metadata/{registrationId}
によって識別されます {baseUrl}/login/saml2/sso/{registrationId}
で Http-POST または Http-Redirect を介して SAML レスポンスに埋め込まれたアサーションを受信する Converter<Assertion, Collection<? extends GrantedAuthority>>
を使用して、アサーション属性を機関に抽出できます GrantedAuthoritiesMapper
を使用して機関のマッピングとホワイトリストを許可する java.security.cert.X509Certificate
形式の公開鍵。AuthNRequest
を介した SP 開始認証 saml2Login()
を Spring Security フィルターチェーンに追加するには、最小限の Java 構成には、SAML 構成と HttpSecurity.saml2Login()
メソッドの呼び出しを含む構成リポジトリ RelyingPartyRegistrationRepository
が必要です。
@EnableWebSecurity public class SecurityConfig extends WebSecurityConfigurerAdapter { @Bean public RelyingPartyRegistrationRepository relyingPartyRegistrationRepository() { //SAML configuration //Mapping this application to one or more Identity Providers return new InMemoryRelyingPartyRegistrationRepository(...); } @Override protected void configure(HttpSecurity http) throws Exception { http .authorizeRequests() .anyRequest().authenticated() .and() .saml2Login() ; } }
Bean 宣言は便利ですが、オプションのアプローチです。メソッド呼び出しを使用してリポジトリを直接接続できます
@EnableWebSecurity public class SecurityConfig extends WebSecurityConfigurerAdapter { @Override protected void configure(HttpSecurity http) throws Exception { http .authorizeRequests() .anyRequest().authenticated() .and() .saml2Login() .relyingPartyRegistrationRepository(...) ; } }
RelyingPartyRegistration
: GitHub (英語) オブジェクトは、このアプリケーション、SP、アサーティングパーティ、IDP 間のマッピングを表します。
URI パターンは、受信リクエストに基づいて URI を自動的に生成するために頻繁に使用されます。saml2Login
の URI パターンには、次の変数を含めることができます
baseUrl
registrationId
baseScheme
baseHost
basePort
例:
{baseUrl}/login/saml2/sso/{registrationId}
registrationId
- (必須)この構成マッピングの一意の識別子。この識別子は URI パスで使用される可能性があるため、URI エンコードが必要ないことに注意する必要があります。localEntityIdTemplate
- (オプション)受信リクエストに基づいてこのアプリケーションのエンティティ ID を作成する URI パターン。デフォルトは {baseUrl}/saml2/service-provider-metadata/{registrationId}
であり、小さなサンプルアプリケーションの場合は次のようになります。http://localhost:8080/saml2/service-provider-metadata/my-test-configuration
この構成オプションはパターンである必要はなく、固定 URI 値を使用できます。
remoteIdpEntityId
- (必須)ID プロバイダーのエンティティ ID。常に固定 URI 値または文字列。パターンは許可されません。assertionConsumerServiceUrlTemplate
- (オプション)SP が開始したフロー中に SP から IDP に AuthNRequest
とともに送信されるアサーションコンシューマーサービス URI を示す URI パターン。これはパターンにすることができますが、実際の URI は SP 上の ACS エンドポイントに解決する必要があります。デフォルト値は {baseUrl}/login/saml2/sso/{registrationId}
であり、 Saml2WebSsoAuthenticationFilter
: GitHub (英語) エンドポイントに直接マップします idpWebSsoUrl
- (必須)SP が AuthNRequest
メッセージを送信する IDP シングルサインオンエンドポイントの固定 URI 値。 credentials
- メッセージの署名、検証、暗号化、復号化に使用される資格情報、秘密鍵、x509 証明書のリスト。このリストには、資格情報を簡単にローテーションできるように冗長な資格情報を含めることができます。たとえば
ENCRYPTION
キーを使用して行われます。SIGNING
キーを使用して行われます。受信メッセージを受信すると、署名が常に必要になります。システムは最初にインデックス [0] の証明書を使用して署名の検証を試み、最初の証明書が失敗した場合にのみ 2 番目の証明書に移動します。
同様に、SP で構成された秘密キーが復号化に使用され、同じ順序で試行されます。IDP へのメッセージに署名するときに、最初の SP 資格情報(type=SIGNING
)が使用されます。
アプリケーションが複数の ID プロバイダーを使用するユースケースでは、2 つの RelyingPartyRegistration
オブジェクト間で一部の構成が重複していることが明らかになります。
構成値の複製にはいくつかの欠点がありますが、バックエンド構成リポジトリはこのデータストレージモデルを複製する必要はありません。
このセットアップには利点があります。一部の ID プロバイダーと他の ID プロバイダーでは、資格情報のローテーションがより簡単になる場合があります。このオブジェクトモデルにより、マルチ IDP のユースケースで構成が変更されたときに混乱が生じず、すべての ID プロバイダーで資格情報をローテーションできなくなります。
Spring Security SAML 2 実装は、XML 形式で SP メタデータをダウンロードするためのエンドポイントをまだ提供していません。交換される最小限のピース
entity ID - デフォルトは {baseUrl}/saml2/service-provider-metadata/{registrationId}
この同じ値を使用する他の既知の構成名
single signon URL - デフォルトは {baseUrl}/login/saml2/sso/{registrationId}
この同じ値を使用する他の既知の構成名
Web アプリケーションから認証を開始するには、単純なリダイレクト
{baseUrl}/saml2/authenticate/{registrationId}
エンドポイントは、構成可能なファクトリで createAuthenticationRequest
メソッドを呼び出して、AuthNRequest
を生成します。構成で Saml2AuthenticationRequestFactory
を Bean として公開するだけです。
public interface Saml2AuthenticationRequestFactory { String createAuthenticationRequest(Saml2AuthenticationRequest request); }
現在、Spring Security SAML ログインの自動構成: GitHub (英語) で Spring Boot チームと協力しています。それまでの間、Yaml 設定をサポートする Spring Boot サンプルを提供しました。
サンプルを実行するには、次の 3 つの手順を実行する
Spring Boot アプリケーションを起動する
./gradlew :spring-security-samples-boot-saml2login:bootRun
ブラウザーを開く
これにより、ID プロバイダーに移動し、次を使用してログインします。
user
password
複数のプロバイダーを使用するのは非常に簡単ですが、注意を払わないと失敗する可能性のあるデフォルトがいくつかあります。RelyingPartyRegistration
オブジェクトの SAML 構成では、SP エンティティ ID をデフォルトに
{baseUrl}/saml2/service-provider-metadata/{registrationId}
つまり、2 つのプロバイダー構成では、システムは次のようになります
registration-1 (Identity Provider 1) - Our local SP Entity ID is: http://localhost:8080/saml2/service-provider-metadata/registration-1 registration-2 (Identity Provider 2) - Our local SP Entity ID is: http://localhost:8080/saml2/service-provider-metadata/registration-2
以下のサンプルに示すこの構成では、外部に対して、実際に同じアプリケーション内でホストされる 2 つの仮想サービスプロバイダー ID を作成しました。
spring: security: saml2: login: relying-parties: - entity-id: &idp-entity-id https://simplesaml-for-spring-saml.cfapps.io/saml2/idp/metadata.php registration-id: simplesamlphp web-sso-url: &idp-sso-url https://simplesaml-for-spring-saml.cfapps.io/saml2/idp/SSOService.php signing-credentials: &service-provider-credentials - private-key: | -----BEGIN PRIVATE KEY----- MIICeAIBADANBgkqhkiG9w0BAQEFAASCAmIwggJeAgEAAoGBANG7v8QjQGU3MwQE ...................SHORTENED FOR READ ABILITY................... INrtuLp4YHbgk1mi -----END PRIVATE KEY----- certificate: | -----BEGIN CERTIFICATE----- MIICgTCCAeoCCQCuVzyqFgMSyDANBgkqhkiG9w0BAQsFADCBhDELMAkGA1UEBhMC ...................SHORTENED FOR READ ABILITY................... RZ/nbTJ7VTeZOSyRoVn5XHhpuJ0B -----END CERTIFICATE----- verification-credentials: &idp-certificates - | -----BEGIN CERTIFICATE----- MIIEEzCCAvugAwIBAgIJAIc1qzLrv+5nMA0GCSqGSIb3DQEBCwUAMIGfMQswCQYD ...................SHORTENED FOR READ ABILITY................... lx13Y1YlQ4/tlpgTgfIJxKV6nyPiLoK0nywbMd+vpAirDt2Oc+hk -----END CERTIFICATE----- - entity-id: *idp-entity-id registration-id: simplesamlphp2 web-sso-url: *idp-sso-url signing-credentials: *service-provider-credentials verification-credentials: *idp-certificates
これが望ましくない場合は、次を使用してローカル SP エンティティ ID を手動で上書きできます。
localEntityIdTemplate = {baseUrl}/saml2/service-provider-metadata
ローカル SP エンティティ ID をこの値に変更する場合、登録 ID に基づいて登録済み ID プロバイダーごとに正しいシングルサインオン URL(アサーションコンシューマーサービス URL)を提供することが重要です。{baseUrl}/login/saml2/sso/{registrationId}