Apache iBATIS
Apache iBATISとは
O/Rデータベースマッピングフレームワーク
オブジェクト指向とリレーショナルデータベースを用いてシステムを開発すると、インピーダンス・ミスマッチ(Impedance Mismatch)と呼ばれるギャップが発生する。これはオブジェクト指向とリレーショナルデータベースとの考え方が異なるためである。
O/Rマッピングフレームワークとは、このギャップを軽減するためのフレームワークのことで、O/RのOはオブジェクト、Rはリレーショナルを意味している。
入手〜設定
解凍後のjarファイルをクラスパス上に置く。
利用してみる
| id | name | age |
|---|---|---|
| 1 | tarou | 30 |
| 2 | jirou | 20 |
| 3 | saburou |
テーブルの項目に対応したクラスを作る
User.java
public class User {
private String id = null;
private String name = null;
private String age = null;
public String getId() {
return id;
}
public void setId(String id) {
this.id = id;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getAge() {
return age;
}
public void setAge(String age) {
this.age = age;
}
}
xmlファイルにマッピング情報を記述する。
human.ibatis.xml
<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE sqlMap
PUBLIC "-//iBATIS.com//DTD SQL Map 2.0//EN"
"http://www.ibatis.com/dtd/sql-map-2.dtd">
<sqlMap namespace="User">
<select id="getUser" parameterClass="java.lang.String" resultClass="ibatis.User">
SELECT
ID,
NAME,
AGE
FROM
USER
WHERE
ID = #VALUE#
</select>
<update id="updateUser" parameterClass="ibatis.User">
UPDATE USER
SET NAME = #name#
<dynamic>
<isNotNull prepend="," property="age">
AGE = #age#
</isNotNull>
</dynamic>
WHERE id = #id#
</update>
<delete id="deleteUser"
parameterClass="string">
DELETE
FROM USER
WHERE ID = #id#
</delete>
<insert id="insertUser"
parameterClass="ibatis.User">
INSERT INTO USER (
ID,
NAME,
AGE
) VALUES (
#id#,
#name#,
#age#
)
</insert>
</sqlMap>
それぞれタグ名の通り、SQL(select,update,insert,delete)が記述してある。
iBATIS用configファイルを記述する。
sql-map-config.xml
<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE sqlMapConfig PUBLIC "-//iBATIS.com//DTD SQL Map Config 2.0//EN"
"http://www.ibatis.com/dtd/sql-map-config-2.dtd">
<sqlMapConfig>
<transactionManager type="JDBC">
<dataSource type="SIMPLE">
<property name="JDBC.Driver" value="sun.jdbc.odbc.JdbcOdbcDriver"/>
<property name="JDBC.ConnectionURL" value="jdbc:odbc:sample"/>
<property name="JDBC.Username" value=""/>
<property name="JDBC.Password" value=""/>
</dataSource>
</transactionManager>
<sqlMap resource="human.ibatis.xml"/>
</sqlMapConfig>
利用する。
SampleSQL.java
import java.io.Reader;
import com.ibatis.common.resources.Resources;
import com.ibatis.sqlmap.client.SqlMapClient;
import com.ibatis.sqlmap.client.SqlMapClientBuilder;
public class SampleSQL {
public static void main(String[] args)throws Exception{
String resource = "sql-map-config.xml";
Reader reader = Resources.getResourceAsReader(resource);
SqlMapClient sqlMap = SqlMapClientBuilder.buildSqlMapClient(reader);
<span class="comment">// SELECT</span>
User user = (User)sqlMap.queryForObject("getUser", "1");
System.out.println(user.getId() + "\t" + user.getName());
<span class="comment">// UPDATE</span>
user.setName("hello");
user.setAge("99");
sqlMap.update("updateUser", user);
<span class="comment">// INSERT</span>
user.setName("XYZ");
user.setAge("99");
user.setId("4");
sqlMap.insert("insertUser", user);
<span class="comment">// DELETE</span>
sqlMap.delete("deleteUser", "1");
}
}
様々なケースへの対応
柔軟なinsert文
<insert id="insertUser" parameterClass="ibatis.User">
INSERT INTO USER (
ID,
NAME,
AGE
) VALUES (
#id#,
#name:VARCHAR:NO_ENTRY#,
#age:NUMERIC:0#
)
</insert>
- ID:必須
- NAME:可変文字列型で、パラメータが空の場合にはNULLを挿入する。
- AGE:数値型で、パラメータが空の場合には0を挿入する。
繰り返し
Listと<iterate>の組み合わせで繰り返しを実現することができる。
<select id="getUsers" parameterClass="list" resultClass="ibatis.User">
SELECT
ID,
NAME,
AGE
FROM USER
WHERE ID IN
<iterate open="(" close=")" conjunction=",">
#[]#
</iterate>
</select>
パラメータで渡したリストの数だけ繰り返し処理が実行される。
呼び出し側の例
List users = new ArrayList();
users.add("1");
users.add("3");
List list = (List)sqlMap.queryForList("getUsers", users);
System.out.println(list.size());
結果
2
特殊記号(メタ文字)の利用
<や>などの記号はXMLではタグとして利用され、SQLでは比較用記号として用いられる。SQLとしてそのまま記述すると、XMLパース時にうまく解析することができなくなるため、エスケープ処理を行う必要がある。
<select id="getUsersByAge" parameterClass="string" resultClass="ibatis.User">
SELECT
ID,
NAME,
AGE
FROM
USER
WHERE
<![CDATA[AGE > #value#]]>
</select>
とすると、文字列の部分の特殊記号は特殊記号として解釈されずに、そのまま利用することが可能となる。
パラメータ以外の動的な設定
条件式(=, like, and, orなど)やソート順指定(asc, desc)などの、パラメータ以外の値を動的に変更するには、$変数名$として指定する。
<select id="getSortUser" parameterClass="string" resultClass="ibatis.User">
SELECT
ID,
NAME,
AGE
FROM USER
ORDER BY AGE $VALUE$
</select>
呼び出し側
List list = sqlMap.queryForList("getSortUser", "asc");
リンク
Java/iBATIS/Abator
概要
基本的なCRUDメソッドを備えたiBATISのdao, model, xml(sqlMap)ファイルを自動生成するための公式ツール。
入手
-http://ibatis.apache.org/abator.html
-jarファイル版とEclipseプラグイン版が存在する。
ドキュメント
-http://ibatis.apache.org/docs/tools/abator/
QuickStart(コマンドラインで実行)
-1.abatorのバイナリファイルをダウンロードする
-2.定義ファイルを作成。
例(abator.xml)
<!DOCTYPE abatorConfiguration
PUBLIC "-//Apache Software Foundation//DTD Abator for iBATIS Configuration 1.0//EN"
"http://ibatis.apache.org/dtd/abator-config_1_0.dtd">
<abatorConfiguration>
<abatorContext id="Test" generatorSet="Java2">
<jdbcConnection driverClass="oracle.jdbc.driver.OracleDriver"
connectionURL="jdbc:oracle:thin:@127.0.0.1:1521:ORCL"
userId="user"
password="password">
<classPathEntry location="C:/classes12.jar" />
</jdbcConnection>
<javaTypeResolver >
<property name="forceBigDecimals" value="false" />
</javaTypeResolver>
<javaModelGenerator targetPackage="model" targetProject="src/">
<property name="enableSubPackages" value="true" />
<property name="trimStrings" value="true" />
</javaModelGenerator>
<sqlMapGenerator targetPackage="xml" targetProject="src/">
<property name="enableSubPackages" value="true" />
</sqlMapGenerator>
<daoGenerator type="IBATIS" targetPackage="dao" targetProject="src/">
<property name="enableSubPackages" value="true" />
</daoGenerator>
<table schema="emp" tableName="EMP" domainObjectName="Emp" >
<property name="useActualColumnNames" value="true"/>
<generatedKey column="empid" sqlStatement="MySql" identity="true" />
</table>
</abatorContext>
</abatorConfiguration>
-実行
-ファイル作成完了


