/*********************************************************************
* All Rights reserved,Copyright (c) K-Opticom
**********************************************************************
*＜プログラム内容＞
*   システム名      ：eo顧客基幹システム
*   モジュール名    ：JKUejbGetKojiDataUtil
*   ソースファイル名：JKUejbGetKojiDataUtil.java
*   作成者          ：富士通
*   日付            ：2011年08月11日
*＜機能概要＞
*   工事受付データ取得部品です。
*＜修正履歴＞
*   バージョン  修正日       修正者      修正内容
*   v1.00.00
*   v5.00.00	2013/08/24	FJ)高橋		【OM-2013-0000830】
*   v5.00.01	2013/08/28	FJ)高橋		【OM-2013-0001134】
*   v7.00.00	2014/03/11	FJ)高橋		【OM-2014-0000620】
*   v10.00.00	2014/07/15	FJ)阪口		【ANK-1918-00-00】US管理対応
*   v11.00.00	2014/11/18	FJ)阪口		【OM-2014-0003634】お客様情報変更時に自宅電話番号が設定されない
*
**********************************************************************/

package eo.ejb.common;


import java.util.ArrayList;
import java.util.Arrays;
import java.util.HashMap;

import java.util.List;

import com.fujitsu.futurity.model.base.CAANException;
import com.fujitsu.futurity.model.base.CAANMsg;

import eo.common.constant.JKUStrConst;
import eo.common.util.JKUSortComparator;
import eo.ejb.cbm.entity.CK0011ETMsg;
import eo.ejb.cbm.entity.CK0201ETMsg;
import eo.ejb.cbm.entity.CK0201LE;
import eo.ejb.cbm.entity.KK0021ETMsg;
import eo.ejb.cbm.entity.KK0081ETMsg;
import eo.ejb.cbm.entity.KK0321ETMsg;
import eo.ejb.cbm.entity.KK0321LE;
import eo.ejb.cbm.entity.KK0451ETMsg;
import eo.ejb.cbm.entity.KK0451LE;
import eo.ejb.cbm.entity.KK0841ETMsg;
import eo.ejb.cbm.entity.KU0011ETMsg;
import eo.ejb.cbm.entity.KU0011LE;
import eo.ejb.cbm.entity.KU0071ETMsg;
import eo.ejb.cbm.entity.KU0071LE;
import eo.ejb.cbm.entity.KU0081LE;
import eo.ejb.cbm.entity.KU0081ETMsg;
import eo.ejb.cbm.entity.KU0091ETMsg;
import eo.ejb.cbm.entity.KU0091LE;
import eo.ejb.common.db.JKUejbCK0011DBABase;
import eo.ejb.common.db.JKUejbKK0021DBABase;
import eo.ejb.common.db.JKUejbKK0081DBABase;
import eo.ejb.common.db.JKUejbKK0841DBABase;
import eo.ejb.common.db.JKUejbKU0011SecProc;
import eo.ejb.common.db.JKUejbKU0081SecProc;
import eo.ejb.common.rule.JKUejbRule0049001;
import eo.ejb.common.rule.JKUejbRule0049002;


/**
 * 工事受付データ取得部品です。<p>
 * サービスインターフェイスで実装します。
 * <BR>
 * @author 富士通
 */
public class JKUejbGetKojiDataUtil
{
	/**
	 * 仕掛中工事案件ステータス
	 */
	/** 仕掛中ステータス（１３０〜１９０） */
	private static final String[] SKKR_KOJIAK_STAT = 
	{
		JKUStrConst.CD00474_UK_ZM
		, JKUStrConst.CD00474_IRI_ZM
		, JKUStrConst.CD00474_TAKNI_CHOSA_FIN_ZM
		, JKUStrConst.CD00474_KOCOMP_KETTEI_ZM
		, JKUStrConst.CD00474_TAKNI_CHOSA_RSV_ZM
		, JKUStrConst.CD00474_KR_KAGI_KAIHAT_IRI_ZM
		, JKUStrConst.CD00474_GEMBA_SAGYO_FIN_ZM
	};
	/** 仕掛中ステータス（１３０〜２００） */
	private static final String[] SKKR_KOJIAK_STAT_FIN = 
	{
		JKUStrConst.CD00474_UK_ZM
		, JKUStrConst.CD00474_IRI_ZM
		, JKUStrConst.CD00474_TAKNI_CHOSA_FIN_ZM
		, JKUStrConst.CD00474_KOCOMP_KETTEI_ZM
		, JKUStrConst.CD00474_TAKNI_CHOSA_RSV_ZM
		, JKUStrConst.CD00474_KR_KAGI_KAIHAT_IRI_ZM
		, JKUStrConst.CD00474_GEMBA_SAGYO_FIN_ZM
		, JKUStrConst.CD00474_KOJI_FIN_ZM
	};
	
	/**
	 * 最新基本工事案件番号を取得します。
	 * @param svcKeiKaisenUcwkNo サービス契約回線内訳番号
	 * @param prcGrpCd 料金グループコード
	 * @return String 最新基本工事案件番号
	 */
	public static String getNewestKihonKojiakNo(String svcKeiKaisenUcwkNo, String prcGrpCd)
	{
		// 最新基本工事案件番号
		String newestKihonKojiakNo = null;
		
		// サービス契約回線内訳番号、サービスコードを用いて工事案件を取得する
		CAANMsg[] inKU0011ETMsg = null;
		inKU0011ETMsg = getKU0011DoitsuKoji(svcKeiKaisenUcwkNo, prcGrpCd);
		
		// 最新基本工事フラグが有効な工事案件番号を判定する
		for (CAANMsg ku0011ETMsg: inKU0011ETMsg)
		{
			if(JKUStrConst.UM_YK.equals(ku0011ETMsg.getString(KU0011ETMsg.RCNT_KIHON_KOJI_FLG)))
			{
				newestKihonKojiakNo = ku0011ETMsg.getString(KU0011ETMsg.KOJIAK_NO);
				break;
			}
		}
		
		return newestKihonKojiakNo;
		
	}
	
	/**
	 * 最新基本工事案件を取得します。
	 * @param svcKeiKaisenUcwkNo サービス契約回線内訳番号
	 * @param prcGrpCd 料金グループコード
	 * @return CAANMsg 最新基本工事案件メッセージ
	 */
	public static CAANMsg getNewestKihonKojiakMsg(String svcKeiKaisenUcwkNo, String prcGrpCd)
	{
		// 最新基本工事案件
		CAANMsg newestKihonKojiakMsg = null;
		
		// サービス契約回線内訳番号、サービスコードを用いて工事案件を取得する
		CAANMsg[] inKU0011ETMsg = null;
		inKU0011ETMsg = getKU0011DoitsuKoji(svcKeiKaisenUcwkNo, prcGrpCd);
		
		// 最新基本工事フラグが有効な工事案件番号を判定する
		for (CAANMsg ku0011ETMsg: inKU0011ETMsg)
		{
			if(JKUStrConst.UM_YK.equals(ku0011ETMsg.getString(KU0011ETMsg.RCNT_KIHON_KOJI_FLG)))
			{
				newestKihonKojiakMsg = ku0011ETMsg;
				break;
			}
		}
		
		return newestKihonKojiakMsg;
	}
	
	/**
	 * 仕掛工事案件番号を取得します。
	 * @param svcKeiKaisenUcwkNo サービス契約回線内訳番号
	 * @param prcGrpCd 料金グループコード
	 * @param adChgTekkyoKjakNo 住所変更撤去工事案件番号
	 * @return String 仕掛工事案件番号
	 */
	public static String getShikakariKojiakNo(String svcKeiKaisenUcwkNo, String prcGrpCd, String adChgTekkyoKjakNo)
	{
		CAANMsg shikakariKojiakMsg = getShikakariKojiakMsg(svcKeiKaisenUcwkNo, prcGrpCd, adChgTekkyoKjakNo);
		String retStr = null;
		if (null != shikakariKojiakMsg)
		{
			retStr = shikakariKojiakMsg.getString(KU0011ETMsg.KOJIAK_NO);
		}
		return retStr;
	}

	/**
	 * 仕掛工事案件を取得します。
	 * @param svcKeiKaisenUcwkNo サービス契約回線内訳番号
	 * @param prcGrpCd 料金グループコード
	 * @param adChgTekkyoKjakNo 住所変更撤去工事案件番号
	 * @return CAANMsg 仕掛工事案件メッセージ
	 */
	public static CAANMsg getShikakariKojiakMsg(String svcKeiKaisenUcwkNo, String prcGrpCd, String adChgTekkyoKjakNo)
	{
		// 工事案件ステータス
		String kojiakStat = null;
		String kojiakSbtCd = null;
		
		// サービス契約回線内訳番号、サービスコードを用いて工事案件を取得する
		CAANMsg[] inKU0011ETMsg = null;
		inKU0011ETMsg = getKU0011DoitsuKoji(svcKeiKaisenUcwkNo, prcGrpCd);
		
		for (CAANMsg ku0011ETMsg: inKU0011ETMsg)
		{
			
			// 最新基本工事フラグが1の場合は仕掛中ではない
			if (JKUStrConst.UM_YK.equals(ku0011ETMsg.getString(KU0011ETMsg.RCNT_KIHON_KOJI_FLG)))
			{
				continue;
			}
			
			// 工事案件番号が住所変更撤去工事案件番号と同じ場合は仕掛中ではない
			if (null == ku0011ETMsg.getString(KU0011ETMsg.KOJIAK_NO)
					|| ku0011ETMsg.getString(KU0011ETMsg.KOJIAK_NO).equals(adChgTekkyoKjakNo))
			{
				continue;
			}
			
			// 工事案件ステータス
			kojiakStat = JKUModelCommon.getYkKojiakStat(
					ku0011ETMsg.getString(KU0011ETMsg.KOJIAK_STAT), ku0011ETMsg.getString(KU0011ETMsg.MANS_KOJIAK_STAT_CD));
			// 工事案件種別コード
			kojiakSbtCd = ku0011ETMsg.getString(KU0011ETMsg.KOJIAK_SBT_CD);
			
			// プラン変更（収容替）の場合
			if (JKUStrConst.CD00577_PLAN_CHG_SHUYO.equals(kojiakSbtCd))
			{
				// プラン変更確定年月日時分秒がnullの場合
				if(ku0011ETMsg.getString(KU0011ETMsg.PLAN_CHG_FIX_DTM) == null)
				{
					// 仕掛中判定を実行する
					for(int i = 0; i < SKKR_KOJIAK_STAT_FIN.length; ++i)
					{
						if (SKKR_KOJIAK_STAT_FIN[i].equals(kojiakStat))
						{
							return ku0011ETMsg;
						}
					}
				}
			}
			// 住所変更（新設）の場合
			else if (JKUStrConst.CD00577_AD_CHG_NEWESTA.equals(kojiakSbtCd))
			{
				// 住所変更確定年月日時分秒がnullの場合
				if(ku0011ETMsg.getString(KU0011ETMsg.AD_CHG_FIX_DTM) == null)
				{
					// 仕掛中判定を実行する
					for(int i = 0; i < SKKR_KOJIAK_STAT_FIN.length; ++i)
					{
						if (SKKR_KOJIAK_STAT_FIN[i].equals(kojiakStat))
						{
							return ku0011ETMsg;
						}
					}
				}
			}
			// 移設、光電話宅内工事の場合
			else if (JKUStrConst.CD00577_ISETSU.equals(kojiakSbtCd) || JKUStrConst.CD00577_EOH_TEL_TNKJ.equals(kojiakSbtCd))
			{
				// 仕掛中工事ではありえない
				continue;
			}
			// その他の場合
			else
			{
				// 仕掛中判定を実行する
				for(int i = 0; i < SKKR_KOJIAK_STAT.length; ++i)
				{
					if (SKKR_KOJIAK_STAT[i].equals(kojiakStat))
					{
						return ku0011ETMsg;
					}
				}
			}
		}
		return null;
	}
	
	/**
	 * 更新対象工事案件番号取得処理
	 * @param svcKeiKaisenUcwkNo	サービス契約回線内訳番号
	 * @param prcGrpCd				料金グループコード
	 * @param updTrgtKojiakNo		更新対象工事案件番号：この項目がnullでない場合は、新たに検索を行わず、この項目を返す
	 * @param adChgTekkyoKjakNo		住所変更撤去工事案件番号
	 * @param kojiakSbtCd	工事案件種別コード
	 * @return	更新対象工事案件番号
	 */
	public static String getUpdTrgtKojiakNo(String svcKeiKaisenUcwkNo, String prcGrpCd, String updTrgtKojiakNo, String adChgTekkyoKjakNo, String kojiakSbtCd)
	{
		// 既に更新対象工事案件番号として使用できる工事案件番号が存在する場合は、
		// 新しく工事案件の検索を行わず、更新対象工事案件番号を返して終了する
		if (null != updTrgtKojiakNo)
		{
			return updTrgtKojiakNo;
		}
		
		String retStr = null;
		CAANMsg updTrgtKojiak = null;
		
		// 更新対象工事案件を取得する
		updTrgtKojiak = getUpdTrgtKojiakMsg(svcKeiKaisenUcwkNo, prcGrpCd, adChgTekkyoKjakNo, kojiakSbtCd);
		
		// 更新対象工事案件が存在する場合
		if (null != updTrgtKojiak)
		{
			retStr = updTrgtKojiak.getString(KU0011ETMsg.KOJIAK_NO);
		}
		
		return retStr;
	}
	
	/**
	 * 更新対象工事案件取得処理
	 * @param svcKeiKaisenUcwkNo	サービス契約回線内訳番号
	 * @param prcGrpCd				料金グループコード
	 * @param adChgTekkyoKjakNo	住所変更撤去工事案件番号
	 * @param kojiakSbtCd	工事案件種別コード
	 * @return	更新対象工事案件
	 */
	public static CAANMsg getUpdTrgtKojiakMsg(String svcKeiKaisenUcwkNo, String prcGrpCd, String adChgTekkyoKjakNo, String kojiakSbtCd)
	{
		CAANMsg retMsg = null;
		
		if(JKUStrConst.CD00577_EOH_TEL_TNKJ.equals(kojiakSbtCd) || JKUStrConst.CD00577_ISETSU.equals(kojiakSbtCd))
		{
			// ---最新基本工事案件を取得する
			
			retMsg = getNewestKihonKojiakMsg(svcKeiKaisenUcwkNo, prcGrpCd);
			
			// ---仕掛中工事案件を取得する
			
			// 最新基本工事案件が存在しない場合のみ実行する
			if (null == retMsg)
			{
				retMsg = getShikakariKojiakMsg(svcKeiKaisenUcwkNo, prcGrpCd, adChgTekkyoKjakNo);
			}
		}
		else
		{
			// ---仕掛中工事案件を取得する
			
			retMsg = getShikakariKojiakMsg(svcKeiKaisenUcwkNo, prcGrpCd, adChgTekkyoKjakNo);
			
			// ---最新基本工事案件を取得する
			
			// 仕掛中工事案件が存在しない場合のみ実行する
			if (null == retMsg)
			{
				retMsg = getNewestKihonKojiakMsg(svcKeiKaisenUcwkNo, prcGrpCd);
			}
		}
			 
		
		
		return retMsg;
	}

	/**
	 * 同一サービス契約回線内訳番号のうち相関ルールに従い同一工事となる工事案件を取得します。
	 * @param svcKeiKaisenUcwkNo サービス契約回線内訳番号
	 * @param prcGrpCd 料金グループコード
	 * @return CAANMsg[] 工事案件（同一工事対象の場合は合わせて取得する）
	 */
	public static CAANMsg[] getKU0011DoitsuKoji(String svcKeiKaisenUcwkNo, String prcGrpCd)
	{
		try
		{
			// 返却リスト
			List<CAANMsg> rsltMsgList = new ArrayList<CAANMsg>();
			
			// サービス契約＿工事案件
			CAANMsg inKU0081ETMsg = new CAANMsg(KU0081ETMsg.class.getName());
			KU0081LE le0081 = new KU0081LE();
			CAANMsg[] outKU0081ETMsg = null;
			
			// 工事案件
			CAANMsg inKU0011ETMsg = new CAANMsg(KU0011ETMsg.class.getName());
			JKUejbKU0011SecProc ku0011SecProc = new JKUejbKU0011SecProc();
			CAANMsg outKU0011ETMsg = null;
			
			// 相関ルール
			JKUejbRule0049001 rule0049001 = new JKUejbRule0049001();
			JKUejbRule0049002 rule0049002 = new JKUejbRule0049002();
			
			// 主要機器
			String dojiMskmPrcGrpMainKiki1 = null;
			String dojiMskmPrcGrpMainKiki2 = null;
			
			// 0. 引数の料金グループコードの主要機器を相関ルールを用いて判定する。
			dojiMskmPrcGrpMainKiki1 =  rule0049001.chkSokanRule0049001(prcGrpCd);

			// 1. 引数のサービス契約回線内訳番号でサービス契約工事案件を取得する。
			inKU0081ETMsg.set(KU0081ETMsg.SVC_KEI_KAISEN_UCWK_NO, svcKeiKaisenUcwkNo);
			inKU0081ETMsg.set(KU0081ETMsg.MK_FLG, JKUStrConst.MK_FLG_YUKO);
			outKU0081ETMsg = le0081.findByCondition(inKU0081ETMsg);
			
			// 2. 取得した工事案件番号について重複を取り除く
			List<String> kojiakNoList = new ArrayList<String>();
			for(CAANMsg ku0081Msg: outKU0081ETMsg)
			{
				if (!kojiakNoList.contains(ku0081Msg.getString(KU0081ETMsg.KOJIAK_NO)))
				{
					kojiakNoList.add(ku0081Msg.getString(KU0081ETMsg.KOJIAK_NO));
				}
			}
			
			// 3. 2の工事案件番号から工事案件レコードを取得する
			for(String kojiakNo: kojiakNoList)
			{
				inKU0011ETMsg.set(KU0011ETMsg.KOJIAK_NO, kojiakNo);
				outKU0011ETMsg = ku0011SecProc.findByPrimaryKey(inKU0011ETMsg, true);
				
				if(null == outKU0011ETMsg)
				{
					continue;
				}
				
				// 取得した工事案件が同一工事対象であるか判定し同一工事の場合は返却するListに格納する
				dojiMskmPrcGrpMainKiki2 = rule0049001.chkSokanRule0049001(outKU0011ETMsg.getString(KU0011ETMsg.PRC_GRP_CD));
				
				String sameKojiTrgtDiv = rule0049002.chkSokanRule0049002(dojiMskmPrcGrpMainKiki1, dojiMskmPrcGrpMainKiki2);
				if(JKUStrConst.UM_YK.equals(sameKojiTrgtDiv))
				{
					rsltMsgList.add(outKU0011ETMsg);
				}
			}
			
			CAANMsg[] retCaanMsg = (CAANMsg[])rsltMsgList.toArray(new CAANMsg[0]);
			
			// 工事受付契機異動年月日時分秒でソート
			Arrays.sort(retCaanMsg, new JKUSortComparator("KOJI_UK_OPTNTY_IDO_DTM", JKUSortComparator.SORT_TYPE_DESC));
			
			return retCaanMsg;
		}
		catch (CAANException ce)
		{
			return null;
		}
	}

	/**
	 * 申込明細指定の工事案件番号を取得します。
	 * @param oldMskmDtlNo
	 * @return CAANMsg[]
	 */
	public static CAANMsg[] getShiteiKojiakNo(String oldMskmDtlNo)
	{
		
		// 申込明細番号をキーに申込明細_工事案件を取得する
		CAANMsg inETMsg = new CAANMsg(KU0091ETMsg.class.getName());
		inETMsg.set(KU0091ETMsg.MSKM_DTL_NO, oldMskmDtlNo);
		KU0091LE le0091 = new KU0091LE();
		CAANMsg[] outKU0091ETMsg = null;
		try
		{
			outKU0091ETMsg = le0091.findByCondition(inETMsg);
		}
		catch (CAANException ce)
		{
			throw new RuntimeException();
		}
		
		return outKU0091ETMsg;
	}

	/**
	 * 工事案件レコード１件取得
	 * @param kojiakNo
	 * @return 
	 */
	public static CAANMsg getKojiak(String kojiakNo)
	{
		// 工事案件番号をキーに工事案件を取得する
		CAANMsg inETMsg = new CAANMsg(KU0011ETMsg.class.getName());
		inETMsg.set(KU0011ETMsg.KOJIAK_NO, kojiakNo);
		KU0011LE le0011 = new KU0011LE();
		CAANMsg outETMsg = null;
		outETMsg = le0011.findByPrimaryKey(inETMsg);
		return outETMsg;
	}

	/**
	 * 提供中サービス契約＿工事案件情報リスト取得します。
	 * @param kojiakNo 工事案件番号
	 * @return CAANMsg[] 提供中サービス契約＿工事案件情報リスト
	 */
	public static CAANMsg[] getTkSvcKeiKojiak(String kojiakNo)
	{
		try
		{
			
			// サービス契約＿工事案件
			CAANMsg inKU0081ETMsg = new CAANMsg(KU0081ETMsg.class.getName());
			KU0081LE le0081 = new KU0081LE();

			// 1. 引数の工事案件番号でサービス契約工事案件を取得する。
			inKU0081ETMsg.set(KU0081ETMsg.KOJIAK_NO, kojiakNo);
			inKU0081ETMsg.set(KU0081ETMsg.SVKEI_KOJIAK_TENDYMD, JKUStrConst.MAX_YMD);
			inKU0081ETMsg.set(KU0081ETMsg.MK_FLG, JKUStrConst.MK_FLG_YUKO);
			
			return le0081.findByCondition(inKU0081ETMsg);
		}
		catch (CAANException ce)
		{
			return null;
		}
	}
	
	/**
	 * 提供中法人サービス契約＿工事案件情報リスト取得します。
	 * @param kojiakNo 工事案件番号
	 * @return CAANMsg[] 提供中法人サービス契約＿工事案件情報リスト
	 */
	public static CAANMsg[] getTkHojinSvcKeiKojiak(String kojiakNo)
	{
		try
		{
			// 法人サービス契約＿工事案件
			CAANMsg inKU0071ETMsg = new CAANMsg(KU0071ETMsg.class.getName());
			KU0071LE le0071 = new KU0071LE();

			// 1. 引数の工事案件番号でサービス契約工事案件を取得する。
			inKU0071ETMsg.set(KU0071ETMsg.KOJIAK_NO, kojiakNo);
			inKU0071ETMsg.set(KU0071ETMsg.HOJINSVKEI_KJAK_TENDYMD, JKUStrConst.MAX_YMD);
			inKU0071ETMsg.set(KU0071ETMsg.MK_FLG, JKUStrConst.MK_FLG_YUKO);
			
			return le0071.findByCondition(inKU0071ETMsg);
		}
		catch (CAANException ce)
		{
			return null;
		}
	}
	
	/**
	 * サービス契約情報の取得処理
	 * @param svc_kei_no
	 * @return HashMap<String, String> サービス契約情報
	 * @throws CAANException
	 */
	public static HashMap<String, String> getSvcKeiInfo(String svc_kei_no) throws CAANException
	{
		HashMap<String, String> rtnMap = new HashMap<String, String>();

		// 運用日付取得
		String opeDate = JKUModelCommon.getOpeDate(new CAANMsg(), null);
		
		// サービス契約のETメッセージを作成
		CAANMsg msgKK0081 = new CAANMsg(KK0081ETMsg.class.getName());
		JKUejbKK0081DBABase baseKK0081 = new JKUejbKK0081DBABase();
		msgKK0081.set(KK0081ETMsg.SVC_KEI_NO, svc_kei_no);
		msgKK0081.set(KK0081ETMsg.RSV_APLY_YMD, opeDate); //findByCurrentを使う際は運用日付を予約適用年月日に入れる
		msgKK0081 = baseKK0081.findByCurrent(msgKK0081);  // TODO: 予約管理の考え方が変わるなら変更が必要

		if(null == msgKK0081)
		{
			return null;
		}

		rtnMap = msgKK0081.getHashMap();

		rtnMap.put(KK0321ETMsg.SEIKY_KEI_NO, null);
		rtnMap.put(KK0021ETMsg.RRKS_OFFC_NM, null);
		rtnMap.put(KK0451ETMsg.WRIB_SVC_CD, null);
		rtnMap.put(KK0841ETMsg.WRIB_TYPE_CD, null);

		// 課金先のETメッセージを作成
		CAANMsg msgKK0321 = new CAANMsg(KK0321ETMsg.class.getName());
		CAANMsg[] outKK0321ETMsg = null;

		KK0321LE leKK0321 = new KK0321LE();
		msgKK0321.set(KK0321ETMsg.SVC_KEI_NO, svc_kei_no);
		msgKK0321.set(KK0321ETMsg.MK_FLG, JKUStrConst.MK_FLG_YUKO);
		outKK0321ETMsg = leKK0321.findByCondition(msgKK0321);

		// 適用年月日の範囲が運用日付に一致するレコードに絞る
		outKK0321ETMsg = getAplyList(outKK0321ETMsg, opeDate, KK0321ETMsg.KAKINS_TSTAYMD, KK0321ETMsg.KAKINS_TENDYMD);

		if(null != outKK0321ETMsg && 0 != outKK0321ETMsg.length)
		{
			// 請求契約番号
			rtnMap.put(KK0321ETMsg.SEIKY_KEI_NO, outKK0321ETMsg[0].getString(KK0321ETMsg.SEIKY_KEI_NO));
		}


		if(null != rtnMap.get(KK0081ETMsg.MSKM_DTL_NO))
		{
			// 申込明細のETメッセージを作成
			CAANMsg msgKK0021 = new CAANMsg(KK0021ETMsg.class.getName());
			JKUejbKK0021DBABase baseKK0021 = new JKUejbKK0021DBABase();
			msgKK0021.set(KK0021ETMsg.MSKM_DTL_NO, rtnMap.get(KK0081ETMsg.MSKM_DTL_NO));
			msgKK0021 = baseKK0021.findByCurrent(msgKK0021);

			if(null != msgKK0021)
			{
				// 連絡先勤務先名設定
				rtnMap.put(KK0021ETMsg.RRKS_OFFC_NM, msgKK0021.getString(KK0021ETMsg.RRKS_OFFC_NM));
			}	

			// 割引サービス契約のETメッセージを作成
			CAANMsg msgKK0451 = new CAANMsg(KK0451ETMsg.class.getName());
			CAANMsg[] outKK0451ETMsg = null;

			KK0451LE leKK0451 = new KK0451LE();
			msgKK0451.set(KK0451ETMsg.MSKM_DTL_NO, rtnMap.get(KK0081ETMsg.MSKM_DTL_NO));
			msgKK0451.set(KK0451ETMsg.MK_FLG, JKUStrConst.MK_FLG_YUKO);
			outKK0451ETMsg = leKK0451.findByCondition(msgKK0451);

			// プライマリーキーごとのカレントレコードに絞る
			outKK0451ETMsg = getCurrentGeneList(outKK0451ETMsg, opeDate, new String[]{KK0451ETMsg.WRIB_SVC_KEI_NO}
				, KK0451ETMsg.GENE_ADD_DTM, KK0451ETMsg.RSV_APLY_CD, KK0451ETMsg.RSV_APLY_YMD);

			if(null != outKK0451ETMsg && 0 != outKK0451ETMsg.length)
			{
				// 割引サービスコードのリストを作成
				List<String> wribSvcCdList = new ArrayList<String>();
				for(CAANMsg msg : outKK0451ETMsg)
				{
					if(!wribSvcCdList.contains(msg.getString(KK0451ETMsg.WRIB_SVC_CD)))
					{
						wribSvcCdList.add(msg.getString(KK0451ETMsg.WRIB_SVC_CD));
					}
				}
				
				
				// 割引サービスのETメッセージを作成
				JKUejbKK0841DBABase baseKK0841 = new JKUejbKK0841DBABase();
				CAANMsg msgKK0841 = null;
				
				for(String wribSvcCd : wribSvcCdList)
				{
					msgKK0841 = new CAANMsg(KK0841ETMsg.class.getName());
					msgKK0841.set(KK0841ETMsg.WRIB_SVC_CD, wribSvcCd);
					msgKK0841.set(KK0841ETMsg.RSV_APLY_YMD, opeDate); //findByCurrentを使う際は運用日付を予約適用年月日に入れる
					msgKK0841 = baseKK0841.findByCurrent(msgKK0841); // TODO: 予約管理の考え方が変わるなら変更が必要
	
					if(null != msgKK0841 
							&& JKUStrConst.CD00284_SOKUWARI.equals(msgKK0841.getString(KK0841ETMsg.WRIB_TYPE_CD)))
					{
						// 割引サービスコード設定
						rtnMap.put(KK0451ETMsg.WRIB_SVC_CD, msgKK0841.getString(KK0451ETMsg.WRIB_SVC_CD));
						// 割引タイプコード設定
						rtnMap.put(KK0841ETMsg.WRIB_TYPE_CD, msgKK0841.getString(KK0841ETMsg.WRIB_TYPE_CD));
						break;
					}
				}
			}
		}

		return rtnMap;
	}

	/**
	 * お客様情報の取得処理
	 * @param sysId
	 * @return HashMap<String, String> お客様情報
	 * @throws CAANException
	 */
	public static HashMap<String, String> getCustInfo(String sysId) throws CAANException
	{

		HashMap<String, String> rtnMap = new HashMap<String, String>();

		// 運用日付取得
		String opeDate = JKUModelCommon.getOpeDate(new CAANMsg(), null);
		

		// お客様のETメッセージを作成
		CAANMsg msgCK0011 = new CAANMsg(CK0011ETMsg.class.getName());
		JKUejbCK0011DBABase baseCK0011 = new JKUejbCK0011DBABase();
		msgCK0011.set(CK0011ETMsg.SYSID, sysId);
		msgCK0011.set(CK0011ETMsg.RSV_APLY_YMD, opeDate); //findByCurrentを使う際は運用日付を予約適用年月日に入れる
		msgCK0011 = baseCK0011.findByCurrent(msgCK0011);  // TODO: 予約管理の考え方が変わるなら変更が必要

		if(null == msgCK0011)
		{
			return null;
		}

		rtnMap = msgCK0011.getHashMap();

		rtnMap.put(KU0011ETMsg.CUST_KTAI_TELNO, null);

		// 連絡先(携帯)のメッセージを取得
		CAANMsg msgCK0201 = getCK0201(opeDate, sysId, JKUStrConst.CD00254_KTAI);
		if(null != msgCK0201)
		{
			rtnMap.put(KU0011ETMsg.CUST_KTAI_TELNO, msgCK0201.getString(CK0201ETMsg.TELNO));
		}

		return rtnMap;
	}

	/**
	 * 連絡先情報の取得処理
	 * @param opeDate
	 * @param sysId
	 * @param rrks_sbt_cd
	 * @return CAANMsg 連絡先情報
	 * @throws CAANException
	 */
	private static CAANMsg getCK0201(String opeDate, String sysId, String rrks_sbt_cd) throws CAANException
	{
		// 連絡先のETメッセージを作成
		CAANMsg msgCK0201 = new CAANMsg(CK0201ETMsg.class.getName());
		CAANMsg[] outCK0201ETMsg = null;

		CK0201LE leCK0201 = new CK0201LE();
		msgCK0201.set(CK0201ETMsg.SYSID, sysId);
		msgCK0201.set(CK0201ETMsg.RRKS_SBT_CD, rrks_sbt_cd);
		msgCK0201.set(CK0201ETMsg.MK_FLG, JKUStrConst.MK_FLG_YUKO);
		outCK0201ETMsg = leCK0201.findByCondition(msgCK0201);

		// カレントレコードに絞る
		msgCK0201 = getCurrentGene(outCK0201ETMsg, opeDate, CK0201ETMsg.GENE_ADD_DTM, CK0201ETMsg.RSV_APLY_CD, CK0201ETMsg.RSV_APLY_YMD);

		return msgCK0201;
	}
	
	/**
	 * //TODO: 有効なデータの予約管理系項目は必ず入ってるという当初の仕様が前提、予約管理の考え方が変わるなら変更が必要
	 * CAANMsgのリストから世代登録年月日時分秒が最大のレコードをカレントとして取得する
	 * @param inputMsg
	 * @param opeDate
	 * @param colNm_GeneAddDtm
	 * @param colNm_RsvAplyCd
	 * @param colNm_RsvAplyYmd
	 * @return CAANMsg
	 */
	private static CAANMsg getCurrentGene(CAANMsg[] inputMsg, String opeDate
			, String colNm_GeneAddDtm, String colNm_RsvAplyCd, String colNm_RsvAplyYmd)
	{
		CAANMsg rtnMsg = null;
		if(0 == inputMsg.length)
		{
			return null;
		}
		// 予約関連項目の有無を取得
		boolean isRsvCd = inputMsg[0].containsKeyOfSchema(colNm_RsvAplyCd);
		boolean isRsvYmd = inputMsg[0].containsKeyOfSchema(colNm_RsvAplyYmd);
		
		for(CAANMsg msg : inputMsg)
		{
			// 予約適用コードが「2：予約確定」 でない場合は対象外
			if(isRsvCd && !JKUStrConst.CD00343_RSV_FIX.equals(msg.getString(colNm_RsvAplyCd)))
			{
				continue;
			}
			
			// 予約適用年月日が運用日付より小さい場合は対象外
			if(isRsvYmd && null != opeDate 
					&& 0 > opeDate.compareTo(msg.getString(colNm_RsvAplyYmd)))
			{
				continue;
			}
			
			// 世代登録年月日時分秒が大きければ上書き
			if(null == rtnMsg
					|| 0 < msg.getString(colNm_GeneAddDtm).compareTo(rtnMsg.getString(KK0451ETMsg.GENE_ADD_DTM)))
			{
				rtnMsg = msg;
			}
		}
		
		return rtnMsg;
	}
	
	/**
	 * CAANMsgのリストからキー項目ごとの世代登録年月日時分秒が最大のレコードをカレントとして取得する
	 * @param inputMsg
	 * @param opeDate
	 * @param colNm_Primary
	 * @param colNm_GeneAddDtm
	 * @param colNm_RsvAplyCd
	 * @param colNm_RsvAplyYmd
	 * @return CAANMsg[] カレントレコードリスト
	 */
	private static CAANMsg[] getCurrentGeneList(CAANMsg[] inputMsg, String opeDate, String[] colNm_Primary
			, String colNm_GeneAddDtm, String colNm_RsvAplyCd, String colNm_RsvAplyYmd)
	{
		List<String> pimaryCdList = new ArrayList<String>();
		List<CAANMsg> wkMsg =  new ArrayList<CAANMsg>();
		List<CAANMsg> rtnMsgList =  new ArrayList<CAANMsg>();
		CAANMsg rtnMsg = null;
		
		if(null == inputMsg || 0 == inputMsg.length)
		{
			return null;
		}
		
		// キー項目の一覧を作成
		StringBuffer key = null;
		for(CAANMsg msg : inputMsg)
		{
			key = new StringBuffer();
			for(String p : colNm_Primary)
			{
				key.append(msg.getString(p));
			}
			
			if(!pimaryCdList.contains(key.toString()))
			{
				pimaryCdList.add(key.toString());
			}
		}
		
		// 作成したキー項目に一致するレコードからカレントを取得し返却リストに格納する
		for(String pimaryCd : pimaryCdList)
		{
			wkMsg = new ArrayList<CAANMsg>();
			
			for(CAANMsg msg : inputMsg)
			{
				key = new StringBuffer();
				for(String p : colNm_Primary)
				{
					key.append(msg.getString(p));
				}
				if(pimaryCd.equals(key.toString()))
				{
					wkMsg.add(msg);
				}
			}
			rtnMsg = getCurrentGene((CAANMsg[])wkMsg.toArray(new CAANMsg[0]), opeDate, colNm_GeneAddDtm, colNm_RsvAplyCd, colNm_RsvAplyYmd);
			if(null != rtnMsg)
			{
				rtnMsgList.add(rtnMsg);
			}
		}
		
		return (CAANMsg[])rtnMsgList.toArray(new CAANMsg[0]);
	}
	
	/**
	 * CAANMsgのリストから適用開始年月日≦運用日付≦適用終了年月日のレコードを取得する
	 * @param inputMsg
	 * @param opeDate
	 * @param colNm_TstaYmd
	 * @param colNm_TendYmd
	 * @return CAANMsg[] 適用年月日の範囲に一致するCAANMsgリスト
	 */
	private static  CAANMsg[] getAplyList(CAANMsg[] inputMsg, String opeDate, String colNm_TstaYmd, String colNm_TendYmd)
	{
		List<CAANMsg> rtnMsgList =  new ArrayList<CAANMsg>();
		String startDate = "";
		String endDate = "";
		
		// 適用開始年月日 ≦ 運用日付 ≦ 適用終了年月日のデータを抽出する
		for(CAANMsg msg : inputMsg)
		{
			
			if(null != msg.getString(colNm_TstaYmd))
			{
				startDate = msg.getString(colNm_TstaYmd);
			}
			else
			{
				startDate = "00000000";
			}
			
			if(null != msg.getString(colNm_TendYmd))
			{
				endDate = msg.getString(colNm_TendYmd);
			}
			else
			{
				endDate = JKUStrConst.MAX_YMD;
			}
			
			if (0 > endDate.compareTo(startDate)) 
			{
				continue;
			}
			
			// 範囲一致結果取得
			if(JKUModelCommon.rangeCheck(endDate, startDate, opeDate, "2"))
			{
				rtnMsgList.add(msg);
			}
		}
		
		if(0 == rtnMsgList.size())
		{
			return null;
		}
		return (CAANMsg[])rtnMsgList.toArray(new CAANMsg[0]);
	}
	
	/**
	 * サービス追加（工事なし）の工事案件情報を取得
	 * @param svcKeiNo
	 * @param updTrgtKojiakNo
	 * @param kojinFlg True 個人/ False 法人
	 * @return CAANMsg
	 */
	public static CAANMsg getSvcAddKojiNonKojiakMsg(String svcKeiNo, String updTrgtKojiakNo, boolean kojinFlg)
	{
		try
		{
			List<String> kojiakNoList = new ArrayList<String>();

			String wk_kojiakNo = "";
			
			if(kojinFlg)
			{
				// サービス契約＿工事案件
				CAANMsg inKU0081ETMsg = new CAANMsg(KU0081ETMsg.class.getName());
				KU0081LE le0081 = new KU0081LE();
				CAANMsg[] outKU0081ETMsg = null;
				
				// 引数のサービス契約番号でサービス契約＿工事案件を取得する。
				inKU0081ETMsg.set(KU0081ETMsg.SVC_KEI_NO, svcKeiNo);
				inKU0081ETMsg.set(KU0081ETMsg.SVKEI_KOJIAK_TENDYMD, JKUStrConst.MAX_YMD);
				inKU0081ETMsg.set(KU0081ETMsg.MK_FLG, JKUStrConst.MK_FLG_YUKO);
				outKU0081ETMsg = le0081.findByCondition(inKU0081ETMsg);
				
				// 取得した工事案件番号について重複を取り除く
				for(CAANMsg ku0081Msg: outKU0081ETMsg)
				{
					wk_kojiakNo = ku0081Msg.getString(KU0081ETMsg.KOJIAK_NO);
					if (!updTrgtKojiakNo.equals(wk_kojiakNo) && !kojiakNoList.contains(wk_kojiakNo))
					{
						kojiakNoList.add(wk_kojiakNo);
					}
				}
			}
			else
			{				
				// 法人サービス契約＿工事案件
				CAANMsg inKU0071ETMsg = new CAANMsg(KU0071ETMsg.class.getName());
				KU0071LE le0071 = new KU0071LE();
				CAANMsg[] outKU0071ETMsg = null;
				
				// 引数のサービス契約番号でサービス契約＿工事案件を取得する。
				inKU0071ETMsg.set(KU0071ETMsg.HJIN_EO_YKAE_SVKEI_NO, svcKeiNo);
				inKU0071ETMsg.set(KU0071ETMsg.HOJINSVKEI_KJAK_TENDYMD, JKUStrConst.MAX_YMD);
				inKU0071ETMsg.set(KU0071ETMsg.MK_FLG, JKUStrConst.MK_FLG_YUKO);
				outKU0071ETMsg = le0071.findByCondition(inKU0071ETMsg);
				
				// 取得した工事案件番号について重複を取り除く
				for(CAANMsg ku0071Msg: outKU0071ETMsg)
				{
					wk_kojiakNo = ku0071Msg.getString(KU0071ETMsg.KOJIAK_NO);
					if (!updTrgtKojiakNo.equals(wk_kojiakNo) && !kojiakNoList.contains(wk_kojiakNo))
					{
						kojiakNoList.add(wk_kojiakNo);
					}
				}
			}

			// 工事案件のETメッセージを作成
			CAANMsg inKU0011ETMsg = new CAANMsg(KU0011ETMsg.class.getName());
			KU0011LE le0011 = new KU0011LE();
			CAANMsg[] outKU0011ETMsg = null;
			
			// 工事案件番号から工事案件レコードを取得する
			for(String kojiakNo: kojiakNoList)
			{
				// 工事案件番号が引数の更新対象工事案件番号と同一であれば次のレコードへ
				if(updTrgtKojiakNo.equals(kojiakNo))
				{
					continue;
				}
				inKU0011ETMsg.set(KU0011ETMsg.KOJIAK_NO, kojiakNo);
				inKU0011ETMsg.set(KU0011ETMsg.UPD_TRGT_KOJIAK_NO, updTrgtKojiakNo);
				inKU0011ETMsg.set(KU0011ETMsg.RNKI_SVC_KEI_NO, svcKeiNo);
				inKU0011ETMsg.set(KU0011ETMsg.KOJIAK_SBT_CD, JKUStrConst.CD00577_SVC_ADD_KOJI_NON);
				inKU0011ETMsg.set(KU0011ETMsg.MK_FLG, JKUStrConst.MK_FLG_YUKO);
				
				outKU0011ETMsg = le0011.findByCondition(inKU0011ETMsg);
				
				if(0 < outKU0011ETMsg.length)
				{
					return outKU0011ETMsg[0];
				}
			}
			
			return null;
				
		}
		catch (CAANException ce)
		{
			return null;
		}
	}
	
	/**
	 * 撤去(解約)または強制解約で工事完了しているものがあるかのチェック
	 * @param newestKojiakNo	最新基本工事案件
	 * @param mansEthFlg	マンションイーサ（その他光配線以外）フラグ
	 * @return	チェック結果
	 */
	public static boolean existsFinDslKojiak(String newestKojiakNo, boolean mansEthFlg)
	{
		if (null == newestKojiakNo || "".equals(newestKojiakNo))
		{
			return false;
		}
		
		try
		{
			// ---最新基本工事案件に対する工事を取得する
			
			CAANMsg ku0011Msg = new CAANMsg(KU0011ETMsg.class.getName());
			// 更新対象工事案件番号
			ku0011Msg.set(KU0011ETMsg.UPD_TRGT_KOJIAK_NO, newestKojiakNo);
			// 無効フラグ
			ku0011Msg.set(KU0011ETMsg.MK_FLG, JKUStrConst.MK_FLG_YUKO);
			
			CAANMsg[] ku0011MsgArray = new JKUejbKU0011SecProc().findByCondition(ku0011Msg);
			
			// 結果が0件の場合は、最新基本工事案件に対する工事が無いため、チェックOKとする
			if (null == ku0011MsgArray || ku0011MsgArray.length == 0)
			{
				return false;
			}
			
			// ---撤去工事であるかの判定を行う
			
			// 取得した工事案件全てで実行する
			for (int i = 0; i < ku0011MsgArray.length; ++i)
			{
				String kojiakSbtCd = ku0011MsgArray[i].getString(KU0011ETMsg.KOJIAK_SBT_CD);
				String kojiakStat = JKUModelCommon.getYkKojiakStat(
						ku0011MsgArray[i].getString(KU0011ETMsg.KOJIAK_STAT), ku0011MsgArray[i].getString(KU0011ETMsg.MANS_KOJIAK_STAT_CD));
				
				// 工事案件種別が強制解約または撤去(解約)
				if (JKUStrConst.CD00577_KYOSEI_DSL.equals(kojiakSbtCd)
						|| JKUStrConst.CD00577_TEKKYO_DSL.equals(kojiakSbtCd))
				{
					// ステータスが工事完了済
					if (JKUStrConst.CD00474_KOJI_FIN_ZM.equals(kojiakStat))
					{
						// 撤去(解約)または強制解約で工事完了のものが存在する
						return true;
					}
				}
			}
			
			return false;
		}
		catch (CAANException ce)
		{
			return false;
		}
	}
	
	/**
	 * 工事案件リストから撤去対象の工事案件を取得する
	 * @param svcKeiNo	サービス契約番号
	 * @param kojiakInfList	工事案件リスト
	 * @return	工事案件リスト
	 */
	public static CAANMsg[] getKojiakForTekkyo(String svcKeiNo, CAANMsg[] kojiakInfList)
	{
		List<CAANMsg> returnList = new ArrayList<CAANMsg>();
		// 工事案件番号
		String kojiakNo = null;
		// サービス契約_工事案件副次処理部品
		CAANMsg inKU0081ETMsg = new CAANMsg(KU0081ETMsg.class.getName());
		JKUejbKU0081SecProc ku0081SecProc = new JKUejbKU0081SecProc();
		CAANMsg outKU0081ETMsg = null;
		// 工事案件副次処理部品
		CAANMsg inKU0011ETMsg = new CAANMsg(KU0011ETMsg.class.getName());
		JKUejbKU0011SecProc ku0011SecProc = new JKUejbKU0011SecProc();
		CAANMsg outKU0011ETMsg = null;
		
		try
		{
			// 工事案件のリスト分繰り返す
			for (int i = 0; i < kojiakInfList.length; ++i)
			{
				kojiakNo = kojiakInfList[i].getString(KU0011ETMsg.KOJIAK_NO);
				
				// 工事案件番号
				inKU0081ETMsg.set(KU0081ETMsg.KOJIAK_NO, kojiakNo);
				// サービス契約番号
				inKU0081ETMsg.set(KU0081ETMsg.SVC_KEI_NO, svcKeiNo);
				
				outKU0081ETMsg = ku0081SecProc.findByPrimaryKey(inKU0081ETMsg, true);
				
				// サービス契約_工事案件の結果がある場合、更新工事案件リストを書き換える
				if(outKU0081ETMsg != null)
				{
					// 工事案件番号
					inKU0011ETMsg.set(KU0011ETMsg.KOJIAK_NO, kojiakNo);
					outKU0011ETMsg = ku0011SecProc.findByPrimaryKey(inKU0011ETMsg, true);
					
					returnList.add(outKU0011ETMsg);
				}
			}
		}
		catch (CAANException ce)
		{
			return null;
		}
		
		return (CAANMsg[])returnList.toArray(new CAANMsg[0]);
	}
}
