2012年4月23日月曜日

Hibernate でデータアクセス(3)

前回、前々回に続き Hibernate と c3p0 を使うための設定を行います。

リファレンス“11.3 Understanding the Spring Framework transaction abstraction”の説明と例に倣いながら Data Source, Session Factory, Transaction Manager を applicationContext.xml に定義します。まずは Data Source から。

Data Source
Data Source には c3p0 コネクションプールを使用します。

pooledDataSource ビーン
applicationContext.xml 内に“pooledDetaSource”というビーンを定義し、class 属性で ComboPooledDataSource を指定しています。

このビーン定義内では基本的なプロパティ driverClass, jdbcUrl そしてdescription を設定しているだけです。詳細な設定はクラスパスに配置した c3p0-config.xml に記述しています(もちろん上記ビーン定義内に記述することも可能です)。
<!-- 'Pooled' DataSource Configuration -->
  <bean id="pooledDataSource" 
  class="com.mchange.v2.c3p0.ComboPooledDataSource" destroy-method="close"
    p:driverClass="com.mysql.jdbc.Driver"
    p:jdbcUrl="jdbc:mysql://[host]/[db]?useUnicode=true&characterEncoding=utf-8"
    p:description="C3P0 Pooled Data Source">
  </bean>

c3p0-config.xml
データベース接続に関するプロパティ(user, password)とコネクションプールの上限、下限に関するプロパティ(maxPoolSize, minPoolSize)を設定しています。maxStatements は、グローバル PreparedStatement キャッシュの上限です。
<?xml version='1.0' encoding='utf-8'?>
<c3p0-config>
  <default-config>
    <property name="user">demo</property>
    <property name="password">demo</property>
    <property name="initialPoolSize">2</property>
    <property name="minPoolSize">2</property>
    <property name="maxPoolSize">5</property>
    <property name="acquireIncrement">1</property>
    <!-- Global PreparedStatement Cache -->
    <property name="maxStatements">200</property>
  </default-config>
</c3p0-config>

設定できるプロパティの詳細は c3p0 サイトの“Appendix A: Configuration Properties”に記載されています。

Session Factory
Hibernate セッションを取得するための Session Factory を構成します。class 属性にLocalSessionFactoryBean を指定しています。

sessionFactory ビーン
DataSource に前述の pooledDataSource を指定しています。Hibernate 関連の詳しいプロパティを <property name="hibernateProperties"> で設定することもできますが、今回は configLocation で示したファイル(/WEB-INF/conf/hibernate.cfg.xml)に記述します。
<bean id="sessionFactory" scope="singleton"
    class="org.springframework.orm.hibernate4.LocalSessionFactoryBean"
    p:dataSource-ref="pooledDataSource"
    p:configLocation="/WEB-INF/conf/hibernate.cfg.xml">
  </bean>

hibernate.cfg.xml
SQL の方言(dialect)を吸収する hibernate.dialect に MySQLDialect を指定しています。また hibernate.show_sql を true にすることで Hibernate が発行した SQL 文をコンソールに出力させます。今回はアノテーションで OR マッピングを定義しているので <mapping/>要素には、対象クラス(UserProfile と IdCard)を登録しているだけです。
<?xml version='1.0' encoding='utf-8'?>
<!DOCTYPE hibernate-configuration PUBLIC
    "-//Hibernate/Hibernate Configuration DTD 3.0//EN"
    "http://www.hibernate.org/dtd/hibernate-configuration-3.0.dtd">
<hibernate-configuration>
  <session-factory>
    <!-- Hibernate properties -->
    <property name="hibernate.dialect">org.hibernate.dialect.MySQLDialect</property>
    <property name="hibernate.show_sql">true</property>
    <property name="hibernate.current_session_context_class">thread</property>
    <!-- Mapping -->
    <mapping class="wrider.model.UserProfile"/>
    <mapping class="wrider.model.IdCard"/>
  </session-factory>
</hibernate-configuration>

Transaction Manager
Spring トランザクションの基点となる Transaction Manager の定義です。

txManager ビーン
HibernateTransactionManager を使います。sessionFactory プロパティは前述の sessionFactory ビーンを参照しています。
<bean id="txManager"
    class="org.springframework.orm.hibernate4.HibernateTransactionManager"
    p:sessionFactory-ref="sessionFactory">
  </bean>

ビュー
最後にビューです。ログインフォーム(login.jsp)では <form:form/> 要素の modelAttribute 属性で“idCard”、アカウント作成フォーム(registrationForm.jsp)では“userProfile”を指定しています。

login.jsp(抜粋)
:
  <form:form action="login.html" method="POST" modelAttribute="idCard">
    <fieldset>
    <legend>ログイン</legend>
    <div class="items">
      <label class="item" for="email">メールアドレス</label>
      <div class="item_body">
        <input type="text" id="email" name="email" value="${idCard.email}"/>
        <form:errors path="email" cssClass="red"/>
      </div>
    </div>
    :

registrationForm.jsp(抜粋)
:
  <form:form action="register.html" method="POST" modelAttribute="userProfile">
    :

図のログイン画面から認証情報を送信すると コンソールに Hibernate セッションで発行された SQL 文が Hibernate: select userprofil0_.pid as pid0_, ... from UserProfile userprofil0_ where userprofil0_.email=? and userprofil0_.password=? のような感じで表示されます。認証が成功すると welcome/home.html に遷移します。アカウント作成が成功した場合も同様です。

尚、MySQL との接続の様子はコマンドラインで
mysqladmin -u [user] -p extended-status | egrep "connect"
あるいはMySQL クライアントから
show status like '%connect%';

のように打ち込めば確かめられます。

以上でミッション終了です。一旦データベースへの接続環境が整えば、Spring (や Hibernate)が持つ色々な機能が利用できるようになります。個人的には AOP の仕掛けを利用したトランザクション管理に興味が沸きました。そうしたものを含めていつか試したいと思います。

0 件のコメント:

コメントを投稿