2019年8月21日

テスト書いてますか?私は好きです!嫌いな人は多いみたいですけど...

Springのテスト部分のリファレンス読んで忘れないうちにまとめよう精神が働いたので書きます。 今回は、@DataJpaTestというレポジトリのテストを書くためのアノテーションを紹介します。

@DataJpaTestアノテーションは、デフォルトでインメモリDBの設定をしたり、@EntityがついたクラスをBean登録したり、@RepositoryついたクラスをBean登録するなどSpring Data JPAレポジトリの設定してくれたりします。 @DataJpaTestのソースコードをのぞいてみるとこんな感じの設定が行われているようです。

...
@AutoConfigureDataJpa
@AutoConfigureTestDatabase
@AutoConfigureTestEntityManager
...

Data JPAテストは、トランザクショナルで各テストの終わりにロールバックします。 もし、こうしたくない場合は、次のように書いてください。

@Transactional(propagation = Propagation.NOT_SUPPORTED)

また、data JPAテストでは、標準的なJPA EntityManagerの代わりにTestEntityManagerのBeanがインジェクトされます。

ソースコード

GitHub

pom.xml

<dependencies>
    <dependency>
        <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-data-jpa</artifactId>
    </dependency>
    <dependency>
    <groupId>com.h2database</groupId>
    <artifactId>h2</artifactId>
    <scope>runtime</scope>
    </dependency>
    <dependency>
        <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-test</artifactId>
    <scope>test</scope>
    <exclusions>
        <exclusion>
        <groupId>junit</groupId>
        <artifactId>junit</artifactId>
        </exclusion>
        </exclusions>
    </dependency>
    <dependency>
        <groupId>org.junit.platform</groupId>
    <artifactId>junit-platform-launcher</artifactId>
    <version>1.2.0</version>
    <scope>test</scope>
    </dependency>
    <dependency>
        <groupId>org.junit.jupiter</groupId>
    <artifactId>junit-jupiter-engine</artifactId>
    <version>5.2.0</version>
    <scope>test</scope>
    </dependency>

    <dependency>
        <groupId>org.junit.jupiter</groupId>
    <artifactId>junit-jupiter-params</artifactId>
    <version>1.2.0</version>
    <scope>test</scope>
    </dependency>
</dependencies>

Brand.java

@Entity
public class Brand implements Serializable {
    enum Gender {
        MAN, WOMAN, UNISEX
    }
    @Id
    @GeneratedValue(strategy = GenerationType.AUTO)
    private Integer id;
    @Column(nullable = false)
    private String name;
    @Enumerated(EnumType.STRING)
    private Gender gender;
    public Brand(String name, Gender gender) {
        this.name = name;
        this.gender = gender;
    }
    ... getter, setter
}

id、ブランド名、ブランドの対象性別をもつBrandエンティティで話を進めていきます。

BrandRepository.java(今回のテスト対象)

Powered by Fruition