SqlSessionFactoryBean
基となる MyBatis では、SqlSessionFactory をビルドする際 SqlSessionFactoryBuilder を使いましたが、MyBatis-Spring では、SqlSessionFactoryBean を使います。
設定
Spring の XML 設定ファイルに次の Bean を定義することで Factory Bean を生成することができます。
<bean id="sqlSessionFactory" class="org.mybatis.spring.SqlSessionFactoryBean">
<property name="dataSource" ref="dataSource" />
</bean>
SqlSessionFactoryBean は Spring の FactoryBean インターフェイス(the Spring documentation(Core Technologies -Customizing instantiation logic with a FactoryBean- を参照してください)を実装しています。
これはつまり、最終的に Spring が生成するのは SqlSessionFactoryBean ではなく、Factory の getObject() メソッドによって返されるオブジェクトであるということです。
上記の設定では、Spring は SqlSessionFactory を生成し、sqlSessionFactory という名前の Bean として登録します。
これに相当する Java のコードは下記のようになるでしょう。
@Configuration
public class MyBatisConfig {
@Bean
public SqlSessionFactory sqlSessionFactory(DataSource dataSource) throws Exception {
SqlSessionFactoryBean factoryBean = new SqlSessionFactoryBean();
factoryBean.setDataSource(dataSource);
return factoryBean.getObject();
}
}
通常 MyBatis-Spring を使う場合、SqlSessionFactoryBean や対応する SqlSessionFactory を直接利用する必要はありません。
SqlSessionFactory は MapperFactoryBean や SqlSessionDaoSupport を継承した他の DAO にインジェクト(注入)されます。
プロパティ
SqlSessionFactory で必須のプロパティは JDBC の DataSource のみです。 どのような DataSource でも構いません。Spring でデータベース接続を定義する通常の手順で定義してください。
configLocation は、MyBatis の XML 設定ファイルの場所を指定する際に使用します。これは、例えば基になる MyBatis の設定の一部を変更したい場合などに必要となります。
よくあるのは <settings> や <typeAliases> などの設定です。
ここで指定する設定ファイルは、完全な MyBatis 設定ファイルである必要はありません。 環境、データソース、MyBatis のトランザクションマネージャーに関する設定は無視されます。
SqlSessionFactoryBean は、独自にカスタマイズした MyBatis Environment を生成し、必要に応じてこれらの値を設定するようになっています。
設定ファイルの指定が必要とされるもう一つの例は、MyBatis の Mapper XML ファイルが Mapper クラスとは別のクラスパスに存在する場合です。
このような構成にする場合、次のどちらかの方法で設定することができます。最初の方法は、MyBatis の設定ファイルの <mappers> で各 XML ファイルのクラスパスを指定する方法です。
そしてもう一つは、Factory Bean の mapperLocations を使った方法です。
mapperLocations プロパティは Resource Location のリストを取り、ここで MyBatis の XML Mapper ファイルの場所を指定することができます。
Ant スタイルのパターン文字列を使って特定のディレクトリ内の全ファイルを指定したり、内包するディレクトリを再帰的に検索対象にすることもできます。次の例を見てください。
<bean id="sqlSessionFactory" class="org.mybatis.spring.SqlSessionFactoryBean">
<property name="dataSource" ref="dataSource" />
<property name="mapperLocations" value="classpath*:sample/config/mappers/**/*.xml" />
</bean>
Javaでは、同等のコードは次のようになります。
@Bean
public SqlSessionFactory sqlSessionFactory(DataSource dataSource) throws Exception {
SqlSessionFactoryBean factoryBean = new SqlSessionFactoryBean();
factoryBean.setDataSource(dataSource);
factoryBean.setMapperLocations(new PathMatchingResourcePatternResolver().getResources("classpath*:sample/config/mappers/**/*.xml"));
return factoryBean.getObject();
}
このように指定すると、クラスパス内の sample.config.mappers パッケージと、そのサブパッケージに含まれる全ての MyBatis Mapper XML ファイルがロードされます。
Container-Managed トランザクションを利用する環境では、transactionFactoryClass プロパティが必須となります。「トランザクション」章の該当する節を参照してください。
複数のデータベースを使用する場合は、databaseIdProvider プロパティを設定する必要があります。
<bean id="databaseIdProvider" class="org.apache.ibatis.mapping.VendorDatabaseIdProvider">
<property name="properties">
<props>
<prop key="SQL Server">sqlserver</prop>
<prop key="DB2">db2</prop>
<prop key="Oracle">oracle</prop>
<prop key="MySQL">mysql</prop>
</props>
</property>
</bean>
<bean id="sqlSessionFactory" class="org.mybatis.spring.SqlSessionFactoryBean">
<property name="dataSource" ref="dataSource" />
<property name="mapperLocations" value="classpath*:sample/config/mappers/**/*.xml" />
<property name="databaseIdProvider" ref="databaseIdProvider"/>
</bean>
Javaでは、同等のコードは次のようになります。
@Bean
public VendorDatabaseIdProvider databaseIdProvider() {
VendorDatabaseIdProvider databaseIdProvider = new VendorDatabaseIdProvider();
Properties properties = new Properties();
properties.setProperty("SQL Server", "sqlserver");
properties.setProperty("DB2", "db2");
properties.setProperty("Oracle", "oracle");
properties.setProperty("MySQL", "mysql");
databaseIdProvider.setProperties(properties);
return databaseIdProvider;
}
@Bean
public SqlSessionFactory sqlSessionFactory(DataSource dataSource, DatabaseIdProvider databaseIdProvider) throws Exception {
SqlSessionFactoryBean factoryBean = new SqlSessionFactoryBean();
factoryBean.setDataSource(dataSource);
factoryBean.setDatabaseIdProvider(databaseIdProvider);
return factoryBean.getObject();
}
NOTE
1.3.0より、configuration プロパティが追加されました。このプロパティには、MyBatisのXML設定ファイルを使わずにConfigurationインスタンスを直接指定することができます。
次の例を見てください。
<bean id="sqlSessionFactory" class="org.mybatis.spring.SqlSessionFactoryBean">
<property name="dataSource" ref="dataSource" />
<property name="configuration">
<bean class="org.apache.ibatis.session.Configuration">
<property name="mapUnderscoreToCamelCase" value="true"/>
</bean>
</property>
</bean>
Javaでは、同等のコードは次のようになります。
@Bean
public SqlSessionFactory sqlSessionFactory(DataSource dataSource) throws Exception {
SqlSessionFactoryBean factoryBean = new SqlSessionFactoryBean();
factoryBean.setDataSource(dataSource);
org.apache.ibatis.session.Configuration configuration = new org.apache.ibatis.session.Configuration();
configuration.setMapUnderscoreToCamelCase(true);
factoryBean.setConfiguration(configuration);
return factoryBean.getObject();
}
Java Configurationサンプル
上記で説明したプロパティを組み合わせた設定クラスの完全な例は以下の通りです。
@Configuration
public class MyBatisConfig {
@Bean
public SqlSessionFactory sqlSessionFactory(DataSource dataSource) throws Exception {
SqlSessionFactoryBean factoryBean = new SqlSessionFactoryBean();
factoryBean.setDataSource(dataSource);
// Setting mapper locations
factoryBean.setMapperLocations(new PathMatchingResourcePatternResolver().getResources("classpath*:sample/config/mappers/**/*.xml"));
// Setting configuration property
org.apache.ibatis.session.Configuration configuration = new org.apache.ibatis.session.Configuration();
configuration.setMapUnderscoreToCamelCase(true);
factoryBean.setConfiguration(configuration);
return factoryBean.getObject();
}
}
NOTE
この設定クラスは、Springコンテナによってスキャンされるパッケージ内に配置する必要があります(例:メインアプリケーションパッケージ内)。クラス名自体(例: MyBatisConfig )は任意で、必要なのは @Configuration アノテーションだけです。
MyBatis