認証の永続性とセッション管理
リクエストを認証するアプリケーションを取得したら、その結果の認証をどのように保持し、将来のリクエストで復元するかを検討することが重要です。
これはデフォルトで自動的に行われるため、追加のコードは必要ありませんが、HttpSecurity
で requireExplicitSave
が何を意味するかを知ることは重要です。
よろしければ、requireExplicitSave の取り組みやそれが重要な理由についてさらに詳しく参照してください。それ以外の場合は、ほとんどの場合、このセクションはこれで完了です。
ただし、終了する前に、次のユースケースのいずれかがアプリケーションに適合するかどうかを検討してください。
ユーザーの同時ログイン回数を制限したい
認証を手動で保存していて、それを削除したい
SessionManagementFilter
を使用しており、それから移動するためのガイダンスが必要です認証をセッション以外に保存したい
ステートレス認証を使用していますが、セッションに保存したい
SessionCreationPolicy.NEVER
を使用していますが、アプリケーションはまだセッションを作成しています。
セッション管理のコンポーネントを理解する
セッション管理サポートは、連携して機能を提供するいくつかのコンポーネントで構成されています。これらのコンポーネントは、SecurityContextHolderFilter
、SecurityContextPersistenceFilter
、および SessionManagementFilter
です。
Spring Security 6 では、 |
SessionManagementFilter
SessionManagementFilter
は、SecurityContextRepository
のコンテンツを SecurityContextHolder
の現在のコンテンツと照合して、通常、事前認証や remember-me [ 1 ] などの非対話型認証メカニズムによって現在のリクエスト中にユーザーが認証されたかどうかを判断します。リポジトリにセキュリティコンテキストが含まれている場合、フィルターは何もしません。存在せず、スレッドローカル SecurityContext
に(非匿名の) Authentication
オブジェクトが含まれている場合、フィルターは、スタック内の前のフィルターによって認証されたと見なします。次に、構成された SessionAuthenticationStrategy
を呼び出します。
ユーザーが現在認証されていない場合、フィルターは無効なセッション ID がリクエストされているかどうかを確認し(タイムアウトなどが原因)、設定されている InvalidSessionStrategy
が設定されている場合はそれを呼び出します。最も一般的な動作は、固定 URL にリダイレクトすることであり、これは標準実装 SimpleRedirectInvalidSessionStrategy
にカプセル化されています。後者は、前述のように、名前空間を介して無効なセッション URL を構成するときにも使用されます。
SessionManagementFilter
からの脱却
Spring Security 5 では、デフォルト構成は、ユーザーが認証されたかどうかを検出し、SessionAuthenticationStrategy (Javadoc) を呼び出すために SessionManagementFilter
に依存しています。これの問題は、一般的な設定では、すべてのリクエストに対して HttpSession
を読み取る必要があることです。
Spring Security 6 では、デフォルトでは、認証メカニズム自体が SessionAuthenticationStrategy
を呼び出す必要があります。つまり、Authentication
がいつ完了したかを検出する必要がないため、リクエストごとに HttpSession
を読み取る必要はありません。
SessionManagementFilter
から離れる際の注意点
Spring Security 6 では、SessionManagementFilter
はデフォルトで使用されないため、sessionManagement
DSL の一部のメソッドは効果がありません。
メソッド | 置換文字列 |
---|---|
| 認証メカニズムで |
| 認証メカニズムで |
| 上記で説明したように、認証メカニズムで |
これらのメソッドのいずれかを使用しようとすると、例外がスローされます。
認証の保存場所のカスタマイズ
デフォルトでは、Spring Security はセキュリティコンテキストを HTTP セッションに保存します。ただし、これをカスタマイズする理由がいくつかあります。
HttpSessionSecurityContextRepository
インスタンスで個々の setter を呼び出すこともできますセキュリティコンテキストをキャッシュまたはデータベースに格納して、水平方向のスケーリングを有効にすることができます。
まず、SecurityContextRepository
の実装を作成するか、HttpSessionSecurityContextRepository
などの既存の実装を使用する必要があります。次に、それを HttpSecurity
に設定できます。
SecurityContextRepository
のカスタマイズ Java
Kotlin
XML
@Bean
public SecurityFilterChain filterChain(HttpSecurity http) {
SecurityContextRepository repo = new MyCustomSecurityContextRepository();
http
// ...
.securityContext((context) -> context
.securityContextRepository(repo)
);
return http.build();
}
@Bean
open fun filterChain(http: HttpSecurity): SecurityFilterChain {
val repo = MyCustomSecurityContextRepository()
http {
// ...
securityContext {
securityContextRepository = repo
}
}
return http.build()
}
<http security-context-repository-ref="repo">
<!-- ... -->
</http>
<bean name="repo" class="com.example.MyCustomSecurityContextRepository" />
上記の構成では、 |
カスタム認証メカニズムを使用している場合は、自分で Authentication
を保存することをお勧めします。
Authentication
を手動で保管する
たとえば、場合によっては、Spring Security フィルターに頼るのではなく、手動でユーザーを認証することがあります。これを行うには、カスタムフィルターまたは Spring MVC コントローラーエンドポイントを使用できます。たとえば、リクエスト間の認証を HttpSession
に保存する場合は、次のようにする必要があります。
Java
private SecurityContextRepository securityContextRepository =
new HttpSessionSecurityContextRepository(); (1)
@PostMapping("/login")
public void login(@RequestBody LoginRequest loginRequest, HttpServletRequest request, HttpServletResponse response) { (2)
UsernamePasswordAuthenticationToken token = UsernamePasswordAuthenticationToken.unauthenticated(
loginRequest.getUsername(), loginRequest.getPassword()); (3)
Authentication authentication = authenticationManager.authenticate(token); (4)
SecurityContext context = securityContextHolderStrategy.createEmptyContext();
context.setAuthentication(authentication); (5)
securityContextHolderStrategy.setContext(context);
securityContextRepository.saveContext(context, request, response); (6)
}
class LoginRequest {
private String username;
private String password;
// getters and setters
}
1 | コントローラーに SecurityContextRepository を追加 |
2 | HttpServletRequest と HttpServletResponse を注入して、SecurityContext を保存できるようにします。 |
3 | 提供された資格情報を使用して、認証されていない UsernamePasswordAuthenticationToken を作成します |
4 | AuthenticationManager#authenticate を呼び出してユーザーを認証する |
5 | SecurityContext を作成し、その中に Authentication を設定します |
6 | SecurityContext を SecurityContextRepository に保存します |
以上です。上記の例で securityContextHolderStrategy
が何であるかわからない場合は、SecurityContextStrategy
セクションの使用で詳細を読むことができます。
認証を適切にクリアする
Spring Security のログアウトのサポートを使用している場合は、コンテキストのクリアや保存など、多くのことを処理します。ただし、ユーザーをアプリから手動でログアウトする必要があるとします。その場合、コンテキストを適切にクリアして保存していることを確認する必要があります。
ステートレス認証の永続性の構成
たとえば、リクエスト間で認証を永続化するために、HttpSession
を作成して維持する必要がない場合があります。HTTP ベーシックなどの一部の認証メカニズムはステートレスであるため、リクエストごとにユーザーを再認証します。
セッションを作成したくない場合は、次のように SessionCreationPolicy.STATELESS
を使用できます。
Java
Kotlin
XML
@Bean
public SecurityFilterChain filterChain(HttpSecurity http) {
http
// ...
.sessionManagement((session) -> session
.sessionCreationPolicy(SessionCreationPolicy.STATELESS)
);
return http.build();
}
@Bean
open fun filterChain(http: HttpSecurity): SecurityFilterChain {
http {
// ...
sessionManagement {
sessionCreationPolicy = SessionCreationPolicy.STATELESS
}
}
return http.build()
}
<http create-session="stateless">
<!-- ... -->
</http>
上記の構成は、NullSecurityContextRepository
を使用するように SecurityContextRepository
を構成しており、また、リクエストがセッションに保存されないようにしています。
SessionCreationPolicy.NEVER
を使用している場合、アプリケーションがまだ HttpSession
を作成していることに気付くかもしれません。ほとんどの場合、これは、認証が成功した後に認証されたリソースが再リクエストするために、リクエストがセッションに保存されるために発生します。これを回避するには、セクションの保存リクエストを防止する方法を参照してください。
セッションへのステートレス認証の保存
何らかの理由で、ステートレス認証メカニズムを使用しているが、認証をセッションに保存したい場合は、NullSecurityContextRepository
の代わりに HttpSessionSecurityContextRepository
を使用できます。
HTTP ベーシックの場合、BasicAuthenticationFilter
で使用される SecurityContextRepository
を変更する ObjectPostProcessor
を追加できます。
HttpSession
に HTTP 基本認証を格納します Java
@Bean
SecurityFilterChain web(HttpSecurity http) throws Exception {
http
// ...
.httpBasic((basic) -> basic
.addObjectPostProcessor(new ObjectPostProcessor<BasicAuthenticationFilter>() {
@Override
public <O extends BasicAuthenticationFilter> O postProcess(O filter) {
filter.setSecurityContextRepository(new HttpSessionSecurityContextRepository());
return filter;
}
})
);
return http.build();
}
上記は、ベアラートークン認証などの他の認証メカニズムにも適用されます。
明示的な保存が必要であることを理解する
Spring Security 5 のデフォルトの動作は、SecurityContextPersistenceFilter
を使用して SecurityContext
が SecurityContextRepository
に自動的に保存されることです。保存は、HttpServletResponse
がコミットされる直前、および SecurityContextPersistenceFilter
の直前に行う必要があります。残念ながら、SecurityContext
の自動永続化は、リクエストが完了する前 (つまり、HttpServletResponse
をコミットする直前) に行われると、ユーザーを驚かせる可能性があります。また、状態を追跡して保存が必要かどうかを判断するのも複雑で、SecurityContextRepository
(つまり HttpSession
) への不必要な書き込みが発生することがあります。
これらの理由から、SecurityContextPersistenceFilter
は廃止され、SecurityContextHolderFilter
に置き換えられました。Spring Security 6 では、デフォルトの動作として、SecurityContextHolderFilter
は SecurityContextRepository
から SecurityContext
のみを読み取り、それを SecurityContextHolder
に入力します。リクエスト間で SecurityContext
を維持したい場合、ユーザーは SecurityContextRepository
で SecurityContext
を明示的に保存する必要があります。これにより、必要なときにのみ SecurityContextRepository
(つまり HttpSession
) への書き込みが必要になるため、あいまいさがなくなり、パフォーマンスが向上します。
使い方
要約すると、requireExplicitSave
が true
の場合、Spring Security は SecurityContextPersistenceFilter
の代わりに SecurityContextHolderFilter
をセットアップします。
同時セッション制御の構成
1 人のユーザーがアプリケーションにログインする機能に制約を課したい場合、Spring Security は、次の簡単な追加で、これをすぐにサポートします。まず、セッションライフサイクルイベントについて Spring Security を最新の状態に保つために、構成に次のリスナーを追加する必要があります。
Java
Kotlin
web.xml
@Bean
public HttpSessionEventPublisher httpSessionEventPublisher() {
return new HttpSessionEventPublisher();
}
@Bean
open fun httpSessionEventPublisher(): HttpSessionEventPublisher {
return HttpSessionEventPublisher()
}
<listener>
<listener-class>
org.springframework.security.web.session.HttpSessionEventPublisher
</listener-class>
</listener>
次に、セキュリティ構成に次の行を追加します。
Java
Kotlin
XML
@Bean
public SecurityFilterChain filterChain(HttpSecurity http) {
http
.sessionManagement(session -> session
.maximumSessions(1)
);
return http.build();
}
@Bean
open fun filterChain(http: HttpSecurity): SecurityFilterChain {
http {
sessionManagement {
sessionConcurrency {
maximumSessions = 1
}
}
}
return http.build()
}
<http>
...
<session-management>
<concurrency-control max-sessions="1" />
</session-management>
</http>
これにより、ユーザーが複数回ログインすることが防止されます。2 回目のログインにより、最初のログインが無効になります。
Spring Boot を使用すると、上記の構成シナリオを次の方法でテストできます。
Java
@SpringBootTest(webEnvironment = SpringBootTest.WebEnvironment.RANDOM_PORT)
@AutoConfigureMockMvc
public class MaximumSessionsTests {
@Autowired
private MockMvc mvc;
@Test
void loginOnSecondLoginThenFirstSessionTerminated() throws Exception {
MvcResult mvcResult = this.mvc.perform(formLogin())
.andExpect(authenticated())
.andReturn();
MockHttpSession firstLoginSession = (MockHttpSession) mvcResult.getRequest().getSession();
this.mvc.perform(get("/").session(firstLoginSession))
.andExpect(authenticated());
this.mvc.perform(formLogin()).andExpect(authenticated());
// first session is terminated by second login
this.mvc.perform(get("/").session(firstLoginSession))
.andExpect(unauthenticated());
}
}
最大セッション数のサンプル [GitHub] (英語) を使用して試すことができます。
また、2 回目のログインを防止したい場合もよくあります。その場合は、次を使用できます。
Java
Kotlin
XML
@Bean
public SecurityFilterChain filterChain(HttpSecurity http) {
http
.sessionManagement(session -> session
.maximumSessions(1)
.maxSessionsPreventsLogin(true)
);
return http.build();
}
@Bean
open fun filterChain(http: HttpSecurity): SecurityFilterChain {
http {
sessionManagement {
sessionConcurrency {
maximumSessions = 1
maxSessionsPreventsLogin = true
}
}
}
return http.build()
}
<http>
<session-management>
<concurrency-control max-sessions="1" error-if-maximum-exceeded="true" />
</session-management>
</http>
2 回目のログインは拒否されます。「拒否」とは、フォームベースのログインが使用されている場合、ユーザーが authentication-failure-url
に送信されることを意味します。2 番目の認証が "remember-me" などの別の非対話型メカニズムを介して行われる場合、"unauthorized" (401) エラーがクライアントに送信されます。代わりにエラーページを使用する場合は、session-authentication-error-url
属性を session-management
要素に追加できます。
Spring Boot を使用すると、上記の構成を次の方法でテストできます。
Java
@SpringBootTest(webEnvironment = SpringBootTest.WebEnvironment.RANDOM_PORT)
@AutoConfigureMockMvc
public class MaximumSessionsPreventLoginTests {
@Autowired
private MockMvc mvc;
@Test
void loginOnSecondLoginThenPreventLogin() throws Exception {
MvcResult mvcResult = this.mvc.perform(formLogin())
.andExpect(authenticated())
.andReturn();
MockHttpSession firstLoginSession = (MockHttpSession) mvcResult.getRequest().getSession();
this.mvc.perform(get("/").session(firstLoginSession))
.andExpect(authenticated());
// second login is prevented
this.mvc.perform(formLogin()).andExpect(unauthenticated());
// first session is still valid
this.mvc.perform(get("/").session(firstLoginSession))
.andExpect(authenticated());
}
}
フォームベースのログイン用にカスタマイズされた認証フィルターを使用している場合は、同時セッション制御のサポートを明示的に構成する必要があります。ログインを防止する最大セッション数のサンプル [GitHub] (英語) を使用して試すことができます。
タイムアウトの検出
セッションは自然に期限切れになり、セキュリティコンテキストが確実に削除されるようにするために必要なことは何もありません。とはいえ、Spring Security はセッションの有効期限が切れたことを検出し、指定された特定のアクションを実行できます。例: ユーザーがすでに期限切れのセッションでリクエストを行ったときに、特定のエンドポイントにリダイレクトしたい場合があります。これは、HttpSecurity
の invalidSessionUrl
によって実現されます。
Java
Kotlin
XML
@Bean
public SecurityFilterChain filterChain(HttpSecurity http) {
http
.sessionManagement(session -> session
.invalidSessionUrl("/invalidSession")
);
return http.build();
}
@Bean
open fun filterChain(http: HttpSecurity): SecurityFilterChain {
http {
sessionManagement {
invalidSessionUrl = "/invalidSession"
}
}
return http.build()
}
<http>
...
<session-management invalid-session-url="/invalidSession" />
</http>
このメカニズムを使用してセッションタイムアウトを検出する場合、ユーザーがログアウトしてブラウザーを閉じずに再度ログインすると、誤ってエラーが報告される可能性があることに注意してください。これは、セッションを無効にしたときにセッション cookie がクリアされず、ユーザーがログアウトした場合でも再送信されるためです。その場合は、セッション Cookie をクリアするようにログアウトを構成することをお勧めします。
無効なセッション戦略のカスタマイズ
invalidSessionUrl
は、SimpleRedirectInvalidSessionStrategy
の実装 (Javadoc) を使用して InvalidSessionStrategy
を設定する便利なメソッドです。動作をカスタマイズする場合は、InvalidSessionStrategy
(Javadoc) インターフェースを実装し、invalidSessionStrategy
メソッドを使用して構成できます。
Java
Kotlin
XML
@Bean
public SecurityFilterChain filterChain(HttpSecurity http) {
http
.sessionManagement(session -> session
.invalidSessionStrategy(new MyCustomInvalidSessionStrategy())
);
return http.build();
}
@Bean
open fun filterChain(http: HttpSecurity): SecurityFilterChain {
http {
sessionManagement {
invalidSessionStrategy = MyCustomInvalidSessionStrategy()
}
}
return http.build()
}
<http>
...
<session-management invalid-session-strategy-ref="myCustomInvalidSessionStrategy" />
<bean name="myCustomInvalidSessionStrategy" class="com.example.MyCustomInvalidSessionStrategy" />
</http>
ログアウト時のセッション Cookie のクリア
ログアウト時に JSESSIONID Cookie を明示的に削除できます。たとえば、ログアウトハンドラーで Clear-Site-Data
ヘッダー (英語) を使用します。
Java
Kotlin
XML
@Bean
public SecurityFilterChain filterChain(HttpSecurity http) {
http
.logout((logout) -> logout
.addLogoutHandler(new HeaderWriterLogoutHandler(new ClearSiteDataHeaderWriter(COOKIES)))
);
return http.build();
}
@Bean
open fun filterChain(http: HttpSecurity): SecurityFilterChain {
http {
logout {
addLogoutHandler(HeaderWriterLogoutHandler(ClearSiteDataHeaderWriter(COOKIES)))
}
}
return http.build()
}
<http>
<logout success-handler-ref="clearSiteDataHandler" />
<b:bean id="clearSiteDataHandler" class="org.springframework.security.web.authentication.logout.HeaderWriterLogoutHandler">
<b:constructor-arg>
<b:bean class="org.springframework.security.web.header.writers.ClearSiteDataHeaderWriter">
<b:constructor-arg>
<b:list>
<b:value>COOKIES</b:value>
</b:list>
</b:constructor-arg>
</b:bean>
</b:constructor-arg>
</b:bean>
</http>
これには、コンテナーに依存しないという利点があり、Clear-Site-Data
ヘッダーをサポートするすべてのコンテナーで機能します。
別の方法として、ログアウトハンドラーで次の構文を使用することもできます。
Java
Kotlin
XML
@Bean
public SecurityFilterChain filterChain(HttpSecurity http) {
http
.logout(logout -> logout
.deleteCookies("JSESSIONID")
);
return http.build();
}
@Bean
open fun filterChain(http: HttpSecurity): SecurityFilterChain {
http {
logout {
deleteCookies("JSESSIONID")
}
}
return http.build()
}
<http>
<logout delete-cookies="JSESSIONID" />
</http>
残念ながら、これがすべてのサーブレットコンテナーで機能することを保証できるわけではないため、ご使用の環境でテストする必要があります。
アプリケーションをプロキシの背後で実行している場合は、プロキシサーバーを構成することでセッション Cookie を削除できる場合もあります。例: Apache HTTPD の |
<LocationMatch "/tutorial/logout">
Header always set Set-Cookie "JSESSIONID=;Path=/tutorial;Expires=Thu, 01 Jan 1970 00:00:00 GMT"
</LocationMatch>
サイトデータのクリアおよびログアウトセクションの詳細。
セッション固定攻撃保護について
セッション固定 [Wikipedia] 攻撃は、悪意のある攻撃者がサイトにアクセスしてセッションを作成し、別のユーザーを同じセッションでログインさせる (たとえば、セッション ID をパラメーターとして含むリンクを送信する) 可能性がある潜在的なリスクです。Spring Security は、ユーザーがログインしたときに新しいセッションを作成するか、セッション ID を変更することで、これを自動的に防止します。
セッション固定保護の構成
次の 3 つの推奨オプションから選択することで、セッション固定保護の戦略を制御できます。
changeSessionId
- 新しいセッションを作成しません。代わりに、サーブレットコンテナー(HttpServletRequest#changeSessionId()
)によって提供されるセッション固定保護を使用します。このオプションは、Servlet 3.1(Java EE 7)以降のコンテナーでのみ使用可能です。古いコンテナーで指定すると、例外が発生します。これは、Servlet 3.1 以降のコンテナーのデフォルトです。newSession
- 既存のセッションデータをコピーせずに、新しい「クリーン」セッションを作成します(Spring セキュリティ関連の属性は引き続きコピーされます)。migrateSession
- 新しいセッションを作成し、既存のすべてのセッション属性を新しいセッションにコピーします。これは、Servlet 3.0 以前のコンテナーのデフォルトです。
次のようにして、セッション固定保護を構成できます。
Java
Kotlin
XML
@Bean
public SecurityFilterChain filterChain(HttpSecurity http) {
http
.sessionManagement((session) -> session
.sessionFixation((sessionFixation) -> sessionFixation
.newSession()
)
);
return http.build();
}
@Bean
open fun filterChain(http: HttpSecurity): SecurityFilterChain {
http {
sessionManagement {
sessionFixation {
newSession()
}
}
}
return http.build()
}
<http>
<session-management session-fixation-protection="newSession" />
</http>
セッション固定保護が発生すると、SessionFixationProtectionEvent
がアプリケーションコンテキストで公開されます。changeSessionId
を使用する場合、この保護により jakarta.servlet.http.HttpSessionIdListener
も通知されるため、コードが両方のイベントをリッスンする場合は注意してください。
セッション固定保護を none
に設定して無効にすることもできますが、アプリケーションが脆弱なままになるため、これはお勧めできません。
SecurityContextHolderStrategy
を使用する
次のコードブロックを検討してください。
Java
UsernamePasswordAuthenticationToken token = new UsernamePasswordAuthenticationToken(
loginRequest.getUsername(), loginRequest.getPassword());
Authentication authentication = this.authenticationManager.authenticate(token);
// ...
SecurityContext context = SecurityContextHolder.createEmptyContext(); (1)
context.setAuthentication(authentication); (2)
SecurityContextHolder.setContext(context); (3)
SecurityContextHolder
に静的にアクセスして、空のSecurityContext
インスタンスを作成します。SecurityContext
インスタンスにAuthentication
オブジェクトを設定します。SecurityContextHolder
にSecurityContext
インスタンスを静的に設定します。
上記のコードは正常に動作しますが、望ましくない効果が生じる可能性があります。コンポーネントが SecurityContextHolder
を介して静的に SecurityContext
にアクセスすると、SecurityContextHolderStrategy
を指定するアプリケーションコンテキストが複数ある場合に競合状態が発生する可能性があります。これは、SecurityContextHolder
では、アプリケーションコンテキストごとではなく、クラスローダーごとに 1 つの戦略があるためです。
これに対処するために、コンポーネントはアプリケーションコンテキストから SecurityContextHolderStrategy
を接続できます。デフォルトでは、依然として SecurityContextHolder
から戦略を検索します。
これらの変更は主に内部的なものですが、アプリケーションが SecurityContext
に静的にアクセスする代わりに SecurityContextHolderStrategy
をオートワイヤーする機会を提供します。そのためには、コードを次のように変更する必要があります。
Java
public class SomeClass {
private final SecurityContextHolderStrategy securityContextHolderStrategy = SecurityContextHolder.getContextHolderStrategy();
public void someMethod() {
UsernamePasswordAuthenticationToken token = UsernamePasswordAuthenticationToken.unauthenticated(
loginRequest.getUsername(), loginRequest.getPassword());
Authentication authentication = this.authenticationManager.authenticate(token);
// ...
SecurityContext context = this.securityContextHolderStrategy.createEmptyContext(); (1)
context.setAuthentication(authentication); (2)
this.securityContextHolderStrategy.setContext(context); (3)
}
}
構成された
SecurityContextHolderStrategy
を使用して、空のSecurityContext
インスタンスを作成します。SecurityContext
インスタンスにAuthentication
オブジェクトを設定します。SecurityContextHolderStrategy
にSecurityContext
インスタンスを設定します。
Eager セッション作成の強制
先行してセッションを作成することが有益な場合があります。これは、以下を使用して構成できる ForceEagerSessionCreationFilter
(Javadoc) を使用して行うことができます。
Java
Kotlin
XML
@Bean
public SecurityFilterChain filterChain(HttpSecurity http) {
http
.sessionManagement(session -> session
.sessionCreationPolicy(SessionCreationPolicy.ALWAYS)
);
return http.build();
}
@Bean
open fun filterChain(http: HttpSecurity): SecurityFilterChain {
http {
sessionManagement {
sessionCreationPolicy = SessionCreationPolicy.ALWAYS
}
}
return http.build()
}
<http create-session="ALWAYS">
</http>
次に読むもの
Spring Session を使用したクラスター化されたセッション
SessionManagementFilter
によって検出されません。これらの場合、セッション管理機能を個別に処理する必要があります。