Fight the Future

Java言語とJVM、そしてJavaエコシステム全般にまつわること

JPAでエンティティ以外のクラスにクエリの結果をマッピングする in Hibernate

JPAでそもそもそういう使い方するなよってことかもしれませんが。 ネイティブクエリを発行してその結果をエンティティ以外のクラスのインスタンスマッピングしたいことがあるとします。 JPAの実装にHibernateを使っているときは、以下のコードで実現できます。

javax.persistence.Query q = JPA.em().createNativeQuery("select empno, ename from emp where job = :job").setParameter("job", "SALESMAN");
org.hibernate.Query hibernateQuery = ((HibernateQuery)q).getHibernateQuery();
List<Emp> resultList = hibernateQuery.setResultTransformer(org.hibernate.transform.Transformers.aliasToBean(Emp.class)).list();

実際はSQLがこんなに簡単だったらこの機能使わないでしょうけど、たくさん結合するとかそんなとき。

いったんJPAのQueryをHibernateQueryにキャストして、内部的に保持しているQueryを取り出します。org.hibernate.QueryにはsetResultTransformer()というメソッドがあり、これを使うと任意のマッピングが実現できます。SQL文の実行結果をクラスのプロパティに単純にマッピングするときは、Transformers.aliasToBean(Class)を使うだけで済みます。