SpringBoot でよく使うアノテーション

# はじめに
業務でよく使っていたアノテーションについて備忘録兼解説です。

# アノテーション
## @RestController
JSON 形式などで返却するコントローラークラスに対して付与するアノテーション。
コントローラーには、ロジックを含む処理は入れずに、サービスからレスポンスを受け取って、そのまま返却するイメージ。

```
@RestController
public class SampleController {

　@GetMapping("/")
  public SampleResponse findSampleResponse() {
...
```
似たようなやつで、@Controller は HTML 形式のレスポンスに利用される。

## @Service
サービスクラスに付与する。「サービスクラスですよー」って宣言しているみたいな感覚で使ってた。
サービスクラスでは、値をフロントエンドで扱いやすくするために、整形して Entity クラスに詰めるみたいなことをやる。
```
@Service
public class SampleService {
...
```

## @Component
DI コンテナに登録したいクラスに付与する。
よくインフラ層で利用してた。
インフラでは、API 通信を実装する。
例えば、BFF(Backend For Frontend) → BE(Backend) 間の通信。
```
@Component
@RequiredArgsConstructor
public class SampleApiClient {

 private final SampleApi sampleApi;

 public SampleApiClientResponse getApi() {
   try {
     return sampleApi.loadSample();
   } catch (RestClientException ex) {
...
```

## @Configuration
@Bean を定義するクラスに付与する。
ApiClient の設定ファイルに付与してた。（要は BE との接続のための RestTemplate 等の設定をするクラス）
```
@Configuration
public class SampleApiClientConfig {

 @Bean
 public SampleApi sampleApi() {
...
```

## @Value
Lombok の @Value（他の @Value もあるっぽいので注意）。
application.yml に設定した固定値を取得するのに利用してた。
固定値使うなら private static final 宣言して利用してもいいけど、
色々なクラスで利用したいなら yml に保管しておいた方が汎用性高まる。
```
// application.yml
hoge:
 fuga: "fuga"
```
```
// ApiClient クラス
@Component
@RequiredArgsConstructor
public class SampleApiClient {

 private final SampleApi sampleApi;

 @Value("${hoge.fuga})
 private final String fuga;

 public SampleApiClientResponse getApi() {
  return sampleApi.loadSampleApi(fuga);
```

## @Getter
getter を自動生成してくれるアノテーション。
主に DTO クラスで利用してた。
```
@Getter
@AllArgsConstructor
public class SampleDto {

 @Valid
 @NotNull
 @ApiModelProperty(value = "hoge", dataType = "object", required = true)
 private Hoge hoge;

 @Getter
 @AllArgsConstructor
 public class Hoge {

  @NotBlank
  @ApiModelProperty(value = "fuga", dataType = "string", required = true)
  private String fuga;
 }
}
```

## @AllArgsConstructor
@Getter のところで出てきたやつ。
すべてのメンバの値をセットするコンストラクタを自動生成してくれる。
省略

## @RequiredArgsConstructor
@Component で出てきたやつ。
final で宣言されたメンバの値だけをセットするコンストラクタを自動生成してくれる。
省略

## @Validated
@Valid と @Validated の違いがまだ完全にはわかってないので、参考にならないかも。
特に気にならなければ、基本 @Validated と @Valid は併用でいいと思う。
グループレベルのバリデーションをしたいときに利用する。要はクラス全体とか。
参照：https://www.baeldung.com/spring-valid-vs-validated
```
@RestController
@Validated
public class SampleController {

 @GetMapping("/")
 public SampleResponse getSample(
      @RequestParam(name = "sample") @Valid @NotBlank private String sample) {

```

## @Valid
メソッドレベル、メンバレベルでバリデーションしたいときに利用する。
@Validated にも記載あるので、省略

## @NotBlank, @NotNull, @NotEmpty
null や空チェックのバリデーションかけたいときに使うやつ。
表に記載した通りの感覚で利用してた。
array はフロントエンドで、どういう場合はエラーにするかで使い分けてた。
例：
null: 汎用エラー画面に遷移、空: 「データはありません」にして、画面自体は表示する → @NotNull
null でも空でもエラー → @NotEmpty
|アノテーション|どの型に対して使うか|
|-|-|
|@NotBlank|string|
|@NotNull|number, boolean, array, object|
|@NotEmpty|array|

## @RequestParam
リクエストパラメータを受け付けるときに使う
@Validated にも記載あるので、省略

## @ApiModelProperty
Swagger で BFF の実装吐き出して、FE で使用していたので、そのときに便利なアノテーション。
特に TypeScript 利用していると有用。
Swagger で吐き出すと、Java で必須/非必須定義してても、全部 optinal で吐き出されてしまう。（下の ? が optional）
```
// api.ts
public class SampleResponse {
 hoge?: string;
 fuga?: number;
}
```
アノテーションをつけると必須/非必須をちゃんと認識できるようになる。(required の箇所が大事)
```
// Java
@Getter
@AllArgsConstructor
public class SampleResponse {

 @NotBlank
 @ApiModelProperty(value = "hoge", dataType = "string", required = true)
 private String hoge;

 @ApiModelProperty(value = "fuga", dataType = "number")
 private Integer fuga;
```
```
// TypeScript
public class SampleResponse {
 hoge: string
 fuga?: number;
}
```