HibernateベースのDAOを作った場合に、トランザクション処理をどのように記述するかが問題になることがあります。
たとえば下記のような二つのテーブル
に対してそれぞれMemberDAOとWorkGroupDAOを作ると思います。さらにそのDAOを使用するビジネスメソッド、たとえば
なんてのが定義されると思います。
このとき、ある処理の場合はメソッド単位でトランザクション管理し、ほかの処理の場合は複数のメソッドにまたがってトランザクション管理したい場合があります。上の例だと、
とした場合、
となります。一つめの例だとaddMember内でトランザクションの開始・終了の処理を書けばよいですが、二つめの例を考えるとaddMember内でトランザクション開始と終了の処理をしちゃうとまずいわけですね。つまりあるメソッドに対してトランザクションのスコープ(境界?)が場面によって異なることがあるのですが、Springではこの辺をトランザクション処理を宣言的に記述することで解決しています。
この辺を考えるために具体例で行きます。今回考えるクラス群の全体像は以下の通りです。
またトランザクション処理を考慮しない状態のSpringの設定は以下の通りになっています。
さて、SpringではBLのビジネスメソッドに対してトランザクション処理を宣言的に追加することができるといいましたが、以下のようにやります。
まず、BLの名前をuserManagerBLからuserManagerBLTargetに変更し、userManagerBLを新規に作成します。その新たなJavaBeans?の型はSpringが提供してくれるProxyで、外部から見たインタフェースは元のuserManagerBLと同じになります。つまり見た目は外部から見たら全く変わっていないことになります。
そのProxyのタグ付けですが、トランザクション設定や、ターゲットになるJavaBeans?(元のuserManagerBLのこと)の指定などを記述しておきます。
さて処理の流れですが、実際BLを使うプログラムはuserManagerBLというキーでSpringからJavaBeans?を取得するので、処理シーケンスは
BLを使うプログラム -> userManagerBL
だったのが
BLを使うプログラム -> userManagerBL -> userManagerBLTarget
となります。
外部から見たら見た目は同じだけど、実際のBLの間に別のクラスが挟まれる用になります。結局、Springのタグ付けは以下のように変更されました。
間に挟まれたPOJOは以下のようにSpringでInjectionされています。
<bean id="userManagerBL" class="org.springframework.transaction.interceptor.TransactionProxyFactoryBean"> <property name="transactionManager"> <ref local="transactionManager" /> </property> <property name="target"> ↓ターゲットにするPOJOを指定 <ref bean="userManagerBLTarget" /> </property> <property name="transactionAttributes"> <props> ↓POJOのメソッドに対してトランザクションの設定を記述 <prop key="*">PROPAGATION_REQUIRED</prop> </props> </property> </bean>
この記事は
現在のアクセス:8134