3

私はDDDとJPAにかなり慣れていません。

私はJPAとSpringを使用して汎用リポジトリに取り組んでいます。DDD:ジェネリックリポジトリJPA実装パターン:データアクセスオブジェクトの記事で公開されているアプローチが本当に好きです。私の目的は、JPAとSpringを使用してドメイン駆動設計で完璧なリポジトリを構築することです。

最初の記事の概念に従って、内部の汎用リポジトリを使用して、データストアとのドメインの契約を尊重します。

public interface IInternalGenericRepository<K, E> {
    List<E> read(String query, Object[] params);
    void persist(E entity);
    void remove(E entity);
}

public class InternalGenericRepository<K, E> implements IInternalGenericRepository<K, E> {

    // Injected through DI in Spring
    @PersistenceContext
    private EntityManager em;

    private final Class<E> entityClass;

    public List<E> read(String query, Object[] params) {
        Query q = em.createQuery(query);
        for (int i = 0; i < params.length; i++) {
            q.setParameter(i + 1, params[i]);
        }
        return q.getResultList();
    }

    public void persist(E entity) {
        em.persist(entity);
    }

    // ...
}

次に、特定のエンティティ(例:組織)のリポジトリは次のようになります。

public interface IOrganizationRepository {
    List<Organization> organizationByCityName(String city);

    void create(Organization o);
}


@Repository
public class OrganizationRepository implements IOrganizationRepository {

    @Autowired
    IInternalGenericRepository<Long, Organization> internalRepository;

    public List<Organization> organizationByCityName(String city) {
        Object[] params = new Object[1];
        params[0] = city;
        return internalRepository.read("select o from Organization o where o.city.name like ?1",
                params);
    }

    @Override
    public void create(Organization o) {
        internalRepository.persist(o);
    }
}

これは、JPAとSpringを使用してDDDリポジトリーを実装するための良い方法のように見えます。次に、OrganizationRepositoryがサービスレイヤーに挿入されます。

欠陥や誤解を避けるために、外部の意見を持ちたいです。あなたはどう思いますか、そしてそれをどのように改善することができますか?

ありがとう。


編集:

  • @AutowiredoninternalRepository-指摘してくれたaxtavtに感謝します。
  • read()を改善できます
4

1 に答える 1

1

まず第一に、Spring は でEntityManager作成された内部オブジェクトに注入できないため、機能しませんnew。したがって、次のように書く必要があります。

public class OrganizationRepository implements IOrganizationRepository { 

    @PersistenceContext
    public void setEntityManager(EntityManager em) {
        internalRepository.em = em;
    }
    ...
}

また、あなたのread方法は少し一般的すぎます。getSigleResultsetFirstResult/など、いくつかの重要な使用例がありませんsetMaxResults

個人的には、2 番目の記事のアプローチを好みます。なぜなら、コンポジションを使用すると、.NET に欠けている機能を実装するEntityManager必要が生じるからです。OrganizationRepositoryIInternalGenericRepository

于 2010-02-10T20:05:38.987 に答える