11

たとえば、エンタープライズアプリケーションにJavaEEスタックを使用することにしました。

さて、ドメインモデリング(またはMVCのMを設計するため)の場合、どのAPIを安全に想定して使用でき、抽象化レイヤーを介して、どのAPIを使用しないようにする必要がありますか?

例えば、

  1. 先に進んで、Hibernate / JPA APIの呼び出しでモデルを散らかす必要がありますか?または、抽象化を構築する必要があります...これらの2つの特定の永続性APIに対するハードコーディングを回避するために、独自の永続性レイヤーを作成しますか?私がこれを尋ねる理由:数年前、Hibernateに取って代わられたこのKodoAPIがありました。永続層を設計し、この層に対してモデルの残りの部分をコーディングした場合(特定のベンダーAPIの呼び出しでモデルを散らかす代わりに)、KodoからHibernate、xyzに(比較的)簡単に切り替えることができます。

  2. ドメインモデルで永続性ベンダーが提供する*QLを積極的に使用することをお勧めしますか?私は、HQLのような言語を多用することから生じる現実の問題(パフォーマンス、スケーラビリティ、移植性など)を認識していません。私がこれを尋ねる理由: SQLよりも移植性の高いクエリ言語を介して同じことが達成できる場合は、カスタムコードを書くことをできるだけ避けたいと思います。

申し訳ありませんが、私はこの分野の完全な初心者です。このトピックに関する詳細情報はどこにありますか?

4

2 に答える 2

8

これが私が伝統的な見方であると信じているものです:

  • プロジェクト内のエンティティがドメイン モデルを形成します。それらは再利用可能で、永続化テクノロジに密結合されていない必要があります (密結合と疎結合については後で説明します)。
  • ビジネス層は、ドメイン モデルを使用しますが、サービスやその他のものも公開します。
  • データ アクセス レイヤーは、ドメイン モデル (エンティティ) を永続的なストアに永続化する役割を果たします。

エンティティは、データ アクセス層を直接呼び出すべきではありません。しかし、ビジネス レイヤーは、ドメイン モデルのエンティティを読み込んで永続化する方法で行います。

それを Java EE テクノロジーにマッピングすると、通常は次のようになります。

  • エンティティ --> Hibernate/JPA アノテーション付きの POJO。注釈は、JPA/Hibernate との密結合を意味するものではないことに注意してください。まったく同じ POJO を、Hibernate なしで別の場所で使用できます。
  • ビジネス層 --> セッション EJB または Spring
  • データ アクセス レイヤー --> JPA/Hibernate

これは大まかなスケッチであり、多くのバリエーションが考えられます。特に、セッション EJB をスキップして、別の方法でビジネス レイヤーを実装できます。ビジネス層で JPA/Hibernate Session/EntityManager を直接呼び出すように決定することもできます。この場合、JPA/Hibernate は実際には DAL です。または、Session/EntityManager へのアクセスをいわゆるデータ アクセス オブジェクト (DAO) にラップすることもできます。 )。

HQL に関しては、移植可能なものに固執するようにしてください。ネイティブ SQL を使用する場合は、SQL-92 規則に従ってください。物事が複雑になる場合は、DAO を導入することもできます。このようにして、HQL クエリが存在する唯一の場所が DAO 内にあることがわかります。また、最初にクエリ ロジックを DAO で "手続き的に" 実装し、パフォーマンスの問題がある場合は、より複雑な HQL クエリを使用して再実装することもできます。

編集

コメントでの質問について:

ビジネス層はデータ層に依存します。ビジネス層が Hibernate/JPA に依存しないようにする場合は、データ層で Hibernate/JPA を抽象化する必要があります。データ層に DAO を使用する場合は、これに該当します。DAO は、「Hibernate 上の薄い手書きの永続化レイヤー」になります (あなたの言葉を借りれば)。あなたの場合、すべてのエンティティにDAOを導入します。

あなたが求めているのは、かなり一般的な設計上の質問です。そのための決定的なレシピを提供することはできません。また、ケースバイケースであるため、すべてのバリエーションを 1 つの回答にまとめることもできません。たとえば、トランザクションの問題についてはこれまで説明してきませんでした。通常はビジネス レイヤーから開始しますが、データ レイヤーは認識しておく必要があります。これは通常、使用するテクノロジーと要件によって異なります。

それでも、興味のあるリソースのリストは次のとおりです。本Pattern of Enterprise Application Architecture、本Real World Java EE Patterns - Rethinking Best Practices、本Domain Driven Design、より具体的にはパターンData Access ObjectRepository patternOpen Session in View (Web アプリの場合)、そしてAnemic Domain Modelかもしれません。

編集2

では、トランザクションに関する文をいくつか追加します。

トランザクションは、概念的にはビジネス レイヤーで管理する必要があります。一貫性を保つために 1 つの作業単位で何を行う必要があるかの定義は、アプリケーションのロジックそのものに依存します。

EJB3 では、アノテーションとアプリでトランザクションを宣言できます。サーバーがそれを管理します。詳細については、この他の私の回答を参照してください。Spring では、トランザクションを宣言的にマークすることもできますが、詳細はわかりません。それ以外の場合は、自分でトランザクションを開始/停止する必要があります。これは、JDBC トランザクションを使用するか JTA トランザクションを使用するかによって少し異なります。

トランザクションは、Hibernate/JPA での遅延読み込みにも関連しています。遅延ロードされたエンティティは、現在のトランザクションがある場合にのみロードできます。トランザクションがビジネス レイヤーで終了した場合、プレゼンテーション レイヤーに返されるエンティティは熱心に読み込まれる必要があります。

この問題を回避するために、Web アプリケーションの一般的なパターンは、既に述べたOpen Session in Viewです。この場合、プレゼンテーション レイヤーはトランザクションを開始/停止しますが (これは概念的には少し間違っています)、遅延読み込みで問題なく動作します。

于 2010-04-14T07:39:06.487 に答える
4

ドメイン モデルとその永続化レイヤーは、理論上は分離されている必要がありEntityます。永続化されているかどうか、および永続化の方法について何かを知るために呼び出されるクラスは必要ないため、Hibernate などを使用して、ドメイン モデル クラス自体を汚染することなく永続化レイヤーを作成できます。 . 「このレイヤーに対して[...]モデルをコーディングする」のではなく、モデルをコーディングしてから、ドメインモデルがORMレイヤーに依存しない、ある種のORMレイヤーを使用して永続ストアにマップします。明らかに永続層はドメイン モデルに依存しますが、それで問題ありません。

私はあなたが尋ねる理由で (N)Hibernate で HQL を使いすぎることを個人的に恥ずかしがり屋で戦っていますが、やむを得ない場合もあります。あなたはすでに知っていて、そこにある主な問題を強調しているので、とにかくこれを使いすぎることはまずありません.

于 2010-04-14T06:40:57.847 に答える