JPA のエンティティクラスに必要なデフォルトコンストラクタは直接記述する

JPA のエンティティクラスにデフォルトコンストラクタとして Lombok@NoArgsConstructorを利用すると開発の邪魔になる問題が発生するので使わないほうがいい。

@Entity
@Table(name = "staff")
@Data
@AllArgsConstructor
@NoArgsConstructor(onConstructor = @__(@PersistenceConstructor))
@With
public class StaffEntity implements Serializable {

    private static final long serialVersionUID = 1374L;

IntelliJ IDEA ではこういう見た目になる。 (ちょっとわかりにくいけど L19 の @__コンパイルエラーになっているため赤字になっている)

あらゆる場所でエラーの存在が喧伝される状態になるため、本当に問題がある場所が分からなくなってしまう。 なので、デフォルトコンストラクタだけは直接記述したほうがいい。

f:id:yujiorama:20201018141701p:plain

詳細

JPA のエンティティクラスには引数無しコンストラクタが必要。

ただ、Spring Data を使ってる場合は @PersistenceConstructor で指定したコンストラクタを利用することもできる。 面倒なので一致させておくけど。

Lombok@NoArgsConstructor を利用すると簡単にデフォルトコンストラクタを生成できる。 生成したコンストラクタに @PersistenceConstructor を指定するには onX 機能を利用する。

@__ は、括弧の中身をコンパイラに解釈させず注釈プロセッサで処理することを指示するための特別な記法。 要するに @__(@xxx) と記述したら Lombok の生成したコードに @xxx を指定することになる。 しかし IDEA の構文チェッカ―は @__ を解釈できないので見た目上はコンパイルエラーになってしまう。

@__ の代替記述として属性名を onConstructor_ とする方法もあるけど、やはり IDE の構文チェッカ―には解釈できないためコンパイルエラーになる。

こちらの方法は左辺値が確定しないため、右辺値を入力するときにコード補完が効かなくなる。つまり @__ を使う場合より都合が悪い。 したがって、こちらの方法を採用するわけにいかないので、結局直接記述するのが一番だという結論になる。

リンク

Lombok : onX

PersistenceConstructor (Spring Data Core 2.3.4.RELEASE API)

Jakarta Persistence