IntelliJ IDEA で Spring Boot をはじめてみるよ
IntelliJ IDEA で Spring Boot をはじめる手順を説明します。
IntelliJ IDEA は用意されている前提で、 Spring Boot のプロジェクトを用意し、起動し、簡単な RESTful API アプリを作成して稼働確認を行うところまで書いています。
プロジェクトの用意と起動確認
それでは、SpringBoot のプロジェクトを用意し、稼働確認するところまで実施します。プロジェクトは雛形があるのでそれを利用する前提として説明します。
手順
Spring Initializr という Spring 公式のプロジェクトの雛形を生成するツールがあります。2020年現在であれば、これを利用してプロジェクトを生成し、その後 IntelliJ IDEA に取り込む(インポートする)のが良いでしょう。
ということで、以下の手順になります。
Spring Initializr の公式サイト(https://start.spring.io/)へアクセス!
欲しいプロジェクトの情報を入力し、ダウンロード!
- IntelliJ IDEA でインポート!
- 必要な設定をちょっとする!
- 試しに実行してみる!
以下に説明をしていきます。
Spring Initializr でプロジェクト生成
前述の手順にある通り、まずは下記の公式サイトへアクセスします。
各種情報を入力するフォームが表示されます。ここでは大きく3つの情報を入力します。
- 環境の情報
- 自身の作成するプロジェクトの情報
- 利用ライブラリ(Dependencies)
環境の情報
利用する環境に合わせた情報を入力します。デプロイ先の環境や、開発する環境に合わせ、任意で好きなものをチョイスすればOKです。
今回の例では、下線太字を入力しています。
入力欄 | 入力例(下線太字を選択) | 意味 |
---|---|---|
Project |
Maven / Gradle | ビルドツールの選択です。 |
Language |
Java / Kotlin / Groovy | 言語の選択です。 |
Spring Boot |
2.3.2 | デフォルトチェックは最新安定版です。 |
Packaging |
Jar / War | ビルド後のファイル形式の選択です。 |
Java |
11 |
Spring Boot
のバージョン番号は、通常はデフォルトでチェックされているもので良いと思います。これが安定版になります。
Packaging
は Jar を選んで良いと思います。これにするとAPサーバも含めたパッケージングがされ、Jar を起動するだけでアプリがAPサーバごと動くようになります。もし、すでにAPサーバ(TomcatやWebLogicなど)が存在してそこにデプロイするのであれば War を選びます。
Java
のバージョンは動かすサーバの環境に合わせます。
自身の作成するプロジェクトの情報
自分が作るプロジェクトの命名をする項目です。好きな名前を入力してください。
入力欄 | 入力例 | 意味 |
---|---|---|
Group |
edu.self |
プロジェクトを一意に識別する名前。 プロジェクトのルートパッケージ名を指定するのが一般的です。 |
Artifact |
sample-spring-boot |
プロジェクトの成果物の名前。 作成する JAR や WAR, EAR ファイルなどの名前に使用されます。 |
Name |
(※自動入力)sample-spring-boot |
Artifact と同じモノが入ります。(違う名前を入れることもできるが推奨しないということで割愛。) |
Description |
Sample project for Spring Boot |
プロジェクトの説明です。とりあえず適当で良いでしょう。 |
Package name |
(※自動入力)edu.self.sample-spring-boot |
Group + Artifact が入ります。 |
自動入力される部分はそのまま自動入力されるままにしておくのが推奨です。
edu.self
は、自分の勉強用に作ってるよ、くらいのニュアンスです。自分のドメインを持っている人はそれを使えばよいと思います。
利用ライブラリ(Dependencies)
とりあえず、RESTful API が動けばOKということで以下を選択しましょう。
- Spring Web
以下もとりあえず選んでおきましょう。まあ好みなのでなくても大丈夫です。
- Spring Boot DevTools
- Lombok
生成内容を確認してダウンロード!
この後「GENERATE」ボタンをクリックすると、プロジェクト一式がZIPファイルでダウンロードできます。
その前に「EXPLORE」ボタンをクリックすると生成されるファイルを確認することができます。左側にプロジェクトのツリーが表示され、build.gradle
が選択されれいます。今回例示した選択や入力をしていると、 build.gradle
は以下のようになっているはずです。
plugins { id 'org.springframework.boot' version '2.3.2.RELEASE' id 'io.spring.dependency-management' version '1.0.9.RELEASE' id 'java' } group = 'edu.self' version = '0.0.1-SNAPSHOT' sourceCompatibility = '11' configurations { compileOnly { extendsFrom annotationProcessor } } repositories { mavenCentral() } dependencies { implementation 'org.springframework.boot:spring-boot-starter-web' compileOnly 'org.projectlombok:lombok' developmentOnly 'org.springframework.boot:spring-boot-devtools' annotationProcessor 'org.projectlombok:lombok' testImplementation('org.springframework.boot:spring-boot-starter-test') { exclude group: 'org.junit.vintage', module: 'junit-vintage-engine' } } test { useJUnitPlatform() }
では、「DOWNLOAD」をクリックしてダウンロードをしましょう。
IntelliJ IDEA にインポート
ダウンロードした zip ファイルを解凍し、任意の場所に置きます。
IntelliJ IDEA を起動し、「File」>「Open」で、この解凍したフォルダを選択します。
試しに起動
Gradle でビルドしますので、Gradleから操作します。「View」>「Tool Window」>「Gradle」をすると、ウインドウ右側のタブの「Gradle」が開きます。
続いて、この中の「Tasks」>「application」>「bootRun」をダブルクリックします。(右クリックで「Run ...」を選んでもOKです。)
すると、ウィンドウ下半分にコンソールが開きます。ここで Started SampleSpringBootApplication in 1.962 seconds (JVM running for 2.454)
が表示されたら起動完了です。8080
ポートが開いている(その数行前に Tomcat started on port(s): 8080 (http) with context path ''
と表示されている)ので、以下のURLにアクセスします。
すると、「Whitelabel Error Page」というページが表示されます。まだ何も実装していないのでエラーページが表示されてはいますが、起動していることの確認はこれでOKです。
再起動と停止
ウィンドウ下半分のコンソールの左側に、縦に ↪
■
っぽいアイコンが並んでいると思います。ここからは起動中のアプリを、 ↪
で再起動、 ■
で停止することができます。
二度目以降の起動
一度起動をすると、右上に以下のように表示されると思います。
「sample-spring-boot[bootRun]] ▶
虫
...
▶
が起動で 虫
がデバッグモードでの起動です。以降はこのボタン一つで操作ができます。
簡単な表示確認
アプリケーションを何も作っていないのでエラーページが表示されてしまっています。次に、簡単な文字が表示されるよう実装してみましょう。シンプルすぎるものを作りたいので、ブラウザの画面上に Hello SpringBoot!!!
とだけ表示されたらOKとします。
シンプルなコントローラの実装
エントリーポイントの確認
パッケージの edu.self.samplespringboot
に SampleSpringBootApplication
というクラスがすでに作成されています。
(※Spring Initializr で Group
に edu.self
を、 Artifact
に sample-spring-boot
を入力したのでこのようなパッケージ名とクラス名なっています。先程の入力内容はこういう部分に影響してきます。)
このクラスは SpringBoot のエントリーポイントとなります。つまり、このプロジェクトが起動するスタート地点がココ。ココからコントローラやサービスが動きます。
コントローラの作成
このクラスとは別に、ブラウザに簡単た文字表示するアプリを作ってみましょう。同一パッケージに置いて大丈夫です。
- パッケージ名(IntelliJ IDEA の左ペインのツリー部)の
edu.self.samplespringboot
を右クリック - 「New」>「Java Class」を選択
- 「Class」を選択し、
IndexController
を入力し、Enterを押す
以下のクラスが作成されました。
package edu.self.samplespringboot; public class IndexController { }
コントローラの編集
こちらを以下のように編集します。コメントは説明上のものですので入力不要です。
(※上記のファイルに1, 2, 3 の順番で手動で(コピペではない)追記してください。アノテーションなどがサジェストされ、全部入力しなくても済むことが分かると思います。また import
文も自動で挿入されます。)
package edu.self.samplespringboot; import org.springframework.web.bind.annotation.RequestMapping; import org.springframework.web.bind.annotation.RestController; @RestController // 1.RESTful API のアプリのリクエストを受け付けるクラスであることの指定 public class IndexController { @RequestMapping("/") // 3.URLのパスの指定 // 2.文字列を返すだけのメソッドを作成 public String index() { return "Hello SpringBoot!!!"; } }
再起動
アプリケーションを再起動します。(ウィンドウ下半分のコンソールの左側の ↪
っぽいアイコンをクリックで再起動します。)それが完了してから( Started SampleSpringBootApplication in 1.962 seconds (JVM running for 2.454)
が表示されてから)再度以下のURLにアクセスします。
今度は以下のように表示されるでしょう。
Hello SpringBoot!!!
これでOKです!
実は、 @RequestMapping()
の中に書いた "/"
が対象のURLになります。もしここに @RequestMapping("hoge")
と書いていたらアクセス先は http://localhost:8080/hoge となります。余裕があれば試してみてください。
簡単なリファクタリング
SampleSpringBootApplication
と同じ階層に置いてしまうのも乱暴かと思いますので、簡単にパッケージを作って移動をして終わりにします。
パッケージの作成
以下の2つのパッケージを作ります。
- パッケージ名(IntelliJ IDEA の左ペインのツリー部)の
edu.self.samplespringboot
を右クリック - 「New」>「Package」を選択
- 以下を入力し、Enterを押す(※
edu.self.samplespringboot.
は初期入力されています)edu.self.samplespringboot.controller
edu.self.samplespringboot.service
パッケージの移動
先程作成した IndexController
を移動します。
- クラス名(IntelliJ IDEA の左ペインのツリー部)の
IndexController
を右クリック - 「Refactor」>「Move Class」を選択
- 「To package」に
edu.self.samplespringboot.controller
を入力し、「Refactor」ボタンを押す
これでクラスが移動されました。
サービスクラスの作成
サービスクラスというものも作成してみます。画面に表示する文字列を返却する機能を持ったクラスです。
- パッケージ名(IntelliJ IDEA の左ペインのツリー部)の
edu.self.samplespringboot.service
を右クリック - 「New」>「Java Class」を選択
- 「Class」を選択し、
IndexService
を入力し、Enterを押す
以下のような内容にします。
package edu.self.samplespringboot.service; import org.springframework.stereotype.Service; @Service public class IndexService { public String getIndexString() { return "Hello SpringBoot from Service Class."; } }
これに伴い、 IndexController
の内容を IndexService
を利用するように変更します。
// 前略 @RestController public class IndexController { // 追加 @Autowired IndexService indexService; @RequestMapping("/") public String index() { // 変更 // return "Hello SpringBoot!!!"; return indexService.getIndexString(); } }
この IndexService
の使い方についてはこの記事の最後の方に説明を記載します。一旦次に進みます。
再起動
もう一度アプリケーションを再起動して稼働確認します。再起動後、再度以下のURLにアクセスします。
今度は以下のように表示されるでしょう。
Hello SpringBoot from Service Class.
これでOKです!
エントリーポイントとパッケージのおまけの話
エントリーポイントのアノテーション
さて、SpringBoot のエントリーポイントとなるのは自動生成された SampleSpringBootApplication
クラスです。 main
メソッドがあり、サーバー起動後はこのクラスが動くんだと思ってOKです。
このクラスには @SpringBootApplication
というアノテーションがついています。これは @Configuration
, @EnableAutoConfiguration
and @ComponentScan
というよく使われるアノテーションがまとめられたものです。
- 参考 : Using Spring Boot
雑な説明になりますが「色々設定しておくよ。コンポーネントを探して使えるようにしておくよ。」という内容です。この「コンポーネント」という部分が、 @RestController
や @Service
というアノテーションがついたクラスを指します。それらを「探して」「使えるように(=インスタンス化)」しておくのが Spring の機能になります。
Spring の動く順序
流れとしては以下のようになっています。
SampleSpringBootApplication
クラスが最初に動く。@SpringBootApplication
(@ComponentScan
が含まれる)アノテーションがあるので@RestController
や@Service
というアノテーションがついたクラスを探す。- 自分で作成した
IndexController
とIndexService
が見つかる。 - 見つかったこれらのクラスは Spring がインスタンス化していつでも使えるようによしなにやってくれる。
- 特に
IndexController
は@RestController
が付いている。このコントローラの@RequestMapping
が付いているメソッドには、ブラウザから(HTTPから)アクセスできるようにしておく。
最初の 1. は自動生成されたクラスの話。2. は Spring の機能。3. が自分らが作ったクラス。4.と5.は Spring の機能。となります。自分らと Spring とで分担作業をしていた訳です。
Spring を使った開発の進め方
Spring を使った開発では、「このように Spring が動くのだ」ということを知った上で、3. のようなクラスを作っていくことになります。その他の動きの部分は作成する必要はありません。
逆に、作らなくて良い部分が分かりにくいため、何をやればいいんだか分かりにくくなりがちなのが Spring の開発です。 Spring がやってくれる部分を一つひとつ押さえて上手く Spring と付き合って行きましょう。すると便利な部分が見えてきて、楽できることが実感できると思います。
コントローラとサービスのおまけの話
サンプルでは、コントローラとサービスを分割しました。それぞれのクラスには何が書かれているでしょうか。
- コントローラにある機能は
@RequestMapping("/")
くらいです。 - サービスにある機能は
return "Hello SpringBoot from Service Class";
くらいです。
今回のサンプルは機能が少ないためピンと来ないかも知れませんが、以下のようなニュアンスでクラスを分割していました。
コントローラ : ブラウザなどからのアクセス制御(何を受け付けて何を返すか?)とサービスの呼び出し
サービス : 詳細なロジック(DBを検索したり、検索結果を編集したりする)
複雑な処理になると、コントローラに膨大な処理を書くことになり見通しが悪くなります。なのでヤリタイコトを整理して分割します。
Spring では最初から @RestController
や @Service
というアノテーションが存在します。上記のように分割することが想定されています。なので、その考えに則り、クラスを分けてみたという訳です。
他にも、Repository, Entity, Form, Validator などなど、必要に応じてクラスを分けて開発を進めることになります。