Service 層を導入する
今回作ること
UserServiceインターフェースとUserServiceImpl実装クラスを作成する- 登録ロジックを
UserControllerからUserServiceに移動する - コンストラクタインジェクションで
UserServiceをUserControllerに注入する
これまで、ユーザ登録処理はすべて UserController の中に書いていた。
今回は「Service 層」を導入し、ビジネスロジックを Controller から分離する。
なぜ Service 層が必要なのか
UserController は「HTTP リクエストを受け取り、レスポンスを返す」役割に集中すべきである。
現状のようにビジネスロジック(データの処理や保存)を Controller に書き続けると、次のような問題が起きる。
- Controller が肥大化し、どこで何をしているか分かりにくくなる
- ロジックを再利用しにくい(同じ処理を別の Controller から呼べない)
- テストが書きにくくなる
Spring では、ビジネスロジックを Service クラスに書くのが一般的な設計である。
@Service を付けたクラスは、Spring が自動的に管理し、インジェクション(注入)して使える。
1. service パッケージを作成する
src/main/java/com/example/ecsample/ 配下に service パッケージを作成する。
ecsample/
└─ src/main/java/com/example/ecsample/
├─ controller/
├─ form/
├─ entity/
└─ service/ ← 新規作成
2. UserService インターフェースを作成する
service/UserService.java を新規作成する。
package com.example.ecsample.service;
import com.example.ecsample.form.UserForm;
public interface UserService {
/**
* ユーザを登録する。
* @param form 登録フォームの入力値
*/
void register(UserForm form);
}
ポイント インターフェースを定義することで、後で実装を差し替えやすくなる。 現段階では「何ができるか」を宣言するだけで、具体的な処理は
UserServiceImplに書く。
3. UserServiceImpl 実装クラスを作成する
service/UserServiceImpl.java を新規作成する。
package com.example.ecsample.service;
import com.example.ecsample.form.UserForm;
import org.springframework.stereotype.Service;
@Service
public class UserServiceImpl implements UserService {
@Override
public void register(UserForm form) {
// 現段階ではコンソールに出力するだけ
System.out.println("ユーザ登録:" + form.getName() + " <" + form.getEmail() + ">");
}
}
ポイント
@Serviceを付けることで、Spring がこのクラスを管理するコンポーネントとして認識する。implements UserServiceにより、UserServiceインターフェースの実装であることを宣言する。- 今はコンソール出力だけだが、後の章でDB保存に置き換える。
4. UserController を修正してインジェクションする
UserController を修正し、UserService をコンストラクタインジェクションで受け取る。
コンストラクタインジェクションとは コンストラクタの引数に型を書くだけで、Spring が自動的に対応する実装クラスを探して注入してくれる。
@Autowiredアノテーションは Spring Boot 3 では省略できる。
5. 動作確認
- アプリを再起動する。
http://localhost:8080/registerにアクセスする。- フォームに値を入力して送信する。
- コンソールに
ユーザ登録:山田太郎 <taro@example.com>のように出力されれば成功。 - 画面の動作は変わっていないことを確認する(リファクタリングのため)。
ファイル構成の確認
ecsample/
└─ src/main/java/com/example/ecsample/
├─ controller/
│ ├─ HomeController.java
│ ├─ ProductController.java
│ └─ UserController.java ← 修正済み
├─ entity/
│ └─ Product.java
├─ form/
│ └─ UserForm.java
└─ service/
├─ UserService.java ← 新規作成
└─ UserServiceImpl.java ← 新規作成
Gitコミット
git add .
git commit -m "feat: UserService層を導入し、登録ロジックをControllerから分離"
次の章では、商品データをデータベース(PostgreSQL)から取得するように変更する。