package itn.let.mjo.msgcampain.web;

import java.io.BufferedReader;
import java.io.InputStreamReader;
import java.math.BigDecimal;
import java.math.RoundingMode;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Calendar;
import java.util.Date;
import java.util.HashMap;
import java.util.List;
import java.util.stream.Collectors;

import javax.annotation.Resource;
import javax.servlet.http.HttpServletRequest;

import org.apache.commons.lang3.StringUtils;
import org.apache.poi.hssf.usermodel.HSSFCell;
import org.apache.poi.hssf.usermodel.HSSFRow;
import org.apache.poi.hssf.usermodel.HSSFSheet;
import org.apache.poi.hssf.usermodel.HSSFWorkbook;
import org.apache.poi.openxml4j.opc.OPCPackage;
import org.apache.poi.ss.usermodel.Cell;
import org.apache.poi.xssf.usermodel.XSSFCell;
import org.apache.poi.xssf.usermodel.XSSFRow;
import org.apache.poi.xssf.usermodel.XSSFSheet;
import org.apache.poi.xssf.usermodel.XSSFWorkbook;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Controller;
import org.springframework.ui.ModelMap;
import org.springframework.web.bind.annotation.ModelAttribute;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.ResponseBody;
import org.springframework.web.multipart.MultipartFile;
import org.springframework.web.multipart.MultipartHttpServletRequest;
import org.springframework.web.servlet.ModelAndView;
import org.springframework.web.servlet.mvc.support.RedirectAttributes;

import egovframework.rte.fdl.idgnr.EgovIdGnrService;
import egovframework.rte.fdl.security.userdetails.util.EgovUserDetailsHelper;
import egovframework.rte.psl.dataaccess.util.EgovMap;
import egovframework.rte.ptl.mvc.tags.ui.pagination.PaginationInfo;
import itn.com.cmm.ComDefaultCodeVO;
import itn.com.cmm.EgovMessageSource;
import itn.com.cmm.JsonResult;
import itn.com.cmm.LoginVO;
import itn.com.cmm.service.EgovCmmUseService;
import itn.com.cmm.service.EgovFileMngService;
import itn.com.cmm.service.EgovFileMngUtil;
import itn.com.cmm.util.MJUtil;
import itn.com.cmm.util.RedirectUrlMaker;
import itn.com.cmm.util.StringUtil;
import itn.com.utl.fcc.service.EgovStringUtil;
import itn.let.lett.service.HashConfVO;
import itn.let.lett.service.LetterService;
import itn.let.lett.service.LetterVO;
import itn.let.mjo.addr.service.AddrGroupService;
import itn.let.mjo.addr.service.AddrService;
import itn.let.mjo.addr.service.AddrVO;
import itn.let.mjo.event.service.MjonEventService;
import itn.let.mjo.event.service.MjonEventVO;
import itn.let.mjo.mjocommon.MjonCommon;
import itn.let.mjo.mjocommon.MjonHolidayApi;
import itn.let.mjo.msg.service.MjonMsgService;
import itn.let.mjo.msg.service.MjonMsgVO;
import itn.let.mjo.msgcampain.service.MjonCandidateService;
import itn.let.mjo.msgcampain.service.MjonCandidateTWVO;
import itn.let.mjo.msgcampain.service.MjonCandidateVO;
import itn.let.mjo.msgdata.service.MjonMsgDataService;
import itn.let.mjo.msgdata.service.MjonMsgDataVO;
import itn.let.mjo.msgdata.service.MjonMsgReturnVO;
import itn.let.mjo.msgdata.service.PhoneVO;
import itn.let.mjo.msgholiday.service.MsgAlarmSetVO;
import itn.let.mjo.msgholiday.service.MsgHolidayService;
import itn.let.mjo.msgholiday.service.MsgHolidayVO;
import itn.let.mjo.pay.service.MjonPayService;
import itn.let.mjo.spammsg.service.MjonSpamMsgService;
import itn.let.mjo.symbol.service.MjonSymbolService;
import itn.let.mjo.symbol.service.MjonSymbolVO;
import itn.let.sym.ccm.cde.service.CateCode;
import itn.let.sym.ccm.cde.service.EgovCcmCmmnDetailCodeManageService;
import itn.let.sym.grd.service.MberGrdService;
import itn.let.sym.site.service.EgovSiteManagerService;
import itn.let.sym.site.service.JoinSettingVO;
import itn.let.uss.umt.service.EgovMberManageService;
import itn.let.uss.umt.service.EgovUserManageService;
import itn.let.uss.umt.service.MberManageVO;
import itn.let.uss.umt.service.UserManageVO;
import itn.let.utl.fcc.service.EgovCryptoUtil;

@Controller
public class MjonMsgCampainTWDataController {

	@Resource(name = "mjonMsgService")
    private MjonMsgService mjonMsgService;
	
	@Resource(name = "mjonPayService")
    private MjonPayService mjonPayService;
	
	@Resource(name = "MjonMsgDataService")
    private MjonMsgDataService mjonMsgDataService;
	
	@Resource(name = "LetterService")
    private LetterService letterService;
	
	@Resource(name = "mjonSymbolService")
	private MjonSymbolService mjonSymbolService;
	
	/** mberManageService */
	@Resource(name = "mberManageService")
	private EgovMberManageService mberManageService;
	
	@Resource (name = "AddrService")
	private AddrService addrService;
	
	@Resource (name = "AddrGroupService")
	private AddrGroupService addrGroupService;
	
	@Resource(name = "mjonCandidateService")
    private MjonCandidateService mjonCandidateService;
	
	@Resource(name = "EgovCmmUseService")
	private EgovCmmUseService cmmUseService;
	
	/** EgovMessageSource */
    @Resource(name="egovMessageSource")
    EgovMessageSource egovMessageSource;
    
    @Resource(name="EgovFileMngUtil")
	private EgovFileMngUtil fileUtil;
    
    @Resource(name="EgovFileMngService")
    private EgovFileMngService fileMngService;
    
    /* 암복호화 */
	@Resource(name = "egovCryptoUtil")
	EgovCryptoUtil egovCryptoUtil;
	
    @Resource(name = "egovMjonMsgGroupIdGnrService")
    private EgovIdGnrService idgenMjonMsgGroupId;
    
	@Resource(name = "egovMjonCashIdGnrService")
    private EgovIdGnrService idgenMjonCashId;
	
	@Resource(name = "CmmnDetailCodeManageService")
    private EgovCcmCmmnDetailCodeManageService cmmnDetailCodeManageService;
	
	/** 첨부파일 저장경로 */
	@Value("#{globalSettings['Globals.file.saveDir']}")
	private String fileSaveDir;
    
	/** userManageService */
	@Resource(name = "userManageService")
	private EgovUserManageService userManageService;
	
	@Resource(name = "MjonEventService")
    private MjonEventService mjonEventService;
	
	@Resource(name = "mjonSpamMsgService")
    private MjonSpamMsgService mjonSpamMsgService;
    
	/** 사이트 설정 */ 
	@Resource(name = "egovSiteManagerService")
	EgovSiteManagerService egovSiteManagerService;
	
	/** 등급제 관리 서비스 */
	@Resource(name = "mberGrdService")
	MberGrdService mberGrdService;
	
	@Resource(name = "MsgHolidayService")
    private MsgHolidayService msgHolidayService;
	
	@Autowired
	private MjonCommon mjonCommon;
	
	 private static final Logger logger = LoggerFactory.getLogger(MjonMsgCampainTWDataController.class);
	
    /**
     * 선거 문자 20건씩 발송 화면 
     * @param searchVO
     * @param model
     * @return	"/web/mjon/msgcampain/selectMsgTWDataView.do"
     * @throws Exception
     */
	@RequestMapping(value= {"/web/mjon/msgcampain/selectMsgTWDataView.do"})
	public String selectMsgTWDataView(@ModelAttribute("searchVO") MjonMsgDataVO searchVO
			, CateCode cateCode
			, HttpServletRequest request
			, ModelMap model) throws Exception{
		
		

		// 요청의 호스트명을 가져오기
		String hostName = request.getServerName();

		// 외부에서 선거발송 페이지로 들어오는걸 막음
		// 20250102 이호영
		System.out.println("hostName :: "+ hostName);
		System.out.println("hostName :: "+ hostName);
		System.out.println("hostName :: "+ hostName);
		System.out.println("hostName :: "+ hostName);
		System.out.println("hostName :: "+ hostName);
		System.out.println("hostName :: "+ hostName);
		if (!"localhost".equals(hostName) 
			&& !"119.193.215.98".equals(hostName))
		{
				return "redirect:/web/mjon/msgdata/selectMsgDataView.do";
		}
		
		String categoryType = cateCode.getCateType();
		
		if(categoryType == null) {
			
			categoryType = "N";
			
		}
		
		// 문자 카테고리 리스트 불러오기
		List<CateCode> cateConfList = letterService.selectCateConfWithList(categoryType);
		model.addAttribute("cateCodeList", cateConfList);	
		
		// 문자 해쉬태그 리스트 불러오기
		String msgType = "M";
		List<HashConfVO> hashTagList = letterService.selectHashTagWithList(msgType);
		model.addAttribute("hashTagList", hashTagList);
		
		// 문자 리스트 불러오기
		LetterVO letterVO = new LetterVO();
		if(letterVO.getPageUnit() != 10) {
			letterVO.setPageUnit(letterVO.getPageUnit());
		}
		
		//로그인 권한정보 불러오기
		LoginVO loginVO = EgovUserDetailsHelper.isAuthenticated()? (LoginVO)EgovUserDetailsHelper.getAuthenticatedUser():null;
		model.addAttribute("loginVO", loginVO);
		
		for(int i=0 ; i < cateConfList.size(); i++) {
			if("선거".equals(cateConfList.get(i).getCateNm())) {
				letterVO.setCategoryCode(cateConfList.get(i).getCateCode());
			}
		}
		
		//주소록에서 선택시 넘어오는 파라미터
		if("Y".equals(searchVO.getMoveAddrFlag())) {
			model.addAttribute("addrVO", searchVO);
		}
		
		//주소록에서 선택시 넘어오는 파라미터
		if("Y".equals(searchVO.getMoveAddrAllFlag())) {
			AddrVO addrVO = new AddrVO();
			
			String userId = loginVO == null ? "" : EgovStringUtil.isNullToString(loginVO.getId());
			if(userId != "") {
				addrVO.setMberId(userId);
			} 
			addrVO.setRecordCountPerPage(100000);
			addrVO.setFirstIndex(0);
			addrVO.setSearchAddrGrpId(request.getParameter("searchAddrGrpId"));
			addrVO.setSearchCondition(request.getParameter("searchCondition"));
			addrVO.setSearchKeyword(request.getParameter("searchKeyword"));	
			addrVO.setStartKeyword(request.getParameter("startKeyword"));
			List<AddrVO> addrList = addrService.selectAddrList(addrVO);
			
			List<String> addrIdList = new ArrayList<String>();
			for(AddrVO item : addrList) {
				addrIdList.add(item.getAddrId());
			}
			
			searchVO.setAddrIdList(addrIdList);
			searchVO.setMoveAddrFlag("Y");
			
			model.addAttribute("addrVO", searchVO);
		}				
		
		PaginationInfo paginationInfo = new PaginationInfo();
		paginationInfo.setCurrentPageNo(letterVO.getPageIndex());
		paginationInfo.setRecordCountPerPage(letterVO.getPageUnit());
		paginationInfo.setPageSize(letterVO.getPageSize());

		letterVO.setFirstIndex(paginationInfo.getFirstRecordIndex());
		letterVO.setLastIndex(paginationInfo.getLastRecordIndex());
		letterVO.setRecordCountPerPage(paginationInfo.getRecordCountPerPage());
		
		
		List<?> resultPhoList = mjonMsgDataService.selectPhotoLetterList(letterVO);
		
		model.addAttribute("resultPhoList", resultPhoList);
		paginationInfo.setTotalRecordCount( resultPhoList.size()> 0 ? ((Long)((EgovMap)resultPhoList.get(0)).get("totCnt")).intValue() : 0);
		model.addAttribute("paginationInfo", paginationInfo);
		
		//발송결과 문자 재전송에서 넘어오는 경우 파마리터 전달
		List<String> temp = searchVO.getMsgSeqList();
		
		if(temp != null) {
			
			model.addAttribute("reSendMsgVO", searchVO);
			
		}
		model.addAttribute("letterVO", letterVO);
		
		// 문자 재전송 New
		model.addAttribute("msgResendAllFlag", searchVO.getMsgResendAllFlag());
		model.addAttribute("msgResendAllGroupId", searchVO.getMsgResendAllGroupId());
		model.addAttribute("msgResendAllAdvertiseYn", searchVO.getMsgResendAllAdvertiseYn());
		model.addAttribute("msgResendAllReplaceYn", searchVO.getMsgResendAllReplaceYn());
		
		return "web/msgcampain/tw/MsgTWDataView";
	}
	
	 /**
     * 선거 문자 20건씩 발송 단문/장문/그림문자 전송 화면 
     * @param searchVO
     * @param model
     * @return	"/web/mjon/msgcampain/selectMsgTWDataSMLViewAjax.do"
     * @throws Exception
     */
	@RequestMapping(value= {"/web/mjon/msgcampain/selectMsgTWDataSMLViewAjax.do"})
	public String selectMsgTWDataSMLView(@ModelAttribute("searchVO") MjonMsgDataVO searchVO, CateCode cateCode, ModelMap model) throws Exception{
		
		//로그인 권한정보 불러오기
    	LoginVO loginVO = EgovUserDetailsHelper.isAuthenticated()? (LoginVO)EgovUserDetailsHelper.getAuthenticatedUser():null;
    	String userId = loginVO == null ? "" : EgovStringUtil.isNullToString(loginVO.getId());
    	String author = loginVO == null ? "" : EgovStringUtil.isNullToString(loginVO.getAuthority());
    	
		String categoryType = cateCode.getCateType();
		
		if(categoryType == null) {
			
			categoryType = "N";
			
		}
		
		//문자 전송 개인 단가 불러오기
		
		//0.이벤트 진행중이 회원 정보 불러오기.
		//이벤트 회원 정보 테이블에서 대상자의 정보를 불러온다.
		MjonEventVO mjonEventVO = new MjonEventVO();
		mjonEventVO.setMberId(userId);
		MjonEventVO eventMberInfo = mjonEventService.selectEventMsgMberDefaultInfo(mjonEventVO);
		
		
		long eventDiffDate = 0;
		float eventRemainCash = 0;
		boolean compareEndDate = false;
		
		if(eventMberInfo != null) {
			
			String eventEndDate = eventMberInfo.getEventEndDate();
			
			/**
			 * MJUtil.getCompareDate()
			 * 현재 날짜와 파라미터 전달 날짜를 비교
			 * 전달날짜를 지난경우 False를 리턴함.
			 * 현재날짜 이전 혹은 같은 날짜면 True를 리턴함.
			 * 
			 * */
			
			if(eventEndDate != null) {
				compareEndDate = MJUtil.getCompareDate(eventEndDate);
				eventRemainCash = (float) eventMberInfo.getEventRemainCash(); 
				
				//이벤트 종료 일자가 지난 경우, 이벤트 상태가 종료아 아니면 종료 처리 시킴
				//이벤트 남은 캐시가 단문 발송금액 7.5원 보다 낮으면 이벤트 종료 시킴
				if(!compareEndDate || eventRemainCash < 7.5) {
					
					if(!eventMberInfo.getEventStatus().equals("E")) {
						
						//이벤트 상태값을 종료로 변경한다.
						mjonEventVO.setEventInfoId(eventMberInfo.getEventInfoId());
						mjonEventVO.setEventStatus("E");
						mjonEventVO.setEventMemo("이벤트 발송 최소 금액(7.5) 부족 혹은 이벤트 종료일 초과되어 이벤트 종료 시킴");
						mjonEventVO.setEventRemainCash(eventRemainCash);
						mjonEventService.updateEventEndStatus(mjonEventVO);
						eventMberInfo.setEventStatus("E");
						
					}
					
				}else {//이벤트 진행중이면 남은 날짜 계산해서 전달.
					
					/**
					 * MJUtil.getDiffDateDay()
					 * 현재 날짜와 파라미터 날짜 사이의 날짜 수를 계산해줌.
					 * 
					 * */
					eventDiffDate = MJUtil.getDiffDateDay(eventEndDate);
					
				}
			}
			
		}
		
		//남은 날짜값을 절대값으로 변경(음수로 나오기 때문)
		model.addAttribute("eventDiffDate", Math.abs(eventDiffDate));
		model.addAttribute("compareEndDate", compareEndDate);
		model.addAttribute("eventRemainCash", eventRemainCash);
		model.addAttribute("eventMberInfo", eventMberInfo);
		
		//1.시스템 기본 단가 정보 불러오기
		JoinSettingVO sysJoinSetVO = mjonMsgDataService.selectJoinSettingInfo();
		
		// 등급제 단가 추출 => 시스템 단가에 적용
		sysJoinSetVO = mberGrdService.selectMberGrdDefaultInfo(sysJoinSetVO, userId);
		
		//2.사용자 개인 단가 정보 불러오기
		MberManageVO mberManageVO = new MberManageVO(); 
		
		if(!userId.equals("") && !author.equals("ROLE_ADMIN")) {
			
			mberManageVO = mjonMsgDataService.selectMberManageInfo(userId);
			searchVO.setUserId(userId);
			
		}
		
		model.addAttribute("exceptSpamYn", mberManageVO.getExceptSpamYn());
		
		//3.사용자 개인단가 정보가 0이 아니면 개인단가 사용, 없으면 시스템 기본 단가 사용
		Float shortPrice = mberManageVO.getShortPrice();
		Float longPrice = mberManageVO.getLongPrice();
		Float picturePrice = mberManageVO.getPicturePrice();
		Float picture2Price = mberManageVO.getPicture2Price();
		Float picture3Price = mberManageVO.getPicture3Price();
		BigDecimal userMoney = new BigDecimal(mberManageVO.getUserMoney()).setScale(2, RoundingMode.HALF_EVEN);
		
		//일반 단가정보 저장 변수 셋팅 - 이벤트 캐시 부족시 일반단가로 계산하기 위해서임.20230328, 우영두추가
		Float norShortPrice = mberManageVO.getShortPrice();
		Float norLongPrice = mberManageVO.getLongPrice();
		Float norPicturePrice = mberManageVO.getPicturePrice();
		Float norPicture2Price = mberManageVO.getPicture2Price();
		Float norPicture3Price = mberManageVO.getPicture3Price();
		
		//기존 소수점 2째자리에서 반올림하였으나, 정책 변경으로 소수점 버림 처리함 20220623 
		/*int shortPrice = (int) mberManageVO.getShortPrice();
		int longPrice = (int) mberManageVO.getLongPrice();
		int picturePrice = (int) mberManageVO.getPicturePrice();
		int picture2Price = (int) mberManageVO.getPicture2Price();
		int picture3Price = (int) mberManageVO.getPicture3Price();
		int userMoney = (int) mberManageVO.getUserMoney();*/
		
		String userPoint = mberManageVO.getUserPoint();
		
		//이벤트 진행 회원의 발송 단가 처리해주기
		if(eventMberInfo != null && eventMberInfo.getEventStatus().equals("Y") && compareEndDate) {
			
			shortPrice = Float.parseFloat(eventMberInfo.getEventShortPrice());
			longPrice = Float.parseFloat(eventMberInfo.getEventLongPrice());
			picturePrice = Float.parseFloat(eventMberInfo.getEventPicturePrice());
			picture2Price = Float.parseFloat(eventMberInfo.getEventPicture2Price());
			picture3Price = Float.parseFloat(eventMberInfo.getEventPicture3Price());
			
			//이벤트 캐시 부족시 일반단가로 계산하기 위해서임.20230328, 우영두추가
			if(shortPrice < 1 || longPrice < 1 || picturePrice < 1) {//이벤트 단가 적용시 일반단가도 필요하여 셋팅 해줌.
				
				norShortPrice = (float) sysJoinSetVO.getShortPrice();
				norLongPrice = (float) sysJoinSetVO.getLongPrice();
				norPicturePrice = (float) sysJoinSetVO.getPicturePrice();
				norPicture2Price = (float) sysJoinSetVO.getPicture2Price();
				norPicture3Price = (float) sysJoinSetVO.getPicture3Price();
				
			}
			
		}else if(shortPrice < 1 || longPrice < 1 || picturePrice < 1) {
			
			shortPrice = (float) sysJoinSetVO.getShortPrice();
			longPrice = (float) sysJoinSetVO.getLongPrice();
			picturePrice = (float) sysJoinSetVO.getPicturePrice();
			picture2Price = (float) sysJoinSetVO.getPicture2Price();
			picture3Price = (float) sysJoinSetVO.getPicture3Price();
			
		}
		
		model.addAttribute("shortPrice", shortPrice);
		model.addAttribute("longPrice", longPrice);
		model.addAttribute("picturePrice", picturePrice);
		model.addAttribute("picture2Price", picture2Price);
		model.addAttribute("picture3Price", picture3Price);
		model.addAttribute("userMoney", userMoney);
		model.addAttribute("userPoint", userPoint);
		
		//이벤트 캐시 부족시 일반단가로 계산하기 위해서임.20230328, 우영두추가
		if(norShortPrice < 1 || norLongPrice < 1 || norPicturePrice < 1) {//협의 단가가 없는 경우 일반단가에 시스템 단가로 셋팅해줌
			
			norShortPrice = (float) sysJoinSetVO.getShortPrice();
			norLongPrice = (float) sysJoinSetVO.getLongPrice();
			norPicturePrice = (float) sysJoinSetVO.getPicturePrice();
			norPicture2Price = (float) sysJoinSetVO.getPicture2Price();
			norPicture3Price = (float) sysJoinSetVO.getPicture3Price();
			
		}
		
		model.addAttribute("norShortPrice", norShortPrice);
		model.addAttribute("norLongPrice", norLongPrice);
		model.addAttribute("norPicturePrice", norPicturePrice);
		model.addAttribute("norPicture2Price", norPicture2Price);
		model.addAttribute("norPicture3Price", norPicture3Price);
		
		//선거 후보자 정보 불러오기
		MjonCandidateVO mjonCandidateVO = new MjonCandidateVO();
		
		if(userId != ""){
			
			mjonCandidateVO = mjonCandidateService.selectCandidateDataInfo(userId);
			
			//String cryptText = egovCryptoUtil.encrypt(plainText);

			if(mjonCandidateVO != null) {
				
				// 주민번호 복호화 하기
				String regidentNo1 = egovCryptoUtil.decrypt(mjonCandidateVO.getRegidentNo1());
		    	String regidentNo2 = egovCryptoUtil.decrypt(mjonCandidateVO.getRegidentNo2());
		    	
		    	mjonCandidateVO.setRegidentNo1(regidentNo1);
		    	mjonCandidateVO.setRegidentNo2(regidentNo2);
				
			}
			
		}
		
		model.addAttribute("mjonCandidateVO", mjonCandidateVO);
		
		// 이메일 코드조회
		ComDefaultCodeVO voComCode = new ComDefaultCodeVO();
		voComCode.setCodeId("ITN031");
		model.addAttribute("emailCode", cmmUseService.selectCmmCodeDetail(voComCode));
		
		if(!userId.equals("")) {//로그인 했을때만 발신번호 리스트 불러오기
			
			//아이디 발신번호 리스트 불러오기.
			List<String> resultSendPhonList = mjonMsgDataService.selectSendPhonNumList(userId);
			List<String> resultPhonList = new ArrayList<String>();
			MJUtil mjUtil = new MJUtil();
			
			for(String phone : resultSendPhonList) {
				
				resultPhonList.add(mjUtil.addDash(phone));
				
			}
			model.addAttribute("resultPhonList", resultPhonList);
			
		}
		
		// 문자 카테고리 리스트 불러오기
		List<CateCode> cateConfList = letterService.selectCateConfWithList(categoryType);
		model.addAttribute("cateCodeList", cateConfList);	
		
		//그림 문자 리스트 불러오기
		LetterVO letterVO = new LetterVO();
		if(letterVO.getPageUnit() != 10) {
			letterVO.setPageUnit(letterVO.getPageUnit());
		}
		
		MjonSymbolVO symbolVO = new MjonSymbolVO();
		// 특수문자 리스트 불러오기
		List<MjonSymbolVO> symbolList = mjonSymbolService.selectMjonSymbolList(symbolVO);
		model.addAttribute("symbolList", symbolList);
		
		//최근 전송 내역
		/*Calendar cal = Calendar.getInstance();
    	Date now = new Date();
    	
    	SimpleDateFormat format = new SimpleDateFormat("yyyy/MM/dd");
    	
    	cal.setTime(now);
    	cal.add(Calendar.DATE, -3);
    	
    	String chkDate = format.format(cal.getTime());
    	
    	searchVO.setMyMsgStDt(chkDate);	//검색 시작일 저장 - 현재날짜로 부터 3일 이전 날짜로 시작
		List<?> resultLatestMsgList = mjonMsgDataService.selectLatestMsgList(searchVO);
		model.addAttribute("resultLatestMsgList", resultLatestMsgList);*/
		
		//자주보내는 번호
		/*List<?> resultBookMarkMsgList = mjonMsgDataService.selectBookMarkMsgList(searchVO);
		model.addAttribute("resultBookMarkMsgList", resultBookMarkMsgList);*/
		

		/** pageing */
		PaginationInfo paginationInfo = new PaginationInfo();
		paginationInfo.setCurrentPageNo(letterVO.getPageIndex());
		paginationInfo.setRecordCountPerPage(letterVO.getPageUnit());
		paginationInfo.setPageSize(letterVO.getPageSize());

		letterVO.setFirstIndex(paginationInfo.getFirstRecordIndex());
		letterVO.setLastIndex(paginationInfo.getLastRecordIndex());
		letterVO.setRecordCountPerPage(paginationInfo.getRecordCountPerPage());
		
		List<?> resultPhoList = mjonMsgDataService.selectPhotoLetterList(letterVO);
		
		model.addAttribute("resultPhoList", resultPhoList);
		paginationInfo.setTotalRecordCount( resultPhoList.size()> 0 ? ((Long)((EgovMap)resultPhoList.get(0)).get("totCnt")).intValue() : 0);
		model.addAttribute("paginationInfo", paginationInfo);
		model.addAttribute("mberManageVO", mberManageVO);
		
		//기존 작업하던 수신목록 정보가 있는지 확인
		int callSeq = mjonCandidateService.selectMsgCallToSeqNum(userId);
		model.addAttribute("callSeq", callSeq);
		
		return "web/msgcampain/tw/MsgTWDataSMLView";
	}
	
	//선거문자 20건 받는사람 목록 불러오기
	@RequestMapping(value="/web/mjon/msgcampain/selectMsgTWCallToListAjax.do")
	public String selectMsgTWCallToListAjax(MjonCandidateTWVO mjonCandidateTWVO, ModelMap model, RedirectAttributes redirectAttributes) throws Exception{
		
		
		//로그인 권한정보 불러오기
    	LoginVO loginVO = EgovUserDetailsHelper.isAuthenticated()? (LoginVO)EgovUserDetailsHelper.getAuthenticatedUser():null;
    	String userId = loginVO == null ? "" : EgovStringUtil.isNullToString(loginVO.getId());
    	
    	if(userId.equals("")) {
    		
    		redirectAttributes.addFlashAttribute("message", "로그인이 필요합니다.");
			RedirectUrlMaker redirectUrlMaker = new RedirectUrlMaker("/web/user/login/login.do");
			return redirectUrlMaker.getRedirectUrl();
    		
    	}
		
		/** pageing */
		PaginationInfo paginationInfo = new PaginationInfo();
		paginationInfo.setCurrentPageNo(mjonCandidateTWVO.getPageIndex());
		paginationInfo.setRecordCountPerPage(20);
		paginationInfo.setPageSize(5);

		mjonCandidateTWVO.setFirstIndex(paginationInfo.getFirstRecordIndex());
		mjonCandidateTWVO.setLastIndex(paginationInfo.getLastRecordIndex());
		mjonCandidateTWVO.setRecordCountPerPage(20);
		
		mjonCandidateTWVO.setMberId(userId);
		List<?> resultCallToList = mjonCandidateService.selectCampainTWCalltoList(mjonCandidateTWVO);
		
		model.addAttribute("resultCallToList", resultCallToList);
		paginationInfo.setTotalRecordCount( resultCallToList.size()> 0 ? ((Long)((EgovMap)resultCallToList.get(0)).get("totCnt")).intValue() : 0);
		model.addAttribute("paginationInfo", paginationInfo);
		model.addAttribute("mjonCandidateTWVO", mjonCandidateTWVO);
		
		//전체 남은 리스트 수 및 전송완료 등 건수 정보 조회
		MjonCandidateTWVO resultTotCallToInfo = mjonCandidateService.selectMsgTWCallToTotCount(mjonCandidateTWVO);
		
		model.addAttribute("resultTotCallToInfo", resultTotCallToInfo);
		
		return "web/msgcampain/tw/MsgTWDataCallToListView";
	}
	
	
	@RequestMapping(value="/web/mjon/msgcampain/insertMyAddrTWCallToAjax.do")
	public ModelAndView insertMyAddrTWCallToAjax(MjonCandidateTWVO mjonCandidateTWVO) throws Exception{
		
		ModelAndView modelAndView = new ModelAndView();
		modelAndView.setViewName("jsonView");
		
		//로그인 권한정보 불러오기
    	LoginVO loginVO = EgovUserDetailsHelper.isAuthenticated()? (LoginVO)EgovUserDetailsHelper.getAuthenticatedUser():null;
    	String userId = loginVO == null ? "" : EgovStringUtil.isNullToString(loginVO.getId());

    	if(userId.equals("")) {
    		
    		modelAndView.addObject("result", "loginFail");
    		modelAndView.addObject("message", "로그인이 필요합니다.");
    		return modelAndView;
    		
    	}
    	try {
			
    		/*
    		 * 2024.01.25 우영두 성능 개선
    		 * 데이터수가 10만건이 넘는 상황일 경우 중복제거 및 데이터 처리 Loop 문 최소화
    		 * 
    		 * */
    		List<String> callToList = new ArrayList<String>();
    		int totRowDataCnt = mjonCandidateTWVO.getCallToArr().length;
    		
    		/*for(String callTo : mjonCandidateTWVO.getCallToArr()) {
    			
    			callToList.add(callTo);
    			totRowDataCnt++;
    			
    		}*/
    		
    		//전달받은 수신목록 중복 제거
    		callToList = Arrays.asList(mjonCandidateTWVO.getCallToArr());
    		callToList = callToList.stream().distinct().collect(Collectors.toList());
    		
    		//수신자 목록 중복 체크 및 디비화 처리
    		//List<String> dupCallToList = MJUtil.getDuplicateList(callToList);
    		
    		String dupCallCnt = Integer.toString(totRowDataCnt - callToList.size());
    		//System.out.println("++++++++++++++++++ dupCallCnt ::: "+dupCallCnt);
    		//입력되어있는 데이터의 마지막 순번(call_seq)을 조회해 온다.
    		int maxCallSeq = mjonCandidateService.selectCandidateTWMaxCallSeq(userId);
    		maxCallSeq += 1;//마지막 순번에 1을 더해서 다음 순번을 지정해준다.
    		
    		List<MjonCandidateTWVO> mjonCandidateTwVO = new ArrayList<MjonCandidateTWVO>();
    		
    		for(String callTo : callToList) {
    			
    			MjonCandidateTWVO tmpCandidateTwVO = new MjonCandidateTWVO();
    			
    			tmpCandidateTwVO.setMberId(userId);
    			tmpCandidateTwVO.setCallTo(callTo);
    			tmpCandidateTwVO.setFrstRegisterId(userId);
    			tmpCandidateTwVO.setLastUpdusrId(userId);
    			tmpCandidateTwVO.setCallSeq(maxCallSeq);
    			
    			mjonCandidateTwVO.add(tmpCandidateTwVO);
    			
    		}
    		
    		int resultCnt = mjonCandidateService.insertCandidateTWCallToData(mjonCandidateTwVO);
    		
    		if(resultCnt > 0) {
    			
    			modelAndView.addObject("result", "success");
    			modelAndView.addObject("dupCallCnt", dupCallCnt);
    			modelAndView.addObject("maxCallSeq", maxCallSeq);
    			
    		}else {
    			
    			modelAndView.addObject("result", "fail");
        		modelAndView.addObject("message", "주소록을 불러오는 중 오류가 발생하였습니다. 잠시 후 다시 시도해 주세요.");
    			
    		}
    		
    		
		} catch (Exception e) {
			System.out.println("insertMyAddrTWCallToAjax Controller Error!!! " + e);
			modelAndView.addObject("result", "fail");
    		modelAndView.addObject("message", "주소록을 불러오는 중 오류가 발생하였습니다. 잠시 후 다시 시도해 주세요.");
    		return modelAndView;
		}
		
		return modelAndView;
	}
	
	/*
	 * 받는사람 목록 데이터 전체 초기화 처리
	 * 데이터베이스에 저장된 해당 회원의 발신목록 정보를 모두 초기화 처리
	 * */
	@RequestMapping(value="/web/mjon/msgcampain/updateMsgTWCallToListResetAjax.do")
	public ModelAndView updateMsgTWCallToListResetAjax(MjonCandidateTWVO mjonCandidateTWVO) throws Exception{
		
		ModelAndView modelAndView = new ModelAndView();
		modelAndView.setViewName("jsonView");
		
		//로그인 권한정보 불러오기
    	LoginVO loginVO = EgovUserDetailsHelper.isAuthenticated()? (LoginVO)EgovUserDetailsHelper.getAuthenticatedUser():null;
    	String userId = loginVO == null ? "" : EgovStringUtil.isNullToString(loginVO.getId());

    	if(userId.equals("")) {
    		
    		modelAndView.addObject("result", "loginFail");
    		modelAndView.addObject("message", "로그인이 필요합니다.");
    		return modelAndView;
    		
    	}
    	
    	try {
    		
    		mjonCandidateTWVO.setMberId(userId);
    		
    		//수신목록 테이블에 있는 회원의 데이터를 모두 취소 처리해준다.
    		int resultCnt = mjonCandidateService.updateCandidateTWCallToDataCancel(userId);
    		
    		if(resultCnt > 0) {
    			
    			modelAndView.addObject("result", "success");
    			
    		}else {
    			
    			modelAndView.addObject("result", "fail");
        		modelAndView.addObject("message", "받는사람 초기화 중 오류가 발생하였습니다. 잠시 후 다시 시도해 주세요.");
    			
    		}
			
		} catch (Exception e) {
			System.out.println("updateMsgTWCallToListResetAjax Controller Error!!! " + e);
			modelAndView.addObject("result", "fail");
    		modelAndView.addObject("message", "받는사람 초기화 중 오류가 발생하였습니다. 잠시 후 다시 시도해 주세요.");
    		return modelAndView;
		}
		
		return modelAndView;
	}
	
	/*
	 * 받는사람 목록 선택 삭제 데이터 취소 처리
	 * 
	 * */
	@RequestMapping(value="/web/mjon/msgcampain/updateMsgTWCallToListChkDelAjax.do")
	public ModelAndView updateMsgTWCallToListChkDelAjax(MjonCandidateTWVO mjonCandidateTWVO) throws Exception{
		
		ModelAndView modelAndView = new ModelAndView();
		modelAndView.setViewName("jsonView");
		
		//로그인 권한정보 불러오기
    	LoginVO loginVO = EgovUserDetailsHelper.isAuthenticated()? (LoginVO)EgovUserDetailsHelper.getAuthenticatedUser():null;
    	String userId = loginVO == null ? "" : EgovStringUtil.isNullToString(loginVO.getId());

    	if(userId.equals("")) {
    		
    		modelAndView.addObject("result", "loginFail");
    		modelAndView.addObject("message", "로그인이 필요합니다.");
    		return modelAndView;
    		
    	}
    	
    	try {
    		
    		mjonCandidateTWVO.setMberId(userId);
    		
    		int resultCnt = mjonCandidateService.updateMsgTWCallToListChkDel(mjonCandidateTWVO);
    		
    		if(resultCnt > 0) {
    			
    			modelAndView.addObject("result", "success");
    			
    		}else {
    			
    			modelAndView.addObject("result", "fail");
        		modelAndView.addObject("message", "받는사람 삭제 중 오류가 발생하였습니다. 잠시 후 다시 시도해 주세요.");
    			
    		}
			
		} catch (Exception e) {
			System.out.println("updateMsgTWCallToListResetAjax Controller Error!!! " + e);
			modelAndView.addObject("result", "fail");
    		modelAndView.addObject("message", "받는사람 초기화 중 오류가 발생하였습니다. 잠시 후 다시 시도해 주세요.");
    		return modelAndView;
		}
		
		return modelAndView;
	}
	
	@RequestMapping(value="/web/mjon/msgcampain/insertMsgTWCallToOneNumberAddAjax.do")
	public ModelAndView insertMsgTWCallToOneNumberAdd(MjonCandidateTWVO mjonCandidateTWVO) throws Exception{
		
		ModelAndView modelAndView = new ModelAndView();
		modelAndView.setViewName("jsonView");
		
		//로그인 권한정보 불러오기
    	LoginVO loginVO = EgovUserDetailsHelper.isAuthenticated()? (LoginVO)EgovUserDetailsHelper.getAuthenticatedUser():null;
    	String userId = loginVO == null ? "" : EgovStringUtil.isNullToString(loginVO.getId());

    	if(userId.equals("")) {
    		
    		modelAndView.addObject("result", "loginFail");
    		modelAndView.addObject("message", "로그인이 필요합니다.");
    		return modelAndView;
    		
    	}
    	
    	try {
			
    		
    		System.out.println("================ callSeq ::: "+mjonCandidateTWVO.getCallSeq());
    		String callToNum = "";
    		for(String callTo : mjonCandidateTWVO.getCallToArr()) {
    			
    			System.out.println("++++++++++++++++ callToArr ::: "+callTo);
    			callToNum = callTo;
    			
    		}
    		
    		int callSeq = mjonCandidateTWVO.getCallSeq();
    		
    		//처음 등록되는 연락처 번호이면 기존 회원 CallSeq 마지막 번호 다음으로 신규 추가
    		if(callSeq == 0) {
    			
    			int maxCallSeq = mjonCandidateService.selectCandidateTWMaxCallSeq(userId);
    			maxCallSeq += 1;//마지막 순번에 1을 더해서 다음 순번을 지정해준다.
    			
    			mjonCandidateTWVO.setCallSeq(maxCallSeq);
    			
    		}
    		
    		//연락처 추가 관련 입력정보 셋팅해주기
    		mjonCandidateTWVO.setMberId(userId);
			mjonCandidateTWVO.setCallTo(callToNum.replaceAll("-", ""));
			mjonCandidateTWVO.setFrstRegisterId(userId);
			mjonCandidateTWVO.setLastUpdusrId(userId);
			
			//중복 연락처 체크 해주기
			int dupCallNum = mjonCandidateService.selectCandidateTWCallToDupleCnt(mjonCandidateTWVO);
			
			if(dupCallNum > 0) {
				modelAndView.addObject("result", "fail");
        		modelAndView.addObject("message", "이미 등록된 연락처 입니다. 연락처를 다시 확인해 주세요.");
				return modelAndView;
			}
			
			int resultCnt = mjonCandidateService.insertCandidateTWCallToDataOnlyAdd(mjonCandidateTWVO);
    		
			if(resultCnt > 0) {
				modelAndView.addObject("result", "success");
				modelAndView.addObject("callSeq", mjonCandidateTWVO.getCallSeq());
			}else {
				modelAndView.addObject("result", "fail");
        		modelAndView.addObject("message", "연락처 추가 중 오류가 발생하였습니다. 잠시 후 다시 시도해 주세요.");
			}
    		
    		
		} catch (Exception e) {
			System.out.println("insertMsgTWCallToOneNumberAdd Controller Error!!! " + e);
			modelAndView.addObject("result", "fail");
    		modelAndView.addObject("message", "연락처 추가 중 오류가 발생하였습니다. 잠시 후 다시 시도해 주세요.");
    		return modelAndView;
		}
    	
    	return modelAndView;
		
	}
	
	
	
	/*
	 * 선거문자 20건 발송 처리
	 * 
	 * */
	
	   /**
     * 선거문자 20건 문자 발송 화면 
     * @param searchVO
     * @param model
     * @return	"/web/mjon/msgcampain/sendMsgTWDataAjax.do"
     * @throws Exception
     */
	@RequestMapping(value= {"/web/mjon/msgcampain/sendMsgTWDataAjax.do"})
	public ModelAndView sendMsgTWData(@ModelAttribute("searchVO") MjonMsgVO mjonMsgVO, 
			RedirectAttributes redirectAttributes, 
			HttpServletRequest request,
			ModelMap model) throws Exception{
		
		ModelAndView modelAndView = new ModelAndView();
		modelAndView.setViewName("jsonView");
		
		//String resultSts = "0";
		//String resultBlockSts = "0";
		
		int resultSts = 0;			//발송결과 건수
		int resultBlockSts = 0;	//수신거부 등록번호로 발송을 안한 건수
		String userId = "";
		
		try {
			
			LoginVO loginVO = EgovUserDetailsHelper.isAuthenticated()? (LoginVO)EgovUserDetailsHelper.getAuthenticatedUser():null;
	    	userId = loginVO == null ? "" : EgovStringUtil.isNullToString(loginVO.getId());
	    	
        	if(userId.equals("")) {
        		
        		modelAndView.addObject("message", "로그인 후 이용이 가능합니다.");
    			modelAndView.addObject("result", "loginFail");
    			modelAndView.addObject("resultSts", resultSts);
    			return modelAndView;
        		
        	}else {
        		
        		mjonMsgVO.setUserId(userId);
        		
    	    	//발신번호가 등록된 유효한 번호인지 확인 
    	    	int sendCallFromCnt = mjonMsgService.selectCallFromNumberChk(mjonMsgVO);
    	    	
    	    	if(sendCallFromCnt < 1) {
    	    		
    	    		modelAndView.addObject("message", "등록된 발신번호를 찾을 수 없습니다.");
        			modelAndView.addObject("result", "loginFail");
        			modelAndView.addObject("resultSts", resultSts);
        			return modelAndView;
    	    		
    	    	}
        		
        		/**
        		 * 회원 정지된 상태이면 문자 발송이 안되도록 처리함
        		 * 현재 로그인 세션도 만료 처리함
        		 * */
        		boolean mberSttus = userManageService.selectUserStatusInfo(userId);
        		
        		if(!mberSttus) {
        			
        			modelAndView.addObject("message", "현재 고객님께서는 문자온 서비스 이용이 정지된 상태로 문자를 발송하실 수 없습니다. 이용정지 해제를 원하시면 고객센터로 연락주시기 바랍니다.");
        			modelAndView.addObject("result", "statusFail");
        			modelAndView.addObject("resultSts", resultSts);
        			
        			request.getSession().invalidate();
        			
        			return modelAndView;
        			
        		}
        		
        	}
        	
        	//회원정보에서 스미싱 회원 여부 정보 조회
        	UserManageVO userManageVO = new UserManageVO();
        	
        	userManageVO.setMberId(userId);
        	UserManageVO resultUserVO = userManageService.selectSmishingYnUserInfo(userManageVO);
        	String smishingYn = resultUserVO.getSmishingYn();
        	mjonMsgVO.setSmishingYn(smishingYn);
        	
        	String charset = "euc-kr"; 						//문자 바이트 계산에 필요한 캐릭터 셋 : 한글 2Byte로 계산
        	String smsCont = mjonMsgVO.getSmsTxt().replace("\r\n", "\n");
        	
        	int FrBytes = smsCont.getBytes(charset).length;
        	
        	if(FrBytes > 2000) {
        		
        		modelAndView.addObject("message", "문자 내용은 2000Byte를 넘을 수 없습니다.");
    			modelAndView.addObject("result", "smsLengFail");
    			return modelAndView;
        		
        	}
    		
        	System.out.println("mjonMsgVO.getMsgType1() ::: "+mjonMsgVO.getMsgType());
        	
        	String msgType = mjonMsgVO.getMsgType();
        	
        	//내문자저장함에 저장후 문자를 발송하는경우 문자 타입이 숫자가 아닌 문자로 넘어와서 변경 처리함- 20220520 우영두
        	if(msgType.equals("P") || msgType.equals("L")) {
        		msgType = "6";
        	}else if(msgType.equals("S")) {
        		
        		msgType = "4";
        	}
        	
        	//메세지 타입이 단문이면 진짜 단문인지 한번더 확인해 준다.
        	if(msgType.equals("4")) {
        		
        		//메세지 길이가 90Byte를초과 하거나, 그림 이미지가 있는경우 메세지 타입을 6으로 변경해준다.
        		if(FrBytes > 90 || mjonMsgVO.getImgFilePath().length > 0) {
        			
        			msgType = "6";
        			
        		}
        		
        	}
        	
        	mjonMsgVO.setMsgType(msgType);
        	
        	//장문 메세지일 경우
        	int fileCount = 0;
        	if(msgType.equals("6")) {
        		
        		//그림 이미지가 첨부된 경우
        		if(mjonMsgVO.getImgFilePath() != null || mjonMsgVO.getImgFilePath().length > 0) {
        			
        			String[] path = mjonMsgVO.getImgFilePath();
        			String[] fileId = mjonMsgVO.getImgFileId();
        			String[] templateYn = mjonMsgVO.getTemplateYn();
        			
            		for(int i=0; i<path.length; i++) {
            			
                		if("Y".equals(templateYn[i])) {
            				//템플릿 사용누계 증가
                			letterService.updateTemplateUseCount(fileId[i]);
            			}
                		
                		String atchFileId = fileId[i];
                		String imgFilePath = mjonMsgService.selectPhotoImgFileRealPath(atchFileId);
                		
                		// 아이하트, 현대퓨쳐넷 두 중계사는 이미지 경로는 풀패스 경로로 넘겨주면 됨
                		if(i == 0) {
                			
                			mjonMsgVO.setFileName1(imgFilePath);
                			
                		}else if(i == 1) {
                			
                			mjonMsgVO.setFileName2(imgFilePath);
                			
                		}else {
                			
                			mjonMsgVO.setFileName3(imgFilePath);
                			
                		}
                		fileCount ++;
                	}
                	
                	//첨부파일 갯수 셋팅해주기
                	mjonMsgVO.setFileCnt(Integer.toString(fileCount));
        			
        		}
            	
        	}
        	
        	//파일 갯수는 있는데 파일 경로가 없는 경우 문자발송이 안되도록 튕겨내도록 함 - 20220520 우영두
        	if(fileCount > 0) {
        		
        		if(mjonMsgVO.getFileName1() == null && mjonMsgVO.getFileName2() == null && mjonMsgVO.getFileName3() == null) {
        			
        			modelAndView.addObject("message", "문자 메세지 이미지 추가에 오류가 발생하여 문자 발송이 취소 되었습니다.");
    				modelAndView.addObject("result", "imgSourceFail");
    				modelAndView.addObject("resultSts", "0");
    				modelAndView.addObject("resultBlockSts", "0");
    				
    				return modelAndView; 
        			
        		}
        		
        	}
        	
        	/*
        	 * 화면에서 넘어오는 단가 금액 및 총 결제 캐시 금액 체크 해주기
        	 * 검증을 위해서 시스템 단가, 회원 협의 단가, 이벤트 단가 정보 조회
        	 * 조회 단가를 이용하여 총 결제 캐시 금액 계산
        	 * 파라미터로 넘어온 개별단가(eachPrice), 총 결제캐시(totPrice)를 비요하여 동일하지 않으면 컨트롤러에서 계산한 금액으로 입력해줌.
        	 */
        	MjonEventVO mjonEventVO = new MjonEventVO();
    		mjonEventVO.setMberId(userId);
    		MjonEventVO eventMberInfo = mjonEventService.selectEventMsgMberDefaultInfo(mjonEventVO);
    		
    		//1.시스템 기본 단가 정보 불러오기
    		JoinSettingVO sysJoinSetVO = mjonMsgDataService.selectJoinSettingInfo();
    		
    		// 등급제 단가 추출 => 시스템 단가에 적용
    		sysJoinSetVO = mberGrdService.selectMberGrdDefaultInfo(sysJoinSetVO, userId);
    		
    		//2.사용자 개인 단가 정보 불러오기
    		MberManageVO mberManageVO = new MberManageVO(); 
    		mberManageVO = mjonMsgDataService.selectMberManageInfo(userId);
    			
    		//3.사용자 개인단가 정보가 0이 아니면 개인단가 사용, 없으면 시스템 기본 단가 사용
    		Float shortPrice = mberManageVO.getShortPrice();
    		Float longPrice = mberManageVO.getLongPrice();
    		Float picturePrice = mberManageVO.getPicturePrice();
    		Float picture2Price = mberManageVO.getPicture2Price();
    		Float picture3Price = mberManageVO.getPicture3Price();
    		
    		//기존 소수점 2째자리에서 반올림하였으나, 정책 변경으로 소수점 버림 처리함 20220623 
    		boolean compareEndDate = false;
    		float eventRemainCash = 0;
    		float paramEachPrice = Float.parseFloat(mjonMsgVO.getEachPrice());
    		
    		if(eventMberInfo != null) {
    			
    			String eventEndDate = eventMberInfo.getEventEndDate();
    			
    			if(eventEndDate != null) {
    				compareEndDate = MJUtil.getCompareDate(eventEndDate);
    				eventRemainCash = (float) eventMberInfo.getEventRemainCash();
    				
    				//이벤트 금액 및 기간 체크
    				if(!compareEndDate || eventRemainCash < paramEachPrice) {
    					
    					if(!eventMberInfo.getEventStatus().equals("E")) {
    						
    						//이벤트 상태값을 종료로 변경한다.
    						mjonEventVO.setEventInfoId(eventMberInfo.getEventInfoId());
    						mjonEventVO.setEventStatus("E");
    						mjonEventVO.setEventMemo("발송 최소 금액("+ paramEachPrice +") 부족 혹은 이벤트 종료일 초과되어 이벤트 종료 시킴");
    						mjonEventVO.setEventRemainCash(eventRemainCash);
    						mjonEventService.updateEventEndStatus(mjonEventVO);
    						eventMberInfo.setEventStatus("E");
    						
    					}
    					
    				}
    			}
    		}
    		
    		//이벤트 진행 회원의 발송 단가 처리해주기
    		if(eventMberInfo != null && eventMberInfo.getEventStatus().equals("Y") && compareEndDate) {
    			
    			shortPrice = Float.parseFloat(eventMberInfo.getEventShortPrice());
    			longPrice = Float.parseFloat(eventMberInfo.getEventLongPrice());
    			picturePrice = Float.parseFloat(eventMberInfo.getEventPicturePrice());
    			picture2Price = Float.parseFloat(eventMberInfo.getEventPicture2Price());
    			picture3Price = Float.parseFloat(eventMberInfo.getEventPicture3Price());
    			
    		}else if(shortPrice < 1 || longPrice < 1 || picturePrice < 1) {//협의 단가가 없는 경우 시스템 단가 적용해 주기
    			
    			shortPrice = (float) sysJoinSetVO.getShortPrice();
    			longPrice = (float) sysJoinSetVO.getLongPrice();
    			picturePrice = (float) sysJoinSetVO.getPicturePrice();
    			picture2Price = (float) sysJoinSetVO.getPicture2Price();
    			picture3Price = (float) sysJoinSetVO.getPicture3Price();
    			
    		}
    		
    		// 토탈금액 "," 리플레이스 처리
    		mjonMsgVO.setTotPrice(mjonMsgVO.getTotPrice().replaceAll(",", ""));

        	float tmpOrgEachPrice = Float.parseFloat(mjonMsgVO.getEachPrice());
        	float tmpOrgTotPrice = Float.parseFloat(mjonMsgVO.getTotPrice());
        	
        	System.out.println("mjonMsgVO.getMsgType2() ::: "+mjonMsgVO.getMsgType());
        	
        	// MSG_TYPE 다시계산 
			if(mjonMsgVO.getFileName1() != null) {
				mjonMsgVO.setMsgType("6");
			}else {
				if(FrBytes < 2000) {
					if(FrBytes > 90) {// 90Byte 초과시 장문
						mjonMsgVO.setMsgType("6");
					}else {// 그외 단문
						mjonMsgVO.setMsgType("4"); 
					}
				}
			}
			
			System.out.println("mjonMsgVO.getMsgType3() ::: "+mjonMsgVO.getMsgType());
			
        	//각 문자 종류별 단가 셋팅해주기
    		float tmpEachPrice = 0;
    		if(mjonMsgVO.getMsgType().equals("4")) {
    			mjonMsgVO.setEachPrice(shortPrice.toString());
    			tmpEachPrice = shortPrice;
    		}else if(mjonMsgVO.getMsgType().equals("6")) {
    			
    			if(mjonMsgVO.getFileName3() != null) {
    				mjonMsgVO.setEachPrice(picture3Price.toString());
    				tmpEachPrice = picture3Price;
    			}else if(mjonMsgVO.getFileName2() != null) {
    				mjonMsgVO.setEachPrice(picture2Price.toString());
    				tmpEachPrice = picture2Price;
    			}else if(mjonMsgVO.getFileName1() != null) {
    				mjonMsgVO.setEachPrice(picturePrice.toString());
    				tmpEachPrice = picturePrice;
    			}else {
    				mjonMsgVO.setEachPrice(longPrice.toString());
    				tmpEachPrice = longPrice;
    			}
    			
    		}
    		
    		//수신자 총 수 * 단가 를 통해 총 결제 금액 계산
    		int tmpTotCallCnt = mjonMsgVO.getCallToList().length;
    		float tmpTotPrice = tmpTotCallCnt * tmpEachPrice;
    		
    		
    		//화면에서 넘어온 파라미터 개별 단가와 컨트롤러에서 계산한 단가를 비교하여 맞지 않으면 컨트롤러 계산 단가 입력
    		if(tmpOrgEachPrice != tmpEachPrice) {
    			mjonMsgVO.setEachPrice(Float.toString(tmpEachPrice));
    			
    			System.out.println("화면 : tmpOrgEachPrice ::: "+tmpOrgEachPrice);
    			System.out.println("컨트롤러 : tmpEachPrice ::: "+tmpEachPrice);
    		}else {
    			System.out.println("tmpOrgEachPrice ::: "+tmpOrgEachPrice);
    		}
    		
    		if(tmpOrgTotPrice != tmpTotPrice ) {
    			mjonMsgVO.setTotPrice(Float.toString(tmpTotPrice));
    			
    			System.out.println("화면 : tmpOrgTotPrice ::: "+tmpOrgTotPrice);
    			System.out.println("컨트롤러 : tmpTotPrice ::: "+tmpTotPrice);    			
    		}else {
    			System.out.println("tmpOrgTotPrice ::: "+tmpOrgTotPrice);
    		}
    		
    		/*
    		 * 개별단가 및  총결제 캐시 금액 체크 로직 종료
    		 * 
    		 * */
        	
        	//치환문자 체크 처리
        	String txtReplYn = mjonMsgVO.getTxtReplYn();
        	if(txtReplYn.equals("Y")) {
        	
        		int totListCnt = mjonMsgVO.getCallToList().length;
        		String[] nameList = mjonMsgVO.getNameList();	//치환 이름 리스트
        		String[] phone = mjonMsgVO.getCallToList();		//수신자 휴대폰 번호
        		String[] rep1 = mjonMsgVO.getRep1List();		//치환 문자1 리스트
        		String[] rep2 = mjonMsgVO.getRep2List();		//치환 문자2 리스트
        		String[] rep3 = mjonMsgVO.getRep3List();		//치환 문자3 리스트
        		String[] rep4 = mjonMsgVO.getRep4List();		//치환 문자4 리스트
        		
        		//이름, 휴대폰, 치환문자 데이터가 없으면 취소 처리
        		if((nameList.length == 0 || nameList == null) 
        				&& (rep1.length == 0 || rep1 == null)
        				&& (rep2.length == 0 || rep2 == null)
        				&& (rep3.length == 0 || rep3 == null)
        				&& (rep4.length == 0 || rep4 == null)) {
        			
        			modelAndView.addObject("message", "특정문구 일괄변환 치환문자 데이터가 없습니다.");
        			modelAndView.addObject("result", "fail");
        			return modelAndView;
        			
        		}
        		
				// 치환문자 전체 필수체크 Start
				boolean isRepCountOk = true;
				if (mjonMsgVO.getSmsTxt().indexOf("[*이름*]") > -1) {
					if(nameList.length != phone.length) {
						isRepCountOk = false;
					}
    			}
    			if (mjonMsgVO.getSmsTxt().indexOf("[*1*]") > -1) {
					if(rep1.length != phone.length) {
						isRepCountOk = false;
					}
    			}
    			if (mjonMsgVO.getSmsTxt().indexOf("[*2*]") > -1) {
					if(rep2.length != phone.length) {
						isRepCountOk = false;
					}
    			}
    			if (mjonMsgVO.getSmsTxt().indexOf("[*3*]") > -1) {
					if(rep3.length != phone.length) {
						isRepCountOk = false;
					}
    			}
    			if (mjonMsgVO.getSmsTxt().indexOf("[*4*]") > -1) {
					if(rep4.length != phone.length) {
						isRepCountOk = false;
					}
    			}
				
				if (isRepCountOk == false) {
					modelAndView.addObject("message", "특정문구 일괄변환 치환문자 데이터가 없습니다");
					modelAndView.addObject("result", "fail");
					return modelAndView;
				}
				// End
				
        		//---------------------------------------------------------------------------------------------------------------        		
        		
        		
        		int msgLeng = 90;	//단문 문자열 길이
        		
        		if(msgType.equals("6")) {
        			
        			msgLeng = 2000;	//장문 문자열 길이
        			
        		}
        		
        		for(int i=0; i < totListCnt; i ++) {
        			
        			String smsTxt = mjonMsgVO.getSmsTxt();		//발송 문자 내용
        			
        			/**
        			 * 본문 내용 - 치환 처리 후 문자 길이 초과 여부만 체크
        			 * 치환 리스트 중 데이터가 없는 경우 데이터 밀림방지를 위하여 공백 하나를 추가해줌
        			 * 공백처리를 안하는 경우 데이터가 밀려서 치환되는 오류가 있어서 처리해줌
        			 * 
        			 * */
        			
        			
        			int repCnt = 0;
        			smsTxt = smsTxt.replaceAll(String.valueOf((char)13), "");
        			if (smsTxt.indexOf("[*이름*]") > -1) {
        				if(nameList.length > i && StringUtil.isNotEmpty(nameList[i])) {
        					smsTxt = smsTxt.replaceAll("\\[\\*이름\\*\\]", StringUtil.getString(nameList[i].replaceAll("§", ",")));
        				}else {
        					smsTxt = smsTxt.replaceAll("\\[\\*이름\\*\\]", "");
        					nameList[i] = " ";
        				}
        				repCnt++;
        			}
        			if (smsTxt.indexOf("[*1*]") > -1) {
        				if(rep1.length > i && StringUtil.isNotEmpty(rep1[i])) {
        					smsTxt = smsTxt.replaceAll("\\[\\*1\\*\\]", StringUtil.getString(rep1[i].replaceAll("§", ",")));
        				}else {
        					smsTxt = smsTxt.replaceAll("\\[\\*1\\*\\]", "");
        					rep1[i] = " ";
        				}
        				repCnt++;
        			}
        			if (smsTxt.indexOf("[*2*]") > -1) {
        				if(rep2.length > i && StringUtil.isNotEmpty(rep2[i])) {
        					smsTxt = smsTxt.replaceAll("\\[\\*2\\*\\]", StringUtil.getString(rep2[i].replaceAll("§", ",")));
        				}else {
        					smsTxt = smsTxt.replaceAll("\\[\\*2\\*\\]", "");
        					rep2[i] = " ";
        				}
        				repCnt++;
        			}
        			if (smsTxt.indexOf("[*3*]") > -1) {
        				if(rep3.length > i && StringUtil.isNotEmpty(rep3[i])) {
        					smsTxt = smsTxt.replaceAll("\\[\\*3\\*\\]", StringUtil.getString(rep3[i].replaceAll("§", ",")));
        				}else {
        					smsTxt = smsTxt.replaceAll("\\[\\*3\\*\\]", "");
        					rep3[i] = " ";
        				}
        				repCnt++;
        			}
        			if (smsTxt.indexOf("[*4*]") > -1) {
        				if(rep4.length > i && StringUtil.isNotEmpty(rep4[i])) {
        					smsTxt = smsTxt.replaceAll("\\[\\*4\\*\\]", StringUtil.getString(rep4[i].replaceAll("§", ",")));
        				}else {
        					smsTxt = smsTxt.replaceAll("\\[\\*4\\*\\]", "");
        					rep4[i] = " ";
        				}
        				repCnt++;
        			}
        			
        			//문자열 바이트 수 구하기(한글 2Byte로 계산)
        			// 한글 3Byte로 하기 위해서는 StandardCharsets.UTF_8 로 변경하면 된다. 
        			int bytes = smsTxt.getBytes(charset).length;
        			if(repCnt > 0) {
        				if(bytes > msgLeng) {	//전송 문자 길이를 초과한 경우 전송 취소 - 단문 작성 후 치환했을 때 장문으로 길이가 초과되는 경우 체크
        					modelAndView.addObject("message", "문자 치환 후 전송 문자 길이를 초과하였습니다.");
        					modelAndView.addObject("result", "fail");
        					modelAndView.addObject("resultSts", "0");
        					modelAndView.addObject("resultBlockSts", "0");
        					return modelAndView; 
        				}
        			}
        		}
        		
        		mjonMsgVO.setNameList(nameList);
        		mjonMsgVO.setRep1List(rep1);
        		mjonMsgVO.setRep2List(rep2);
        		mjonMsgVO.setRep3List(rep3);
        		mjonMsgVO.setRep4List(rep4);
        		
        	}
        	
        	//현재 고객의 보유 캐시가 문자 발송이 가능한 금액인지 체크
        	String userMoney = mjonMsgDataService.selectBeforeCashData(mjonMsgVO);
        	String userPoint = mjonMsgDataService.selectBeforePointData(mjonMsgVO);
        	mjonMsgVO.setBefPoint(userPoint); //현재 보유 포인트 정보 저장
        	String totPrice = mjonMsgVO.getTotPrice();
        	String eachPrice = mjonMsgVO.getEachPrice();
        	
        	if(msgType.equals("6")) {//문자 mms, lms 단가 설정하기
        		
        		if(fileCount > 2) {//그림 이미지가 3개
        			
        			eachPrice = mjonMsgVO.getP3Price();
        			
        		}else if(fileCount > 1) {//그림 이미지가 2개
        			
        			eachPrice = mjonMsgVO.getP2Price();
        			
        		}else if(fileCount == 1) {//그림 이미지가 1개
        			eachPrice = mjonMsgVO.getPPrice();
        			
        		}else {//장문 문자인 경우
        			
        			eachPrice = mjonMsgVO.getMPrice();
        		}
        		
        	}
        	
        	BigDecimal befCash = new BigDecimal(userMoney).setScale(2, RoundingMode.HALF_EVEN);
        	BigDecimal totMsgPrice = new BigDecimal(totPrice).setScale(2, RoundingMode.HALF_EVEN);
        	
        	
        	//현재 보유 금액이 발송 문자 총 금액보다 클 경우만 문자 발송
        	//BigDecimal 비교 연산
        	// befCash(현재 보유금액) 값이 totMsgPrice(문자전송 금액) 보다 많으면 문자 전송	
        	if(befCash.compareTo(totMsgPrice) != -1) { // -1 : befCash < totMsgPrice, 0 : befCash = totMsgPrice, 1 : befCash > totMsgPrice,
        		
        		mjonMsgVO.setBefCash(befCash.toString());
        		
        		//문자 전송 그룹아이디 생성
	        	mjonMsgVO.setMsgGroupId(idgenMjonMsgGroupId.getNextStringId());
	        	
	        	String[] tempPhoneList = new String[200];				//임시 수신번호 리스트 저장용 배열
	        	String[] tempNameList = new String[200];				//임시 이름 리스트 저장용 배열
	    		String[] tempRep1List = new String[200];				//임시 치환문자1 리스트 저장용 배열
	    		String[] tempRep2List = new String[200];				//임시 치환문자1 리스트 저장용 배열
	    		String[] tempRep3List = new String[200];				//임시 치환문자1 리스트 저장용 배열
	    		String[] tempRep4List = new String[200];				//임시 치환문자1 리스트 저장용 배열
	    		
	    		String[] phoneList = mjonMsgVO.getCallToList();
	    		String[] nameList = mjonMsgVO.getNameList();
	    		String[] rep1List = mjonMsgVO.getRep1List();
	    		String[] rep2List = mjonMsgVO.getRep2List();
	    		String[] rep3List = mjonMsgVO.getRep3List();
	    		String[] rep4List = mjonMsgVO.getRep4List();
	    		
	    		int callToListCnt = mjonMsgVO.getCallToList().length;
	    		mjonMsgVO.setTotalCallCnt(callToListCnt);
	    		
	    		/**
	    		 * 예약 문자인 경우 시간 및 분할 시간 셋팅 해주기
	    		 * 
	    		 * 
	    		 * */
	
	    		//분할문자 시간에 간격시간 더해주기
	        	String dividDay = null;
	        	Calendar cal = Calendar.getInstance();
	        	
	        	//예약시간 변환
	        	SimpleDateFormat transFormat = new SimpleDateFormat("yyyy/MM/dd HH:mm:ss");
	        	
	    		int turmMin = 0;
	    		int totalCallCnt = 0;
	    		int divideCnt = 0;
	    		int count = 1;		//분할 카운트
	    		
	    		
	    		if(!mjonMsgVO.getReserveYn().equals("N")) {//예약문자인 경우 시간 셋팅
	    			
	    	    	Date toDate = transFormat.parse(mjonMsgVO.getReqDate());
	    	    	cal.setTime(toDate); 										//예약 시간 캘린터 변수에 입력
	    	    	
	    	    	//String 타입 시간 Int로 변환
	    	    	turmMin = Integer.parseInt(mjonMsgVO.getDivideTime()); //분할발송 시간 간격
	    	    	dividDay = transFormat.format(cal.getTime());
	    	    	
	    	    	totalCallCnt = mjonMsgVO.getCallToList().length; // 수신자 전체 갯수
	    	    	divideCnt = Integer.parseInt(mjonMsgVO.getDivideCnt()); //분할 발송 갯수
	    			
	    		}
	    		
	    		//분할 예약 시간 저장 리스트 생성
	    		List<String> dividDayList = new ArrayList<String>();
	    		
	    		//서비스 단으로 특정 문자 건수 이상으로 한번에 보내지 않기 위해서 처리함
	    		//200건이 넘으면 200개씩 서비스로 넘기고
	    		if(callToListCnt > 200) {
	    			
	    			int sendCnt = 0;
	    			for(int i=0; i< callToListCnt; i++) {
	    				
	    				//분할 발송을 체크 한 경우
						if(mjonMsgVO.getDivideChk() != null) {
							
							if(count > divideCnt) {
		            			
		            			count = 1;
		            			
		            			//분할 시간 간격을 증가시켜 준다.
		            			cal.add(Calendar.MINUTE, turmMin);
		            			dividDay = transFormat.format(cal.getTime());
		                    	
		            			dividDayList.add(dividDay);
		            			//tempVO.setReqDate(dividDay); //분할 문자 예약 시간 입력해주기
		                		count++;
		                		
		            		}else {
		            			
		            			dividDayList.add(dividDay);
		            			//tempVO.setReqDate(dividDay); //분할 문자 예약 시간 입력해주기
		            			count++;
		            			
		            		}
							
						}
	    				
	    				if((i < callToListCnt -1) && sendCnt == 199) {
	    					
	    					//sendCnt 200번째 값을 추가해준다.
	    					tempPhoneList[sendCnt] = phoneList[i];
	    					
	    					if(nameList.length > 0) {
	    						tempNameList[sendCnt] = nameList[i];
	    					}
	    					
	    					if(rep1List.length > 0) {
	    						tempRep1List[sendCnt] = rep1List[i];
	    					}
	    					
	    					if(rep2List.length > 0) {
	    						tempRep2List[sendCnt] = rep2List[i];
	    					}
	    					
	    					if(rep3List.length > 0) {
	    						tempRep3List[sendCnt] = rep3List[i];
	    					}
	    					
	    					if(rep4List.length > 0) {
	    						tempRep4List[sendCnt] = rep4List[i];
	    					}
	    					
	    					List<String> arrPhoneList = new ArrayList<String>();
	    					List<String> arrNameList = new ArrayList<String>();
	    					List<String> arrRep1List = new ArrayList<String>();
	    					List<String> arrRep2List = new ArrayList<String>();
	    					List<String> arrRep3List = new ArrayList<String>();
	    					List<String> arrRep4List = new ArrayList<String>();
	    					
	    					for(String temp : tempPhoneList) {
	    						
	    						if(temp != null) {
	    							
	    							arrPhoneList.add(temp);
	    							
	    						}
	    						
	    					}
	    					
	    					if(tempNameList.length > 0) {
	    						for(String tmpName : tempNameList) {
		    						
		    						if(tmpName != null) {
		    							
		    							arrNameList.add(tmpName);
		    							
		    						}
		    						
		    					}
	    						
	    					}
	    					
	    					if(tempRep1List.length > 0) {
	    						for(String tmpRep1 : tempRep1List) {
	    							
	    							if(tmpRep1 != null) {
	    								
	    								arrRep1List.add(tmpRep1);
	    								
	    							}
	    							
	    						}
	    						
	    					}
	    					
	    					if(tempRep2List.length > 0) {
	    						for(String tmpRep2 : tempRep2List) {
	    							
	    							if(tmpRep2 != null) {
	    								
	    								arrRep2List.add(tmpRep2);
	    								
	    							}
	    							
	    						}
	    						
	    					}
	    					
	    					if(tempRep3List.length > 0) {
	    						for(String tmpRep3 : tempRep3List) {
	    							
	    							if(tmpRep3 != null) {
	    								
	    								arrRep3List.add(tmpRep3);
	    								
	    							}
	    							
	    						}
	    						
	    					}
	    					
	    					if(tempRep4List.length > 0) {
	    						for(String tmpRep4 : tempRep4List) {
	    							
	    							if(tmpRep4 != null) {
	    								
	    								arrRep4List.add(tmpRep4);
	    								
	    							}
	    							
	    						}
	    						
	    					}
	    					
	    					//리스트에 추가된 내용 만큼 임시 수신목록 배열에 넣어준다.
	    					String[] sendPhoneList = new String[arrPhoneList.size()];
	    					String[] sendNameList = new String[arrNameList.size()];
	    					String[] sendRep1List = new String[arrRep1List.size()];
	    					String[] sendRep2List = new String[arrRep2List.size()];
	    					String[] sendRep3List = new String[arrRep3List.size()];
	    					String[] sendRep4List = new String[arrRep4List.size()];
	    					
	    					for(int j=0; j< arrPhoneList.size(); j++) {
	    						
	    						sendPhoneList[j] = arrPhoneList.get(j);
	    						
	    					}
	    					
	    					for(int k=0; k< arrNameList.size(); k++) {
	    						
	    						sendNameList[k] = arrNameList.get(k);
	    						
	    					}
	    					
	    					for(int k=0; k< arrRep1List.size(); k++) {
	    						
	    						sendRep1List[k] = arrRep1List.get(k);
	    						
	    					}
	    					
	    					for(int k=0; k< arrRep2List.size(); k++) {
	    						
	    						sendRep2List[k] = arrRep2List.get(k);
	    						
	    					}
	    					
	    					for(int k=0; k< arrRep3List.size(); k++) {
	    						
	    						sendRep3List[k] = arrRep3List.get(k);
	    						
	    					}
	    					
	    					for(int k=0; k< arrRep4List.size(); k++) {
	    						
	    						sendRep4List[k] = arrRep4List.get(k);
	    						
	    					}
	    					
	    					mjonMsgVO.setCallToList(sendPhoneList);
	    					
	    					if(sendNameList.length > 0) {
	    						mjonMsgVO.setNameList(sendNameList);
	    					}
	    					
	    					if(sendRep1List.length > 0) {
	    						mjonMsgVO.setRep1List(sendRep1List);
	    					}

	    					if(sendRep2List.length > 0) {
	    						mjonMsgVO.setRep2List(sendRep2List);
	    					}
	    					
	    					if(sendRep3List.length > 0) {
	    						mjonMsgVO.setRep3List(sendRep3List);
	    					}
	    					
	    					if(sendRep4List.length > 0) {
	    						mjonMsgVO.setRep4List(sendRep4List);
	    					}
	    					sendCnt = 0;
	    					
	    					mjonMsgVO.setDividDay(dividDayList);
	    					MjonMsgReturnVO returnVO = mjonMsgDataService.insertMsgDataInfo(mjonMsgVO);
	    					mjonMsgVO.setAgentCode(returnVO.getAgentCode());
	    					resultSts = resultSts + Integer.parseInt(returnVO.getSendMsgCnt());
	    		    		resultBlockSts = resultBlockSts + Integer.parseInt(returnVO.getSendMsgBlockCnt());
	    		    		
	    		    		//발송 처리후 배열 초기화
	    		    		Arrays.fill(tempPhoneList, null);
	    		    		dividDayList.clear();
	    					
	    		    		
	    		    		System.out.println("=========================================================================");
	    		    		System.out.println("+++++++++++++++++++++++++++++++++++++++++++선거문자 ==> 199 resultSts ::: " + resultSts);
	    		    		System.out.println("+++++++++++++++++++++++++++++++++++++++++++선거문자 ==> 199 resultBlockSts ::: " + resultBlockSts);
	    		    		System.out.println("=========================================================================");
	    		    		
	    				}else if((i == callToListCnt -1) && sendCnt < 200){//수신목록 마지막이면서 200개 미만으로 남은 경우 발송 처리해준다.
	    					
	    					//마지막 리스트의 수신번호를 추가해 준다.
	    					tempPhoneList[sendCnt] = phoneList[i];
	    					if(nameList.length > 0) {
	    						tempNameList[sendCnt] = nameList[i];
	    					}

	    					if(rep1List.length > 0) {
	    						tempRep1List[sendCnt] = rep1List[i];
	    					}
	    					
	    					if(rep2List.length > 0) {
	    						tempRep2List[sendCnt] = rep2List[i];
	    					}
	    					
	    					if(rep3List.length > 0) {
	    						tempRep3List[sendCnt] = rep3List[i];
	    					}
	    					
	    					if(rep4List.length > 0) {
	    						tempRep4List[sendCnt] = rep4List[i];
	    					}
	    					
	    					List<String> arrPhoneList2 = new ArrayList<String>();
	    					List<String> arrNameList2 = new ArrayList<String>();
	    					List<String> arrRep1List2 = new ArrayList<String>();
	    					List<String> arrRep2List2 = new ArrayList<String>();
	    					List<String> arrRep3List2 = new ArrayList<String>();
	    					List<String> arrRep4List2 = new ArrayList<String>();
	    					
	    					for(String temp : tempPhoneList) {
	    						
	    						if(temp != null) {
	    							
	    							arrPhoneList2.add(temp);
	    							
	    						}
	    						
	    					}
	    					
	    					if(tempNameList.length > 0) {
	    						for(String tmpName : tempNameList) {
	    							
	    							if(tmpName != null) {
	    								
	    								arrNameList2.add(tmpName);
	    								
	    							}
	    							
	    						}
	    						
	    					}
	    					
	    					if(tempRep1List.length > 0) {
	    						for(String tmpRep1 : tempRep1List) {
	    							
	    							if(tmpRep1 != null) {
	    								
	    								arrRep1List2.add(tmpRep1);
	    								
	    							}
	    							
	    						}
	    						
	    					}
	    					
	    					
	    					if(tempRep2List.length > 0) {
	    						for(String tmpRep2 : tempRep2List) {
	    							
	    							if(tmpRep2 != null) {
	    								
	    								arrRep2List2.add(tmpRep2);
	    								
	    							}
	    							
	    						}
	    						
	    					}
	    					
	    					if(tempRep3List.length > 0) {
	    						for(String tmpRep3 : tempRep3List) {
	    							
	    							if(tmpRep3 != null) {
	    								
	    								arrRep3List2.add(tmpRep3);
	    								
	    							}
	    							
	    						}
	    						
	    					}
	    					
	    					if(tempRep4List.length > 0) {
	    						for(String tmpRep4 : tempRep4List) {
	    							
	    							if(tmpRep4 != null) {
	    								
	    								arrRep4List2.add(tmpRep4);
	    								
	    							}
	    							
	    						}
	    						
	    					}
	    					
	    					String[] sendPhoneList2 = new String[arrPhoneList2.size()];
	    					String[] sendNameList2 = new String[arrNameList2.size()];
	    					String[] sendRep1List2 = new String[arrRep1List2.size()];
	    					String[] sendRep2List2 = new String[arrRep2List2.size()];
	    					String[] sendRep3List2 = new String[arrRep3List2.size()];
	    					String[] sendRep4List2 = new String[arrRep4List2.size()];
	    					
	    					for(int j=0; j< arrPhoneList2.size(); j++) {
	    						
	    						sendPhoneList2[j] = arrPhoneList2.get(j);
	    						
	    					}
	    					
	    					for(int j=0; j< arrNameList2.size(); j++) {
	    						
	    						sendNameList2[j] = arrNameList2.get(j);
	    						
	    					}
	    					
	    					for(int k=0; k< arrRep1List2.size(); k++) {
	    						
	    						sendRep1List2[k] = arrRep1List2.get(k);
	    						
	    					}
	    					
	    					for(int k=0; k< arrRep2List2.size(); k++) {
	    						
	    						sendRep2List2[k] = arrRep2List2.get(k);
	    						
	    					}
	    					
	    					for(int k=0; k< arrRep3List2.size(); k++) {
	    						
	    						sendRep3List2[k] = arrRep3List2.get(k);
	    						
	    					}
	    					
	    					for(int k=0; k< arrRep4List2.size(); k++) {
	    						
	    						sendRep4List2[k] = arrRep4List2.get(k);
	    						
	    					}
	    					
	    					mjonMsgVO.setCallToList(sendPhoneList2);
	    					
	    					if(sendNameList2.length > 0) {
	    						mjonMsgVO.setNameList(sendNameList2);
	    					}

	    					if(sendRep1List2.length > 0) {
	    						mjonMsgVO.setRep1List(sendRep1List2);
	    					}
	    					
	    					if(sendRep2List2.length > 0) {
	    						mjonMsgVO.setRep2List(sendRep2List2);
	    					}
	    					
	    					if(sendRep3List2.length > 0) {
	    						mjonMsgVO.setRep3List(sendRep3List2);
	    					}
	    					
	    					if(sendRep4List2.length > 0) {
	    						mjonMsgVO.setRep4List(sendRep4List2);
	    					}
	    					sendCnt = 0;
	    					
	    					mjonMsgVO.setDividDay(dividDayList);
	    					MjonMsgReturnVO returnVO = mjonMsgDataService.insertMsgDataInfo(mjonMsgVO);
	    					mjonMsgVO.setAgentCode(returnVO.getAgentCode());
	    					resultSts = resultSts + Integer.parseInt(returnVO.getSendMsgCnt());
	    		    		resultBlockSts = resultBlockSts + Integer.parseInt(returnVO.getSendMsgBlockCnt());
	    		    		
	    		    		System.out.println("=========================================================================");
	    		    		System.out.println("+++++++++++++++++++++++++++++++++++++++++++선거문자 ==> 200 resultSts ::: " + resultSts);
	    		    		System.out.println("+++++++++++++++++++++++++++++++++++++++++++선거문자 ==> 200 resultBlockSts ::: " + resultBlockSts);
	    		    		System.out.println("=========================================================================");
	    					
	    				}else {
	    					
	    					tempPhoneList[sendCnt] = phoneList[i];
	    					
	    					if(nameList.length > 0) {//이름 치환문자가 있는 경우
	    						tempNameList[sendCnt] = nameList[i];
	    					}
	    					
	    					if(rep1List.length > 0) {//치환1 문자가 있는 경우
	    						tempRep1List[sendCnt] = rep1List[i];
	    					}
	    					
	    					if(rep2List.length > 0) {//치환2 문자가 있는 경우
	    						tempRep2List[sendCnt] = rep2List[i];
	    					}
	    					
	    					if(rep3List.length > 0) {//치환3 문자가 있는 경우
	    						tempRep3List[sendCnt] = rep3List[i];
	    					}
	    					
	    					if(rep4List.length > 0) {//치환4 문자가 있는 경우
	    						tempRep4List[sendCnt] = rep4List[i];
	    					}
	    					
	    					sendCnt++;
	    					
	    				}
	    				
	    			}
	    			
	    		}else {//200건 미만일 경우 한번에 발송 처리
	    			
	    			//분할 발송을 체크 한 경우
					if(mjonMsgVO.getDivideChk() != null) {
						for(int i=0; i< callToListCnt; i++) {
							if(count > divideCnt) {
		            			
		            			count = 1;
		            			
		            			//분할 시간 간격을 증가시켜 준다.
		            			cal.add(Calendar.MINUTE, turmMin);
		            			dividDay = transFormat.format(cal.getTime());
		                    	
		            			dividDayList.add(dividDay);
		            			//tempVO.setReqDate(dividDay); //분할 문자 예약 시간 입력해주기
		                		count++;
		                		
		            		}else {
		            			
		            			dividDayList.add(dividDay);
		            			//tempVO.setReqDate(dividDay); //분할 문자 예약 시간 입력해주기
		            			count++;
		            			
		            		}
						
						}
	    				
	    			}
	    			
					mjonMsgVO.setDividDay(dividDayList);
	    			MjonMsgReturnVO returnVO = mjonMsgDataService.insertMsgDataInfo(mjonMsgVO);
	    			mjonMsgVO.setAgentCode(returnVO.getAgentCode());
		    		resultSts = Integer.parseInt(returnVO.getSendMsgCnt());
		    		resultBlockSts = Integer.parseInt(returnVO.getSendMsgBlockCnt());
		    		
		    		System.out.println("=========================================================================");
		    		System.out.println("+++++++++++++++++++++++++++++++++++++++++++200건 미만 건수 선거문자 ==> resultSts ::: " + resultSts);
		    		System.out.println("+++++++++++++++++++++++++++++++++++++++++++200건 미만 건수 선거문자 ==> resultBlockSts ::: " + resultBlockSts);
		    		System.out.println("=========================================================================");
	    			
	    		}
	    		
	    		System.out.println("=========================================================================");
	    		System.out.println("+++++++++++++++++++++++++++++++++++++++++++최종 건수 선거문자 ==> resultSts ::: " + resultSts);
	    		System.out.println("+++++++++++++++++++++++++++++++++++++++++++최종 건수 선거문자 ==> resultBlockSts ::: " + resultBlockSts);
	    		System.out.println("=========================================================================");
	    		
	    		try {
	    			
		    		//스팸문구 포함된 문자 발송의 경우 스팸 문구 내용도 별도 저장함.
		    		String spamStatus = mjonMsgVO.getSpamStatus();
		    		
		    		if(spamStatus == null) {
		    			
		    			spamStatus = "N";
		    			mjonMsgVO.setSpamStatus("N");
		    			
		    		}
		    		
		    		if(spamStatus.equals("Y")) {
		    			
		    			int resultCnt = mjonSpamMsgService.insertSpamKeyWordMsgData(mjonMsgVO);
		    			
		    			System.out.println("+++++++++++++스팸문구 발송 내용 등록 +++++++++++++++++++++ "+resultCnt);
		    			
		    		}
					
				} catch (Exception e) {
					System.out.println("=========================================================================");
					System.out.println("+++++++++++++++++++++++++++++ 선거문자 ==> MJ_MSG_GROUP && CASH INSER ERROR !!! : " + e.getMessage());
					System.out.println("=========================================================================");
				}
	    		
	        	
        	}else {
        		
        		modelAndView.addObject("message", "문자 발송에 필요한 보유 잔액이 부족 합니다.");
    			modelAndView.addObject("result", "fail");
    			modelAndView.addObject("resultSts", "0");
    			modelAndView.addObject("resultBlockSts", "0");
    			
    			return modelAndView;
        		
        	}
        	
        	//문자 발송 후 남은 보유 캐시 정보 불러오기
        	String afterCash = mjonMsgDataService.selectBeforeCashData(mjonMsgVO);
        	modelAndView.addObject("afterCash", afterCash);
        	
    	}catch(Exception e) {

			System.out.println("=========================================================================");
			System.out.println("+++++++++++++++++++++++++++++ 선거문자 ==> 기타 시스템 오류 !!! : " + e.getMessage());
			System.out.println("=========================================================================");
			
    		logger.error(e.getMessage(), e);
    		modelAndView.addObject("result", "fail");
    		modelAndView.addObject("message", "기타 시스템 오류 : " + e.getMessage());
    	}
		
		//if(!resultSts.equals("0")) {
			
		modelAndView.addObject("message", "문자 전송이 완료되었습니다.");
		modelAndView.addObject("result", "success");
		modelAndView.addObject("resultSts", resultSts);
		modelAndView.addObject("resultBlockSts", resultBlockSts);
			

		/*
		 * 
		 * 문자전송이 완료되면 전송한 연락처의 발송 상태값을 변경처리 해준다.
		 * 사용자 화면의 받는사람 리스트에서 다음 페이지의 20건을 불러오고, 발송완료 및 전송대기건의 카운트 계산을 위함이다.
		 * 
		 * */
		if(resultSts > 0) {
			
			System.out.println(userId);
			
			MjonCandidateTWVO mjonCandidateTWVO = new MjonCandidateTWVO();
			
			mjonCandidateTWVO.setMberId(userId);
			mjonCandidateTWVO.setCallToArr(mjonMsgVO.getCallToList());
			
			mjonCandidateService.updateMsgTWCallToListSendFlag(mjonCandidateTWVO);
			
		}
		
		/**
		 * 사용자가 보낸 문자를 문자온 법인폰으로도 하나 전송하는 기능 시작
		 * 
		 * */
		
		try {
			
			if(resultSts > 0) {//전송 결과가 한건 이상인 경우
				
				String adminSmsNoticeYn = "Y";
				String smishingYn = "N";
				String spamStatus = mjonMsgVO.getSpamStatus(); //스미싱 의심으로 체크된 문자 정보
				
				UserManageVO userManageVO = new UserManageVO();
				userManageVO.setMberId(userId);
				if(!userId.equals("")) {
					userManageVO = userManageService.selectAdminSmsNoticeYn(userManageVO);
					adminSmsNoticeYn = userManageVO.getAdminSmsNoticeYn(); 
					smishingYn = userManageVO.getSmishingYn();
				}
				
				//법인폰 알림 온 이거나 스미싱의심 문자인 경우 법인폰으로 발송
				if(adminSmsNoticeYn.equals("Y") || spamStatus.equals("Y") || smishingYn.equals("Y")) {

					if(spamStatus.equals("Y")) {
						
						mjonMsgVO.setDelayYn("Y");
						
					}else if(smishingYn.equals("Y")) {
						
						mjonMsgVO.setSmishingYn("Y");
					}
					
					// 법인폰 알람여부 체크
					JoinSettingVO joinSettingVO = new JoinSettingVO();
					joinSettingVO = egovSiteManagerService.selectAdminNotiDetail();

					String holiSmishingNoti = joinSettingVO.getHoliSmishingNoti();
					
					// SMS 체크
					if (joinSettingVO != null && joinSettingVO.getSmsNoti().equals("Y")) {
						MjonMsgCampainDataController mjonCampDataController = new MjonMsgCampainDataController();
						mjonCampDataController.getAdminPhoneSendMsgData(mjonMsgVO);						
					}

					//야간 스미싱의심 알림이 활성화 되어있는 경우만 슬랙 알림 전송처리
					if(holiSmishingNoti.equals("Y")) {
						// SLACK 체크
						if (joinSettingVO != null && joinSettingVO.getSlackNoti().equals("Y")) {
							
							MsgAlarmSetVO msgAlarmSetVO = new MsgAlarmSetVO();
							
							msgAlarmSetVO.setUseYn("Y");
							msgAlarmSetVO.setFirstIndex(0);
							
							List<MsgAlarmSetVO> resultAlarmList = msgHolidayService.selectAlarmSettingList(msgAlarmSetVO);
							
							Calendar calendar = Calendar.getInstance(); 
							int year = calendar.get(Calendar.YEAR);
							
							MsgHolidayVO msgHolidayVO = new MsgHolidayVO();
							msgHolidayVO.setFirstIndex(0);
							msgHolidayVO.setRecordCountPerPage(100);
							msgHolidayVO.setSearchHoliYear(Integer.toString(year));
							
							List<MsgHolidayVO> resultHolidayList = msgHolidayService.selectMsgHolidayList(msgHolidayVO);
							
							MjonHolidayApi mjonHolidayApi = new MjonHolidayApi();
							
							boolean smishingAlarmPassSts = mjonHolidayApi.getHolidaySmishingPassStatus(resultAlarmList, resultHolidayList);
							
							if(!smishingAlarmPassSts) {//평일,주말, 공휴일 알림설정 시간에 포함되지 않는 경우 슬랙 알림 발송
								/*
								MjonCommon comm = new MjonCommon();
								comm.getAdminMsgSandSlack(mjonMsgVO);
								*/
								mjonCommon.getAdminMsgSandSlack(mjonMsgVO);
							}
							
						}
					}
					
				}
				
			}

    	} catch (Exception e) {
			throw new Exception("++++++++++++++++++++++ 선거문자 메뉴 getAdminPhoneSendMsgData Error !!! " + e);
		}

		return modelAndView;
	}
	
	
	/**
	 * 선거문자 20건씩 문자 발송 - 엑셀파일 불러오기
	 * @param body
	 * @param uploadFile
	 * @param search
	 * @param result
	 * @param model
	 * @param request
	 * @return
	 * @throws Exception
	 */
	@RequestMapping(value = "/web/mjon/msgcampain/insertExelFileTWCallToAjax.do")
	@ResponseBody
	public Object insertExelFileTWCallToAjax(final MultipartHttpServletRequest multiRequest) throws Exception {
		
		JsonResult jr = new JsonResult();
		jr.setSuccess(false);
		jr.setMessage("엑셀 파일만 업로드할 수 있습니다.");
		
		//로그인 권한정보 불러오기
    	LoginVO loginVO = EgovUserDetailsHelper.isAuthenticated()? (LoginVO)EgovUserDetailsHelper.getAuthenticatedUser():null;
    	String userId = loginVO == null ? "" : EgovStringUtil.isNullToString(loginVO.getId());
    	String author = loginVO == null ? "" : EgovStringUtil.isNullToString(loginVO.getAuthority());
    	
    	if(userId.equals("") || author.equals("")) {
    		
    		jr.setMessage("엑셀파일 업로드는 로그인이 필요합니다.");
    		return jr;
    		
    	}
		
		try {
			
			//final Map<String, MultipartFile> files = multiRequest.getFileMap();
			List<MultipartFile> files = (List<MultipartFile>) multiRequest.getFiles("file0");
			
			// 파일명에 .이 있을경우 오류 => Ex) 테스트6.20.xlsx 
			int fileNameSplitCnt = 0;
			List<HashMap<String, String>> json = new ArrayList<HashMap<String, String>>();
			
			//전체 엑셀 데이터 갯수 체크 변수
			int totRowDataCnt = 0;
			
			//수신자 목록을 디비화 하기 위한 변수 셋팅
			List<MjonCandidateTWVO> mjonCandidateTwVO = new ArrayList<MjonCandidateTWVO>();
			List<String> callToList = new ArrayList<String>();
			
			if(!files.isEmpty()) {
				fileNameSplitCnt = files.get(0).getOriginalFilename().split("[.]").length;
				
				if (files.get(0).getSize() > 0 
						&& (files.get(0).getContentType().indexOf("spreadsheetml") > -1) 
						|| files.get(0).getContentType().indexOf("ms-excel") > -1 
						|| files.get(0).getOriginalFilename().split("[.]")[fileNameSplitCnt-1].indexOf("xlsx") > -1 
						|| files.get(0).getOriginalFilename().split("[.]")[fileNameSplitCnt-1].indexOf("xls") > -1) {
					
					// 엑셀 파일 용량 3MB이상 시 10만건 이상으로 서버가 다운되는 증상 발생
					long fileSize = multiRequest.getFile("file0").getSize();
					
					if(fileSize > 3374653) {
						jr.setMessage("엑셀 파일은 3MB를 넘을수 없습니다.");
						return jr;
					}
					
					String Ext = files.get(0).getOriginalFilename().split("[.]")[1];
					String errMessage = "";
			        String cellValue  = "";
			        
					String phoneRegExp = "^(050[2345678]{1}|01[016789]{1})-?[0-9]{3,4}-?[0-9]{4}$";
					
		            int errPhoneCnt = 0;
		            String errPhoneLine = "";
		            String errEtcLine = "";
			        
		            //엑셀 확장자에 따른 처리 로직 분리
					if(Ext.equals("xls")) {
						
						HSSFWorkbook workbook = new HSSFWorkbook(files.get(0).getInputStream());
					    HSSFSheet sheet = workbook.getSheetAt(0);
					    
					    if(sheet.getLastRowNum() > 20000) { //
			            	errMessage = "20000건 이상의 업로드는 데이터 부하로 업로드 할수 없습니다.";
			            	jr.setSuccess(false);
			            	jr.setMessage(errMessage);
			            	return jr;
			            }
			            
			            //List<HashMap<String, String>> json = new ArrayList<HashMap<String, String>>();
			            PhoneVO pVO = new PhoneVO();
			            for(int i=2; i< sheet.getLastRowNum() + 2; i++){ //먼저 밸리데이션 체크(1줄은 생략)
			            	HSSFRow row = sheet.getRow(i); //열읽기
			            	if(null == row) { 
			                    continue;
			                }
			            	
			            	//전체 엑셀의 Row 갯수 카운트 해주기
			            	totRowDataCnt++;
			            	
			            	//HashMap<String, String> jm = new HashMap<>();
			            	// 행의 두번째 열(이름부터 받아오기) 
			                HSSFCell cell = null;
			                boolean errSts = true;
			                for(int j = 0 ; j < 1; j++){ //행읽기
			                	cellValue = "";
			                	cell = row.getCell(j); //핸드폰
			                	if(null == cell || "".equals(cell.toString().trim())) { //셀에 값이 없으면 
			                    	//System.out.println("Cell 데이터가 없습니다.");
			                		if(j == 0) {
				                		if (sheet.getLastRowNum() == i) {
				                			continue;
				                		}
				                		
				                		//errPhoneCnt++;
				                		//errSts = false;
				    	            	break;
			                		}
			                    	
			                    }
			                	if(null != cell){
			                		switch(cell.getCellType()){ //숫자타임을 문자로 변환
			                			case  Cell.CELL_TYPE_NUMERIC:
			                			cell.setCellType(Cell.CELL_TYPE_STRING);
			                		}
			                		cellValue =  StringUtil.getString(cell.getStringCellValue().trim()) ;
			                    }
			                	
			                	if(j == 0) {
			                		//전화번호
			                		if(cellValue.matches(phoneRegExp) && errSts) {
			                			//수신자목록을 디비화 하기 위하여 리스트에 저장해줌
			                			callToList.add(cellValue);
			                		}else {
				    	            	errPhoneCnt++;
				    	            	errPhoneLine += (i+1) + "행 ";
				    	            	errSts = false;
				    	            	break;
			                		}
			                	}
			                	
			                }
			                
			            }
			            
			            int resultErrCnt = errPhoneCnt;
			            
						if(resultErrCnt > 0) {
							if (errPhoneCnt <= 10) {
								if (StringUtils.isNotEmpty(errPhoneLine.trim())) {
									errPhoneLine = "[" + errPhoneLine.trim() + "]";
								}
							}
							else {
								errPhoneLine = "";
							}
							jr.setMessage("유효하지 않은 형식의 전화번호  "+ errPhoneCnt +"건" + errPhoneLine.trim() + " 있습니다.\n해당 건을 제외하고 수신목록에 추가됩니다.");
						}else {
							jr.setMessage("");
						}
						
					}else {	//확장자가 xlsx
						
						OPCPackage opcPackage = OPCPackage.open(files.get(0).getInputStream());
						XSSFWorkbook workbook = new XSSFWorkbook(opcPackage);
			            XSSFSheet sheet = workbook.getSheetAt(0); // 첫번째 시트 불러오기
			            opcPackage.close();
			            
			            for(int r=2; r<sheet.getPhysicalNumberOfRows(); r++) {
			            	
			            	XSSFRow tmpRow = sheet.getRow(r);
			            	//System.out.println("=================r:"+r);
			            	XSSFCell cell = null;
			            	if(tmpRow.getCell(0) != null) {
			            		
			            		cell = tmpRow.getCell(0); //핸드폰 번호만 받아오기
				            	if(cell != null && !cell.toString().trim().equals("")) {
				            		//System.out.println("value-" + r + ":" +cell.getStringCellValue()); 
				            		totRowDataCnt++;
				            		//System.out.println("tmpRowCnt:"+totRowDataCnt);
				            	}
			            		
			            	}
			            	
			            }
			            
			            //if(sheet.getLastRowNum() > 20000) { //
			            if(totRowDataCnt > 20000) { //
			            	errMessage = "20000건 이상의 업로드는 데이터 부하로 업로드 할수 없습니다.";
			            	jr.setSuccess(false);
			            	jr.setMessage(errMessage);
			            	return jr;
			            }
			            
			            //List<HashMap<String, String>> json = new ArrayList<HashMap<String, String>>();
			            PhoneVO pVO = new PhoneVO();
			            for(int i=2; i< sheet.getLastRowNum() + 2; i++){ //먼저 밸리데이션 체크(1줄은 생략)
			            	XSSFRow row = sheet.getRow(i); //열읽기
			            	if(null == row) { 
			                    continue;
			                }
			            	
			            	//HashMap<String, String> jm = new HashMap<>();
			            	// 행의 두번째 열(이름부터 받아오기) 
			                XSSFCell cell = null;
			                boolean errSts = true;
			                
			                for(int j = 0 ; j < 1; j++){ //행읽기
			                	cellValue = "";
			                	cell = row.getCell(j); //이름/핸드폰/변환1/변환2/변환3/변환4/변환5
			                	if(null == cell || "".equals(cell.toString().trim())) { //셀에 값이 없으면 
			                    	//System.out.println("Cell 데이터가 없습니다.");
			                		if(j == 0) {
				                		if (sheet.getLastRowNum() == i) {
				                			continue;
				                		}
				                		
				                		//errPhoneCnt++;
				                		//errSts = false;
				    	            	break;
				                		
			                		}
			                    }
			                	if(null != cell){
			                		switch(cell.getCellType()){ //숫자타임을 문자로 변환
			                			case  Cell.CELL_TYPE_NUMERIC:
			                			cell.setCellType(Cell.CELL_TYPE_STRING);
			                		}
			                		cellValue =  StringUtil.getString(cell.getStringCellValue().trim()) ;
			                    }
			                	
			                	if(j == 0) {
			                		//전화번호
			                		if(cellValue.matches(phoneRegExp) && errSts) {
			                			//수신자목록을 디비화 하기 위하여 리스트에 저장해줌
			                			callToList.add(cellValue);
			                			
			                		}else {
				    	            	errPhoneCnt++;
				    	            	errPhoneLine += (i+1) + "행 ";
				    	            	errSts = false;
				    	            	break;
			                		}
			                	}
			                	
			                }
			                
			            }
			            
			            int resultErrCnt = errPhoneCnt;
			            
						if(resultErrCnt > 0) {
							if (errPhoneCnt <= 10) {
								if (StringUtils.isNotEmpty(errPhoneLine.trim())) {
									errPhoneLine = "[" + errPhoneLine.trim() + "]";
								}
							}
							else {
								errPhoneLine = "";
							}
							jr.setMessage("유효하지 않은 형식의 전화번호  "+ errPhoneCnt +"건" + errPhoneLine.trim() + " 있습니다.\n해당 건을 제외하고 수신목록에 추가됩니다.");
						}else {
							jr.setMessage("");
						}
					}	//xlsx 처리 끝
					
				}
				
				//수신자 목록 중복 체크 및 디비화 처리
				List<String> dupCallToList = MJUtil.getDuplicateList(callToList);
				
				String dupCallCnt = Integer.toString(totRowDataCnt - dupCallToList.size());
				
				//입력되어있는 데이터의 마지막 순번(call_seq)을 조회해 온다.
				int maxCallSeq = mjonCandidateService.selectCandidateTWMaxCallSeq(userId);
				maxCallSeq += 1;//마지막 순번에 1을 더해서 다음 순번을 지정해준다.
				HashMap<String, String> callHm = new HashMap<>();
				for(String callTo : dupCallToList) {
					
					MjonCandidateTWVO tmpCandidateTwVO = new MjonCandidateTWVO();
					
					tmpCandidateTwVO.setMberId(userId);
					tmpCandidateTwVO.setCallTo(callTo.replaceAll("-", ""));
					tmpCandidateTwVO.setFrstRegisterId(userId);
					tmpCandidateTwVO.setLastUpdusrId(userId);
					tmpCandidateTwVO.setCallSeq(maxCallSeq);
					
					mjonCandidateTwVO.add(tmpCandidateTwVO);
					
				}
				
				int resultCnt = mjonCandidateService.insertCandidateTWCallToData(mjonCandidateTwVO);
				
				if(resultCnt > 0) {
					
					callHm.put("callSeq", Integer.toString(maxCallSeq));
					json.add(callHm);

					jr.setData(json);
					jr.setSuccess(true);
					
				}else {
					
					jr.setSuccess(false);
					jr.setMessage("엑셀 데이터 처리에 오류가 발생하였습니다. 잠시후 다시 시도해 주세요.");
					
				}
				
			}
			
			return jr;
			
		} catch (Exception e) {
			// TODO: handle exception
			System.out.println("+++++++++++++++++ insertExelFileTWCallToAjax Controller Error !!! "+e);
			jr.setSuccess(false);
			jr.setMessage("엑셀 데이터에 오류가 있습니다. 엑셀 데이터를 확인해 주세요.");
			return jr;
		}
		
	}
	
	
	/**
	 * 선거문자 20건씩 문자 발송 - TXT파일 불러오기
	 * @param body
	 * @param uploadFile
	 * @param search
	 * @param result
	 * @param model
	 * @param request
	 * @return
	 * @throws Exception
	 */
	@RequestMapping(value = "/web/mjon/msgcampain/insertTxtFileTWCallToAjax.do")
	@ResponseBody
	public Object insertTxtFileTWCallToAjax(final MultipartHttpServletRequest multiRequest) throws Exception {
		
		JsonResult jr = new JsonResult();
		jr.setSuccess(false);
		jr.setMessage("TXT 파일만 업로드할 수 있습니다.");
		
		//로그인 권한정보 불러오기
    	LoginVO loginVO = EgovUserDetailsHelper.isAuthenticated()? (LoginVO)EgovUserDetailsHelper.getAuthenticatedUser():null;
    	String userId = loginVO == null ? "" : EgovStringUtil.isNullToString(loginVO.getId());
    	String author = loginVO == null ? "" : EgovStringUtil.isNullToString(loginVO.getAuthority());
    	
    	if(userId.equals("") || author.equals("")) {
    		
    		jr.setMessage("TXT 파일 업로드는 로그인이 필요합니다.");
    		return jr;
    		
    	}
		
		try {
			
			List<MultipartFile> files = (List<MultipartFile>) multiRequest.getFiles("file0");
			List<MjonCandidateTWVO> mjonCandidateTwVO = new ArrayList<MjonCandidateTWVO>();
			List<String> callToList = new ArrayList<String>();
			List<HashMap<String, String>> json = new ArrayList<HashMap<String, String>>();
			//전체 엑셀 데이터 갯수 체크 변수
			int totRowDataCnt = 0;
			
			if(!files.isEmpty()) {
				
				if (files.get(0).getSize() > 0 
						|| files.get(0).getOriginalFilename().split("[.]")[1].indexOf("txt") > -1) {
					
					// txt 파일 용량 3MB이상 시 10만건 이상으로 서버가 다운되는 증상 발생
					long fileSize = multiRequest.getFile("file0").getSize();
					
					if(fileSize > 3374653) {
						jr.setMessage("txt 파일은 3MB를 넘을수 없습니다.");
						return jr;
					}
					
					BufferedReader reader = new BufferedReader(new InputStreamReader(multiRequest.getFile("file0").getInputStream()));
					
					String line = null;
					String[] splitedStr = null;
					String[] tempStr = null;
					int errPhoneCnt = 0;
					
					//String phoneRegExp = "^01(?:0|1|[6-9])[.-]?(\\d{3}|\\d{4})[.-]?(\\d{4})$";
					String phoneRegExp = "^(050[2345678]{1}|01[016789]{1})-?[0-9]{3,4}-?[0-9]{4}$";				
					
					//파일 읽어서 탭으로 구분해주기
					while ((line = reader.readLine()) != null) {

						HashMap<String, String> jm = new HashMap<>();
						splitedStr = null;
						tempStr = null;
						
						//txt 파일의 데이터가 탭 혹은 콤마로 구분되어 있는지 구분처리
						tempStr = line.split("\t");
						if(tempStr.length > 0) {
							
							splitedStr = tempStr;
							
						}else {
							
							splitedStr = line.split(",");
							
						}

						for (int i = 0; i < splitedStr.length; i++) {

							splitedStr[i] = splitedStr[i].trim();
							
							if(i == 0) {
								
								if(splitedStr[i].matches(phoneRegExp)) {
									//휴대폰 번호
									//jm.put("phone", splitedStr[i]);
									callToList.add(splitedStr[i]);
									totRowDataCnt++;
						
								}else {
			    	            	errPhoneCnt++;
		                		}
								
							}
							
						}
						
					} // end while
					//jr.setData(json);
					//jr.setSuccess(true);
					if(errPhoneCnt > 0) {
						
						jr.setMessage("올바르지 않은 휴대폰 번호가 "+ errPhoneCnt +" 건 있습니다.");
						
					}else {
						
						jr.setMessage("");
						
					}
				}
				
				
				//수신자 목록 중복 체크 및 디비화 처리
				List<String> dupCallToList = MJUtil.getDuplicateList(callToList);
				
				String dupCallCnt = Integer.toString(totRowDataCnt - dupCallToList.size());
				
				//입력되어있는 데이터의 마지막 순번(call_seq)을 조회해 온다.
				int maxCallSeq = mjonCandidateService.selectCandidateTWMaxCallSeq(userId);
				maxCallSeq += 1;//마지막 순번에 1을 더해서 다음 순번을 지정해준다.
				HashMap<String, String> callHm = new HashMap<>();
				for(String callTo : dupCallToList) {
					
					MjonCandidateTWVO tmpCandidateTwVO = new MjonCandidateTWVO();
					
					tmpCandidateTwVO.setMberId(userId);
					tmpCandidateTwVO.setCallTo(callTo.replaceAll("-", ""));
					tmpCandidateTwVO.setFrstRegisterId(userId);
					tmpCandidateTwVO.setLastUpdusrId(userId);
					tmpCandidateTwVO.setCallSeq(maxCallSeq);
					
					mjonCandidateTwVO.add(tmpCandidateTwVO);
					
				}
				
				int resultCnt = mjonCandidateService.insertCandidateTWCallToData(mjonCandidateTwVO);
				
				if(resultCnt > 0) {
					
					callHm.put("callSeq", Integer.toString(maxCallSeq));
					json.add(callHm);

					jr.setData(json);
					jr.setSuccess(true);
					
				}else {
					
					jr.setSuccess(false);
					jr.setMessage("엑셀 데이터 처리에 오류가 발생하였습니다. 잠시후 다시 시도해 주세요.");
					
				}
				
				
			}
			
			return jr;
			
		} catch (Exception e) {
			// TODO: handle exception
			System.out.println("+++++++++++++++++ insertTxtFileTWCallToAjax Controller Error !!! "+e);
			jr.setSuccess(false);
			jr.setMessage("TXT 데이터에 오류가 있습니다. TXT 데이터를 확인해 주세요.");
			return jr;
		}
		
	}
	
}
