Guice WebExtensions Persist ?

正式名称がこれであっているのかよくわからないのですが、GuiceHibernateを組み合わせたものみたいです(今後はJPAもサポートするらしいです)。
http://www.wideplay.com/guicewebextensions2

Guice WebExtensions Persistの一機能であるDynamic Findersを使うとインタフェースとアノテーションだけでDAOが作れるらしいです。(検索のメソッドはDAOだけでなくエンティティにも持たせられます。これをDDDとか言っていますが、ちょっと違うような。)
http://www.wideplay.com/dynamicfinders


機能は多くないです。ざっとこんな感じ。

動かしてみました。

サービスのクラス

Hibernateと連携するトランザクションのインタセプターは用意されています。@Transactionalで使えます。

public class EmpService {
  @Inject
  EmpAccess empAccess;

  @Transactional
  public List<Emp> findAll() {
    return empAccess.findAll();
  }

  @Transactional
  public Emp findByName(String name) {
    return empAccess.findByName(name);
  }

}

DAOのインタフェース

public interface EmpAccess {

  @Finder(query = "from Emp")
  List<Emp> findAll();

  @Finder(query = "from Emp e where e.empName = :empName")
  Emp findByName(@Named("empName") String name);
}

テストコード

public class EmpAccessTest extends TestCase {
  EmpService service;

  @Override
  protected void setUp() throws Exception {
    super.setUp();
    Injector injector = Guice.createInjector(PersistenceService
        .usingHibernate().across(UnitOfWork.TRANSACTION).addAccessor(
            EmpAccess.class).buildModule(), new AbstractModule() {

      protected void configure() {
        bind(Configuration.class).toInstance(
            new AnnotationConfiguration()
                .addAnnotatedClass(Emp.class));
      }
    });
    injector.getInstance(PersistenceService.class).start();
    service = injector.getInstance(EmpService.class);
  }

  public void testFindAll() throws Exception {
    assertEquals(2, service.findAll().size());
  }

  public void testFindByName() {
    assertNotNull(service.findByName("hoge"));
  }

}

追記
取得は@Finder使えばいいとして、更新・追加・削除の処理はどすればいいんでしょうか...。インタフェースに書けないですね。EmpAccessの抽象クラスを作ってそこでSessionに直接アクセスすればいいのかなと思ったんですが、これは認めれられていないようでした。

JPA、とりあえず覚えたい5つのアノテーション

前回のエントリを見直してグループを3つに分けてみました。アルファベット順ではなく優先度順で並べています。とりあえずAグループの5つのアノテーションを覚えればJPAで簡単なサンプル(よくあるEmpとDepとか)を楽しめるはず。JPAのデフォルトのマッピング規約を最大限使用します。

  • Aグループ
    1. @Entity
    2. @Id
    3. @ManyToOne
    4. @OneToMany
    5. @PersistenceContext

次に覚えたいのがBグループの5つのアノテーション。簡単なサンプルでは使わなくてもOKなのですが実務では必須となるアノテーションです。

  • Bグループ
    1. @GeneratedValue
    2. @Version
    3. @Temporal
    4. @Enumerated
    5. @Transient

で、最後はCグループの5つのアノテーション。必須ではないですが、JPAのデフォルトのマッピング規約が使えない場合やIDを採番する戦略を自分で選択する場合に利用するアノテーションです。

  • Cグループ
    1. @Table
    2. @Column
    3. @JoinColumn
    4. @SequenceGenerator
    5. @TableGenerator