[Seasar-user:3426] S2HibernateでgetSession() の処理に時間がかかる

Tetsuya Kuramochi [E-MAIL ADDRESS DELETED]
2006年 3月 25日 (土) 12:06:00 JST


こんにちは、倉持といいます。
こちらのMLははじめてです。どうぞよろしくお願いします。

JDK1.5、JSF(Myfaces1.1.1)、S2Container  
2.3.7 、S2Hibernate 1.1.2、Hibernate3.1.3、 
Oracle10g、Tomcat5.5 の環境でちょっとしたサンプルを作成し 
ました。
作ったJSFのサンプルは至ってシンプルで、最初の画面の 
Submitをクリックすると、DBのあるテーブルの最初の数件を拾っ 
てきて表示するものです。最初の画面で使われている 
ManagedBean(SampleJSF.java)のscopeはsession 
にしています。
長くなって読みにくくなると思いますので、j2ee.dicon、 
s2hibernate3.dicon、サンプル用のdiconを文末にコピペしてお 
きます。

ボタンが押されたとき割り当てているメソッドでは、

	public void hogePushed(ActionEvent e) {
		try {
			S2Container container = S2ContainerFactory.create(PATH);
			SampleDAO service = (SampleDAO) container
					.getComponent(SampleDAO.class);
			System.out.println("hogePushed.....");
			itemName = service.getSampleData().getUserName();

		} finally {
			container.destroy();
		}
	}

としてて、登録されているコンポーネントのSampleDAOimpl.java 
でDBへアクセスしている部分は
	private S2SessionFactory  sessionFactory_;
	private Session session;

	public SampleData getSampleData(){
		System.out.println("getSession...start" );
		long st = System.currentTimeMillis();
		session = (Session)sessionFactory_.getSession();
		long e = System.currentTimeMillis();
		System.out.println("getSession...end:" + (e-st));

		Criteria cr = session.createCriteria(S2SessionFactory.class);
		cr.setMaxResults(5);
		List list = cr.list();
		SampleData i = (SampleData)list.get(0);
		return i;
	}

と、しています。
前置きが長くなってすいません。おたずねしたいことは、
		session = (Session)sessionFactory_.getSession();
のgetSession()の処理時間が長く感じる、というもので、上記サ 
ンプルを実行した結果、
アプリ起動直後にアクセスして実行した場合は…
DEBUG 2006-03-24 19:25:33,781 [http-8080-Processor24] トランザク 
ションを開始しました
getSession...start
DEBUG 2006-03-24 19:25:42,171 [http-8080-Processor24] 物理的なコ 
ネクションを取得しました
DEBUG 2006-03-24 19:25:42,203 [http-8080-Processor24] 論理的なコ 
ネクションを取得しました
getSession...end:8687
DEBUG 2006-03-24 19:25:43,875 [http-8080-Processor24] トランザク 
ションをコミットしました
DEBUG 2006-03-24 19:25:43,906 [http-8080-Processor24] 論理的なコ 
ネクションを閉じました
DEBUG 2006-03-24 19:25:43,906 [http-8080-Processor24] 物理的なコ 
ネクションを閉じました

と出ます。そして最初の画面に戻ってSubmitすると、getSession 
()の処理でかかった時間は
getSession...end:2656
になり、処理時間はぐっと減ります。更に画面をリロードしたり最初の 
画面に戻ってSubmitすると、getSession...end:63 となっ 
て実際にブラウザを操作しても何ら待たされることなくレスポンスが 
返ってきます。

さらに、一度ブラウザを閉じる、もしくは別マシンからアクセスをした 
場合(つまり新規セッションでアクセスした場合)、最初のアクセスと 
二回目のリロードではgetSession...end:2750ぐらいでした。何 
度か試したところ、2200〜2800ぐらいの数値で、3 
回目以降のリロードでは40〜70ぐらいと素早いレスポンス 
となっています。JSF側の新規セッションが発生するたびに 
S2Hibernate側のgetSession()の生成コストがとても高い、と感 
じています。

(開発機上の話ですので、運用機ではまた違った数字になるとは思いま 
すけど)ブラウザから最初にアクセスしたときに1〜3秒ほど待たされ 
るのは何かやり方が悪いのではないかと思っています(アプリ起動直後 
のアクセスで時間がかかるのはわかりますが、その後の新規セッション 
でのアクセスに関してはキャッシュ効果があるなどして、数値でいうと 
40〜70ぐらい出てくれないと実務では使えないと思ったりしま 
す)。
・getSession()はもともとコストがかかる処理である
・書き方が悪い、各種diconの設定に不備がある
…などアドバイスをいただけるとありがたいです。ManagedBeanを 
sessionではなくrequestにするケースもあり、その中で 
sessionFactory_.getSession()の処理が実行されるたびにこの時間がか 
かるのは実用的ではなくなりますから、皆さんどのようにされているか 
を知りたいと思っています。

JSFやS2Hibernateなどの組み合わせは使いはじめて二日目なので 
勘違いしてるところがあるかもしれませんけど、どうぞ、よろしくお願 
いします。



-------------------------------j2ee.dicon
<?xml version="1.0" encoding="Shift_JIS"?>
<!DOCTYPE components PUBLIC "-//SEASAR//DTD S2Container//EN"
"http://www.seasar.org/dtd/components.dtd">
<components namespace="j2ee">

	<component name="transactionManager"
		class="org.seasar.extension.jta.TransactionManagerImpl"/>
	<component name="requiredTx"
		class="org.seasar.extension.tx.RequiredInterceptor"/>
	<component name="requiresNewTx"
		class="org.seasar.extension.tx.RequiresNewInterceptor"/>
	<component name="mandatoryTx"
		class="org.seasar.extension.tx.MandatoryInterceptor"/>

	<component name="xaDataSource"
		class="org.seasar.extension.dbcp.impl.XADataSourceImpl">
		<property name="driverClassName">
			"oracle.jdbc.driver.OracleDriver"
		</property>
		<property name="URL">
			"jdbc:oracle:thin:@***.***.***.***:1521:HogeHoge"
		</property>
		<property name="user">"hogehoge"</property>
		<property name="password">"hogehoge"</property>
	</component>

	<component name="connectionPool"
		class="org.seasar.extension.dbcp.impl.ConnectionPoolImpl">
		<property name="timeout">600</property>
		<property name="maxPoolSize">0</property>
		<destroyMethod name="close"/>
	</component>
	
	<component name="dataSource"  
class="org.seasar.extension.dbcp.impl.DataSourceImpl"/>
</components>

------------------------------- s2hibernate3.dicon
<?xml version="1.0" encoding="Shift_JIS"?>
<!DOCTYPE components PUBLIC "-//SEASAR//DTD S2Container//EN"
"http://www.seasar.org/dtd/components.dtd">

<components namespace="s2hibernate">
     <include path="j2ee.dicon"/>

     <component  
class="org.seasar.hibernate3.impl.S2SessionFactoryImpl" >
		<initMethod name="setConfigPath">
			<arg>"hibernate.cfg.xml"</arg>
		</initMethod>	   		
	</component>

     <component  
class="org.seasar.hibernate3.dao.impl.HibernateDaoMetaDataFactoryImpl"/>
     <component name="readOnly"  
class="org.seasar.hibernate3.interceptor.ReadOnlySessionInterceptor"/>
     <component name="interceptor"
          
class="org.seasar.hibernate3.dao.interceptors.S2HibernateDaoInterceptor" 
/>
</components>

------------------------------- SampleData.dicon
<?xml version="1.0" encoding="EUC-JP"?>
<!DOCTYPE components PUBLIC "-//SEASAR//DTD S2Container//EN"
"http://www.seasar.org/dtd/components.dtd">

<components>
     <include path="s2hibernate3.dicon"/>
     <component class="sample.dao.SampleDAOimpl">
         <aspect>j2ee.requiredTx</aspect>
         <aspect>s2hibernate.interceptor</aspect>
     </component>
</components>


------------------------------------------------------
Tetsuya Kuramochi
WebSite : LiFE with "WebObjects"
                    http://web1.aaacafe.ne.jp/~tetsuyak/
e-Mail : [E-MAIL ADDRESS DELETED]
------------------------------------------------------





Seasar-user メーリングリストの案内