ヘッダーをスキップ
Oracle® Fusion Middleware Oracle TopLinkソリューション・ガイド
12c (12.1.3)
E57549-01
  ドキュメント・ライブラリへ移動
ライブラリ
製品リストへ移動
製品
目次へ移動
目次

前
 
次
 

10 クラスタ内のアプリケーションのスケーリング

この章では、アプリケーション・サーバー環境でスケーラビリティを保証するためにOracle TopLinkアプリケーションを構成する手順を説明します。この手順は、すべてのアプリケーション・サーバー・クラスタに適用できる汎用的なものですが、Oracle WebLogic ServerおよびOracle GlassFish Serverに対応した追加のコンテンツも用意されています。必要に応じて、ベンダーのドキュメントを参照してください。

この章の内容は次のとおりです。

ユース・ケース

顧客の要求に応えるためにアプリケーションを拡張する必要があります。

解決方法

この実装は、キャッシュの構成、キャッシュ・コーディネーションの構成、データのパーティション化を使用して実現できます。

コンポーネント

サンプルへのリンクは、10.3項「その他の参考資料」を参照してください。

10.1 ソリューションの概要

アプリケーション・サーバー・クラスタにデプロイされたEclipseLinkアプリケーションは、クラスタのスケーラビリティ、負荷分散およびフェイルオーバーのメリットを受けることができます。これらの機能は、EclipseLinkアプリケーションの可用性を高め、アプリケーションの需要拡大に伴ってスケーリングできます。EclipseLinkのアプリケーションは、アプリケーション・サーバー・クラスタへも、スタンドアロンのサーバー環境と同様にデプロイできます。ただし、アプリケーション・サーバー・クラスタの場合には、キャッシュの一貫性を確保するために、その他に計画や構成を実行する必要があります。

EclipseLinkでは、オブジェクトおよびそのリレーションシップのデータベース・アクセスを回避する共有(L2)オブジェクト・キャッシュが利用されます。このキャッシュはデフォルトで有効になり、アプリケーションのパフォーマンスが向上します。アプリケーション・サーバー・クラスタでキャッシングを使用すると、1つのサーバーで行われた変更が、他のサーバーでキャッシュされているオブジェクトに反映されないために、整合性の問題(失効データなど)が発生する場合があります。キャッシュの整合性が問題になるのは、頻繁に更新されるオブジェクトのみです。読取り専用のオブジェクトは、キャッシュの整合性の影響を受けません。キャッシュの詳細は、次を参照してください。

http://wiki.eclipse.org/EclipseLink/UserGuide/JPA/Basic_JPA_Development/Caching/Caching_Overview

キャッシュの整合性に対処するには、次のように様々な方法があります。

10.2 ソリューションの実装

次のタスクでは、EclipseLinkアプリケーションをアプリケーション・サーバー・クラスタでスケーリングするための一般的な手順を説明します。タスクは、アプリケーションのデプロイ前に完了する必要があります。

この項の内容は次のとおりです。

10.2.1 タスク1: キャッシュの整合性の構成

このタスクには、アプリケーション・サーバーのクラスタにアプリケーションがデプロイされた場合に、アプリケーションが失効データを使用する可能性を少なくする様々な構成オプションが含まれています。キャッシュ・コーディネーション・オプションは、クラスタ化されたアプリケーション用に特に設計されていますが、すべてのオプションを評価し、(適用可能な場合は)一緒に使用して、アプリケーションのパフォーマンスが最高になるようなソリューションを作成します。キャッシュを適切に構成すれば、キャッシュ・コーディネーションを使用する必要がなくなる場合もあります。これらのオプションの詳細は、次を参照してください。

http://wiki.eclipse.org/Introduction_to_Cache_%28ELUG%29#Handling_Stale_Data

次の構成オプションを利用できます。


注意:

TopLinkでCoherenceをL2キャッシュとして使用できるようにするTopLinkとCoherenceの統合が提供されています。TopLink Gridの詳細は、第19章「TopLink GridでのOracle Coherenceを使用したアプリケーションのスケーリング」を参照してください。


10.2.1.1 エンティティのキャッシュの無効化

非常に不安定なエンティティまたは必要に応じてすべてのエンティティで共有キャッシュを無効にします。すべてのオブジェクトの共有キャッシュを無効にするには、persistence.xmlファイルの<shared-cache-mode>要素を使用します。次に例を示します。

<shared-cache-mode>NONE</shared-cache-mode>

デフォルトでは、DISABLE_SELECTIVEが構成されており、エンティティごとにキャッシュを無効にできます。共有キャッシュを選択的に有効または無効にするには、エンティティを定義する際に、@Cache注釈のshared属性を使用します。次に例を示します。

@Entity
@Cache(shared=false)
public class Employee {
}

10.2.1.2 キャッシュのリフレッシュ

アプリケーションが現在のデータの使用を確実にするために、キャッシュをリフレッシュするとデータベースからキャッシュがリロードされます。キャッシュは様々な方法でリフレッシュできます。

@Cache注釈には、データベースに対するすべての問合せで強制的にキャッシュをリフレッシュさせるalwaysRefresh属性とrefreshOnlyIfNewer属性が用意されています。キャッシュは、データベース内のオプティミスティック・ロック値がキャッシュ内のものよりも実際に新しい場合にのみリフレッシュされます。

@Entity
@Cache(
   alwaysRefresh=true, 
   refreshOnlyIfNewer=true)
public class Employee {
}

javax.persistence.Cacheインタフェースには、キャッシュが最新でない場合に失効オブジェクトを削除するメソッドが含まれています。

  • evictAllメソッドは、キャッシュ内のすべてのオブジェクトを無効にします。

    em.getEntityManagerFactory().getCache().evictAll();
    
  • evictメソッドは、特定のクラスを無効にします。

    em.getEntityManagerFactory().getCache().evict(MyClass);
    

これまでに説明したメソッドは受動的で、次回にキャッシュにアクセスしたときにのみオブジェクトがリフレッシュされます。オブジェクトを能動的にリフレッシュするには、EntityManager.refreshメソッドを使用します。このメソッドは1回に1つのオブジェクトをリフレッシュします。

キャッシュをリフレッシュする問合せをトリガーする、問合せのヒントを設定するsetHintメソッドを設定することも可能です。次に例を示します。

Query query = em.createQuery("Select e from Employee e");
query.setHint("javax.persistence.cache.storeMode", "REFRESH");

最後にネイティブAPIのメソッドも使用できます。詳細は、『Oracle TopLink Java APIリファレンス』ClassDescriptorに関する項を参照してください。

10.2.1.3 エンティティのキャッシュの期限の設定

キャッシュ有効期限を設定した場合、指定時間が経過すると、キャッシュされたオブジェクト・インスタンスが無効になります。そのオブジェクトを使用しようとすると、最新バージョンのオブジェクトがデータ・ソースからリロードされます。有効期限は、アプリケーションが確実に最新データを使用するようにするのに便利です。有効期限を設定するには、様々な方法があります。

@Cache注釈には、特定の時間が経つとキャッシュ・インスタンスを削除するexpiryおよびexpiryTimeOfDay属性が用意されています。expiry属性は、ミリ秒単位で入力します。値を指定しない場合のデフォルト値は-1で、有効期限が無効になっていることを示します。expiryTimeOfDay属性は、org.eclipse.persistence.annotations.TimeOfDayインタフェースのインスタンスです。次の例では、5分後にオブジェクトが期限切れになるように設定しています。

@Entity
@Cache(expiry=300000)
public class Employee {
}

10.2.1.4 オプティミスティック・ロックの設定

オプティミスティック・ロックでは、あるユーザーが別のユーザーの作業を上書きできないようにします。ロックは、複数のサーバーまたは複数のアプリケーションが同じデータにアクセスする場合に重要で、単一サーバーとマルチサーバーの両方の環境に関係があります。マルチサーバー環境においては、アプリケーションがキャッシュ・リフレッシュやキャッシュ・コーディネーションを使用している場合であっても、やはりロックは必要です。オプティミスティック・ロックを設定するには、様々な方法があります。

標準のJPA @Versionの注釈は、単一値の値およびタイムスタンプ・ベースのロックで使用されます。ただし、高度なロッキング機能には、@OptimisticLocking注釈を使用します。@OptimisticLocking注釈には、エンティティを更新または削除する際に使用するオプティミスティック・ロックのタイプを指定します。オプティミスティック・ロックは、@Entityまたは@MappedSuperclass注釈でサポートされています。次のポリシーをtype属性内に設定して利用できます。

  • ALL_COLUMNS: このポリシーでは、更新または削除操作を実行するときに、WHERE句で表のすべてのフィールドを比較します。

  • CHANGED_COLUMNS: このポリシーでは、更新操作の実行時に、WHERE句で変更されたフィールドのみを比較します。削除操作では、主キーのみが比較されます。

  • SELECTED_COLUMNS: このポリシーでは、更新または削除操作を実行するときに、WHERE句で選択したフィールドを比較します。指定したフィールドはマップされている必要があり、主キーではない必要があります。

  • VERSION_COLUMN: (デフォルト)このポリシーでは、単一のバージョン番号をオプティミスティック・ロックに使用することを許可します。バージョン・フィールドはマップされている必要があり、主キーではない必要があります。親オブジェクトが私有する子オブジェクトのバージョン・フィールドが変更された場合に、その親オブジェクトのバージョン・フィールドが強制的に自動更新されるようにするには、cascadedメソッドをtrueに設定します。デフォルトでは、このメソッドはfalseに設定されます。

10.2.1.5 キャッシュ・コーディネーションの使用

キャッシュ・コーディネーションは、分散セッション間で変更を同期します。すべてのアプリケーションでデータの整合性を維持するのが困難なアプリケーション・サーバー・クラスタでは、キャッシュ・コーディネーションが最も有効です。さらに、1つの環境内のサーバー数が増えるにつれて、キャッシュの整合性を保つのはますます難しくなります。

キャッシュ・コーディネーションは、クラスタ内のセッション(EntityManagerFactoryまたは永続性ユニット)間のトランザクション・オブジェクトの変更通知をブロードキャストすることにより動作します。アプリケーションが読取り中心で、複数の分散セッションで運用される同一アプリケーションによって変更が実行される場合に、キャッシュ・コーディネーションは最も有効です。

キャッシュ・コーディネーションを使用すると、失効データが大幅に減少しますが、遅延のために失効データが発生する可能性を完全になくすことはできません。さらに、キャッシュ・コーディネーションにより、分散アーキテクチャで発生するオプティミスティック・ロック例外の数は減少し、アプリケーションで失敗するトランザクションや繰り返されるトランザクションの数も減少します。とはいえ、キャッシュ・コーディネーションを行っても、効果的なロック・ポリシーが不要になることはありません。現在のデータを確実に使用するには、オプティミスティック・ロックまたはペシミスティック・ロックとともにキャッシュ・コーディネーションを使用しますが、オプティミスティック・ロックの使用の方をお薦めします。

キャッシュ・コーディネーションはRemote Method Invocation (RMI)およびJava Message Service (JMS)プロトコル上でサポートされており、persistence.xmlファイルの永続性プロパティを使用して宣言的に構成することも、キャッシュ・コーディネーションのAPIを使用して構成することもできます。永続性プロパティに一致するシステム・プロパティも使用できます。

キャッシュ・コーディネーションの詳細は、次を参照してください。

『Oracle TopLink Java Persistence API (JPA)拡張機能リファレンス』

10.2.1.5.1 キャッシュ同期の設定

キャッシュ同期では、オブジェクトの変更通知がセッション・メンバー間にブロードキャストされる方法を決定します。使用できる同期オプションは次のとおりです。

  • SEND_OBJECT_CHANGES: (デフォルト)このオプションでは、変更に関するデータを含む、変更されたオブジェクトのリストがブロードキャストされます。このデータは、受信キャッシュにマージされます。

  • INVALIDATE_CHANGED_OBJECTS: このオプションでは、変更されたオブジェクトのIDリストがブロードキャストされます。受信キャッシュでは、データを変更するのではなく、オブジェクトが無効にされます。このオプションは、他のクラスタ・メンバーに対しデータを送信したり処理を実行するには最も軽量です。

  • SEND_NEW_OBJECTS_WITH_CHANGES: このオプションは、トランザクションで新規作成されたオブジェクトも含まれる点以外はSEND_OBJECT_CHANGESオプションと同じです。

  • NONE: このオプションでは、キャッシュ・コーディネーションは行われません。

@cache注釈のcoordinationType属性は、同期を指定するために使用します。次に例を示します。

@Entity
@Cache(CacheCoordinationType.SEND_NEW_OBJECTS_CHANGES)
public class Employee {
}

ClassDescriptor.setCacheSynchronizationTypeネイティブAPIメソッドも、同期を指定するために使用できます。詳細は、『Oracle TopLink Java APIリファレンス』ClassDescriptorに関する項を参照してください。

10.2.1.5.2 永続性プロパティを使用したJMSキャッシュ・コーディネーションの構成

次の例は、persistence.xmlファイルでキャッシュ・コーディネーションを構成する方法を示しており、通知のブロードキャストにJMSを使用しています。JMSでは、JMSトピック、JNDI名およびトピック接続ファクトリのJNDI名を指定します。JMSトピックでは、JTAを有効にせず、永続性メッセージを指定しないでください。

<property name="eclipselink.cache.coordination.protocol" value="jms" />
<property name="eclipselink.cache.coordination.jms.topic" 
   value="jms/EmployeeTopic" />
<property name="eclipselink.cache.coordination.jms.factory"
   value="jms/EmployeeTopicConnectionFactory" />

クラスタで実行されるアプリケーションでは、リソースを探して使用するにはトピックで十分なので、URLは通常不要です。クラスタ外部で実行されるアプリケーションの場合は、URLが必要です。WebLogicサーバー・クラスタのURLの例を次に示します。

<property name="eclipselink.cache.coordination.jms.host"
   value="t3://myserver:7001/" />

必要な場合は、サーバーにアクセスするために必要なユーザー名とパスワードも設定できます。次に例を示します。

<property name="eclipselink.cache.coordination.jndi.user" value="user" />
<property name="eclipselink.cache.coordination.jndi.password" value="password" />
10.2.1.5.3 永続性プロパティを使用したRMIキャッシュ・コーディネーションの構成

次の例は、persistence.xmlファイルでキャッシュ・コーディネーションを構成する方法を示し、通知のブロードキャストにRMIを使用しています。

<property name="eclipselink.cache.coordination.protocol" value="rmi" />

クラスタで実行されるアプリケーションでは、JNDIがレプリケートされてサーバーが相互を参照できるので、URLは通常不要です。アプリケーションがクラスタ外部で実行される場合またはJNDIがレプリケートされない場合は、各サーバーでURLを指定する必要があります。これは、persistence.xmlファイルを使用して行えますが、各サーバーに対して別のpersistence.xmlファイル(たとえばJARまたはEAR)が必要になり、通常は望ましくありません。2番目のオプションとしては、キャッシュ・コーディネーションAPIを使用して、URLをプログラムで設定します。詳細は、「キャッシュ・コーディネーションAPIを使用したキャッシュ・コーディネーションの構成」を参照してください。最後のオプションは、各アプリケーション・サーバーのシステム・プロパティとしてURLを設定する方法です。次の例では、システム・プロパティを使用してWebLogicサーバー・クラスタのURLを設定しています。

-Declipselink.cache.coordination.jms.host=t3://myserver:7001/

必要な場合は、サーバーにアクセスするために必要なユーザー名とパスワードも、次のように設定できます。

<property name="eclipselink.cache.coordination.jndi.user" value="user" /><property name="eclipselink.cache.coordination.jndi.password" value="password" />

RMIキャッシュ・コーディネーションでは、非同期または同期のブロードキャスト通知を使用できます(デフォルトでは非同期です)。同期ブロードキャストでは、リクエストが返される前に、すべてのサーバーが確実に更新されます。次の例では、同期ブロードキャストを構成しています。

<property name="eclipselink.cache.coordination.propagate-asynchronously"
   value="false" />

同じサーバーまたはネットワーク上の複数のアプリケーションがキャッシュ・コーディネーションを使用する場合は、アプリケーションごとに別のチャネルを使用できます。次に例を示します。

<property name="eclipselink.cache.coordination.channel" value="EmployeeChannel" />

最後に、必要に応じて、サーバーが相互に検索できるようにするデフォルトのRMIマルチキャスト・ソケット・アドレスを変更します。次の例では、マルチキャスト設定を明示的に構成しています。

<property name="eclipselink.cache.coordination.rmi.announcement-delay"
   value="1000" />
<property name="eclipselink.cache.coordination.rmi.multicast-group"
   value="239.192.0.0" />
<property name="eclipselink.cache.coordination.rmi.multicast-group.port"
   value="3121" />
<property name="eclipselink.cache.coordination.packet-time-to-live" value="2" />
10.2.1.5.4 キャッシュ・コーディネーションおよびOracle WebLogic

RMIのキャッシュ・コーディネーションとJMSのキャッシュ・コーディネーションの両方ともOracle WebLogic Serverで動作します。WebLogicクラスタが使用される場合、JNDIがクラスタ・サーバー間でレプリケートされるため、cache.coordination.rmi.urlまたはcache.coordination.jms.hostオプションは不要です。JMSのキャッシュ・コーディネーションでは、JMSトピックは(Oracle WebLogic 10.3.6以上の)サーバーの1つにのみデプロイする必要があります。JMSメッセージの通信量が多い場合、状況に応じて専用のJMSサーバーを用意することをお薦めします。

WebLogicで他のJMSサービスを使用する場合、他の要件が存在することがあります。

10.2.1.5.5 キャッシュ・コーディネーションおよびGlassfish

JMSのキャッシュ・コーディネーションはGlassfish Serverで動作します。Glassfishクラスタが使用される場合、JNDIがクラスタ・サーバー間でレプリケートされるため、cache.coordination.jms.hostオプションは不要です。

Glassfishで他のJMSサービスを使用する場合、他の要件が存在することがあります。

RMIのキャッシュ・コーディネーションは、JNDIネーミング・サービス・オプションがGlassfishクラスタで使用されている場合には動作しません。RMIは、eclipselink.cache.coordination.naming-serviceオプションがrmiに設定されている場合に動作します。各サーバーでは、サーバーごとに異なるpersistence.xmlファイルを用意するか、サーバーのシステム・プロパティとしてURLを設定するか、カスタマイザを使用して独自のeclipselink.cache.coordination.rmi.urlオプションを提供する必要があります。

10.2.1.5.6 キャッシュ・コーディネーションおよびIBM WebSphere

JMSのキャッシュ・コーディネーションでは、IBM WebSphere上で問題が発生することがあります。JMSへのアクセスを可能にするため、メッセージドリブンBean (MDB)の使用が必要になることがあります。MDBをキャッシュ・コーディネーションとともに使用するには、eclipselink.cache.coordination.protocolオプションの値をjms-publishingに設定します。アプリケーションでも、そのEARファイルのキャッシュ・コーディネーション・メッセージを処理するMDBをデプロイする必要があります。

10.2.1.5.7 キャッシュ・コーディネーションAPIを使用したキャッシュ・コーディネーションの構成

CommandManagerインタフェースを使用して、セッションのキャッシュ・コーディネーションをプログラムで構成します。インタフェースは、DatabaseSessionインタフェースのgetCommandManagerメソッドを使用してアクセスします。

10.2.2 タスク2: EclipseLinkの有効化の確認

EclipseLink JARファイルが、EclipseLinkアプリケーションがデプロイされているクラスタの各アプリケーション・サーバーのクラスパスに含まれていることを確認して、EclipseLinkを永続性プロバイダとして構成します。TopLinkをWebLogic ServerおよびGlassFish Serverで設定する方法の詳細は、第3章「WebLogic ServerでのTopLinkの使用」および第4章「GlassFish ServerでのTopLinkの使用」をそれぞれ参照してください。

10.2.3 タスク3: すべてのアプリケーション・サーバーがクラスタ内にあることの確認

EclipseLinkアプリケーションをホストする各アプリケーション・サーバーを含むアプリケーション・サーバー・クラスタを構成します。


注意:

TopLinkはJMSおよびRMIに依存し、アプリケーション・サーバーのクラスタ構成は使用しません。


10.2.4 データのスケールのためのデータ・パーティション化の使用

データのパーティション化では、1つ以上のデータベース・マシンにアプリケーションのデータをスケーリングします。データのパーティション化では、同じクラスの別のセットのエンティティ・インスタンスを、別の物理データベースまたはデータベース・クラスタの別のノードにエンティティ・レベルで保存することをサポートしています。標準のデータベースもクラスタ化されたデータベースもサポートされています。データは水平にも垂直にもパーティション化できます。

パーティションは、エンティティ、リレーションシップ、問合せ、永続性ユニットで有効にできます。データのパーティション化を構成するには、@Partitioned注釈と1つ以上のパーティショニング・ポリシー注釈を使用します。表10-1では、パーティション・ポリシーについて説明します。

表10-1 パーティション・ポリシー

注釈 説明

@HashPartitioning

パーティションは、オブジェクトのID、場所、テナントなどのオブジェクトのフィールド値のハッシュからデータベース・クラスタにアクセスします。接続プール/ノード一覧に対してハッシュ索引を作成します。そのハッシュ値を持つオブジェクトに対するすべての書込みまたは読取り要求は、同じサーバーに送信されます。問合せにパラメータとしてハッシュ・フィールドが含まれない場合、すべてのサーバーに送信され結合されるか、セッションのデフォルトの処理が行われます。

@PinnedPartitioning

1つの接続プール/ノードに要求を固定します。これによりパーティショニングは垂直方向で行われるようになります。

@RangePartitioning

パーティションは、オブジェクトのID、場所、テナントなどのオブジェクトのフィールド値を使用しデータベース・クラスタにアクセスします。各サーバーには値の範囲が割り当てられます。その値を持つオブジェクトに対するすべての書込みまたは読取り要求は、同じサーバーに送信されます。問合せにパラメータとしてそのフィールドが含まれない場合、すべてのサーバーに送信され結合されるか、セッションのデフォルトの処理が行われます。

@ReplicationPartitioning

接続プール/ノードのセットに要求を送信します。このポリシーは、データベース・マシンのクラスタ間でデータをレプリケートするためのものです。変更の問合せのみがレプリケートされます。

@RoundRobinPartitioning

接続プール/ノードのセットにラウンドロビン方式で要求を送信します。このポリシーは、データベース・マシンのクラスタ全体に対して、読取り問合せの負荷を分散するために使用します。これでは、パーティショニングをサポートしないよう、データベースを完全にマシンにレプリケートする必要があります。データは、読取り専用のみであるか、書込みをレプリケートする必要があります。

@UnionPartitioning

問合せをすべての接続プールに送信し、結果を結合します。これは、ManyToManyのパーティションをまたがるリレーションシップなど、パーティショニングが使用されているときに、パーティションをまたぐ問合せやリレーションシップで使用します。

@ValuePartitioning

パーティションは、オブジェクトの場所やテナントなどのオブジェクトのフィールド値を使用しデータベース・クラスタにアクセスします。各値には特定のサーバーが割り当てられます。その値を持つオブジェクトに対するすべての書込みまたは読取り要求は、同じサーバーに送信されます。問合せにパラメータとしてフィールドが含まれない場合、すべてのサーバーに送信され結合されるか、セッションのデフォルトの処理が行われます。

@Partitioning

パーティションは、カスタム・パーティション・ポリシーを使用してデータベース・クラスタにアクセスします。PartitioningPolicyクラスを拡張するクラスを提供する必要があります。


パーティション・ポリシーとは、永続性ユニットでグローバルに命名されたオブジェクトで、複数の識別子または問合せで再利用できます。これにより、特にJPA注釈およびXMLの構成の使い勝手が向上します。

永続性ユニットのプロパティは、読取り、書込み、シーケンスの既存の構成に加え、名前付きの接続プールの追加をサポートしています。接続プールは、参加している各データベースのpersistence.xmlファイル内に定義します。パーティション・ポリシーは、その特定のアルゴリズムに基づいて適切な接続を選択します。

トランザクションにより複数のパーティションのデータが変更される場合、JTAを使用してデータが2段階でコミットされるようにする必要があります。1つのトランザクションに1つのノードのみが使用されるようEntityManagerの実装で排他接続を構成することも可能です。

次の例では、場所ごとにEmployeeデータをパーティション分割します。2つの主要サイトOttawaおよびTorontoは、それぞれ別のデータベースに保存されています。その他のすべての場所は、デフォルトのデータベースに保存されています。プロジェクトはそのIDで範囲がパーティション分割されています。ID値の各範囲は、別のデータベースに保存されます。

@Entity
@IdClass(EmployeePK.class)
@UnionPartitioning(
        name="UnionPartitioningAllNodes",
        replicateWrites=true)
@ValuePartitioning(
        name="ValuePartitioningByLOCATION",
        partitionColumn=@Column(name="LOCATION"),
        unionUnpartitionableQueries=true,
        defaultConnectionPool="default",
        partitions={
            @ValuePartition(connectionPool="node2", value="Ottawa"),
            @ValuePartition(connectionPool="node3", value="Toronto")
        })
@Partitioned("ValuePartitioningByLOCATION")
public class Employee {
    @Id
    @Column(name = "EMP_ID")
    private Integer id;
     @Id
    private String location;
    ...
 
    @ManyToMany(cascade = { PERSIST, MERGE })
    @Partitioned("UnionPartitioningAllNodes")
    private Collection<Project> projects;
    ...
}

従業員とプロジェクトのリレーションシップが、パーティションをまたぐリレーションシップの例です。従業員およびプロジェクトを別のデータベースに保存するために、結合ポリシーが使用され、結合表が各データベースにレプリケートされます。

@Entity
@RangePartitioning(
        name="RangePartitioningByPROJ_ID",
        partitionColumn=@Column(name="PROJ_ID"),
        partitionValueType=Integer.class,
        unionUnpartitionableQueries=true,
        partitions={
            @RangePartition(connectionPool="default", startValue="0",
               endValue="1000"),
            @RangePartition(connectionPool="node2", startValue="1000",
               endValue="2000"),
            @RangePartition(connectionPool="node3", startValue="2000")
        })
@Partitioned("RangePartitioningByPROJ_ID")
public class Project {
    @Id
    @Column(name="PROJ_ID")
    private Integer id;
    ...
}

10.2.4.1 クラスタ化されたデータベースおよびOracle RAC

一部のデータベースでは、複数のサーバーにデータベースをクラスタリングできます。Oracle Real Application Clusters (RAC)では1つのデータベースを別の複数のサーバー・ノードにスパンできます。Oracle RACでは、データを表およびノードでパーティション化することも可能です。データベース・クラスタを使用すると、クラスタの任意のノードから任意のデータにアクセスできます。ただし、一般的には、ノード間での通信を減らすために、データへのアクセスを特定のノードにパーティション化する方が効率的です。パーティション化を、クラスタ・データベースとともに使用すると、ノード間の通信を減らし、拡張性を向上させることができます。Oracle RACでEclipseLinkを使用する方法の詳細は、24.2.5項「Oracle RACでのEclipseLinkの使用」を参照してください。

データベース・クラスタでデータのパーティション化を使用する際の要件は、次のとおりです。

  • データベース・クラスタによりすべてのノードがデータを利用できるようになってしまうので、パーティション・ポリシーでは、レプリケーションを有効にしないようにする必要があります。

  • データベース・クラスタによりすべてのノードの問合せ結果がすべて返されてしまうので、パーティション・ポリシーでは結合を使用しないようにする必要があります。

  • クラスタの各ノードにDataSourceおよび接続プールを定義する必要があります。

  • アプリケーションのデータ・アクセスおよびデータ・パーティション化で、各トランザクションが1つのノードにのみアクセスするよう設計する必要があります。

  • 1つのトランザクションで複数のノードがあったり、2段階でのコミットを避けるは、EntityManagerで排他接続を使用することが推奨されます。

10.3 その他の参考資料

この章のソリューションが実装されているその他のテクノロジおよびツールの詳細は、次の参考資料を参照してください。

次のコード例およびJavaDocの参考資料を参照できます。