/**
 * ÀÌ ¼Ò½º´Â Spring ÇÁ·¹ÀÓ¿öÅ© ¿öÅ©ºÏ¿¡¼­ »ç¿ëÇÑ ¿¹Á¦ ¼Ò½ºÀÔ´Ï´Ù. 
 * ÀÌ ¼Ò½º´Â ¸ðµç °³¹ßÀÚµéÀÌ ÀÚÀ¯·Ó°Ô ¼öÁ¤ ¹× ¹èÆ÷ÇÒ ¼ö ÀÖ½À´Ï´Ù. 
 * ´Ü, ÀÌ ¼Ò½º¸¦ ±â¹ÝÀ¸·Î »õ·Î¿î ¾ÖÇÃ¸®ÄÉÀÌ¼ÇÀ» °³¹ßÇÒ °æ¿ì ÃâÃ³¸¦ ¸í½ÃÇØ ÁÖ½Ã¸é µË´Ï´Ù. 
 */
package net.javajigi.board.dao;

import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Types;
import java.util.Iterator;
import java.util.List;

import javax.sql.DataSource;

import net.javajigi.board.model.BoardFile;
import net.javajigi.common.dao.MyJdbcDaoSupport;

import org.springframework.dao.DataAccessException;
import org.springframework.jdbc.core.SqlParameter;
import org.springframework.jdbc.object.BatchSqlUpdate;
import org.springframework.jdbc.object.MappingSqlQuery;
import org.springframework.jdbc.object.SqlUpdate;

/**
 * ÁÖ¼®À» ³Ö¾î ÁÖ¼¼¿ä. ¹è°¡ °íÆÄ¿ä.
 * 
 * @author ¹ÚÀç¼º(ÀÚ¹ÙÁö±â, javajigi@gmail.com)
 */
public class SpringJDBCWithMSBoardFileDAO extends MyJdbcDaoSupport implements
        BoardFileDAO {
    private SelectByBoardFileNo selectByBoardFileNo;

    private DeleteByBoardNo deleteByBoardNo;

    private DeleteByBoardFileNo deleteByBoardFileNo;

    private SelectList selectList;

    protected void initDao() throws Exception {
        super.initDao();

        deleteByBoardNo = new DeleteByBoardNo(getDataSource());
        deleteByBoardFileNo = new DeleteByBoardFileNo(getDataSource());
        selectByBoardFileNo = new SelectByBoardFileNo(getDataSource());
        selectList = new SelectList(getDataSource());
    }

    /*
     * (non-Javadoc)
     * 
     * @see net.javajigi.board.dao.BoardFileDAO#insert(java.util.List)
     */
    public int insert(int boardNo, List boardFileList)
            throws DataAccessException {
        BatchSqlUpdate boardFileInsert = new BatchSqlUpdate(getDataSource(),
                getMessageSourceAccessor().getMessage("boardfile.sql.insert"));
        boardFileInsert.declareParameter(new SqlParameter("fileNo",
                Types.INTEGER));
        boardFileInsert.declareParameter(new SqlParameter("boardNo",
                Types.INTEGER));
        boardFileInsert.declareParameter(new SqlParameter("fileSize",
                Types.INTEGER));
        boardFileInsert.declareParameter(new SqlParameter("fileName",
                Types.VARCHAR));
        boardFileInsert.declareParameter(new SqlParameter("contentType",
                Types.VARCHAR));
        boardFileInsert.declareParameter(new SqlParameter("tempFileName",
                Types.VARCHAR));
        boardFileInsert.compile();

        Iterator boardFileIter = boardFileList.iterator();
        while (boardFileIter.hasNext()) {
            BoardFile boardFile = (BoardFile) boardFileIter.next();
            int boardFileNo = getIncrementer().nextIntValue();

            boardFileInsert.update(new Object[] { new Integer(boardFileNo),
                    new Integer(boardNo), new Long(boardFile.getFileSize()),
                    boardFile.getFileName(), boardFile.getContentType(),
                    boardFile.getTempFileName() });
        }
        int result[] = boardFileInsert.flush();

        int insertResult = 0;
        for (int i = 0; i < result.length; i++) {
            insertResult += result[i];
        }
        return insertResult;
    }

    /*
     * (non-Javadoc)
     * 
     * @see net.javajigi.board.dao.BoardFileDAO#deleteByBoardFileNo(int)
     */
    public int deleteByBoardFileNo(int boardFileNo) throws DataAccessException {
        return deleteByBoardFileNo.update(boardFileNo);
    }

    public int deleteByBoardNo(int boardNo) throws DataAccessException {
        return deleteByBoardNo.update(boardNo);
    }

    public BoardFile findBoardFile(int boardFileNo) throws DataAccessException {
        BoardFile boardFile = (BoardFile) selectByBoardFileNo
                .findObject(boardFileNo);
        return boardFile;
    }

    /*
     * (non-Javadoc)
     * 
     * @see net.javajigi.board.dao.BoardFileDAO#findBoardFileList(int)
     */
    public List findBoardFileList(int boardNo) throws DataAccessException {
        return selectList.execute(boardNo);
    }

    class DeleteByBoardNo extends SqlUpdate {
        public DeleteByBoardNo(DataSource dataSource) {
            super(dataSource, getMessageSourceAccessor().getMessage(
                    "boardfile.sql.delete.byboardno"));

            declareParameter(new SqlParameter(Types.INTEGER));
        }
    }

    class DeleteByBoardFileNo extends SqlUpdate {
        public DeleteByBoardFileNo(DataSource dataSource) {
            super(dataSource, getMessageSourceAccessor().getMessage(
                    "boardfile.sql.delete.byboardfileno"));

            declareParameter(new SqlParameter(Types.INTEGER));
        }
    }

    class SelectByBoardFileNo extends MappingSqlQuery {
        protected SelectByBoardFileNo(DataSource ds) {
            super(ds, getMessageSourceAccessor().getMessage(
                    "boardfile.sql.select.byboardfileno"));
            declareParameter(new SqlParameter(Types.INTEGER));
        }

        protected Object mapRow(ResultSet rs, int rownum) throws SQLException {
            BoardFile boardFile = new BoardFile();
            boardFile.setFileNo(rs.getInt("fileNo"));
            boardFile.setFileSize(rs.getInt("fileSize"));
            boardFile.setFileName(rs.getString("fileName"));
            boardFile.setContentType(rs.getString("contentType"));
            boardFile.setTempFileName(rs.getString("tempFileName"));

            return boardFile;
        }
    }

    class SelectList extends MappingSqlQuery {
        protected SelectList(DataSource ds) {
            super(ds, getMessageSourceAccessor().getMessage(
                    "boardfile.sql.select.byboardno"));
            declareParameter(new SqlParameter(Types.INTEGER));
        }

        protected Object mapRow(ResultSet rs, int rownum) throws SQLException {
            BoardFile boardFile = new BoardFile();
            boardFile.setFileNo(rs.getInt("fileNo"));
            boardFile.setFileSize(rs.getInt("fileSize"));
            boardFile.setFileName(rs.getString("fileName"));

            return boardFile;
        }
    }
}
