iBATIS

コーディング

iBATIS用のDAOクラスを作成します。
既存のソースに手を加える必要はありません。

AuthorDao

まずWEB-INF/srcの下に
com.ziqoo.dao.ibatisパッケージを作成します。
ここにクラスAuthorDaoを作成します。

AuthorDao.java生成直後


package com.ziqoo.dao.ibatis;

import java.util.List;
import org.springframework.orm.ibatis.support.SqlMapClientDaoSupport;
import com.ziqoo.dao.IAuthorDao;
import com.ziqoo.entity.Author;

public class AuthorDao extends SqlMapClientDaoSupport implements IAuthorDao {

	public List getAuthors() {
		// TODO Auto-generated method stub
		return null;
	}

	public Author getAuthor(Long id) {
		// TODO Auto-generated method stub
		return null;
	}

}

ではメソッドgetAuthorからコーディングしていきますが、
その前にmapファイルを作成します。
WEB-INFフォルダの下にmapフォルダを作成し、そこへ
Author.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="Author">
    <select id="queryAuthor" parameterClass="com.ziqoo.entity.Author" resultClass="com.ziqoo.entity.Author">
    	select id, name
    	from author
    	<dynamic prepend="where">
    	    <isNotEmpty property="id">
    		id = #id#
    	    </isNotEmpty>
    	</dynamic>

    </select>
</sqlMap>

これは指定されたidに一致する著者情報を検索するための定義です。
内容をちょっと説明すると、
検索なのでselectタグを使用しています。
idはこのmap定義を識別するためのidです。
parameterClassはパラメータとして渡されるクラスを指定しています。
resultClassは検索結果を格納するクラスを指定しています。
検索結果のマッピングはテーブルのカラム名と、
ここで指定されたクラスのプロパティ名が同じ場合はこれだけです。
dynamicタグはこのタグ内が動的に追加されることを指定しています。
<isNotEmpty property="id">はparameterClassで指定したAuthorのプロパティ"id"が
空でなければ追加せよという意味です。
#id#がAuthor.idの値に置換されます。
そして、getAuthorメソッドは以下のようになります。

	public Author getAuthor(Long id) {
		Author author = new Author();
		author.setId(id);
		
		return (Author)getSqlMapClientTemplate().queryForObject("queryAuthor", author);
	}

次はgetAuthorsですが、idを指定せずに"queryAuthor"を実行すればよいので
以下のようになります。

	public List getAuthors() {
		return getSqlMapClientTemplate().queryForList("queryAuthor", new Author());
	}

PublisherDao

PublisherDaoも同様にcom.ziqoo.dao.ibatisパッケージ下に作成します。
PublisherDao.java、Publisher.xmlはそれぞれ以下のようになります。
package com.ziqoo.dao.ibatis;

import java.util.List;

import org.springframework.orm.ibatis.support.SqlMapClientDaoSupport;

import com.ziqoo.dao.IPublisherDao;
import com.ziqoo.entity.Publisher;

/**
 * iBATISによる出版社情報アクセスクラス
 *
 */
public class PublisherDao extends SqlMapClientDaoSupport implements IPublisherDao {

	public List getPublishers() {
		return getSqlMapClientTemplate().queryForList("queryPublisher", new Publisher());
	}

	public Publisher getPublisher(Long id) {
		Publisher publisher = new Publisher();
		publisher.setId(id);

		return (Publisher)getSqlMapClientTemplate().queryForObject("queryPublisher", publisher);
	}

}
<?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="Publisher">
    <select id="queryPublisher" parameterClass="com.ziqoo.entity.Publisher" resultClass="com.ziqoo.entity.Publisher">
    	select id, name, address
    	from publisher
    	<dynamic prepend="where">
    	    <isNotEmpty property="id">
    		id = #id#
    	    </isNotEmpty>

    	</dynamic>
    </select>
</sqlMap>

BookDao

BookDaoも同様にcom.ziqoo.dao.ibatisパッケージ下に作成します。
先にBookDao.javaの内容を示します。

package com.ziqoo.dao.ibatis;

import java.util.HashMap;
import java.util.List;
import java.util.Map;

import org.springframework.orm.ibatis.support.SqlMapClientDaoSupport;

import com.ziqoo.dao.IBookDao;
import com.ziqoo.entity.Book;
/**
 * iBATISによる書籍情報アクセスクラス
 *
 */
public class BookDao extends SqlMapClientDaoSupport implements IBookDao {

	public Book getBook(Long id) {
		Map map = new HashMap();
		map.put("id", id);
		return (Book)getSqlMapClientTemplate().queryForList("queryBook", map);
	}

	public List getBooks(String publisherName, String bookTitle,
			String authorName) {
		Map map = new HashMap();
		map.put("publisherName", publisherName);
		map.put("title", bookTitle);
		map.put("authorName", authorName);
		return getSqlMapClientTemplate().queryForList("queryBook", map);
	}

	public void delete(Book book) {
		getSqlMapClientTemplate().delete("deleteBook", book.getId());

	}

	public void save(Book book) {
		Map map = new HashMap();
		map.put("title", book.getTitle());
		map.put("authorId", book.getAuthor().getId());
		map.put("publisherId", book.getPublisher().getId());
		Long id = book.getId();
		if ( id == null){
			id = (Long)getSqlMapClientTemplate().insert("insertBook", map);
			book.setId(id);
		} else {
			map.put("id", id);
			getSqlMapClientTemplate().update("updateBook", map);
		}
	}

}
まず、getBookとgetBooksです。
まえの2つのDaoとの違いは引数にMapクラスを使っているところです。
対応するマッピングは以下のようになります。

    <resultMap id="resultMap" class="com.ziqoo.entity.Book">

        <result property="id" column="id" />
        <result property="title" column="title" />
        <result property="publisher" column="publisherId" select="getPublisher" />
        <result property="author" column="authorId" select="getAuthor" />
    </resultMap>
    
    <select id="queryBook" parameterClass="java.util.Map" resultMap="resultMap">

    	select b.id, b.title, b.publisherId, b.authorId
    	from book b
    	<dynamic>
    		<isNotEmpty property="publisherName">
    			join publisher p on b.publisherId = p.id
    		</isNotEmpty>
    		<isNotEmpty property="authorName">
	    		join author a on b.authorId = a.id
    		</isNotEmpty>

    	</dynamic>
    	<dynamic prepend="where">
    		<isNotEmpty prepend="and" property="id">
    			b.id = #id#
    		</isNotEmpty>
    		<isNotEmpty prepend="and" property="title">
    			b.title = #title#
    		</isNotEmpty>

    		<isNotEmpty prepend="and" property="publisherName">
    			p.name = #publisherName#
    		</isNotEmpty>
    		<isNotEmpty prepend="and" property="authorName">
    			a.name = #authorName#
    		</isNotEmpty>
    	</dynamic>

    </select>
    
    <select id="getPublisher" resultClass="com.ziqoo.entity.Publisher">
        select id, name, address
	from publisher
    	where
	    id = #value#
    </select>
    <select id="getAuthor" resultClass="com.ziqoo.entity.Author">
        select id, name
	from author
    	where
	    id = #value#
    </select>

ちょっと複雑になってますが、これは結果を格納するBookエンティティがAuthorとPublisherエンティティを
内部にプロパティとして持っている為です。
resultMapタグで、検索結果をどのプロパティにマッピングするか指定しています。
propertyのauthorとpublisherのところで、入れ子になっているauthorとpublisherへの
マッピング方法を指定しています。
例えばpublisherなら検索結果のpublisherIdを引数にしてgetPublisherを実行し、
結果をセットしなさいという意味です。
そしてgetPublisherは以下のようになっています。
    <select id="getPublisher" resultClass="com.ziqoo.entity.Publisher">
        select id, name, address
	from publisher
    	where
		id = #value#
    </select>
authorも同様です。 queryBookでは結果の格納方法として先に示したresultMapを指定しています。
    <select id="queryBook" parameterClass="java.util.Map" resultMap="resultMap">