浏览代码

Merge branch 'develop' into style

card007 4 年之前
父节点
当前提交
e8a7c01f69
共有 44 个文件被更改,包括 5504 次插入153 次删除
  1. 44 0
      src/main/java/com/style24/admin/biz/dao/TsaBusinessDao.java
  2. 22 0
      src/main/java/com/style24/admin/biz/dao/TsaDeliveryDao.java
  3. 18 0
      src/main/java/com/style24/admin/biz/dao/TsaGoodsDao.java
  4. 25 0
      src/main/java/com/style24/admin/biz/dao/TsaStatisticsDao.java
  5. 45 0
      src/main/java/com/style24/admin/biz/service/TsaBusinessService.java
  6. 97 0
      src/main/java/com/style24/admin/biz/service/TsaDeliveryService.java
  7. 253 10
      src/main/java/com/style24/admin/biz/service/TsaGoodsService.java
  8. 143 1
      src/main/java/com/style24/admin/biz/service/TsaStatisticsService.java
  9. 81 0
      src/main/java/com/style24/admin/biz/web/TsaBusinessController.java
  10. 67 0
      src/main/java/com/style24/admin/biz/web/TsaDeliveryController.java
  11. 6 4
      src/main/java/com/style24/admin/biz/web/TsaGoodsController.java
  12. 286 53
      src/main/java/com/style24/admin/biz/web/TsaStatisticsController.java
  13. 1 0
      src/main/java/com/style24/persistence/domain/Delivery.java
  14. 3 1
      src/main/java/com/style24/persistence/domain/Goods.java
  15. 4 1
      src/main/java/com/style24/persistence/domain/GoodsMass.java
  16. 58 4
      src/main/java/com/style24/persistence/domain/Statistics.java
  17. 174 1
      src/main/java/com/style24/persistence/mybatis/shop/TsaBusiness.xml
  18. 372 0
      src/main/java/com/style24/persistence/mybatis/shop/TsaDelivery.xml
  19. 31 8
      src/main/java/com/style24/persistence/mybatis/shop/TsaGoods.xml
  20. 15 3
      src/main/java/com/style24/persistence/mybatis/shop/TsaPlan.xml
  21. 870 43
      src/main/java/com/style24/persistence/mybatis/shop/TsaStatistics.xml
  22. 152 0
      src/main/webapp/WEB-INF/views/business/Bizday2Form.html
  23. 152 0
      src/main/webapp/WEB-INF/views/business/SupplyCompanyPopupForm2.html
  24. 1 1
      src/main/webapp/WEB-INF/views/dashboard.html
  25. 612 0
      src/main/webapp/WEB-INF/views/delivery/DeliveryListScmForm.html
  26. 3 3
      src/main/webapp/WEB-INF/views/order/OrderListForm.html
  27. 1 1
      src/main/webapp/WEB-INF/views/statistics/BestTradingForm.html
  28. 1 1
      src/main/webapp/WEB-INF/views/statistics/BrandTradingForm.html
  29. 1 1
      src/main/webapp/WEB-INF/views/statistics/ChannelTradingForm.html
  30. 1 1
      src/main/webapp/WEB-INF/views/statistics/ClaimTradingForm.html
  31. 5 3
      src/main/webapp/WEB-INF/views/statistics/CouponTradingForm.html
  32. 242 0
      src/main/webapp/WEB-INF/views/statistics/CustomerActiveForm.html
  33. 310 0
      src/main/webapp/WEB-INF/views/statistics/CustomerAgeOrderForm.html
  34. 402 0
      src/main/webapp/WEB-INF/views/statistics/CustomerGradeOrderForm.html
  35. 367 0
      src/main/webapp/WEB-INF/views/statistics/CustomerJoinForm.html
  36. 337 0
      src/main/webapp/WEB-INF/views/statistics/CustomerRankingForm.html
  37. 1 1
      src/main/webapp/WEB-INF/views/statistics/DailyOrderForm.html
  38. 1 1
      src/main/webapp/WEB-INF/views/statistics/ExtmallTradingForm.html
  39. 2 2
      src/main/webapp/WEB-INF/views/statistics/GoodsTradingForm.html
  40. 1 1
      src/main/webapp/WEB-INF/views/statistics/HourlyTradingForm.html
  41. 15 6
      src/main/webapp/WEB-INF/views/statistics/PlanTradingForm.html
  42. 250 0
      src/main/webapp/WEB-INF/views/statistics/SubPaymentForm.html
  43. 4 2
      src/main/webapp/WEB-INF/views/statistics/TmtbTradingForm.html
  44. 28 0
      src/main/webapp/ux/js/admin.popup.js

+ 44 - 0
src/main/java/com/style24/admin/biz/dao/TsaBusinessDao.java

@@ -359,6 +359,40 @@ public interface TsaBusinessDao {
 	 */
 	void updateBizday(Bizday bizday);
 
+	/**
+	 * 총알배송 휴무일 목록
+	 * @param bizday - 영업일 정보
+	 * @return
+	 * @author gagamel
+	 * @since 2021. 9. 29
+	 */
+	Collection<Bizday> getHoliday2List(Bizday bizday);
+
+	/**
+	 * 총알배송 영업일여부 조회
+	 * @param bizday - 영업일
+	 * @return
+	 * @author gagamel
+	 * @since 2021. 9. 29
+	 */
+	String getBizday2Yn(String bizday);
+
+	/**
+	 * 총알배송 영업일 생성
+	 * @param bizday - 영업일 정보
+	 * @author gagamel
+	 * @since 2021. 9. 29
+	 */
+	void createBizday2(Bizday bizday);
+
+	/**
+	 * 총알배송 영업일 수정 처리
+	 * @param bizday - 영업일 정보
+	 * @author gagamel
+	 * @since 2021. 9. 29
+	 */
+	void updateBizday2(Bizday bizday);
+
 	/**
 	 * 총알배송 브랜드 등록
 	 * @param brand - 브랜드 정보
@@ -374,4 +408,14 @@ public interface TsaBusinessDao {
 	 * @since 2021. 07. 29
 	 */
 	void createBrandGroupMainLayout(BrandGroup brandGroup);
+	
+	/**
+	 * 공급업체 목록
+	 * @param supplyComp - 공급업체 정보
+	 * @return
+	 * @author moon
+	 * @since 2021. 09. 29
+	 */
+	Collection<SupplyCompany> getSupplyCompanyList2(SupplyCompany supplyComp);
+	
 }

+ 22 - 0
src/main/java/com/style24/admin/biz/dao/TsaDeliveryDao.java

@@ -359,5 +359,27 @@ public interface TsaDeliveryDao {
 	 * @since 2021. 06. 08
 	 */
 	int updateSoldOut(Delivery delivery);
+
+	/**
+	 * 배송 목록 (입점)건수
+	 *
+	 * @param Delivery
+	 * @return
+	 * @author moon
+	 * @since 2021. 09. 15
+	 */
+	int getDeliveryListScmCount(Delivery delivery);
+
+	
+	/**
+	 * 배송 목록(입점)
+	 *
+	 * @param delivery - 배송정보
+	 * @return Collection<Delivery>
+	 * @author moon
+	 * @since 2021. 09. 15
+	 */
+	Collection<Delivery> getDeliveryScmList(Delivery delivery);
+
 	
 }

+ 18 - 0
src/main/java/com/style24/admin/biz/dao/TsaGoodsDao.java

@@ -815,6 +815,24 @@ public interface TsaGoodsDao {
 	 */
 	int getGoodsOptionCount(Option option);
 
+	/**
+	 * 상품옵션 중복건수여부 확인 // 20210929 eskim (안전인증)
+	 * @param option
+	 * @return
+	 * @author eskim
+	 * @since 2021. 9. 29
+	 */
+	int getGoodsOptionDupCountCheck(Option option);
+
+	/**
+	 * 상품옵션 패턴조회 // 20210929 eskim (안전인증)
+	 * @param option
+	 * @return
+	 * @author eskim
+	 * @since 2021. 9. 29
+	 */
+	Option getGoodsOption(Option option);
+
 	/**
 	 * 상품 가격 승인 목록
 	 *

+ 25 - 0
src/main/java/com/style24/admin/biz/dao/TsaStatisticsDao.java

@@ -6,6 +6,7 @@ import com.gagaframework.web.parameter.GagaMap;
 import com.style24.core.support.annotation.ShopDs;
 import com.style24.persistence.domain.Card;
 import com.style24.persistence.domain.Statistics;
+import jdk.internal.dynalink.beans.StaticClass;
 
 /**
  * 통계 Dao
@@ -167,4 +168,28 @@ public interface TsaStatisticsDao {
 
 	Collection<Statistics> getPaymentList(Statistics statistics);
 
+	Collection<Statistics> getSubPaymentList(Statistics statistics);
+
+	Long getRemainPoint();
+
+	Long getRemainGiftCard();
+
+	Collection<Statistics> getCustomerJoinList(Statistics statistics);
+
+	Collection<Statistics> getCustomerGradOrderList(Statistics statistics);
+
+	Collection<Statistics> getCustomerAgeOrderList(Statistics statistics);
+
+	Collection<Statistics> getCustomerRankingList(Statistics statistics);
+
+	Collection<Statistics> getCustomerUnloginList();
+
+	Collection<GagaMap> getCustomerUnloginInfoList(Statistics statistics);
+
+	Collection<Statistics> getCustomerMarketingList();
+
+	Collection<Statistics> getCustomerDormRemainList();
+
+	Collection<GagaMap> getCustomerDormRemainInfoList(Statistics statistics);
+
 }

+ 45 - 0
src/main/java/com/style24/admin/biz/service/TsaBusinessService.java

@@ -576,4 +576,49 @@ public class TsaBusinessService {
 		}
 	}
 
+	/**
+	 * 총알배송 휴무일 목록
+	 * @param bizday - 영업일 정보
+	 * @return
+	 * @author gagamel
+	 * @since 2021. 9. 29
+	 */
+	public Collection<Bizday> getHoliday2List(Bizday bizday) {
+		return businessDao.getHoliday2List(bizday);
+	}
+
+	/**
+	 * 총알배송 영업일 저장 처리
+	 * @param
+	 * @return
+	 * @author jaewonHo
+	 * @since 2019. 12. 13
+	 */
+	@Transactional("shopTxnManager")
+	public void saveBizday2(Bizday bizday) {
+		bizday.setRegNo(TsaSession.getInfo().getUserNo());
+		bizday.setUpdNo(TsaSession.getInfo().getUserNo());
+
+		String bizdayYn = businessDao.getBizday2Yn(bizday.getBizday());
+
+		if (StringUtils.isEmpty(bizdayYn)) {
+			// 영업일여부 값이 없으면 신규로 등록
+			businessDao.createBizday2(bizday);
+		} else {
+			bizday.setBizdayYn(bizdayYn);
+			businessDao.updateBizday2(bizday);
+		}
+	}
+
+	/**
+	 * 공급업체 목록
+	 * @param supplyComp - 공급업체 정보
+	 * @return
+	 * @author moon
+	 * @since 2021. 09. 29
+	 */
+	public Collection<SupplyCompany> getSupplyCompanyList2(SupplyCompany supplyComp) {
+		return businessDao.getSupplyCompanyList2(supplyComp);
+	}	
+	
 }

+ 97 - 0
src/main/java/com/style24/admin/biz/service/TsaDeliveryService.java

@@ -641,4 +641,101 @@ public class TsaDeliveryService {
 		return deliveryDao.getExchangeDelvFailList(delivery);
 	}
 	
+	
+	/**
+	 * 배송 목록(입점) 건수
+	 *
+	 * @param Delivery
+	 * @return
+	 * @author moon
+	 * @since 2021. 09. 15
+	 */
+	public int getDeliveryListScmCount(Delivery delivery) {
+		
+		if (StringUtils.isNotBlank(delivery.getCondition())) {
+			delivery.setConditions(delivery.getCondition().replaceAll("\r", "").split("\n"));
+		}
+		
+		// 외부몰권한일 때 외부몰벤더ID 설정
+		if (TsaSession.getInfo().getRoleCd().startsWith("G001_C")) {
+			delivery.setMallGb(TsaConstants.MallGb.EXTMALL.value());
+			delivery.setVendorId(TsaSession.getInfo().getVendorId());
+		}
+		
+		if (!StringUtils.isBlank(delivery.getBrandList())) {
+			try {
+				String [] arrBrandCd = mapper.readValue(delivery.getBrandList(), String[].class);
+				delivery.setMultiBrand(arrBrandCd);
+			} catch (Exception e) {
+				e.printStackTrace();
+				throw new IllegalStateException("브랜드코드 검색중 오류로 인해 조회되지 않았습니다.");
+			}
+		}
+
+		if (!StringUtils.isBlank(delivery.getSupplyCompList())) {
+			try {
+				String [] arrSupplyComp = mapper.readValue(delivery.getSupplyCompList(), String[].class);
+				delivery.setMultiSupplyCompCd(arrSupplyComp);
+			} catch (Exception e) {
+				e.printStackTrace();
+				throw new IllegalStateException("업체코드 검색중 오류로 인해 조회되지 않았습니다.");
+			}
+		}		
+		return deliveryDao.getDeliveryListScmCount(delivery);
+	}
+	
+	/**
+	 * 배송 목록(입점)
+	 *
+	 * @param -Delivery
+	 * @return Collection<Delivery>
+	 * @author moon
+	 * @since 2021. 09. 15
+	 */
+	public Collection<Delivery> getDeliveryScmList(Delivery delivery) {
+		// multi row 검색관련 처리
+		
+		if (StringUtils.isNotBlank(delivery.getCondition())) {
+			delivery.setConditions(delivery.getCondition().replaceAll("\r", "").split("\n"));
+		}
+
+		// 외부몰권한일 때 외부몰벤더ID 설정
+		if (TsaSession.getInfo().getRoleCd().startsWith("G001_C")) {
+			delivery.setMallGb(TsaConstants.MallGb.EXTMALL.value());
+			delivery.setVendorId(TsaSession.getInfo().getVendorId());
+		}
+		
+		if (!StringUtils.isBlank(delivery.getBrandList())) {
+			try {
+				String [] arrBrandCd = mapper.readValue(delivery.getBrandList(), String[].class);
+				delivery.setMultiBrand(arrBrandCd);
+			} catch (Exception e) {
+				e.printStackTrace();
+				throw new IllegalStateException("브랜드코드 검색중 오류로 인해 조회되지 않았습니다.");
+			}
+		}
+
+		if (!StringUtils.isBlank(delivery.getSupplyCompList())) {
+			try {
+				String [] arrSupplyComp = mapper.readValue(delivery.getSupplyCompList(), String[].class);
+				delivery.setMultiSupplyCompCd(arrSupplyComp);
+			} catch (Exception e) {
+				e.printStackTrace();
+				throw new IllegalStateException("업체코드 검색중 오류로 인해 조회되지 않았습니다.");
+			}
+		}
+		
+		if (!StringUtils.isBlank(delivery.getSupplyCompList())) {
+			try {
+				String[] arrSupplyComp = mapper.readValue(delivery.getSupplyCompList(), String[].class);
+				delivery.setMultiSupplyCompCd(arrSupplyComp);
+			} catch (Exception e) {
+				e.printStackTrace();
+				throw new IllegalStateException("업체코드 검색중 오류로 인해 조회되지 않았습니다.");
+			}
+		}		
+		
+		return deliveryDao.getDeliveryScmList(delivery);
+	}
+	
 }

+ 253 - 10
src/main/java/com/style24/admin/biz/service/TsaGoodsService.java

@@ -2860,14 +2860,124 @@ public class TsaGoodsService {
 			return goods.getGoodsStat();
 		}
 
-		// 옵션
-		if (!UPDATE_NO_PATTERN.equals(goodsMass.getOptStr().trim())) {
-			goods.setGoodsRegMsg("옵션은 변경할 수 없습니다.");
+		// 옵션 // 20210929 eskim (안전인증)
+		if (!UPDATE_NO_PATTERN.equals(goodsMass.getOptStr().trim()) && "Y".equals(goodsOrigin.getSelfGoodsYn())) {
+			goods.setGoodsRegMsg("자사상품은 옵션은 변경할 수 없습니다.");
 			goods.setGoodsStat("10");
 			this.setGoodsRegResult(goods, goodsMass, procJob);
 			return goods.getGoodsStat();
 		}
 
+		// 20210929 eskim (안전인증)
+		// 옵션-입점상품만
+		Collection<Option> stockList = new ArrayList<>();
+		if (!UPDATE_NO_PATTERN.equals(goodsMass.getOptStr().trim()) ) {
+
+			//옵션1[필수]^옵션2[선택]^추가금액^안전재고[필수]^판매재고[필수]  |
+			//검정^90^0^0^10|검정^95^0^0^8|검정^100^0^0^5|파랑^90^0^0^15|파랑^95^0^0^5|파랑^100^0^0^1|파랑^105^0^0^7
+
+			Option dupOption = new Option();
+			dupOption.setGoodsCd(goodsMass.getGoodsCd());
+			int cnt = goodsDao.getGoodsOptionCount(dupOption); // 기 등록된 옵션 건수 조회
+
+			String[] arrSizeCd = goodsMass.getOptStr().trim().split("\\|");
+			for (int i = 0; i < arrSizeCd.length; i++) {
+				String[] arrOptCd = arrSizeCd[i].split("\\^");
+				//log.info("[ arrOptCd.length] {}", arrOptCd.length);
+				if (arrOptCd.length != 5) {
+					goods.setGoodsRegMsg("옵션(SKU) " + (i + 1) + "번째 옵션구분자[^] 갯수 상이");
+					goods.setGoodsStat("10");
+					break;
+				}
+
+				// 옵션1 - 필수
+				if (StringUtils.isBlank(arrOptCd[0])) {
+					goods.setGoodsRegMsg("옵션(SKU) " + (i + 1) + "번째 옵션1 정보없음");
+					goods.setGoodsStat("10");
+					break;
+				}
+				// 추가금액 - 필수
+				if (StringUtils.isBlank(arrOptCd[2])) {
+					goods.setGoodsRegMsg("옵션(SKU) " + (i + 1) + "번째 추가금액 정보없음");
+					goods.setGoodsStat("10");
+					break;
+				}
+				if (!arrOptCd[2].trim().matches(NUMBER_PATTERN)) {
+					goods.setGoodsRegMsg("옵션(SKU) " + (i + 1) + "번째 추가금액 숫자 오류");
+					goods.setGoodsStat("10");
+					break;
+				}
+				// 안전재고 - 필수
+				if (StringUtils.isBlank(arrOptCd[3])) {
+					goods.setGoodsRegMsg("옵션(SKU) " + (i + 1) + "번째 안전재고 정보없음");
+					goods.setGoodsStat("10");
+					break;
+				}
+				if (!arrOptCd[3].trim().matches(NUMBER_PATTERN)) {
+					goods.setGoodsRegMsg("옵션(SKU) " + (i + 1) + "번째 안전재고 숫자 오류");
+					goods.setGoodsStat("10");
+					break;
+				}
+				// 판매재고 - 필수
+				if (StringUtils.isBlank(arrOptCd[4])) {
+					goods.setGoodsRegMsg("옵션(SKU) " + (i + 1) + "번째 판매재고 정보없음");
+					goods.setGoodsStat("10");
+					break;
+				}
+				if (!arrOptCd[4].trim().matches(NUMBER_PATTERN)) {
+					goods.setGoodsRegMsg("옵션(SKU) " + (i + 1) + "번째 판매재고 숫자 오류");
+					goods.setGoodsStat("10");
+					break;
+				}
+
+				// 옵션 중복 여부 확인
+				String optCd1 = arrOptCd[0];
+				String optCd2 = arrOptCd[1];
+				dupOption.setOptCd1(optCd1);
+				dupOption.setOptCd2(optCd2);
+
+				//상품옵션 중복건수여부 확인
+				int dupOptionCnt = goodsDao.getGoodsOptionDupCountCheck(dupOption);
+				if (dupOptionCnt > 0) {
+					goods.setGoodsRegMsg("옵션(SKU) " + (i + 1) + "번째 옵션1과 옵션2가 중복되는 옵션이 존재합니다.");
+					goods.setGoodsStat("10");
+					break;
+				}
+
+				//상품옵션 패턴조회
+				Option goodsOption = goodsDao.getGoodsOption(dupOption);
+				if (goodsOption != null) {
+					if (StringUtils.isBlank(goodsOption.getOptCd2()) == !StringUtils.isBlank(optCd2) || !StringUtils.isBlank(goodsOption.getOptCd2()) == StringUtils.isBlank(optCd2)) {
+						goods.setGoodsRegMsg("옵션(SKU) " + (i + 1) + "번째 옵션2가 기 등록된 옵션2의 패턴과 다릅니다.");
+						goods.setGoodsStat("10");
+						break;
+					}
+				}
+
+				Option goodsStock = new Option();
+				goodsStock.setGoodsCd(goods.getGoodsCd());
+				goodsStock.setOptCd(goods.getGoodsCd() + "-" + (cnt + (i + 1)));
+				goodsStock.setOptCd1(arrOptCd[0].trim());
+				goodsStock.setOptCd2(arrOptCd[1].trim());
+				goodsStock.setAddPrice(Integer.parseInt(arrOptCd[2]));
+				goodsStock.setBaseStockQty(Integer.parseInt(arrOptCd[3]));
+				goodsStock.setCurrStockQty(Integer.parseInt(arrOptCd[4]));
+				goodsStock.setSoldoutYn("N");
+				goodsStock.setDispOrd(cnt + (i + 1));
+				goodsStock.setDispYn("Y");
+				goodsStock.setRegNo(goods.getRegNo());
+				goodsStock.setUpdNo(goods.getUpdNo());
+
+				stockList.add(goodsStock);
+			}
+			goods.setChoOtYn("Y");
+		}
+
+		if ("10".equals(goods.getGoodsStat())) { // 정보 오류
+			this.setGoodsRegResult(goods, goodsMass, procJob);
+			return goods.getGoodsStat();  //continue
+		}
+
 		// 상품 고시
 		Collection<GoodsNotiInfo> newGoodsNotiList = new ArrayList<>(); //적용할 고시 정보
 		goods = this.getUpdateMassGoodsNotiCheck(goods, gagaMap, goodsOrigin, newGoodsNotiList);
@@ -2887,13 +2997,6 @@ public class TsaGoodsService {
 			goods.setChkDescKeep("Y");
 		}
 
-		if ("N".equals(goods.getChDataYn()) && "N".equals(goods.getChkDescKeep()) && "N".equals(goods.getChNotiYn())) {
-			goods.setGoodsRegMsg("변경정보 없음");
-			goods.setGoodsStat("10");
-			this.setGoodsRegResult(goods, goodsMass, procJob);
-			return goods.getGoodsStat();
-		}
-
 		//상품 기본정보 변경여부 와 촬영업체가 아닌경우
 		if ("Y".equals(goods.getChDataYn()) && !"G001_E000".equals(TsaSession.getInfo().getRoleCd())) {
 
@@ -2942,6 +3045,13 @@ public class TsaGoodsService {
 			}
 		}
 
+		// 20210929 eskim(안전인증)
+		// 옵션 적용
+		if (!UPDATE_NO_PATTERN.equals(goodsMass.getOptStr().trim()) && stockList != null && !stockList.isEmpty()) {
+			goods.setSelfGoodsYn(goodsOrigin.getSelfGoodsYn());
+			this.createGoodsSize(goods, stockList); // 입점 상품사이즈 정보 자장
+		}
+
 		// 품목변경시 카테고리 자동 전시
 		if (!UPDATE_NO_PATTERN.equals(goods.getItemkindCd().trim())) {
 			GoodsCategory goodsCategory = new GoodsCategory();
@@ -2954,11 +3064,144 @@ public class TsaGoodsService {
 
 		}
 
+		// 20210929 eskim (안전인증)
+		// 안전인증 적용
+		if (!UPDATE_NO_PATTERN.equals(goodsMass.getCertTargetGb().trim()) || !UPDATE_NO_PATTERN.equals(goodsMass.getCertFormGb().trim()) ||
+			 !UPDATE_NO_PATTERN.equals(goodsMass.getCertType().trim()) || !UPDATE_NO_PATTERN.equals(goodsMass.getCertNum().trim())) {
+
+			//기존안전인증정보
+			GoodsSafeNo dataGoodsSafeNo = goodsDao.getGoodsDetailSafe(goods);
+			GoodsSafeNo goodsSafeNo = new GoodsSafeNo();
+			goodsSafeNo.setGoodsCd(goods.getGoodsCd());
+			if (dataGoodsSafeNo == null || StringUtils.isBlank(dataGoodsSafeNo.getGoodsCd())) {
+				goodsSafeNo.setCertTargetGb(!UPDATE_NO_PATTERN.equals(goodsMass.getCertTargetGb().trim())?goodsMass.getCertTargetGb().trim():"");
+				goodsSafeNo.setCertFormGb(!UPDATE_NO_PATTERN.equals(goodsMass.getCertFormGb().trim())?goodsMass.getCertFormGb().trim():"");
+				goodsSafeNo.setCertType(!UPDATE_NO_PATTERN.equals(goodsMass.getCertType().trim())?goodsMass.getCertType().trim():"");
+				goodsSafeNo.setCertNum(!UPDATE_NO_PATTERN.equals(goodsMass.getCertNum().trim())?goodsMass.getCertNum().trim():"");
+			}else {
+				goodsSafeNo.setCertTargetGb(!UPDATE_NO_PATTERN.equals(goodsMass.getCertTargetGb().trim())?goodsMass.getCertTargetGb().trim():dataGoodsSafeNo.getCertTargetGb());
+				goodsSafeNo.setCertFormGb(!UPDATE_NO_PATTERN.equals(goodsMass.getCertFormGb().trim())?goodsMass.getCertFormGb().trim():dataGoodsSafeNo.getCertFormGb());
+				goodsSafeNo.setCertType(!UPDATE_NO_PATTERN.equals(goodsMass.getCertType().trim())?goodsMass.getCertType().trim():dataGoodsSafeNo.getCertType());
+				goodsSafeNo.setCertNum(!UPDATE_NO_PATTERN.equals(goodsMass.getCertNum().trim())?goodsMass.getCertNum().trim():dataGoodsSafeNo.getCertNum());
+			}
+			// 안전인증 체크
+			if (!StringUtils.isBlank(goodsSafeNo.getCertTargetGb())) {
+				CommonCode commonCode = new CommonCode();
+				//인증대상구분
+
+				commonCode.setCdGb("G083");
+				commonCode.setCd(goodsSafeNo.getCertTargetGb());
+				Collection<CommonCode> certTargetGbList = rendererService.getCommonCodeList(commonCode);
+				if (certTargetGbList == null || certTargetGbList.isEmpty()) {
+					goods.setGoodsRegMsg("인증대상 오류");
+					goods.setGoodsStat("10");
+					this.setGoodsRegResult(goods, goodsMass, procJob);
+					return goods.getGoodsStat();
+
+				}
+
+				if ("G083_1".equals(goodsSafeNo.getCertTargetGb())) {
+					//인증형태구분
+					if (StringUtils.isBlank(goodsSafeNo.getCertFormGb())) {
+
+						goods.setGoodsRegMsg("인증형태 오류");
+						goods.setGoodsStat("10");
+						this.setGoodsRegResult(goods, goodsMass, procJob);
+						return goods.getGoodsStat();
+					}else {
+						commonCode.setCdGb("G084");
+						commonCode.setCd(goodsSafeNo.getCertFormGb());
+						Collection<CommonCode> certFormGbList = rendererService.getCommonCodeList(commonCode);
+						if (certFormGbList == null || certFormGbList.isEmpty()) {
+
+							goods.setGoodsRegMsg("인증형태 오류");
+							goods.setGoodsStat("10");
+							this.setGoodsRegResult(goods, goodsMass, procJob);
+							return goods.getGoodsStat();
+						}
+					}
+
+					//인증타입
+					if (UPDATE_NO_PATTERN.equals(goodsSafeNo.getCertType()) || StringUtils.isBlank(goodsSafeNo.getCertType())) {
+
+						goods.setGoodsRegMsg("인증타입 오류");
+						goods.setGoodsStat("10");
+						this.setGoodsRegResult(goods, goodsMass, procJob);
+						return goods.getGoodsStat();
+					}
+
+					commonCode.setCdGb("G081");
+					commonCode.setCd(goodsSafeNo.getCertType());
+					Collection<CommonCode> certTypeList = rendererService.getCommonCodeList(commonCode);
+					if (certTypeList == null || certTypeList.isEmpty()) {
+						goods.setGoodsRegMsg("인증타입 오류");
+						goods.setGoodsStat("10");
+						this.setGoodsRegResult(goods, goodsMass, procJob);
+						return goods.getGoodsStat();
+					}
+
+					if ("G081_1".equals(goodsSafeNo.getCertType()) || "G081_2".equals(goodsSafeNo.getCertType())) {
+						if (UPDATE_NO_PATTERN.equals(goodsSafeNo.getCertNum()) || StringUtils.isBlank(goodsSafeNo.getCertNum())) {
+
+							goods.setGoodsRegMsg("인증번호 오류");
+							goods.setGoodsStat("10");
+							this.setGoodsRegResult(goods, goodsMass, procJob);
+							return goods.getGoodsStat();
+						}
+					}
+				}else {
+					goodsSafeNo.setCertFormGb("");
+					goodsSafeNo.setCertType("");
+					goodsSafeNo.setCertNum("");
+				}
+
+				saveGoodsDetailCertNum(goodsSafeNo);
+
+			}else{
+				if ((!StringUtils.isBlank(goodsSafeNo.getCertNum())) ||
+					(!StringUtils.isBlank(goodsSafeNo.getCertFormGb())) ||
+					(!StringUtils.isBlank(goodsSafeNo.getCertType()))) {
+
+					goods.setGoodsRegMsg("인증대상 오류");
+					goods.setGoodsStat("10");
+					this.setGoodsRegResult(goods, goodsMass, procJob);
+					return goods.getGoodsStat();
+				}
+			}
+			goods.setChSafeYn("Y");
+		}
+
+		if ("N".equals(goods.getChDataYn()) && "N".equals(goods.getChkDescKeep()) &&
+				"N".equals(goods.getChNotiYn()) && "N".equals(goods.getChSafeYn()) &&
+				"N".equals(goods.getChoOtYn()) ) {
+			goods.setGoodsRegMsg("변경정보 없음");
+			goods.setGoodsStat("10");
+			this.setGoodsRegResult(goods, goodsMass, procJob);
+			return goods.getGoodsStat();
+		}
+
 		this.setGoodsRegResult(goods, goodsMass, procJob);
 
 		return goods.getGoodsStat();
 	}
 
+	/**
+	 * 상품등록 - 상품재고정보 (입점)  // 20210929 eskim(안전인증)
+	 *
+	 * @param goods
+	 * @param excelMap
+	 * @return Goods
+	 * @author eskim
+	 * @since 2021. 09. 29
+	 */
+	private void createGoodsSize(Goods goods, Collection<Option> stockist) {
+
+		for (Option stock : stockist) {
+			goodsDao.saveStock(stock);
+		}
+	}
+
+
 	/**
 	 * 상품 대량 등록 결과 정보
 	 *

+ 143 - 1
src/main/java/com/style24/admin/biz/service/TsaStatisticsService.java

@@ -5,6 +5,7 @@ import java.util.Collection;
 import java.util.List;
 import java.util.Map;
 
+import com.style24.admin.support.security.session.TsaSession;
 import org.apache.catalina.mapper.Mapper;
 import org.apache.commons.collections4.map.LinkedMap;
 import org.apache.commons.lang3.StringUtils;
@@ -106,7 +107,7 @@ public class TsaStatisticsService {
 	}
 
 	/**
-	 * 시별 주문 조회
+	 * 시별 주문 조회
 	 * @return Collection<Statistics>
 	 * @author lmc
 	 * @since 2021. 9. 16.
@@ -286,4 +287,145 @@ public class TsaStatisticsService {
 		return statisticsDao.getPaymentList(statistics);
 	}
 
+	public Collection<Statistics> getSubPaymentList(Statistics statistics) {
+		return statisticsDao.getSubPaymentList(statistics);
+	}
+
+	public long getRemainPoint() {
+		return statisticsDao.getRemainPoint();
+	}
+
+	public long getRemainGiftCard() {
+		return statisticsDao.getRemainGiftCard();
+	}
+
+	public Collection<Statistics> getCustomerJoinList(Statistics statistics) {
+		return statisticsDao.getCustomerJoinList(statistics);
+	}
+
+	public Collection<Statistics> getCustomerGradOrderList(Statistics statistics) {
+		return statisticsDao.getCustomerGradOrderList(statistics);
+	}
+
+	public Collection<Statistics> getCustomerAgeOrderList(Statistics statistics) {
+		return statisticsDao.getCustomerAgeOrderList(statistics);
+	}
+
+	public Collection<Statistics> getCustomerRankingList(Statistics statistics) {
+		return statisticsDao.getCustomerRankingList(statistics);
+	}
+
+	public Collection<Statistics> getCustomerUnloginList() {
+		return statisticsDao.getCustomerUnloginList();
+	}
+
+//	public Collection<Statistics> getCustomerUnloginInfoList() {
+//		return statisticsDao.getCustomerUnloginInfoList();
+//	}
+
+	public Collection<Statistics> getCustomerMarketingList() {
+		return statisticsDao.getCustomerMarketingList();
+	}
+
+	public Collection<Statistics> getCustomerDormRemainList() {
+		return statisticsDao.getCustomerDormRemainList();
+	}
+
+//	public Collection<Statistics> getCustomerDormRemainInfoList() {
+//		return statisticsDao.getCustomerDormRemainInfoList();
+//	}
+
+	/**
+	 * 미로그인회원현황 엑셀다운로드
+	 * @param
+	 * @return
+	 * @author yujung
+	 * @since 2021. 09. 30
+	 */
+	public void getCustomerUnloginExcelList(Statistics statistics, String excelFilenameWithPath) {
+		statistics.setRegNo(TsaSession.getInfo().getUserNo());
+
+		List<String> colInfoList = new ArrayList<String>();
+		String[] listTitles;
+		String[] cellNames;
+		String[] cellTypes;
+
+		colInfoList.add("아이디|CUST_ID|"+ GagaExcelConstants.CellType.CHAR_CENTER.name());
+		colInfoList.add("회원명|CUST_NM|"+ GagaExcelConstants.CellType.CHAR_CENTER.name());
+		colInfoList.add("개월수|MONTHS|"+ GagaExcelConstants.CellType.CHAR_CENTER.name());
+		colInfoList.add("휴대폰번호|CELL_PHNNO|"+ GagaExcelConstants.CellType.CHAR_CENTER.name());
+		colInfoList.add("이메일|EMAIL|"+ GagaExcelConstants.CellType.CHAR_CENTER.name());
+		colInfoList.add("생년|BIRTH_YM|"+ GagaExcelConstants.CellType.CHAR_CENTER.name());
+
+		listTitles = new String[colInfoList.size()];
+		cellNames = new String[colInfoList.size()];
+		cellTypes = new String[colInfoList.size()];
+
+		String[] temp;
+		int i = 0;
+		for (String colInfo : colInfoList) {
+			temp = colInfo.split("\\|");
+			listTitles[i] = temp[0];
+			cellNames[i] = temp[1];
+			cellTypes[i] = temp[2];
+			i++;
+		}
+
+		String targetPath = env.getProperty("upload.goods.view");
+		Collection<GagaMap> customerUnloginInfoList = statisticsDao.getCustomerUnloginInfoList(statistics); // map형식으로 조회
+
+		try {
+			GagaExcelUtil.createExcel(excelFilenameWithPath, customerUnloginInfoList, "미로그인회원현황", listTitles, cellNames, cellTypes, TsaConstants.EXCEL_FOOTER_TITLE);
+		} catch (Exception e) {
+			throw new IllegalStateException(e);
+		}
+
+	}
+
+	/**
+	 * 휴면전환 잔여일별 회원 리스트 엑셀다운로드
+	 * @param
+	 * @return
+	 * @author yujung
+	 * @since 2021. 09. 30
+	 */
+	public void getCustomerDormRemainExcelList(Statistics statistics, String excelFilenameWithPath) {
+		statistics.setRegNo(TsaSession.getInfo().getUserNo());
+
+		List<String> colInfoList = new ArrayList<String>();
+		String[] listTitles;
+		String[] cellNames;
+		String[] cellTypes;
+
+		colInfoList.add("구분|GB|"+ GagaExcelConstants.CellType.CHAR_CENTER.name());
+		colInfoList.add("아이디|CUST_ID|"+ GagaExcelConstants.CellType.CHAR_CENTER.name());
+		colInfoList.add("회원명|CUST_NM|"+ GagaExcelConstants.CellType.CHAR_CENTER.name());
+		colInfoList.add("휴대폰번호|CELL_PHNNO|"+ GagaExcelConstants.CellType.CHAR_CENTER.name());
+		colInfoList.add("이메일|EMAIL|"+ GagaExcelConstants.CellType.CHAR_CENTER.name());
+		colInfoList.add("생년|BIRTH_YM|"+ GagaExcelConstants.CellType.CHAR_CENTER.name());
+
+		listTitles = new String[colInfoList.size()];
+		cellNames = new String[colInfoList.size()];
+		cellTypes = new String[colInfoList.size()];
+
+		String[] temp;
+		int i = 0;
+		for (String colInfo : colInfoList) {
+			temp = colInfo.split("\\|");
+			listTitles[i] = temp[0];
+			cellNames[i] = temp[1];
+			cellTypes[i] = temp[2];
+			i++;
+		}
+
+		String targetPath = env.getProperty("upload.goods.view");
+		Collection<GagaMap> customerDormRemainInfoList = statisticsDao.getCustomerDormRemainInfoList(statistics); // map형식으로 조회
+
+		try {
+			GagaExcelUtil.createExcel(excelFilenameWithPath, customerDormRemainInfoList, "휴면전환_잔여일별_회원", listTitles, cellNames, cellTypes, TsaConstants.EXCEL_FOOTER_TITLE);
+		} catch (Exception e) {
+			throw new IllegalStateException(e);
+		}
+
+	}
 }

+ 81 - 0
src/main/java/com/style24/admin/biz/web/TsaBusinessController.java

@@ -890,6 +890,48 @@ public class TsaBusinessController extends TsaBaseController {
 		return super.ok(message.getMessage("SUCC_0009"));
 	}
 
+	/**
+	 * 총알배송 영업일관리 화면
+	 * @return
+	 * @author gagamel
+	 * @since 2021. 9. 29
+	 */
+	@GetMapping("/bizday2/form")
+	public ModelAndView bizday2Form() {
+		ModelAndView mav = new ModelAndView();
+
+		mav.setViewName("business/Bizday2Form");
+
+		return mav;
+	}
+
+	/**
+	 * 총알배송 휴무일 목록
+	 * @param bizday - 영업일 정보
+	 * @return
+	 * @author gagamel
+	 * @since 2021. 9. 29
+	 */
+	@GetMapping("/holiday2/list")
+	@ResponseBody
+	public Collection<Bizday> getHoliday2List(Bizday bizday) {
+		return businessService.getHoliday2List(bizday);
+	}
+
+	/**
+	 * 총알배송영업일 저장
+	 * @param bizday - 영업일 정보
+	 * @return
+	 * @author gagamel
+	 * @since 2021. 9. 29
+	 */
+	@PostMapping("/bizday2/save")
+	@ResponseBody
+	public GagaResponse saveBizday2(@RequestBody Bizday bizday) {
+		businessService.saveBizday2(bizday);
+		return super.ok(message.getMessage("SUCC_0009"));
+	}
+
 	/**
 	 * 계좌인증
 	 *
@@ -911,4 +953,43 @@ public class TsaBusinessController extends TsaBaseController {
 		result.setBoolean("isValid", isValid);
 		return result;
 	}
+	
+	/**
+	 * 공급업체 목록 화면(팝업)
+	 * @param brandMd - 담당MD 정보
+	 * @return
+	 * @author moon
+	 * @since 2021. 09. 29
+	 */
+	@GetMapping("/comapny/search/scm/form")
+	public ModelAndView companySearchForm2(SupplyCompany company) {
+		ModelAndView mav = new ModelAndView();
+		log.info("company={}", company);
+		mav.addObject("params", company);
+		mav.setViewName("business/SupplyCompanyPopupForm2");
+		return mav;
+	}
+	
+	/**
+	 * 공급업체 목록
+	 * @param supplyComp - 공급업체 정보
+	 * @return
+	 * @author moon
+	 * @since 2021. 09. 29
+	 */
+	@PostMapping("/supply/company/scm/list")
+	@ResponseBody
+	public Collection<SupplyCompany> getSupplyCompanyList2(@RequestBody SupplyCompany supplyComp) {
+		// multi row 검색관련 처리
+		if (!StringUtils.isBlank(supplyComp.getSearchSupplyCompCd())) {
+			supplyComp.setMultiSupplyCompCd(supplyComp.getSearchSupplyCompCd().replaceAll("\r", "").trim().split("\n"));
+		}
+		if (!StringUtils.isBlank(supplyComp.getSearchSupplyCompNm())) {
+			supplyComp.setMultiSupplyCompNm(supplyComp.getSearchSupplyCompNm().replaceAll("\r", "").trim().split("\n"));
+		}
+		supplyComp.setSelfYn("N");
+		//log.info("supplyComp  {}", supplyComp);
+		return businessService.getSupplyCompanyList2(supplyComp);
+	}
+	
 }

+ 67 - 0
src/main/java/com/style24/admin/biz/web/TsaDeliveryController.java

@@ -573,4 +573,71 @@ public class TsaDeliveryController extends TsaBaseController {
 		return dataList;
 	}
 	
+	
+	/**
+	 * 배송 목록 화면(입점)
+	 * @return
+	 * @author moon
+	 * @since 2021. 09. 14
+	 */
+	@GetMapping("/scm/list/form")
+	public ModelAndView deliveryListScmForm() {
+		ModelAndView mav = new ModelAndView();
+
+		// 몰구분
+		//mav.addObject("mallGbList", rendererService.getMallGbCommonCodeList(TsaSession.getInfo().getRoleCd()));
+		mav.addObject("mallGbList", rendererService.getAvailCommonCodeList("G011"));
+		// 주문상세상태코드
+		mav.addObject("ordDtlStatList", rendererService.getAvailCommonCodeList("G013"));
+		// 출고처
+		mav.addObject("deliveryLocList", rendererService.getDeliveryLocAllList());
+		// 사이트구분
+		mav.addObject("siteCdList", rendererService.getAvailCommonCodeList("G000"));
+		// 택배사명 목록
+		mav.addObject("shipCompanyList", rendererService.getShipCompanyList());
+		// 출고처분류
+		// mav.addObject("delvTypeList", rendererService.getAvailCommonCodeList("G024"));
+		
+		String supplyCompCd = "";
+		if ("G001_B000".equals(TsaSession.getInfo().getRoleCd())) {
+			supplyCompCd = TsaSession.getInfo().getSupplyCompCd();
+		}
+		
+		// 공급업체
+		mav.addObject("supplyCompList", rendererService.getSupplyCompanyList("","Y"));
+        //mav.addObject("vendorList", rendererService.getVendorCommonCodeList(TsaSession.getInfo().getRoleCd()));
+
+		mav.setViewName("delivery/DeliveryListScmForm");
+
+		return mav;
+	}
+
+	/**
+	 * 배송 목록 화면(입점) - 배송 목록(입점)
+	 *
+	 * @param
+	 * @return
+	 * @throws Exception
+	 * @author moon
+	 * @since 2021. 09. 14
+	 */
+	@PostMapping("/scm/list")
+	@ResponseBody
+	public GagaMap getDeliveryScmList(@RequestBody Delivery delivery) throws Exception {
+		
+		GagaMap result = new GagaMap();
+		delivery.setPageable(new TscPageRequest(delivery.getPageNo() - 1, delivery.getPageSize()));
+		delivery.getPageable().setTotalCount(deliveryService.getDeliveryListScmCount(delivery));
+		TscSession.setAttribute("maskingYn", TsaSession.getInfo().getMaskingYn());
+
+		if ("N".equals(delivery.getPageingYn())) {
+			delivery.setPageable(null);
+		}		
+		
+		result.set("pageing", delivery);
+		result.set("deliveryList", deliveryService.getDeliveryScmList(delivery));
+		
+		return result;
+	}
+	
 }

+ 6 - 4
src/main/java/com/style24/admin/biz/web/TsaGoodsController.java

@@ -3080,12 +3080,14 @@ public class TsaGoodsController extends TsaBaseController {
 		String targetPath = GagaFileUtil.getConcatenationPath(env.getProperty("upload.excel.target.path"), "excel");
 		Collection<GagaMap> ecxelGoodsList = new ArrayList<>();
 
+		// 20210929 eskim (안전인증)
 		// 상품수장
 		// DB 처리 시 사용되는 파라미터명(셀명) 설정 -
 		String[] goodsNames = {"goodsCd", "goodsNm", "goodsTnm", "goodsSnm1", "itemkindCd", "seasonCd",
 			"sexGb", "goodsStatCd", "listPrice", "currPrice", "sellFeeRate", "goodsGb", "formalGb", "minOrdQty", "maxOrdQty", "dayMaxOrdQty",
 			"giftPackYn", "newCustOrdYn", "pntPrate", "prePpntUsableYn", "pntMrate", "preMpntUsableYn",
 			"returnableYn", "changeableYn", "taxGb", "ageGrpCd", "adultYn", "delvFeeCd", "optStr", "goodsContent",
+			"certTargetGb", "certFormGb", "certType", "certNum",
 			"niClsfCd", "niContent1", "niContent2",
 			"niContent3", "niContent4", "niContent5", "niContent6", "niContent7", "niContent8", "niContent9",
 			"niContent10", "niContent11", "niContent12", "niContent13", "niContent14", "niContent15", "niContent16",
@@ -3415,16 +3417,16 @@ public class TsaGoodsController extends TsaBaseController {
 		if (!StringUtils.isBlank(ifIncomelot.getCondition())) {
 			ifIncomelot.setConditionList(ifIncomelot.getCondition().replaceAll("\r", "").trim().split("\n"));
 		}
-		
+
 		// wms상품번호
 		if (!StringUtils.isBlank(ifIncomelot.getCondition2())) {
 			ifIncomelot.setConditionList2(ifIncomelot.getCondition2().replaceAll("\r", "").trim().split("\n"));
 		}
-		
-		// sku코드 
+
+		// sku코드
 		if (!StringUtils.isBlank(ifIncomelot.getCondition3())) {
 			ifIncomelot.setConditionList3(ifIncomelot.getCondition3().replaceAll("\r", "").trim().split("\n"));
-		}		
+		}
 
 		ifIncomelot.setPageable(new TscPageRequest(ifIncomelot.getPageNo() - 1, ifIncomelot.getPageSize()));
 		ifIncomelot.getPageable().setTotalCount(goodsService.getGoodsWmsIncomelotSkuListCount(ifIncomelot));

+ 286 - 53
src/main/java/com/style24/admin/biz/web/TsaStatisticsController.java

@@ -646,21 +646,6 @@ public class TsaStatisticsController extends TsaBaseController {
 		return mav;
 	}
 
-	/**
-	 * 결제수단별통계 화면
-	 * @return
-	 * @author swkim
-	 * @since 2021. 9. 28
-	 */
-	@GetMapping("/payment/main/form")
-	public ModelAndView paymentForm() {
-		ModelAndView mav = new ModelAndView();
-
-		mav.setViewName("statistics/PaymentForm");
-
-		return mav;
-	}
-
 	/**
 	 * 쿠폰 사용 통계 조회
 	 * author: 이명철
@@ -707,6 +692,103 @@ public class TsaStatisticsController extends TsaBaseController {
 		return mav;
 	}
 
+	/**
+	 * 다다익선 통계 조회
+	 * author: 이명철
+	 * return: Collection<Statistics>
+	 * since: 2021. 9. 28.
+	 */
+	@PostMapping("/tmtb/order/list")
+	@ResponseBody
+	public Collection<Statistics> getTmtbOrderList(@RequestBody Statistics statistics) {
+
+		if (!StringUtils.isBlank(statistics.getTmtbSq())) {
+			statistics.setMultiTmtbSq(statistics.getTmtbSq().split(System.lineSeparator()));
+		}
+
+		return statisticsService.getTmtbOrderList(statistics);
+	}
+
+	/**
+	 * 다다익선 주문 상세조회
+	 * author: 이명철
+	 * return: Collection<Statistics>
+	 * since: 2021. 9. 28.
+	 */
+	@PostMapping("/tmtb/order/detail/list")
+	@ResponseBody
+	public Collection<Statistics> getTmtbOrderDetailList(@RequestBody Statistics statistics) {
+		return statisticsService.getTmtbOrderDetailList(statistics);
+	}
+
+	/**
+	 * 기획전 통게 화면
+	 * author: 이명철
+	 * return: ModelAndView
+	 * since: 2021. 9. 28.
+	 */
+	@GetMapping("/plan/trading/form")
+	public ModelAndView planTradingForm() {
+		ModelAndView mav = new ModelAndView();
+		mav.setViewName("statistics/PlanTradingForm");
+		return mav;
+	}
+
+	/**
+	 * 기획전 통계 조회
+	 * author: 이명철
+	 * return: Collection<Statistics>
+	 * since: 2021. 9. 28.
+	 */
+	@PostMapping("/plan/order/list")
+	@ResponseBody
+	public Collection<Statistics> getPlanOrderList(@RequestBody Statistics statistics) {
+		if (!StringUtils.isBlank(statistics.getPlanSq())) {
+			statistics.setMultiPlanSq(statistics.getPlanSq().split(System.lineSeparator()));
+		}
+		return statisticsService.getPlanOrderList(statistics);
+	}
+
+	/**
+	 * 기획전 주문 상세조회
+	 * author: 이명철
+	 * return: Collection<Statistics>
+	 * since: 2021. 9. 28.
+	 */
+	@PostMapping("/plan/order/detail/list")
+	@ResponseBody
+	public Collection<Statistics> getPlanOrderDetailList(@RequestBody Statistics statistics) {
+		return statisticsService.getPlanOrderDetailList(statistics);
+	}
+
+	/**
+	 * 카드 목록
+	 * @param
+	 * @return
+	 * @author swkim
+	 * @since 2021. 09. 29
+	 */
+	@PostMapping("/card/list")
+	@ResponseBody
+	public Collection<Card> getCardList() {
+		return statisticsService.getCardList();
+	}
+
+	/**
+	 * 결제수단별통계 화면
+	 * @return
+	 * @author swkim
+	 * @since 2021. 9. 28
+	 */
+	@GetMapping("/payment/main/form")
+	public ModelAndView paymentForm() {
+		ModelAndView mav = new ModelAndView();
+
+		mav.setViewName("statistics/PaymentForm");
+
+		return mav;
+	}
+
 	/**
 	 * 결제수단별통계 조회
 	 * author: swkim
@@ -747,85 +829,236 @@ public class TsaStatisticsController extends TsaBaseController {
 	}
 
 	/**
-	 * 다다익선 통계 조회
-	 * author: 이명철
+	 * 부결제수단별통계 화면
+	 * @return
+	 * @author swkim
+	 * @since 2021. 9. 28
+	 */
+	@GetMapping("/payment/sub/form")
+	public ModelAndView subPaymentForm() {
+		ModelAndView mav = new ModelAndView();
+
+		// 포인트유형
+		mav.addObject("pointGbList", rendererService.getCommonCodeList("G069"));
+
+		// 상품권유형
+		mav.addObject("giftCardGbList", rendererService.getCommonCodeList("G074"));
+
+		// 포인트잔액
+		mav.addObject("remainPoint", statisticsService.getRemainPoint());
+
+		// 상품권잔액
+		mav.addObject("remainGiftCard", statisticsService.getRemainGiftCard());
+
+		mav.setViewName("statistics/SubPaymentForm");
+
+		return mav;
+	}
+
+	/**
+	 * 결제수단별통계 조회
+	 * author: swkim
 	 * return: Collection<Statistics>
 	 * since: 2021. 9. 28.
 	 */
-	@PostMapping("/tmtb/order/list")
+	@PostMapping("/payment/sub/list")
 	@ResponseBody
-	public Collection<Statistics> getTmtbOrderList(@RequestBody Statistics statistics) {
+	public Collection<Statistics> getSubPaymentList(@RequestBody Statistics statistics) {
 
-		if (!StringUtils.isBlank(statistics.getTmtbSq())) {
-			statistics.setMultiTmtbSq(statistics.getTmtbSq().split(System.lineSeparator()));
-		}
+		return statisticsService.getSubPaymentList(statistics);
+	}
 
-		return statisticsService.getTmtbOrderList(statistics);
+	/**
+	 * 가입현황 화면
+	 * @return
+	 * @author swkim
+	 * @since 2021. 9. 28
+	 */
+	@GetMapping("/customer/join/form")
+	public ModelAndView customerJoinForm() {
+		ModelAndView mav = new ModelAndView();
+
+		mav.setViewName("statistics/CustomerJoinForm");
+
+		return mav;
 	}
 
 	/**
-	 * 다다익선 주문 상세조회
-	 * author: 이명철
+	 * 가입현황 조회
+	 * author: swkim
 	 * return: Collection<Statistics>
 	 * since: 2021. 9. 28.
 	 */
-	@PostMapping("/tmtb/order/detail/list")
+	@PostMapping("/customer/join/list")
 	@ResponseBody
-	public Collection<Statistics> getTmtbOrderDetailList(@RequestBody Statistics statistics) {
-		return statisticsService.getTmtbOrderDetailList(statistics);
+	public Collection<Statistics> getCustomerJoinList(@RequestBody Statistics statistics) {
+
+		return statisticsService.getCustomerJoinList(statistics);
 	}
 
 	/**
-	 * 기획전 통게 화면
-	 * author: 이명철
-	 * return: ModelAndView
-	 * since: 2021. 9. 28.
+	 * 등급별주문현황 화면
+	 * @return
+	 * @author swkim
+	 * @since 2021. 9. 28
 	 */
-	@GetMapping("/plan/trading/form")
-	public ModelAndView planTradingForm() {
+	@GetMapping("/customer/grade/order/form")
+	public ModelAndView customerGradOrderForm() {
 		ModelAndView mav = new ModelAndView();
-		mav.setViewName("statistics/PlanTradingForm");
+
+		mav.setViewName("statistics/CustomerGradeOrderForm");
+
 		return mav;
 	}
 
 	/**
-	 * 기획전 통계 조회
-	 * author: 이명철
+	 * 등급별주문현황 조회
+	 * author: swkim
 	 * return: Collection<Statistics>
 	 * since: 2021. 9. 28.
 	 */
-	@PostMapping("/plan/order/list")
+	@PostMapping("/customer/grade/order/list")
 	@ResponseBody
-	public Collection<Statistics> getPlanOrderList(@RequestBody Statistics statistics) {
-		if (!StringUtils.isBlank(statistics.getPlanSq())) {
-			statistics.setMultiPlanSq(statistics.getPlanSq().split(System.lineSeparator()));
+	public Collection<Statistics> getCustomerGradOrderList(@RequestBody Statistics statistics) {
+
+		if (!StringUtils.isBlank(statistics.getBrandCdList())) {
+			statistics.setMultiBrandCd(statistics.getBrandCdList().split(","));
 		}
-		return statisticsService.getPlanOrderList(statistics);
+
+		if (!StringUtils.isBlank(statistics.getItemkindCdList())) {
+			statistics.setMultiItemkindCd(statistics.getItemkindCdList().split(","));
+		}
+
+		return statisticsService.getCustomerGradOrderList(statistics);
 	}
 
 	/**
-	 * 기획전 주문 상세조회
-	 * author: 이명철
+	 * 연령별주문현황 화면
+	 * @return
+	 * @author swkim
+	 * @since 2021. 9. 28
+	 */
+	@GetMapping("/customer/age/order/form")
+	public ModelAndView customerAgeOrderForm() {
+		ModelAndView mav = new ModelAndView();
+
+		// 회원등급
+		mav.addObject("gradeGbList", rendererService.getAvailCommonCodeList("G110"));
+		mav.setViewName("statistics/CustomerAgeOrderForm");
+
+		return mav;
+	}
+
+	/**
+	 * 연령별주문현황 조회
+	 * author: swkim
 	 * return: Collection<Statistics>
 	 * since: 2021. 9. 28.
 	 */
-	@PostMapping("/plan/order/detail/list")
+	@PostMapping("/customer/age/order/list")
 	@ResponseBody
-	public Collection<Statistics> getPlanOrderDetailList(@RequestBody Statistics statistics) {
-		return statisticsService.getPlanOrderDetailList(statistics);
+	public Collection<Statistics> getCustomerAgeOrderList(@RequestBody Statistics statistics) {
+
+		if (!StringUtils.isBlank(statistics.getBrandCdList())) {
+			statistics.setMultiBrandCd(statistics.getBrandCdList().split(","));
+		}
+
+		if (!StringUtils.isBlank(statistics.getItemkindCdList())) {
+			statistics.setMultiItemkindCd(statistics.getItemkindCdList().split(","));
+		}
+
+		return statisticsService.getCustomerAgeOrderList(statistics);
 	}
 
 	/**
-	 * 카드 목록
-	 * @param
+	 * 구매자랭킹 화면
 	 * @return
 	 * @author swkim
-	 * @since 2021. 09. 29
+	 * @since 2021. 9. 28
 	 */
-	@PostMapping("/card/list")
+	@GetMapping("/customer/ranking/form")
+	public ModelAndView customerRankingForm() {
+		ModelAndView mav = new ModelAndView();
+
+		mav.setViewName("statistics/CustomerRankingForm");
+
+		return mav;
+	}
+
+	/**
+	 * 구매자랭킹 조회
+	 * author: swkim
+	 * return: Collection<Statistics>
+	 * since: 2021. 9. 28.
+	 */
+	@PostMapping("/customer/ranking/list")
 	@ResponseBody
-	public Collection<Card> getCardList() {
-		return statisticsService.getCardList();
+	public Collection<Statistics> getCustomerRankingList(@RequestBody Statistics statistics) {
+
+		if (!StringUtils.isBlank(statistics.getBrandCdList())) {
+			statistics.setMultiBrandCd(statistics.getBrandCdList().split(","));
+		}
+
+		if (!StringUtils.isBlank(statistics.getItemkindCdList())) {
+			statistics.setMultiItemkindCd(statistics.getItemkindCdList().split(","));
+		}
+
+		return statisticsService.getCustomerRankingList(statistics);
 	}
 
+	/**
+	 * 회원활동현황 화면
+	 * @return
+	 * @author swkim
+	 * @since 2021. 9. 28
+	 */
+	@GetMapping("/customer/active/form")
+	public ModelAndView customerActiveForm() {
+		ModelAndView mav = new ModelAndView();
+
+		//미로그인회원형황
+		mav.addObject("unloginList", statisticsService.getCustomerUnloginList());
+		//마케팅수신동의현황
+		mav.addObject("marketingList", statisticsService.getCustomerMarketingList());
+		//휴면전환 잔여일별 회원현황
+		mav.addObject("dormRemainList", statisticsService.getCustomerDormRemainList());
+
+		mav.setViewName("statistics/CustomerActiveForm");
+
+		return mav;
+	}
+
+	/**
+	 * 미로그인회원현황 엑셀다운로드
+	 * @param
+	 * @return
+	 * @author yujung
+	 * @since 2021. 09. 30
+	 */
+	@GetMapping("/customer/unlogin/excel")
+	public ResponseEntity<InputStreamResource> customerUnloginExcelList(HttpServletRequest request, Statistics statistics) throws Exception {
+		String excelfileName = "미로그인회원현황 " + GagaDateUtil.getTodayDateTime() + ".xlsx";
+		String excelFilenameWithPath = GagaFileUtil.getConcatenationPath(env.getProperty("download.path"), "excel", excelfileName);
+
+		statisticsService.getCustomerUnloginExcelList(statistics, excelFilenameWithPath);
+
+		return GagaFileUtil.writeFile(request, excelFilenameWithPath);
+	}
+
+	/**
+	 * 휴면전환 잔여일별 회원현황 엑셀다운로드
+	 * @param
+	 * @return
+	 * @author yujung
+	 * @since 2021. 09. 30
+	 */
+	@GetMapping("/customer/dormremain/excel")
+	public ResponseEntity<InputStreamResource> customerDormremainExcelList(HttpServletRequest request, Statistics statistics) throws Exception {
+		String excelfileName = "휴면전환잔여일별회원 " + GagaDateUtil.getTodayDateTime() + ".xlsx";
+		String excelFilenameWithPath = GagaFileUtil.getConcatenationPath(env.getProperty("download.path"), "excel", excelfileName);
+
+		statisticsService.getCustomerDormRemainExcelList(statistics, excelFilenameWithPath);
+
+		return GagaFileUtil.writeFile(request, excelFilenameWithPath);
+	}
 }

+ 1 - 0
src/main/java/com/style24/persistence/domain/Delivery.java

@@ -119,6 +119,7 @@ public class Delivery extends TscBaseDomain {
 	private String soldoutMemo;
 	private String soldoutRegNo;
 	private String custId;
+	private String supplyCompSearchTxt;
 	
 	private Integer ordDtlNo;
 	private Integer ordNo;

+ 3 - 1
src/main/java/com/style24/persistence/domain/Goods.java

@@ -107,6 +107,8 @@ public class Goods extends TscBaseDomain {
 	private String chDataYn = "N";
 	private String chImgYn = "N";
 	private String chNotiYn = "N";
+	private String chSafeYn = "N";	// 20210929 eskim (안전인증)
+	private String choOtYn = "N";	// 20210929 eskim (안전인증)
 	private String chStockDataYn = "N";
 	private String chGoodsStatYn = "N";
 	private String chCfrmYn = "N";		//입점용추가
@@ -147,7 +149,7 @@ public class Goods extends TscBaseDomain {
 //	private String sizeSoldoutYn;
 	private String siteCd;
 	private int sellDay15Qty;
-	
+
 	private String certTargetGb;
 	private String certFormGb;
 	private String certType;

+ 4 - 1
src/main/java/com/style24/persistence/domain/GoodsMass.java

@@ -38,8 +38,11 @@ public class GoodsMass extends TscBaseDomain {
 //	private String distributionGb;	//유통구분(공콩코드 G065)
 	private String taxGb;			//과세구분(10:과세, 20:비과세)
 	private String ageGrpCd;		//상품연령코드(공통코드G023)
-	private String adultYn;			//성인용품여부 'Y', 'N'
+	private String certTargetGb;	//안전인증대상구분		// 20210929 eskim (안전인증)
+	private String certFormGb;		//안전인증형태구분
+	private String certType;		//안전인증타입구분
 	private String certNum;			//안전인증번호
+	private String adultYn;			//성인용품여부 'Y', 'N'
 
 	private String pntPrate;		//포인트적립율(PC)
 	private String pntMrate;		//포인트적립율(모바일)

+ 58 - 4
src/main/java/com/style24/persistence/domain/Statistics.java

@@ -152,7 +152,7 @@ public class Statistics extends TscBaseDomain {
 	private int sellFeeAmt;				// 수수료(실판매금액 * 판매수수료율)
 	private int totAmt10;				// 정상
 	private int totAmt20;				// 이월
-	private int amtRate10;				// 정상비
+	private double amtRate10;			// 정상비
 	private String mdId;				// 담당MD아이디
 	private String mdNm;				// 담당MD명
 	private String formalGb;			// 이월구분
@@ -167,8 +167,8 @@ public class Statistics extends TscBaseDomain {
 
 	private long clmAmt;      //클래임금액
 	private int clmQty;       //클랭미수량
-	private int amtRate;      //금액비
-	private int clmRate;      //클래임율
+	private double amtRate;      //금액비
+	private double clmRate;      //클래임율
 	private int rtnQty;       //반품수량
 	private long rtnAmt;      //반품금액
 	private int chgQty;       //교환수량
@@ -205,7 +205,7 @@ public class Statistics extends TscBaseDomain {
 	private int ordQty;
 	private int custCnt;
 	private int custCpnCnt;
-	private int ordRate;
+	private double ordRate;
 
 	private String planSq;
 	private String planNm;
@@ -228,4 +228,58 @@ public class Statistics extends TscBaseDomain {
 
 	@JsonFormat(with = JsonFormat.Feature.ACCEPT_SINGLE_VALUE_AS_ARRAY)
 	private String[] multiCardId;
+
+	private long pntGive;
+	private int pntOrdCnt;
+	private long pntUse;
+	private int giftRegCnt;
+	private int giftOrdCnt;
+	private long giftUse;
+	private String pointGb;
+	private String giftCardGb;
+
+	private int allCnt;
+	private int realCnt;
+	private int dormCnt;
+	private int vipCnt;
+	private int goldCnt;
+	private int silverCnt;
+	private int bronzeCnt;
+	private int welcomeCnt;
+	private int joinCnt;
+	private int drJoinCnt;
+	private int afJoinCnt;
+	private int chgDormCnt;
+	private int rmDormCnt;
+	private int seceedCnt;
+
+	private int priority;
+	private String custGrade;
+	private double avgOrdCnt;
+	private double avgSellQty;
+
+	private String age;
+	private String sexGb;
+
+	@JsonFormat(with = JsonFormat.Feature.ACCEPT_SINGLE_VALUE_AS_ARRAY)
+	private String[] multiGradeGb;
+
+	private String custId;
+	private int custNo;
+	private int custPoint;
+
+	private String distributionGbS;
+	private String distributionGbW;
+
+	private double perCnt1;
+	private double perCnt2;
+	private double perCnt3;
+	private double perCnt4;
+	private double perCnt5;
+
+	private int cnt1;
+	private int cnt2;
+	private int cnt3;
+	private int cnt4;
+	private int cnt5;
 }

+ 174 - 1
src/main/java/com/style24/persistence/mybatis/shop/TsaBusiness.xml

@@ -1187,7 +1187,7 @@
 
 	<!-- 영업일 생성 -->
 	<insert id="createBizday" parameterType="Bizday">
-		/*  TsaBusiness.saveBizday */
+		/*  TsaBusiness.createBizday */
 		INSERT INTO TB_BIZDAY (
 		       BIZDAY
 		     , WEEK_DAY
@@ -1245,6 +1245,88 @@
 		WHERE  BIZDAY = #{bizday}
 	</insert>
 	
+	<!-- 총알배송 휴무일 목록 -->
+	<select id="getHoliday2List" parameterType="Bizday" resultType="Bizday">
+		/* TsaBusiness.getHoliday2List */
+		SELECT DATE_FORMAT(BIZDAY,'%Y-%m-%d') AS BIZDAY /*영업일*/
+		     , WEEK_DAY                                 /*요일*/
+		     , BIZDAY_YN                                /*영업일여부*/
+		     , RESTDAY_DESC                             /*휴무일설명*/
+		FROM   TB_BIZDAY2
+		WHERE  1= 1
+		AND    BIZDAY <![CDATA[>=]]> #{startDt}
+		AND    BIZDAY <![CDATA[<]]> #{endDt}
+		AND    BIZDAY_YN = 'N' /*영업일이 아닌 넘만*/
+	</select>
+	
+	<!-- 총알배송 영업일여부 조회 -->
+	<select id="getBizday2Yn" parameterType="String" resultType="String">
+		/* TsaBusiness.getBizday2Yn */
+		SELECT BIZDAY_YN
+		FROM   TB_BIZDAY2
+		WHERE  BIZDAY = #{bizday}
+	</select>
+
+	<!-- 총알배송 영업일 생성 -->
+	<insert id="createBizday2" parameterType="Bizday">
+		/*  TsaBusiness.createBizday2 */
+		INSERT INTO TB_BIZDAY2 (
+		       BIZDAY
+		     , WEEK_DAY
+		     , BIZDAY_YN
+		     , RESTDAY_DESC
+		     , REG_NO
+		     , REG_DT
+		     , UPD_NO
+		     , UPD_DT
+		)
+		VALUES (
+		       #{bizday}
+		     , CASE DAYOFWEEK(#{bizday})
+		            WHEN 1 THEN '일'
+		            WHEN 2 THEN '월'
+		            WHEN 3 THEN '화'
+		            WHEN 4 THEN '수'
+		            WHEN 5 THEN '목'
+		            WHEN 6 THEN '금'
+		            WHEN 7 THEN '토'
+		       END
+		     , CASE DAYOFWEEK(#{bizday})
+		            WHEN 1 THEN 'N'
+		            WHEN 2 THEN 'Y'
+		            WHEN 3 THEN 'Y'
+		            WHEN 4 THEN 'Y'
+		            WHEN 5 THEN 'Y'
+		            WHEN 6 THEN 'Y'
+		            WHEN 7 THEN 'N'
+		       END
+		     , CASE DAYOFWEEK(#{bizday})
+		            WHEN 1 THEN '휴일'
+		            WHEN 2 THEN NULL
+		            WHEN 3 THEN NULL
+		            WHEN 4 THEN NULL
+		            WHEN 5 THEN NULL
+		            WHEN 6 THEN NULL
+		            WHEN 7 THEN '휴일'
+		       END
+		     , #{regNo}
+		     , NOW()
+		     , #{updNo}
+		     , NOW()
+		)
+	</insert>
+	
+	<!-- 총알배송 영업일 수정 -->
+	<insert id="updateBizday2" parameterType="Bizday">
+		/*  TsaBusiness.updateBizday2 */
+		UPDATE TB_BIZDAY2
+		SET    BIZDAY_YN = (CASE WHEN #{bizdayYn} = 'Y' THEN 'N' ELSE 'Y' END)
+		     , RESTDAY_DESC = (CASE WHEN #{bizdayYn} = 'Y' THEN '휴일' ELSE NULL END)
+		     , UPD_NO = #{updNo}
+		     , UPD_DT = NOW()
+		WHERE  BIZDAY = #{bizday}
+	</insert>
+	
 	<!-- 총알배송 브랜드 등록 -->
 	<insert id="createShotDelvBrand" parameterType="Brand">
 		/*  TsaBusiness.createShotDelvBrand */
@@ -1304,4 +1386,95 @@
 		  AND CD NOT IN ('SBM014','SBM015','SBM016','SBM017','SBM018','SBM019')
 		ORDER BY DISP_ORD
 	</insert>
+	
+	<!-- 공급업체 목록 -->
+	<select id="getSupplyCompanyList2" parameterType="SupplyCompany" resultType="SupplyCompany">
+		/* TsaBusiness.getSupplyCompanyList2 */
+		SELECT SC.SUPPLY_COMP_CD                                       /*공급업체코드*/
+		     , SC.SUPPLY_COMP_NM                                       /*공급업체명*/
+		     , SC.SUPPLY_VENDOR_CD                                     /*공급벤더코드*/
+		     , SV.SUPPLY_VENDOR_NM                                     /*공급벤더명*/
+		     , SV.BIZ_GB                                               /*사업자구분*/
+		     , SV.BIZ_NO                                               /*사업자등록번호*/
+		     , SV.BIZ_KIND                                             /*업종*/
+		     , SV.BIZ_TYPE                                             /*업태*/
+		     , SV.OWNER_NM                                             /*대표자명*/
+		     , SV.BIZ_ZIPCODE                                          /*사업장우편번호*/
+		     , SV.BIZ_BASE_ADDR                                        /*사업장기본주소*/
+		     , SV.BIZ_DTL_ADDR                                         /*사업장상세주소*/
+		     , SV.MAIN_TELNO                                           /*대표전화번호*/
+		     , SV.MAIN_FAXNO                                           /*대표팩스번호*/
+		     , SV.HOMEPAGE_URL                                         /*홈페이지URL*/
+		     , SC.DISTRIBUTION_GB                                      /*유통구분*/
+		     , SC.SHOT_DELV_YN                                         /*총알배송여부*/
+		     , SC.SUPPLY_STAT                                          /*입점상태*/
+		     , FN_GET_CODE_NM('G010',SC.SUPPLY_STAT) AS SUPPLY_STAT_NM /*입점상태명*/
+		     , SC.SELL_FEE_RATE                                        /*판매수수료율*/
+		     , SC.SETTLE_DAY                                           /*정산일*/
+		     , SC.BANK_CD                                              /*은행코드*/
+		     , SC.ACCOUNT_NO                                           /*계좌번호*/
+		     , SC.DEPOSITOR_NM                                         /*예금주명*/
+		     , SC.CS_CHARGE_NM                                         /*CS담당자명*/
+		     , SC.CS_CHARGE_TELNO                                      /*CS담당자전화번호*/
+		     , SC.SETTLE_CHARGE_NM                                     /*정산담당자명*/
+		     , SC.SETTLE_CHARGE_TELNO                                  /*정산담당자전화번호*/
+		     , SC.SETTLE_CHARGE_EMAIL                                  /*정산담당자이메일*/
+		     , SC.BILL_EMAIL                                           /*계산서이메일*/
+		     , SC.ECONTRACT_YN                                         /*전자계약여부*/
+		     , SC.REMARKS                                              /*비고*/
+		     , SC.USE_YN                                               /*사용여부*/
+		     , SC.NOTE                                                 /*배송안내*/
+		FROM   TB_SUPPLY_COMPANY SC
+		     , TB_SUPPLY_VENDOR SV
+		WHERE  SC.SUPPLY_VENDOR_CD = SV.SUPPLY_VENDOR_CD
+		<if test="useYn != null and useYn != ''">
+		AND SC.USE_YN = #{useYn}
+		</if>
+		
+		<if test="supplyStat != null and supplyStat != ''">
+		AND    SC.SUPPLY_STAT = #{supplyStat}
+		</if>
+		<if test="searchTxt != null and searchTxt != ''">
+		    <if test='searchGb == "NAME"'>
+		AND    (
+		        UPPER(SC.SUPPLY_COMP_NM) LIKE CONCAT('%',UPPER(#{searchTxt}),'%')
+		        OR
+		        UPPER(SV.SUPPLY_VENDOR_NM) LIKE CONCAT('%',UPPER(#{searchTxt}),'%')
+		       )
+		    </if>
+		    <if test='searchGb == "OWNER"'>
+		AND    UPPER(SV.OWNER_NM) LIKE CONCAT('%',UPPER(#{searchTxt}),'%')
+		    </if>
+		</if>
+		<if test="econtractYn != null and econtractYn != ''">
+		AND    SC.ECONTRACT_YN = #{econtractYn}
+		</if>
+		<if test="supplyCompCd != null and supplyCompCd != ''"> <!-- 브랜드관리 화면에서 사용 -->
+		AND    SC.SUPPLY_COMP_CD = #{supplyCompCd}
+		</if>
+		<if test="multiSupplyCompCd != null and multiSupplyCompCd.length > 0">
+		AND    SC.SUPPLY_COMP_CD IN
+		    <foreach collection="multiSupplyCompCd" item="item" index="index"  open="(" close=")" separator=",">
+		UPPER(#{item})
+		    </foreach>
+		</if>
+		<if test="multiSupplyCompNm != null and multiSupplyCompNm.length > 0">
+		AND (
+		    <foreach collection="multiSupplyCompNm" item="item" index="index" separator="or">
+		    UPPER(SC.SUPPLY_COMP_NM) LIKE CONCAT('%',UPPER(#{item}),'%')
+		    </foreach>
+		 )
+		</if>
+		<if test='selfYn != null and (selfYn == "Y" or selfYn == "N")'>
+		<choose>
+		    <when test='selfYn  == "Y"'>
+		AND    SC.DISTRIBUTION_GB IN ('G065_10','G065_11','G065_12') 
+		    </when>
+		    <otherwise>
+		AND    SC.DISTRIBUTION_GB IN ('G065_20')
+		    </otherwise>
+		</choose>
+		</if>
+	</select>
+		
 </mapper>

+ 372 - 0
src/main/java/com/style24/persistence/mybatis/shop/TsaDelivery.xml

@@ -1264,4 +1264,376 @@
 	</update>
 
 
+	<!-- 배송목록 건수 -->
+	<select id="getDeliveryListScmCount" parameterType="Delivery" resultType="int">
+		/* TsaDelivery.getDeliveryListScmCount */
+		SELECT COUNT(*) AS TOTCNT
+		  FROM (
+				SELECT A.*
+				  FROM (
+					SELECT
+							  CASE WHEN ORD_DTL_STAT IN('G013_20','G013_30','G013_35','G013_40')
+							       THEN FN_GET_BIZDAYS(IF(A.ORD_EXCH_GB='O',DATE_FORMAT(A.PAY_DT,'%Y%m%d'),DATE_FORMAT(A.WD_EDDT,'%Y%m%d')),DATE_FORMAT(NOW(),'%Y%m%d')) - 1
+							       ELSE NULL END AS DELV_DELAY_DAYS
+							, FN_GET_CODE_NM('G024', (SELECT B.DELV_LOC_CLSF FROM TB_DELIVERY_LOC B WHERE  A.DELV_LOC_CD = B.DELV_LOC_CD AND A.SUPPLY_COMP_CD = B.SUPPLY_COMP_CD ) ) AS DELV_LOC_CLSF  -- 출고처 분류 G024  물류창고, 일반매장, 직송매장, 입점업체
+							, SUPPLY_COMP_NM
+					  FROM (
+							SELECT
+								  A.PAY_DT         -- 결제일시
+								, B.SUPPLY_COMP_CD -- 공급업체
+								, B.ORD_DTL_STAT  -- 주문상세상태
+								, B.DELV_LOC_CD   -- 출고처
+								, (SELECT MAX(CH.WD_EDDT) FROM TB_ORDER_CHANGE CH INNER JOIN TB_ORDER_CHANGE_DETAIL CHD ON CH.ORD_CHG_SQ = CHD.ORD_CHG_SQ WHERE CHD.ORD_DTL_NO =  B.ORG_ORD_DTL_NO) AS WD_EDDT
+					            , B.ORD_EXCH_GB
+					            , (SELECT SUPPLY_COMP_NM FROM TB_SUPPLY_COMPANY S WHERE S.SUPPLY_COMP_CD = B.SUPPLY_COMP_CD) AS SUPPLY_COMP_NM
+							FROM  TB_ORDER A
+							      INNER JOIN TB_ORDER_DETAIL B        ON A.ORD_NO       = B.ORD_NO
+							      INNER JOIN TB_GOODS C               ON B.GOODS_CD     = C.GOODS_CD
+							      INNER JOIN TB_DELIVERY_ADDR D       ON B.DELV_ADDR_SQ = D.DELV_ADDR_SQ
+							      INNER JOIN TB_CUSTOMER CUST         ON A.CUST_NO      = CUST.CUST_NO
+							WHERE 1=1
+							  AND C.SELF_GOODS_YN = 'N'
+							<include refid="getDeliveryListCondition_sql"/>
+					) A
+				) A
+				WHERE 1=1
+				<if test='delvDelayDays != null and delvDelayDays != ""'>
+				<![CDATA[
+				AND A.DELV_DELAY_DAYS >= #{delvDelayDays}
+				]]>
+				</if>
+				<if test='delvLocClsf != null and delvLocClsf != ""'>
+				AND   A.DELV_LOC_CLSF = #{delvLocClsf}
+				</if>
+				<if test='supplyCompSearchTxt != null and supplyCompSearchTxt != ""'>
+				AND   A.SUPPLY_COMP_NM like concat(#{supplyCompSearchTxt},'%') 
+				</if>				
+			) A
+
+	</select>
+
+	<!-- 배송목록 -->
+	<select id="getDeliveryScmList" parameterType="Delivery" resultType="Delivery">
+		/* TsaDelivery.getDeliveryScmList */
+		SELECT Z.*
+		    , FN_GET_CODE_NM('G000', Z.SITE_CD) AS SITE_NM
+			, ( SELECT SELL_STORE_NM
+		      FROM   TB_SELL_STORE
+		      WHERE  SUPPLY_COMP_CD = Z.SUPPLY_COMP_CD
+		      AND    SELL_STORE_CD = Z.SELL_STORE_CD
+		     ) AS SELL_STORE_NM
+		    , FN_GET_CODE_NM('G011', Z.MALL_GB) AS MALL_GB_NM
+		    , CASE WHEN Z.ORD_DTL_STAT = 'G013_99' AND (SELECT MAX(OC.CHG_REASON) FROM TB_ORDER_CHANGE OC JOIN TB_ORDER_CHANGE_DETAIL OCD ON OC.ORD_CHG_SQ = OCD.ORD_CHG_SQ AND OCD.ORD_DTL_NO = Z.ORD_DTL_NO AND OC.CHG_REASON = 'G686_30') IS NOT NULL
+		           THEN '품절취소' ELSE FN_GET_CODE_NM('G013', Z.ORD_DTL_STAT) END  AS ORD_DTL_STAT_NM
+		    , (SELECT B.DELV_LOC_NM FROM TB_DELIVERY_LOC B WHERE  Z.DELV_LOC_CD = B.DELV_LOC_CD AND Z.SUPPLY_COMP_CD = B.SUPPLY_COMP_CD ) AS DELV_LOC_NM   -- 출고처명
+		    , (SELECT BD.BRAND_KNM FROM TB_BRAND BD WHERE BD.BRAND_CD = Z.BRAND_CD ) AS BRAND_NM
+		    , FN_GET_CODE_NM('G056', Z.GOODS_TYPE ) AS GOODS_TYPE_NM
+		    
+		    , IFNULL((SELECT  MAX(SWT_TRC_SEND_YN) FROM TB_ORDER_DETAIL_INVOICE V WHERE V.ORD_NO = Z.ORD_NO AND V.ORD_DTL_NO = Z.ORD_DTL_NO AND V.INVOICE_NO = Z.INVOICE_NO  ),'N') AS INVC_TRACKING
+
+		FROM (
+		    SELECT A.*, ROW_NUMBER() OVER(ORDER BY  A.ORD_NO DESC, A.ORD_DTL_NO) RNUM
+		    FROM (
+				SELECT A.*
+
+				  FROM (
+					SELECT
+							  CASE WHEN ORD_DTL_STAT IN('G013_20','G013_30','G013_35','G013_40')
+							       THEN FN_GET_BIZDAYS(IF(A.ORD_EXCH_GB='O',DATE_FORMAT(A.PAY_DT,'%Y%m%d'),DATE_FORMAT(A.WD_EDDT,'%Y%m%d')),DATE_FORMAT(NOW(),'%Y%m%d')) - 1
+							       ELSE NULL END AS DELV_DELAY_DAYS
+							, (SELECT CUST_ID FROM TB_CUSTOMER CT WHERE CT.CUST_NO= A.CUST_NO ) AS CUST_ID
+							, (SELECT SUPPLY_COMP_NM FROM TB_SUPPLY_COMPANY S WHERE S.SUPPLY_COMP_CD = A.SUPPLY_COMP_CD) AS SUPPLY_COMP_NM
+							, A.ORD_NO     -- 주문번호
+							, A.ORD_DTL_NO -- 주문상세번호
+							, A.SITE_CD    -- 사이트
+							, A.SELL_STORE_CD -- 판매몰
+							, A.EXTMALL_NM  -- 판매몰명
+							, A.ORD_DT         -- 주문일시
+							, A.PAY_DT         -- 결제일시
+							, A.MALL_GB        -- 몰구분
+							, A.ORD_NM         -- 주문자
+							, A.RECIP_NM       -- 수령인
+							, A.SUPPLY_COMP_CD -- 공급업체
+							, A.GOODS_CD       -- 상품코드
+							, A.GOODS_TYPE     -- 구성유형
+							, A.GOODS_NM       -- 상품명
+							, A.OPT_CD1        -- 옵션1
+							, A.OPT_CD2        -- 옵션2
+							, A.OPT_CD         -- SKU
+							, A.SKU_MODEL_NO
+							, A.PRODUCT_NO
+							, A.PRODUCT_CODE
+							, A.ORD_QTY        -- 주문수량
+							, A.CNCL_RTN_QTY   -- 취소수량
+							, A.SALE_QTY       -- 판매수량
+							, A.SALE_AMT       -- 판매금액
+							, A.REAL_ORD_AMT   -- 실결제금액
+							, A.ORD_DTL_STAT   -- 주문상세상태
+							, A.DELV_LOC_CD
+							, A.SHIP_COMP_CD  -- 출고택배사
+							, A.INVOICE_NO    -- 출고송장
+							-- 송장등록수정
+							-- 배송완료처리
+							, A.EXTMALL_ORDER_ID -- 외부몰주문번호
+							, A.AGENT_ORDER_ID   -- 에이전트주문번호
+							, A.SOLDOUT_YN    -- 결품여부
+							, A.DELV_MEMO     -- 배송메모
+							, CASE WHEN A.ORD_EXCH_GB ='E' THEN 'Y' ELSE 'N' END AS ORD_EXCH_GB   -- 교환여부
+							, A.DELV_STDT     -- 배송시작일
+							, A.BRAND_CD      -- 브랜드
+                            , A.CUST_NO
+                            , CASE WHEN A.SHOT_DELV_YN = 'Y' THEN '총알배송' ELSE '일반배송' END AS SHOT_DELV_YN
+				  			, A.PG_GB
+						    , A.PAY_MEANS
+						    , A.BANK_CD
+						    , A.ACCOUNT_NO
+						    , A.ACCOUNT_NM
+						    , A.ORD_PHNNO
+							, A.RECIP_ZIPCODE
+							, A.RECIP_BASE_ADDR
+							, A.RECIP_DTL_ADDR
+					  FROM (
+							SELECT
+								  A.ORD_NO     -- 주문번호
+								, B.ORD_DTL_NO -- 주문상세번호
+								, A.SITE_CD    -- 사이트
+								, B.SELL_STORE_CD -- 판매몰
+								, IFNULL((SELECT MAX(EXTMALL_NM) FROM TB_EXTMALL WHERE VENDOR_ID = B.VENDOR_ID
+								          AND  EXTMALL_ID = B.EXTMALL_ID), '아이스타일24')  AS EXTMALL_NM  -- 판매몰명
+								, A.ORD_DT         -- 주문일시
+								, A.PAY_DT         -- 결제일시
+								, A.MALL_GB        -- 몰구분
+								, A.ORD_NM         -- 주문자
+								, D.RECIP_NM       -- 수령인
+								, B.SUPPLY_COMP_CD -- 공급업체
+								, B.GOODS_CD       -- 상품코드
+								, B.GOODS_TYPE     -- 구성유형
+								, C.GOODS_NM       -- 상품명
+								, ODI.OPT_CD1      -- 옵션1
+								, ODI.OPT_CD2      -- 옵션2
+								, ODI.OPT_CD       -- SKU
+								, ODI.SKU_MODEL_NO
+								, ODI.PRODUCT_NO
+								, ODI.PRODUCT_CODE
+								, ODI.ITEM_QTY * B.ORD_QTY      AS ORD_QTY      -- 주문수량
+								, ODI.ITEM_QTY * B.CNCL_RTN_QTY AS CNCL_RTN_QTY -- 취소수량
+								, (ODI.ITEM_QTY * B.ORD_QTY  - ODI.ITEM_QTY * B.CNCL_RTN_QTY) SALE_QTY -- 판매수량
+								, B.ORD_AMT - B.CNCL_RTN_AMT  AS SALE_AMT       -- 판매금액
+								, B.REAL_ORD_AMT  -- 실결제금액
+								, B.ORD_DTL_STAT  -- 주문상세상태
+								, B.DELV_LOC_CD   -- 출고처
+								, B.SHIP_COMP_CD  -- 출고택배사
+								, B.INVOICE_NO    -- 출고송장
+								, B.EXTMALL_ORDER_ID -- 외부몰주문번호
+								, B.AGENT_ORDER_ID
+								, B.SOLDOUT_YN    -- 결품여부
+								, D.DELV_MEMO     -- 배송메모
+								, B.ORD_EXCH_GB   -- 교환여부
+								, B.DELV_STDT     -- 배송시작일
+								, (SELECT MAX(CH.WD_EDDT) FROM TB_ORDER_CHANGE CH INNER JOIN TB_ORDER_CHANGE_DETAIL CHD ON CH.ORD_CHG_SQ = CHD.ORD_CHG_SQ WHERE CHD.ORD_DTL_NO =  B.ORG_ORD_DTL_NO) AS WD_EDDT
+							    , C.BRAND_CD
+							    , A.CUST_NO
+							    , B.SHOT_DELV_YN
+							    , P.PG_GB
+							    , P.PAY_MEANS
+							    , T.BANK_CD
+							    , T.ACCOUNT_NO
+							    , T.ACCOUNT_NM
+							    , A.ORD_PHNNO
+							    , D.RECIP_ZIPCODE
+							    , D.RECIP_BASE_ADDR
+							    , D.RECIP_DTL_ADDR
+							FROM  TB_ORDER A
+							      INNER JOIN TB_ORDER_DETAIL B        ON A.ORD_NO       = B.ORD_NO
+								  INNER JOIN TB_ORDER_DETAIL_ITEM ODI ON B.ORD_DTL_NO   = ODI.ORD_DTL_NO
+							      INNER JOIN TB_GOODS C               ON ODI.ITEM_CD    = C.GOODS_CD
+							      INNER JOIN TB_DELIVERY_ADDR D       ON B.DELV_ADDR_SQ = D.DELV_ADDR_SQ
+								  INNER JOIN TB_PAYMENT       P       ON A.ORD_NO       = P.ORD_NO  AND P.PAY_STAT = 'G016_30' AND P.PAY_GB = 'O'
+							 LEFT OUTER JOIN TB_CUST_ACCOUNT  T       ON A.CUST_NO      = T.CUST_NO AND T.DEL_YN = 'N' AND T.CUST_NO NOT IN(0)
+							      INNER JOIN TB_CUSTOMER CUST         ON A.CUST_NO      = CUST.CUST_NO
+							WHERE 1=1
+							  AND B.GOODS_TYPE NOT IN ('G056_S')
+							  AND C.SELF_GOODS_YN = 'N'
+					        <include refid="getDeliveryListScmCondition_sql"/>
+
+							UNION ALL
+
+							SELECT
+								  A.ORD_NO     -- 주문번호
+								, B.ORD_DTL_NO -- 주문상세번호
+								, A.SITE_CD    -- 사이트
+								, B.SELL_STORE_CD -- 판매몰
+								, IFNULL((SELECT MAX(EXTMALL_NM) FROM TB_EXTMALL WHERE VENDOR_ID = B.VENDOR_ID
+								          AND  EXTMALL_ID = B.EXTMALL_ID), '아이스타일24')  AS EXTMALL_NM  -- 판매몰명
+								, A.ORD_DT         -- 주문일시
+								, A.PAY_DT         -- 결제일시
+								, A.MALL_GB        -- 몰구분
+								, A.ORD_NM         -- 주문자
+								, D.RECIP_NM       -- 수령인
+								, B.SUPPLY_COMP_CD -- 공급업체
+								, B.GOODS_CD       -- 상품코드
+								, B.GOODS_TYPE     -- 구성유형
+								, C.GOODS_NM       -- 상품명
+								, '-' AS OPT_CD1   -- 옵션1
+								, '-' AS OPT_CD2   -- 옵션2
+								, '-' AS OPT_CD    -- SKU
+								, '-' AS SKU_MODEL_NO
+								, NULL  AS PRODUCT_NO
+								, '-'  AS PRODUCT_CODE
+								, B.ORD_QTY      AS ORD_QTY      -- 주문수량
+								, B.CNCL_RTN_QTY AS CNCL_RTN_QTY -- 취소수량
+								, B.ORD_QTY  - B.CNCL_RTN_QTY   AS SALE_QTY   -- 판매수량
+								, B.ORD_AMT - B.CNCL_RTN_AMT    AS SALE_AMT   -- 판매금액
+								, B.REAL_ORD_AMT  -- 실결제금액
+								, B.ORD_DTL_STAT  -- 주문상세상태
+								, B.DELV_LOC_CD   -- 출고처
+								, B.SHIP_COMP_CD  -- 출고택배사
+								, B.INVOICE_NO    -- 출고송장
+								, B.EXTMALL_ORDER_ID -- 외부몰주문번호
+								, B.AGENT_ORDER_ID
+								, B.SOLDOUT_YN    -- 결품여부
+								, D.DELV_MEMO     -- 배송메모
+								, B.ORD_EXCH_GB   -- 교환여부
+								, B.DELV_STDT     -- 배송시작일
+								, (SELECT MAX(CH.WD_EDDT) FROM TB_ORDER_CHANGE CH INNER JOIN TB_ORDER_CHANGE_DETAIL CHD ON CH.ORD_CHG_SQ = CHD.ORD_CHG_SQ WHERE CHD.ORD_DTL_NO =  B.ORG_ORD_DTL_NO) AS WD_EDDT
+							    , C.BRAND_CD
+							    , A.CUST_NO
+							    , B.SHOT_DELV_YN
+							    , P.PG_GB
+							    , P.PAY_MEANS
+							    , T.BANK_CD
+							    , T.ACCOUNT_NO
+							    , T.ACCOUNT_NM
+							    , A.ORD_PHNNO
+							    , D.RECIP_ZIPCODE
+							    , D.RECIP_BASE_ADDR
+							    , D.RECIP_DTL_ADDR
+							FROM  TB_ORDER A
+							      INNER JOIN TB_ORDER_DETAIL B        ON A.ORD_NO       = B.ORD_NO
+							      INNER JOIN TB_GOODS C               ON B.GOODS_CD     = C.GOODS_CD
+							      INNER JOIN TB_DELIVERY_ADDR D       ON B.DELV_ADDR_SQ = D.DELV_ADDR_SQ
+								  INNER JOIN TB_PAYMENT       P       ON A.ORD_NO       = P.ORD_NO  AND P.PAY_STAT = 'G016_30' AND P.PAY_GB ='O'
+							 LEFT OUTER JOIN TB_CUST_ACCOUNT  T       ON A.CUST_NO      = T.CUST_NO AND T.DEL_YN = 'N' AND T.CUST_NO NOT IN(0)
+							      INNER JOIN TB_CUSTOMER CUST         ON A.CUST_NO      = CUST.CUST_NO
+							WHERE 1=1
+							  AND B.GOODS_TYPE IN ('G056_S')
+							  AND C.SELF_GOODS_YN = 'N'
+							<include refid="getDeliveryListScmCondition_sql"/>
+					) A
+				) A
+				WHERE 1=1
+				<if test='delvDelayDays != null and delvDelayDays != ""'>
+				<![CDATA[
+				AND A.DELV_DELAY_DAYS >= #{delvDelayDays}
+				]]>
+				</if>
+				<if test='supplyCompSearchTxt != null and supplyCompSearchTxt != ""'>
+				AND   A.SUPPLY_COMP_NM like concat(#{supplyCompSearchTxt},'%') 
+				</if>
+				ORDER BY A.ORD_NO DESC, A.ORD_DTL_NO
+	<include refid="getListPagingCondition_sql"/>
+	</select>
+
+    <!-- 배송목록 조회 조건  -->
+	<sql id="getDeliveryListScmCondition_sql">
+		AND  A.MALL_GB = 'G011_10'
+		<if test='supplyCompCd != null and supplyCompCd != ""'>
+		AND B.SUPPLY_COMP_CD = #{supplyCompCd}
+		</if>
+        <if test="multiBrand != null and multiBrand != ''">
+        AND C.BRAND_CD IN
+            <foreach collection="multiBrand" item="item" index="index"  open="(" close=")" separator=",">
+        	#{item}
+            </foreach>
+        </if>
+		<if test='orderNm != null and orderNm != ""'>
+		AND   A.ORD_NM = #{orderNm}
+		</if>
+
+		<if test='orderPhnno != null and orderPhnno != ""'>
+		AND   REPLACE(A.ORD_PHNNO, '-', '') = REPLACE(#{orderPhnno}, '-', '')
+		</if>
+		<if test='ordDtlNo != null and ordDtlNo != ""'>
+		AND   B.ORD_DTL_NO = #{ordDtlNo}
+		</if>
+		<if test='conditions != null and conditions != "" '>
+		AND (
+		<choose>
+		     <when test='search != null and search == "searchOrdNo"'>
+		         A.ORD_NO IN
+		          <foreach collection="conditions" item="item" index="index"  open="(" close=")" separator=",">
+		      		#{item}
+		         </foreach>
+
+		     </when>
+		     <when test='search != null and search == "searchExtmallOrderId"'>
+		         B.EXTMALL_ORDER_ID IN
+		         <foreach collection="conditions" item="item" index="index"  open="(" close=")" separator=",">
+		      		#{item}
+		         </foreach>
+		      </when>
+		     <when test='search != null and search == "searchCustId"'>
+		         CUST.CUST_ID IN
+		         <foreach collection="conditions" item="item" index="index"  open="(" close=")" separator=",">
+		      		#{item}
+		         </foreach>
+		      </when>
+		</choose>
+		      )
+		</if>
+		
+		<if test="multiSupplyCompCd != null and multiSupplyCompCd != ''">
+		       AND B.SUPPLY_COMP_CD IN
+			<foreach collection="multiSupplyCompCd" item="item" index="index"  open="(" close=")" separator=",">
+		           #{item}
+			</foreach>
+		</if>
+				
+		<if test='recipNm != null and recipNm != ""'>
+		AND   D.RECIP_NM = #{recipNm}
+		</if>
+		<if test='invoiceNo != null and invoiceNo != ""'>
+		AND   B.INVOICE_NO = #{invoiceNo}
+		</if>
+		<if test='goodsCd != null and goodsCd != ""'>
+		AND   C.GOODS_CD = #{goodsCd}
+		</if>
+
+		<if test="multiOrdDtlStat != null and multiOrdDtlStat !=''">
+		AND  B.ORD_DTL_STAT IN
+		    <foreach collection="multiOrdDtlStat" item="item" index="index"  open="(" close=")" separator=",">
+		     #{item}
+		    </foreach>
+		</if>
+		<if test='termGb == "ordDt"'>
+		    <if test='stDate != null and stDate != ""'>
+		AND   A.ORD_DT >= STR_TO_DATE(REPLACE(#{stDate},'-',''), '%Y%m%d%H%i%s')
+		    </if>
+		    <if test='edDate != null and edDate != ""'>
+		AND   A.ORD_DT <![CDATA[<]]> DATE_ADD(STR_TO_DATE(REPLACE(#{edDate},'-',''), '%Y%m%d%H%i%s'), INTERVAL 1 DAY)
+		    </if>
+		</if>
+		<if test='termGb == "delvDt"'>
+		    <if test='stDate != null and stDate != ""'>
+		AND   B.DELV_EDDT >= STR_TO_DATE(REPLACE(#{stDate},'-',''), '%Y%m%d%H%i%s')
+		    </if>
+		    <if test='edDate != null and edDate != ""'>
+		AND   B.DELV_EDDT <![CDATA[<]]> DATE_ADD(STR_TO_DATE(REPLACE(#{edDate},'-',''), '%Y%m%d%H%i%s'), INTERVAL 1 DAY)
+		    </if>
+		</if>
+		<if test='termGb == "delvStDt"'>
+		    <if test='stDate != null and stDate != ""'>
+		AND   B.DELV_STDT >= STR_TO_DATE(REPLACE(#{stDate},'-',''), '%Y%m%d%H%i%s')
+		    </if>
+		    <if test='edDate != null and edDate != ""'>
+		AND   B.DELV_STDT <![CDATA[<]]> DATE_ADD(STR_TO_DATE(REPLACE(#{edDate},'-','') , '%Y%m%d%H%i%s'), INTERVAL 1 DAY)
+		    </if>
+		</if>
+		<if test='custId != null and custId != ""'>
+		AND   CUST.CUST_ID = #{custId}
+		</if>
+		AND B.ORD_DTL_STAT != 'G013_00'
+	</sql>
+
+
 </mapper>

+ 31 - 8
src/main/java/com/style24/persistence/mybatis/shop/TsaGoods.xml

@@ -3124,6 +3124,29 @@
 		</if>
 	</select>
 
+	<!-- 상품옵션 패턴조회 // 20210929 eskim (안전인증)-->
+	<select id="getGoodsOption" parameterType="Option" resultType="Option">
+		/* TssGoods.getGoodsOption */
+		SELECT GOODS_CD
+		     , OPT_CD
+		     , OPT_CD1
+		     , OPT_CD2
+		FROM TB_OPTION
+		WHERE  GOODS_CD = #{goodsCd}
+		ORDER BY DISP_ORD
+		LIMIT 1
+	</select>
+
+	<!-- 상품옵션 중복건수여부 확인 // 20210929 eskim (안전인증)-->
+	<select id="getGoodsOptionDupCountCheck" parameterType="Option" resultType="int">
+		/* TssGoods.getGoodsOptionDupCountCheck */
+		SELECT COUNT(*)
+		FROM TB_OPTION
+		WHERE  GOODS_CD = #{goodsCd}
+		AND OPT_CD1 = #{optCd1}
+		AND OPT_CD2 = #{optCd2}
+	</select>
+
 	<!-- 상품 가격 승인 목록 -->
 	<select id="getGoodsSupplyPriceList"  parameterType="GoodsSupplyPrice" resultType="GoodsSupplyPrice">
 		/* TsaGoods.getGoodsSupplyPriceList */
@@ -3968,7 +3991,7 @@
 			       UPPER(G.PRODUCT_CODE) LIKE CONCAT(UPPER(#{item}),'%')
 			      </foreach>
 			     )
-			      </when>			      
+			      </when>
 			      <otherwise>
 			AND 1 = 1
 			      </otherwise>
@@ -4015,7 +4038,7 @@
 			AND 1 = 1
 			      </otherwise>
 			    </choose>
-			</if>		
+			</if>
 		ORDER BY G.PRODUCT_NO DESC
 	</select>
 
@@ -5149,7 +5172,7 @@
 		        </foreach>
 		     )
 		     </if>
-		     
+
 		    <if test='conditionList2 != null and conditionList2.length>0'>
 		    AND (
 		        <foreach collection="conditionList2" item="item2" index="index" separator="or">
@@ -5157,7 +5180,7 @@
 		        </foreach>
 		     )
 		     </if>
-		     
+
 		    <if test='conditionList3 != null and conditionList3.length>0'>
 		    AND (
 		        <foreach collection="conditionList3" item="item3" index="index" separator="or">
@@ -5165,7 +5188,7 @@
 		        </foreach>
 		     )
 		     </if>
-		     		     
+
 	</select>
 
 	<!-- WMS입고단품목록 -->
@@ -5219,7 +5242,7 @@
 		              </foreach>
 		           )
 		           </if>
-		           
+
 				    <if test='conditionList2 != null and conditionList2.length>0'>
 				    AND (
 				        <foreach collection="conditionList2" item="item2" index="index" separator="or">
@@ -5227,14 +5250,14 @@
 				        </foreach>
 				     )
 				     </if>
-				     
+
 				    <if test='conditionList3 != null and conditionList3.length>0'>
 				    AND (
 				        <foreach collection="conditionList3" item="item3" index="index" separator="or">
 				       Z.SKUCODE LIKE CONCAT(UPPER(#{item3}),'%')
 				        </foreach>
 				     )
-				     </if>		           
+				     </if>
 		            ORDER BY LOTNO, DATEINCOME, SKUCODE
 		          ) Q
 		LIMIT #{pageable.limitStartRow} ,  #{pageable.pageSize}

+ 15 - 3
src/main/java/com/style24/persistence/mybatis/shop/TsaPlan.xml

@@ -45,14 +45,20 @@
 		     , REG_DT                
 		     , UPD_NO                
 		     , UPD_DT                
-		   ) VALUES (
+		) VALUES (
 		       #{planSq}
 		     , #{planNm}
 		     , #{planGb}
 		     , #{siteCd}
 		     , #{frontGb}
+		<if test='planGb == "C"'>
+		     , DATE_FORMAT(#{startSearchDate} , '%Y-%m-01 %H:%i:%s')
+		     , DATE_FORMAT(LAST_DAY(#{startSearchDate}) , '%Y-%m-%d 23:59:59')
+		</if>
+		<if test='planGb != "C"'>
 		     , DATE_FORMAT(#{dispStdt} , '%Y-%m-%d %H:%i:%s')
 		     , DATE_FORMAT(#{dispEddt} , '%Y-%m-%d %H:%i:%s')
+		</if>
 		     , #{mainPimg}
 		     , #{mainMimg}
 		     , #{dtlPimg}
@@ -79,9 +85,9 @@
 		     , #{badgeFcolor}
 		     , #{badgeBcolor}
 		     , #{regNo}
-		     , now() 
+		     , NOW()
 		     , #{updNo}
-		     , now()
+		     , NOW()
 		)
 	</insert>
 	
@@ -298,8 +304,14 @@
 		   SET PLAN_GB = #{planGb}
 		     , FRONT_GB = #{frontGb}
 		     , PLAN_NM = #{planNm}
+		    <if test='planGb == "C"'>
+		     , DISP_STDT = DATE_FORMAT(#{startSearchDate} , '%Y-%m-01 %H:%i:%s')
+		     , DISP_EDDT =DATE_FORMAT(LAST_DAY(#{startSearchDate}) , '%Y-%m-%d 23:59:59')
+		    </if>
+		    <if test='planGb != "C"'>
 		     , DISP_STDT = DATE_FORMAT(#{dispStdt} , '%Y-%m-%d %H:%i:%s')
 		     , DISP_EDDT = DATE_FORMAT(#{dispEddt} , '%Y-%m-%d %H:%i:%s')
+		     </if>
 		     , CORNER_NM_DISP_YN = #{cornerNmDispYn}
 		     , OPEN_YN = #{openYn}
 		     , SITE_CD = #{siteCd}

+ 870 - 43
src/main/java/com/style24/persistence/mybatis/shop/TsaStatistics.xml

@@ -1193,7 +1193,7 @@
 		    , CPN_NM -- 쿠폰명
 		    , BURDEN -- 자사분담율
 		    , DOWN_CNT
-		    , FLOOR(USE_CNT / DOWN_CNT * 100 * 10) / 10 AS USE_RATE -- 사용율
+			, ROUND((USE_CNT / DOWN_CNT) * 100 * 100) / 10 / 10 AS USE_RATE
 		    , USE_CNT -- 사용수
 		    , ORD_AMT -- 주문금액
 		    , CPN_AMT -- 쿠폰비용
@@ -1231,7 +1231,7 @@
 		    , Z.ORD_QTY
 		    , Z.CUST_CNT
 		    , X.CUST_CPN_CNT
-		    , FLOOR((X.CUST_CPN_CNT / Z.CUST_CNT * 100) / 10) * 10 AS ORD_RATE
+			, ROUND((X.CUST_CPN_CNT / Z.CUST_CNT * 100 * 100) / 10) / 10 AS ORD_RATE
 		FROM (
 		     SELECT
 		        A.BRAND_CD
@@ -1339,21 +1339,23 @@
 		      ]]>
 		      AND B.ORD_DTL_STAT NOT IN ('G013_00', 'G013_10', 'G013_98')               -- 주문접수,입금대기,입금전취소 제외
 		      AND B.ORD_QTY > B.CNCL_RTN_QTY
-              <if test="applyGbArr == null">
-	              /* 프로모션유형값없을시 */
-			      AND (B.TMTB1_DC_AMT + B.TMTB2_DC_AMT) > 0
-              </if>
-	          <if test="applyGbArr != null">
-	              /* 프로모션유형 */
-	              <foreach collection="applyGbArr" item="item" index="index">
-	                  <if test='item == "G810_10"'>
-	                      AND TMTB1_DC_AMT > 0 -- 수량
-	                  </if>
-	                  <if test='item == "G810_11"'>
-	                      AND TMTB2_DC_AMT > 0 -- 금액
-	                  </if>
-	              </foreach>
-	          </if>
+              <choose>
+				  <when test="applyGbArr != null and applyGbArr != ''">
+					  /* 프로모션유형 */
+					  <foreach collection="applyGbArr" item="item" index="index">
+						  <if test='item == "G810_10"'>
+							  AND TMTB1_DC_AMT > 0 -- 수량
+						  </if>
+						  <if test='item == "G810_11"'>
+							  AND TMTB2_DC_AMT > 0 -- 금액
+						  </if>
+					  </foreach>
+				  </when>
+		    	<otherwise>
+					/* 프로모션유형값없을시 */
+					AND (B.TMTB1_DC_AMT + B.TMTB2_DC_AMT) > 0
+				</otherwise>
+			  </choose>
 		)
 		-- 수량할인
 		, TMTB1 AS (
@@ -1468,7 +1470,7 @@
 		GROUP BY A.BRAND_CD, B.BRAND_ENM, A.GOODS_CD
 	</select>
 
-	<!-- 사은품 주문조회 -->
+	<!-- 기획전 주문조회 -->
 	<select id="getPlanOrderList" parameterType="Statistics" resultType="Statistics">
 	    /* TsaStatistics.getPlanOrderList */
 		SELECT
@@ -1501,18 +1503,18 @@
 		      ]]>
 		      AND B.ORD_DTL_STAT NOT IN ('G013_00', 'G013_10', 'G013_98')               -- 주문접수,입금대기,입금전취소 제외
 		      AND B.ORD_QTY > B.CNCL_RTN_QTY
-	          <if test="multiDistributionGb != null">
-	              /* 물류구분 */
-	              <foreach collection="multiDistributionGb" item="item" index="index">
-	                  <if test="item == 'SCM'">
-	                      AND C.DISTRIBUTION_GB = 'G065_20' -- 입점
-	                  </if>
-	                  <if test="item == 'WMS'">
-		                  AND C.DISTRIBUTION_GB IN ('G065_10', 'G065_11', 'G065_12') -- 위탁
-	                  </if>
-	              </foreach>
-	          </if>
-		      <if test="multiTmtbSq != null">
+		      <choose>
+				  <when test="distributionGbS != null and distributionGbS !='' and distributionGbW != null and distributionGbW !=''">
+					  AND C.DISTRIBUTION_GB IN ('G065_10', 'G065_11', 'G065_12', 'G065_20')
+				  </when>
+				  <when test="distributionGbW != null and distributionGbW !=''">
+					  AND C.DISTRIBUTION_GB IN ('G065_10', 'G065_11', 'G065_12')
+				  </when>
+				  <when test="distributionGbS != null and distributionGbS !=''">
+					  AND C.DISTRIBUTION_GB = 'G065_20'
+				  </when>
+			  </choose>
+		      <if test="multiPlanSq != null">
 		          /* 기획전번호  */
 		          <foreach collection="multiPlanSq" item="item" index="index"  open="AND E.PLAN_SQ IN (" close=")" separator=",">#{item}</foreach>
 		      </if>
@@ -1521,7 +1523,7 @@
 		GROUP BY DISTRIBUTION_GB, BRAND_ENM, PLAN_SQ
 	</select>
 
-	<!-- 사은품 주문상세 조회 -->
+	<!-- 기획전 주문상세 조회 -->
 	<select id="getPlanOrderDetailList" parameterType="Statistics" resultType="Statistics">
 	    /* TsaStatistics.getPlanOrderDetailList */
 		WITH TAB AS (
@@ -1556,7 +1558,7 @@
 		    , SUM(ORD_AMT) AS ORD_AMT
 		    , SUM(ORD_QTY) AS ORD_QTY
 		    , SUM(CUST_CNT) AS CUST_CNT
-		    , FLOOR((SUM(CUST_CNT) / (SELECT TOT_CUST_CNT FROM TAB) * 100) / 10) * 10 AS ORD_RATE
+		    , ROUND((SUM(CUST_CNT) / (SELECT TOT_CUST_CNT FROM TAB) * 100 * 100) / 10) / 10 AS ORD_RATE
 		FROM (
 		     SELECT C.DISTRIBUTION_GB
 		         , C.GOODS_CD
@@ -1581,17 +1583,6 @@
 		      ]]>
 		      AND B.ORD_DTL_STAT NOT IN ('G013_00', 'G013_10', 'G013_98')               -- 주문접수,입금대기,입금전취소 제외
 		      AND B.ORD_QTY > B.CNCL_RTN_QTY
-              <if test="multiDistributionGb != null">
-                  /* 물류구분 */
-                  <foreach collection="multiDistributionGb" item="item" index="index">
-                      <if test="item == 'SCM'">
-                          AND C.DISTRIBUTION_GB = 'G065_20' -- 입점
-                      </if>
-                      <if test="item == 'WMS'">
-                          AND C.DISTRIBUTION_GB IN ('G065_10', 'G065_11', 'G065_12') -- 위탁
-                      </if>
-                  </foreach>
-              </if>
 		      AND E.PLAN_SQ = #{planSq}
 		    GROUP BY C.DISTRIBUTION_GB, C.GOODS_CD, C.GOODS_NM, A.CUST_NO
 		) X
@@ -1882,4 +1873,840 @@
 		GROUP BY DAY
 	</select>
 
+	<!-- 부결제수단별통계 목록 -->
+	<select id="getSubPaymentList" parameterType="Statistics" resultType="Statistics">
+		/* TsaStatistics.getSubPaymentList */
+		SELECT
+		<choose>
+			<when test='dayGb == "W"'> <!-- 주별 -->
+				CONCAT(MONTH(DAY), '월 ', WEEK(DAY,5) - WEEK(DATE_SUB(DAY, INTERVAL DAYOFMONTH(DAY) - 1 DAY), 5) + 1, '주') AS DAY
+			</when>
+			<when test='dayGb == "M"'> <!-- 월별 -->
+				DATE_FORMAT(DAY,'%Y-%m')                          AS DAY
+			</when>
+			<otherwise> <!-- 일별 -->
+				DATE_FORMAT(DAY,'%Y-%m-%d')                       AS DAY
+			</otherwise>
+		</choose>
+			, SUM(A.PNT_GIVE) AS PNT_GIVE -- 포인트적립액
+			, SUM(A.PNT_ORD_CNT) AS PNT_ORD_CNT -- 포인트사용주문수
+			, SUM(A.PNT_USE) AS PNT_USE -- 포인트사용액
+			, SUM(A.GIFT_REG_CNT) AS GIFT_REG_CNT -- 상품권등록매수
+			, SUM(A.GIFT_ORD_CNT) AS GIFT_ORD_CNT -- 상품권주문수
+			, SUM(A.GIFT_USE) AS GIFT_USE -- 상품권사용액
+		FROM TB_STAT_SUB_PAY A
+		WHERE A.DAY <![CDATA[>=]]> STR_TO_DATE(#{startDt},'%Y-%m-%d')
+		  AND A.DAY <![CDATA[<]]> DATE_ADD(STR_TO_DATE(#{endDt},'%Y-%m-%d'), INTERVAL 1 DAY)
+		<choose>
+			<when test='pointGb != null and pointGb != "" and giftCardGb != null and giftCardGb != ""'>
+				AND OCCUR_GB IN(#{pointGb}, #{giftCardGb})
+			</when>
+			<when test='pointGb != null and pointGb != ""'>
+				AND OCCUR_GB = #{pointGb}
+			</when>
+			<when test='giftCardGb != null and giftCardGb != ""'>
+				AND OCCUR_GB = {giftCardGb}
+			</when>
+		</choose>
+		<choose>
+			<when test='dayGb == "W"'> <!-- 주별 -->
+				GROUP  BY CONCAT(MONTH(DAY), '월 ', WEEK(DAY,5) - WEEK(DATE_SUB(DAY, INTERVAL DAYOFMONTH(DAY) - 1 DAY), 5) + 1, '주')
+			</when>
+			<when test='dayGb == "M"'> <!-- 월별 -->
+				GROUP  BY DATE_FORMAT(DAY,'%Y-%m')
+			</when>
+			<otherwise> <!-- 일별 -->
+				GROUP  BY DATE_FORMAT(DAY,'%Y-%m-%d')
+			</otherwise>
+		</choose>
+	</select>
+
+	<!-- 포인트잔액 -->
+	<select id="getRemainPoint" resultType="java.lang.Long">
+		/* TsaStatistics.getRemainPoint */
+		SELECT
+			SUM(RM_PNT_AMT) AS RM_PNT_AMT
+		FROM TB_CUST_POINT A
+		WHERE A.EXP_CMP_DT IS NULL
+	</select>
+
+	<!-- 포인트잔액 -->
+	<select id="getRemainGiftCard" resultType="java.lang.Long">
+		/* TsaStatistics.getRemainGiftCard */
+		SELECT
+		SUM(RM_GFCD_AMT) AS RM_GFCD_AMT
+		FROM TB_CUST_GIFTCARD A
+		WHERE DATE_FORMAT(USE_EXP_DATE, '%Y%m%d') &lt; NOW()
+	</select>
+
+	<!-- 가입통계 -->
+	<select id="getCustomerJoinList" parameterType="Statistics" resultType="Statistics">
+		/* TsaStatistics.getCustomerJoinList */
+		SELECT
+	<choose>
+		<when test='dayGb == "W"'> <!-- 주별 -->
+			CONCAT(MONTH(DAY), '월 ', WEEK(DAY,5) - WEEK(DATE_SUB(DAY, INTERVAL DAYOFMONTH(DAY) - 1 DAY), 5) + 1, '주') AS DAY
+		</when>
+		<when test='dayGb == "M"'> <!-- 월별 -->
+			DATE_FORMAT(DAY,'%Y-%m')                          AS DAY
+		</when>
+		<otherwise> <!-- 일별 -->
+			DATE_FORMAT(DAY,'%Y-%m-%d')                       AS DAY
+		</otherwise>
+	</choose>
+			, MAX(ALL_CNT) AS ALL_CNT
+			, MAX(REAL_CNT) AS REAL_CNT
+			, MAX(DORM_CNT) AS DORM_CNT
+			, MAX(VIP_CNT) AS VIP_CNT
+			, MAX(GOLD_CNT) AS GOLD_CNT
+			, MAX(SILVER_CNT) AS SILVER_CNT
+			, MAX(BRONZE_CNT) AS BRONZE_CNT
+			, MAX(WELCOME_CNT) AS WELCOME_CNT
+			, SUM(JOIN_CNT) AS JOIN_CNT
+			, SUM(DR_JOIN_CNT) AS DR_JOIN_CNT
+			, SUM(AF_JOIN_CNT) AS AF_JOIN_CNT
+			, SUM(CHG_DORM_CNT) AS CHG_DORM_CNT
+			, SUM(RM_DORM_CNT) AS RM_DORM_CNT
+			, SUM(SECEED_CNT) AS SECEED_CNT
+		FROM TB_STAT_CUST
+		WHERE DAY <![CDATA[>=]]> STR_TO_DATE(#{startDt},'%Y-%m-%d')
+		  AND DAY <![CDATA[<]]> DATE_ADD(STR_TO_DATE(#{endDt},'%Y-%m-%d'), INTERVAL 1 DAY)
+	<if test="multiSexGb != null">
+		/* 성별구분 */
+		<foreach collection="multiSexGb" item="item" index="index"  open="AND SEX_GB IN (" close=")" separator=",">#{item}</foreach>
+	</if>
+	<if test="multiAgeGb != null">
+		/* 연령구분 */
+		<foreach collection="multiAgeGb" item="item" index="index"  open="AND AGE IN (" close=")" separator=",">#{item}</foreach>
+	</if>
+	<choose>
+		<when test='dayGb == "W"'> <!-- 주별 -->
+			GROUP  BY CONCAT(MONTH(DAY), '월 ', WEEK(DAY,5) - WEEK(DATE_SUB(DAY, INTERVAL DAYOFMONTH(DAY) - 1 DAY), 5) + 1, '주')
+		</when>
+		<when test='dayGb == "M"'> <!-- 월별 -->
+			GROUP  BY DATE_FORMAT(DAY,'%Y-%m')
+		</when>
+		<otherwise> <!-- 일별 -->
+			GROUP  BY DATE_FORMAT(DAY,'%Y-%m-%d')
+		</otherwise>
+	</choose>
+		ORDER BY DAY DESC
+	</select>
+
+	<!-- 등급별주문현황 -->
+	<select id="getCustomerGradOrderList" parameterType="Statistics" resultType="Statistics">
+		/* TsaStatistics.getCustomerGradOrderList */
+		SELECT
+			CASE WHEN A.CUST_GRADE = 'G110_10' THEN 1
+				WHEN A.CUST_GRADE = 'G110_20' THEN 2
+				WHEN A.CUST_GRADE = 'G110_30' THEN 3
+				WHEN A.CUST_GRADE = 'G110_40' THEN 4
+				WHEN A.CUST_GRADE = 'G110_50' THEN 5
+			ELSE 6 END AS PRIORITY
+			, FN_GET_CODE_NM('G110', A.CUST_GRADE) AS CUST_GRADE
+			, SUM(A.ORD_AMT - A.CNCL_AMT - A.RTN_AMT) AS TOT_ORD_AMT -- 총매출액
+			, SUM(A.ORD_AMT) AS ORD_AMT -- 매출액
+			, SUM(A.CNCL_AMT + A.RTN_AMT) AS CNCL_AMT -- 취/반품액
+			, SUM(A.ORD_CNT) AS ORD_CNT -- 주문수
+			, SUM(A.CNCL_QTY + A.RTN_QTY) AS CNCL_QTY -- 취/반품갯수
+			, ROUND(CEIL(AVG(A.ORD_CNT) * 10) / 10, 1) AS AVG_ORD_CNT -- 평균주문수
+			, ROUND(CEIL(AVG(A.SELL_QTY) * 10) / 10, 1) AS AVG_SELL_QTY -- 평균주문상품개수
+			, FLOOR(SUM(A.ORD_AMT) / SUM(A.ORD_CNT)) AS CUST_PRICE -- 객단가
+		FROM TB_STAT_CUST_ORD A
+		WHERE DAY <![CDATA[>=]]> STR_TO_DATE(#{startDt},'%Y-%m-%d')
+			AND DAY <![CDATA[<]]> DATE_ADD(STR_TO_DATE(#{endDt},'%Y-%m-%d'), INTERVAL 1 DAY)
+		<if test="multiFrontGb != null">
+			/* 디바이스 */
+			<foreach collection="multiFrontGb" item="item" index="index"  open="AND FRONT_GB IN (" close=")" separator=",">#{item}</foreach>
+		</if>
+		<if test="multiSexGb != null">
+			/* 성별구분 */
+			<foreach collection="multiSexGb" item="item" index="index"  open="AND SEX_GB IN (" close=")" separator=",">#{item}</foreach>
+		</if>
+		<if test="multiAgeGb != null">
+			/* 연령구분 */
+			<foreach collection="multiAgeGb" item="item" index="index"  open="AND AGE IN (" close=")" separator=",">#{item}</foreach>
+		</if>
+		<if test="multiBrandCd != null">
+			/* 브랜드 */
+			<foreach collection="multiBrandCd" item="item" index="index"  open="AND BRAND_CD IN (" close=")" separator=",">#{item}</foreach>
+		</if>
+		<if test="multiItemkindCd != null">
+			/* 품목 */
+			<foreach collection="multiItemkindCd" item="item" index="index"  open="AND ITEMKIND_CD IN (" close=")" separator=",">#{item}</foreach>
+		</if>
+		GROUP BY A.CUST_GRADE
+		ORDER BY PRIORITY
+	</select>
+
+	<!-- 등급별주문현황 -->
+	<select id="getCustomerAgeOrderList" parameterType="Statistics" resultType="Statistics">
+		/* TsaStatistics.getCustomerAgeOrderList */
+		SELECT
+			CASE WHEN A.AGE != 'X' THEN CONCAT(A.AGE, '대') ELSE '50대이상/기타' END AS AGE
+			, FN_GET_CODE_NM('G007', A.SEX_GB) AS SEX_GB
+			, SUM(A.ORD_AMT - A.CNCL_AMT - A.RTN_AMT) AS TOT_ORD_AMT -- 총매출액
+			, SUM(A.ORD_AMT) AS ORD_AMT -- 매출액
+			, SUM(A.CNCL_AMT + A.RTN_AMT) AS CNCL_AMT -- 취/반품액
+			, SUM(A.ORD_CNT) AS ORD_CNT -- 주문수
+			, SUM(A.CNCL_QTY + A.RTN_QTY) AS CNCL_QTY -- 취/반품갯수
+			, ROUND(CEIL(AVG(A.ORD_CNT) * 10) / 10, 1) AS AVG_ORD_CNT -- 평균주문수
+			, ROUND(CEIL(AVG(A.SELL_QTY) * 10) / 10, 1) AS AVG_SELL_QTY -- 평균주문상품개수
+			, FLOOR(SUM(A.ORD_AMT) / SUM(A.ORD_CNT)) AS CUST_PRICE -- 객단가
+		FROM TB_STAT_CUST_ORD A
+		WHERE DAY <![CDATA[>=]]> STR_TO_DATE(#{startDt},'%Y-%m-%d')
+			AND DAY <![CDATA[<]]> DATE_ADD(STR_TO_DATE(#{endDt},'%Y-%m-%d'), INTERVAL 1 DAY)
+		<if test="multiFrontGb != null">
+			/* 디바이스 */
+			<foreach collection="multiFrontGb" item="item" index="index"  open="AND FRONT_GB IN (" close=")" separator=",">#{item}</foreach>
+		</if>
+		<if test="multiGradeGb != null">
+			/* 등급 */
+			<foreach collection="multiGradeGb" item="item" index="index"  open="AND CUST_GRADE IN (" close=")" separator=",">#{item}</foreach>
+		</if>
+		<if test="multiBrandCd != null">
+			/* 브랜드 */
+			<foreach collection="multiBrandCd" item="item" index="index"  open="AND BRAND_CD IN (" close=")" separator=",">#{item}</foreach>
+		</if>
+		<if test="multiItemkindCd != null">
+			/* 품목 */
+			<foreach collection="multiItemkindCd" item="item" index="index"  open="AND ITEMKIND_CD IN (" close=")" separator=",">#{item}</foreach>
+		</if>
+		GROUP BY A.AGE, A.SEX_GB
+		ORDER BY A.AGE, A.SEX_GB
+	</select>
+
+	<!-- 구매자랭킹 -->
+	<select id="getCustomerRankingList" parameterType="Statistics" resultType="Statistics">
+		/* TsaStatistics.getCustomerRankingList */
+		WITH TAB AS (
+			SELECT *
+			FROM (
+			SELECT A.ORD_NO
+				, B.ORD_DTL_NO
+				, B.ORD_QTY
+				, B.CNCL_RTN_QTY
+				, B.ORD_AMT
+				, B.CNCL_RTN_AMT
+				, B.CPN1_DC_AMT
+				, A.PAY_DT
+				, A.FRONT_GB
+				, C.ITEMKIND_CD
+				, C.BRAND_CD
+				, E.CUST_NO
+				, E.CUST_GRADE
+				, RANK() OVER (PARTITION BY B.ORD_DTL_NO ORDER BY B.ORD_DTL_HST_SQ) AS RNK
+			FROM TB_ORDER A,
+				TB_ORDER_DETAIL_HST B,
+				TB_GOODS C,
+				TB_CUSTOMER E
+			WHERE A.ORD_NO = B.ORD_NO
+				AND B.GOODS_CD = C.GOODS_CD
+				AND A.CUST_NO = E.CUST_NO
+				AND A.PAY_DT >= STR_TO_DATE(#{startDt},'%Y-%m-%d')                         -- 시작일변수
+				AND A.PAY_DT <![CDATA[<]]> DATE_ADD(STR_TO_DATE(#{endDt},'%Y-%m-%d'), INTERVAL 1 DAY) -- 종료일변수
+				AND E.CUST_NO > 0
+				AND A.MALL_GB = 'G011_10'
+				AND B.ORD_EXCH_GB = 'O'
+				AND B.ORD_DTL_STAT = 'G013_20' -- 결제완료
+		<if test="multiFrontGb != null">
+			/* 디바이스 */
+			<foreach collection="multiFrontGb" item="item" index="index"  open="AND A.FRONT_GB IN (" close=")" separator=",">#{item}</foreach>
+		</if>
+		<if test="multiSexGb != null">
+			/* 성별구분 */
+			<foreach collection="multiSexGb" item="item" index="index"  open="AND FN_DEC_AES(E.SEX_GB) IN (" close=")" separator=",">#{item}</foreach>
+		</if>
+		<if test="multiAgeGb != null">
+			/* 연령구분 */
+			<foreach collection="multiAgeGb" item="item" index="index"  open="AND CASE WHEN FN_DEC_AES(E.BIRTH_YMD) = '' OR FN_DEC_AES(E.BIRTH_YMD) IS NULL THEN 'X'
+				WHEN (DATE_FORMAT(NOW(), '%Y') - DATE_FORMAT(CONCAT(SUBSTRING(FN_DEC_AES(E.BIRTH_YMD), 1, 4), '0101'), '%Y') + 1) BETWEEN 10 AND 19 THEN '10'
+				WHEN (DATE_FORMAT(NOW(), '%Y') - DATE_FORMAT(CONCAT(SUBSTRING(FN_DEC_AES(E.BIRTH_YMD), 1, 4), '0101'), '%Y') + 1) BETWEEN 20 AND 29 THEN '20'
+				WHEN (DATE_FORMAT(NOW(), '%Y') - DATE_FORMAT(CONCAT(SUBSTRING(FN_DEC_AES(E.BIRTH_YMD), 1, 4), '0101'), '%Y') + 1) BETWEEN 30 AND 39 THEN '30'
+				WHEN (DATE_FORMAT(NOW(), '%Y') - DATE_FORMAT(CONCAT(SUBSTRING(FN_DEC_AES(E.BIRTH_YMD), 1, 4), '0101'), '%Y') + 1) BETWEEN 40 AND 49 THEN '40'
+				ELSE 'X' END IN (" close=")" separator=",">#{item}</foreach>
+		</if>
+		<if test="multiBrandCd != null">
+			/* 브랜드 */
+			<foreach collection="multiBrandCd" item="item" index="index"  open="AND BRAND_CD IN (" close=")" separator=",">#{item}</foreach>
+		</if>
+		<if test="multiItemkindCd != null">
+			/* 품목 */
+			<foreach collection="multiItemkindCd" item="item" index="index"  open="AND ITEMKIND_CD IN (" close=")" separator=",">#{item}</foreach>
+		</if>
+			) A
+			WHERE RNK = 1
+		)
+		-- 판매수
+		, TAB_SELL_QTY AS (
+			SELECT
+				SUM(ORD_QTY) AS VAL
+				, '1' AS GBN
+				, CUST_NO
+			FROM TAB
+			GROUP BY CUST_NO
+		)
+		-- 매출
+		, TAB_ORD AS (
+			SELECT
+				SUM(ORD_AMT + CPN1_DC_AMT + (SELECT SUM(OPT_ADD_PRICE * ITEM_QTY) FROM TB_ORDER_DETAIL_ITEM X WHERE X.ORD_DTL_NO = A.ORD_DTL_NO)) AS VAL
+				, '2' AS GBN
+				, CUST_NO
+			FROM TAB A
+			GROUP BY CUST_NO
+		)
+		-- 취소갯수
+		, TAB_CNCL_QTY AS (
+			SELECT SUM(CHG_QTY) AS VAL
+				, '3' AS GBN
+				, C.CUST_NO
+			FROM TB_ORDER_CHANGE_DETAIL A, TB_ORDER_DETAIL B, TB_ORDER C, TB_GOODS E, TB_CUSTOMER G
+			WHERE A.ORD_DTL_NO = B.ORD_DTL_NO
+				AND B.ORD_NO = C.ORD_NO
+				AND B.GOODS_CD = E.GOODS_CD
+				AND C.CUST_NO = G.CUST_NO
+				AND CHG_STAT = 'G685_18' -- 결제후취소
+				AND COMPLETE_DT >= STR_TO_DATE(#{startDt},'%Y-%m-%d') -- 시작일변수
+				AND COMPLETE_DT <![CDATA[<]]> DATE_ADD(STR_TO_DATE(#{endDt},'%Y-%m-%d'), INTERVAL 1 DAY) -- 종료일변수
+				AND MALL_GB = 'G011_10'
+				AND G.CUST_NO > 0
+		<if test="multiFrontGb != null">
+			/* 디바이스 */
+			<foreach collection="multiFrontGb" item="item" index="index"  open="AND C.FRONT_GB IN (" close=")" separator=",">#{item}</foreach>
+		</if>
+		<if test="multiSexGb != null">
+			/* 성별구분 */
+			<foreach collection="multiSexGb" item="item" index="index"  open="AND FN_DEC_AES(G.SEX_GB) IN (" close=")" separator=",">#{item}</foreach>
+		</if>
+		<if test="multiAgeGb != null">
+			/* 연령구분 */
+			<foreach collection="multiAgeGb" item="item" index="index"  open="AND CASE WHEN FN_DEC_AES(G.BIRTH_YMD) = '' OR FN_DEC_AES(G.BIRTH_YMD) IS NULL THEN 'X'
+				WHEN (DATE_FORMAT(NOW(), '%Y') - DATE_FORMAT(CONCAT(SUBSTRING(FN_DEC_AES(G.BIRTH_YMD), 1, 4), '0101'), '%Y') + 1) BETWEEN 10 AND 19 THEN '10'
+				WHEN (DATE_FORMAT(NOW(), '%Y') - DATE_FORMAT(CONCAT(SUBSTRING(FN_DEC_AES(G.BIRTH_YMD), 1, 4), '0101'), '%Y') + 1) BETWEEN 20 AND 29 THEN '20'
+				WHEN (DATE_FORMAT(NOW(), '%Y') - DATE_FORMAT(CONCAT(SUBSTRING(FN_DEC_AES(G.BIRTH_YMD), 1, 4), '0101'), '%Y') + 1) BETWEEN 30 AND 39 THEN '30'
+				WHEN (DATE_FORMAT(NOW(), '%Y') - DATE_FORMAT(CONCAT(SUBSTRING(FN_DEC_AES(G.BIRTH_YMD), 1, 4), '0101'), '%Y') + 1) BETWEEN 40 AND 49 THEN '40'
+				ELSE 'X' END IN (" close=")" separator=",">#{item}</foreach>
+		</if>
+		<if test="multiBrandCd != null">
+			/* 브랜드 */
+			<foreach collection="multiBrandCd" item="item" index="index"  open="AND BRAND_CD IN (" close=")" separator=",">#{item}</foreach>
+		</if>
+		<if test="multiItemkindCd != null">
+			/* 품목 */
+			<foreach collection="multiItemkindCd" item="item" index="index"  open="AND ITEMKIND_CD IN (" close=")" separator=",">#{item}</foreach>
+		</if>
+			GROUP BY C.CUST_NO
+		)
+		-- 반품갯수
+		, TAB_RTN_QTY AS (
+			SELECT SUM(CHG_QTY) AS VAL
+				, '4' AS GBN
+				, C.CUST_NO
+			FROM TB_ORDER_CHANGE_DETAIL A, TB_ORDER_DETAIL B, TB_ORDER C, TB_GOODS E, TB_CUSTOMER G
+			WHERE A.ORD_DTL_NO = B.ORD_DTL_NO
+				AND B.ORD_NO = C.ORD_NO
+				AND B.GOODS_CD = E.GOODS_CD
+				AND C.CUST_NO = G.CUST_NO
+				AND CHG_STAT = 'G685_60' -- 반품완료
+				AND COMPLETE_DT >= STR_TO_DATE(#{startDt},'%Y-%m-%d') -- 시작일변수
+				AND COMPLETE_DT <![CDATA[<]]> DATE_ADD(STR_TO_DATE(#{endDt},'%Y-%m-%d'), INTERVAL 1 DAY) -- 종료일변수
+				AND MALL_GB = 'G011_10'
+				AND G.CUST_NO > 0
+		<if test="multiFrontGb != null">
+			/* 디바이스 */
+			<foreach collection="multiFrontGb" item="item" index="index"  open="AND C.FRONT_GB IN (" close=")" separator=",">#{item}</foreach>
+		</if>
+		<if test="multiSexGb != null">
+			/* 성별구분 */
+			<foreach collection="multiSexGb" item="item" index="index"  open="AND FN_DEC_AES(G.SEX_GB) IN (" close=")" separator=",">#{item}</foreach>
+		</if>
+		<if test="multiAgeGb != null">
+			/* 연령구분 */
+			<foreach collection="multiAgeGb" item="item" index="index"  open="AND CASE WHEN FN_DEC_AES(G.BIRTH_YMD) = '' OR FN_DEC_AES(G.BIRTH_YMD) IS NULL THEN 'X'
+				WHEN (DATE_FORMAT(NOW(), '%Y') - DATE_FORMAT(CONCAT(SUBSTRING(FN_DEC_AES(G.BIRTH_YMD), 1, 4), '0101'), '%Y') + 1) BETWEEN 10 AND 19 THEN '10'
+				WHEN (DATE_FORMAT(NOW(), '%Y') - DATE_FORMAT(CONCAT(SUBSTRING(FN_DEC_AES(G.BIRTH_YMD), 1, 4), '0101'), '%Y') + 1) BETWEEN 20 AND 29 THEN '20'
+				WHEN (DATE_FORMAT(NOW(), '%Y') - DATE_FORMAT(CONCAT(SUBSTRING(FN_DEC_AES(G.BIRTH_YMD), 1, 4), '0101'), '%Y') + 1) BETWEEN 30 AND 39 THEN '30'
+				WHEN (DATE_FORMAT(NOW(), '%Y') - DATE_FORMAT(CONCAT(SUBSTRING(FN_DEC_AES(G.BIRTH_YMD), 1, 4), '0101'), '%Y') + 1) BETWEEN 40 AND 49 THEN '40'
+				ELSE 'X' END IN (" close=")" separator=",">#{item}</foreach>
+		</if>
+		<if test="multiBrandCd != null">
+			/* 브랜드 */
+			<foreach collection="multiBrandCd" item="item" index="index"  open="AND BRAND_CD IN (" close=")" separator=",">#{item}</foreach>
+		</if>
+		<if test="multiItemkindCd != null">
+			/* 품목 */
+			<foreach collection="multiItemkindCd" item="item" index="index"  open="AND ITEMKIND_CD IN (" close=")" separator=",">#{item}</foreach>
+		</if>
+			GROUP BY C.CUST_NO
+		)
+		-- 취소액
+		, TAB_CNCL_AMT AS (
+			SELECT SUM((C.CURR_PRICE + (SELECT SUM(OPT_ADD_PRICE * ITEM_QTY) FROM TB_ORDER_DETAIL_ITEM X WHERE X.ORD_DTL_NO = C.ORD_DTL_NO)) * B.CHG_QTY) AS VAL
+				, '5' AS GBN
+				, D.CUST_NO
+			FROM TB_ORDER_CHANGE_DETAIL B, TB_ORDER_DETAIL C, TB_ORDER D, TB_GOODS E, TB_CUSTOMER G
+			WHERE B.ORD_DTL_NO = C.ORD_DTL_NO
+				AND C.ORD_NO = D.ORD_NO
+				AND C.GOODS_CD = E.GOODS_CD
+				AND D.CUST_NO = G.CUST_NO
+				AND CHG_STAT = 'G685_18' -- 결제후취소
+				AND B.COMPLETE_DT >= STR_TO_DATE(#{startDt},'%Y-%m-%d') -- 시작일변수
+				AND B.COMPLETE_DT <![CDATA[<]]> DATE_ADD(STR_TO_DATE(#{endDt},'%Y-%m-%d'), INTERVAL 1 DAY) -- 종료일변수
+				AND MALL_GB = 'G011_10'
+				AND G.CUST_NO > 0
+		<if test="multiFrontGb != null">
+			/* 디바이스 */
+			<foreach collection="multiFrontGb" item="item" index="index"  open="AND D.FRONT_GB IN (" close=")" separator=",">#{item}</foreach>
+		</if>
+		<if test="multiSexGb != null">
+			/* 성별구분 */
+			<foreach collection="multiSexGb" item="item" index="index"  open="AND FN_DEC_AES(G.SEX_GB) IN (" close=")" separator=",">#{item}</foreach>
+		</if>
+		<if test="multiAgeGb != null">
+			/* 연령구분 */
+			<foreach collection="multiAgeGb" item="item" index="index"  open="AND CASE WHEN FN_DEC_AES(G.BIRTH_YMD) = '' OR FN_DEC_AES(G.BIRTH_YMD) IS NULL THEN 'X'
+				WHEN (DATE_FORMAT(NOW(), '%Y') - DATE_FORMAT(CONCAT(SUBSTRING(FN_DEC_AES(G.BIRTH_YMD), 1, 4), '0101'), '%Y') + 1) BETWEEN 10 AND 19 THEN '10'
+				WHEN (DATE_FORMAT(NOW(), '%Y') - DATE_FORMAT(CONCAT(SUBSTRING(FN_DEC_AES(G.BIRTH_YMD), 1, 4), '0101'), '%Y') + 1) BETWEEN 20 AND 29 THEN '20'
+				WHEN (DATE_FORMAT(NOW(), '%Y') - DATE_FORMAT(CONCAT(SUBSTRING(FN_DEC_AES(G.BIRTH_YMD), 1, 4), '0101'), '%Y') + 1) BETWEEN 30 AND 39 THEN '30'
+				WHEN (DATE_FORMAT(NOW(), '%Y') - DATE_FORMAT(CONCAT(SUBSTRING(FN_DEC_AES(G.BIRTH_YMD), 1, 4), '0101'), '%Y') + 1) BETWEEN 40 AND 49 THEN '40'
+				ELSE 'X' END IN (" close=")" separator=",">#{item}</foreach>
+		</if>
+		<if test="multiBrandCd != null">
+			/* 브랜드 */
+			<foreach collection="multiBrandCd" item="item" index="index"  open="AND BRAND_CD IN (" close=")" separator=",">#{item}</foreach>
+		</if>
+		<if test="multiItemkindCd != null">
+			/* 품목 */
+			<foreach collection="multiItemkindCd" item="item" index="index"  open="AND ITEMKIND_CD IN (" close=")" separator=",">#{item}</foreach>
+		</if>
+			GROUP BY D.CUST_NO
+		)
+		-- 반품액
+		, TAB_RTN_AMT AS (
+			SELECT SUM((C.CURR_PRICE + (SELECT SUM(OPT_ADD_PRICE * ITEM_QTY) FROM TB_ORDER_DETAIL_ITEM X WHERE X.ORD_DTL_NO = C.ORD_DTL_NO)) * B.CHG_QTY) AS VAL
+				, '6' AS GBN
+				, D.CUST_NO
+			FROM TB_ORDER_CHANGE_DETAIL B, TB_ORDER_DETAIL C, TB_ORDER D, TB_GOODS E, TB_CUSTOMER G
+			WHERE B.ORD_DTL_NO = C.ORD_DTL_NO
+				AND C.ORD_NO = D.ORD_NO
+				AND C.GOODS_CD = E.GOODS_CD
+				AND D.CUST_NO = G.CUST_NO
+				AND CHG_STAT = 'G685_60' -- 반품완료
+				AND B.COMPLETE_DT >= STR_TO_DATE(#{startDt},'%Y-%m-%d') -- 시작일변수
+				AND B.COMPLETE_DT <![CDATA[<]]> DATE_ADD(STR_TO_DATE(#{endDt},'%Y-%m-%d'), INTERVAL 1 DAY) -- 종료일변수
+				AND MALL_GB = 'G011_10'
+				AND G.CUST_NO > 0
+		<if test="multiFrontGb != null">
+			/* 디바이스 */
+			<foreach collection="multiFrontGb" item="item" index="index"  open="AND D.FRONT_GB IN (" close=")" separator=",">#{item}</foreach>
+		</if>
+		<if test="multiSexGb != null">
+			/* 성별구분 */
+			<foreach collection="multiSexGb" item="item" index="index"  open="AND FN_DEC_AES(G.SEX_GB) IN (" close=")" separator=",">#{item}</foreach>
+		</if>
+		<if test="multiAgeGb != null">
+			/* 연령구분 */
+			<foreach collection="multiAgeGb" item="item" index="index"  open="AND CASE WHEN FN_DEC_AES(G.BIRTH_YMD) = '' OR FN_DEC_AES(G.BIRTH_YMD) IS NULL THEN 'X'
+				WHEN (DATE_FORMAT(NOW(), '%Y') - DATE_FORMAT(CONCAT(SUBSTRING(FN_DEC_AES(G.BIRTH_YMD), 1, 4), '0101'), '%Y') + 1) BETWEEN 10 AND 19 THEN '10'
+				WHEN (DATE_FORMAT(NOW(), '%Y') - DATE_FORMAT(CONCAT(SUBSTRING(FN_DEC_AES(G.BIRTH_YMD), 1, 4), '0101'), '%Y') + 1) BETWEEN 20 AND 29 THEN '20'
+				WHEN (DATE_FORMAT(NOW(), '%Y') - DATE_FORMAT(CONCAT(SUBSTRING(FN_DEC_AES(G.BIRTH_YMD), 1, 4), '0101'), '%Y') + 1) BETWEEN 30 AND 39 THEN '30'
+				WHEN (DATE_FORMAT(NOW(), '%Y') - DATE_FORMAT(CONCAT(SUBSTRING(FN_DEC_AES(G.BIRTH_YMD), 1, 4), '0101'), '%Y') + 1) BETWEEN 40 AND 49 THEN '40'
+				ELSE 'X' END IN (" close=")" separator=",">#{item}</foreach>
+		</if>
+		<if test="multiBrandCd != null">
+			/* 브랜드 */
+			<foreach collection="multiBrandCd" item="item" index="index"  open="AND BRAND_CD IN (" close=")" separator=",">#{item}</foreach>
+		</if>
+		<if test="multiItemkindCd != null">
+			/* 품목 */
+			<foreach collection="multiItemkindCd" item="item" index="index"  open="AND ITEMKIND_CD IN (" close=")" separator=",">#{item}</foreach>
+		</if>
+			GROUP BY D.CUST_NO
+		)
+		-- 주문수
+		, TAB_ORD_CNT AS (
+			SELECT
+				SUM(VAL) AS VAL
+				, '7' AS GBN
+				, CUST_NO
+			FROM (
+				SELECT
+					1 AS VAL
+					, ORD_NO
+					, CUST_NO
+				FROM TAB
+				GROUP BY ORD_NO, CUST_NO
+			) A
+			GROUP BY CUST_NO
+		)
+		SELECT
+			CONCAT(SUBSTRING(CUST_ID, 1, 3), '****', '(', SUBSTRING(FN_DEC_AES(CUST_NM), 1, 1), '**', ')') AS CUST_ID -- 아이디
+			, CASE WHEN FN_DEC_AES(BIRTH_YMD) = '' OR FN_DEC_AES(BIRTH_YMD) IS NULL THEN 'X'
+				WHEN (DATE_FORMAT(NOW(), '%Y') - DATE_FORMAT(CONCAT(SUBSTRING(FN_DEC_AES(BIRTH_YMD), 1, 4), '0101'), '%Y') + 1) BETWEEN 10 AND 19 THEN '10'
+				WHEN (DATE_FORMAT(NOW(), '%Y') - DATE_FORMAT(CONCAT(SUBSTRING(FN_DEC_AES(BIRTH_YMD), 1, 4), '0101'), '%Y') + 1) BETWEEN 20 AND 29 THEN '20'
+				WHEN (DATE_FORMAT(NOW(), '%Y') - DATE_FORMAT(CONCAT(SUBSTRING(FN_DEC_AES(BIRTH_YMD), 1, 4), '0101'), '%Y') + 1) BETWEEN 30 AND 39 THEN '30'
+				WHEN (DATE_FORMAT(NOW(), '%Y') - DATE_FORMAT(CONCAT(SUBSTRING(FN_DEC_AES(BIRTH_YMD), 1, 4), '0101'), '%Y') + 1) BETWEEN 40 AND 49 THEN '40'
+			ELSE 'X' END AS AGE
+		    , X.CUST_NO
+			, FN_GET_CODE_NM('G007', FN_DEC_AES(SEX_GB)) AS SEX_GB
+			, FN_GET_CODE_NM('G110', CUST_GRADE) AS CUST_GRADE -- 등급
+			, SUM(ORD_AMT - CNCL_AMT - RTN_AMT) AS TOT_ORD_AMT -- 매출액
+			, SUM(ORD_CNT) AS ORD_CNT -- 주문수
+			, SUM(SELL_QTY - CNCL_QTY - RTN_QTY) AS SELL_QTY -- 판매수
+			, FLOOR(SUM(ORD_AMT) / SUM(ORD_CNT)) AS CUST_PRICE -- 객단가
+			, IFNULL((SELECT SUM(RM_PNT_AMT) FROM TB_CUST_POINT CP WHERE CP.CUST_NO = X.CUST_NO AND EXP_CMP_DT IS NULL), 0) AS CUST_POINT -- 회원포인트
+		FROM (
+			SELECT
+				CUST_NO
+				, SUM(CASE WHEN GBN = '1' THEN VAL ELSE 0 END) AS SELL_QTY -- 판매수
+				, SUM(CASE WHEN GBN = '2' THEN VAL ELSE 0 END) AS ORD_AMT -- 매출액(판매금액)
+				, SUM(CASE WHEN GBN = '3' THEN VAL ELSE 0 END) AS CNCL_QTY -- 취소수량
+				, SUM(CASE WHEN GBN = '4' THEN VAL ELSE 0 END) AS RTN_QTY -- 반품수량
+				, SUM(CASE WHEN GBN = '5' THEN VAL ELSE 0 END) AS CNCL_AMT -- 취소금액
+				, SUM(CASE WHEN GBN = '6' THEN VAL ELSE 0 END) AS RTN_AMT -- 반품금액
+				, SUM(CASE WHEN GBN = '7' THEN VAL ELSE 0 END) AS ORD_CNT -- 주문수
+			FROM (
+				SELECT * FROM TAB_SELL_QTY
+				UNION ALL
+				SELECT * FROM TAB_ORD
+				UNION ALL
+				SELECT * FROM TAB_CNCL_QTY
+				UNION ALL
+				SELECT * FROM TAB_RTN_QTY
+				UNION ALL
+				SELECT * FROM TAB_CNCL_AMT
+				UNION ALL
+				SELECT * FROM TAB_RTN_AMT
+				UNION ALL
+				SELECT * FROM TAB_ORD_CNT
+			) A
+			GROUP BY CUST_NO
+		) X, TB_CUSTOMER Y
+		WHERE X.CUST_NO = Y.CUST_NO
+		GROUP BY X.CUST_NO
+		ORDER BY TOT_ORD_AMT DESC
+		LIMIT 50
+	</select>
+
+	<!-- 미로그인현황 -->
+	<select id="getCustomerUnloginList" resultType="Statistics">
+		/* TsaStatistics.getCustomerUnloginList */
+		SELECT
+			X.*
+			, ROUND(CNT_5 / TOT_CNT * 100) AS PER_CNT_5
+			, ROUND(CNT_4 / TOT_CNT * 100) AS PER_CNT_4
+			, ROUND(CNT_3 / TOT_CNT * 100) AS PER_CNT_3
+			, ROUND(CNT_2 / TOT_CNT * 100) AS PER_CNT_2
+			, ROUND(CNT_1 / TOT_CNT * 100) AS PER_CNT_1
+		FROM (
+			SELECT
+				SUM(CASE WHEN GB = 5 THEN CNT ELSE 0 END) AS CNT_5
+				, SUM(CASE WHEN GB = 4 THEN CNT ELSE 0 END) AS CNT_4
+				, SUM(CASE WHEN GB = 3 THEN CNT ELSE 0 END) AS CNT_3
+				, SUM(CASE WHEN GB = 2 THEN CNT ELSE 0 END) AS CNT_2
+				, SUM(CASE WHEN GB = 1 THEN CNT ELSE 0 END) AS CNT_1
+				, SUM(CNT) AS TOT_CNT
+			FROM (
+				-- 1년
+				SELECT COUNT(1) AS CNT
+					, 5 AS GB -- 1년 ~
+				FROM TB_CUSTOMER
+				WHERE CUST_NO > 0
+					AND CUST_STAT = 'G104_10'
+					AND LOGIN_LDT &lt; DATE_FORMAT(DATE_ADD(STR_TO_DATE(DATE_FORMAT(NOW(), '%Y%m%d%H'), '%Y%m%d%H'), INTERVAL -1 YEAR ), '%Y%m%d%H%i%s') -- now() 수정 : 조회시점의 시간까지만. ex) 2019년9월25일15시 조회 -> 20210925150000
+				-- 12개월
+				UNION ALL
+				SELECT COUNT(1) AS CNT
+					, 4 AS GB -- 9개월~12개월
+				FROM TB_CUSTOMER
+				WHERE CUST_NO > 0
+					AND CUST_STAT = 'G104_10'
+					AND LOGIN_LDT >= DATE_FORMAT(DATE_ADD(STR_TO_DATE(DATE_FORMAT(NOW(), '%Y%m%d%H'), '%Y%m%d%H'), INTERVAL -1 YEAR ), '%Y%m%d%H%i%s')
+					AND LOGIN_LDT &lt; DATE_FORMAT(DATE_ADD(STR_TO_DATE(DATE_FORMAT(NOW(), '%Y%m%d%H'), '%Y%m%d%H'), INTERVAL -9 MONTH ), '%Y%m%d%H%i%s')
+				-- 9개월
+				UNION ALL
+				SELECT COUNT(1) AS CNT
+					, 3 AS GB -- 6개월~9개월
+				FROM TB_CUSTOMER
+				WHERE CUST_NO > 0
+					AND CUST_STAT = 'G104_10'
+					AND LOGIN_LDT >= DATE_FORMAT(DATE_ADD(STR_TO_DATE(DATE_FORMAT(NOW(), '%Y%m%d%H'), '%Y%m%d%H'), INTERVAL -9 MONTH ), '%Y%m%d%H%i%s')
+					AND LOGIN_LDT &lt; DATE_FORMAT(DATE_ADD(STR_TO_DATE(DATE_FORMAT(NOW(), '%Y%m%d%H'), '%Y%m%d%H'), INTERVAL -6 MONTH ), '%Y%m%d%H%i%s')
+				-- 6개월
+				UNION ALL
+				SELECT COUNT(1) AS CNT
+					, 2 AS GB -- 3개월~6개월
+				FROM TB_CUSTOMER
+				WHERE CUST_NO > 0
+					AND CUST_STAT = 'G104_10'
+					AND LOGIN_LDT >= DATE_FORMAT(DATE_ADD(STR_TO_DATE(DATE_FORMAT(NOW(), '%Y%m%d%H'), '%Y%m%d%H'), INTERVAL -6 MONTH ), '%Y%m%d%H%i%s')
+					AND LOGIN_LDT &lt; DATE_FORMAT(DATE_ADD(STR_TO_DATE(DATE_FORMAT(NOW(), '%Y%m%d%H'), '%Y%m%d%H'), INTERVAL -3 MONTH ), '%Y%m%d%H%i%s')
+				-- 3개월
+				UNION ALL
+				SELECT COUNT(1) AS CNT
+					, 1 AS GB -- ~3개월
+				FROM TB_CUSTOMER
+				WHERE CUST_NO > 0
+					AND CUST_STAT = 'G104_10'
+					AND LOGIN_LDT >= DATE_FORMAT(DATE_ADD(STR_TO_DATE(DATE_FORMAT(NOW(), '%Y%m%d%H'), '%Y%m%d%H'), INTERVAL -3 MONTH ), '%Y%m%d%H%i%s')
+					AND LOGIN_LDT &lt; DATE_FORMAT(NOW(), '%Y%m%d%H%i%s')
+			) Z
+		) X
+	</select>
+
+	<!-- 미로그인현황 회원리스트 -->
+	<select id="getCustomerUnloginInfoList" parameterType="Statistics" resultType="paramMap">
+		/* TsaStatistics.getCustomerUnloginInfoList */
+		SELECT (
+		        SELECT CASE WHEN ROLE_CD = 'G001_0000'
+		                         THEN A.CUST_ID
+		                    ELSE CONCAT(LEFT(A.CUST_ID, 3), REPEAT('*', CHAR_LENGTH(A.CUST_ID) - 3 ) )
+		               END
+		        FROM   TB_USER
+		        WHERE  USER_NO = #{regNo}
+		       ) AS CUST_ID
+		     , (
+		        SELECT CASE WHEN ROLE_CD = 'G001_0000'
+		                         THEN A.CUST_NM
+		                    ELSE CONCAT(LEFT(A.CUST_NM, 1), REPEAT('*', CHAR_LENGTH(A.CUST_NM) - 1 ) )
+		               END
+		        FROM   TB_USER
+		        WHERE  USER_NO = #{regNo}
+		       ) AS CUST_NM
+		    , (
+		       SELECT CASE WHEN ROLE_CD = 'G001_0000'
+		                        THEN A.CELL_PHNNO
+		                   ELSE CONCAT(substr(A.CELL_PHNNO, 1, 4), '****', substr(A.CELL_PHNNO, 9, 13))
+		              END
+		       FROM   TB_USER
+		       WHERE  USER_NO = #{regNo}
+		      ) AS CELL_PHNNO
+		    , (
+		       SELECT CASE WHEN ROLE_CD = 'G001_0000'
+		                        THEN A.EMAIL
+		                   ELSE CONCAT(LEFT(A.EMAIL, 2), REPEAT('*', instr(A.EMAIL, '@') - 3), SUBSTRING(A.EMAIL, instr(EMAIL, '@'), LENGTH(A.EMAIL)))
+		              END
+		       FROM   TB_USER
+		       WHERE  USER_NO = #{regNo}
+		      ) AS EMAIL
+		    , MONTHS
+		    , BIRTH_YM
+		FROM   (
+		        SELECT CUST_ID
+		             , FN_DEC_AES(CUST_NM)                    AS CUST_NM
+		             , TIMESTAMPDIFF(MONTH, LOGIN_LDT, NOW()) AS MONTHS
+		             , CASE WHEN CELL_PHNNO != 'xx'
+		                         THEN FN_DEC_AES(CELL_PHNNO)
+		                    ELSE CELL_PHNNO
+		               END                                    AS CELL_PHNNO
+		             , FN_DEC_AES(EMAIL)                      AS EMAIL
+		             , SUBSTRING(FN_DEC_AES(BIRTH_YMD), 1, 6) AS BIRTH_YM
+		        FROM   TB_CUSTOMER
+		        WHERE  CUST_NO > 0
+		        AND    CUST_STAT = 'G104_10'
+		        AND    LOGIN_LDT <![CDATA[ < ]]> DATE_FORMAT(STR_TO_DATE(DATE_FORMAT(STR_TO_DATE(DATE_FORMAT(NOW(), '%Y%m%d%H'), '%Y%m%d%H'), '%Y%m%d%H'), '%Y%m%d%H'), '%Y-%m-%d %H:%i:%s') -- now() 수정 : 조회시점의 시간까지만. ex) 2019년9월25일15시 조회 -> 20210925150000
+		       ) A
+	</select>
+
+	<!-- 마케팅수신동의현황 -->
+	<select id="getCustomerMarketingList" resultType="Statistics">
+		/* TsaStatistics.getCustomerMarketingList */
+		SELECT
+			X.*
+			 , ROUND(CNT_4 / TOT_CNT * 100) AS PER_CNT_4
+			 , ROUND(CNT_3 / TOT_CNT * 100) AS PER_CNT_3
+			 , ROUND(CNT_2 / TOT_CNT * 100) AS PER_CNT_2
+			 , ROUND(CNT_1 / TOT_CNT * 100) AS PER_CNT_1
+		FROM (
+			 SELECT SUM(CASE WHEN GB = 4 THEN CNT ELSE 0 END) AS CNT_4
+				  , SUM(CASE WHEN GB = 3 THEN CNT ELSE 0 END) AS CNT_3
+				  , SUM(CASE WHEN GB = 2 THEN CNT ELSE 0 END) AS CNT_2
+				  , SUM(CASE WHEN GB = 1 THEN CNT ELSE 0 END) AS CNT_1
+				  , SUM(CNT)                                  AS TOT_CNT
+			 FROM (
+				  -- SMS
+				  SELECT COUNT(1) AS CNT
+					   , 4        AS GB
+				  FROM TB_CUSTOMER
+				  WHERE CUST_NO > 0
+					AND CUST_STAT = 'G104_10'
+					AND SMS_AGREE_YN = 'Y'
+					-- EMAIL
+				  UNION ALL
+				  SELECT COUNT(1) AS CNT
+					   , 3        AS GB
+				  FROM TB_CUSTOMER
+				  WHERE CUST_NO > 0
+					AND CUST_STAT = 'G104_10'
+					AND EMAIL_AGREE_YN = 'Y'
+					-- 푸쉬
+				  UNION ALL
+				  SELECT COUNT(1) AS CNT
+					   , 2        AS GB
+				  FROM TB_CUSTOMER
+				  WHERE CUST_NO > 0
+					AND CUST_STAT = 'G104_10'
+					AND APP_AGREE_YN = 'Y'
+					-- 미동의
+				  UNION ALL
+				  SELECT COUNT(1) AS CNT
+					   , 1        AS GB
+				  FROM TB_CUSTOMER
+				  WHERE CUST_NO > 0
+					AND CUST_STAT = 'G104_10'
+					AND SMS_AGREE_YN = 'N'
+					AND EMAIL_AGREE_YN = 'N'
+					AND APP_AGREE_YN = 'N'
+			  ) Z
+		 ) X
+	</select>
+
+	<!-- 휴면전환 잔여일별현황 -->
+	<select id="getCustomerDormRemainList" resultType="Statistics">
+		/* TsaStatistics.getCustomerDormRemainList */
+		SELECT
+			SUM(CASE WHEN GB = 4 THEN CNT ELSE 0 END) AS CNT_4 -- 12개월
+			, SUM(CASE WHEN GB = 3 THEN CNT ELSE 0 END) AS CNT_3 -- 9개월
+			, SUM(CASE WHEN GB = 2 THEN CNT ELSE 0 END) AS CNT_2 -- 6개월
+			, SUM(CASE WHEN GB = 1 THEN CNT ELSE 0 END) AS CNT_1 -- 9개월
+		FROM (
+			-- 12개월
+			SELECT COUNT(1) AS CNT
+				, 4 AS GB -- 12개월
+			FROM TB_CUSTOMER
+			WHERE CUST_NO > 0
+				AND CUST_STAT = 'G104_10'
+				AND LOGIN_LDT &lt; DATE_FORMAT(DATE_ADD(STR_TO_DATE(DATE_FORMAT(NOW(), '%Y%m%d%H'), '%Y%m%d%H'), INTERVAL -1 DAY ), '%Y%m%d%H%i%s') -- now() 수정 : 조회시점의 시간까지만. ex) 2019년9월25일15시 조회 -> 20210925150000
+			-- 9개월
+			UNION ALL
+			SELECT COUNT(1) AS CNT
+				, 3 AS GB -- 9개월
+			FROM TB_CUSTOMER
+			WHERE CUST_NO > 0
+				AND CUST_STAT = 'G104_10'
+				AND LOGIN_LDT >= DATE_FORMAT(DATE_ADD(STR_TO_DATE(DATE_FORMAT(NOW(), '%Y%m%d%H'), '%Y%m%d%H'), INTERVAL -3 MONTH ), '%Y%m%d%H%i%s')
+				AND LOGIN_LDT &lt; DATE_FORMAT(DATE_ADD(STR_TO_DATE(DATE_FORMAT(NOW(), '%Y%m%d%H'), '%Y%m%d%H'), INTERVAL -1 DAY ), '%Y%m%d%H%i%s')
+			-- 6개월
+			UNION ALL
+			SELECT COUNT(1) AS CNT
+				, 2 AS GB -- 6개월
+			FROM TB_CUSTOMER
+			WHERE CUST_NO > 0
+				AND CUST_STAT = 'G104_10'
+				AND LOGIN_LDT >= DATE_FORMAT(DATE_ADD(STR_TO_DATE(DATE_FORMAT(NOW(), '%Y%m%d%H'), '%Y%m%d%H'), INTERVAL -6 MONTH ), '%Y%m%d%H%i%s')
+				AND LOGIN_LDT &lt; DATE_FORMAT(DATE_ADD(STR_TO_DATE(DATE_FORMAT(NOW(), '%Y%m%d%H'), '%Y%m%d%H'), INTERVAL -3 MONTH ), '%Y%m%d%H%i%s')
+			-- 3개월
+			UNION ALL
+			SELECT COUNT(1) AS CNT
+				, 1 AS GB -- ~3개월
+			FROM TB_CUSTOMER
+			WHERE CUST_NO > 0
+				AND CUST_STAT = 'G104_10'
+				AND LOGIN_LDT >= DATE_FORMAT(DATE_ADD(STR_TO_DATE(DATE_FORMAT(NOW(), '%Y%m%d%H'), '%Y%m%d%H'), INTERVAL -9 MONTH ), '%Y%m%d%H%i%s')
+				AND LOGIN_LDT &lt; DATE_FORMAT(DATE_ADD(STR_TO_DATE(DATE_FORMAT(NOW(), '%Y%m%d%H'), '%Y%m%d%H'), INTERVAL -6 MONTH ), '%Y%m%d%H%i%s')
+		) Z
+	</select>
+
+	<!-- 휴면전환 잔여일별현황 회원리스트 -->
+	<select id="getCustomerDormRemainInfoList" parameterType="Statistics" resultType="paramMap">
+	/* TsaStatistics.getCustomerDormRemainInfoList */
+		SELECT GB
+			 , BIRTH_YM
+		     , (
+			    SELECT CASE WHEN ROLE_CD = 'G001_0000'
+							     THEN A.CUST_ID
+				   	        ELSE CONCAT(LEFT(A.CUST_ID, 3), REPEAT('*', CHAR_LENGTH(A.CUST_ID) - 3 ) )
+					   END
+			    FROM   TB_USER
+			    WHERE  USER_NO = #{regNo}
+		       ) AS CUST_ID
+			 , (
+			    SELECT CASE WHEN ROLE_CD = 'G001_0000'
+							     THEN A.CUST_NM
+						    ELSE CONCAT(LEFT(A.CUST_NM, 1), REPEAT('*', CHAR_LENGTH(A.CUST_NM) - 1 ) )
+					   END
+			    FROM   TB_USER
+			    WHERE  USER_NO = #{regNo}
+		       ) AS CUST_NM
+			 , (
+			    SELECT CASE WHEN ROLE_CD = 'G001_0000'
+							     THEN A.CELL_PHNNO
+						    ELSE CONCAT(substr(A.CELL_PHNNO, 1, 4), '****', substr(A.CELL_PHNNO, 9, 13))
+					   END
+			    FROM   TB_USER
+			    WHERE  USER_NO = #{regNo}
+		       ) AS CELL_PHNNO
+			 , (
+			    SELECT CASE WHEN ROLE_CD = 'G001_0000'
+							     THEN A.EMAIL
+						    ELSE CONCAT(LEFT(A.EMAIL, 2), REPEAT('*', instr(A.EMAIL, '@') - 3), SUBSTRING(A.EMAIL, instr(EMAIL, '@'), LENGTH(A.EMAIL)))
+					   END
+			    FROM   TB_USER
+			    WHERE  USER_NO = #{regNo}
+		       ) AS EMAIL
+		FROM (
+			-- 12개월
+			SELECT '12개월' AS GB -- 12개월
+				, CUST_ID
+				, FN_DEC_AES(CUST_NM) AS CUST_NM
+				, CASE WHEN CELL_PHNNO != 'xx'
+		                         THEN FN_DEC_AES(CELL_PHNNO)
+					   ELSE CELL_PHNNO
+				  END                                AS CELL_PHNNO
+				, FN_DEC_AES(EMAIL) AS EMAIL
+				, SUBSTRING(FN_DEC_AES(BIRTH_YMD), 1, 6) AS BIRTH_YM
+			FROM TB_CUSTOMER
+			WHERE CUST_NO > 0
+				AND CUST_STAT = 'G104_10'
+				AND LOGIN_LDT > DATE_FORMAT(DATE_ADD(STR_TO_DATE(DATE_FORMAT(NOW(), '%Y%m%d%H'), '%Y%m%d%H'), INTERVAL -1 DAY ), '%Y%m%d%H%i%s') -- now() 수정 : 조회시점의 시간까지만. ex) 2019년9월25일15시 조회 -> 20210925150000
+			-- 9개월
+			UNION ALL
+			SELECT '9개월' AS GB -- 9개월
+				, CUST_ID
+				, FN_DEC_AES(CUST_NM) AS CUST_NM
+				, CASE WHEN CELL_PHNNO != 'xx'
+		                         THEN FN_DEC_AES(CELL_PHNNO)
+					   ELSE CELL_PHNNO
+				  END                                AS CELL_PHNNO
+				, FN_DEC_AES(EMAIL) AS EMAIL
+				, SUBSTRING(FN_DEC_AES(BIRTH_YMD), 1, 6) AS BIRTH_YM
+			FROM TB_CUSTOMER
+			WHERE CUST_NO > 0
+				AND CUST_STAT = 'G104_10'
+				AND LOGIN_LDT >= DATE_FORMAT(DATE_ADD(STR_TO_DATE(DATE_FORMAT(NOW(), '%Y%m%d%H'), '%Y%m%d%H'), INTERVAL -3 MONTH ), '%Y%m%d%H%i%s')
+				AND LOGIN_LDT <![CDATA[ < ]]>  DATE_FORMAT(DATE_ADD(STR_TO_DATE(DATE_FORMAT(NOW(), '%Y%m%d%H'), '%Y%m%d%H'), INTERVAL -1 DAY ), '%Y%m%d%H%i%s')
+			-- 6개월
+			UNION ALL
+			SELECT '6개월' AS GB -- 6개월
+				, CUST_ID
+				, FN_DEC_AES(CUST_NM) AS CUST_NM
+				, CASE WHEN CELL_PHNNO != 'xx'
+		                         THEN FN_DEC_AES(CELL_PHNNO)
+					   ELSE CELL_PHNNO
+				  END                                AS CELL_PHNNO
+				, FN_DEC_AES(EMAIL) AS EMAIL
+				, SUBSTRING(FN_DEC_AES(BIRTH_YMD), 1, 6) AS BIRTH_YM
+			FROM TB_CUSTOMER
+			WHERE CUST_NO > 0
+				AND CUST_STAT = 'G104_10'
+				AND LOGIN_LDT >= DATE_FORMAT(DATE_ADD(STR_TO_DATE(DATE_FORMAT(NOW(), '%Y%m%d%H'), '%Y%m%d%H'), INTERVAL -6 MONTH ), '%Y%m%d%H%i%s')
+				AND LOGIN_LDT <![CDATA[ < ]]> DATE_FORMAT(DATE_ADD(STR_TO_DATE(DATE_FORMAT(NOW(), '%Y%m%d%H'), '%Y%m%d%H'), INTERVAL -3 MONTH ), '%Y%m%d%H%i%s')
+			-- 3개월
+			UNION ALL
+			SELECT '3개월' AS GB -- ~3개월
+				, CUST_ID
+				, FN_DEC_AES(CUST_NM) AS CUST_NM
+				, CASE WHEN CELL_PHNNO != 'xx'
+		                         THEN FN_DEC_AES(CELL_PHNNO)
+					   ELSE CELL_PHNNO
+				  END                                AS CELL_PHNNO
+				, FN_DEC_AES(EMAIL) AS EMAIL
+			, SUBSTRING(FN_DEC_AES(BIRTH_YMD), 1, 6) AS BIRTH_YM
+			FROM TB_CUSTOMER
+			WHERE CUST_NO > 0
+				AND CUST_STAT = 'G104_10'
+				AND LOGIN_LDT >= DATE_FORMAT(DATE_ADD(STR_TO_DATE(DATE_FORMAT(NOW(), '%Y%m%d%H'), '%Y%m%d%H'), INTERVAL -9 MONTH ), '%Y%m%d%H%i%s')
+				AND LOGIN_LDT <![CDATA[ < ]]> DATE_FORMAT(DATE_ADD(STR_TO_DATE(DATE_FORMAT(NOW(), '%Y%m%d%H'), '%Y%m%d%H'), INTERVAL -6 MONTH ), '%Y%m%d%H%i%s')
+		) A
+	</select>
 </mapper>

+ 152 - 0
src/main/webapp/WEB-INF/views/business/Bizday2Form.html

@@ -0,0 +1,152 @@
+<!DOCTYPE html>
+<html lang="ko"
+	xmlns:th="http://www.thymeleaf.org">
+<!--
+ *******************************************************************************
+ * @source  : Bizday2Form.html
+ * @desc    : 총알배송영업일관리 Page
+ *============================================================================
+ * STYLE24
+ * Copyright(C) 2020 TSIT, All rights reserved.
+ *============================================================================
+ * VER  DATE         AUTHOR      DESCRIPTION
+ * ===  ===========  ==========  =============================================
+ * 1.0  2021.09.29   gagamel     최초 작성
+ *******************************************************************************
+ -->
+	<link rel="stylesheet" href="/ux/plugins/fullcalendar/fullcalendar-4.2.0.css"/>
+	
+	<div id="main">
+		<!-- 메인타이틀 영역 -->
+		<div class="main-title">
+		</div>
+		<!-- //메인타이틀 영역 -->
+		
+		<!-- 메뉴 설명 -->
+		<div class="infoBox menu-desc">
+		</div>
+		<!-- //메뉴 설명 -->
+		
+		<div class="panelStyle">
+			<ul class="notice">
+				<li><strong class="cBlue">영업일 : </strong>휴일을 클릭하시면 영업일로 변경됩니다.</li>
+				<li><strong class="cRed">휴무일 : </strong>영업일을 클릭하시면 휴무일로 변경됩니다.</li>
+			</ul>
+			
+			<!-- FULLCALENDAR -->
+			<div id="calendar"></div>
+			<!-- //FULLCALENDAR -->
+		</div>
+	</div>
+	
+	<form id="calendarForm" name="calendarForm">
+		<input type="hidden" name="startDt" id="startDt"/>
+		<input type="hidden" name="endDt" id="endDt"/>
+		<input type="hidden" name="bizday" id="bizday"/>
+	</form>
+
+<script type="text/javascript" src="/ux/plugins/fullcalendar/fullcalendar-4.2.0.js"></script>
+<script th:inline="javascript">
+/*<![CDATA[*/
+	// 해당월의 시작일, 마지막일 설정
+	var setViewDate = function(date) {
+		var dt = [];
+		dt[0] = (new Date(date.startStr)).format('YYYYMMDD');
+		dt[1] = (new Date(date.endStr)).format('YYYYMMDD');
+		return dt;
+	}
+	
+	// 휴일,영업일 업데이트(저장)
+	var fnUpdateBizday = function(day ,arg) {
+		var start = "";
+		var end = "";
+		$('#calendarForm input[name=bizday]').val("");
+		
+		if (day == 'Holiday') {
+			var bizday = (new Date(arg.start)).format('YYYYMMDD');
+			$('#calendarForm input[name=bizday]').val(bizday);
+			
+			gagajf.ajaxFormSubmit('/business/bizday2/save', '#calendarForm', function() {
+				calendar.addEvent({
+					title: '휴일',
+					start: arg.start,
+					end: arg.end,
+					allDay: arg.allDay
+				});
+			});
+		} else {
+			var bizday = (new Date(arg.event.start)).format('YYYYMMDD');
+			$('#calendarForm input[name=bizday]').val(bizday);
+			
+			gagajf.ajaxFormSubmit('/business/bizday2/save', '#calendarForm', function() {
+				arg.event.remove();
+			});
+		}
+	}
+	
+	// 캘린더 생성
+	var calendar;
+	var fnCreateCalendar = function() {
+		var calendarEl = document.getElementById('calendar');
+		
+		calendar = new FullCalendar.Calendar(calendarEl, {
+			plugins: [ 'interaction', 'dayGrid' ],
+			locale: 'ko', // 한글화
+// 			weekNumberCalculation: 'ISO', //월~일 순서로
+			selectable: true,
+			editable: true,
+			eventLimit: true, // allow "more" link when too many events
+
+			select: function(arg) {
+				if ((new Date(arg.end)).format('YYYYMMDD') - (new Date(arg.start)).format('YYYYMMDD') > 1) return;
+				var title ='휴일';
+				
+				mcxDialog.confirm("휴일로 변경하시겠습니까?", {
+					cancelBtnText: "취소",
+					sureBtnText: "확인",
+					sureBtnClick: function() {
+						fnUpdateBizday('Holiday', arg);
+					}
+				});
+				calendar.unselect();
+			},
+
+			// 영업일로 변경 -----
+			eventClick: function(arg) {
+				mcxDialog.confirm("영업일로 변경하시겠습니까?", {
+					cancelBtnText: "취소",
+					sureBtnText: "확인",
+					sureBtnClick: function() {
+						fnUpdateBizday('Bizday', arg);
+					}
+				});
+			},
+
+			events: function(info, callback) {
+				var dt = setViewDate(info);
+				$('#calendarForm input[name=startDt]').val(dt[0]);
+				$('#calendarForm input[name=endDt]').val(dt[1]);
+				$.get('/business/holiday2/list' + '?' + $('#calendarForm').serialize()
+					, function(data) {
+						var events = [];
+						for (var i = 0 ; i < data.length ; i++) {
+							events.push({
+								title : (gagajf.isNull(data[i].restdayDesc) ? '' : data[i].restdayDesc),
+								start : data[i].bizday
+							});
+						}
+						callback(events);
+					});
+			}
+		});
+		
+		calendar.render();
+	}
+
+	$(document).ready(function() {
+		fnCreateCalendar();
+	});
+/*]]>*/
+</script>
+
+</html>

+ 152 - 0
src/main/webapp/WEB-INF/views/business/SupplyCompanyPopupForm2.html

@@ -0,0 +1,152 @@
+<!DOCTYPE html>
+<html lang="ko"
+	  xmlns:th="http://www.thymeleaf.org">
+<!--
+ *******************************************************************************
+ * @source  : SupplyCompanyPopupForm2.html
+ * @desc    : 공급업체 목록 페이지
+ *============================================================================
+ * STYLE24
+ * Copyright(C) 2020 TSIT, All rights reserved.
+ *============================================================================
+ * VER  DATE         AUTHOR      DESCRIPTION
+ * ===  ===========  ==========  =============================================
+ * 1.0  2020.12.23   xodud1202   최초 작성
+ *******************************************************************************
+ -->
+<div class="modalPopup" data-width="530" id="popupCompanyList2">
+	<div class="panelStyle"  style="max-height:700px;overflow-y:scroll;">
+		<!-- TITLE -->
+		<div class="panelTitle">
+			<strong>공급업체 목록</strong>
+			<button type="button" class="close" onclick="uifnPopupClose('popupCompanyList2');"><em class="fa fa-times"></em></button>
+		</div>
+		<!-- //TITLE -->
+		<!-- 검색 조건 -->
+		<div class="panelContent">
+			<form id="searchCompanyListForm" name="searchCompanyListForm" action="#" th:action="@{'/business/supply/company/scm/list'}" onsubmit="$('#btnSearchCompanyList').trigger('click'); return false;">
+				<input type="hidden" name="searchGb" value="NAME" />		<!-- 공급업체 목록 검색 조건은 업체명으로만 -->
+				<table class="frmStyle" aria-describedby="검색조건">
+					<colgroup>
+						<col style="width:15%;"/>
+						<col style="width:35%;"/>
+						<col style="width:15%;"/>
+						<col/>
+					</colgroup>
+					<tbody>
+						<tr>
+							<th>사용여부</th>
+							<td colspan="3">
+								<select name="useYn" id="useYn">
+									<option value="">전체</option>
+									<option value="Y" selected>사용</option>
+									<option value="N">중지</option>
+								</select>
+							</td>
+						</tr>
+						<tr>
+							<th>업체코드<i class="required" title="필수"></i></th>
+							<td>
+								<textarea class="textareaR2" name="searchSupplyCompCd" id="searchSupplyCompCd"></textarea>
+							</td>
+							<th>업체명<i class="required" title="필수"></i></th>
+							<td>
+								<textarea class="textareaR2" name="searchSupplyCompNm" id="searchSupplyCompNm"></textarea>
+							</td>
+						</tr>
+					</tbody>
+				</table>
+				<ul class="panelBar">
+					<li class="center">
+						<button type="button" class="btn btn-base btn-lg" id="btnSearchCompanyList">조회</button>
+					</li>
+				</ul>
+			</form>
+			<!-- 리스트 영역 -->
+			<div class="panelContent">
+				<div id="gridComapanyPopupList" style="width: 100%; height: 380px" class="ag-theme-balham"></div>
+			</div>
+			<!-- //리스트 영역 -->
+	
+			<!-- 버튼 배치 영역 -->
+			<ul class="panelBar">
+				<li class="right">
+					<button type="button" class="btn btn-info btn-lg" id="btnConfirmCompany">확인</button>
+				</li>
+			</ul>
+		</div>
+		<!-- //검색 조건 -->
+	</div>
+	<script th:inline="javascript">
+		/*<![CDATA[*/
+		let headerSelection = false;
+		if([[${params.multiGb}]] == "M") headerSelection = true;
+		let columnCompanyPopupDefList = [
+			{width: 40, minWidth: 40, cellClass: 'text-center', headerCheckboxSelection: headerSelection, checkboxSelection: true, filter: false},
+			{headerName: "공급업체번호", field: "supplyCompCd", width: 120, cellClass: 'text-center'},
+			{headerName: "공급업체국문명", field: "supplyCompNm", width: 150, cellClass: 'text-center'},
+			{headerName: "입점상태", field: "supplyStatNm", width: 150, cellClass: 'text-center'}
+		];
+
+		let gridOptionsCompanyPopupList = gagaAgGrid.getGridOptions(columnCompanyPopupDefList);
+		if(headerSelection) {	gridOptionsCompanyPopupList.rowSelection = "multiple";	}
+
+		// Row double click
+		gridOptionsCompanyPopupList.onRowDoubleClicked = function(event) {
+			$('#btnConfirmCompany').trigger('click');
+		}
+
+		// 조회
+		$('#btnSearchCompanyList').on('click', function() {
+			
+			// if (gagajf.isNull($('#searchCompanyListForm textarea[name=searchSupplyCompCd]').val())  && gagajf.isNull($('#searchCompanyListForm textarea[name=searchSupplyCompNm]').val())){
+			// 	mcxDialog.alert('검색조건을 입력하세요.');
+			// 	return false;
+			// }
+			
+			// Fetch data
+			gagaAgGrid.fetch($('#searchCompanyListForm').prop('action'), gridOptionsCompanyPopupList, '#searchCompanyListForm');
+		});
+
+		// 확인
+		$('#btnConfirmCompany').on('click', function() {
+			var selectedData = gagaAgGrid.selectedRowData(gridOptionsCompanyPopupList);
+
+			if (selectedData.length == 0) {
+				mcxDialog.alert('선택된 공급업체가 없습니다.');
+				return false;
+			}
+
+			var callbackFn = [[${params.callbackFn}]];
+
+			var jsonData = JSON.stringify(selectedData);
+
+			if (typeof callbackFn != 'undefined' && callbackFn) {
+				if (typeof callbackFn == 'function') {
+					callbackFn(jsonData);
+				} else {
+					if (callbackFn) {
+						if (callbackFn.indexOf("(") == -1) {
+							(new Function(callbackFn + "(" + jsonData + ");"))();
+						} else {
+							(new Function(callbackFn(jsonData)))();
+						}
+					}
+				}
+				uifnPopupClose('popupCompanyList2');
+			}
+		});
+
+		$(document).ready(function() {
+			// Create a agGrid
+			gagaAgGrid.createGrid('gridComapanyPopupList', gridOptionsCompanyPopupList);
+
+			//  조회
+			//$('#btnSearchCompanyList').trigger('click');
+		});
+		/*]]>*/
+	</script>
+
+</div>
+
+</html>

+ 1 - 1
src/main/webapp/WEB-INF/views/dashboard.html

@@ -48,4 +48,4 @@
 </div>
 
 </body>
-</html>
+</html>

+ 612 - 0
src/main/webapp/WEB-INF/views/delivery/DeliveryListScmForm.html

@@ -0,0 +1,612 @@
+<!DOCTYPE html>
+<html lang="ko"
+	  xmlns:th="http://www.thymeleaf.org">
+<!--
+ *******************************************************************************
+ * @source  : DeliveryListForm.html
+ * @desc    : 배송목록(입점)Page
+ *============================================================================
+ * ISTYLE24
+ * Copyright(C) 2020 TSIT, All rights reserved.
+ *============================================================================
+ * VER  DATE         AUTHOR      DESCRIPTION
+ * ===  ===========  ==========  =============================================
+ * 1.0  2021.09.15   moon        최초 작성
+ *******************************************************************************
+ -->
+<div id="main">
+	<!-- 메인타이틀 영역 -->
+	<div class="main-title">
+	</div>
+	<!-- //메인타이틀 영역 -->
+
+	<!-- 메뉴 설명 -->
+	<div class="infoBox menu-desc">
+	</div>
+	<!-- //메뉴 설명 -->
+	<!-- 검색조건 영역 -->
+	<form id="searchForm" name="searchForm" action="#" th:action="@{'/delivery/scm/list/'}" onsubmit="fnSearchList(); return false;">
+	<div class="panelStyle">
+		<!-- TITLE -->
+		<div class="panelTitle">
+			<h3><i class="fa fa-info-circle"></i>아래 검색조건 <font color="red">기간, 키워드</font>중 하나를 꼭 입력해 주세요.</h3>
+			<span class="panelControl">
+				<i class="fa fa-chevron-up"></i>
+			</span>
+		</div>
+		<!-- //TITLE -->
+		<div class="panelContent">
+
+				<table class="frmStyle">
+					<colgroup>
+						<col style="width:8%;"/>
+						<col style="width:12%;"/>
+						<col style="width:8%;"/>
+						<col style="width:12%;"/>
+						<col style="width:8%;"/>
+						<col style="width:12%;"/>
+						<col style="width:8%;"/>
+						<col style="width:12%;"/>
+					</colgroup>
+					<tr>
+						<th>업체</th>
+						<td>
+							<input type="text" class="w100" name="supplyCompSearchTxt" id="supplyCompSearchTxt" maxlength="20" />
+							<button type="button" class="btn icn" id="btnSearchSupplyComp"><i class="fa fa-search"></i></button>
+							<span id="supplyCompText"></span>
+							<input type="hidden" name="supplyCompList"/>
+						</td>
+
+						<th>주문상세상태</th>
+						<td colspan="3">
+							<div class="multiCheckBox" style="width:190px">
+								<button type="button" class="sltBtn" data-name="[전체]" style="overflow-x: hidden; padding-right:5px;">[전체]</button>
+								<ul style="display: none; box-shadow: 3px 3px 3px; overflow-y: scroll; height: 112px;" id="group1">
+									<li th:if="${ordDtlStatList}" th:each="oneData, status : ${ordDtlStatList}">
+										<label class="chkBox" data-group="group1">
+											<input type="checkbox" name="multiOrdDtlStat" th:value="${oneData.cd}" th:text="|[${oneData.cd}] ${oneData.cdNm}|">
+										</label>
+									</li>
+								</ul>
+							</div>
+						</td>
+						
+						<th rowspan="5">키워드<em class="required" title="필수"></em><i class="star"></i></th>
+						<td rowspan="5" colspan="5">
+							<select class="w200" name="search" id="search">
+								<option value="searchOrdNo">주문번호</option>
+								<option value="searchCustId">고객ID</option>
+							</select>
+							<textarea class="textareaR3 w90p" name="condition" id="condition"></textarea>
+						</td>
+						
+												
+					</tr>
+					<tr>
+						<th>주문자명</th>
+						<td>
+							<input type="text" class="" name="orderNm" placeholder="" maxlength="20"/>
+						</td>
+						<th>주문자휴대폰번호</th>
+						<td>
+							<input type="text" class="" name="orderPhnno" placeholder="" maxlength="20"/>
+						</td>
+						<th>주문상세번호</th>
+						<td>
+							<input type="text" class="w200" name="ordDtlNo" oninput="this.value = this.value.replace(/[^0-9.]/g, '').replace(/(\..*)\./g, '$1');" placeholder="" maxlength="9"/>
+						</td>
+
+					</tr>
+					<tr>
+						<th>수령인</th>
+						<td>
+							<input type="text" class="" name="recipNm" placeholder="" maxlength="20"/>
+						</td>
+						<th>송장번호</th>
+						<td>
+							<input type="text" class="" name="invoiceNo" placeholder="" maxlength="20"/>
+						</td>
+						<th>상품코드</th>
+						<td>
+							<input type="text" class="w200" name="goodsCd" placeholder="" maxlength="20"/>
+						</td>
+					</tr>
+					<tr>
+						<th>고객ID</th>
+						<td>
+							<input type="text" class="" name="custId" placeholder="" maxlength="20" />
+						</td>
+						<th>배송지연일</th>
+						<td colspan="4">
+							<input type="text" class="w50" name="delvDelayDays" data-valid-type="integer" placeholder="" maxlength="3" style="width:20%;"/>일
+							이상(결제일 기준)
+						</td>
+					</tr>
+					<tr>
+						<th>기간<em class="required" title="필수"></em></th>
+						<td colspan="8">
+							<select name="termGb" id="termGb">
+								<option value="ordDt">주문등록일</option>
+								<option value="delvDt">배송일자</option>
+								<option value="delvStDt">배송시작일자</option>
+							</select>
+							<span id="terms"></span>
+						</td>
+					</tr>
+
+				</table>
+				<ul class="panelBar">
+					<li class="center">
+					<button type="button" class="btn btn-base btn-lg" id="btnSearch">조회</button>
+					<button type="button" class="btn btn-gray btn-lg" onclick="$('#searchForm')[0].reset(); fnInitCalendar(); $('#multiBrand').empty(); fnInitSupplyComp();">초기화</button>
+					<button type="button" id="btnExcel" class="btn btn-info btn-lg">엑셀다운로드</button>
+					</li>
+				</ul>
+
+		</div>
+	</div>
+	<!-- //검색조건 영역 -->
+
+	<!-- 리스트 영역 -->
+	<div class="panelStyle">
+		<ul class="panelBar">
+			<li class="left">
+				<!--  <button type="button" id="btnSoldout" class="btn btn-danger btn-lg">품절처리</button> -->
+				<!-- <button type="button" id="btnSave" class="btn btn-success btn-lg btnRight" onclick="deliveryInfoSave();">저장</button>
+				<button type="button" id="btnWith" class="btn btn-success btn-lg btnRight">T</button> -->
+			</li>
+			<li class="right">
+				검색결과 : <strong><span id="gridRowTotalCount">0</span> 건</strong>&nbsp;
+				쪽번호 <span id="pgNo">0</span>/ <strong id="endPgNo">0</strong>&nbsp;&nbsp;
+				<select id="pageSize" name="pageSize">
+					<option value="50" selected="selected">50개씩 보기</option>
+					<option value="100">100개씩 보기</option>
+					<option value="500">500개씩 보기</option>
+					<option value="1000">1000개씩 보기</option>
+					<option value="3000">3000개씩 보기</option>
+					<option value="5000">5000개씩 보기</option>
+				</select>
+				<input type="hidden" name="pageNo" id="pageNo" value ="1"/>
+			</li>
+		</ul>
+
+		<div id="gridDeliveryList" style="width:100%; height: 700px;" class="ag-theme-balham"></div>
+		<ul class="panelBar">
+			<li class="center">
+				<div class="tablePaging" id="deliveryListPagination"></div>
+			</li>
+		</ul>
+	</div>
+	</form>
+	<!-- //리스트 영역 -->
+</div>
+<script type="text/javascript" src="/ux/plugins/gaga/gaga.paging.js?v=20210114"></script>
+<script th:inline="javascript">
+	/*<![CDATA[*/
+	/*************************************************************************
+	* AG-GRID 영역
+	**************************************************************************/
+	var shipCompanyList =  gagajf.convertToArray([[${shipCompanyList}]]);
+	var roleCd          = [[${sessionInfo.roleCd}]];
+	var currOrdNo       = 0;
+	var columnDefs = [
+		/*
+		{
+			headerName: "결품",
+			field: "soldout",
+			width: 50,
+			cellClass: 'text-center',
+			headerCheckboxSelection: true,
+			headerCheckboxSelectionFilteredOnly: true
+			,
+			checkboxSelection: function (params) {
+				return (params.data.ordDtlStat == 'G013_20') ? true : false;
+			}
+		},
+		*/
+		{headerName: "지연일",	field: "delvDelayDays", 	width: 70, cellClass: 'text-center'},
+		{headerName: "업체명", 	field: "supplyCompNm", 	width: 150, cellClass: 'text-center'},
+		{headerName: "주문번호",	field: "ordNo", width: 95, cellClass: 'text-center',
+			cellRenderer: function (params) {
+				if (roleCd.indexOf("C") < 0) {
+					return "<a href=\"javascript:void(0);\" onclick=\"fnOrderDetailPopup('" + params.data.ordNo + "');\">" + params.data.ordNo + "</a>";
+				} else {
+					return params.value;
+				}
+			}
+		},
+		{headerName: "주문상세번호", 	field: "ordDtlNo", 		width: 90, cellClass: 'text-center'},
+		{headerName: "주문상세상태", 	field: "ordDtlStatNm", 	width: 120, cellClass: 'text-center'},
+		{headerName: "주문교환", 		field: "ordExchGb", 	width: 80, cellClass: 'text-center',
+			cellRenderer: function (params) {
+				if (params.value == "Y") {
+					return "교환";
+				} else {
+					return "주문";
+				}
+			}
+		},
+		{headerName: "판매몰명", 		field: "extmallNm", 	width: 150, cellClass: 'text-left'},
+		{headerName: "주문일시", 		field: "ordDt", 		width: 150, cellClass: 'text-center',
+			cellRenderer: function (params) {
+				return !gagajf.isNull(params.value) ? gagaAgGrid.toDateTimeFormat(params.value) : '';
+			}
+		},
+		{headerName: "결제일시", 		field: "ordDt", 		width: 150, cellClass: 'text-center',
+			cellRenderer: function (params) {
+				return !gagajf.isNull(params.value) ? gagaAgGrid.toDateTimeFormat(params.value) : '';
+			}
+		},
+		{headerName: "몰구분", 		field: "mallGbNm", 		width: 70, cellClass: 'text-center'},
+		{headerName: "주문자", 		field: "maskingOrdNm", 		width: 100, cellClass: 'text-center',
+			cellRenderer: function (params) {
+				if (roleCd.indexOf("C") < 0 && !gagajf.isNull(params.value) && params.data.mallGb === 'G011_10' && params.data.custNo > 0) {
+					return '<a href="javascript:void(0);" onclick=\"cfnOpenCustDetailPopup(' + params.data.custNo + ');\">' + params.data.maskingOrdNm + '</a>';
+				} else {
+					return params.data.maskingOrdNm;
+				}
+			}
+		},
+		{headerName: "고객ID", 			field: "custId", 		width: 100, cellClass: 'text-center'},
+		{headerName: "휴대번호", 		field: "maskingOrdPhnno", 		width: 100, cellClass: 'text-center',
+			valueGetter: function (params) { return params.data.maskingOrdPhnno; }
+		},
+		{headerName: "LMS", 			field: "maskingOrdPhnno", 	width: 80, cellClass: "text-center",
+			cellRenderer: function(params) {
+				return '<button type="button" class="btn btn-base btn-sm" onclick="fnLms(\'' + params.data.ordPhnno + '\',\'' + params.data.custNo + '\');">&nbsp;LMS&nbsp;</button>';
+			}
+		},
+		{headerName: "수령인", 		field: "maskingRecipNm", 		width: 100, cellClass: 'text-center'},
+		
+		{headerName: "상품코드", 		field: "goodsCd", 		width: 120, cellClass: 'text-center',
+			cellRenderer: function (params) {
+				if (roleCd.indexOf("C") < 0) {
+					return "<a href=\"javascript:void(0);\" onclick=\"cfnOpenGoodsDetailPopup('U','" + params.value + "');\">" + params.value + "</a>";
+				} else {
+					return params.value;
+				}
+			}
+		},
+		{headerName: "구성유형", 		field: "goodsTypeNm",	 width: 130, cellClass: 'text-center',
+			cellRenderer: function (params) {
+				var option;
+				if (params.data.goodsType == 'G056_S') {
+					option = "<a href=\"javascript:void(0);\" onclick=\"fnOrderDetailItemForm('" + params.data.ordDtlNo + "');\">" + params.value + "</a>";
+				} else {
+					option = params.value
+				}
+				return option;
+			}
+		},
+		{headerName: "상품명", 		field: "goodsNm", 		width: 280, cellClass: 'text-left'},
+		{headerName: "옵션코드", 		field: "optCd", 		width: 100, cellClass: 'text-left'},
+		{headerName: "옵션코드1", 		field: "optCd1", 		width: 100, cellClass: 'text-center'},
+		{headerName: "옵션코드2", 		field: "optCd2", 		width: 100, cellClass: 'text-center'},
+		{headerName: "주문수량", 		field: "ordQty", 		width: 80, cellClass: 'text-center'},
+		{headerName: "취소수량", 		field: "cnclRtnQty", 	width: 80, cellClass: 'text-center'},
+		{headerName: "판매수량", 		field: "saleQty", 		width: 80, cellClass: 'text-right'},
+		{headerName: "판매금액", 		field: "saleAmt", 		width: 100, cellClass: 'text-right'
+			, valueFormatter: function (params) {
+				return params.value.addComma();
+			}
+		},
+		{headerName: "실결제금액", 	field: "realOrdAmt", 	width: 100, cellClass: 'text-right'
+			, valueFormatter: function (params) {
+				return params.value.addComma();
+			}
+		},
+		{headerName: "출고택배사", 	field: "shipCompCd", 	width: 170, cellClass: 'text-center'
+			, valueGetter: function (params) { return gagaAgGrid.lookupValue(shipCompanyList, params.data.shipCompCd); }
+		},
+		{headerName: "배송추적", 		field: "invcTracking", 	width: 80, cellClass: 'text-center',
+			cellRenderer: function (params) {
+				if (params.value == "Y") {
+					return "요청";
+				} else {
+					return "미요청";
+				}
+			}
+		},
+		{headerName: "출고송장", 		field: "invoiceNo", 	width: 150, cellClass: 'text-left'},
+		{headerName: "송장등록수정", 	field: "invoiceNo", 	width: 120, cellClass: 'text-center'
+			, cellRenderer : function (params) {
+				var buttonTag = '';
+				if (params.data.ordDtlStat == 'G013_30' || params.data.ordDtlStat == 'G013_40' || params.data.ordDtlStat == 'G013_50' || params.data.ordDtlStat == 'G013_55') {
+					buttonTag = '<button type="button"class="btn btn-success" onClick="fnSaveInvoiceNo('+params.data.ordDtlNo+');">송장등록수정</button>';
+
+				}
+				return buttonTag;
+			}
+		},
+		{headerName: "배송완료처리", 	field: "ordDtlStat", width: 120, cellClass: 'text-center'
+			, cellRenderer: function(params) {
+				var buttonTag = '';
+				if (params.value == 'G013_50' || params.value == 'G013_55'  ) {
+					buttonTag = '<button type="button"class="btn btn-success" onClick="deliveryComplete(\''+params.data.ordNo+ '\' , \''+params.data.ordDtlNo+'\' , \'' + params.data.ordDtlStat + '\');">배송완료</button>';
+
+				}
+				return buttonTag;
+			}
+		},
+		{headerName: "배송메모", 		field: "delvMemo", 		width: 200, cellClass: 'text-left'},
+		{headerName: "우편번호", 		field: "recipZipcode", 		width: 80, cellClass: 'text-center'},
+		{headerName: "기본주소", 		field: "recipBaseAddr", 	width: 200, cellClass: 'text-left'},
+		{headerName: "상세주소", 		field: "maskingRecipDtlAddr", 		width: 200, cellClass: 'text-left'},
+		{headerName: "product_no", 	field: "productNo", 	width: 100, cellClass: 'text-center'},
+		{headerName: "product_code",field: "productCode", 	width: 100, cellClass: 'text-center'}
+
+	];
+
+	//Get GridOptions
+	var gridOptions = gagaAgGrid.getGridOptions(columnDefs);
+
+	//Grid editable
+	//gridOptions.defaultColDef.editable = true;
+
+	gridOptions.suppressRowClickSelection = true;
+	gridOptions.rowSelection = 'multiple';
+	gridOptions.isRowSelectable = function(rowNode) {
+		return rowNode.data.ordDtlStat == 'G013_20' || rowNode.data.ordDtlStat == 'G013_25';
+	}
+	gridOptions.getRowStyle = function (params) {
+		if (params.data.ordExchGb === 'Y') {
+			return {background: 'orange'}
+		}
+	}
+
+	var fnInitCalendar = function () {
+		$(".btnToday").trigger('click');
+	}
+
+	var fnInitSupplyComp = function(){
+		$("#searchForm #supplyCompText").text("");
+		$('#searchForm input[name=supplyCompList]').val('');
+	}
+
+	
+	
+	/*************************************************************************
+	*  주문상세 팝업
+	**************************************************************************/
+	var fnOrderDetailPopup = function(ordNo){
+		currOrdNo = ordNo;
+		cfnOpenOrderDetailPopup(currOrdNo);
+	}
+
+	/*************************************************************************
+	*  팝업 콜백
+	**************************************************************************/
+	var fnReOpenOrderDetailPopup = function () {
+		cfnOpenOrderDetailPopup(currOrdNo);
+		fnSearchList();
+	};
+
+
+	/*************************************************************************
+	* 조회 클릭
+	**************************************************************************/
+	$('#btnSearch').on('click', function () {
+		$("#searchForm input[name=pageNo]").val('1');
+		fnSearchList();
+	});
+
+	/*************************************************************************
+	* 조회
+	**************************************************************************/
+	var fnSearchList = function () {
+
+		if ($('#searchForm input[name=ordNo]').val() == '') {
+			if ($('#stDate').val() == '') {
+				mcxDialog.alert('시작 기간을 입력하세요.');
+				return;
+			}
+
+			if ($('#edDate').val() == '') {
+				mcxDialog.alert('종료 기간을 입력하세요.');
+				return;
+			}
+		}
+
+		if ($('#searchForm input[name=delvDelayDays]').val() != '') {
+			if ($('#stDate').val() == '') {
+				mcxDialog.alert('시작 기간을 입력하세요.');
+				return;
+			}
+
+			if ($('#edDate').val() == '') {
+				mcxDialog.alert('종료 기간을 입력하세요.');
+				return;
+			}
+		}
+
+		gagaPaging.init('searchForm', fnSearchCallBack, 'deliveryListPagination', $('#searchForm').find('#pageSize').val());
+	    gagaPaging.load($("#searchForm input[name=pageNo]").val());
+
+	}
+
+	// 페이징
+	$('#searchForm select[name=pageSize]').on('change', function() {
+		$("#searchForm input[name=pageNo]").val('1');
+		fnSearchList();
+	});
+
+
+	/*************************************************************************
+	* 조회 콜백
+	**************************************************************************/
+	var fnSearchCallBack = function(result){
+
+		$('#searchForm').find('#gridRowTotalCount').html(result.pageing.pageable.totalCount.addComma());
+		$('#searchForm').find('#pageNo').val(result.pageing.pageable.pageNo.addComma());
+		$('#searchForm').find('#pgNo').html(result.pageing.pageable.pageNo.addComma());
+		$('#searchForm').find('#endPgNo').html(result.pageing.pageable.totalPage.addComma());
+		gridOptions.api.setRowData(result.deliveryList);
+		gagaPaging.createPagination(result.pageing.pageable);
+
+	}
+
+
+	/*************************************************************************
+	* 구성상품 내역 팝업 호출
+	**************************************************************************/
+	var fnOrderDetailItemForm = function (ordDtlNo) {
+		var actionUrl = "/delivery/detail/item/form/" + ordDtlNo;
+		cfnOpenModalPopup(actionUrl, 'popupDeliveryDetailItemForm');
+	}
+
+	/*************************************************************************
+	*  LMS
+	**************************************************************************/
+	var fnLms = function(chgerPhnno, custNo){
+		let param = {};
+		param.elementCellPhnno = chgerPhnno;
+		param.elementCustNo =    custNo;
+		param.pageGb = 'delv';
+		cfnOpenLmsPopup2(param);
+	}
+
+
+	/*************************************************************************
+	* 엑셀다운로드
+	**************************************************************************/
+	$('#btnExcel').on('click', function () {
+		var totalRows = gridOptions.api.getDisplayedRowCount();
+		if (totalRows == 0) {
+			mcxDialog.alert('조회된 내역이 없습니다.');
+			return;
+		}
+		var date = new Date().format("YYYYMMDDHHmmss");
+		var params = {
+
+			fileName: "배송목록_" + date,
+			sheetName: "DATA"
+		}
+		gridOptions.excelStyles = [
+			{
+				id: 'dateFormat',
+				dataType: 'dateTime',
+				numberFormat: {
+					format: 'YYYY-MM-DD;@'
+				}
+			},
+			{
+				id: 'textFormat',
+				dataType: 'string'
+			}
+		]
+		gridOptions.api.exportDataAsExcel(params);
+	});
+
+
+	/*************************************************************************
+	* 품절처리
+	**************************************************************************/
+	$('#btnSoldout').on('click', function () {
+		var selectedData = gridOptions.api.getSelectedRows();
+
+		if (selectedData.length == 0) {
+			mcxDialog.alert('선택된 행이 없습니다.');
+			return;
+		}
+
+		mcxDialog.confirm('품절 처리하시겠습니까?', {
+			cancelBtnText: "취소",
+			sureBtnText: "확인",
+			sureBtnClick: function () {
+				var jsonData = JSON.stringify(selectedData);
+				gagajf.ajaxJsonSubmit('/delivery/list/soldout'
+					, jsonData
+					, function () {
+						$('#btnSearch').trigger('click');
+				});
+			}
+		});
+	});
+
+
+	/*************************************************************************
+	* 배송완료처리 -수동
+	**************************************************************************/
+	var deliveryComplete = function (ordNo,ordDtlNo, odStat) {
+
+		mcxDialog.confirm('배송완료 처리를 하시겠습니까?', {
+			cancelBtnText: "취소",
+			sureBtnText: "확인",
+			sureBtnClick: function () {
+				var jsonData = {
+					"ordNo": ordNo,
+					"ordDtlNo": ordDtlNo,
+					"orgOrdDtlStat": odStat
+				};
+				var tranData = JSON.stringify(jsonData);
+				gagajf.ajaxJsonSubmit('/delivery/complete/save', tranData, fnSearchList);
+			}
+		});
+	}
+
+	/*************************************************************************
+	* 송장변경 팝업호출
+	**************************************************************************/
+	var fnSaveInvoiceNo = function (ordDtlNo) {
+		var actionUrl = "/delivery/save/invoice/form/" + ordDtlNo ;
+		cfnOpenModalPopup(actionUrl, 'popupChangeInvoice');
+	};
+
+	/*************************************************************************
+	*  업체 콤보박스 변경 시
+	**************************************************************************/
+	$('#searchForm select[name=supplyCompCd]').on('change', function() {
+		var actionUrl = '/renderer/supplyCompany/brand/list/'+ $(this).val();
+		cfnCreateMultiCombo(actionUrl, "multiBrand",  "[전체]", null, 'Y');
+		var actionUrl2 = '/renderer/delvloc/list/'+ $(this).val();
+		cfnCreateCombo(actionUrl2, $('#searchForm select[name=delvLocCd]'), "[전체]");
+	});
+
+	// 업체 조회 선택시
+	$('#btnSearchSupplyComp').on('click', function() {
+		cfnOpenCompanyListPopup2('fnSetSupplyCompInfo', 'M');
+	});
+
+	// 업체 조회 팝업에서 호출
+	var fnSetSupplyCompInfo = function(result) {
+		var arrSupplyComp 	= [];
+		var supplyCompText 	= "";
+		var sIndex 			= 0;
+
+		$('#searchForm').find('#supplyCompText').html('');
+		$('#searchForm input[name=supplyCompSearchTxt]').val('');
+
+		result.forEach(function(supplyComp){
+			sIndex++;
+			arrSupplyComp.push(supplyComp.supplyCompCd);
+		});
+
+		// 조회값이 하나일 경우 화면에 코드 노출 그외는 갯수 처리
+		if (sIndex == 1) {
+			$('#searchForm input[name=supplyCompSearchTxt]').val(arrSupplyComp[0]);
+		} else {
+			supplyCompText = sIndex + " 개";
+			$('#searchForm').find('#supplyCompText').html(supplyCompText);
+		}
+
+		var jsonData = JSON.stringify(arrSupplyComp);
+		$("#searchForm input[name=supplyCompList]").val(jsonData);
+	}
+	
+
+	
+	/*************************************************************************
+	* init
+	**************************************************************************/
+	$(document).ready(function () {
+		gagaAgGrid.createGrid('gridDeliveryList', gridOptions);
+		var hideList = ["btnThisWeek", "btnYesterWeek", "btnRecentMonth", "btnThisMonth", "btnYesterMonth", "btnRecent3Month"];
+		cfnCreateCalendar('#terms', 'stDate', 'edDate', true, '주문', '', hideList);
+		$(".btnToday").trigger('click');
+		$('#searchForm select[name=mallGb]').trigger('change');
+		$('#searchForm').find('#multiBrand').empty();
+	});
+
+	/*]]>*/
+</script>
+</html>

+ 3 - 3
src/main/webapp/WEB-INF/views/order/OrderListForm.html

@@ -516,12 +516,12 @@ var fnSearchList = function () {
 	var edDate 	= $('#edDate').val();
 
 	if (gagajf.isNull(ordNo)) {
-		if (gagajf.isNull(stDate)) {
+		if (gagajf.isNull($('#searchForm input[name=orderPhnno]').val()) && gagajf.isNull(stDate)) {
 			mcxDialog.alert('시작 기간을 입력하세요.');
 			return;
 		}
 
-		if (gagajf.isNull(edDate)) {
+		if (gagajf.isNull($('#searchForm input[name=orderPhnno]').val()) && gagajf.isNull(edDate)) {
 			mcxDialog.alert('종료 기간을 입력하세요.');
 			return;
 		}
@@ -533,7 +533,7 @@ var fnSearchList = function () {
 	var brandText 				= $("#searchForm #brandText").val();
 	var brandList 				= $('#searchForm input[name=brandList]').val();
 	
-	if (gagajf.isNull(stDate) && gagajf.isNull(edDate)) {
+	if (gagajf.isNull($('#searchForm input[name=orderPhnno]').val()) && gagajf.isNull(stDate) && gagajf.isNull(edDate)) {
 		var temp = false;
 		
 		if (!gagajf.isNull(ordNo)) {

+ 1 - 1
src/main/webapp/WEB-INF/views/statistics/BestTradingForm.html

@@ -95,7 +95,7 @@
 						<td>
 							<input type="text" class="w100" name="itemkindCdSearchTxt" id="itemkindCdSearchTxt" maxlength="20" />
 							<button type="button" class="btn icn" onclick="cfnOpenItemkindListPopup('fnSetItemkindInfo', 'M');"><i class="fa fa-search"></i></button>
-							<span id="itemkindTxt"></span>
+							<span id="itemkindCdTxt"></span>
 							<input type="hidden" name="itemkindCdList"/>
 						</td>
 					</tr>

+ 1 - 1
src/main/webapp/WEB-INF/views/statistics/BrandTradingForm.html

@@ -89,7 +89,7 @@
 						<td>
 							<input type="text" class="w100" name="itemkindCdSearchTxt" id="itemkindCdSearchTxt" maxlength="20" />
 							<button type="button" class="btn icn" onclick="cfnOpenItemkindListPopup('fnSetItemkindInfo', 'M');"><i class="fa fa-search"></i></button>
-							<span id="itemkindTxt"></span>
+							<span id="itemkindCdTxt"></span>
 							<input type="hidden" name="itemkindCdList"/>
 						</td>
 					</tr>

+ 1 - 1
src/main/webapp/WEB-INF/views/statistics/ChannelTradingForm.html

@@ -71,7 +71,7 @@
 						<td>
 							<input type="text" class="w100" name="itemkindCdSearchTxt" id="itemkindCdSearchTxt" maxlength="20" />
 							<button type="button" class="btn icn" onclick="cfnOpenItemkindListPopup('fnSetItemkindInfo', 'M');"><i class="fa fa-search"></i></button>
-							<span id="itemkindTxt"></span>
+							<span id="itemkindCdTxt"></span>
 							<input type="hidden" name="itemkindCdList"/>
 						</td>
 					</tr>

+ 1 - 1
src/main/webapp/WEB-INF/views/statistics/ClaimTradingForm.html

@@ -82,7 +82,7 @@
 						<td>
 							<input type="text" class="w100" name="itemkindCdSearchTxt" id="itemkindCdSearchTxt" maxlength="20" />
 							<button type="button" class="btn icn" onclick="cfnOpenItemkindListPopup('fnSetItemkindInfo', 'M');"><i class="fa fa-search"></i></button>
-							<span id="itemkindTxt"></span>
+							<span id="itemkindCdTxt"></span>
 							<input type="hidden" name="itemkindCdList"/>
 						</td>
 					</tr>

+ 5 - 3
src/main/webapp/WEB-INF/views/statistics/CouponTradingForm.html

@@ -75,6 +75,7 @@
 			<ul class="panelBar">
 				<li>
 					<button type="button" class="btn btn-default btn-lg" onclick="fnDetailExcelDownLoad();">엑셀다운로드</button>
+					<span id="couponNmTxt" style="text-align: left"></span>
 				</li>
 			</ul>
 			<div id="detailGridList" style="width: 100%; height: 470px" class="ag-theme-balham"></div>
@@ -155,7 +156,7 @@
 		},
 		{ headerName: "구매율", field: "ordRate", width: 150, cellClass: 'text-right',
 			cellRenderer: function(params) {
-				return !gagajf.isNull(params.value) ? params.value.addComma() : '0';
+				return params.value + '%';
 			}
 		},
 	];
@@ -176,6 +177,7 @@
 			$("#detailSearchForm input[name=startDt]").val($("#searchForm input[name=startDt]").val());
 			$("#detailSearchForm input[name=endDt]").val($("#searchForm input[name=endDt]").val());
 			$("#detailSearchForm input[name=cpnId]").val(params.cpnId);
+			$("#couponNmTxt").text(params.cpnNm);
 			gagaAgGrid.fetch($('#detailSearchForm').prop('action'), detailGridOptions, '#detailSearchForm', fnDetailCreateTotal);
 		}
 	}
@@ -184,10 +186,10 @@
 	detailGridOptions.onCellClicked = function(event) {
 		var params = event.data;
 		if (event.colDef.field == "goodsCd"){
-			cfnOpenGoodsDetailPopup('U',goodsCd);
+			cfnOpenGoodsDetailPopup('U',params.goodsCd);
 		}
 		else if (event.colDef.field == "goodsNm"){
-			cfnOpenGoodsDetailPopup('U',goodsCd);
+			cfnOpenGoodsDetailPopup('U',params.goodsCd);
 		}
 	}
 

+ 242 - 0
src/main/webapp/WEB-INF/views/statistics/CustomerActiveForm.html

@@ -0,0 +1,242 @@
+<!DOCTYPE html>
+<html lang="ko"
+	xmlns:th="http://www.thymeleaf.org">
+<!--
+ *******************************************************************************
+ * @source  : CustomerActiveForm.html
+ * @desc    : 회원활동현황 Page
+ *============================================================================
+ * STYLE24
+ * Copyright(C) 2020 TSIT, All rights reserved.
+ *============================================================================
+ * VER  DATE         AUTHOR      DESCRIPTION
+ * ===  ===========  ==========  =============================================
+ * 1.0  2021.09.28   swkim       최초 작성
+ *******************************************************************************
+ -->
+	<div id="main">
+		<!-- 메인타이틀 영역 -->
+		<div class="main-title"></div>
+		<!-- //메인타이틀 영역 -->
+
+		<!-- 메뉴 설명 -->
+		<div class="infoBox menu-desc"></div>
+		<!-- //메뉴 설명 -->
+
+		<!-- 검색조건 영역 -->
+		<div class="panelStyle">
+			* [[${#calendars.format(#calendars.createNow(), 'yyyy년 MM월 dd일 hh:00:00')}]] / 휴면 회원 제외
+			<!-- 리스트 영역 -->
+			<div class="panelStyle">
+				<ul class="panelBar">
+					<li class="left" style="width: 50%;">
+						<div id="chart1" class="chartUnit c3" style="max-height: 300px; position: relative;"></div>
+						<table class="frmStyle">
+							<colgroup>
+								<col width="10%;"/>
+								<col width="10%;"/>
+								<col width="10%;"/>
+								<col width="10%;"/>
+								<col width="10%;"/>
+								<col/>
+							</colgroup>
+							<tbody>
+								<th>3개월이내</th>
+								<th>~6개월</th>
+								<th>~9개월</th>
+								<th>~12개월</th>
+								<th>1년~</th>
+								<tr>
+									<td class="aC" th:text="${#numbers.formatInteger(unloginList[0].cnt1, 0, 'COMMA')}"></td>
+									<td class="aC" th:text="${#numbers.formatInteger(unloginList[0].cnt2, 0, 'COMMA')}"></td>
+									<td class="aC" th:text="${#numbers.formatInteger(unloginList[0].cnt3, 0, 'COMMA')}"></td>
+									<td class="aC" th:text="${#numbers.formatInteger(unloginList[0].cnt4, 0, 'COMMA')}"></td>
+									<td class="aC" th:text="${#numbers.formatInteger(unloginList[0].cnt5, 0, 'COMMA')}"></td>
+								</tr>
+							</tbody>
+						</table>
+						<button type="button" class="btn btn-default btn-lg" onclick="fnExcelDownLoad('unlogin');">엑셀다운로드</button>
+					</li>
+					<li class="right"  style="width: 50%;">
+						<div id="chart2" class="chartUnit c3" style="max-height: 300px; position: relative;"></div>
+						<table class="frmStyle" style="margin-left: 10%;">
+							<colgroup>
+								<col width="10%;"/>
+								<col width="10%;"/>
+								<col width="10%;"/>
+								<col width="10%;"/>
+								<col width="10%;"/>
+								<col/>
+							</colgroup>
+							<tbody>
+							<th>SMS/LMS</th>
+							<th>이메일</th>
+							<th>푸시</th>
+							<th>미동의</th>
+							<tr>
+								<td class="aC" th:text="${#numbers.formatInteger(marketingList[0].cnt4, 0, 'COMMA')}"></td>
+								<td class="aC" th:text="${#numbers.formatInteger(marketingList[0].cnt3, 0, 'COMMA')}"></td>
+								<td class="aC" th:text="${#numbers.formatInteger(marketingList[0].cnt2, 0, 'COMMA')}"></td>
+								<td class="aC" th:text="${#numbers.formatInteger(marketingList[0].cnt1, 0, 'COMMA')}"></td>
+							</tr>
+							</tbody>
+						</table>
+					</li>
+				</ul>
+				<ul>
+					<li class="left"  style="width: 50%;">
+						<div id="chart3" class="chartUnit c3" style="max-height: 300px; position: relative;"></div>
+						<table class="frmStyle">
+							<colgroup>
+								<col width="10%;"/>
+								<col width="10%;"/>
+								<col width="10%;"/>
+								<col width="10%;"/>
+								<col width="10%;"/>
+								<col/>
+							</colgroup>
+							<tbody>
+							<th>3개월이내</th>
+							<th>6개월이내</th>
+							<th>9개월이내</th>
+							<th>12개월이내</th>
+							<tr>
+								<td class="aC" th:text="${#numbers.formatInteger(dormRemainList[0].cnt1, 0, 'COMMA')}"></td>
+								<td class="aC" th:text="${#numbers.formatInteger(dormRemainList[0].cnt2, 0, 'COMMA')}"></td>
+								<td class="aC" th:text="${#numbers.formatInteger(dormRemainList[0].cnt3, 0, 'COMMA')}"></td>
+								<td class="aC" th:text="${#numbers.formatInteger(dormRemainList[0].cnt4, 0, 'COMMA')}"></td>
+							</tr>
+							</tbody>
+						</table>
+						<button type="button" class="btn btn-default btn-lg" onclick="fnExcelDownLoad('dormRemain');">엑셀다운로드</button>
+					</li>
+				</ul>
+			</div>
+			<a href="javascript:void(0);" id="excelList" style="display: none;"></a>
+		</div>
+		<!-- 검색조건 영역 -->
+
+<script th:inline="javascript">
+/*<![CDATA[*/
+
+	var unloginList = [[${unloginList}]];
+	var marketingList = [[${marketingList}]];
+	var dormRemainList = [[${dormRemainList}]];
+
+	//chart1 미로그인 회원 현황
+	var chart1  =   c3.generate({
+		bindto: "#chart1",
+		data: {
+			columns: [
+				['3개월 이내', unloginList[0].perCnt1],
+				['~6개월'   , unloginList[0].perCnt2],
+				['~9개월'   , unloginList[0].perCnt3],
+				['~12개월'  , unloginList[0].perCnt4],
+				['1년~'    , unloginList[0].perCnt5],
+			],
+			type : 'pie',
+		},
+		title: {
+			text: '미로그인 회원 현황'
+		},
+		color : {pattern : ['#FF7043', '#48C9B0', '#FFD54F', '#FF7043', '#FFD54F']},
+		legend: {
+			padding: 15, //범례 item 우측 간격
+		},
+		axis: {
+			x: {
+				type: 'category',
+				padding: {left:0, right: 0.7}, //x축 data 좌우 여백
+
+			},
+		},
+		padding: {bottom: 40},
+		size: {
+			height: 300
+		},
+
+	});
+
+	//chart2 마케팅 수신동의 현황
+	var chart2  =   c3.generate({
+		bindto: "#chart2",
+		data: {
+			columns: [
+				['SMS/LMS', marketingList[0].perCnt4],
+				['이메일'  , marketingList[0].perCnt3],
+				['푸시'    , marketingList[0].perCnt2],
+				['미동의'  , marketingList[0].perCnt1],
+			],
+			type : 'pie',
+		},
+		title: {
+			text: '마케팅 수신동의 현황'
+		},
+		color : {pattern : ['#FF7043', '#48C9B0', '#FFD54F', '#48C9B0']},
+		legend: {
+			padding: 15, //범례 item 우측 간격
+		},
+		axis: {
+			x: {
+				type: 'category',
+				padding: {left:0, right: 0.7}, //x축 data 좌우 여백
+
+			},
+		},
+		padding: {bottom: 40},
+		size: {
+			height: 300
+		},
+
+	})
+
+	//chart3 휴면전환 잔여일별 회원현황
+	var chart3  =   c3.generate({
+		bindto: "#chart3",
+		data: {
+			// x : 'x',
+			columns: [
+				['data', dormRemainList[0].cnt1, dormRemainList[0].cnt2, dormRemainList[0].cnt3, dormRemainList[0].cnt4],
+			],
+			type : 'bar',
+		},
+		title: {
+			text: '휴면전환 잔여일별 회원현황'
+		},
+		color : {pattern : ['#FF7043', '#48C9B0', '#FFD54F', '#48C9B0']},
+		legend: {
+			padding: 15, //범례 item 우측 간격
+		},
+		grid: {
+			y: {
+				show: true
+			}
+		},
+		axis: {
+			x: {
+				type: 'category',
+				categories: ['3개월이내', '6개월이내', '9개월이내', '12개월이내'],
+				padding: {left:0, right: 0.7}, //x축 data 좌우 여백
+
+			},
+		},
+		padding: {bottom: 40},
+		size: {
+			height: 300
+		},
+
+	});
+
+	// 엑셀다운로드 클릭 시
+	var fnExcelDownLoad = function(type) {
+		var actionUrl = '/statistics/customer/unlogin/excel';
+		if ( type != 'unlogin') actionUrl = '/statistics/customer/dormremain/excel';
+
+		$('#excelList').attr({ href : actionUrl }).get(0).click();
+	}
+
+/*]]>*/
+</script>
+
+	</div>
+</html>

+ 310 - 0
src/main/webapp/WEB-INF/views/statistics/CustomerAgeOrderForm.html

@@ -0,0 +1,310 @@
+<!DOCTYPE html>
+<html lang="ko"
+	xmlns:th="http://www.thymeleaf.org">
+<!--
+ *******************************************************************************
+ * @source  : CustomerAgeOrderForm.html
+ * @desc    : 연령별주문현황 Page
+ *============================================================================
+ * STYLE24
+ * Copyright(C) 2020 TSIT, All rights reserved.
+ *============================================================================
+ * VER  DATE         AUTHOR      DESCRIPTION
+ * ===  ===========  ==========  =============================================
+ * 1.0  2021.09.28   swkim       최초 작성
+ *******************************************************************************
+ -->
+	<div id="main">
+		<!-- 메인타이틀 영역 -->
+		<div class="main-title"></div>
+		<!-- //메인타이틀 영역 -->
+
+		<!-- 메뉴 설명 -->
+		<div class="infoBox menu-desc"></div>
+		<!-- //메뉴 설명 -->
+
+		<!-- 검색조건 영역 -->
+		<div class="panelStyle">
+			<form id="searchForm" name="searchForm" action="#" th:action="@{'/statistics/customer/age/order/list'}" onsubmit="$('#btnSearch').trigger('click'); return false;">
+				<input type="hidden" name="dayGb" value="D"/>
+
+				<table class="frmStyle" aria-describedby="검색조건">
+					<colgroup>
+						<col style="width:10%;"/>
+						<col style="width:25%;"/>
+						<col style="width:10%;"/>
+						<col/>
+					</colgroup>
+					<tr>
+						<th>기간<i class="required" title="필수" aria-hidden="true"></i></th>
+						<td colspan="3" id="terms"></td>
+					</tr>
+					<tr>
+						<th>디바이스</th>
+						<td colspan="3">
+							<label class="chkBox checked"><input type="checkbox" name="multiFrontGb" value="P" checked="checked"/>PC웹</label>
+							<label class="chkBox checked"><input type="checkbox" name="multiFrontGb" value="M" checked="checked"/>모바일웹</label>
+							<label class="chkBox checked"><input type="checkbox" name="multiFrontGb" value="A" checked="checked"/>APP</label>
+						</td>
+					</tr>
+					<tr>
+						<th>등급</th>
+						<td colspan="3">
+							<label th:if="${gradeGbList}" th:each="oneData, status : ${gradeGbList}" class="chkBox checked"><input type="checkbox" name="multiGradeGb" th:value="${oneData.cd}" th:text="${oneData.cdNm}" checked="checked"/></label>
+						</td>
+					</tr>
+					<tr>
+						<th>브랜드</th>
+						<td>
+							<input type="text" class="w100" name="brandCdSearchTxt" id="brandCdSearchTxt" maxlength="20" />
+							<button type="button" class="btn icn" onclick="cfnOpenBrandListPopup('fnSetBrandInfo', 'M');"><i class="fa fa-search"></i></button>
+							<span id="brandCdTxt"></span>
+							<input type="hidden" name="brandCdList"/>
+						</td>
+						<th>매출카테고리</th>
+						<td>
+							<input type="text" class="w100" name="itemkindCdSearchTxt" id="itemkindCdSearchTxt" maxlength="20" />
+							<button type="button" class="btn icn" onclick="cfnOpenItemkindListPopup('fnSetItemkindInfo', 'M');"><i class="fa fa-search"></i></button>
+							<span id="itemkindCdTxt"></span>
+							<input type="hidden" name="itemkindCdList"/>
+						</td>
+					</tr>
+				</table>
+
+				<ul class="panelBar">
+					<li class="center">
+						<button type="button" class="btn btn-base btn-lg" id="btnSearch">조회</button>
+						<button type="button" class="btn btn-gray btn-lg" id="btnInit">초기화</button>
+					</li>
+				</ul>
+			</form>
+		</div>
+		<!-- 검색조건 영역 -->
+
+		<!-- 리스트 영역 -->
+		<div class="panelStyle">
+			<ul class="panelBar">
+				<li>
+					<button type="button" class="btn btn-default btn-lg" onclick="fnExcelDownLoad();">엑셀다운로드</button>
+				</li>
+			</ul>
+			<div id="gridList" style="width: 100%; height: 470px" class="ag-theme-balham"></div>
+		</div>
+		<!-- //리스트 영역 -->
+	</div>
+
+<style>
+.ag-header-group-text{
+	margin-left: calc(50% - 25px);
+}
+</style>
+<script th:inline="javascript">
+/*<![CDATA[*/
+	let columnDefs = [
+		{ headerName: "연령", field: "age", width: 100, cellClass: 'text-center' },
+		{ headerName: "성별", field: "sexGb", width: 100, cellClass: 'text-center' },
+		{
+			headerName: "주문 현황", field: "", width: 1200, cellClass: 'text-center',
+			children: [
+				{headerName: "총매출액(A+B)", field: "totOrdAmt", width: 150, cellClass: 'text-center',
+					cellRenderer: function(params) {
+						return gagaAgGrid.toAddComma(params.value);
+					}
+				},
+				{headerName: "매출액(A)", field: "ordAmt", width: 150, cellClass: 'text-center',
+					cellRenderer: function(params) {
+						return gagaAgGrid.toAddComma(params.value);
+					}
+				},
+				{headerName: "취/반품액(B)", field: "cnclAmt", width: 150, cellClass: 'text-center',
+					cellRenderer: function(params) {
+						return gagaAgGrid.toAddComma(params.value);
+					}
+				},
+				{headerName: "주문수", field: "ordCnt", width: 150, cellClass: 'text-center',
+					cellRenderer: function(params) {
+						return gagaAgGrid.toAddComma(params.value);
+					}
+				},
+				{headerName: "취/반품갯수", field: "cnclQty", width: 150, cellClass: 'text-center',
+					cellRenderer: function(params) {
+						return gagaAgGrid.toAddComma(params.value);
+					}
+				},
+				{headerName: "기간평균주문수", field: "avgOrdCnt", width: 150, cellClass: 'text-center',
+					cellRenderer: function(params) {
+						return gagaAgGrid.toAddComma(params.value);
+					}
+				},
+				{headerName: "평균주문상품개수", field: "avgSellQty", width: 150, cellClass: 'text-center',
+					cellRenderer: function(params) {
+						return gagaAgGrid.toAddComma(params.value);
+					}
+				},
+				{headerName: "객단가", field: "custPrice", width: 150, cellClass: 'text-center',
+					cellRenderer: function(params) {
+						return gagaAgGrid.toAddComma(params.value);
+					}
+				}
+			]
+		}
+	];
+
+	let gridOptions = gagaAgGrid.getGridOptions(columnDefs);
+
+    gridOptions.excelStyles = [
+        {
+            id: 'text-center',
+            dataType: 'string',
+			font: {size : 10, bold: false}
+        },
+        {
+            id: 'text-left',
+            dataType: 'string',
+			font: {size : 10, bold: false}
+        },
+        {
+            id: 'text-right',
+            dataType: 'number',
+			font: {size : 10, bold: false}
+        }
+    ];
+
+    var fnExcelDownLoad = function(){
+
+    	var totalRows = gridOptions.api.getDisplayedRowCount();
+		if(totalRows==0){
+			mcxDialog.alert('조회된 내역이 없습니다.');
+			return;
+		}
+
+    	var date = new Date().format("YYYYMMDDHHmmss");
+		var params = {
+						fileName : "연령별주문현황_"+ date,
+						sheetName: "DATA"
+					 };
+		gridOptions.api.exportDataAsExcel(params);
+    }
+
+	// 브랜드 조회 팝업에서 호출
+	var fnSetBrandInfo = function(result) {
+		var arrBrandCd = [];
+		var brandCdTxt = "";
+		var bIndex = 0;
+		$('#brandCdTxt').html('');
+		$('#searchForm input[name=brandCdSearchTxt]').val('');
+
+		result.forEach(function(brand){
+			bIndex++;
+			arrBrandCd.push(brand.brandCd);
+		});
+
+		// 조회 값이 하나일 경우 화면에 코드 노출. 그 외는 갯수 처리
+		if (bIndex == 1) {
+			$('#searchForm input[name=brandCdSearchTxt]').val(arrBrandCd[0]);
+		} else {
+			brandCdTxt = bIndex + " 개";
+			$('#brandCdTxt').html(brandCdTxt);
+		}
+
+		var jsonData = JSON.stringify(arrBrandCd);
+		$("#searchForm input[name=brandCdList]").val(arrBrandCd.join(","));
+	}
+
+	// 품목 조회 팝업에서 호출
+	var fnSetItemkindInfo = function(result) {
+		var arrItemkindCd = [];
+		var itemkindCdTxt = "";
+		var bIndex = 0;
+		$('#itemkindCdTxt').html('');
+		$('#searchForm input[name=itemkindCdSearchTxt]').val('');
+
+		result.forEach(function(itemkind){
+			bIndex++;
+			arrItemkindCd.push(itemkind.itemkindCd);
+		});
+
+		// 조회 값이 하나일 경우 화면에 코드 노출. 그 외는 갯수 처리
+		if (bIndex == 1) {
+			$('#searchForm input[name=itemkindCdSearchTxt]').val(arrItemkindCd[0]);
+		} else {
+			itemkindCdTxt = bIndex + " 개";
+			$('#itemkindCdTxt').html(itemkindCdTxt);
+		}
+
+		var jsonData = JSON.stringify(arrItemkindCd);
+		$("#searchForm input[name=itemkindCdList]").val(arrItemkindCd.join(','));
+	}
+
+	// 검색
+	$('#btnSearch').on('click', function() {
+		// 입력 값 체크
+		if (!gagajf.validation($('#searchForm')))
+			return false;
+
+		gagaAgGrid.fetch($('#searchForm').prop('action'), gridOptions, '#searchForm', fnCreateTotal);
+	});
+
+	// 합계 생성
+	let fnCreateTotal = function() {
+		let len = 0;
+
+		let totInfo = {};
+		totInfo.age     = '';
+		totInfo.sexGb = 'TOTAL';
+		totInfo.totOrdAmt   = 0;
+		totInfo.ordAmt     = 0;
+		totInfo.cnclAmt = 0;
+		totInfo.ordCnt  = 0;
+		totInfo.cnclQty  = 0;
+		totInfo.avgOrdCnt     = 0;
+		totInfo.avgSellQty    = 0;
+		totInfo.custPrice    = 0;
+
+		gridOptions.api.forEachNode(function(rowNode, index) {
+			if (!rowNode.group) {
+				if( typeof rowNode.data.totOrdAmt      == 'number') { totInfo.totOrdAmt       += rowNode.data.totOrdAmt      ; }
+				if( typeof rowNode.data.ordAmt     == 'number') { totInfo.ordAmt      += rowNode.data.ordAmt     ; }
+				if( typeof rowNode.data.cnclAmt == 'number') { totInfo.cnclAmt  += rowNode.data.cnclAmt ; }
+				if( typeof rowNode.data.ordCnt  == 'number') { totInfo.ordCnt   += rowNode.data.ordCnt  ; if (rowNode.data.ordCnt > 0) len++; }
+				if( typeof rowNode.data.cnclQty  == 'number') { totInfo.cnclQty   += rowNode.data.cnclQty  ; }
+				if( typeof rowNode.data.avgOrdCnt  == 'number') { totInfo.avgOrdCnt   += rowNode.data.avgOrdCnt  ; }
+				if( typeof rowNode.data.avgSellQty     == 'number') { totInfo.avgSellQty      += rowNode.data.avgSellQty     ; }
+				if( typeof rowNode.data.custPrice    == 'number') { totInfo.custPrice     += rowNode.data.custPrice    ; }
+			}
+		});
+
+		totInfo.avgOrdCnt = (Math.round(totInfo.avgOrdCnt / len * 10) / 10);
+		totInfo.avgSellQty = (Math.round(totInfo.avgSellQty / len * 10) / 10);
+		totInfo.custPrice = Math.floor(totInfo.custPrice / len);
+
+		gagaAgGrid.setPinnedRowData(gridOptions, totInfo, 'top');
+	}
+
+	// 초기화 클릭시
+	$('#btnInit').on('click', function() {
+		$('#searchForm')[0].reset();
+
+		$('#brandCdTxt').html('');
+		$('#searchForm input[name=brandCdList]').val('');
+		$('#itemkindCdTxt').html('');
+		$('#searchForm input[name=itemkindCdList]').val('');
+	});
+
+	// 엑셀다운로드
+	$('#btnExcel').on('click', function() {
+		gagaAgGrid.exportToExcel('일자별주문 목록', gridOptions);
+	});
+
+	$(document).ready(function() {
+		cfnCreateCalendar('#terms', 'startDt', 'endDt', true, '주문', undefined, ['btnToday']);
+		$('.btnYesterday').trigger('click');
+
+		// Create a agGrid
+		gagaAgGrid.createGrid('gridList', gridOptions);
+
+	});
+/*]]>*/
+</script>
+
+</html>

+ 402 - 0
src/main/webapp/WEB-INF/views/statistics/CustomerGradeOrderForm.html

@@ -0,0 +1,402 @@
+<!DOCTYPE html>
+<html lang="ko"
+	xmlns:th="http://www.thymeleaf.org">
+<!--
+ *******************************************************************************
+ * @source  : CustomerGradeOrderForm.html
+ * @desc    : 등급별주문현황 Page
+ *============================================================================
+ * STYLE24
+ * Copyright(C) 2020 TSIT, All rights reserved.
+ *============================================================================
+ * VER  DATE         AUTHOR      DESCRIPTION
+ * ===  ===========  ==========  =============================================
+ * 1.0  2021.09.28   swkim       최초 작성
+ *******************************************************************************
+ -->
+	<div id="main">
+		<!-- 메인타이틀 영역 -->
+		<div class="main-title"></div>
+		<!-- //메인타이틀 영역 -->
+
+		<!-- 메뉴 설명 -->
+		<div class="infoBox menu-desc"></div>
+		<!-- //메뉴 설명 -->
+
+		<!-- 검색조건 영역 -->
+		<div class="panelStyle">
+			<form id="searchForm" name="searchForm" action="#" th:action="@{'/statistics/customer/grade/order/list'}" onsubmit="$('#btnSearch').trigger('click'); return false;">
+				<input type="hidden" name="dayGb" value="D"/>
+
+				<table class="frmStyle" aria-describedby="검색조건">
+					<colgroup>
+						<col style="width:10%;"/>
+						<col style="width:25%;"/>
+						<col style="width:10%;"/>
+						<col/>
+					</colgroup>
+					<tr>
+						<th>기간<i class="required" title="필수" aria-hidden="true"></i></th>
+						<td colspan="3" id="terms"></td>
+					</tr>
+					<tr>
+						<th>디바이스</th>
+						<td colspan="3">
+							<label class="chkBox checked"><input type="checkbox" name="multiFrontGb" value="P" checked="checked"/>PC웹</label>
+							<label class="chkBox checked"><input type="checkbox" name="multiFrontGb" value="M" checked="checked"/>모바일웹</label>
+							<label class="chkBox checked"><input type="checkbox" name="multiFrontGb" value="A" checked="checked"/>APP</label>
+						</td>
+					</tr>
+					<tr>
+						<th>성별</th>
+						<td>
+							<label class="chkBox checked"><input type="checkbox" name="multiSexGb" value="G007_F" checked="checked"/>여성</label>
+							<label class="chkBox checked"><input type="checkbox" name="multiSexGb" value="G007_M" checked="checked"/>남성</label>
+							<label class="chkBox checked"><input type="checkbox" name="multiSexGb" value="G007_X" checked="checked"/>알수없음</label>
+						</td>
+						<th>연령</th>
+						<td>
+							<label class="chkBox checked"><input type="checkbox" name="multiAgeGb" value="10" checked="checked"/>10대</label>
+							<label class="chkBox checked"><input type="checkbox" name="multiAgeGb" value="20" checked="checked"/>20대</label>
+							<label class="chkBox checked"><input type="checkbox" name="multiAgeGb" value="30" checked="checked"/>30대</label>
+							<label class="chkBox checked"><input type="checkbox" name="multiAgeGb" value="40" checked="checked"/>40대</label>
+							<label class="chkBox checked"><input type="checkbox" name="multiAgeGb" value="X" checked="checked"/>기타/미상</label>
+						</td>
+
+					</tr>
+					<tr>
+						<th>브랜드</th>
+						<td>
+							<input type="text" class="w100" name="brandCdSearchTxt" id="brandCdSearchTxt" maxlength="20" />
+							<button type="button" class="btn icn" onclick="cfnOpenBrandListPopup('fnSetBrandInfo', 'M');"><i class="fa fa-search"></i></button>
+							<span id="brandCdTxt"></span>
+							<input type="hidden" name="brandCdList"/>
+						</td>
+						<th>매출카테고리</th>
+						<td>
+							<input type="text" class="w100" name="itemkindCdSearchTxt" id="itemkindCdSearchTxt" maxlength="20" />
+							<button type="button" class="btn icn" onclick="cfnOpenItemkindListPopup('fnSetItemkindInfo', 'M');"><i class="fa fa-search"></i></button>
+							<span id="itemkindCdTxt"></span>
+							<input type="hidden" name="itemkindCdList"/>
+						</td>
+					</tr>
+				</table>
+
+				<ul class="panelBar">
+					<li class="center">
+						<button type="button" class="btn btn-base btn-lg" id="btnSearch">조회</button>
+						<button type="button" class="btn btn-gray btn-lg" id="btnInit">초기화</button>
+					</li>
+				</ul>
+			</form>
+		</div>
+		<!-- 검색조건 영역 -->
+
+		<!-- 차트영역 -->
+		<div class="panelStyle" id="chartDiv">
+			<div id="chart" class="chartUnit"></div>
+		</div>
+		<!-- //차트영역 -->
+
+		<!-- 리스트 영역 -->
+		<div class="panelStyle">
+			<ul class="panelBar">
+				<li>
+					<button type="button" class="btn btn-default btn-lg" onclick="fnExcelDownLoad();">엑셀다운로드</button>
+				</li>
+			</ul>
+			<div id="gridList" style="width: 100%; height: 470px" class="ag-theme-balham"></div>
+		</div>
+		<!-- //리스트 영역 -->
+	</div>
+
+<style>
+.ag-header-group-text{
+	margin-left: calc(50% - 25px);
+}
+</style>
+<script th:inline="javascript">
+/*<![CDATA[*/
+	let columnDefs = [
+		{ headerName: "등급", field: "custGrade", width: 100, cellClass: 'text-center' },
+		{
+			headerName: "주문 현황", field: "", width: 1200, cellClass: 'text-center',
+			children: [
+				{headerName: "총매출액(A+B)", field: "totOrdAmt", width: 150, cellClass: 'text-center',
+					cellRenderer: function(params) {
+						return gagaAgGrid.toAddComma(params.value);
+					}
+				},
+				{headerName: "매출액(A)", field: "ordAmt", width: 150, cellClass: 'text-center',
+					cellRenderer: function(params) {
+						return gagaAgGrid.toAddComma(params.value);
+					}
+				},
+				{headerName: "취/반품액(B)", field: "cnclAmt", width: 150, cellClass: 'text-center',
+					cellRenderer: function(params) {
+						return gagaAgGrid.toAddComma(params.value);
+					}
+				},
+				{headerName: "주문수", field: "ordCnt", width: 120, cellClass: 'text-center',
+					cellRenderer: function(params) {
+						return gagaAgGrid.toAddComma(params.value);
+					}
+				},
+				{headerName: "취/반품갯수", field: "cnclQty", width: 150, cellClass: 'text-center',
+					cellRenderer: function(params) {
+						return gagaAgGrid.toAddComma(params.value);
+					}
+				},
+				{headerName: "기간평균주문수", field: "avgOrdCnt", width: 150, cellClass: 'text-center',
+					cellRenderer: function(params) {
+						return gagaAgGrid.toAddComma(params.value);
+					}
+				},
+				{headerName: "평균주문상품개수", field: "avgSellQty", width: 150, cellClass: 'text-center',
+					cellRenderer: function(params) {
+						return gagaAgGrid.toAddComma(params.value);
+					}
+				},
+				{headerName: "객단가", field: "custPrice", width: 150, cellClass: 'text-center',
+					cellRenderer: function(params) {
+						return gagaAgGrid.toAddComma(params.value);
+					}
+				}
+			]
+		}
+	];
+
+	let gridOptions = gagaAgGrid.getGridOptions(columnDefs);
+
+    gridOptions.excelStyles = [
+        {
+            id: 'text-center',
+            dataType: 'string',
+			font: {size : 10, bold: false}
+        },
+        {
+            id: 'text-left',
+            dataType: 'string',
+			font: {size : 10, bold: false}
+        },
+        {
+            id: 'text-right',
+            dataType: 'number',
+			font: {size : 10, bold: false}
+        }
+    ];
+
+    var fnExcelDownLoad = function(){
+
+    	var totalRows = gridOptions.api.getDisplayedRowCount();
+		if(totalRows==0){
+			mcxDialog.alert('조회된 내역이 없습니다.');
+			return;
+		}
+
+    	var date = new Date().format("YYYYMMDDHHmmss");
+		var params = {
+						fileName : "등급별주문현황_"+ date,
+						sheetName: "DATA"
+					 };
+		gridOptions.api.exportDataAsExcel(params);
+    }
+
+	// 브랜드 조회 팝업에서 호출
+	var fnSetBrandInfo = function(result) {
+		var arrBrandCd = [];
+		var brandCdTxt = "";
+		var bIndex = 0;
+		$('#brandCdTxt').html('');
+		$('#searchForm input[name=brandCdSearchTxt]').val('');
+
+		result.forEach(function(brand){
+			bIndex++;
+			arrBrandCd.push(brand.brandCd);
+		});
+
+		// 조회 값이 하나일 경우 화면에 코드 노출. 그 외는 갯수 처리
+		if (bIndex == 1) {
+			$('#searchForm input[name=brandCdSearchTxt]').val(arrBrandCd[0]);
+		} else {
+			brandCdTxt = bIndex + " 개";
+			$('#brandCdTxt').html(brandCdTxt);
+		}
+
+		var jsonData = JSON.stringify(arrBrandCd);
+		$("#searchForm input[name=brandCdList]").val(arrBrandCd.join(","));
+	}
+
+	// 품목 조회 팝업에서 호출
+	var fnSetItemkindInfo = function(result) {
+		var arrItemkindCd = [];
+		var itemkindCdTxt = "";
+		var bIndex = 0;
+		$('#itemkindCdTxt').html('');
+		$('#searchForm input[name=itemkindCdSearchTxt]').val('');
+
+		result.forEach(function(itemkind){
+			bIndex++;
+			arrItemkindCd.push(itemkind.itemkindCd);
+		});
+
+		// 조회 값이 하나일 경우 화면에 코드 노출. 그 외는 갯수 처리
+		if (bIndex == 1) {
+			$('#searchForm input[name=itemkindCdSearchTxt]').val(arrItemkindCd[0]);
+		} else {
+			itemkindCdTxt = bIndex + " 개";
+			$('#itemkindCdTxt').html(itemkindCdTxt);
+		}
+
+		var jsonData = JSON.stringify(arrItemkindCd);
+		$("#searchForm input[name=itemkindCdList]").val(arrItemkindCd.join(','));
+	}
+
+	// 검색
+	$('#btnSearch').on('click', function() {
+		// 입력 값 체크
+		if (!gagajf.validation($('#searchForm')))
+			return false;
+
+		gagaAgGrid.fetch($('#searchForm').prop('action'), gridOptions, '#searchForm', fnCreateTotal);
+	});
+
+	// 합계 생성
+	let fnCreateTotal = function() {
+
+		// Draw chart
+		fnDrawChart(gagaAgGrid.getAllRowData(gridOptions));
+
+		let len = 0;
+
+		let totInfo = {};
+		totInfo.custGrade     = 'TOTAL';
+		totInfo.totOrdAmt   = 0;
+		totInfo.ordAmt     = 0;
+		totInfo.cnclAmt = 0;
+		totInfo.ordCnt  = 0;
+		totInfo.cnclQty  = 0;
+		totInfo.avgOrdCnt     = 0;
+		totInfo.avgSellQty    = 0;
+		totInfo.custPrice    = 0;
+
+		gridOptions.api.forEachNode(function(rowNode, index) {
+			if (!rowNode.group) {
+				if( typeof rowNode.data.totOrdAmt      == 'number') { totInfo.totOrdAmt       += rowNode.data.totOrdAmt      ; }
+				if( typeof rowNode.data.ordAmt     == 'number') { totInfo.ordAmt      += rowNode.data.ordAmt     ; }
+				if( typeof rowNode.data.cnclAmt == 'number') { totInfo.cnclAmt  += rowNode.data.cnclAmt ; }
+				if( typeof rowNode.data.ordCnt  == 'number') { totInfo.ordCnt   += rowNode.data.ordCnt  ; if (rowNode.data.ordCnt > 0) len++; }
+				if( typeof rowNode.data.cnclQty  == 'number') { totInfo.cnclQty   += rowNode.data.cnclQty  ; }
+				if( typeof rowNode.data.avgOrdCnt  == 'number') { totInfo.avgOrdCnt   += rowNode.data.avgOrdCnt  ; }
+				if( typeof rowNode.data.avgSellQty     == 'number') { totInfo.avgSellQty      += rowNode.data.avgSellQty     ; }
+				if( typeof rowNode.data.custPrice    == 'number') { totInfo.custPrice     += rowNode.data.custPrice    ; }
+			}
+		});
+
+		totInfo.avgOrdCnt = (Math.round(totInfo.avgOrdCnt / len * 10) / 10);
+		totInfo.avgSellQty = (Math.round(totInfo.avgSellQty / len * 10) / 10);
+		totInfo.custPrice = Math.floor(totInfo.custPrice / len);
+
+		gagaAgGrid.setPinnedRowData(gridOptions, totInfo, 'top');
+	}
+
+	// 그래프 그리기
+	var chart1;
+	var fnDrawChart = function(data) {
+		let xList = [];
+		let ordAmtList = [];
+
+		$(data).each(function(idx, item) {
+			xList.push(item.custGrade);
+			ordAmtList.push(item.ordAmt);
+		});
+
+		chart1 = c3.generate({
+			bindto: "#chart",
+			padding: {
+				bottom: 20 //adjust chart padding bottom
+			},
+			data: {
+				x: 'x',
+				json: {
+					x: xList,
+					등급별매출액: ordAmtList
+				},
+				types: {
+					등급별매출액: 'bar'
+				}/* ,
+					regions: {
+						'data1': [
+							{
+								'start': 1,
+								'end': 2,
+								'style': 'dashed'
+							}, {
+								'start': 3
+							}
+						]
+					} */
+			},
+			color: {
+				pattern: ['#48C9B0', '#FF7043', '#FF7043']
+			},
+			legend: { padding: 15 }, //범례 item 우측 간격
+			axis: {
+				x: {
+					type: 'category',
+					padding: { left: 0.5, right: 0.5 }
+				}/* ,
+					y: {
+						tick: {
+							format: function(d) { return Number(d).addComma() + 'K'; }
+						}
+					} */
+			},
+			tooltip: {
+				format: {
+					title: function (d) {
+						return '등급별 매출액 Chart';
+					}
+				}
+			}/* ,
+				bar: {
+					width: { ratio: 0.2 } // 막대 폭 20%로 조절
+				} */
+		});
+	}
+
+	// LNB 또는 GNB 클릭시 차트 넓이 변경
+	var chartResize = function() {
+		setTimeout(function () {
+			// 모든 차트 ID객체에 적용
+			chart1.resize();
+		}, 300);
+	}
+
+	// 초기화 클릭시
+	$('#btnInit').on('click', function() {
+		$('#searchForm')[0].reset();
+
+		$('#brandCdTxt').html('');
+		$('#searchForm input[name=brandCdList]').val('');
+		$('#itemkindCdTxt').html('');
+		$('#searchForm input[name=itemkindCdList]').val('');
+	});
+
+	// 엑셀다운로드
+	$('#btnExcel').on('click', function() {
+		gagaAgGrid.exportToExcel('일자별주문 목록', gridOptions);
+	});
+
+	$(document).ready(function() {
+		cfnCreateCalendar('#terms', 'startDt', 'endDt', true, '주문', undefined, ['btnToday']);
+		$('.btnYesterday').trigger('click');
+
+		// Create a agGrid
+		gagaAgGrid.createGrid('gridList', gridOptions);
+
+	});
+/*]]>*/
+</script>
+
+</html>

+ 367 - 0
src/main/webapp/WEB-INF/views/statistics/CustomerJoinForm.html

@@ -0,0 +1,367 @@
+<!DOCTYPE html>
+<html lang="ko"
+	xmlns:th="http://www.thymeleaf.org">
+<!--
+ *******************************************************************************
+ * @source  : CustomerJoinForm.html
+ * @desc    : 회원가입현황 Page
+ *============================================================================
+ * STYLE24
+ * Copyright(C) 2020 TSIT, All rights reserved.
+ *============================================================================
+ * VER  DATE         AUTHOR      DESCRIPTION
+ * ===  ===========  ==========  =============================================
+ * 1.0  2021.09.28   swkim       최초 작성
+ *******************************************************************************
+ -->
+	<div id="main">
+		<!-- 메인타이틀 영역 -->
+		<div class="main-title">
+		</div>
+		<!-- //메인타이틀 영역 -->
+
+		<!-- 메뉴 설명 -->
+		<div class="infoBox menu-desc">
+		</div>
+		<!-- //메뉴 설명 -->
+
+		<!-- 검색조건 영역 -->
+		<div class="panelStyle">
+			<form id="searchForm" name="searchForm" action="#" th:action="@{'/statistics/customer/join/list'}" onsubmit="$('#btnSearch').trigger('click'); return false;">
+				<input type="hidden" name="dayGb" value="D"/>
+
+				<table class="frmStyle" aria-describedby="검색조건">
+					<colgroup>
+						<col style="width:10%;"/>
+						<col style="width:25%;"/>
+						<col style="width:10%;"/>
+						<col style="width:25%;"/>
+						<col style="width:10%;"/>
+						<col style="width:20%;"/>
+					</colgroup>
+					<tr>
+						<th>기간<i class="required" title="필수" aria-hidden="true"></i></th>
+						<td colspan="5" id="terms">
+						</td>
+					</tr>
+					<tr>
+						<th>성별</th>
+						<td>
+							<label class="chkBox checked"><input type="checkbox" name="multiSexGb" value="G007_F" checked="checked"/>여성</label>
+							<label class="chkBox checked"><input type="checkbox" name="multiSexGb" value="G007_M" checked="checked"/>남성</label>
+							<label class="chkBox checked"><input type="checkbox" name="multiSexGb" value="G007_X" checked="checked"/>알수없음</label>
+						</td>
+						<th>연령별</th>
+						<td colspan="3">
+							<label class="chkBox checked"><input type="checkbox" name="multiAgeGb" value="10" checked="checked"/>10대</label>
+							<label class="chkBox checked"><input type="checkbox" name="multiAgeGb" value="20" checked="checked"/>20대</label>
+							<label class="chkBox checked"><input type="checkbox" name="multiAgeGb" value="30" checked="checked"/>30대</label>
+							<label class="chkBox checked"><input type="checkbox" name="multiAgeGb" value="40" checked="checked"/>40대</label>
+							<label class="chkBox checked"><input type="checkbox" name="multiAgeGb" value="X" checked="checked"/>기타/미상</label>
+						</td>
+
+					</tr>
+				</table>
+
+				<ul class="panelBar">
+					<li class="center">
+						<button type="button" class="btn btn-base btn-lg" id="btnSearch">조회</button>
+						<button type="button" class="btn btn-gray btn-lg" id="btnInit">초기화</button>
+					</li>
+				</ul>
+			</form>
+		</div>
+		<!-- 검색조건 영역 -->
+
+		<!-- 차트영역 -->
+		<div class="panelStyle" id="chartDiv">
+			<div id="chart" class="chartUnit"></div>
+		</div>
+		<!-- //차트영역 -->
+
+		<!-- 리스트 영역 -->
+		<div class="panelStyle">
+			<!-- 버튼 배치 영역 -->
+			<ul class="panelBar">
+				<li class="left">
+					<button type="button" class="btn btn-default btn-lg" id="btnExcel">엑셀다운로드</button>
+				</li>
+				<li class="right">
+					<span class="btnGroup marR10">
+						<button type="button" class="btn btn-default btn-lg active" id="dayGbD" onclick="fnSetDayGb('D');">일별</button>
+						<button type="button" class="btn btn-default btn-lg" id="dayGbW" onclick="fnSetDayGb('W');">주별</button>
+						<button type="button" class="btn btn-default btn-lg" id="dayGbM" onclick="fnSetDayGb('M');">월별</button>
+					</span>
+				</li>
+			</ul>
+			<!-- //버튼 배치 영역 -->
+
+			<div id="gridList" style="width: 100%; height: 470px" class="ag-theme-balham"></div>
+		</div>
+		<!-- //리스트 영역 -->
+	</div>
+
+<script th:inline="javascript">
+/*<![CDATA[*/
+	let columnDefs = [
+		{ headerName: "기간", field: "day", width: 100, cellClass: 'text-center' },
+		{
+			headerName: "전체회원", field: "", width: 450, cellClass: 'text-center',
+			children: [
+				{headerName: "전체회원", field: "allCnt", width: 150, cellClass: 'text-center',
+					cellRenderer: function(params) {
+						return gagaAgGrid.toAddComma(params.value);
+					}
+				},
+				{headerName: "실회원", field: "realCnt", width: 150, cellClass: 'text-center',
+					cellRenderer: function(params) {
+						return gagaAgGrid.toAddComma(params.value);
+					}
+				},
+				{headerName: "휴면회원", field: "dormCnt", width: 150, cellClass: 'text-center',
+					cellRenderer: function(params) {
+						return gagaAgGrid.toAddComma(params.value);
+					}
+				}
+			]
+		},
+		{
+			headerName: "등급별회원수(실회원)", field: "", width: 600, cellClass: 'text-center',
+			children: [
+				{headerName: "VIP", field: "vipCnt", width: 120, cellClass: 'text-center',
+					cellRenderer: function(params) {
+						return gagaAgGrid.toAddComma(params.value);
+					}
+				},
+				{headerName: "GOLD", field: "goldCnt", width: 120, cellClass: 'text-center',
+					cellRenderer: function(params) {
+						return gagaAgGrid.toAddComma(params.value);
+					}
+				},
+				{headerName: "SILVER", field: "silverCnt", width: 120, cellClass: 'text-center',
+					cellRenderer: function(params) {
+						return gagaAgGrid.toAddComma(params.value);
+					}
+				},
+				{headerName: "BRONZE", field: "bronzeCnt", width: 120, cellClass: 'text-center',
+					cellRenderer: function(params) {
+						return gagaAgGrid.toAddComma(params.value);
+					}
+				},
+				{headerName: "WELCOME", field: "welcomeCnt", width: 120, cellClass: 'text-center',
+					cellRenderer: function(params) {
+						return gagaAgGrid.toAddComma(params.value);
+					}
+				}
+			]
+		},
+		{
+			headerName: "가입", field: "", width: 450, cellClass: 'text-center',
+			children: [
+				{headerName: "가입수", field: "joinCnt", width: 150, cellClass: 'text-center',
+					cellRenderer: function(params) {
+						return gagaAgGrid.toAddComma(params.value);
+					}
+				},
+				{headerName: "직방문", field: "drJoinCnt", width: 150, cellClass: 'text-center',
+					cellRenderer: function(params) {
+						return gagaAgGrid.toAddComma(params.value);
+					}
+				},
+				{headerName: "제휴", field: "afJoinCnt", width: 150, cellClass: 'text-center',
+					cellRenderer: function(params) {
+						return gagaAgGrid.toAddComma(params.value);
+					}
+				}
+			]
+		},
+		{
+			headerName: "휴면/탈퇴", field: "", width: 450, cellClass: 'text-center',
+			children: [
+				{headerName: "휴면전환", field: "chgDormCnt", width: 150, cellClass: 'text-center',
+					cellRenderer: function(params) {
+						return gagaAgGrid.toAddComma(params.value);
+					}
+				},
+				{headerName: "휴면해제", field: "rmDormCnt", width: 150, cellClass: 'text-center',
+					cellRenderer: function(params) {
+						return gagaAgGrid.toAddComma(params.value);
+					}
+				},
+				{headerName: "탈퇴", field: "seceedCnt", width: 150, cellClass: 'text-center',
+					cellRenderer: function(params) {
+						return gagaAgGrid.toAddComma(params.value);
+					}
+				}
+			]
+		}
+	];
+
+	let gridOptions = gagaAgGrid.getGridOptions(columnDefs);
+
+	gridOptions.autoGroupColumnDef = {
+			headerName: "일자",
+			field: "grouping",
+			width: 200,
+			cellRendererParams: {
+				suppressCount: true
+			}
+		};
+
+	// for expand everything
+	gridOptions.groupDefaultExpanded = -1;
+
+	// 검색
+	$('#btnSearch').on('click', function() {
+		// 입력 값 체크
+		if (!gagajf.validation($('#searchForm')))
+			return false;
+
+		gagaAgGrid.fetch($('#searchForm').prop('action'), gridOptions, '#searchForm', fnCreateTotal);
+	});
+
+	// 합계 생성
+	let fnCreateTotal = function() {
+		// Draw chart
+		fnDrawChart(gagaAgGrid.getAllRowData(gridOptions));
+
+		let tmpData = gagaAgGrid.getAllRowData(gridOptions);
+		let tmpLen = 0;
+
+		let allCnt = tmpData[tmpLen].allCnt;
+		let realCnt = tmpData[tmpLen].realCnt;
+		let dormCnt = tmpData[tmpLen].dormCnt;
+		let vipCnt = tmpData[tmpLen].vipCnt;
+		let goldCnt = tmpData[tmpLen].goldCnt;
+		let silverCnt = tmpData[tmpLen].silverCnt;
+		let bronzeCnt = tmpData[tmpLen].bronzeCnt;
+		let welcomeCnt = tmpData[tmpLen].welcomeCnt;
+		let joinCnt = 0;
+		let drJoinCnt = 0;
+		let afJoinCnt = 0;
+		let chgDormCnt = 0;
+		let rmDormCnt = 0;
+		let seceedCnt = 0;
+
+		gridOptions.api.forEachNode(function(rowNode, index) {
+			if (!rowNode.group) {
+				if (typeof rowNode.data.joinCnt == 'number') { joinCnt += rowNode.data.joinCnt; }
+				if (typeof rowNode.data.drJoinCnt == 'number') { drJoinCnt += rowNode.data.drJoinCnt; }
+				if (typeof rowNode.data.afJoinCnt == 'number') { afJoinCnt += rowNode.data.afJoinCnt; }
+				if (typeof rowNode.data.chgDormCnt == 'number') { chgDormCnt += rowNode.data.chgDormCnt; }
+				if (typeof rowNode.data.rmDormCnt == 'number') { rmDormCnt += rowNode.data.rmDormCnt; }
+				if (typeof rowNode.data.seceedCnt == 'number') { seceedCnt += rowNode.data.seceedCnt; }
+			}
+		});
+
+		let data = {
+			day: 'TOTAL',
+			allCnt: allCnt, realCnt: realCnt, dormCnt: dormCnt,
+			vipCnt: vipCnt, goldCnt: goldCnt, silverCnt: silverCnt,
+			bronzeCnt: bronzeCnt, welcomeCnt: welcomeCnt, joinCnt: joinCnt,
+			drJoinCnt: drJoinCnt, afJoinCnt: afJoinCnt, chgDormCnt: chgDormCnt,
+			rmDormCnt: rmDormCnt, seceedCnt: seceedCnt
+		};
+
+		gagaAgGrid.setPinnedRowData(gridOptions, data, 'top');
+	}
+
+	// 그래프 그리기
+	var chart1;
+	var fnDrawChart = function(data) {
+		let xList = [];
+		let totCntList = [];
+
+		for(var i = (data.length - 1); i > -1; i--){
+			if ($('#dayGbD').hasClass('active')) {
+				xList.push(data[i].day.toDate('YYYY-MM-DD').format('MM-DD'));
+			} else {
+				xList.push(data[i].day);
+			}
+			totCntList.push(data[i].allCnt);
+		}
+
+		chart1 = c3.generate({
+			bindto: "#chart",
+			padding: {
+				bottom: 20 //adjust chart padding bottom
+			},
+			data: {
+				x: 'x',
+				json: {
+					x: xList,
+					회원수: totCntList
+				},
+				types: {
+					x: 'line',
+					회원수: 'line'
+				}
+			},
+			axis : {
+				x: {
+					type: 'category',
+					padding: { left: 0.5, right: 0.5 }
+				},
+				y : {
+					tick: {
+						format: d3.format(",")
+					}
+				}
+			},
+			color: {
+				pattern: ['#48C9B0', '#FF7043']
+			},
+			legend: { padding: 15 }, //범례 item 우측 간격
+			tooltip: {
+				format: {
+					title: function (d) {
+						return '가입 통계 Chart';
+					},
+				}
+			}
+		});
+	}
+
+	// LNB 또는 GNB 클릭시 차트 넓이 변경
+	var chartResize = function() {
+		setTimeout(function () {
+			// 모든 차트 ID객체에 적용
+			chart1.resize();
+		}, 300);
+	}
+
+	// 초기화 클릭시
+	$('#btnInit').on('click', function() {
+		$('#searchForm')[0].reset();
+
+		$('#cardIdTxt').html('');
+		$('#searchForm input[name=cardIdList]').val('');
+	});
+
+	// 엑셀다운로드
+	$('#btnExcel').on('click', function() {
+		gagaAgGrid.exportToExcel('결제수단별통계 목록', gridOptions);
+	});
+
+	// 일자구분 변경 시
+	var fnSetDayGb = function(dayGb) {
+		$('#searchForm input[name=dayGb]').val(dayGb);
+		$('#dayGbD').removeClass('active');
+		$('#dayGbW').removeClass('active');
+		$('#dayGbM').removeClass('active');
+		$('#dayGb' + dayGb).addClass('active');
+		$('#btnSearch').trigger('click');
+	}
+
+	$(document).ready(function() {
+		cfnCreateCalendar('#terms', 'startDt', 'endDt', true, '주문', undefined, ['btnToday']);
+		$('.btnRecentWeek').trigger('click');
+
+		// Create a agGrid
+		gagaAgGrid.createGrid('gridList', gridOptions);
+
+	});
+/*]]>*/
+</script>
+
+</html>

+ 337 - 0
src/main/webapp/WEB-INF/views/statistics/CustomerRankingForm.html

@@ -0,0 +1,337 @@
+<!DOCTYPE html>
+<html lang="ko"
+	xmlns:th="http://www.thymeleaf.org">
+<!--
+ *******************************************************************************
+ * @source  : CustomerRankingForm.html
+ * @desc    : 구매자랭킹 Page
+ *============================================================================
+ * STYLE24
+ * Copyright(C) 2020 TSIT, All rights reserved.
+ *============================================================================
+ * VER  DATE         AUTHOR      DESCRIPTION
+ * ===  ===========  ==========  =============================================
+ * 1.0  2021.09.28   swkim       최초 작성
+ *******************************************************************************
+ -->
+	<div id="main">
+		<!-- 메인타이틀 영역 -->
+		<div class="main-title"></div>
+		<!-- //메인타이틀 영역 -->
+
+		<!-- 메뉴 설명 -->
+		<div class="infoBox menu-desc"></div>
+		<!-- //메뉴 설명 -->
+
+		<!-- 검색조건 영역 -->
+		<div class="panelStyle">
+			<form id="searchForm" name="searchForm" action="#" th:action="@{'/statistics/customer/ranking/list'}" onsubmit="$('#btnSearch').trigger('click'); return false;">
+				<input type="hidden" name="dayGb" value="D"/>
+
+				<table class="frmStyle" aria-describedby="검색조건">
+					<colgroup>
+						<col style="width:10%;"/>
+						<col style="width:25%;"/>
+						<col style="width:10%;"/>
+						<col/>
+					</colgroup>
+					<tr>
+						<th>기간<i class="required" title="필수" aria-hidden="true"></i></th>
+						<td colspan="3" id="terms"></td>
+					</tr>
+					<tr>
+						<th>디바이스</th>
+						<td colspan="3">
+							<label class="chkBox checked"><input type="checkbox" name="multiFrontGb" value="P" checked="checked"/>PC웹</label>
+							<label class="chkBox checked"><input type="checkbox" name="multiFrontGb" value="M" checked="checked"/>모바일웹</label>
+							<label class="chkBox checked"><input type="checkbox" name="multiFrontGb" value="A" checked="checked"/>APP</label>
+						</td>
+					</tr>
+					<tr>
+						<th>성별</th>
+						<td>
+							<label class="chkBox checked"><input type="checkbox" name="multiSexGb" value="G007_F" checked="checked"/>여성</label>
+							<label class="chkBox checked"><input type="checkbox" name="multiSexGb" value="G007_M" checked="checked"/>남성</label>
+							<label class="chkBox checked"><input type="checkbox" name="multiSexGb" value="G007_X" checked="checked"/>알수없음</label>
+						</td>
+						<th>연령</th>
+						<td>
+							<label class="chkBox checked"><input type="checkbox" name="multiAgeGb" value="10" checked="checked"/>10대</label>
+							<label class="chkBox checked"><input type="checkbox" name="multiAgeGb" value="20" checked="checked"/>20대</label>
+							<label class="chkBox checked"><input type="checkbox" name="multiAgeGb" value="30" checked="checked"/>30대</label>
+							<label class="chkBox checked"><input type="checkbox" name="multiAgeGb" value="40" checked="checked"/>40대</label>
+							<label class="chkBox checked"><input type="checkbox" name="multiAgeGb" value="X" checked="checked"/>기타/미상</label>
+						</td>
+					</tr>
+					<tr>
+						<th>브랜드</th>
+						<td>
+							<input type="text" class="w100" name="brandCdSearchTxt" id="brandCdSearchTxt" maxlength="20" />
+							<button type="button" class="btn icn" onclick="cfnOpenBrandListPopup('fnSetBrandInfo', 'M');"><i class="fa fa-search"></i></button>
+							<span id="brandCdTxt"></span>
+							<input type="hidden" name="brandCdList"/>
+						</td>
+						<th>매출카테고리</th>
+						<td>
+							<input type="text" class="w100" name="itemkindCdSearchTxt" id="itemkindCdSearchTxt" maxlength="20" />
+							<button type="button" class="btn icn" onclick="cfnOpenItemkindListPopup('fnSetItemkindInfo', 'M');"><i class="fa fa-search"></i></button>
+							<span id="itemkindCdTxt"></span>
+							<input type="hidden" name="itemkindCdList"/>
+						</td>
+					</tr>
+				</table>
+
+				<ul class="panelBar">
+					<li class="center">
+						<button type="button" class="btn btn-base btn-lg" id="btnSearch">조회</button>
+						<button type="button" class="btn btn-gray btn-lg" id="btnInit">초기화</button>
+					</li>
+				</ul>
+			</form>
+		</div>
+		<!-- 검색조건 영역 -->
+
+		<!-- 리스트 영역 -->
+		<div class="panelStyle">
+			<ul class="panelBar">
+				<li>
+					<button type="button" class="btn btn-default btn-lg" onclick="fnExcelDownLoad();">엑셀다운로드</button>
+				</li>
+			</ul>
+			<div id="gridList" style="width: 100%; height: 470px" class="ag-theme-balham"></div>
+		</div>
+		<!-- //리스트 영역 -->
+	</div>
+
+<style>
+.ag-header-group-text{
+	margin-left: calc(50% - 25px);
+}
+</style>
+<script th:inline="javascript">
+/*<![CDATA[*/
+	let columnDefs = [
+		{ headerName: "순위", field: "rank", width: 100, cellClass: 'text-center',
+			cellRenderer: function(params) {
+				if(params.data.custId != 'TOTAL') return  params.node.rowIndex + 1;
+				else return '';
+			}
+		},
+		{headerName: "회원NO", field: "custNo", width: 120, cellClass: 'text-center', hide: true},
+		{
+			headerName: "회원정보", field: "", width: 450, cellClass: 'text-center',
+			children: [
+				{headerName: "아이디(이름)", field: "custId", width: 200, cellClass: 'text-center',
+					cellRenderer: function(params) { return '<a href="javascript:void(0);">' + params.value + '</a>'; }
+				},
+				{headerName: "연령/성별", field: "age", width: 150, cellClass: 'text-center',
+					cellRenderer: function(params) {
+						let str1 = params.value;
+						let str2 = params.data.sexGb;
+
+						if(str1 == 'X') str1 = "알수없음";
+						else str1 = str1 + '대';
+						if(str2 == 'X') str2 = "알수없음";
+
+						if(params.data.custId != 'TOTAL') return str1 + '(' + str2 + ')';
+						else return '';
+					}
+				},
+				{headerName: "등급", field: "custGrade", width: 100, cellClass: 'text-center',
+					cellRenderer: function(params) {
+						return gagaAgGrid.toAddComma(params.value);
+					}
+				}
+			]
+		},
+		{
+			headerName: "주문 현황", field: "", width: 1200, cellClass: 'text-center',
+			children: [
+				{headerName: "총매출액", field: "totOrdAmt", width: 150, cellClass: 'text-center',
+					cellRenderer: function(params) {
+						return gagaAgGrid.toAddComma(params.value);
+					}
+				},
+				{headerName: "주문수", field: "ordCnt", width: 150, cellClass: 'text-center',
+					cellRenderer: function(params) {
+						return gagaAgGrid.toAddComma(params.value);
+					}
+				},
+				{headerName: "판매수량", field: "sellQty", width: 150, cellClass: 'text-center',
+					cellRenderer: function(params) {
+						return gagaAgGrid.toAddComma(params.value);
+					}
+				},
+				{headerName: "객단가", field: "custPrice", width: 150, cellClass: 'text-center',
+					cellRenderer: function(params) {
+						return gagaAgGrid.toAddComma(params.value);
+					}
+				},
+				{headerName: "보유포인트", field: "custPoint", width: 150, cellClass: 'text-center',
+					cellRenderer: function(params) {
+						return gagaAgGrid.toAddComma(params.value);
+					}
+				}
+			]
+		}
+	];
+
+	let gridOptions = gagaAgGrid.getGridOptions(columnDefs);
+
+	// 셀 클릭 이벤트
+	gridOptions.onCellClicked = function(event) {
+		if (event.colDef.field === 'custId') {
+			// 고객 상세
+			cfnOpenCustDetailPopup(event.data.custNo);
+		}
+	}
+
+    gridOptions.excelStyles = [
+        {
+            id: 'text-center',
+            dataType: 'string',
+			font: {size : 10, bold: false}
+        },
+        {
+            id: 'text-left',
+            dataType: 'string',
+			font: {size : 10, bold: false}
+        },
+        {
+            id: 'text-right',
+            dataType: 'number',
+			font: {size : 10, bold: false}
+        }
+    ];
+
+    var fnExcelDownLoad = function(){
+
+    	var totalRows = gridOptions.api.getDisplayedRowCount();
+		if(totalRows==0){
+			mcxDialog.alert('조회된 내역이 없습니다.');
+			return;
+		}
+
+    	var date = new Date().format("YYYYMMDDHHmmss");
+		var params = {
+						fileName : "연령별주문현황_"+ date,
+						sheetName: "DATA"
+					 };
+		gridOptions.api.exportDataAsExcel(params);
+    }
+
+	// 브랜드 조회 팝업에서 호출
+	var fnSetBrandInfo = function(result) {
+		var arrBrandCd = [];
+		var brandCdTxt = "";
+		var bIndex = 0;
+		$('#brandCdTxt').html('');
+		$('#searchForm input[name=brandCdSearchTxt]').val('');
+
+		result.forEach(function(brand){
+			bIndex++;
+			arrBrandCd.push(brand.brandCd);
+		});
+
+		// 조회 값이 하나일 경우 화면에 코드 노출. 그 외는 갯수 처리
+		if (bIndex == 1) {
+			$('#searchForm input[name=brandCdSearchTxt]').val(arrBrandCd[0]);
+		} else {
+			brandCdTxt = bIndex + " 개";
+			$('#brandCdTxt').html(brandCdTxt);
+		}
+
+		var jsonData = JSON.stringify(arrBrandCd);
+		$("#searchForm input[name=brandCdList]").val(arrBrandCd.join(","));
+	}
+
+	// 품목 조회 팝업에서 호출
+	var fnSetItemkindInfo = function(result) {
+		var arrItemkindCd = [];
+		var itemkindCdTxt = "";
+		var bIndex = 0;
+		$('#itemkindCdTxt').html('');
+		$('#searchForm input[name=itemkindCdSearchTxt]').val('');
+
+		result.forEach(function(itemkind){
+			bIndex++;
+			arrItemkindCd.push(itemkind.itemkindCd);
+		});
+
+		// 조회 값이 하나일 경우 화면에 코드 노출. 그 외는 갯수 처리
+		if (bIndex == 1) {
+			$('#searchForm input[name=itemkindCdSearchTxt]').val(arrItemkindCd[0]);
+		} else {
+			itemkindCdTxt = bIndex + " 개";
+			$('#itemkindCdTxt').html(itemkindCdTxt);
+		}
+
+		var jsonData = JSON.stringify(arrItemkindCd);
+		$("#searchForm input[name=itemkindCdList]").val(arrItemkindCd.join(','));
+	}
+
+	// 검색
+	$('#btnSearch').on('click', function() {
+		// 입력 값 체크
+		if (!gagajf.validation($('#searchForm')))
+			return false;
+
+		gagaAgGrid.fetch($('#searchForm').prop('action'), gridOptions, '#searchForm', fnCreateTotal);
+	});
+
+	// 합계 생성
+	let fnCreateTotal = function() {
+		let len = 0;
+
+		let totInfo = {};
+		totInfo.rank     = '';
+		totInfo.custId = 'TOTAL';
+		totInfo.age = '';
+		totInfo.totOrdAmt   = 0;
+		totInfo.ordCnt  = 0;
+		totInfo.sellQty  = 0;
+		totInfo.custPrice    = 0;
+		totInfo.custPoint    = 0;
+
+		gridOptions.api.forEachNode(function(rowNode, index) {
+			if (!rowNode.group) {
+				if( typeof rowNode.data.totOrdAmt      == 'number') { totInfo.totOrdAmt       += rowNode.data.totOrdAmt      ; }
+				if( typeof rowNode.data.ordCnt  == 'number') { totInfo.ordCnt   += rowNode.data.ordCnt  ; if (rowNode.data.ordCnt > 0) len++; }
+				if( typeof rowNode.data.sellQty  == 'number') { totInfo.sellQty   += rowNode.data.sellQty  ; }
+				if( typeof rowNode.data.custPrice    == 'number') { totInfo.custPrice     += rowNode.data.custPrice    ; }
+				if( typeof rowNode.data.custPoint    == 'number') { totInfo.custPoint     += rowNode.data.custPoint    ; }
+			}
+		});
+
+		totInfo.custPrice = Math.floor(totInfo.custPrice / len);
+
+		gagaAgGrid.setPinnedRowData(gridOptions, totInfo, 'top');
+	}
+
+	// 초기화 클릭시
+	$('#btnInit').on('click', function() {
+		$('#searchForm')[0].reset();
+
+		$('#brandCdTxt').html('');
+		$('#searchForm input[name=brandCdList]').val('');
+		$('#itemkindCdTxt').html('');
+		$('#searchForm input[name=itemkindCdList]').val('');
+	});
+
+	// 엑셀다운로드
+	$('#btnExcel').on('click', function() {
+		gagaAgGrid.exportToExcel('구매자랭킹 목록', gridOptions);
+	});
+
+	$(document).ready(function() {
+		cfnCreateCalendar('#terms', 'startDt', 'endDt', true, '주문', undefined, ['btnToday']);
+		$('.btnYesterday').trigger('click');
+
+		// Create a agGrid
+		gagaAgGrid.createGrid('gridList', gridOptions);
+
+	});
+/*]]>*/
+</script>
+
+</html>

+ 1 - 1
src/main/webapp/WEB-INF/views/statistics/DailyOrderForm.html

@@ -90,7 +90,7 @@
 						<td>
 							<input type="text" class="w100" name="itemkindCdSearchTxt" id="itemkindCdSearchTxt" maxlength="20" />
 							<button type="button" class="btn icn" onclick="cfnOpenItemkindListPopup('fnSetItemkindInfo', 'M');"><i class="fa fa-search"></i></button>
-							<span id="itemkindTxt"></span>
+							<span id="itemkindCdTxt"></span>
 							<input type="hidden" name="itemkindList"/>
 						</td>
 					</tr>

+ 1 - 1
src/main/webapp/WEB-INF/views/statistics/ExtmallTradingForm.html

@@ -64,7 +64,7 @@
 						<td>
 							<input type="text" class="w100" name="itemkindCdSearchTxt" id="itemkindCdSearchTxt" maxlength="20" />
 							<button type="button" class="btn icn" onclick="cfnOpenItemkindListPopup('fnSetItemkindInfo', 'M');"><i class="fa fa-search"></i></button>
-							<span id="itemkindTxt"></span>
+							<span id="itemkindCdTxt"></span>
 							<input type="hidden" name="itemkindCdList"/>
 						</td>
 					</tr>

+ 2 - 2
src/main/webapp/WEB-INF/views/statistics/GoodsTradingForm.html

@@ -69,7 +69,7 @@
 						</td>
 						<th>정상/이월구분</th>
 						<td>
-							<label th:if="${formalGbList}" th:each="oneData, status : ${formalGbList}" class="chkBox checked"><input type="checkbox" name="multiFormalGb" th:value="${oneData.cd}" th:text="${'[' + oneData.cd + '] ' + oneData.cdNm}" checked="checked"/></label>
+							<label th:if="${formalGbList}" th:each="oneData, status : ${formalGbList}" class="chkBox checked"><input type="checkbox" name="multiFormalGb" th:value="${oneData.cd}" th:text="${oneData.cdNm}" checked="checked"/></label>
 						</td>
 					</tr>
 					<tr>
@@ -100,7 +100,7 @@
 						<td>
 							<input type="text" class="w100" name="itemkindCdSearchTxt" id="itemkindCdSearchTxt" maxlength="20" />
 							<button type="button" class="btn icn" onclick="cfnOpenItemkindListPopup('fnSetItemkindInfo', 'M');"><i class="fa fa-search"></i></button>
-							<span id="itemkindTxt"></span>
+							<span id="itemkindCdTxt"></span>
 							<input type="hidden" name="itemkindCdList"/>
 						</td>
 					</tr>

+ 1 - 1
src/main/webapp/WEB-INF/views/statistics/HourlyTradingForm.html

@@ -75,7 +75,7 @@
 						<td>
 							<input type="text" class="w100" name="itemkindCdSearchTxt" id="itemkindCdSearchTxt" maxlength="20" />
 							<button type="button" class="btn icn" onclick="cfnOpenItemkindListPopup('fnSetItemkindInfo', 'M');"><i class="fa fa-search"></i></button>
-							<span id="itemkindTxt"></span>
+							<span id="itemkindCdTxt"></span>
 							<input type="hidden" name="itemkindCdList"/>
 						</td>
 					</tr>

+ 15 - 6
src/main/webapp/WEB-INF/views/statistics/PlanTradingForm.html

@@ -43,8 +43,8 @@
 					<tr>
 					   <th>물류구분</th>
 					   <td colspan="2">
-                            <label class="chkBox checked"><input type="checkbox" name="multiDistributionGb" value="SCM" checked="checked"/>입점</label>
-                            <label class="chkBox checked"><input type="checkbox" name="multiDistributionGb" value="WMS" checked="checked"/>위탁</label>
+                            <label class="chkBox checked"><input type="checkbox" name="distributionGbS" value="SCM" checked="checked"/>입점</label>
+                            <label class="chkBox checked"><input type="checkbox" name="distributionGbW" value="WMS" checked="checked"/>위탁</label>
 					   </td>
 					</tr>
 				</table>
@@ -76,6 +76,7 @@
 			<ul class="panelBar">
 				<li>
 					<button type="button" class="btn btn-default btn-lg" onclick="fnDetailExcelDownLoad();">엑셀다운로드</button>
+					<span id="planNmTxt" style="text-align: left"></span>
 				</li>
 			</ul>
 			<div id="detailGridList" style="width: 100%; height: 470px" class="ag-theme-balham"></div>
@@ -139,9 +140,9 @@
 				return !gagajf.isNull(params.value) ? params.value.addComma() : '0';
 			}
 		},
-		{ headerName: "구매율", field: "custCnt", width: 150, cellClass: 'text-right',
+		{ headerName: "구매율", field: "ordRate", width: 150, cellClass: 'text-right',
 			cellRenderer: function(params) {
-				return !gagajf.isNull(params.value) ? params.value.addComma() : '0';
+				return params.value + '%';
 			}
 		},
 	];
@@ -162,6 +163,7 @@
 			$("#detailSearchForm input[name=startDt]").val($("#searchForm input[name=startDt]").val());
 			$("#detailSearchForm input[name=endDt]").val($("#searchForm input[name=endDt]").val());
 			$("#detailSearchForm input[name=planSq]").val(params.planSq);
+			$("#planNmTxt").text(params.planNm);
 			gagaAgGrid.fetch($('#detailSearchForm').prop('action'), detailGridOptions, '#detailSearchForm', fnDetailCreateTotal);
 		}
 	}
@@ -170,10 +172,10 @@
 	detailGridOptions.onCellClicked = function(event) {
 		var params = event.data;
 		if (event.colDef.field == "goodsCd"){
-			cfnOpenGoodsDetailPopup('U',goodsCd);
+			cfnOpenGoodsDetailPopup('U',params.goodsCd);
 		}
 		else if (event.colDef.field == "goodsNm"){
-			cfnOpenGoodsDetailPopup('U',goodsCd);
+			cfnOpenGoodsDetailPopup('U',params.goodsCd);
 		}
 	}
 
@@ -270,15 +272,22 @@
 		totInfo.ordAmt   = 0;
 		totInfo.ordQty   = 0;
 		totInfo.custCnt  = 0;
+		totInfo.ordRate = 0;
+
+		let len = 0;
 
 		detailGridOptions.api.forEachNode(function(rowNode, index) {
 			if (!rowNode.group) {
 				if( typeof rowNode.data.ordAmt        == 'number') { totInfo.ordAmt         += rowNode.data.ordAmt        ; }
 				if( typeof rowNode.data.ordQty        == 'number') { totInfo.ordQty         += rowNode.data.ordQty        ; }
 				if( typeof rowNode.data.custCnt       == 'number') { totInfo.custCnt        += rowNode.data.custCnt       ; }
+				if( typeof rowNode.data.ordRate       == 'number') { totInfo.ordRate        += rowNode.data.ordRate       ; if (rowNode.data.ordRate > 0) len++;}
 			}
 		});
 
+		if (len == 0) totInfo.ordRate = 0;
+		else totInfo.ordRate = Math.floor(totInfo.ordRate / len);
+
 		gagaAgGrid.setPinnedRowData(detailGridOptions, totInfo, 'top');
 	}
 

+ 250 - 0
src/main/webapp/WEB-INF/views/statistics/SubPaymentForm.html

@@ -0,0 +1,250 @@
+<!DOCTYPE html>
+<html lang="ko"
+	xmlns:th="http://www.thymeleaf.org">
+<!--
+ *******************************************************************************
+ * @source  : SubPaymentForm.html
+ * @desc    : 부결제수단별통계 Page
+ *============================================================================
+ * STYLE24
+ * Copyright(C) 2020 TSIT, All rights reserved.
+ *============================================================================
+ * VER  DATE         AUTHOR      DESCRIPTION
+ * ===  ===========  ==========  =============================================
+ * 1.0  2021.09.28   swkim       최초 작성
+ *******************************************************************************
+ -->
+	<div id="main">
+		<!-- 메인타이틀 영역 -->
+		<div class="main-title">
+		</div>
+		<!-- //메인타이틀 영역 -->
+
+		<!-- 메뉴 설명 -->
+		<div class="infoBox menu-desc">
+		</div>
+		<!-- //메뉴 설명 -->
+
+		<!-- 검색조건 영역 -->
+		<div class="panelStyle">
+			<form id="searchForm" name="searchForm" action="#" th:action="@{'/statistics/payment/sub/list'}" onsubmit="$('#btnSearch').trigger('click'); return false;">
+				<input type="hidden" name="dayGb" value="D"/>
+
+				<table class="frmStyle" aria-describedby="검색조건">
+					<colgroup>
+						<col style="width:10%;"/>
+						<col style="width:25%;"/>
+						<col style="width:10%;"/>
+						<col style="width:25%;"/>
+						<col style="width:10%;"/>
+						<col style="width:20%;"/>
+					</colgroup>
+					<tr>
+						<th>기간<i class="required" title="필수" aria-hidden="true"></i></th>
+						<td colspan="5" id="terms">
+						</td>
+					</tr>
+					<tr>
+						<th>포인트 유형</th>
+						<td>
+							<select name="pointGb">
+								<option value="">[전체]</option>
+								<option th:if="${pointGbList}" th:each="oneData, status : ${pointGbList}" th:value="${oneData.cd}" th:text="${'[' + oneData.cd + '] ' + oneData.cdNm}"></option>
+							</select>
+						</td>
+						<th>상품권 유형</th>
+						<td colspan="3">
+							<select name="giftCardGb">
+								<option value="">[전체]</option>
+								<option th:if="${giftCardGbList}" th:each="oneData, status : ${giftCardGbList}" th:value="${oneData.cd}" th:text="${'[' + oneData.cd + '] ' + oneData.cdNm}"></option>
+							</select>
+						</td>
+					</tr>
+				</table>
+
+				<ul class="panelBar">
+					<li class="center">
+						<button type="button" class="btn btn-base btn-lg" id="btnSearch">조회</button>
+						<button type="button" class="btn btn-gray btn-lg" id="btnInit">초기화</button>
+					</li>
+				</ul>
+			</form>
+		</div>
+		<!-- 검색조건 영역 -->
+
+		<!-- 리스트 영역 -->
+		<div class="panelStyle">
+			<!-- 버튼 배치 영역 -->
+			<ul class="panelBar">
+				<li class="left">
+					<button type="button" class="btn btn-default btn-lg" id="btnExcel">엑셀다운로드</button>
+				</li>
+				<li class="right">
+					<span class="btnGroup marR10">
+						<button type="button" class="btn btn-default btn-lg active" id="dayGbD" onclick="fnSetDayGb('D');">일별</button>
+						<button type="button" class="btn btn-default btn-lg" id="dayGbW" onclick="fnSetDayGb('W');">주별</button>
+						<button type="button" class="btn btn-default btn-lg" id="dayGbM" onclick="fnSetDayGb('M');">월별</button>
+					</span>
+				</li>
+			</ul>
+			<!-- //버튼 배치 영역 -->
+
+			<div id="gridList" style="width: 100%; height: 470px" class="ag-theme-balham"></div>
+		</div>
+		<!-- //리스트 영역 -->
+
+		<div class="panelStyle">
+			<table class="frmStyle" aria-describedby="잔액">
+				<colgroup>
+					<col style="width:30%;"/>
+					<col style="width:35%;"/>
+					<col style="width:35%;"/>
+				</colgroup>
+				<tr>
+					<th rowspan="2">현 잔액</th>
+					<th>포인트</th>
+					<th>상품권</th>
+				</tr>
+				<tr>
+					<td style="text-align: center;" th:text="${#numbers.formatInteger(remainPoint, 0,'COMMA')}"></td>
+					<td style="text-align: center;" th:text="${#numbers.formatInteger(remainGiftCard, 0,'COMMA')}"></td>
+				</tr>
+			</table>
+		</div>
+	</div>
+
+<script th:inline="javascript">
+/*<![CDATA[*/
+	let columnDefs = [
+		{ headerName: "기간", field: "day", width: 100, cellClass: 'text-center' },
+		{
+			headerName: "포인트", field: "", width: 600, cellClass: 'text-center',
+			children: [
+				{headerName: "적립액", field: "pntGive", width: 200, cellClass: 'text-center',
+					cellRenderer: function(params) {
+						return gagaAgGrid.toAddComma(params.value);
+					}
+				},
+				{headerName: "사용주문수", field: "pntOrdCnt", width: 200, cellClass: 'text-center',
+					cellRenderer: function(params) {
+						return gagaAgGrid.toAddComma(params.value);
+					}
+				},
+				{headerName: "사용액", field: "pntUse", width: 200, cellClass: 'text-center',
+					cellRenderer: function(params) {
+						return gagaAgGrid.toAddComma(params.value);
+					}
+				}
+			]
+		},
+		{
+			headerName: "상품권", field: "", width: 600, cellClass: 'text-center',
+			children: [
+				{headerName: "등록매수", field: "giftRegCnt", width: 200, cellClass: 'text-center',
+					cellRenderer: function(params) {
+						return gagaAgGrid.toAddComma(params.value);
+					}
+				},
+				{headerName: "사용주문수", field: "giftOrdCnt", width: 200, cellClass: 'text-center',
+					cellRenderer: function(params) {
+						return gagaAgGrid.toAddComma(params.value);
+					}
+				},
+				{headerName: "사용액", field: "giftUse", width: 200, cellClass: 'text-center',
+					cellRenderer: function(params) {
+						return gagaAgGrid.toAddComma(params.value);
+					}
+				}
+			]
+		}
+	];
+
+	let gridOptions = gagaAgGrid.getGridOptions(columnDefs);
+
+	gridOptions.autoGroupColumnDef = {
+			headerName: "일자",
+			field: "grouping",
+			width: 200,
+			cellRendererParams: {
+				suppressCount: true
+			}
+		};
+
+	// for expand everything
+	gridOptions.groupDefaultExpanded = -1;
+
+	// 검색
+	$('#btnSearch').on('click', function() {
+		// 입력 값 체크
+		if (!gagajf.validation($('#searchForm')))
+			return false;
+
+		gagaAgGrid.fetch($('#searchForm').prop('action'), gridOptions, '#searchForm', fnCreateTotal);
+	});
+
+	// 합계 생성
+	let fnCreateTotal = function() {
+		// Draw chart
+
+		let pntGive = 0;
+		let pntOrdCnt = 0;
+		let pntUse = 0;
+		let giftRegCnt = 0;
+		let giftOrdCnt = 0;
+		let giftUse = 0;
+
+		gridOptions.api.forEachNode(function(rowNode, index) {
+			if (!rowNode.group) {
+				if (typeof rowNode.data.pntGive == 'number') { pntGive += rowNode.data.pntGive; }
+				if (typeof rowNode.data.pntOrdCnt == 'number') { pntOrdCnt += rowNode.data.pntOrdCnt; }
+				if (typeof rowNode.data.pntUse == 'number') { pntUse += rowNode.data.pntUse; }
+				if (typeof rowNode.data.giftRegCnt == 'number') { giftRegCnt += rowNode.data.giftRegCnt; }
+				if (typeof rowNode.data.giftOrdCnt == 'number') { giftOrdCnt += rowNode.data.giftOrdCnt; }
+				if (typeof rowNode.data.giftUse == 'number') { giftUse += rowNode.data.giftUse; }
+			}
+		});
+
+		let data = {
+			day: 'TOTAL',
+			pntGive: pntGive, pntOrdCnt: pntOrdCnt, pntUse: pntUse,
+			giftRegCnt: giftRegCnt, giftOrdCnt: giftOrdCnt, giftUse: giftUse
+		};
+
+		gagaAgGrid.setPinnedRowData(gridOptions, data, 'top');
+	}
+
+	// 초기화 클릭시
+	$('#btnInit').on('click', function() {
+		$('#searchForm')[0].reset();
+
+		$('#cardIdTxt').html('');
+		$('#searchForm input[name=cardIdList]').val('');
+	});
+
+	// 엑셀다운로드
+	$('#btnExcel').on('click', function() {
+		gagaAgGrid.exportToExcel('부결제수단별통계 목록', gridOptions);
+	});
+
+	// 일자구분 변경 시
+	var fnSetDayGb = function(dayGb) {
+		$('#searchForm input[name=dayGb]').val(dayGb);
+		$('#dayGbD').removeClass('active');
+		$('#dayGbW').removeClass('active');
+		$('#dayGbM').removeClass('active');
+		$('#dayGb' + dayGb).addClass('active');
+		$('#btnSearch').trigger('click');
+	}
+
+	$(document).ready(function() {
+		cfnCreateCalendar('#terms', 'startDt', 'endDt', true, '주문', undefined, ['btnToday']);
+		$('.btnRecentWeek').trigger('click');
+
+		// Create a agGrid
+		gagaAgGrid.createGrid('gridList', gridOptions);
+
+	});
+/*]]>*/
+</script>
+
+</html>

+ 4 - 2
src/main/webapp/WEB-INF/views/statistics/TmtbTradingForm.html

@@ -75,6 +75,7 @@
 			<ul class="panelBar">
 				<li>
 					<button type="button" class="btn btn-default btn-lg" onclick="fnDetailExcelDownLoad();">엑셀다운로드</button>
+					<span id="tmtbNmTxt" style="text-align: left"></span>
 				</li>
 			</ul>
 			<div id="detailGridList" style="width: 100%; height: 470px" class="ag-theme-balham"></div>
@@ -165,6 +166,7 @@
 			$("#detailSearchForm input[name=startDt]").val($("#searchForm input[name=startDt]").val());
 			$("#detailSearchForm input[name=endDt]").val($("#searchForm input[name=endDt]").val());
 			$("#detailSearchForm input[name=tmtbSq]").val(params.tmtbSq);
+			$("#tmtbNmTxt").text(params.tmtbNm);
 			gagaAgGrid.fetch($('#detailSearchForm').prop('action'), detailGridOptions, '#detailSearchForm', fnDetailCreateTotal);
 		}
 	}
@@ -173,10 +175,10 @@
 	detailGridOptions.onCellClicked = function(event) {
 		var params = event.data;
 		if (event.colDef.field == "goodsCd"){
-			cfnOpenGoodsDetailPopup('U',goodsCd);
+			cfnOpenGoodsDetailPopup('U',params.goodsCd);
 		}
 		else if (event.colDef.field == "goodsNm"){
-			cfnOpenGoodsDetailPopup('U',goodsCd);
+			cfnOpenGoodsDetailPopup('U',params.goodsCd);
 		}
 	}
 

+ 28 - 0
src/main/webapp/ux/js/admin.popup.js

@@ -873,6 +873,34 @@ var cfnOpenCompanyListPopup = function(callbackfn, multiGb, searchTxt, inputId,
 	}
 }
 
+var cfnOpenCompanyListPopup2 = function(callbackfn, multiGb, searchTxt, inputId, selfYn) {
+	var actionUrl = "/business/comapny/search/scm/form?callbackFn=" + callbackfn;
+	if (typeof(multiGb) != 'undefined' && multiGb != null && multiGb == "M") actionUrl += "&multiGb=" + multiGb; else actionUrl += "&multiGb=S";
+	if (typeof(searchTxt) != 'undefined') actionUrl += "&searchTxt=" + encodeURIComponent(searchTxt);
+	if (typeof(selfYn) != 'undefined') actionUrl += "&selfYn="+ selfYn ; else actionUrl += "&selfYn=" ;
+	if(multiGb == "S") {
+		if(searchTxt && searchTxt != "" && inputId && inputId != "") {
+			var data = {  searchTxt : searchTxt, searchGb : "NAME"};
+			var jsonData = JSON.stringify(data);
+
+			gagajf.ajaxJsonSubmit('/business/supply/company/scm/list', jsonData, function(result) {
+				if(result && result.length == 1) {
+					$("#" + inputId).val(result[0].supplyCompCd);
+				} else {
+					uifnPopupClose('popupCompanyList2');
+					cfnOpenModalPopup(actionUrl, 'popupCompanyList2');
+				}
+			});
+		} else {
+			uifnPopupClose('popupCompanyList2');
+			cfnOpenModalPopup(actionUrl, 'popupCompanyList2');
+		}
+	} else {
+		uifnPopupClose('popupCompanyList2');
+		cfnOpenModalPopup(actionUrl, 'popupCompanyList2');
+	}
+}
+
 /**
  * @type   : function
  * @access : public