/*
 * FixedLengthRecordWriterTest.java
 * Copyright (C) 2008 Cyber Beans Corporation. All rights reserved.
 */
package jp.co.cybec.cb3.accessor.fileaccess.flat.fixed;

import java.util.LinkedHashMap;

import jp.co.cybec.cb3.accessor.fileaccess.flat.FlatFileRecord;
import jp.co.cybec.cb3.accessor.fileaccess.flat.fixed.FixedLengthRecordWriter;
import jp.co.cybec.cb3.exception.AccessorNotOpenException;
import jp.co.cybec.cb3.exception.ConfigFileNotFoundException;
import jp.co.cybec.cb3.exception.DataFormatException;

import org.junit.After;
import org.junit.Before;
import org.junit.Test;

/**
 * {@link FixedLengthRecordWriter} のテストケース。
 * @author Sufang Gou
 */

public class FixedLengthRecordWriterTest {
	// クラスをインスタンスする
	private FixedLengthRecordWriter target = null;
	private FlatFileRecord record;

	/** 設定ファイル 正常 */
	private static final String CONFIG_WRITER1 = "jp/co/cybec/cb3/accessor/fileaccess/flat/fixed/writer/writeConfig1.xml";
	private static final String CONFIG_WRITER2 = "jp/co/cybec/cb3/accessor/fileaccess/flat/fixed/writer/writeConfig2.xml";

	/** 設定データファイルの記述が正しくない */
	private static final String CONFIG_WRITER_PARSE_ERROR1 = "jp/co/cybec/cb3/accessor/fileaccess/flat/fixed/writer/writeConfig3.xml";
	private static final String CONFIG_WRITER_PARSE_ERROR2 = "jp/co/cybec/cb3/accessor/fileaccess/flat/fixed/writer/writeConfig4.xml";
	private static final String CONFIG_WRITER_PARSE_ERROR3 = "jp/co/cybec/cb3/accessor/fileaccess/flat/fixed/writer/writeConfig5.xml";

	/** 正常データファイル */
	private static final String FILE_NORMAL= "src/test/testdata/fixed/test_write.txt";

	/**
	 * @throws Exception
	 */
	@Before
	public void setUp() throws Exception {
		// クラスをインスタンスする
		target = new FixedLengthRecordWriter();
	}

	/**
	 * @throws Exception
	 */
	@After
	public void tearDown() throws Exception {
	}

	/**
	 * {@link FixedLengthRecordWriter#open(String)} のためのテスト・メソッド。
	 * 例外が発生しないことを確認する。
	 */
	@Test
	public void testOpenString() {
		target.initialize(CONFIG_WRITER1);
		target.open(FILE_NORMAL);
	}

	/**
	 * {@link FixedLengthRecordWriter#write(FlatFileRecord)} のためのテスト・メソッド。
	 * 例外が発生しないことを確認する
	 * append true
	 * encode Shift_JIS
	 * lineSeparator \r\n
	 */
	@Test
	public void testWrite01() {
		// テストデータ
		LinkedHashMap<String, String> fileRecordMap = new LinkedHashMap<String, String>();

		fileRecordMap.put("intField", "1111111111");
		fileRecordMap.put("strField1", "2222222222");
		fileRecordMap.put("strField2", "翻訳　先\"週の先週｛１２３｝");
		fileRecordMap.put("strField3", "www.bb@hotmail.com.cn");
		fileRecordMap.put("strField4", "10%");
		fileRecordMap.put("dateField1", "2007/05/28 00:00:00");
		fileRecordMap.put("dateField2", "2001/11/05 00:00:00");
		fileRecordMap.put("dateField3", "2001/10/05 08:01:00");
		fileRecordMap.put("dateField4", "2001/09/29 00:00:00");
		fileRecordMap.put("dateField5", "2001/09/10 10:10:010");
		fileRecordMap.put("longField", "123456789120325");
		fileRecordMap.put("shortField", "1045852642");
		fileRecordMap.put("bigField1", "1897512535544585264.2");
		fileRecordMap.put("bigField2", "18975125355445852642");
		fileRecordMap.put("floatField", "5125355445852642.2");

		// 設定ファイルを読み込む。
		target.initialize(CONFIG_WRITER1);

		//ファイルをオープンする。
		target.open();

		// FlatFileRecordデータを作成する。
		record = target.createFlatFileRecord(fileRecordMap);

		// レコードの書き込み。
		target.write(record);
		target.write(record);
		target.write(record);

		// ファイルをクローズする。
		target.close();
	}
	/**
	 * {@link FixedLengthRecordWriter#write(FlatFileRecord)} のためのテスト・メソッド。
	 * 例外が発生しないことを確認する
	 * append false
	 * encode null
	 * lineSeparator null
	 */
	@Test
	public void testWrite02() {
		// テストデータ
		LinkedHashMap<String, String> fileRecordMap = new LinkedHashMap<String, String>();

		fileRecordMap.put("intField", "1111111111");
		fileRecordMap.put("strField1", "2222222222");
		fileRecordMap.put("strField2", "翻訳　先\"週の先週｛１２３｝");
		fileRecordMap.put("strField3", "www.bb@hotmail.com.cn");
		fileRecordMap.put("strField4", "10%");
		fileRecordMap.put("dateField1", "2007/05/28 00:00:00");
		fileRecordMap.put("dateField2", "2001/11/05 00:00:00");
		fileRecordMap.put("dateField3", "2001/10/05 08:01:00");
		fileRecordMap.put("dateField4", "2001/09/29 00:00:00");
		fileRecordMap.put("dateField5", "2001/09/10 10:10:010");
		fileRecordMap.put("longField", "123456789120325");
		fileRecordMap.put("shortField", "1045852642");
		fileRecordMap.put("bigField1", "1897512535544585264.2");
		fileRecordMap.put("bigField2", "18975125355445852642");
		fileRecordMap.put("floatField", "5125355445852642.2");

		// 設定ファイルを読み込む。
		target.initialize(CONFIG_WRITER2);

		//ファイルをオープンする。
		target.open();

		// FlatFileRecordデータを作成する。
		record = target.createFlatFileRecord(fileRecordMap);

		// レコードの書き込み。
		target.write(record);
		target.write(record);
		target.write(record);

		// ファイルをクローズする。
		target.close();

	}

	/**
	 * {@link FixedLengthRecordWriter#write(FlatFileRecord)} のためのテスト・メソッド。
	 * ファイルをオープンしないときに例外が発生することを確認する。
	 */
	@Test(expected = AccessorNotOpenException.class)
	public void testWrite03() {
		// テストデータ
		LinkedHashMap<String, String> fileRecordMap = new LinkedHashMap<String, String>();

		fileRecordMap.put("intField", "1111111111");
		fileRecordMap.put("strField1", "2222222222");
		fileRecordMap.put("strField3", "www.bb@hotmail.com.cn");
		fileRecordMap.put("strField4", "10%");
		fileRecordMap.put("dateField1", "2007/05/28 00:00:00");
		fileRecordMap.put("dateField2", "2001/11/05 00:00:00");
		fileRecordMap.put("dateField3", "2001/10/05 08:01:00");
		fileRecordMap.put("dateField4", "2001/09/29 00:00:00");
		fileRecordMap.put("dateField5", "2001/09/10 10:10:010");
		fileRecordMap.put("longField", "123456789120325");
		fileRecordMap.put("shortField", "1045852642");
		fileRecordMap.put("bigField1", "1897512535544585264.2");
		fileRecordMap.put("bigField2", "18975125355445852642");
		fileRecordMap.put("floatField", "5125355445852642.2");

		// 設定ファイルを読み込む。
		target.initialize(CONFIG_WRITER2);

		// FlatFileRecordデータを作成する。
		record = target.createFlatFileRecord(fileRecordMap);

		// レコードの書き込み。
		target.write(record);
		target.write(record);
		target.write(record);

		// ファイルをクローズする。
		target.close();
	}

	/**
	 * {@link FixedLengthRecordWriter#write(FlatFileRecord)} のためのテスト・メソッド。
	 * ユーザー定義クラスのインスタンス失敗するときに例外が発生することを確認する。
	 */
	@Test(expected = DataFormatException.class)
	public void testWrite04() {
		// テストデータ
		LinkedHashMap<String, String> fileRecordMap = new LinkedHashMap<String, String>();

		fileRecordMap.put("intField", "1111111111");

		// 設定ファイルを読み込む。
		target.initialize(CONFIG_WRITER_PARSE_ERROR1);

		//ファイルをオープンする。
		target.open();

		// FlatFileRecordデータを作成する。
		record = target.createFlatFileRecord(fileRecordMap);

		// レコードの書き込み。
		target.write(record);

		// ファイルをクローズする。
		target.close();
	}

	/**
	 * {@link FixedLengthRecordWriter#write(FlatFileRecord)} のためのテスト・メソッド。
	 * １行データのバイト数 <> 設定ファイルのバイト数合計のときに例外が発生することを確認する。
	 */
	@Test(expected = DataFormatException.class)
	public void testWrite05() {
		// テストデータ
		LinkedHashMap<String, String> fileRecordMap = new LinkedHashMap<String, String>();

		fileRecordMap.put("strField1", "");

		// 設定ファイルを読み込む
		target.initialize(CONFIG_WRITER_PARSE_ERROR2);

		//ファイルをオープンする。
		target.open();

		// FlatFileRecordデータを作成する。
		record = target.createFlatFileRecord(fileRecordMap);

		// レコードの書き込み。
		target.write(record);

		// ファイルをクローズする。
		target.close();
	}

	/**
	 * {@link FixedLengthRecordWriter#createFlatFileRecord(Map)} のためのテスト・メソッド。
	 * Mapはnullのときに例外が発生しないことを確認する。
	 */
	@Test
	public void testWrite06() {

		// FlatFileRecordデータを作成します。
		target.createFlatFileRecord(null);
	}

	/**
	 * {@link FixedLengthRecordWriter#write(FlatFileRecord)} のためのテスト・メソッド。
	 * データファイルのフォーマットを失敗するの場合、例外が発生することを確認する。
	 */
	@Test(expected = DataFormatException.class)
	public void testWrite07() {
		// テストデータ
		LinkedHashMap<String, String> fileRecordMap = new LinkedHashMap<String, String>();

		fileRecordMap.put("intField", "1111111111");

		// 設定ファイルを読み込む
		target.initialize(CONFIG_WRITER_PARSE_ERROR3);

		//ファイルをオープンする。
		target.open();

		// FlatFileRecordデータを作成する。
		record = target.createFlatFileRecord(fileRecordMap);

		// レコードの書き込み。
		target.write(record);

		// ファイルをクローズする。
		target.close();
	}

	/**
	 * {@link FixedLengthRecordWriter#write(FlatFileRecord)} のためのテスト・メソッド。
	 * データファイルはnullの場合、例外が発生しないことを確認する。
	 */
	@Test
	public void testWrite08() {
		// 設定ファイルを読み込む
		target.initialize(CONFIG_WRITER_PARSE_ERROR3);

		//ファイルをオープンする。
		target.open();

		// レコードの書き込み。
		target.write(null);

		// ファイルをクローズする。
		target.close();
	}

	/**
	 * {@link FixedLengthRecordWriter#initialize(String)} のためのテスト・メソッド。<br>
	 * 例外が発生しないことを確認する。
	 */
	@Test
	public void testInitialize() {
		// 設定ファイルを読み込む。
		target.initialize(CONFIG_WRITER1);
	}

	/**
	 * {@link FixedLengthRecordWriter#initialize(String)} のためのテスト・メソッド。<br>
	 * 引数に存在しないキー（設定ファイル）を指定したときに例外が発生することを確認する。
	 */
	@Test(expected = ConfigFileNotFoundException.class)
	public void testInitializeConfigFileNotFoundException() {
		// 設定ファイルを読み込む。
		target.initialize("aaa");
	}
}
