S2Hibernate-JPA を使ってみる
Hibernate 上での JPA の使用を更に簡単に実施する事ができる S2Hibernate-JPA を使ってみた。
クラスパスへの設定
以下の JAR ファイルをクラスパスに設定する。
- Seasar2 の lib ディレクトリ内の全 JAR ファイル
- S2Tiger の lib ディレクトリ内の全 JAR ファイル
- S2Hibernate JPA の lib ディレクトリ内の全 JAR ファイル
dicon ファイルの準備
以下のファイルをクラスパスに設定されているディレクトリにコピーする。
Entity や Dao の作成
JPA のアノテーションを使用して Entity を作成する。
Dept.java
package aaa.entity; import javax.persistence.*; @Entity public class Dept { @Id @GeneratedValue private long id; @Column(name = "DEPT_NO") private Integer deptNo; @Column(name = "DEPT_NAME") private String deptName; private String loc; //・・・アクセサメソッドの実装(記述を省略) ・・・ }
Dao のインターフェースを作成する。
DeptDao.java
package aaa.dao; import aaa.entity.*; public interface DeptDao { Dept find(long id); long add(String name); }
次に、Dao の実装クラスを作成する。
通常は、サービスクラスの実装クラスに @Stateless アノテーションを付与する事になるだろうが、今回は簡単に実装するために Dao の実装クラスに @Stateless アノテーションを付ける事にした。
@Stateless アノテーションの付与により、メソッドの実行がトランザクション内で実施されるようになる。
DeptDaoImpl.java
package aaa.dao; import javax.ejb.*; import javax.persistence.*; import aaa.entity.Dept; @Stateless public class DeptDaoImpl implements DeptDao { @PersistenceContext private EntityManager entityManager; public Dept find(long id) { return entityManager.find(Dept.class, id); } public long add(String name) { Dept dept = new Dept(); dept.setDeptName(name); entityManager.persist(dept); return dept.getId(); } }
テスト用の実行クラス作成
Entity と Dao をテストするための実行クラスを作成する。
Seasar2 には、JUnit 用のテストクラスを作成するために org.seasar.extension.unit.S2TestCase が用意されており、通常はこのクラスを継承するクラスを作成する事でユニットテストが作成できるが、今回は普通の実行クラスでテストを実装する事にした。
Test.java
package test; import javax.persistence.*; import org.seasar.framework.container.*; import org.seasar.framework.container.factory.*; import aaa.dao.*; import aaa.entity.*; public class Test { public static void main(String[] args) { SingletonS2ContainerFactory.init(); DeptDao dao = (DeptDao)SingletonS2Container.getComponent("dao"); long id = dao.add("テストデータ"); System.out.println(id); Dept dept = dao.find(id); System.out.println(dept.getDeptName()); } }
dicon ファイルの追加と編集
SingletonS2Container がデフォルトで読み込む app.dicon ファイルを「dicon ファイルの準備」のコピー先に以下のように作成する。javaee5.dicon と jpa.dicon の include は決まり事になっている模様。
app.dicon
<?xml version="1.0" encoding="UTF-8"?> <!DOCTYPE components PUBLIC "-//SEASAR//DTD S2Container 2.4//EN" "http://www.seasar.org/dtd/components24.dtd"> <components> <include path="javaee5.dicon"/> <include path="jpa.dicon"/> <component name="dao" class="aaa.dao.DeptDaoImpl"/> </components>
jdbc.dicon ファイルを編集し、JDBC ドライバークラスや URL の設定を行い、META-INF/persistence.xml ファイルを必要に応じて編集する。
今回は HSQLDB を使用したため、jdbc.dicon と META-INF/persistence.xml を以下のように変更した。
jdbc.dicon
<?xml version="1.0" encoding="UTF-8"?> <!DOCTYPE components PUBLIC "-//SEASAR2.1//DTD S2Container//EN" "http://www.seasar.org/dtd/components21.dtd"> <components namespace="jdbc"> <include path="jta.dicon"/> <include path="jdbc-extension.dicon"/> ・・・ <!-- for HSQLDB --> <component name="xaDataSource" class="org.seasar.extension.dbcp.impl.XADataSourceImpl"> <property name="driverClassName">"org.hsqldb.jdbcDriver"</property> <property name="URL">"jdbc:hsqldb:./data/test1"</property> <property name="user">"sa"</property> <property name="password">""</property> </component> ・・・ </component>
META-INF/persistence.xml
<?xml version="1.0" encoding="UTF-8"?> <persistence xmlns="http://java.sun.com/xml/ns/persistence" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://java.sun.com/xml/ns/persistence http://java.sun.com/xml/ns/persistence/persistence_1_0.xsd" version="1.0"> <persistence-unit name="persistenceUnit" transaction-type="JTA"> <provider>org.hibernate.ejb.HibernatePersistence</provider> <jta-data-source>jdbc/dataSource</jta-data-source> <properties> <property name="hibernate.dialect" value="org.hibernate.dialect.HSQLDialect"/> <property name="hibernate.jndi.class" value="org.seasar.extension.j2ee.JndiContextFactory" /> <property name="hibernate.transaction.manager_lookup_class" value="org.seasar.hibernate.jpa.transaction.SingletonTransactionManagerProxyLookup" /> <property name="hibernate.show_sql" value="true"/> <property name="hibernate.format_sql" value="true"/> <property name="hibernate.use_sql_comments" value="false"/> <property name="hibernate.hbm2ddl.auto" value="update" /> </properties> </persistence-unit> </persistence>