Contents
1. 公式サポート概要
| Spring Boot バージョン | サポートする JDK |
|---|---|
| 3.0 – 3.2 (パッチ) | Java 17、Java 21(※Toolchain 等で明示的に利用) |
| 3.3 以降 | Java 21(最低要件かつデフォルト) |
- Spring Boot 3.3 のリリースノートは「Minimum required JDK version is now 21」と明記しています【Spring Boot 3.3 Release Notes】。
java.versionプロパティのデフォルトが 21 に変更されたことは、同リリースノート内の「Default Java version: 21」でも確認できます。
ポイント:Java 8/11 はサポート対象外です(Spring Boot 3 系全体で非推奨)。
2. 実行環境とビルド環境の整合性を保つ理由
2.1 バージョン不一致が招く典型的な障害
| 障害例 | 発生原因 |
|---|---|
java.lang.UnsupportedClassVersionError: ... major version 65 |
ビルドは JDK 21、実行は JRE 17 以下 |
NoClassDefFoundError: jakarta/servlet/ServletException |
依存ライブラリがまだ javax 系を使用している |
| JPMS のモジュール解決失敗 | module-info.java が Jakarta EE モジュールを宣言していない |
Java 21 のバイトコードは 65.0(class file version)で、JRE 17 以前では読み込めません。したがって 開発 → CI → 本番 のすべてのステージで同一 JDK バージョンを使用することが必須です。
2.2 推奨構成
| フェーズ | 推奨設定 |
|---|---|
| ローカル IDE | Project SDK → JDK 21、JAVA_HOME を同バージョンに設定 |
| ビルドツール (Maven / Gradle) | Toolchain 機能で JDK 21 を強制 |
| Docker 本番イメージ | eclipse-temurin:21-jre などの JRE‑only イメージを使用し、コンパイル用 JDK はマルチステージビルドで分離 |
3. Maven / Gradle における Java 21 指定手順
3.1 Maven の Toolchains 設定例
|
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 |
<!-- pom.xml --> <properties> <!-- Spring Boot が期待するバージョン --> <java.version>21</java.version> </properties> <build> <plugins> <!-- Toolchains による JDK 自動選択 --> <plugin> <groupId>org.apache.maven.plugins</groupId> <artifactId>toolchains-maven-plugin</artifactId> <version>3.1.1</version> <executions> <execution> <phase>initialize</phase> <goals><goal>toolchain</goal></goals> </execution> </executions> <configuration> <toolchains> <jdk> <version>${java.version}</version> <vendor>temurin</vendor> </jdk> </toolchains> </configuration> </plugin> <!-- Spring Boot Maven Plugin(3.3.x) --> <plugin> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-maven-plugin</artifactId> <version>3.3.0</version> </plugin> </plugins> </build> |
Toolchains が有効になると、JAVA_HOME の値に関わらず Maven は必ず JDK 21 を使用します。
3.2 Gradle(Kotlin DSL)での Toolchain 設定例
|
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 |
plugins { id("org.springframework.boot") version "3.3.0" java } java { toolchain { languageVersion.set(JavaLanguageVersion.of(21)) vendor.set(JvmVendorSpec.TEMURIN) } } // コンパイルバイトコードを 21 に固定(release オプションは JDK 17 以降で推奨) tasks.withType<JavaCompile> { options.release.set(21) } |
Gradle は java.toolchain が自動的にテストタスクや実行タスクへも伝播するため、CI 環境で JDK 21 がインストールされていればローカルと同一条件が保証されます。
3.3 主要プロパティまとめ
| ツール | プロパティ/設定 | 推奨値 |
|---|---|---|
| Maven | <java.version> (POM) |
21 |
| Gradle | java.toolchain.languageVersion |
JavaLanguageVersion.of(21) |
| Spring Boot Plugin (Maven/Gradle) | バージョン 3.3.x |
- |
4. Spring Boot 2.x → 3.x 移行の必須ポイント
4.1 Jakarta EE 名前空間への置換
Spring Boot 3 系は Jakarta EE 9 に合わせて、すべての javax.* パッケージが jakarta.* に変更されました。代表的な変換表は以下です。
| 旧パッケージ | 新パッケージ |
|---|---|
javax.servlet |
jakarta.servlet |
javax.persistence |
jakarta.persistence |
javax.validation |
jakarta.validation |
実践的な置換手順
1. IDE の Replace in Path で javax. → jakarta. を一括置換。
2. pom.xml / build.gradle の依存バージョンを 3.x 系(例: spring-boot-starter-web → 3.3.0)に更新し、transitive で取得される Jakarta 対応ライブラリへ自動切り替えさせます。
3. jdeps -summary target/classes を実行し、残存する javax. 参照が無いか最終確認。
4.2 Spring Security 6 の設定刷新
WebSecurityConfigurerAdapter が削除され、代わりに SecurityFilterChain Bean が推奨されています。
|
1 2 3 4 5 6 7 8 9 |
// Spring Boot 2.x(非推奨) @EnableWebSecurity public class SecurityConfig extends WebSecurityConfigurerAdapter { @Override protected void configure(HttpSecurity http) throws Exception { http.authorizeRequests().anyRequest().authenticated(); } } |
|
1 2 3 4 5 6 7 8 9 10 11 12 13 |
// Spring Boot 3.x(標準スタイル) @Configuration public class SecurityConfig { @Bean public SecurityFilterChain securityFilterChain(HttpSecurity http) throws Exception { return http .authorizeHttpRequests(auth -> auth.anyRequest().authenticated()) .httpBasic(Customizer.withDefaults()) .build(); } } |
4.3 その他の主要変更点
| 項目 | 主な変更 | 移行時の対策 |
|---|---|---|
| Actuator エンドポイント | デフォルトベースパスは /actuator/** のみ |
management.endpoints.web.base-path を必要に応じて上書き |
| WebMvc のハンドラ引数 | HandlerMethodArgumentResolver が Jakarta 系へ |
インポート文を jakarta.* に置換 |
| ConfigurationProperties バインディング | アノテーションが jakarta.validation.constraints.* へ移行 |
@Validated と併せて jakarta.validation のアノテーションを使用 |
4.4 移行支援ツール
- Spring Initializr(https://start.spring.io/)で同一依存構成の Spring Boot 3 プロジェクトを生成し、差分比較に利用。
jdepsコマンドで残りのjavax.参照を検出:
bash
jdeps --module-path target/classes -summary target/classes | grep javax
5. テスト・CI/CD における Java 21 の組み込み
5.1 Maven Surefire と Toolchain の連携例
|
1 2 3 4 5 6 7 8 9 10 |
<plugin> <groupId>org.apache.maven.plugins</groupId> <artifactId>maven-surefire-plugin</artifactId> <version>3.1.2</version> <configuration> <!-- Toolchains が提供する JDK を使用 --> <useSystemClassLoader>false</useSystemClassLoader> </configuration> </plugin> |
Toolchain が有効な状態であれば、surefire は自動的に JDK 21 へ切り替わります。
5.2 Gradle テストタスク(Kotlin DSL)
|
1 2 3 4 |
tasks.test { useJUnitPlatform() } |
Gradle の java.toolchain 設定が継承され、テストも同一 JDK 21 で実行されます。
6. CI パイプライン例
6.1 GitHub Actions
|
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 |
name: Build & Test (Java 21) on: push: pull_request: jobs: build: runs-on: ubuntu-latest steps: - uses: actions/checkout@v4 - name: Set up JDK 21 uses: actions/setup-java@v3 with: distribution: temurin java-version: '21' cache: maven # Maven 用キャッシュを有効化 - name: Build & Verify run: ./mvnw verify |
6.2 Jenkins(Declarative Pipeline)
|
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 |
pipeline { agent any tools { jdk 'jdk-21' } // 管理画面で登録した JDK 名称 stages { stage('Compile') { steps { sh './mvnw clean compile -DskipTests' } } stage('Test') { steps { sh './mvnw test' } } stage('Package') { steps { sh './mvnw package -DskipTests' } } } } |
ポイント:Jenkins の「Global Tool Configuration」で jdk-21 を登録し、Maven/Gradle の Toolchain と合わせて使用するとローカルと完全に同一環境が保証されます。
7. よくあるエラーと対策(Q&A)
| 質問 | 現象 | 原因 | 解決策 |
|---|---|---|---|
java.lang.UnsupportedClassVersionError: major version 65 |
アプリ起動時に例外 | 実行 JRE が 21 未満 | 本番コンテナを *-jre:21 系イメージへ差し替える |
NoClassDefFoundError: jakarta/servlet/ServletException |
Spring 起動直後に失敗 | 依存ライブラリが javax.* のまま |
すべての spring-boot-starter-* と外部ライブラリを 3.3.x に更新 |
| JPMS のモジュール解決エラー | module-info.java が不足 |
Jakarta EE モジュールを requires していない |
requires jakarta.servlet; 等の宣言を追加し、java --add-modules=... オプションで補完 |
仮想スレッド使用時に IllegalStateException: Cannot create a virtual thread |
Thread.startVirtualThread(...) が失敗 |
JDK 21 のプレビューオプションが無効(古い JDK) | 実行環境を JDK 21.0.2+ に統一し、-Djdk.virtualThreadScheduler=... を付与 |
8. Java 21 新機能の活用ヒント(任意)
| 機能 | 主な利点 | Spring Boot での利用例 |
|---|---|---|
| 仮想スレッド (Project Loom) | 数十万規模の軽量スレッドでブロッキング I/O を非同期化 | Executors.newVirtualThreadPerTaskExecutor() → TaskExecutor に登録し、@Async と組み合わせる |
| CRaC(Coordinated Restore at Checkpoint) | アプリ起動時間を数秒に短縮できるチェックポイント復元機能 | spring-boot-maven-plugin の build-image ゴールで --crac フラグを付与し、GraalVM Native Image と併用 |
注意:仮想スレッドは JDK 21.0.2 以降で正式に有効です。CRaC は OS のサポートが必要(例: Ubuntu 22.04+)なので、本番環境の要件を事前に確認してください。
9. 参考リンク(Markdown 統一)
- Spring Boot 3.3 Release Notes
- Spring Boot と Java 21 の対応状況 – アプリの達人
- Maven Toolchains Plugin 公式ドキュメント
- Gradle Java Toolchains ガイド
- Jakarta EE 9 移行ガイド (Oracle)
- Spring Initializr
まとめ
- 公式サポートは Spring Boot 3.3 以降で Java 21 が最低要件です。
- Toolchain を用いることで、IDE・ローカル・CI・本番すべてのステージで JDK 21 が統一されます。
- 移行時は Jakarta EE への名前空間変更 と Spring Security 6 の設定刷新 に注意し、
jdepsで残存参照を検出してください。 - CI/CD(GitHub Actions / Jenkins)と Docker マルチステージビルドを組み合わせれば、実行時に JDK が混入するリスクはゼロになります。
上記手順を踏めば、安全かつスムーズに Spring Boot と Java 21 の統合が完了し、最新の仮想スレッドや CRaC などの先進機能も活用できるようになります。 Happy coding!