10

私たちの設計には、jboss/webapp (読み取り/書き込み) である 1 つの jvm があり、休止状態 (jpa を使用) を介してデータベースへのデータを維持するために使用されます。このモデルには、3 ~ 5 レベルの深さの関係を持つ 10 ~ 15 の永続クラスがあります。

次に、このデータを使用するサーバーである別の jvm があります。継続的に実行されているため、長いデータベース セッションが 1 つだけあります (読み取り専用)。

現在、jvm 内キャッシュは関与していません。そのため、一方の jvm から他方の jvm に手動でシグナルを送ります。

webapp が一部のデータを変更すると、変更されたデータを再ロードするようにサーバーに通知します。私たちが見つけたのは、休止状態にデータをパージしてから再ロードするように指示する必要があるということです。データベースでフェッチ/マージを実行するだけでは、機能しません。主に、階層のいくつかのレイヤーの下にあるオブジェクトに関してです。

この設計に根本的な問題があるかどうか、または誰かがこれを行っていて、リロード時に休止状態で作業する方がうまくいったかどうかについての考え。

ありがとう、クリス

4

4 に答える 4

14

Hibernate セッションは、DB から読み取ったすべてのデータを、いわゆる第 1 レベル キャッシュにロードします。行が DB からロードされると、同じ PK を持つ行の後続のフェッチでは、このキャッシュからデータが返されます。さらに、Hibernate gaurentee は、単一のセッションで同じ PK を持つオブジェクトの等価性を参照します。

私が理解していることから、読み取り専用のサーバー アプリケーションは Hibernate セッションを閉じることはありません。そのため、読み取り/書き込みアプリケーションによって DB が更新されても、読み取り専用サーバーのセッションは変更を認識しません。事実上、読み取り専用アプリケーションはデータベースのメモリ内コピーをロードし、そのコピーを使用していますが、それはやがて古くなります。

私が提案できる最も簡単で最善の方法は、必要に応じてセッションを閉じたり開いたりすることです。これにより、問題全体が回避されます。Hibernate セッションは、DB との短期間の対話のためのウィンドウとなることを目的としています。オブジェクトグラフを何度もリロードしないことでパフォーマンスが向上することに同意します。しかし、あなたはそれを測定し、苦労する価値があることを自分自身に納得させる必要があります.

もう 1 つのオプションは、定期的にセッションを閉じて再度開くことです。これにより、読み取り専用アプリケーションが特定の時間間隔よりも古いデータで動作することが保証されます。ただし、読み取り専用アプリケーションが古いデータを処理するウィンドウが確実に存在します (ただし、最終的に最新のデータを取得することが設計によって保証されます)。これは、多くのアプリケーションで許容される可能性があります。状況を評価する必要があります。

3 番目のオプションは、2 番目のレベルのキャッシュの実装を使用し、存続期間の短いセッションを使用することです。Hibernate で動作するさまざまなキャッシュ パッケージがあり、相対的な長所と短所があります。

于 2008-09-08T19:45:49.880 に答える
5

クリス、私はあなたの状況について少し混乱しています。私が正しく理解していれば、Hibernateを使用して共有データベースにアクセスするWebアプリ(読み取り/書き込み)とスタンドアロンアプリケーション(読み取り専用?)の両方があります。Webアプリで行った変更は、スタンドアロンアプリには表示されません。そうですか?

もしそうなら、別の第2レベルのキャッシュ実装を使用することを検討しましたか?Webアプリケーションとスタンドアロンアプリケーションの両方で共有されるクラスター化されたキャッシュを使用できるのではないかと思います。Hibernateと統合されているSwarmCacheでこれが可能になると思いますが、私自身は試していません。

ただし、一般的に、特定のキャッシュのコンテンツが別のアプリケーションによるアクティビティを認識しないことを知っておく必要があります(そのため、両方のアプリでキャッシュを共有することをお勧めします)。幸運を!

于 2008-09-07T21:16:58.717 に答える
2

私の見解では、下線付きの Hibernate キャッシュをクラスター化モードをサポートするものに変更する必要があります。JBoss CacheまたはSwarm Cacheの可能性があります。最初のものは、データ同期 (レプリケーションと無効化) のサポートが向上しており、JTA もサポートしています。

次に、webapp とサーバー間のキャッシュ同期を構成できます。JBoss Cache を使用する場合は、分離レベルも確認してください。同じセッションからサーバー上の新しいデータを取得したい場合は、 READ_COMMITTEDモードを使用する必要があると思います。

于 2009-02-22T07:40:25.643 に答える
1

最もよく使用される方法は、コンテナー管理エンティティー・マネージャーを使用して、同じコンテナー内の2つ以上のアプリケーション(Glassfish、Tomcat、Websphereなど)が同じキャッシュを共有できるようにすることです。ただし、アプリケーションコンテナを使用しない場合は、Playを使用するためです。たとえば、プライマリアプリケーションでいくつかのWebサービスを構築して、キャッシュで一貫して読み取り/書き込みを行います。

古いデータを使用することは、災害への扉を開くことだと思います。シングルトンがマルチトンになるのと同じように、読み取り専用アプリケーションは書き込みであることがよくあります。

ベルトとブレース:)

于 2012-11-27T07:30:21.163 に答える