前述のように、JPA <> EJB は関係ありません。EJB 3 はたまたま JPA を利用していますが、それだけです。JPA を使用して、EJB を実行することさえできないものがたくさんあります。
あなたの問題はテクノロジーではなく、あなたのデザインです。
または、あなたのデザインは、ほとんどすべての最新のフレームワークに簡単に適合するとは言えません。
具体的には、いくつかの HTTP リクエストでトランザクションを存続させようとしています。
当然のことながら、ほとんどすべての一般的なイディオムは、各要求がより大きなトランザクションの一部ではなく、各要求自体が 1 つまたは複数のトランザクションであるというものです。
トランザクションは本質的にステートフルであるため、同じ議論で「ステートレス」と「トランザクション」という用語を使用すると、明らかな混乱が生じます。
あなたの大きな問題は、トランザクションを手動で管理することです。
トランザクションが複数の HTTP リクエストで発生しており、それらの HTTP リクエストがたまたま「非常に迅速」に次々と実行されている場合、実際に問題が発生することはありません。データベースのトランザクション機能を利用するために、リクエストは同じ DB 接続を使用しています。
つまり、簡単に言えば、DB への接続を取得し、それをセッションに詰め込み、トランザクションの期間中、すべての HTTP リクエストが同じセッションだけでなく、そのような方法で通過することを確認します。実際の接続がまだ有効であること。具体的には、あるマシンから別のマシンへのフェイルオーバーまたは負荷分散を実際に生き残る既製の JDBC 接続があるとは思えません。
したがって、単純に、DB トランザクションを使用する場合は、同じ DB 接続を使用していることを確認する必要があります。
ここで、長時間実行されるトランザクションに「ユーザー インタラクション」が含まれている場合、つまり、DB トランザクションを開始し、ユーザーが「何かを行う」のを待つ場合、単純に言えば、その設計はすべて間違っています。特にインタラクティブな環境では、長期間存続するトランザクションは単純に悪いだけなので、そうしたくありません。「クロッシング・ザ・ストリーム」のように悪い。やらないでください。バッチ トランザクションは異なりますが、対話型の長期トランザクションは良くありません。
インタラクティブなトランザクションは、実用的である限り短命に保ちたいと考えています。
トランザクションに同じ DB 接続を使用できるかどうかを確認できない場合は、おめでとうございます。独自のトランザクションを実装できます。つまり、バックエンドにトランザクション機能がないかのように、システムとデータ フローを設計できます。
これは基本的に、データを「コミット」するための独自のメカニズムを考え出す必要があることを意味します。
これを行う良い方法は、データを段階的に単一の「トランザクション」ドキュメントに構築し、そのドキュメントを実際の作業の多くを行う「保存」ルーチンにフィードすることです。同様に、データベースに行を保存し、「未保存」のフラグを立てることができます。すべての行でこれを行い、最後に、保存したすべてのデータを実行するルーチンを呼び出し、単一のトランザクション ミニバッチ プロセスですべてを「保存済み」としてマークします。
一方、他のすべての SQL は、「保存」されていないデータを「無視」します。いくつかのタイム スタンプを投入し、リーパー プロセス スカベンジングを実行します (本当に面倒なことをしたい場合は、ボリュームによっては、デッド ローを DB に残しておく方が実際には安価かもしれません)。 「コミットされていない」トランザクション。
それは思ったほど悪くはありません。本当にステートレスな環境が必要な場合は、私にはそう聞こえますが、このようなことをする必要があります。
このすべてにおいて、永続化技術は実際には何の関係もありません。問題は、テクノロジーではなく、トランザクションをどのように使用するかです。