/*********************************************************************
*  All Rights reserved,Copyright (c) K-Opticom
**********************************************************************
*＜プログラム内容＞
*	システム名			：eo顧客基幹システム
*	モジュール名		：JBSBatCKOutHuryoCstInfStk
*	ソースファイル名	：JBSBatCKOutHuryoCstInfStk.java
*	作成者				：富士通　
*	作成日				：2012年01月27日
*＜機能概要＞
*　外部不良顧客情報取得部品です。
*＜修正履歴＞
*	バージョン	修正日		修正者		修正内容
*	v1.00.00	2012/01/27   FJ)藤本	新規作成
*	v3.00.00	2012/09/06	FAP)神吉	【ST1-2012-0000524】顧客電子ファイル管理登録対応
*	v3.01.00	2012/12/04	FJ)柳		【ST4_2012_0000139】圧縮解凍対応
*	v4.00.00	2013/03/30   FJ)強矢	【IKK-2013-0000650】性能改善対応 (ST3-2012-0000490)
*********************************************************************/
package eo.business.service;

import java.io.BufferedInputStream;
import java.io.ByteArrayOutputStream;
import java.io.File;
import java.io.FileInputStream;
import java.sql.SQLException;

import eo.business.common.JBSbatBusinessService;
import eo.business.common.JCCBatCommon;
import eo.business.common.JCCbatDenshiFileUtil;
import eo.business.common.JKKBatConst;
import eo.business.util.file.JBSbatCKIFM004;
import eo.business.util.table.JBSbatCK_T_CUST_EFILE_KNRI;
import eo.common.util.JCCFileUtil;
import eo.common.util.JCCFrameworkException;
import eo.common.util.JCCUnCompressFileUtil;
import eo.framework.application.JCCbatFrameworkException;
import eo.framework.db.JBSbatSQLAccess;
import eo.framework.item.JBSbatCommonDBInterface;
import eo.framework.item.JBSbatCommonItem;
import eo.framework.item.JBSbatOutputItem;
import eo.framework.item.JBSbatServiceInterfaceMap;
import eo.framework.util.JBSbatOracleSeqUtil;
import eo.framework.util.JBSbatStringUtil;

/**
* (クラスの機能概要) <p>
*<BR>
* @author 富士通
*/
public class JBSbatCKOutHuryoCstInfStk extends JBSbatBusinessService
{
	/**▼▼▼▼▼▼ツールから生成した宣言です 開始▼▼▼▼▼▼*/
	/** テーブル(顧客電子ファイル管理)*/
	private static final String D_TBL_NAME_CK_T_CUST_EFILE_KNRI = "CK_T_CUST_EFILE_KNRI";

	/** テーブルアクセスクラス(顧客電子ファイル管理)*/
	private JBSbatSQLAccess db_CK_T_CUST_EFILE_KNRI = null;
	/**▲▲▲▲▲▲ツールから生成した宣言です 終了▲▲▲▲▲▲*/
	
	/**
	 * 初期処理
	 * @param JBSbatCommonItem commonItem　バッチ共通パラメータ電文
	 * @throws Exception
	 */
	public void initial(JBSbatCommonItem commonItem) throws Exception
	{
	/**▼▼▼▼▼▼業務サービスの初期処理を記述してください。▼▼▼▼▼▼*/
		/**▼▼▼▼▼▼ツールから生成した初期化のソースです 開始▼▼▼▼▼▼*/
		// 共通パラメータを設定します
		super.setCommonInfo(commonItem);
		
		// DBアクセスクラスを生成します
		db_CK_T_CUST_EFILE_KNRI = new JBSbatSQLAccess(commonItem, D_TBL_NAME_CK_T_CUST_EFILE_KNRI);
		/**▲▲▲▲▲▲ツールから生成した初期化のソースです 終了▲▲▲▲▲▲*/
	/**▲▲▲▲▲▲業務サービスの初期処理を記述してください。▲▲▲▲▲▲*/
	}

	/**
	 * 主処理
	 * @param inMap　入力電文
	 * @return JBSbatOutputItem　出力情報
	 * @throws Exception
	 */
	public JBSbatOutputItem execute(JBSbatServiceInterfaceMap inMap) throws Exception
	{
	/**▼▼▼▼▼▼業務サービスの主処理を記述してください。▼▼▼▼▼▼*/
		
		super.logPrint.printDebugLog("execute_START");
		
		// 出力ファイル用クラスの生成
		JBSbatOutputItem out_item = new JBSbatOutputItem();
		
		// 顧客電子ファイル管理検索結果より電子ファイル処理状態フラグを取得します。
		String efileTrnStatFlg = JBSbatStringUtil.Rtrim(inMap.getString(JBSbatCK_T_CUST_EFILE_KNRI.EFILE_TRN_STAT_FLG));
		
		// 顧客電子ファイル管理検索結果より電子ファイル管理番号を取得します。
		String efile_kanri_no = JBSbatStringUtil.Rtrim(inMap.getString(JBSbatCK_T_CUST_EFILE_KNRI.EFILE_KANRI_NO));
		//解凍顧客電子ファイル取得
		byte[] efile = getDenshiFileByte(super.commonItem,efile_kanri_no);
		if(efile == null){
			return null;
		}
		String efileStr = new String(efile,"MS932");

		// 結果が格納されていたら且つ、顧客電子ファイル管理検索結果の電子ファイル処理状態フラグ <> "1"（処理済）
		if(null != efileStr && efileStr.length() >0 && !"1".equals(efileTrnStatFlg))
		{
			// ファイル項目数が12項目のファイル判定フラグ
			boolean flg = false;

			// 「電子ファイル」を取得し改行コードで分割します（CCIFE001のファイルが格納）
			String[] strFile = efileStr.split(JKKBatConst.S_LINE_SEPARAOR_LF);
			for(int i = 0; i < strFile.length; i++)
			{
				// 出力ファイル用クラスの生成
				JBSbatServiceInterfaceMap out_map = new JBSbatServiceInterfaceMap();
				
				// カンマで分割し、"（ダブルクォート）をカットします。
				String[] strCKIFE001 = strFile[i].replaceAll("\"", "").split(JKKBatConst.CONMA);
				
				// 項目数が12項目ではない場合、スキップします。
				if(12 != strCKIFE001.length)
				{
					super.logPrint.printDebugLog("CKIFE001項目数が12ではないので出力しません：" + strCKIFE001.length);
					continue;
				}
				
				// 「不良顧客番号」
				out_map.setString(JBSbatCKIFM004.HURYO_CUST_NO, 
						JBSbatStringUtil.padNumFormString(JBSbatOracleSeqUtil.getNextSeq(commonItem.getConnection(), "SEQ_HURYO_CUST_NO"), 12));
				// 「不良顧客登録コード」→ 02：加入者交換
				out_map.setString(JBSbatCKIFM004.HURYO_CUST_ADD_CD, "02");
				// 「加入者交換出力開始年月」
				out_map.setString(JBSbatCKIFM004.KNYSHA_KOKAN_OUTPUT_STA_YM, "");
				// 「ＳＹＳＩＤ」
				out_map.setString(JBSbatCKIFM004.SYSID, "");
				// 「請求契約番号」
				out_map.setString(JBSbatCKIFM004.SEIKY_KEI_NO, "");
				// 「サービス契約番号」
				out_map.setString(JBSbatCKIFM004.SVC_KEI_NO, "");
				// 「顧客番号」→ 加入者交換情報受信ファイル．顧客番号
				out_map.setString(JBSbatCKIFM004.CUST_NO, JBSbatStringUtil.Rtrim(strCKIFE001[9]));
				// 「督促番号」
				out_map.setString(JBSbatCKIFM004.TOKUSOKU_NO, "");
				// 「多重申込グループコード」
				out_map.setString(JBSbatCKIFM004.TAJU_MSKM_GRP_CD, "");
				// 「契約者タイプコード」
				out_map.setString(JBSbatCKIFM004.KEISHA_TYPE_CD, "");
				// 「不良顧客名」→ 加入者交換情報受信ファイル．漢字氏名
				out_map.setString(JBSbatCKIFM004.HURYO_CUST_NM, JBSbatStringUtil.Rtrim(strCKIFE001[1]));
				// 「不良顧客カナ名」→ 加入者交換情報受信ファイル．カナ氏名
				out_map.setString(JBSbatCKIFM004.HURYO_CUST_KANA, JBSbatStringUtil.Rtrim(strCKIFE001[0]));
				// 「不良顧客性別コード」→ 加入者交換情報受信ファイル．性別
				String sex_cd = JBSbatStringUtil.trim(strCKIFE001[3]);
				if(!"".equals(sex_cd))
				{
					// 数値変換を行い、1：男性、2：女性の場合は変換した数値を設定
					int sex_cd_int = Integer.parseInt(sex_cd);
					if(1 == sex_cd_int || 2 == sex_cd_int)
					{
						out_map.setString(JBSbatCKIFM004.HURYO_CUST_SEX_CD, sex_cd_int);
					}
					// 以外は3：不明を設定する。
					else
					{
						out_map.setString(JBSbatCKIFM004.HURYO_CUST_SEX_CD, "3");
					}
				}
				else
				{
					out_map.setString(JBSbatCKIFM004.HURYO_CUST_SEX_CD, "3");
				}
				// 「不良顧客生年月日」→ 加入者交換情報受信ファイル．生年月日
				out_map.setString(JBSbatCKIFM004.HURYO_CUST_BIRTHD, JBSbatStringUtil.Rtrim(strCKIFE001[2]));
				// 「不良顧客電話番号」→ 加入者交換情報受信ファイル．契約者電話番号
				out_map.setString(JBSbatCKIFM004.HURYO_CUST_TELNO, JBSbatStringUtil.Rtrim(strCKIFE001[7]));
				// 「不良顧客移動電話番号」→ 加入者交換情報受信ファイル．移動電話番号
				out_map.setString(JBSbatCKIFM004.HURYO_CUST_MOVE_TELNO, JBSbatStringUtil.Rtrim(strCKIFE001[8]));
				// 「不良顧客住所コード」→ 加入者交換情報受信ファイル．住所コード
				out_map.setString(JBSbatCKIFM004.HURYO_CUST_AD_CD, JBSbatStringUtil.Rtrim(strCKIFE001[6]));
				// 「不良顧客郵便番号」→ 加入者交換情報受信ファイル．郵便番号
				out_map.setString(JBSbatCKIFM004.HURYO_CUST_PCD, JBSbatStringUtil.Rtrim(strCKIFE001[4]));
				// 「不良顧客都道府県名」
				out_map.setString(JBSbatCKIFM004.HURYO_CUST_STATE_NM, "");
				// 「不良顧客市区町村名」
				out_map.setString(JBSbatCKIFM004.HURYO_CUST_CITY_NM, "");
				// 「不良顧客大字通称名」
				out_map.setString(JBSbatCKIFM004.HURYO_CUST_OAZTSU_NM, "");
				// 「不良顧客字丁目名」
				out_map.setString(JBSbatCKIFM004.HURYO_CUST_AZCHO_NM, "");
				// 「不良顧客住所名」→ 加入者交換情報受信ファイル．漢字契約者住所
				out_map.setString(JBSbatCKIFM004.HURYO_CUST_AD_NM, JBSbatStringUtil.Rtrim(strCKIFE001[5]));
				// 「不良顧客番地号」
				out_map.setString(JBSbatCKIFM004.HURYO_CUST_BNCHIGO, "");
				// 「不良顧客住所補記・建物名」
				out_map.setString(JBSbatCKIFM004.HURYO_CUST_ADRTTM, "");
				// 「不良顧客住所補記・部屋番号」
				out_map.setString(JBSbatCKIFM004.HURYO_CUST_ADRRM, "");
				// 「不良顧客住所手動入力フラグ」
				out_map.setString(JBSbatCKIFM004.HRYCST_AD_MAN_INPUT_FLG, "");
				// 「職業コード」
				out_map.setString(JBSbatCKIFM004.SHOKUGYO_CD, "");
				// 「業種コード」
				out_map.setString(JBSbatCKIFM004.GSHU_CD, "");
				// 「親権者続柄コード」
				out_map.setString(JBSbatCKIFM004.SKSHA_ZOKUGARA_CD, "");
				// 「滞納額」→ 加入者交換情報受信ファイル．滞納金額（CIFE001ファイルの最終項目の改行コードをカット）
				out_map.setString(JBSbatCKIFM004.NONPAY_AMNT, JBSbatStringUtil.Rtrim(strCKIFE001[11]).replaceAll("\r", ""));
				// 「不良顧客事業者コード」→ 加入者交換情報受信ファイル．事業者コード(先頭の４桁)
				String jigyosha_cd = JBSbatStringUtil.Rtrim(strCKIFE001[10]);
				if(4 <= jigyosha_cd.length())
				{
					out_map.setString(JBSbatCKIFM004.HURYO_CUST_JIGYOSHA_CD, jigyosha_cd.substring(0, 4));
				}
				else
				{
					out_map.setString(JBSbatCKIFM004.HURYO_CUST_JIGYOSHA_CD, "");
					super.logPrint.printDebugLog("加入者交換情報受信ファイル．事業者コードが8桁で設定されていません：" + jigyosha_cd);
				}
				// 「不良顧客補足備考」
				out_map.setString(JBSbatCKIFM004.HURYO_CUST_HSK_BIKO, "");
				
				out_map.setOutFlg(true);
				out_item.addOutMapList(out_map);
				
				// ファイル項目数が12項目のファイル判定フラグへ「true」を設定
				flg = true;
			}
			
			// ファイル項目数が12項目のファイル判定フラグが「true」の場合
			if (flg)
			{
				// 顧客電子ファイル管理テーブル登録
				insertCustEfileKnri(inMap);
			}
		}
		
		super.logPrint.printDebugLog("execute_END");
		
		return out_item;
	/**▲▲▲▲▲▲業務サービスの主処理を記述してください。▲▲▲▲▲▲*/
	}

	
	/**
	 * 業務サービス終了処理
	 * @throws Exception
	 */
	public void terminal() throws Exception
	{
	/**▼▼▼▼▼▼業務サービスの終了処理を記述してください。▼▼▼▼▼▼*/
		/**▼▼▼▼▼▼ツールから生成した終了処理のソースです 開始▼▼▼▼▼▼*/
		// DBアクセスクラスをクローズします
		db_CK_T_CUST_EFILE_KNRI.close();
		/**▲▲▲▲▲▲ツールから生成した終了処理のソースです 終了▲▲▲▲▲▲*/
	/**▲▲▲▲▲▲業務サービスの終了処理を記述してください。▲▲▲▲▲▲*/
	}

	/**▼▼▼▼▼▼ツールから生成したメソッドです 開始▼▼▼▼▼▼*/
	/**
	 * PK(全項目登録)でDBアクセスを行います。<br>
	 * <p>
	 * <b>処理フロー</b><br>
	 * <pre>
	 * 1.引数で設定項目マップを作ります。<br>
	 *
	 * 2.DBアクセスを実行します。<br>
	 * 
	 * 3.メソッドの呼び出し方です。<br>
	 *		引数:
	 *		setParam:設定したい項目の(項目、値)を(key、value)として、setParamマップに入れます。項目キーは以下に説明します。
	 *		 	電子ファイル管理番号				EFILE_KANRI_NO
	 *		 	世代登録年月日時分秒				GENE_ADD_DTM
	 *		 	電子ファイル作成年月日時分秒				EFILE_SAKSEI_DTM
	 *		 	顧客電子ファイル種別コード				CUST_EFILE_SBT_CD
	 *		 	電子ファイル種別番号				EFILE_SBT_NO
	 *		 	電子ファイル名				EFILE_NM
	 *		 	電子ファイル処理状態フラグ				EFILE_TRN_STAT_FLG
	 *		 	登録年月日時分秒				ADD_DTM
	 *		 	登録オペレータアカウント				ADD_OPEACNT
	 *		 	更新年月日時分秒				UPD_DTM
	 *		 	更新オペレータアカウント				UPD_OPEACNT
	 *		 	削除年月日時分秒				DEL_DTM
	 *		 	削除オペレータアカウント				DEL_OPEACNT
	 *		 	無効フラグ				MK_FLG
	 *		 	登録運用年月日				ADD_UNYO_YMD
	 *		 	登録処理ＩＤ				ADD_TRN_ID
	 *		 	更新運用年月日				UPD_UNYO_YMD
	 *		 	更新処理ＩＤ				UPD_TRN_ID
	 *		 	削除運用年月日				DEL_UNYO_YMD
	 *		 	削除処理ＩＤ				DEL_TRN_ID
	 * </pre>
	 * <p>
	 * @param setParam 設定項目の値。
	 * @throws Exception 業務サービス内で発生した例外全般。
	 */
	private void executeCK_T_CUST_EFILE_KNRI_PKINSERT(Object[] setParam) throws Exception
	{
		// 設定値のマップを作成します
		JBSbatCommonDBInterface setMap = new JBSbatCommonDBInterface();
		setMap.setValue("EFILE_KANRI_NO", setParam[0]);
		setMap.setValue("GENE_ADD_DTM", setParam[1]);
		setMap.setValue("EFILE_SAKSEI_DTM", setParam[2]);
		setMap.setValue("CUST_EFILE_SBT_CD", setParam[3]);
		setMap.setValue("EFILE_SBT_NO", setParam[4]);
		setMap.setValue("EFILE_NM", setParam[5]);
		setMap.setValue("EFILE_TRN_STAT_FLG", setParam[6]);
		setMap.setValue("ADD_DTM", setParam[7]);
		setMap.setValue("ADD_OPEACNT", setParam[8]);
		setMap.setValue("UPD_DTM", setParam[9]);
		setMap.setValue("UPD_OPEACNT", setParam[10]);
		setMap.setValue("DEL_DTM", setParam[11]);
		setMap.setValue("DEL_OPEACNT", setParam[12]);
		setMap.setValue("MK_FLG", setParam[13]);
		setMap.setValue("ADD_UNYO_YMD", setParam[14]);
		setMap.setValue("ADD_TRN_ID", setParam[15]);
		setMap.setValue("UPD_UNYO_YMD", setParam[16]);
		setMap.setValue("UPD_TRN_ID", setParam[17]);
		setMap.setValue("DEL_UNYO_YMD", setParam[18]);
		setMap.setValue("DEL_TRN_ID", setParam[19]);
	
		// DBアクセスを実行します
		db_CK_T_CUST_EFILE_KNRI.insertByPrimaryKeys(setMap);
	}
	/**▲▲▲▲▲▲ツールから生成したメソッドです 終了▲▲▲▲▲▲*/
	
	/**
	 * 
	 * 顧客電子ファイル管理登録処理を行います。
	 * 
	 * @param JBSbatServiceInterfaceMap inMap
	 * 
	 * @throws Exception メソッド内で発生した例外全般。
	 */
	private void insertCustEfileKnri(JBSbatServiceInterfaceMap inMap) throws Exception
	{
		// 顧客電子ファイル管理検索結果より電子ファイル管理番号を取得します。
		String efileKanriNo = JBSbatStringUtil.Rtrim(inMap.getString(JBSbatCK_T_CUST_EFILE_KNRI.EFILE_KANRI_NO));
		
		// 顧客電子ファイル管理検索結果より電子ファイル作成年月日時分秒を取得します。
		String efileSakuseiDtm = JBSbatStringUtil.Rtrim(inMap.getString(JBSbatCK_T_CUST_EFILE_KNRI.EFILE_SAKSEI_DTM));
		
		// 顧客電子ファイル管理検索結果より顧客電子ファイル種別コードを取得します。
		String custEfileSbtCd = JBSbatStringUtil.Rtrim(inMap.getString(JBSbatCK_T_CUST_EFILE_KNRI.CUST_EFILE_SBT_CD));
		
		// 顧客電子ファイル管理検索結果より電子ファイル種別番号を取得します。
		String efileSbtNo = JBSbatStringUtil.Rtrim(inMap.getString(JBSbatCK_T_CUST_EFILE_KNRI.EFILE_SBT_NO));
		
		// 顧客電子ファイル管理検索結果より電子ファイル名を取得します。
		String efileNm = JBSbatStringUtil.Rtrim(inMap.getString(JBSbatCK_T_CUST_EFILE_KNRI.EFILE_NM));
		
		// システム日付を取得
		String sysDate = JCCBatCommon.getSysDateTimeStamp();
		
		// 登録する顧客電子ファイル管理のパラメータを設定します
		String [] setParam = {
				efileKanriNo,
				sysDate,
				efileSakuseiDtm,
				custEfileSbtCd,
				efileSbtNo,
				efileNm,
				"1",
				sysDate,
				batchUserId,
				sysDate,
				batchUserId,
				"",
				"",
				"0",
				"",
				"",
				"",
				"",
				"",
				""};
		
		executeCK_T_CUST_EFILE_KNRI_PKINSERT(setParam);
	}
	
	/**
	 * 電子ファイルをbyteの配列に変換します。
	 * 
	 * @param cmnItem 業務共通電文クラス
	 * @param eFileKanriNo 電子ファイル管理番号
	 * @return 変換後のbyteの配列
	 * @throws Exception 
	 * @throws SQLException 
	 */
	private byte[] getDenshiFileByte(JBSbatCommonItem cmnItem,String eFileKanriNo) throws Exception
	{
		if(null == eFileKanriNo || "".equals(eFileKanriNo)){
			return null;
		}
		BufferedInputStream in = null;
		ByteArrayOutputStream baos = null;
		byte reb[] = null; 
		String unZipPath = null;
		String path = null;
		try
		{
			//電子ファイル管理テーブルからファイルの取得処理
		    path = JCCbatDenshiFileUtil.searchDenshiFile(cmnItem, eFileKanriNo);

			if(null == path){
				return null;
			}

			String parentPath = new File(path).getParent();
			
			//ファイル解凍
			unZipPath = JCCUnCompressFileUtil.uncompressFile(path, parentPath, "0");
			
			in = new BufferedInputStream(new FileInputStream( unZipPath ));
			baos = new ByteArrayOutputStream();
			byte btmp[] = new byte[1024]; 
			int j;
			while((j = in.read(btmp))!=-1){
				baos.write(btmp, 0, j);
			}
			
			reb = baos.toByteArray();

		}
		catch (Exception e)
		{
			throw new JCCbatFrameworkException( "ファイルをbyteの配列変換に失敗しました。" + e);
		}
		finally
		{
			
			if (null != in)
			{
				try {
					in.close();
				} catch (Exception e) {
					;//なにもしない
				}
			}
			if (null != baos)
			{
				try {
					baos.close();
				} catch (Exception e) {
					;//なにもしない
				}
			}
			
			//作業用ファイルの削除
			removeDir(unZipPath);

		}

		return reb;
	}
	
	/**
	 * 引数のファイルが残っている場合、そのファイルが入っているディレクトリごと削除する。
	 * @param filePath 削除対象のファイルパス
	 * @throws JCCFrameworkException
	 */
	private void removeDir(String filePath) throws JCCFrameworkException
	{
		// 作業ディレクトリが残っていた場合、削除
		if(filePath != null)
		{
			File f_dir = new File(new File(filePath).getParent());
			if(f_dir.exists())
			{
				JCCFileUtil.removeDir(new File(filePath).getParent());
			}
		}
	}
}
