2013-07-03 22 views
6

これは私が現在持っているアーキテクチャの問題です。私はプロジェクトにEJBとJPAを統合するベストプラクティスに関して助けが必要です。自分のアプリケーションのビジネスロジックを含むサービスレイヤの仕事をするEJBを用意したいと思います。そのすぐ下に、DAOレイヤを用意して、EJBがDAOファクトリを使用して2つのレイヤを可能な限り分離するハンドルを持つようにしたいと考えています。それを知って、私は明らかに私は工場で作成されたいので、私はそれらを自動的に注入したくないので、EJBとして私のDAOを作ることができません。それはJPAと分離されたDAOとサービス層を持つEJBを使用する

Persistence.createEntityManagerFactory("PortalEJB").createEntityManager(); 

を使用して手動でEntityManagerを作成するために私をリードさて...このコールは私の抽象JPA DAOに位置しています:

public abstract class JPADataAccessorObject<K, E> implements DataAccessorObject<K, E> { 
    protected Class<E> entityClass; 

    protected EntityManager entityManager; 

    protected JPADataAccessorObject(Class<E> pEntityClass) { 
     this.entityManager = Persistence.createEntityManagerFactory("PortalEJB").createEntityManager(); 
     this.entityClass = pEntityClass; 
    } 

    /* Other DAO functions (update, delete, create) */ 
} 

私はこれが悪いだと思う、それはないですか?このクラスのすべての具体的なエクステントは、永続コンテキストの新しいコピーを持ち、私は奇妙な動作をします。また、私がそれをするとき、私はと思う私はサービス層で自分自身でトランザクションを管理する必要があります。

  • (いずれかの例外が発生した場合にトランザクションをロールバック)
  • 任意のサービス層の機能/手順の前には、任意のサービス層の機能の後にトランザクションをコミット

    • トランザクションを作成します。私のような何かが、そのために側面を作成しようとしていましただからここに/手順

    私の質問は以下のとおりです。

    • 私はmanag必要がありますどのようにEntityManager?
    • マルチスレッドから保護された1つのコピーを管理するJPAユーティリティー・クラスを用意する必要がありますか?
    • 私が間違いを犯している場合は、ベストプラクティスを提供してください。
    +0

    Java EEのどのバージョンですか? –

    +0

    GlassFish 3.1でEJB 3.1、Java 1.6、JPA 2.0(EclipseLink)を使用しています –

    答えて

    5

    Adam Bien JPA/EJB3 KILLED THE DAODAOS AREN'T DEAD - BUT THEY EITHER COLLAPSED OR DISAPPEAREDの投稿を見ましたか?別の手で

    、あなたはサービス層のための抽象クラスを考えることができます。

    public abstract class AbstractFacade<E extends Serializable, 
                PK extends Serializable> { 
    
        private final transient Class<E> entityClass; 
    
        public AbstractFacade(final Class<E> entityClass) { 
         this.entityClass = entityClass; 
        } 
    
        protected abstract EntityManager getEntityManager(); 
    
        public void create(final E entity) { 
         final EntityManager entityManager = getEntityManager(); 
         entityManager.persist(entity); 
        } 
    
        public final E find(final PK id) { 
         return getEntityManager().find(entityClass, id); 
        } 
    
        // Other common operations 
    
    } 
    

    特にサービス

    @Stateless 
    public class UserFacade extends AbstractFacade<User, String> { 
    
        @PersistenceContext(unitName = "MyPU") 
        private EntityManager em; 
    
        @Override 
        protected EntityManager getEntityManager() { 
         return em; 
        } 
    
        public UserFacade() { 
         super(User.class); 
        } 
    
        // Other methods of this service 
    
    } 
    

    は、サンフランシスコでのJavaOne 2012からJava EE 6/7: The Lean Partsもっと見ます。

    +0

    あなたの例では、サービス層はJPAに依存しています。これは私の意見では悪いことです。古いメインフレームからFTPサーバーに「ダンプ」するユーザーがいるとします。 DAO工場では、UserDAOの範囲となるFTPUserDAOとJPAUserDAOを持つことができます。あなたが提案した方法では、FTPのための全く新しいサービスレイヤセットが必要です。さて、あなたは本当に複雑なビジネスアルゴリズムをあなたのユーザに持っていればどうでしょうか? –

    +1

    問題ありません。レガシーシステム用の特定のファクトリを作成し、それをCDIで挿入することができます。 –

    +0

    私はそれに同意しません。 DAOとサービスを分離しているのは、私の謙虚な意見では、より安全です。あなたの最後のリンクは、ビデオの冒頭で、その人はJSF JPAチュートリアルを検索し、私が必要とするものを正確にチュートリアルしています! http://wiki.eclipse.org/EclipseLink/Examples/JPA/JSF_Tutorial –

    関連する問題