Spring Boot(1系) + spring-security-oauth2 + Redis Session の組み合わせで Heroku上で動かすと SerializationException が発生した。
(1インスタンスなら起きない。複数インスタンスの場合のみ)
原因と解決策
ちなみにSpring Boot 2系(Spring5系) を使っている場合は Spring Security5系 を使用すれば良いらしい。(試してない)
Spring Boot 2系(Spring5系)に上げられるならその方がいい。
問題はどうやら spring-security-oauth2 にあるっぽい。
ググって出てきた解決策は 2つ
- SerializationException が起きたらRedis該当キーを消す。(id:katsu68 さんのブログ)
- スティッキーセッションにする(Heroku スティッキーセッションの設定)
1だけの場合、Heroku上だと頻繁にSerializationExceptionが起きるため、ログイン状態をほとんど維持できないことになる。
2だけの場合だと複数インスタンスにしている意味が薄いし、再起動が走るとやはりSerializationExceptionが起きる。
そのため両方の対応を行い対応した。
デプロイ時とHerokuのインスタンス再起動時だけセッション切れするがしばらくはこれで運用することに。
しかし、Herokuの再起動はいつされるかわからない(任意のタイミングで再起動することによりある程度はコントロールできる)
頻繁にログアウトされるのはユーザにとってもストレス。
ライブラリを作った
それを回避するため一部処理を自分で作ることにした。
また、それをライブラリとして公開することにもした。 -> 作ったライブラリ
<dependency>
<groupId>jp.co.ap-com</groupId>
<artifactId>spring-oauth2-serializable</artifactId>
<version>0.0.2</version>
</dependency>
spring-security-oauth2 の設定が済んでいるならばソースコードは@EnableOAuth2Sso
を @EnableOAuth2Serializable
に変えるだけ
ただし、一箇所でも @EnableOAuth2Sso
か @EnableOAuth2Client
が残ってるとダメ。
デモ用アプリケーションはこちら
https://github.com/apc-hattori/spring-oauth2-demo
spring-security-oauth2だけのときから修正する際の差分はこちら
https://github.com/apc-hattori/spring-oauth2-demo/compare/use-spring-security-oauth2...master