Spring Data JPAでカスタムRepositoryインターフェースを実装する方法




Spring Data JPAとは

JPA(Java Persistence API)はHibernateを基盤としたSpringに最初から導入されているORMのことです。

JPAの実装には下記のように非常に多くの実装方法があり用途に合わせて実装方法を変える必要があります。

  • Criteria API
  • 名前付きクエリー:NamedQuery, NamedNaticeQueryアノテーションによる実装
  • ネイティブSQL:createNativeQueryメソッドで実装
  • メソッドの命名規則に応じたSQLを生成してくれる:シンプルなクエリはほぼこの方法で可能
  • カスタムRepositoryインターフェースを利用した実装(カスタムRepositoryインターフェースと呼ぶかは不明)

今回はカスタムRepositoryインターフェースの実装方法とそのときに気をつけないといけないことを説明します。

カスタムRepositoryインターフェースの実装方法

今回は説明の都合上、Personというエンティティを対象に実装方法の説明をします。

準備するファイル

  • PersonRepository(エンティティ名+Repository)
  • PersonRepositoryCustom(エンティティ名+Repository+Custom)
  • PersonRepositoryImp(エンティティ名+Repository+Impl)

このとき注意することとしてファイル名の規則は間違わないようにしないといけません。自分はこの規則を知らずに勝手につけていたら下記エラーになりかなりの時間を浪費してしまいました。エラーからだとなぜプロパティ名が参照できないのか全く推測できないので気をつけてください。

org.springframework.data.mapping.PropertyReferenceException

 

PersonRepository(Kotlin実装)

定義したカスタムインターフェースを継承させるだけです。

package com.sample.repository

import com.sample.entity.Person
import com.sample.repository.PersonRepositoryCustom
import org.springframework.data.jpa.repository.JpaRepository
import org.springframework.stereotype.Repository

@Repository
interface PersonRepository : JpaRepository<Person, Long>, PersonRepositoryCustom {

}

 

PersonRepositoryCustom(Kotlin実装)

実装したいメソッドを定義するだけの普通のインターフェースです。

package com.sample.repository

import com.sample.entity.Person
import java.sql.Date

interface PersonRepositoryCustom {

    fun findByGender(gender: Int): Person
}

 

PersonRepositoryImp(Kotlin実装)

カスタムインターフェースを継承してメソッドの中身を実装するだけです。

簡易的にEntityManagerFactoryのDIやcreateNativeQueryの箇所は大雑把に簡略化させていただいています。

注意点としてentityManagerのclose()を忘れないようにしてください。コネクションをずっと維持したままになってしまいます。コネクションプールの設定は下記を参照してください。

関連記事:Spring BootでHikariCPを使ってコネクションプールを設定する方法

package com.sample.repository.impl

import com.sample.entity.Person
import com.sample.repository.PersonRepositoryCustom
import org.springframework.beans.factory.annotation.Autowired
import org.springframework.beans.factory.annotation.Qualifier
import javax.persistence.EntityManager
import javax.persistence.EntityManagerFactory
import javax.persistence.Query

class PersonRepositoryImpl @Autowired constructor(@Qualifier("entityManagerFactory") val emf: EntityManagerFactory) : PersonRepositoryCustom {

    override fun findByGender(gender: Int): List<Person> {
        val sql: String = """
                            SELECT
                                id
                            FROM
                                person
                            WHERE
                                gender = :gender
                          """

        val em: EntityManager = emf.createEntityManager()
        val query: Query = em.createNativeQuery(sql, "Person")
            .setParameter("gender", gender)
        val resultList =query.getResultList() as List<Person>
        em.close()
        return resultList
    }
}

まとめ

JPAはいろんな実装方法があり混乱してしまうので初学者にとっては非常に難しく感じると思います。個人的にはこんなにいっぱい実装方法を準備している時点で微妙なフレームワークだなと感じています。

上記で紹介したエラーは下記投稿を見つけて解決できたのでもし同じような方がいたら一読するのをお勧めします。

https://stackoverflow.com/questions/20777785/org-springframework-data-mapping-propertyreferenceexception-no-property-catch-f

おすすめ書籍

JPAに関して体系的に学べる良い書籍だと思います。良くあるSpring系書籍ですとJPAは少ししか紹介がありませんが丸々一冊JPAに関してなので詳細な解説がされています。内容はJPAと他のORMとの比較から始まりセットアップ、実装の仕方まで幅広く網羅されています。これからJPAで開発を初めてみようかなと考えている方は一読することをオススメします!

Springの概要からインストール方法、各コア機能(Security, Sessionなど)の解説が体系的にまとめられています。2018年に出版されたばかりなので情報も新しいです。これからSpring Bootでアプリケーション開発をしたい方の最初に読む一冊としておすすめします。対象は初心者だけでなく上級者まで幅広く学べるので是非読んでみてください!

 

The following two tabs change content below.

髙妻智一

2013年CyberAgent新卒入社 スマホゲームを作る子会社に所属し、サーバーサイドのエンジニアを担当。2年目の終わりから新規子会社の立ち上げに参加し、サーバーサイドのエンジニアリーダーとしてサービースのリリースから運用までを担当。 2018年仮想通貨のスマホウォレットを提供するGinco Incにブロックチェーンエンジニアとして入社。






よく読まれている関連記事はこちら




コメントを残す

メールアドレスが公開されることはありません。 が付いている欄は必須項目です