변경 파일 목록
총 124개
반응형→적응형 스킨 전환 시 프론트 오류 수정
design_skin_list.phpAdmin/design/mobile_config.phpAdmin/mobile/DesignSkinPolicy.phpComponent/Policy/Policy.phpComponent/Policy/MobileConfigController.phpController/Admin/Mobile/UserLayoutFront.phpCore/Base/Interceptor/UserLayoutMobile.phpCore/Base/Interceptor/HttpHandler.phpFramework/Debug/Handler/카카오페이 결제 처리 안정성 개선
PgNoti.phpComponent/Payment/Kakaopay/PgReturn.phpComponent/Payment/Kakaopay/PaymentNotiLockGuard.phpComponent/Payment/카카오페이 결제 취소 시 주문 상태 처리 개선
KakaopayConfig.phpComponent/Payment/Kakaopay/NotiCancelReservation.phpComponent/Payment/Kakaopay/PgNoti.phpComponent/Payment/Kakaopay/PgReturn.phpComponent/Payment/Kakaopay/PaymentNotiLockGuard.phpComponent/Payment/탈퇴·휴면 회원 주문 개인정보 보안 강화
frame_cash_receipt_register.phpAdmin/order/frame_cash_receipt_view.phpAdmin/order/inc_claim_view.phpAdmin/order/layer_refund_view.phpAdmin/order/layer_regular_order_shipping_address.phpAdmin/order/layout_order_goods_list.phpAdmin/order/layout_order_goods_simple_list.phpAdmin/order/layout_order_list.phpAdmin/order/layout_order_search_form.phpAdmin/order/layout_order_view_order_info.phpAdmin/order/layout_order_view_receiver_info.phpAdmin/order/layout_order_view_receiver_info_modify.phpAdmin/order/logistics_layout_order_goods_list.phpAdmin/order/order_list_withdrawn_member.phpAdmin/order/order_print_customerReport.phpAdmin/order/order_print_report.phpAdmin/order/order_print_taxInvoice.phpAdmin/order/order_view.phpAdmin/order/popup_order_cash_receipt_reissue.phpAdmin/order/popup_order_packet.phpAdmin/order/post_issue.phpAdmin/order/post_reserve.phpAdmin/order/refund_do.phpAdmin/order/refund_do_new.phpAdmin/order/regular_order_view.phpAdmin/order/tax_invoice_request.phpAdmin/order/_manage_permission_menu_list.phpAdmin/policy/layer_handle_reason.phpAdmin/share/AdminLogDAO.phpComponent/Admin/AdminMenu.phpComponent/Admin/CouponAdmin.phpComponent/Coupon/DBTableField.phpComponent/Database/ExcelRequest.phpComponent/Excel/HackOutService.phpComponent/Member/HackOut/MemberMasking.phpComponent/Member/MemberSleep.phpComponent/Member/SleepDAO.phpComponent/Member/Sleep/SleepService.phpComponent/Member/Sleep/Order.phpComponent/Order/OrderAdmin.phpComponent/Order/OrderAdminNew.phpComponent/Order/OrderDelete.phpComponent/Order/OrderNew.phpComponent/Order/ReOrderCalculation.phpComponent/Order/Tax.phpComponent/Order/CashReceipt.phpComponent/Payment/Escrow.phpComponent/Payment/PresentNotification.phpComponent/Present/Notification/RegularOrderAdminDetail.phpComponent/RegularDelivery/RegularOrderAdmin/RegularOrderAdminDetailHandler.phpComponent/RegularDelivery/RegularOrderAdmin/RegularOrderAdminList.phpComponent/RegularDelivery/RegularOrderAdmin/RegularOrderAdminListExcel.phpComponent/RegularDelivery/RegularOrderAdmin/SafeNumber.phpComponent/Service/SmsAdmin.phpComponent/Sms/SmsSendPsController.phpController/Admin/Member/CashReceiptListController.phpController/Admin/Order/EpostReturnRequestController.phpController/Admin/Order/FrameCashReceiptRegisterController.phpController/Admin/Order/FrameCashReceiptViewController.phpController/Admin/Order/FrameTaxInvoiceRegisterController.phpController/Admin/Order/IncClaimViewController.phpController/Admin/Order/LayerRefundViewController.phpController/Admin/Order/LayerRegularOrderController.phpController/Admin/Order/LogisticsListController.phpController/Admin/Order/OrderListAllController.phpController/Admin/Order/OrderListBackController.phpController/Admin/Order/OrderListCancelController.phpController/Admin/Order/OrderListDeliveryController.phpController/Admin/Order/OrderListDeliveryOkController.phpController/Admin/Order/OrderListExchangeController.phpController/Admin/Order/OrderListFailController.phpController/Admin/Order/OrderListGoodsController.phpController/Admin/Order/OrderListOrderController.phpController/Admin/Order/OrderListPayController.phpController/Admin/Order/OrderListRefundController.phpController/Admin/Order/OrderListSettleController.phpController/Admin/Order/OrderListUserExchangeController.phpController/Admin/Order/OrderListWithdrawnMemberController.phpController/Admin/Order/OrderPrintController.phpController/Admin/Order/OrderViewController.phpController/Admin/Order/PopupOrderCashReceiptReissueController.phpController/Admin/Order/PopupOrderPacketController.phpController/Admin/Order/PostIssueController.phpController/Admin/Order/PostReserveController.phpController/Admin/Order/RefundViewController.phpController/Admin/Order/RefundViewNewController.phpController/Admin/Order/RegularOrderListController.phpController/Admin/Order/RegularOrderViewController.phpController/Admin/Order/TaxInvoiceListController.phpController/Admin/Order/TaxInvoiceRequestController.phpController/Admin/Order/CouponManageController.phpController/Admin/Promotion/CouponOfflineManageController.phpController/Admin/Promotion/OrderListWithdrawnMemberController.phpController/Admin/Provider/Order/LayerComebackCouponResultController.phpController/Admin/Share/LayerHandleReasonController.phpController/Admin/Share/SetNaverpayController.phpController/Api/Godo/SyncController.phpController/Internal/Naverpay/AutoOrderCancelJob.phpJob/AutoOrderStatusDeliveryJob.phpJob/AutoOrderStatusJob.phpJob/LapseOrderDeleteJob.phpJob/MemberHackoutOrderJob.phpJob/MemberSleepJob.phpJob/MemberSleepOrderJob.phpJob/OrderGoodsRepository.phpRepository/Order/RegularOrderApplierRepository.phpRepository/RegularDelivery/RegularOrder/ContainerDefinitionsBundle.phpFramework/Application/Bootstrap/ContainerDefinitionsOrigin.phpFramework/Application/Bootstrap/변경 파일 코드
추가삭제
변경 전design_skin_list.php
| const skinDevice = targetType === SKIN_TYPE.RESPONSIVE ? 'front' : targetType; | |
| const deviceLabel = skinDevice === 'front' ? 'PC' : '모바일'; | |
| const otherDeviceLabel = skinDevice === 'front' ? '모바일' : 'PC'; | |
| return { | |
| message: `${skinName} 스킨을 게시하시겠습니까?`, | |
| subMessage: `<p class="layer-description--sub">현재 선택한 ${deviceLabel} 스킨만 게시할 경우, 일부 디바이스에서 페이지 접근 오류가 발생할 수 있습니다.<br><br>정상적인 서비스 제공을 위해 ${otherDeviceLabel} 스킨을 함께 게시해 주세요.<br><br>※ 모바일 스킨은 [모바일샵 설정 > 사용함] 상태에서만 정상적으로 노출됩니다.<br>※ [확인] 클릭 시 스킨이 게시되며, '모바일샵 설정' 페이지로 바로 이동합니다.</p>`, | |
| skinName, | |
| ); | |
| NCDSConfirm({ | |
| message: config.message, | |
| subMessage: config.subMessage | |
변경 후design_skin_list.php
| const skinDevice = targetType === SKIN_TYPE.RESPONSIVE ? 'front' : targetType; | |
| const deviceLabel = skinDevice === 'front' ? 'PC' : '모바일'; | |
| const otherDeviceLabel = skinDevice === 'front' ? '모바일' : 'PC'; | |
| // 모바일만 먼저 게시하면 PC 사용스킨이 비어 PC 프론트 전체가 열리지 않는다 | |
| if (skinDevice === 'mobile') { | |
| return { | |
| message: 'PC 스킨을 먼저 게시해 주세요.', | |
| subMessage: '<p class="layer-description--sub">현재 반응형 스킨을 사용 중입니다. 적응형 스킨으로 변경하려면 PC 스킨을 먼저 게시한 뒤 모바일 스킨을 게시해 주세요.</p>', | |
| onConfirm: 'block' | |
| }; | |
| } | |
| return { | |
| message: `${skinName} 스킨을 게시하시겠습니까?`, | |
| subMessage: `<p class="layer-description--sub">현재 선택한 ${deviceLabel} 스킨만 게시할 경우, 일부 디바이스에서 페이지 접근 오류가 발생할 수 있습니다.<br><br>정상적인 서비스 제공을 위해 ${otherDeviceLabel} 스킨을 함께 게시해 주세요.<br><br>※ 모바일 스킨은 [모바일샵 설정 > 사용함] 상태에서만 정상적으로 노출됩니다.<br>※ [확인] 클릭 시 스킨이 게시되며, '모바일샵 설정' 페이지로 바로 이동합니다.</p>`, | |
| skinName, | |
| ); | |
| if (config.onConfirm === 'block') { | |
| NCDSAlert({ | |
| message: config.message, | |
| subMessage: config.subMessage | |
| }); | |
| return; | |
| } | |
| NCDSConfirm({ | |
| message: config.message, | |
| subMessage: config.subMessage | |
변경 전mobile_config.php
| const initialMobileShopFl = '<?= $data['mobileShopFl'] ?? 'n' ?>'; | |
| const isMyappInstalled = <?= json_encode($isMyappInstalled ?? false) ?>; | |
| const isMyappReleased = <?= json_encode($isMyappReleased ?? false) ?>; | |
| // 마이앱 사용 중 + 적응형 스킨 사용 중 + 모바일샵 사용안함인 경우 안내 얼럿 | |
| if (isMyappInstalled && isMyappReleased && currentSkinType === 'adaptive' && initialMobileShopFl === 'n') { | |
| return false; | |
| } | |
| form.target = 'ifrmProcess'; | |
| form.submit(); | |
| return false; | |
변경 후mobile_config.php
| const initialMobileShopFl = '<?= $data['mobileShopFl'] ?? 'n' ?>'; | |
| const isMyappInstalled = <?= json_encode($isMyappInstalled ?? false) ?>; | |
| const isMyappReleased = <?= json_encode($isMyappReleased ?? false) ?>; | |
| const hasMobileLiveSkin = <?= json_encode($hasMobileLiveSkin ?? true) ?>; | |
| // 마이앱 사용 중 + 적응형 스킨 사용 중 + 모바일샵 사용안함인 경우 안내 얼럿 | |
| if (isMyappInstalled && isMyappReleased && currentSkinType === 'adaptive' && initialMobileShopFl === 'n') { | |
| return false; | |
| } | |
| // 적응형인데 모바일 사용스킨이 비어 있으면 모바일 전 페이지가 열리지 않는다 | |
| if (currentSkinType === 'adaptive' && !hasMobileLiveSkin && selectedMobileShopFl === 'y') { | |
| NCDSConfirm({ | |
| message: '게시된 모바일 스킨이 없습니다.', | |
| subMessage: '<p class="layer-description--sub">모바일샵을 사용하려면 \'디자인 스킨 리스트\'에서 모바일 스킨을 먼저 게시해 주세요. 모바일 스킨 없이 모바일샵을 사용하면 모바일 쇼핑몰이 열리지 않습니다.</p>' | |
| }).then(function(result) { | |
| if (result) { | |
| location.href = '/design/design_skin_list.php'; | |
| } | |
| }); | |
| return false; | |
| } | |
| form.target = 'ifrmProcess'; | |
| form.submit(); | |
| return false; | |
변경 전DesignSkinPolicy.php
| if ($this->hasGlobalMallDefaultSkin() === false) { | |
| $currentPolicy = $this->getValue(self::KEY, $this->requestPolicy['sno']); | |
| } | |
| $this->initBoardSkinByChangeSkinLive(); | |
| $validatePolicy = $this->validateSkin(); | |
| && $newSkinType === DesignEditorSkinType::RESPONSIVE->value; | |
| } | |
| /** | |
| * 스킨 타입 전환 시 충돌 하는 정책 초기화 | |
| * | |
| { | |
| // 반응형 -> 적응형 전환 | |
| if ($this->isResponsiveToAdaptiveTransition($currentPolicy)) { | |
| // mobileLive 게시 중이면 frontLive 초기화 | |
| if (!empty($validatePolicy['mobileLive'])) { | |
| $validatePolicy['frontLive'] = ''; | |
| \Logger::channel('designEditor')->info(__METHOD__ . ' - Responsive to Adaptive: frontLive reset (mobile skin publish)'); | |
| } | |
| // frontLive 게시 중이면 mobileLive 초기화 | |
| if (!empty($validatePolicy['frontLive'])) { | |
| $validatePolicy['mobileLive'] = ''; | |
| \Logger::channel('designEditor')->info(__METHOD__ . ' - Responsive to Adaptive: mobileLive reset (PC skin publish)'); | |
| } | |
| } | |
| // 적응형 -> 반응형 전환 | |
변경 후DesignSkinPolicy.php
| if ($this->hasGlobalMallDefaultSkin() === false) { | |
| $currentPolicy = $this->getValue(self::KEY, $this->requestPolicy['sno']); | |
| } | |
| // 게시판 테마가 먼저 바뀐 뒤 거부되면 사용스킨과 게시판 테마가 어긋난 채 남는다 | |
| if ($this->requestPolicy['skinUse'] === 'Live') { | |
| $this->validateResponsiveSkinPublishOrder($currentPolicy); | |
| } | |
| $this->initBoardSkinByChangeSkinLive(); | |
| $validatePolicy = $this->validateSkin(); | |
| && $newSkinType === DesignEditorSkinType::RESPONSIVE->value; | |
| } | |
| /** | |
| * 반응형 사용 중 PC 스킨 없이 모바일 스킨만 게시하는 요청 거부 | |
| * | |
| * @param array $currentPolicy | |
| * @return void | |
| * @throws Exception | |
| */ | |
| protected function validateResponsiveSkinPublishOrder(array $currentPolicy): void | |
| { | |
| if (!$this->isResponsiveToAdaptiveTransition($currentPolicy)) { | |
| return; | |
| } | |
| // 모바일만 먼저 게시하면 PC 사용스킨이 비어 PC 프론트 전체가 열리지 않는다 | |
| if (empty($this->requestPolicy['frontLive']) && !empty($this->requestPolicy['mobileLive'])) { | |
| throw new Exception(__('반응형 스킨 사용 중에는 PC 스킨을 먼저 게시해 주세요.')); | |
| } | |
| } | |
| /** | |
| * 스킨 타입 전환 시 충돌 하는 정책 초기화 | |
| * | |
| { | |
| // 반응형 -> 적응형 전환 | |
| if ($this->isResponsiveToAdaptiveTransition($currentPolicy)) { | |
| // frontLive 만 게시 중이면 mobileLive 초기화 | |
| if (!empty($validatePolicy['frontLive']) && empty($validatePolicy['mobileLive'])) { | |
| $validatePolicy['mobileLive'] = ''; | |
| \Logger::channel('designEditor')->info(__METHOD__ . ' - Responsive to Adaptive: mobileLive reset (PC skin publish)'); | |
| } | |
| // PC·모바일을 한 요청에 함께 게시하면 둘 다 유지하되 게시판 테마는 saveSkin 이 한쪽만 갱신하므로, 동시 게시 호출부를 만들 때 initialSaveSkin 처럼 양쪽 테마 갱신을 함께 넣어야 한다 | |
| } | |
| // 적응형 -> 반응형 전환 | |
변경 전Policy.php
| use Framework\Utility\HttpUtils; | |
| use Framework\Utility\StringUtils; | |
| use Framework\Debug\Exception\AlertCloseException; | |
| use Globals; | |
| use Logger; | |
| use Origin\Service\Policy\ShopInfoChangedTopicService; | |
| use Request; | |
| */ | |
| public function saveMobileConfig($getValue) | |
| { | |
| // 이미지 폴더의 체크 | |
| $imagePath = UserFilePath::data('mobile'); | |
| if ($imagePath->isDir() === false) { | |
| } | |
| } | |
| /** | |
| * 모바일샵 디자인 설정 저장하기 | |
| * | |
변경 후Policy.php
| use Framework\Utility\HttpUtils; | |
| use Framework\Utility\StringUtils; | |
| use Framework\Debug\Exception\AlertCloseException; | |
| use Framework\Debug\Exception\LayerNotReloadException; | |
| use Globals; | |
| use Origin\Enum\Design\DesignEditorSkinType; | |
| use Logger; | |
| use Origin\Service\Policy\ShopInfoChangedTopicService; | |
| use Request; | |
| */ | |
| public function saveMobileConfig($getValue) | |
| { | |
| $this->validateMobileShopUsable($getValue); | |
| // 이미지 폴더의 체크 | |
| $imagePath = UserFilePath::data('mobile'); | |
| if ($imagePath->isDir() === false) { | |
| } | |
| } | |
| /** | |
| * 모바일샵 사용함 저장 요청을 현재 사용스킨 기준으로 거부 | |
| * | |
| * @param array $getValue 모바일샵 설정 저장 요청 (mobileShopFl: y|n) | |
| * @return void | |
| * @throws LayerNotReloadException | |
| */ | |
| protected function validateMobileShopUsable(array $getValue): void | |
| { | |
| if (($getValue['mobileShopFl'] ?? '') !== 'y') { | |
| return; | |
| } | |
| $skinPolicy = $this->getValue('design.skin') ?: []; | |
| $skinType = $skinPolicy['skinType'] ?? DesignEditorSkinType::ADAPTIVE->value; | |
| if ($skinType === DesignEditorSkinType::RESPONSIVE->value) { | |
| throw new LayerNotReloadException(__('반응형 스킨 사용 중에는 모바일샵을 사용할 수 없습니다. \'디자인 스킨 리스트\'에서 적응형 스킨으로 변경해 주세요.')); | |
| } | |
| // 모바일 사용스킨이 비면 모바일 프론트 전체가 503 으로 열리지 않는다 | |
| if (empty($skinPolicy['mobileLive'])) { | |
| throw new LayerNotReloadException(__('게시된 모바일 스킨이 없어 모바일샵을 사용할 수 없습니다. 모바일 스킨을 먼저 게시해 주세요.')); | |
| } | |
| } | |
| /** | |
| * 모바일샵 디자인 설정 저장하기 | |
| * | |
변경 전MobileConfigController.php
| $this->setData('browserCheck', $browserCheck); | |
| $this->setData('checked', $checked); | |
| $this->setData('currentSkinType', $currentSkinType); | |
| $this->setData('isMyappInstalled', $isMyappInstalled); | |
| $this->setData('isMyappReleased', $isMyappReleased); | |
| } | |
변경 후MobileConfigController.php
| $this->setData('browserCheck', $browserCheck); | |
| $this->setData('checked', $checked); | |
| $this->setData('currentSkinType', $currentSkinType); | |
| $this->setData('hasMobileLiveSkin', !empty($designSkinConfig['mobileLive'])); | |
| $this->setData('isMyappInstalled', $isMyappInstalled); | |
| $this->setData('isMyappReleased', $isMyappReleased); | |
| } | |
변경 전UserLayoutFront.php
| { | |
| } | |
| /** | |
| * {@inheritDoc} | |
| */ | |
| public function preHandle(AbstractController $controller) | |
| { | |
| // 현재 페이지가 index 인경우 main -> index 로 처리 (스킨 동기화 처리) | |
| if ($controller->getPageName() === 'index') { | |
| $currentPageName = gd_entryway('front'); | |
변경 후UserLayoutFront.php
| { | |
| } | |
| /** | |
| * @throws HttpException | |
| */ | |
| protected function validateUsingSkinName(?string $skinName): void | |
| { | |
| // 스킨 전환 직후 사용스킨이 비면 이후 스킨 경로 해석에서 Fatal 이 나므로 진입부에서 오류 화면으로 끊는다 | |
| if (empty($skinName)) { | |
| Logger::channel('designEditor')->error('사용스킨이 지정되지 않아 레이아웃을 구성할 수 없습니다.', [ | |
| 'skinKey' => 'gSkin.frontSkinName', | |
| ]); | |
| throw new HttpException('not exists using skin', 503); | |
| } | |
| } | |
| protected function isLayoutlessRequest(string $phpSelf): bool | |
| { | |
| // PG 통보·처리 요청은 레이아웃을 그리지 않아 사용스킨이 비어도 처리됐으므로 막지 않는다 | |
| return str_starts_with($phpSelf, '/payment/') || str_contains(basename($phpSelf), '_ps'); | |
| } | |
| /** | |
| * {@inheritDoc} | |
| */ | |
| public function preHandle(AbstractController $controller) | |
| { | |
| if (!$this->isLayoutlessRequest(Request::getPhpSelf())) { | |
| $this->validateUsingSkinName(Globals::get('gSkin.frontSkinName')); | |
| } | |
| // 현재 페이지가 index 인경우 main -> index 로 처리 (스킨 동기화 처리) | |
| if ($controller->getPageName() === 'index') { | |
| $currentPageName = gd_entryway('front'); | |
변경 전UserLayoutMobile.php
| { | |
| } | |
| /** | |
| * {@inheritDoc} | |
| */ | |
| public function preHandle(AbstractController $controller) | |
| { | |
| // 현재 페이지가 index 인경우 main -> index 로 처리 (스킨 동기화 처리) | |
| if ($controller->getPageName() === 'index') { | |
| $currentPageName = gd_entryway('mobile'); | |
| // 상단 배경이미지 | |
| if (empty($cfg['outline_header']) === false) { | |
| if (empty($pagesInfo[$cfg['outline_header']]['inbg_img']) === false) { | |
| $cfg['topbg_img'] = UserFilePath::frontSkin(Globals::get('gSkin.frontSkinName'), 'img', 'codi', $pagesInfo[$cfg['outline_header']]['inbg_img'])->www(); | |
| } | |
| } | |
| return gd_array_key_exists($outlineName, $dataFile) && $dataFile[$outlineName] != 'noprint' ? $dataFile[$outlineName] : ''; | |
| } | |
| /** | |
| * 정기결제(배송) 사용 여부 조회 | |
| * | |
변경 후UserLayoutMobile.php
| { | |
| } | |
| /** | |
| * @throws HttpException | |
| */ | |
| protected function validateUsingSkinName(?string $skinName): void | |
| { | |
| // 스킨 전환 직후 사용스킨이 비면 이후 스킨 경로 해석에서 Fatal 이 나므로 진입부에서 오류 화면으로 끊는다 | |
| if (empty($skinName)) { | |
| Logger::channel('designEditor')->error('사용스킨이 지정되지 않아 레이아웃을 구성할 수 없습니다.', [ | |
| 'skinKey' => 'gSkin.mobileSkinName', | |
| ]); | |
| throw new HttpException('not exists using skin', 503); | |
| } | |
| } | |
| protected function isLayoutlessRequest(string $phpSelf): bool | |
| { | |
| // PG 통보·처리 요청은 레이아웃을 그리지 않아 사용스킨이 비어도 처리됐으므로 막지 않는다 | |
| return str_starts_with($phpSelf, '/payment/') || str_contains(basename($phpSelf), '_ps'); | |
| } | |
| /** | |
| * {@inheritDoc} | |
| */ | |
| public function preHandle(AbstractController $controller) | |
| { | |
| if (!$this->isLayoutlessRequest(Request::getPhpSelf())) { | |
| $this->validateUsingSkinName(Globals::get('gSkin.mobileSkinName')); | |
| } | |
| // 현재 페이지가 index 인경우 main -> index 로 처리 (스킨 동기화 처리) | |
| if ($controller->getPageName() === 'index') { | |
| $currentPageName = gd_entryway('mobile'); | |
| // 상단 배경이미지 | |
| if (empty($cfg['outline_header']) === false) { | |
| if (empty($pagesInfo[$cfg['outline_header']]['inbg_img']) === false) { | |
| $topBgImg = $this->getTopBgImageUrl(Globals::get('gSkin.frontSkinName'), $pagesInfo[$cfg['outline_header']]['inbg_img']); | |
| if (!is_null($topBgImg)) { | |
| $cfg['topbg_img'] = $topBgImg; | |
| } | |
| } | |
| } | |
| return gd_array_key_exists($outlineName, $dataFile) && $dataFile[$outlineName] != 'noprint' ? $dataFile[$outlineName] : ''; | |
| } | |
| protected function getTopBgImageUrl(?string $frontSkinName, string $imageName): ?string | |
| { | |
| // 반응형에서 적응형으로 바꾸며 모바일 스킨만 게시하면 PC 사용스킨이 비어도 모바일은 진입 검사를 통과한다 | |
| if (empty($frontSkinName)) { | |
| return null; | |
| } | |
| return UserFilePath::frontSkin($frontSkinName, 'img', 'codi', $imageName)->www(); | |
| } | |
| /** | |
| * 정기결제(배송) 사용 여부 조회 | |
| * | |
변경 전HttpHandler.php
| $seoPolicy = gd_policy('basic.seo', $mallBySession); | |
| $seoData = is_array($seoPolicy) ? ($seoPolicy['errPage'] ?? []) : []; | |
| if (($seoData['useFl'] ?? '') == 'y') { | |
| $exErrorPage = [ | |
| '/payment/payment/payco/pg_start.php', | |
| ]; | |
| // @TODO 에러가 핸들링 되지 않는 부분에 대한 처리 (정적 HTML을 불러와 별도 처리하는 식의 처리가 필요) | |
| } | |
| } | |
| } | |
변경 후HttpHandler.php
| $seoPolicy = gd_policy('basic.seo', $mallBySession); | |
| $seoData = is_array($seoPolicy) ? ($seoPolicy['errPage'] ?? []) : []; | |
| if ($this->isErrorPageRedirectable($exception, $seoData)) { | |
| $exErrorPage = [ | |
| '/payment/payment/payco/pg_start.php', | |
| ]; | |
| // @TODO 에러가 핸들링 되지 않는 부분에 대한 처리 (정적 HTML을 불러와 별도 처리하는 식의 처리가 필요) | |
| } | |
| } | |
| protected function isErrorPageRedirectable(\Throwable $exception, array $seoData): bool | |
| { | |
| // 503 은 사용스킨이 비어 모든 프론트 페이지가 같은 예외를 던지는 상태라, 에러 페이지로 보내면 그 페이지에서 다시 503 이 나 리다이렉트가 반복된다 | |
| if ($exception->getCode() === 503) { | |
| return false; | |
| } | |
| return ($seoData['useFl'] ?? '') == 'y'; | |
| } | |
| } | |
변경 전PgNoti.php
| private $pgClass = ''; | |
| private $orderNo = ''; | |
| private $pgMobileCode = ''; | |
| /** | |
| * 생성자 | |
| $this->orderNo = $requestValue['partner_order_id']; | |
| // 노티 중복 수신 방지 — 중계서버는 나중 응답만 보고 카카오 결제 취소 여부를 판단하므로, | |
| // 락 대기 후 실제 확정된 결과로 응답한다(즉시 낙관적 OK 금지). 대기해도 못 얻으면 안전하게 FAIL. | |
| $lockGuard = new PaymentNotiLockGuard(App::getInstance('DB'), 'kakaopay'); | |
| if ($lockGuard->lock($this->orderNo, self::NOTI_LOCK_WAIT_SECONDS) === false) { | |
| Logger::channel('pgKakaopayResult')->error('Noti Lock Failed :' . $this->pgMobileCode, [$this->orderNo]); | |
| echo '{"result":"FAIL"}'; | |
| exit; | |
| } | |
| register_shutdown_function(function () use ($lockGuard) { | |
| $lockGuard->unlock($this->orderNo); | |
| }); | |
| // 결과 정보 로그 | |
| Logger::channel('pgKakaopayResult')->info('PG Settle Data :' . $this->pgMobileCode, [$this->orderNo . ' : Settle Success']); | |
| // 결제 결과 저장 | |
| $saveResult = $this->pgClass->setPgData($this->orderNo, $getPg, null); | |
| // 결과 DB 처리 | |
| if ($saveResult === true) { | |
| Logger::channel('pgKakaopayResult')->info('Set Pg Data :' . $this->pgMobileCode, ['OK']); | |
| echo '{"result":"OK"}'; | |
| exit; | |
| $errorData = $this->pgClass->setPgResultCode($e->getMessage()); | |
| Logger::channel('pgKakaopayResult')->info('Noti Exception Data :' . $errorData['message'], ['FAIL']); | |
| if ($e->getMessage() == 'PG_STOP_ORDER_DATA') { | |
| Logger::channel('pgKakaopayResult')->info('Stop Pg Data : ' . $errorData['message'], ['FAIL']); | |
| } | |
| } | |
| /** | |
| * 결제 결과 정보 데이터 설정 | |
| * | |
변경 후PgNoti.php
| private $pgClass = ''; | |
| private $orderNo = ''; | |
| private $pgMobileCode = ''; | |
| private bool $accepted = false; | |
| private bool $saved = false; | |
| private ?\Exception $saveException = null; | |
| /** | |
| * 생성자 | |
| $this->orderNo = $requestValue['partner_order_id']; | |
| // 노티 중복 수신 방지 — 중계서버는 나중 응답만 보고 카카오 결제 취소 여부를 판단하므로, | |
| // 락 대기 후 실제 확정된 결과로 응답한다(즉시 낙관적 OK 금지). | |
| $lockGuard = new PaymentNotiLockGuard(App::getInstance('DB'), 'kakaopay'); | |
| if ($lockGuard->lock($this->orderNo, self::NOTI_LOCK_WAIT_SECONDS) === false) { | |
| // 앞선 노티가 검증을 통과해 저장 중이면 FAIL 응답 시 정상 결제가 취소되므로 PAYED로 응답한다 | |
| if ($lockGuard->isAccepted($this->orderNo)) { | |
| Logger::channel('pgKakaopayResult')->warning('Noti Lock Wait Timeout, Accepted :' . $this->pgMobileCode, [$this->orderNo]); | |
| echo '{"result":"PAYED"}'; | |
| exit; | |
| } | |
| // 대기가 끝나는 사이 앞선 처리가 끝났을 수 있어 한 번 더 시도한다 | |
| if ($lockGuard->lock($this->orderNo) === false) { | |
| Logger::channel('pgKakaopayResult')->error('Noti Lock Failed :' . $this->pgMobileCode, [$this->orderNo]); | |
| echo '{"result":"FAIL"}'; | |
| exit; | |
| } | |
| } | |
| register_shutdown_function(function () use ($lockGuard) { | |
| $this->logAcceptedSaveFailed(); | |
| $lockGuard->unlock($this->orderNo); | |
| }); | |
| // 결과 정보 로그 | |
| Logger::channel('pgKakaopayResult')->info('PG Settle Data :' . $this->pgMobileCode, [$this->orderNo . ' : Settle Success']); | |
| // 저장이 늦어져 재시도 노티가 들어와도 결제가 취소되지 않도록 승인 확정을 표시한다 | |
| $this->accepted = $lockGuard->markAccepted($this->orderNo); | |
| if (!$this->accepted) { | |
| Logger::channel('pgKakaopayResult')->warning('Noti Accepted Mark Failed :' . $this->pgMobileCode, [$this->orderNo]); | |
| } | |
| // 결제 결과 저장 | |
| $saveResult = $this->pgClass->setPgData($this->orderNo, $getPg, null); | |
| // 결과 DB 처리 | |
| if ($saveResult === true) { | |
| $this->saved = true; | |
| Logger::channel('pgKakaopayResult')->info('Set Pg Data :' . $this->pgMobileCode, ['OK']); | |
| echo '{"result":"OK"}'; | |
| exit; | |
| $errorData = $this->pgClass->setPgResultCode($e->getMessage()); | |
| Logger::channel('pgKakaopayResult')->info('Noti Exception Data :' . $errorData['message'], ['FAIL']); | |
| $this->saveException = $e; | |
| if ($e->getMessage() == 'PG_STOP_ORDER_DATA') { | |
| Logger::channel('pgKakaopayResult')->info('Stop Pg Data : ' . $errorData['message'], ['FAIL']); | |
| } | |
| } | |
| /** | |
| * 승인 확정 표시 후 저장되지 않고 끝나면(실패 응답·예외·치명 오류) 재시도 노티가 PAYED로 응답해 | |
| * 카카오 결제가 유지됐을 수 있어 대사용으로 남긴다. 종료 시점 한 곳에서 판정한다. | |
| * | |
| * @return void | |
| */ | |
| private function logAcceptedSaveFailed(): void | |
| { | |
| if (!$this->accepted || $this->saved) { | |
| return; | |
| } | |
| $context = ['orderNo' => $this->orderNo]; | |
| if ($this->saveException !== null) { | |
| $context['exception'] = $this->saveException; | |
| $context['errorMessage'] = $this->saveException->getMessage(); | |
| } | |
| Logger::channel('pgKakaopayResult')->error('Noti Accepted But Save Failed :' . $this->pgMobileCode, $context); | |
| } | |
| /** | |
| * 결제 결과 정보 데이터 설정 | |
| * | |
변경 전PgReturn.php
| namespace Bundle\Component\Payment\Kakaopay; | |
| use Request; | |
| use Logger; | |
| use Origin\Traits\Payment\PaymentProcessingSessionTrait; | |
| /** | |
| */ | |
| const KAKAOPAY_PG_DB_ERROR = '99'; | |
| /** | |
| * 생성자 | |
| * | |
| $getPg['pgFailReason'] = $setPayData['retmsg']; | |
| $this->pgClass->setPgErrorData($this->orderNo, $getPg, null); | |
| \Logger::channel('pgKakaopayResult')->info(__METHOD__ . " ORDER NO : {$this->orderNo} ", $setPayData); | |
| } else { | |
| $script .= "location.href='../../order/order_end.php?orderNo=" . $this->orderNo . "';"; | |
| } | |
| <?php | |
| } | |
| /** | |
| * 인증 정보 데이터 설정 | |
| * | |
변경 후PgReturn.php
| namespace Bundle\Component\Payment\Kakaopay; | |
| use Component\Member\Util\MemberUtil; | |
| use Framework\Database\DBManager; | |
| use Request; | |
| use Logger; | |
| use Origin\Enum\Order\OrderStatusCode; | |
| use Origin\Traits\Payment\PaymentProcessingSessionTrait; | |
| /** | |
| */ | |
| const KAKAOPAY_PG_DB_ERROR = '99'; | |
| // 결제 성공 복귀 시 노티의 결제완료 저장을 기다리는 최대 시간(초)과 주문상태 확인 간격(마이크로초) | |
| private int $notiWaitSeconds = 25; | |
| private int $notiPollMicroseconds = 500000; | |
| /** | |
| * 생성자 | |
| * | |
| $getPg['pgFailReason'] = $setPayData['retmsg']; | |
| $this->pgClass->setPgErrorData($this->orderNo, $getPg, null); | |
| \Logger::channel('pgKakaopayResult')->info(__METHOD__ . " ORDER NO : {$this->orderNo} ", $setPayData); | |
| } elseif ($this->isNotiProcessing()) { | |
| // 재시도 노티의 PAYED 응답으로 결제가 유지됐는데 앞선 노티가 아직 저장 중이면, 주문완료 화면은 결제시도 상태라 | |
| // '다시 결제' 안내가 나와 이중결제로 이어질 수 있어 안내 후 주문내역으로 보낸다(비회원은 로그인·비회원 주문조회로 이동) | |
| $script = $this->getOrderListGuideScript($script); | |
| } else { | |
| $script .= "location.href='../../order/order_end.php?orderNo=" . $this->orderNo . "';"; | |
| } | |
| <?php | |
| } | |
| /** | |
| * 결제는 됐는데 주문 확인이 필요한 경우 안내 후 주문내역으로 보내는 스크립트 | |
| * 비회원은 주문내역 대신 로그인 화면으로 이동(PageAccess)해 비회원 주문조회에 쓸 주문번호를 함께 안내한다. | |
| * | |
| * @param string $script 창 위치 접두(opener.parent. 등) | |
| * @return string | |
| */ | |
| private function getOrderListGuideScript(string $script): string | |
| { | |
| if (MemberUtil::isLogin()) { | |
| $message = __('결제는 완료되었으며 주문 정보를 확인하고 있습니다. 잠시 후 주문내역에서 확인해 주세요.'); | |
| } else { | |
| $message = sprintf(__('결제는 완료되었으며 주문 정보를 확인하고 있습니다. 잠시 후 주문내역에서 확인해 주세요. (주문번호: %s)'), $this->orderNo); | |
| } | |
| return 'alert(' . json_encode($message) . ');' . $script . "location.href='../../mypage/order_list.php';"; | |
| } | |
| /** | |
| * 결제 성공으로 돌아왔는데 주문이 아직 결제시도(f1)면 노티가 결제완료를 저장할 때까지 주문상태를 짧은 간격으로 다시 확인한다. | |
| * 노티 락은 메일·SMS 등 후처리까지 끝나야 풀려서, 락 대신 주문상태로 판정해 저장 즉시 빠져나온다. | |
| * | |
| * @return bool true = 최대 대기 후에도 결제시도 상태(또는 확인 실패) | |
| */ | |
| private function isNotiProcessing(): bool | |
| { | |
| try { | |
| $db = \App::getInstance('DB'); | |
| // 분산서버(read replica) 상점에서 복제 지연으로 방금 저장된 결제완료를 놓치지 않도록 primary에서 조회한다 | |
| if (method_exists($db, 'stickyPrimary')) { | |
| $db->stickyPrimary(); | |
| } | |
| $deadline = microtime(true) + $this->notiWaitSeconds; | |
| while ($this->getOrderStatus($db) === OrderStatusCode::PAYMENT_ATTEMPT->value) { | |
| if (microtime(true) >= $deadline) { | |
| return true; | |
| } | |
| usleep($this->notiPollMicroseconds); | |
| } | |
| return false; | |
| } catch (\Throwable $e) { | |
| // 확인할 수 없으면 결제시도로 보고 주문내역 안내로 보낸다(주문완료 화면의 '다시 결제' 안내 방지) | |
| \Logger::channel('pgKakaopayResult')->warning(__METHOD__ . ' 주문상태 확인 실패 : ' . $this->orderNo, ['exception' => $e]); | |
| return true; | |
| } | |
| } | |
| /** | |
| * @param DBManager $db | |
| * @return string | |
| */ | |
| private function getOrderStatus(DBManager $db): string | |
| { | |
| $arrBind = []; | |
| $db->bind_param_push($arrBind, 's', $this->orderNo); | |
| $orderData = $db->query_fetch('SELECT orderStatus FROM ' . DB_ORDER . ' WHERE orderNo = ?', $arrBind, false); | |
| return (string)($orderData['orderStatus'] ?? ''); | |
| } | |
| /** | |
| * 인증 정보 데이터 설정 | |
| * | |
변경 전PaymentNotiLockGuard.php
| * | |
| * 주의: GET_LOCK은 커넥션 단위 스코프라, lock()/unlock()에는 노티 처리에 쓰는 DB 커넥션과 동일한 | |
| * 인스턴스(mysqli 싱글턴, \App::getInstance('DB'))를 넘겨야 한다. 판정 결과만 반환하며 로깅은 호출부 책임이다. | |
| */ | |
| class PaymentNotiLockGuard | |
| { | |
| const LOCK_PREFIX = 'pgNoti:'; | |
| private DBManager $db; | |
| private string $pgName; | |
| /** | |
| * @param DBManager $db 노티 처리에 사용하는 DB 커넥션과 동일한 인스턴스 | |
| { | |
| $this->db = $db; | |
| $this->pgName = $pgName; | |
| } | |
| /** | |
| * @throws DatabaseException | |
| */ | |
| public function unlock(string $orderNo): void | |
| { | |
| $arrBind = []; | |
| $this->db->bind_param_push($arrBind, 's', $this->lockName($orderNo)); | |
| $this->db->query_fetch('SELECT RELEASE_LOCK(?) AS released', $arrBind, false); | |
| } | |
| /** | |
| * @param string $orderNo | |
| * @return string | |
| */ | |
| private function lockName(string $orderNo): string | |
| { | |
| return self::LOCK_PREFIX . $this->pgName . ':' . $orderNo; | |
| } | |
| } | |
변경 후PaymentNotiLockGuard.php
| * | |
| * 주의: GET_LOCK은 커넥션 단위 스코프라, lock()/unlock()에는 노티 처리에 쓰는 DB 커넥션과 동일한 | |
| * 인스턴스(mysqli 싱글턴, \App::getInstance('DB'))를 넘겨야 한다. 판정 결과만 반환하며 로깅은 호출부 책임이다. | |
| * | |
| * 승인 확정 표시(markAccepted/isAccepted): 처리 중인 요청이 주문·금액 검증을 통과했다는 표시를 별도 락으로 남긴다. | |
| * 웹서버가 여러 대여도 같은 DB에서 보이고, 요청이 비정상 종료되면 커넥션과 함께 풀린다. | |
| * | |
| * 락 이름은 상점 단위로 분리한다 — lockName() 참고. | |
| */ | |
| class PaymentNotiLockGuard | |
| { | |
| const LOCK_PREFIX = 'pgNoti:'; | |
| const ACCEPTED_LOCK_PREFIX = 'pgNotiAccepted:'; | |
| private DBManager $db; | |
| private string $pgName; | |
| /** @var string 락 이름에 쓰는 상점 식별자 — lock()/unlock() 이 같은 이름을 쓰도록 생성 시점에 한 번만 읽는다 */ | |
| private string $shopNo; | |
| /** | |
| * @param DBManager $db 노티 처리에 사용하는 DB 커넥션과 동일한 인스턴스 | |
| { | |
| $this->db = $db; | |
| $this->pgName = $pgName; | |
| $this->shopNo = (string)\Globals::get('gLicense.godosno'); | |
| } | |
| /** | |
| * @throws DatabaseException | |
| */ | |
| public function unlock(string $orderNo): void | |
| { | |
| // 주문 락을 먼저 푼다 — 표시를 먼저 풀면 그 사이 대기가 끝난 재시도가 표시 없음·락 점유로 판정해 FAIL 응답할 수 있다 | |
| foreach ([$this->lockName($orderNo), $this->acceptedLockName($orderNo)] as $lockName) { | |
| $arrBind = []; | |
| $this->db->bind_param_push($arrBind, 's', $lockName); | |
| $this->db->query_fetch('SELECT RELEASE_LOCK(?) AS released', $arrBind, false); | |
| } | |
| } | |
| /** | |
| * 주문·금액 검증을 통과해 결제를 확정 처리 중이라는 표시를 남긴다. lock() 획득 후에만 호출한다. | |
| * | |
| * @param string $orderNo | |
| * @return bool | |
| * @throws DatabaseException | |
| */ | |
| public function markAccepted(string $orderNo): bool | |
| { | |
| $arrBind = []; | |
| $this->db->bind_param_push($arrBind, 's', $this->acceptedLockName($orderNo)); | |
| $result = $this->db->query_fetch('SELECT GET_LOCK(?, 0) AS acquired', $arrBind, false); | |
| return !empty($result) && (int)$result['acquired'] === 1; | |
| } | |
| /** | |
| * 다른 요청이 승인 확정 표시를 들고 처리 중인지 확인한다. | |
| * | |
| * @param string $orderNo | |
| * @return bool | |
| * @throws DatabaseException | |
| */ | |
| public function isAccepted(string $orderNo): bool | |
| { | |
| if (method_exists($this->db, 'stickyPrimary')) { | |
| $this->db->stickyPrimary(); | |
| } | |
| $arrBind = []; | |
| $this->db->bind_param_push($arrBind, 's', $this->acceptedLockName($orderNo)); | |
| $result = $this->db->query_fetch('SELECT IS_USED_LOCK(?) AS holder', $arrBind, false); | |
| return !empty($result) && $result['holder'] !== null; | |
| } | |
| /** | |
| * GET_LOCK 이름은 스키마가 아니라 MySQL 인스턴스 전역이라, 여러 상점 DB가 한 서버를 공유하면 | |
| * 주문번호만으로는 다른 상점의 같은 주문번호와 겹친다(주문번호에 상점 식별자 없음). 예치금 표준 | |
| * 락(SimpleCache Redis executeWithLock)과 동일하게 상점 식별자(godosno)를 이름에 포함한다. | |
| * | |
| * @param string $orderNo | |
| * @return string | |
| */ | |
| private function lockName(string $orderNo): string | |
| { | |
| return self::LOCK_PREFIX . $this->shopNo . ':' . $this->pgName . ':' . $orderNo; | |
| } | |
| /** | |
| * @param string $orderNo | |
| * @return string | |
| */ | |
| private function acceptedLockName(string $orderNo): string | |
| { | |
| return self::ACCEPTED_LOCK_PREFIX . $this->shopNo . ':' . $this->pgName . ':' . $orderNo; | |
| } | |
| } | |
변경 전KakaopayConfig.php
| */ | |
| class KakaopayConfig | |
| { | |
| public $kakaopayApiDomain = ''; | |
| public $kakaopayReadyUrl = ''; | |
| public $kakaopayShopDomain = ''; | |
| // kakaopay 결제 취소 url | |
| $this->kakaopayCancelUrl = $this->kakaopayApiDomain . '/api/KakaoCancel'; | |
| // kakaopay 결과 노티 url | |
| $this->kakaopayNotiUrl = $this->kakaopayPaymentDomain . DS . 'pg_noti.php'; | |
| // kakaopay 결과 회신 url | |
| $this->kakaopayReturnUrl = $this->kakaopayPaymentDomain . DS . 'pg_return.php'; | |
변경 후KakaopayConfig.php
| */ | |
| class KakaopayConfig | |
| { | |
| // 노티 url 표식 — 이 표식이 있는 주문만 중계서버가 결제 취소 직전 확인(PgNoti mode=cancel)을 보낸다 | |
| const RELAY_CANCEL_CHECK_QUERY = 'relayCancelCheck=1'; | |
| public $kakaopayApiDomain = ''; | |
| public $kakaopayReadyUrl = ''; | |
| public $kakaopayShopDomain = ''; | |
| // kakaopay 결제 취소 url | |
| $this->kakaopayCancelUrl = $this->kakaopayApiDomain . '/api/KakaoCancel'; | |
| // kakaopay 결과 노티 url — 중계서버는 이 표식이 있을 때만 결제 취소 전 확인을 보낸다(구버전 쇼핑몰은 기존 동작 유지) | |
| $this->kakaopayNotiUrl = $this->kakaopayPaymentDomain . DS . 'pg_noti.php?' . self::RELAY_CANCEL_CHECK_QUERY; | |
| // kakaopay 결과 회신 url | |
| $this->kakaopayReturnUrl = $this->kakaopayPaymentDomain . DS . 'pg_return.php'; | |
변경 전NotiCancelReservation.php
변경 후NotiCancelReservation.php
| <?php | |
| /* | |
| * Copyright (C) 2026 NHN COMMERCE. - All Rights Reserved | |
| * | |
| * Unauthorized copying or redistribution of this file in source and binary forms via any medium | |
| * is strictly prohibited. | |
| */ | |
| namespace Bundle\Component\Payment\Kakaopay; | |
| use Bundle\Component\Order\OrderAdmin; | |
| use Bundle\Component\Payment\PaymentNotiLockGuard; | |
| use Framework\Database\DBManager; | |
| use Framework\Debug\Exception\DatabaseException; | |
| use Logger; | |
| use Origin\Enum\Order\OrderStatusCode; | |
| use Origin\Enum\Order\OrderStatusGroup; | |
| /** | |
| * 카카오페이 중계서버(commerce-relay-kakaopay)가 결제를 취소하기 직전에 쇼핑몰과 결과를 확정하는 취소 예약. | |
| * | |
| * 중계서버는 노티 응답이 정상(OK/PAYED)이 아니면 결제를 취소한다. 취소 후에 알리면 그사이 저장 중인 노티가 | |
| * 결제완료로 덮어쓰므로, 취소 전에 승인 확정 표시(PaymentNotiLockGuard::markAccepted)를 대기 없이 잡아 | |
| * 노티의 확정과 상호배제한다. 표시를 잡으면 결제시도 주문을 결제실패로 바꾸고(취소 예약), 못 잡으면 노티가 | |
| * 이미 확정해 저장 중이므로 결제를 유지시킨다. 노티는 확정 표시 후 isPaymentAttempt()로 예약 여부를 다시 확인한다. | |
| */ | |
| class NotiCancelReservation | |
| { | |
| const RESULT_PAYED = 'PAYED'; | |
| const RESULT_CANCEL = 'CANCEL'; | |
| // 암호화 노티 데이터를 다시 보내 결제시도 주문을 실패로 바꾸지 못하도록 승인 직후 요청만 받는다 | |
| const REQUEST_VALID_SECONDS = 600; | |
| private const RESERVE_REASON = '중계서버 결제 취소로 인해'; | |
| // 카카오페이 결제수단 코드 — 다른 결제수단의 결제시도 주문은 취소 예약하지 않는다 | |
| private const SETTLE_KIND_KAKAOPAY = 'pk'; | |
| private DBManager $db; | |
| private PaymentNotiLockGuard $lockGuard; | |
| /** | |
| * @param DBManager $db 노티 처리에 사용하는 DB 커넥션과 동일한 인스턴스 | |
| * @param PaymentNotiLockGuard $lockGuard | |
| */ | |
| public function __construct(DBManager $db, PaymentNotiLockGuard $lockGuard) | |
| { | |
| $this->db = $db; | |
| $this->lockGuard = $lockGuard; | |
| } | |
| /** | |
| * @param string $orderNo | |
| * @param OrderAdmin $orderAdmin 결제실패 상태 변경(복귀 결제실패 처리와 동일 경로) | |
| * @return string RESULT_PAYED = 결제 유지, RESULT_CANCEL = 취소 진행 | |
| * @throws DatabaseException | |
| */ | |
| public function reserve(string $orderNo, OrderAdmin $orderAdmin): string | |
| { | |
| if (!$this->lockGuard->markAccepted($orderNo)) { | |
| return self::RESULT_PAYED; | |
| } | |
| try { | |
| $orderData = $this->getOrderData($orderNo); | |
| $orderStatus = (string)($orderData['orderStatus'] ?? ''); | |
| // 노티가 확정 표시를 풀기 전에 결제완료 저장까지 끝낸 경우 | |
| if ($orderStatus !== '' && substr($orderStatus, 0, 1) !== OrderStatusGroup::FAIL->value) { | |
| return self::RESULT_PAYED; | |
| } | |
| if ($orderStatus !== OrderStatusCode::PAYMENT_ATTEMPT->value) { | |
| return self::RESULT_CANCEL; | |
| } | |
| // 카카오페이 주문이 아니면 이 결제와 맞지 않는 주문이므로 건드리지 않고 결제만 취소되게 한다 | |
| if (($orderData['settleKind'] ?? '') !== self::SETTLE_KIND_KAKAOPAY) { | |
| Logger::channel('pgKakaopayResult')->warning(__METHOD__ . ' 카카오페이 주문 아님, 취소 예약 생략', ['orderNo' => $orderNo, 'settleKind' => $orderData['settleKind'] ?? '']); | |
| return self::RESULT_CANCEL; | |
| } | |
| // 상태변경이 화면용 스크립트 등을 출력해도 중계서버 응답 JSON 과 섞이지 않게 버린다 | |
| ob_start(); | |
| try { | |
| $orderAdmin->updateStatusPreprocess( | |
| $orderNo, | |
| $orderAdmin->getOrderGoods($orderNo), | |
| OrderStatusGroup::FAIL->value, | |
| OrderStatusCode::PAYMENT_FAILED->value, | |
| self::RESERVE_REASON, | |
| true | |
| ); | |
| } finally { | |
| ob_end_clean(); | |
| } | |
| return self::RESULT_CANCEL; | |
| } finally { | |
| $this->lockGuard->releaseAccepted($orderNo); | |
| } | |
| } | |
| /** | |
| * 노티가 확정 표시를 남긴 뒤 저장 직전에 호출한다 — 취소 예약됐으면 false. | |
| * | |
| * @param string $orderNo | |
| * @return bool | |
| * @throws DatabaseException | |
| */ | |
| public function isPaymentAttempt(string $orderNo): bool | |
| { | |
| return ($this->getOrderData($orderNo)['orderStatus'] ?? '') === OrderStatusCode::PAYMENT_ATTEMPT->value; | |
| } | |
| /** | |
| * @param string $approvedAt 카카오 승인 시각(Y-m-d H:i:s) | |
| * @return bool | |
| */ | |
| public function isFreshApproval(string $approvedAt): bool | |
| { | |
| $approvedTime = strtotime($approvedAt); | |
| if ($approvedTime === false) { | |
| return false; | |
| } | |
| return abs(time() - $approvedTime) <= self::REQUEST_VALID_SECONDS; | |
| } | |
| /** | |
| * 분산서버(read replica) 상점에서 복제 지연으로 방금 바뀐 상태를 놓치지 않도록 primary에서 조회한다. | |
| * | |
| * @param string $orderNo | |
| * @return array orderStatus·settleKind (주문이 없으면 빈 배열) | |
| * @throws DatabaseException | |
| */ | |
| private function getOrderData(string $orderNo): array | |
| { | |
| if (method_exists($this->db, 'stickyPrimary')) { | |
| $this->db->stickyPrimary(); | |
| } | |
| $arrBind = []; | |
| $this->db->bind_param_push($arrBind, 's', $orderNo); | |
| $orderData = $this->db->query_fetch('SELECT orderStatus, settleKind FROM ' . DB_ORDER . ' WHERE orderNo = ?', $arrBind, false); | |
| return is_array($orderData) ? $orderData : []; | |
| } | |
| } | |
변경 전PgNoti.php
| namespace Bundle\Component\Payment\Kakaopay; | |
| use App; | |
| use Component\Payment\PaymentNotiLockGuard; | |
| use Globals; | |
| use Request; | |
| { | |
| // 중계서버가 1차 노티를 10초 만에 포기하고 재시도하므로, 뒤에 온 노티는 앞선 처리가 끝날 때까지 대기한다. | |
| private const NOTI_LOCK_WAIT_SECONDS = 20; | |
| private $pgConfig = ''; | |
| private $pgSetting = ''; | |
| // 주문번호 | |
| $this->orderNo = $requestValue['partner_order_id']; | |
| // 노티 중복 수신 방지 — 중계서버는 나중 응답만 보고 카카오 결제 취소 여부를 판단하므로, | |
| // 락 대기 후 실제 확정된 결과로 응답한다(즉시 낙관적 OK 금지). | |
| $lockGuard = new PaymentNotiLockGuard(App::getInstance('DB'), 'kakaopay'); | |
| if ($lockGuard->lock($this->orderNo, self::NOTI_LOCK_WAIT_SECONDS) === false) { | |
| // 앞선 노티가 검증을 통과해 저장 중이면 FAIL 응답 시 정상 결제가 취소되므로 PAYED로 응답한다 | |
| if ($lockGuard->isAccepted($this->orderNo)) { | |
| Logger::channel('pgKakaopayResult')->warning('Noti Lock Wait Timeout, Accepted :' . $this->pgMobileCode, [$this->orderNo]); | |
| exit; | |
| } | |
| // 대기가 끝나는 사이 앞선 처리가 끝났을 수 있어 한 번 더 시도한다 | |
| if ($lockGuard->lock($this->orderNo) === false) { | |
| Logger::channel('pgKakaopayResult')->error('Noti Lock Failed :' . $this->pgMobileCode, [$this->orderNo]); | |
| echo '{"result":"FAIL"}'; | |
| exit; | |
| } | |
| } | |
| Logger::channel('pgKakaopayResult')->info('PG Settle Data :' . $this->pgMobileCode, [$this->orderNo . ' : Settle Success']); | |
| // 저장이 늦어져 재시도 노티가 들어와도 결제가 취소되지 않도록 승인 확정을 표시한다 | |
| $this->accepted = $lockGuard->markAccepted($this->orderNo); | |
| if (!$this->accepted) { | |
| Logger::channel('pgKakaopayResult')->warning('Noti Accepted Mark Failed :' . $this->pgMobileCode, [$this->orderNo]); | |
| } | |
| // 결제 결과 저장 | |
| } | |
| } | |
| /** | |
| * 승인 확정 표시 후 저장되지 않고 끝나면(실패 응답·예외·치명 오류) 재시도 노티가 PAYED로 응답해 | |
| * 카카오 결제가 유지됐을 수 있어 대사용으로 남긴다. 종료 시점 한 곳에서 판정한다. | |
변경 후PgNoti.php
| namespace Bundle\Component\Payment\Kakaopay; | |
| use App; | |
| use Component\Payment\Kakaopay\NotiCancelReservation; | |
| use Component\Payment\PaymentNotiLockGuard; | |
| use Globals; | |
| use Request; | |
| { | |
| // 중계서버가 1차 노티를 10초 만에 포기하고 재시도하므로, 뒤에 온 노티는 앞선 처리가 끝날 때까지 대기한다. | |
| private const NOTI_LOCK_WAIT_SECONDS = 20; | |
| // 중계서버 취소 직전 확인이 결제실패 기록을 마칠 때까지 기다린다(그 전에 상태를 읽으면 결제시도로 보여 저장이 진행됨) | |
| private const ACCEPT_WAIT_SECONDS = 10; | |
| // 중계서버가 노티 응답을 확정하지 못했을 때 결제를 취소하기 직전에 보내는 확인 요청(암호화 data 안의 mode) | |
| private const RELAY_MODE_CANCEL = 'cancel'; | |
| private $pgConfig = ''; | |
| private $pgSetting = ''; | |
| // 주문번호 | |
| $this->orderNo = $requestValue['partner_order_id']; | |
| $lockGuard = new PaymentNotiLockGuard(App::getInstance('DB'), 'kakaopay'); | |
| $cancelReservation = new NotiCancelReservation(App::getInstance('DB'), $lockGuard); | |
| // 중계서버가 결제를 취소하기 직전 확인 — 노티의 승인 확정과 상호배제해 취소 예약 또는 결제 유지로 응답한다 | |
| if (is_scalar($requestValue['mode'] ?? null) && (string)$requestValue['mode'] === self::RELAY_MODE_CANCEL) { | |
| $approvedAt = $requestValue['approved_at'] ?? ''; | |
| $this->replyCancelReservation($cancelReservation, is_scalar($approvedAt) ? (string)$approvedAt : ''); | |
| } | |
| // 노티 중복 수신 방지 — 중계서버는 나중 응답만 보고 카카오 결제 취소 여부를 판단하므로, | |
| // 락 대기 후 실제 확정된 결과로 응답한다(즉시 낙관적 OK 금지). | |
| if (!$lockGuard->lock($this->orderNo, self::NOTI_LOCK_WAIT_SECONDS)) { | |
| // 앞선 노티가 검증을 통과해 저장 중이면 FAIL 응답 시 정상 결제가 취소되므로 PAYED로 응답한다 | |
| if ($lockGuard->isAccepted($this->orderNo)) { | |
| Logger::channel('pgKakaopayResult')->warning('Noti Lock Wait Timeout, Accepted :' . $this->pgMobileCode, [$this->orderNo]); | |
| exit; | |
| } | |
| // 대기가 끝나는 사이 앞선 처리가 끝났을 수 있어 한 번 더 시도한다 | |
| // 그래도 처리 중이면 결과를 모르므로 WAIT로 응답해 중계서버가 취소 전 확인을 거치게 한다(구버전 중계서버는 실패로 봄) | |
| if (!$lockGuard->lock($this->orderNo)) { | |
| Logger::channel('pgKakaopayResult')->error('Noti Lock Failed :' . $this->pgMobileCode, [$this->orderNo]); | |
| echo '{"result":"WAIT"}'; | |
| exit; | |
| } | |
| } | |
| Logger::channel('pgKakaopayResult')->info('PG Settle Data :' . $this->pgMobileCode, [$this->orderNo . ' : Settle Success']); | |
| // 저장이 늦어져 재시도 노티가 들어와도 결제가 취소되지 않도록 승인 확정을 표시한다 | |
| $this->accepted = $lockGuard->markAccepted($this->orderNo, self::ACCEPT_WAIT_SECONDS); | |
| // 확정 표시를 못 잡으면 취소 직전 확인과 상호배제가 깨지므로 저장하지 않고 결과 미확정으로 응답한다 | |
| if (!$this->accepted) { | |
| Logger::channel('pgKakaopayResult')->warning('Noti Accepted Mark Failed :' . $this->pgMobileCode, [$this->orderNo]); | |
| $this->pgClass->failDoRollbackQueryPG(); | |
| echo '{"result":"WAIT"}'; | |
| exit; | |
| } | |
| // 중계서버가 취소 직전 확인에서 결제실패로 예약했으면 카카오 결제가 취소되므로 결제완료로 저장하지 않는다 | |
| if (!$cancelReservation->isPaymentAttempt($this->orderNo)) { | |
| $this->accepted = false; | |
| Logger::channel('pgKakaopayResult')->warning('Noti Cancel Reserved, Skip Save :' . $this->pgMobileCode, [$this->orderNo]); | |
| throw new Exception('PG_STOP_ORDER_DATA'); | |
| } | |
| // 결제 결과 저장 | |
| } | |
| } | |
| /** | |
| * 중계서버 취소 직전 확인에 응답하고 종료한다. | |
| * | |
| * @param NotiCancelReservation $cancelReservation | |
| * @param string $approvedAt | |
| * @return void | |
| */ | |
| private function replyCancelReservation(NotiCancelReservation $cancelReservation, string $approvedAt): void | |
| { | |
| // 예약하지 못하면 결과를 모르는 것이므로 WAIT로 응답해 중계서버가 취소하지 않고 결제 확인 필요로 처리하게 한다 | |
| if (!$cancelReservation->isFreshApproval($approvedAt)) { | |
| Logger::channel('pgKakaopayResult')->warning('Relay Cancel Check Expired :' . $this->pgMobileCode, [$this->orderNo, $approvedAt]); | |
| echo '{"result":"WAIT"}'; | |
| exit; | |
| } | |
| try { | |
| $result = $cancelReservation->reserve($this->orderNo, App::load('\\Component\\Order\\OrderAdmin')); | |
| } catch (\Throwable $e) { | |
| Logger::channel('pgKakaopayResult')->error('Relay Cancel Reserve Failed :' . $this->pgMobileCode, ['orderNo' => $this->orderNo, 'exception' => $e, 'errorMessage' => $e->getMessage()]); | |
| echo '{"result":"WAIT"}'; | |
| exit; | |
| } | |
| Logger::channel('pgKakaopayResult')->info('Relay Cancel Check :' . $this->pgMobileCode, [$this->orderNo, $result]); | |
| echo '{"result":"' . $result . '"}'; | |
| exit; | |
| } | |
| /** | |
| * 승인 확정 표시 후 저장되지 않고 끝나면(실패 응답·예외·치명 오류) 재시도 노티가 PAYED로 응답해 | |
| * 카카오 결제가 유지됐을 수 있어 대사용으로 남긴다. 종료 시점 한 곳에서 판정한다. | |
변경 전PgReturn.php
| use Request; | |
| use Logger; | |
| use Origin\Enum\Order\OrderStatusCode; | |
| use Origin\Traits\Payment\PaymentProcessingSessionTrait; | |
| /** | |
| */ | |
| const KAKAOPAY_PG_DB_ERROR = '99'; | |
| // 결제 성공 복귀 시 노티의 결제완료 저장을 기다리는 최대 시간(초)과 주문상태 확인 간격(마이크로초) | |
| private int $notiWaitSeconds = 25; | |
| private int $notiPollMicroseconds = 500000; | |
| /** | |
| * 생성자 | |
| // 인증 처리 체크 | |
| if (empty($setPayData['retcode']) === true || $this->orderNo == '') { | |
| $script .= "location.href='../../order/order_end.php?orderNo='"; | |
| } elseif ($setPayData['retcode'] != '0') { | |
| // 카카오페이 결제 실패 | |
| $script .= "location.href='../../order/order_end.php?orderNo=" . $this->orderNo . "&mode="; | |
| return 'alert(' . json_encode($message) . ');' . $script . "location.href='../../mypage/order_list.php';"; | |
| } | |
| /** | |
| * 결제 성공으로 돌아왔는데 주문이 아직 결제시도(f1)면 노티가 결제완료를 저장할 때까지 주문상태를 짧은 간격으로 다시 확인한다. | |
| * 노티 락은 메일·SMS 등 후처리까지 끝나야 풀려서, 락 대신 주문상태로 판정해 저장 즉시 빠져나온다. | |
| * | |
| * @return bool true = 최대 대기 후에도 결제시도 상태(또는 확인 실패) | |
| */ | |
| private function isNotiProcessing(): bool | |
| { | |
| try { | |
| $db = \App::getInstance('DB'); | |
| $db->stickyPrimary(); | |
| } | |
| $deadline = microtime(true) + $this->notiWaitSeconds; | |
| while ($this->getOrderStatus($db) === OrderStatusCode::PAYMENT_ATTEMPT->value) { | |
| if (microtime(true) >= $deadline) { | |
| return true; | |
변경 후PgReturn.php
| use Request; | |
| use Logger; | |
| use Origin\Enum\Order\OrderStatusCode; | |
| use Origin\Enum\Order\OrderStatusGroup; | |
| use Origin\Traits\Payment\PaymentProcessingSessionTrait; | |
| /** | |
| */ | |
| const KAKAOPAY_PG_DB_ERROR = '99'; | |
| /** | |
| * 중계서버가 결제 결과를 확정하지 못해 카카오 결제를 유지함 (쇼핑몰 응답 지연·결제 취소 실패·결제창 재진입) | |
| */ | |
| const KAKAOPAY_PG_CONFIRM_REQUIRED = '98'; | |
| // 결제 성공 복귀 시 노티의 결제완료 저장을 기다리는 최대 시간(초)과 주문상태 확인 간격(마이크로초) | |
| private int $notiWaitSeconds = 25; | |
| private int $notiPollMicroseconds = 500000; | |
| // 결제 확인 필요(98) 복귀는 고객이 이미 오래 기다린 뒤라 노티 저장을 짧게만 기다린다 | |
| private int $confirmRequiredWaitSeconds = 10; | |
| /** | |
| * 생성자 | |
| // 인증 처리 체크 | |
| if (empty($setPayData['retcode']) === true || $this->orderNo == '') { | |
| $script .= "location.href='../../order/order_end.php?orderNo='"; | |
| } elseif ($setPayData['retcode'] === self::KAKAOPAY_PG_CONFIRM_REQUIRED) { | |
| // 카카오 결제는 유지됐으므로 결제실패로 바꾸지 않는다. 노티가 저장을 끝내는 중일 수 있어 잠시 기다린 뒤 | |
| // 결제완료면 주문완료로, 아니면 사유를 남기고 주문내역 안내로 보낸다(대사 대상) | |
| if (!$this->isNotiProcessing($this->confirmRequiredWaitSeconds) && $this->isPaid()) { | |
| $script .= "location.href='../../order/order_end.php?orderNo=" . $this->orderNo . "';"; | |
| } else { | |
| \Logger::channel('pgKakaopayResult')->error(__METHOD__ . ' Relay Confirm Required : ' . $this->orderNo, $setPayData); | |
| $getPg['pgFailReason'] = is_scalar($setPayData['retmsg'] ?? null) ? (string)$setPayData['retmsg'] : ''; | |
| $this->pgClass->setPgErrorData($this->orderNo, $getPg, null); | |
| $script = $this->getOrderListGuideScript($script); | |
| } | |
| } elseif ($setPayData['retcode'] != '0') { | |
| // 카카오페이 결제 실패 | |
| $script .= "location.href='../../order/order_end.php?orderNo=" . $this->orderNo . "&mode="; | |
| return 'alert(' . json_encode($message) . ');' . $script . "location.href='../../mypage/order_list.php';"; | |
| } | |
| /** | |
| * 노티가 결제완료를 이미 저장했는지 primary에서 확인한다. 확인할 수 없으면 false(주문내역 안내로 보냄). | |
| * | |
| * @return bool | |
| */ | |
| private function isPaid(): bool | |
| { | |
| try { | |
| $db = \App::getInstance('DB'); | |
| if (method_exists($db, 'stickyPrimary')) { | |
| $db->stickyPrimary(); | |
| } | |
| $orderStatus = $this->getOrderStatus($db); | |
| } catch (\Throwable $e) { | |
| \Logger::channel('pgKakaopayResult')->warning(__METHOD__ . ' 주문상태 확인 실패 : ' . $this->orderNo, ['exception' => $e, 'errorMessage' => $e->getMessage()]); | |
| return false; | |
| } | |
| return $orderStatus !== '' && substr($orderStatus, 0, 1) !== OrderStatusGroup::FAIL->value; | |
| } | |
| /** | |
| * 결제 성공으로 돌아왔는데 주문이 아직 결제시도(f1)면 노티가 결제완료를 저장할 때까지 주문상태를 짧은 간격으로 다시 확인한다. | |
| * 노티 락은 메일·SMS 등 후처리까지 끝나야 풀려서, 락 대신 주문상태로 판정해 저장 즉시 빠져나온다. | |
| * | |
| * @param int|null $waitSeconds 최대 대기 시간(초), null 이면 기본값(notiWaitSeconds) | |
| * @return bool true = 최대 대기 후에도 결제시도 상태(또는 확인 실패) | |
| */ | |
| private function isNotiProcessing(?int $waitSeconds = null): bool | |
| { | |
| try { | |
| $db = \App::getInstance('DB'); | |
| $db->stickyPrimary(); | |
| } | |
| $deadline = microtime(true) + ($waitSeconds ?? $this->notiWaitSeconds); | |
| while ($this->getOrderStatus($db) === OrderStatusCode::PAYMENT_ATTEMPT->value) { | |
| if (microtime(true) >= $deadline) { | |
| return true; | |
변경 전PaymentNotiLockGuard.php
| } | |
| /** | |
| * 주문·금액 검증을 통과해 결제를 확정 처리 중이라는 표시를 남긴다. lock() 획득 후에만 호출한다. | |
| * | |
| * @param string $orderNo | |
| * @return bool | |
| * @throws DatabaseException | |
| */ | |
| public function markAccepted(string $orderNo): bool | |
| { | |
| $arrBind = []; | |
| $this->db->bind_param_push($arrBind, 's', $this->acceptedLockName($orderNo)); | |
| $result = $this->db->query_fetch('SELECT GET_LOCK(?, 0) AS acquired', $arrBind, false); | |
| return !empty($result) && (int)$result['acquired'] === 1; | |
| } | |
| /** | |
| * 다른 요청이 승인 확정 표시를 들고 처리 중인지 확인한다. | |
| * | |
변경 후PaymentNotiLockGuard.php
| } | |
| /** | |
| * 주문·금액 검증을 통과해 결제를 확정 처리 중이라는 표시를 남긴다. | |
| * 노티는 lock() 획득 후 호출하고, 중계서버 취소 직전 확인은 노티의 확정과 상호배제하려고 대기 없이 호출한다. | |
| * | |
| * @param string $orderNo | |
| * @param int $waitSeconds GET_LOCK 대기 시간(초). 0이면 즉시 실패. | |
| * @return bool | |
| * @throws DatabaseException | |
| */ | |
| public function markAccepted(string $orderNo, int $waitSeconds = 0): bool | |
| { | |
| // 중계서버 취소 직전 확인은 lock()을 거치지 않으므로 여기서도 primary에 고정한다(복제 DB에 표시가 잡히면 상호배제가 깨짐) | |
| if (method_exists($this->db, 'stickyPrimary')) { | |
| $this->db->stickyPrimary(); | |
| } | |
| $arrBind = []; | |
| $this->db->bind_param_push($arrBind, 's', $this->acceptedLockName($orderNo)); | |
| $this->db->bind_param_push($arrBind, 'i', $waitSeconds); | |
| $result = $this->db->query_fetch('SELECT GET_LOCK(?, ?) AS acquired', $arrBind, false); | |
| return !empty($result) && (int)$result['acquired'] === 1; | |
| } | |
| /** | |
| * markAccepted()로 잡은 승인 확정 표시만 해제한다(주문 락을 잡지 않은 중계서버 취소 직전 확인용). | |
| * | |
| * @param string $orderNo | |
| * @return void | |
| * @throws DatabaseException | |
| */ | |
| public function releaseAccepted(string $orderNo): void | |
| { | |
| $arrBind = []; | |
| $this->db->bind_param_push($arrBind, 's', $this->acceptedLockName($orderNo)); | |
| $this->db->query_fetch('SELECT RELEASE_LOCK(?) AS released', $arrBind, false); | |
| } | |
| /** | |
| * 다른 요청이 승인 확정 표시를 들고 처리 중인지 확인한다. | |
| * | |
변경 전frame_cash_receipt_register.php
| </tr> | |
| <tr> | |
| <th>신청자명</th> | |
| <td class="form-inline"><?php echo $orderData['orderName'];?></td> | |
| </tr> | |
| <tr> | |
| <th>상품명</th> | |
변경 후frame_cash_receipt_register.php
| </tr> | |
| <tr> | |
| <th>신청자명</th> | |
| <td class="form-inline"><?= $orderMaskLabel ?: $orderData['orderName'] ?></td> | |
| </tr> | |
| <tr> | |
| <th>상품명</th> | |
변경 전frame_cash_receipt_view.php
| </tr> | |
| <tr> | |
| <th>신청자명</th> | |
| <td><?php echo $data['requestNm'];?></td> | |
| <th>발급방법</th> | |
| <td> | |
| <?php | |
| </tr> | |
| <tr> | |
| <th>휴대폰 번호</th> | |
| <td class="font-num"><?php echo $data['requestCellPhone'];?></td> | |
| <th>이메일</th> | |
| <td><?php echo $data['requestEmail'];?></td> | |
| </tr> | |
| <tr> | |
| <th>상품명</th> | |
| </tr> | |
| <tr> | |
| <th>인증 번호</th> | |
| <td class="font-num" colspan="3"><?php echo $certNo . ' (' . $arrCertFl[$data['certFl']] . ')'; ?></td> | |
| </tr> | |
| </table> | |
| <?php if ($data['issueMode'] == 'a' && empty($data['adminMemo']) === false) { ?> | |
변경 후frame_cash_receipt_view.php
| </tr> | |
| <tr> | |
| <th>신청자명</th> | |
| <td><?= $data['requestNm']; ?></td> | |
| <th>발급방법</th> | |
| <td> | |
| <?php | |
| </tr> | |
| <tr> | |
| <th>휴대폰 번호</th> | |
| <td class="font-num"><?= $data['requestCellPhone']; ?></td> | |
| <th>이메일</th> | |
| <td><?= $data['requestEmail']; ?></td> | |
| </tr> | |
| <tr> | |
| <th>상품명</th> | |
| </tr> | |
| <tr> | |
| <th>인증 번호</th> | |
| <td class="font-num" colspan="3"><?= $displayCertNo; ?></td> | |
| </tr> | |
| </table> | |
| <?php if ($data['issueMode'] == 'a' && empty($data['adminMemo']) === false) { ?> | |
변경 전inc_claim_view.php
| <td <?= $orderAddGoodsRowSpan; ?> class="text-center nowrap"> | |
| <div class="toggleRefundBank"> | |
| <span class="off"> | |
| <?= $withdrawnMembersRefundData['refundBankName'] ?: $val['refundBankName']; ?> | |
| <?= $withdrawnMembersRefundData['refundAccountNumber'] ?: $val['refundAccountNumber']; ?> | |
| <?= $withdrawnMembersRefundData['refundDepositor'] ?: $val['refundDepositor']; ?> | |
| </span> | |
| <span class="on form-inline" style="display:none;"> | |
| <?= gd_select_box('claimRefundBankName', 'claim[refundBankName][' . $val['handleSno'] . ']', $bankNm, null, $val['refundBankName'], '= 은행 선택 =',$claimElementDisabled); ?> | |
| <?php if ($data['statusMode'] !== 'c') { ?> | |
| <td <?= $orderAddGoodsRowSpan; ?> class="text-center"> | |
| <?php if ($val['handleCompleteFl'] === 'n') { ?> | |
| <button type="button" class="btn btn-sm btn-gray js-claim-modify js-claim-act-modify">수정</button> | |
| <button type="button" class="btn btn-sm btn-gray js-claim-modify js-claim-act-complete display-none">완료</button> | |
| <?php } ?> | |
| </td> | |
변경 후inc_claim_view.php
| <td <?= $orderAddGoodsRowSpan; ?> class="text-center nowrap"> | |
| <div class="toggleRefundBank"> | |
| <span class="off"> | |
| <?php if (!empty($isRefundMaskTarget)) { echo $maskChar; } else { ?> | |
| <?= $withdrawnMembersRefundData['refundBankName'] ?: $val['refundBankName']; ?> | |
| <?= $withdrawnMembersRefundData['refundAccountNumber'] ?: $val['refundAccountNumber']; ?> | |
| <?= $withdrawnMembersRefundData['refundDepositor'] ?: $val['refundDepositor']; ?> | |
| <?php } ?> | |
| </span> | |
| <span class="on form-inline" style="display:none;"> | |
| <?= gd_select_box('claimRefundBankName', 'claim[refundBankName][' . $val['handleSno'] . ']', $bankNm, null, $val['refundBankName'], '= 은행 선택 =',$claimElementDisabled); ?> | |
| <?php if ($data['statusMode'] !== 'c') { ?> | |
| <td <?= $orderAddGoodsRowSpan; ?> class="text-center"> | |
| <?php if ($val['handleCompleteFl'] === 'n') { ?> | |
| <button type="button" class="btn btn-sm btn-gray js-claim-modify js-claim-act-modify" <?= !empty($isRefundMaskTarget) ? 'disabled' : '' ?>>수정</button> | |
| <button type="button" class="btn btn-sm btn-gray js-claim-modify js-claim-act-complete display-none">완료</button> | |
| <?php } ?> | |
| </td> | |
변경 전layer_refund_view.php
| <td> | |
| <?= $handleData['handleDt'] ?> | |
| </td> | |
| <td><?= $handleData['refundBankName'] ?><br><?= $handleData['refundAccountNumber'] ?><br><?= $handleData['refundDepositor'] ?></td> | |
| <td><?= gd_select_box(null, 'handleReason', $refundReason, null, $handleData['handleReason'], null); ?></td> | |
| </tr> | |
| <?php } ?> | |
변경 후layer_refund_view.php
| <td> | |
| <?= $handleData['handleDt'] ?> | |
| </td> | |
| <td><?php if (!empty($isRefundMaskTarget)) { echo $maskChar; } else { ?><?= $handleData['refundBankName'] ?><br><?= $handleData['refundAccountNumber'] ?><br><?= $handleData['refundDepositor'] ?><?php } ?></td> | |
| <td><?= gd_select_box(null, 'handleReason', $refundReason, null, $handleData['handleReason'], null); ?></td> | |
| </tr> | |
| <?php } ?> | |
변경 전layer_regular_order_shipping_address.php
| <td><input type="radio" name="shippingSno" value="<?=$info['sno']?>"></td> | |
| <td><?php if ($info['defaultFl'] == 'y'): ?> (기본배송지) <br><?php endif;?><?=$info['shippingTitle']?></td> | |
| <td><?=$info['shippingName']?></td> | |
| <td><?=$info['shippingZonecode']?> <?=$info['shippingAddress']?> <?=$info['shippingAddressSub']?></td> | |
| <td> 전화번호 : <?=$info['shippingPhone']?> <br/> 휴대폰 : <?=$info['shippingCellPhone']?></td> | |
| <td><?=$info['shippingMessage']?></td> | |
| </tr> | |
변경 후layer_regular_order_shipping_address.php
| <td><input type="radio" name="shippingSno" value="<?=$info['sno']?>"></td> | |
| <td><?php if ($info['defaultFl'] == 'y'): ?> (기본배송지) <br><?php endif;?><?=$info['shippingTitle']?></td> | |
| <td><?=$info['shippingName']?></td> | |
| <?php /* 주소 구성요소가 각각 '-' 로 치환돼 하이픈이 반복되므로 칸 전체를 단일 '-' 로 표시 */ ?> | |
| <?php if (!empty($shippingMaskLabel)) { ?> | |
| <td><?= $maskChar ?></td> | |
| <?php } else { ?> | |
| <td><?=$info['shippingZonecode']?> <?=$info['shippingAddress']?> <?=$info['shippingAddressSub']?></td> | |
| <?php } ?> | |
| <td> 전화번호 : <?=$info['shippingPhone']?> <br/> 휴대폰 : <?=$info['shippingCellPhone']?></td> | |
| <td><?=$info['shippingMessage']?></td> | |
| </tr> | |
변경 전layout_order_goods_list.php
| foreach ($sVal as $dKey => $dVal) { | |
| $rowDelivery = 0; | |
| foreach ($dVal as $key => $val) { | |
| $val['orderCellPhone'] = StringUtils::numberToCellPhone($val['orderCellPhone']); | |
| $statusMode = substr($val['orderStatus'], 0, 1); | |
| <?php if (!$val['memNo']) { ?> | |
| <?php if (!$val['memNoCheck']) { ?> | |
| <span class="font-kor">(비회원)</span> | |
| <?php } else { ?> | |
| <span class="font-kor">(탈퇴회원)</span> | |
| <?php } ?> | |
| <?php } else { ?> | |
| <?php if($useMultiShippingKey === true){ ?> | |
| <?php if($rowMultiShipping === 0){ ?> | |
| <td <?= $orderMultiShippingRowSpan ?>> | |
| <?php if($val['receiverZonecode']){ echo "[".$val['receiverZonecode']."]"; } ?> | |
| <?php if($val['receiverZipcode']){ echo "(".$val['receiverZipcode'].")"; } ?> | |
| <br /> | |
| <?php if($val['receiverAddress']){ echo $val['receiverAddress']; } ?> | |
| <?php if($val['receiverAddressSub']){ echo " ".$val['receiverAddressSub']; } ?> | |
| </td> | |
| <?php } ?> | |
| <?php } else {?> | |
| <?php if($rowChk === 0){ ?> | |
| <td <?= $orderGoodsRowSpan ?>> | |
| <?php if($val['receiverZonecode']){ echo "[".$val['receiverZonecode']."]"; } ?> | |
| <?php if($val['receiverZipcode']){ echo "(".$val['receiverZipcode'].")"; } ?> | |
| <br /> | |
| <?php if($val['receiverAddress']){ echo $val['receiverAddress']; } ?> | |
| <?php if($val['receiverAddressSub']){ echo " ".$val['receiverAddressSub']; } ?> | |
| </td> | |
| <?php } ?> | |
| <?php } ?> | |
변경 후layout_order_goods_list.php
| foreach ($sVal as $dKey => $dVal) { | |
| $rowDelivery = 0; | |
| foreach ($dVal as $key => $val) { | |
| // 마스킹된 번호에 전화 포맷을 적용하면 하이픈이 깨지므로 대상이 아닐 때만 포맷한다 | |
| if (empty($orderData['orderMaskLabel'])) { | |
| $val['orderCellPhone'] = StringUtils::numberToCellPhone($val['orderCellPhone']); | |
| } | |
| $statusMode = substr($val['orderStatus'], 0, 1); | |
| <?php if (!$val['memNo']) { ?> | |
| <?php if (!$val['memNoCheck']) { ?> | |
| <span class="font-kor">(비회원)</span> | |
| <?php } elseif (empty($data[$orderNo]['orderMaskLabel'])) { ?> | |
| <span class="font-kor">(탈퇴회원)</span> | |
| <?php } ?> | |
| <?php } else { ?> | |
| <?php if($useMultiShippingKey === true){ ?> | |
| <?php if($rowMultiShipping === 0){ ?> | |
| <td <?= $orderMultiShippingRowSpan ?>> | |
| <?php /* 배송지: 탈퇴/휴면 회원 주문이면 단일 '-' 표시(개인정보 은닉), 아니면 기존 조합 표시 */ ?> | |
| <?php if (!empty($data[$orderNo]['orderMaskLabel'])) { echo $data[$orderNo]['maskChar']; } else { ?> | |
| <?php if($val['receiverZonecode']){ echo "[".$val['receiverZonecode']."]"; } ?> | |
| <?php if($val['receiverZipcode']){ echo "(".$val['receiverZipcode'].")"; } ?> | |
| <br /> | |
| <?php if($val['receiverAddress']){ echo $val['receiverAddress']; } ?> | |
| <?php if($val['receiverAddressSub']){ echo " ".$val['receiverAddressSub']; } ?> | |
| <?php } ?> | |
| </td> | |
| <?php } ?> | |
| <?php } else {?> | |
| <?php if($rowChk === 0){ ?> | |
| <td <?= $orderGoodsRowSpan ?>> | |
| <?php /* 배송지: 탈퇴/휴면 회원 주문이면 단일 '-' 표시(개인정보 은닉), 아니면 기존 조합 표시 */ ?> | |
| <?php if (!empty($data[$orderNo]['orderMaskLabel'])) { echo $data[$orderNo]['maskChar']; } else { ?> | |
| <?php if($val['receiverZonecode']){ echo "[".$val['receiverZonecode']."]"; } ?> | |
| <?php if($val['receiverZipcode']){ echo "(".$val['receiverZipcode'].")"; } ?> | |
| <br /> | |
| <?php if($val['receiverAddress']){ echo $val['receiverAddress']; } ?> | |
| <?php if($val['receiverAddressSub']){ echo " ".$val['receiverAddressSub']; } ?> | |
| <?php } ?> | |
| </td> | |
| <?php } ?> | |
| <?php } ?> | |
변경 전layout_order_goods_simple_list.php
| foreach ($sVal as $dKey => $dVal) { | |
| $rowDelivery = 0; | |
| foreach ($dVal as $key => $val) { | |
| $val['orderCellPhone'] = StringUtils::numberToCellPhone($val['orderCellPhone']); | |
| $statusMode = substr($val['orderStatus'], 0, 1); | |
| <?php if (!$val['memNo']) { ?> | |
| <?php if (!$val['memNoCheck']) { ?> | |
| <span class="font-kor">(비회원)</span> | |
| <?php } else { ?> | |
| <span class="font-kor">(탈퇴회원)</span> | |
| <?php } ?> | |
| <?php } else { ?> | |
| <?php if($gridKey === 'receiverAddress' && $rowChk === 0){ //수령자 주소?> | |
| <td <?= $orderGoodsRowSpan ?>> | |
| <?php if($val['receiverZonecode']){ echo "[".$val['receiverZonecode']."]"; } ?> | |
| <?php if($val['receiverZipcode']){ echo "(".$val['receiverZipcode'].")"; } ?> | |
| <br /> | |
| <?php if($val['receiverAddress']){ echo $val['receiverAddress']; } ?> | |
| <?php if($val['receiverAddressSub']){ echo " ".$val['receiverAddressSub']; } ?> | |
| </td> | |
| <?php } //수령자 주소?> | |
변경 후layout_order_goods_simple_list.php
| foreach ($sVal as $dKey => $dVal) { | |
| $rowDelivery = 0; | |
| foreach ($dVal as $key => $val) { | |
| // 마스킹된 번호에 전화 포맷을 적용하면 하이픈이 깨지므로 대상이 아닐 때만 포맷한다 | |
| if (empty($orderData['orderMaskLabel'])) { | |
| $val['orderCellPhone'] = StringUtils::numberToCellPhone($val['orderCellPhone']); | |
| } | |
| $statusMode = substr($val['orderStatus'], 0, 1); | |
| <?php if (!$val['memNo']) { ?> | |
| <?php if (!$val['memNoCheck']) { ?> | |
| <span class="font-kor">(비회원)</span> | |
| <?php } elseif (empty($data[$orderNo]['orderMaskLabel'])) { ?> | |
| <span class="font-kor">(탈퇴회원)</span> | |
| <?php } ?> | |
| <?php } else { ?> | |
| <?php if($gridKey === 'receiverAddress' && $rowChk === 0){ //수령자 주소?> | |
| <td <?= $orderGoodsRowSpan ?>> | |
| <?php /* 배송지: 탈퇴/휴면 회원 주문이면 단일 '-' 표시(개인정보 은닉), 아니면 기존 조합 표시 */ ?> | |
| <?php if (!empty($data[$orderNo]['orderMaskLabel'])) { echo $data[$orderNo]['maskChar']; } else { ?> | |
| <?php if($val['receiverZonecode']){ echo "[".$val['receiverZonecode']."]"; } ?> | |
| <?php if($val['receiverZipcode']){ echo "(".$val['receiverZipcode'].")"; } ?> | |
| <br /> | |
| <?php if($val['receiverAddress']){ echo $val['receiverAddress']; } ?> | |
| <?php if($val['receiverAddressSub']){ echo " ".$val['receiverAddressSub']; } ?> | |
| <?php } ?> | |
| </td> | |
| <?php } //수령자 주소?> | |
변경 전layout_order_list.php
| foreach ($orderData['goods'] as $sKey => $sVal) { | |
| foreach ($sVal as $dKey => $dVal) { | |
| foreach ($dVal as $key => $val) { | |
| $val['orderCellPhone'] = StringUtils::numberToCellPhone($val['orderCellPhone']); | |
| if ($key > 0) { | |
| continue; | |
| } | |
| <?php if (!$val['memNo']) { ?> | |
| <?php if (!$val['memNoCheck']) { ?> | |
| <span class="font-kor">(비회원)</span> | |
| <?php } else { ?> | |
| <span class="font-kor">(탈퇴회원)</span> | |
| <?php } ?> | |
| <?php } else { ?> | |
변경 후layout_order_list.php
| foreach ($orderData['goods'] as $sKey => $sVal) { | |
| foreach ($sVal as $dKey => $dVal) { | |
| foreach ($dVal as $key => $val) { | |
| // 마스킹된 번호에 전화 포맷을 적용하면 하이픈이 깨지므로 대상이 아닐 때만 포맷한다 | |
| if (empty($orderData['orderMaskLabel'])) { | |
| $val['orderCellPhone'] = StringUtils::numberToCellPhone($val['orderCellPhone']); | |
| } | |
| if ($key > 0) { | |
| continue; | |
| } | |
| <?php if (!$val['memNo']) { ?> | |
| <?php if (!$val['memNoCheck']) { ?> | |
| <span class="font-kor">(비회원)</span> | |
| <?php } elseif (empty($data[$orderNo]['orderMaskLabel'])) { ?> | |
| <span class="font-kor">(탈퇴회원)</span> | |
| <?php } ?> | |
| <?php } else { ?> | |
변경 전layout_order_search_form.php
| unset($arrQueryString['__amount']); | |
| unset($arrQueryString['__totalPrice']); | |
| $queryString = http_build_query($arrQueryString); | |
| //탈퇴회원거래내역조회 제한 여부 | |
| $session = \App::getInstance('session'); | |
| $manager = \App::load('\\Component\\Member\\Manager'); | |
| $withdrawnMembersOrderLimitViewFl = $manager->getManagerFunctionAuth($session->get('manager.sno'))['functionAuth']['withdrawnMembersOrderLimitViewFl']; | |
| ?> | |
| <!-- 검색을 위한 form --> | |
| <label class="checkbox-inline"> | |
| <input type="checkbox" name="firstSaleFl" value="y" <?= gd_isset($checked['firstSaleFl']['y']); ?>/> 첫주문 | |
| </label> | |
| <?php if ($withdrawnMembersOrderLimitViewFl != 'y') { ?> | |
| <label class="checkbox-inline"> | |
| <input type="checkbox" name="withdrawnMembersOrderFl" value="<?=$search['withdrawnMembersOrderFl']?>" <?= gd_isset($checked['withdrawnMembersOrderFl']['y']); ?>/> 탈퇴회원 주문 | |
| </label> | |
| <?php } ?> | |
| </td> | |
| <th>배송정보</th> | |
| <td class="form-inline"> | |
| <input type="hidden" name="view" value="<?=$search['view']?>"/> | |
| <input type="hidden" name="searchFl" value="y"> | |
| <input type="hidden" name="applyPath" value="<?=gd_php_self()?>?view=<?=$search['view']?>"> | |
| <input type="hidden" name="withdrawnMembersOrderChk" value="<?= $search['withdrawnMembersOrderFl'] ?>"> | |
| </form> | |
| <!-- // 검색을 위한 form --> | |
| </form> | |
| <!-- // 프린트 출력을 위한 form --> | |
| <script type="text/javascript"> | |
| $(document).ready(function () { | |
| $('input[name="withdrawnMembersOrderFl"]').change(function () { | |
| if ($(this).is(':checked')) { | |
| $('input[name="withdrawnMembersOrderChk"]').val('y'); | |
| } else { | |
| $('input[name="withdrawnMembersOrderChk"]').val('n'); | |
| } | |
| }); | |
| }); | |
| </script> | |
| <?php if($isOrderSearchMultiGrid == 'y') { ?> | |
| <script type="text/javascript"> | |
변경 후layout_order_search_form.php
| unset($arrQueryString['__amount']); | |
| unset($arrQueryString['__totalPrice']); | |
| $queryString = http_build_query($arrQueryString); | |
| ?> | |
| <!-- 검색을 위한 form --> | |
| <label class="checkbox-inline"> | |
| <input type="checkbox" name="firstSaleFl" value="y" <?= gd_isset($checked['firstSaleFl']['y']); ?>/> 첫주문 | |
| </label> | |
| </td> | |
| <th>배송정보</th> | |
| <td class="form-inline"> | |
| <input type="hidden" name="view" value="<?=$search['view']?>"/> | |
| <input type="hidden" name="searchFl" value="y"> | |
| <input type="hidden" name="applyPath" value="<?=gd_php_self()?>?view=<?=$search['view']?>"> | |
| </form> | |
| <!-- // 검색을 위한 form --> | |
| </form> | |
| <!-- // 프린트 출력을 위한 form --> | |
| <?php if($isOrderSearchMultiGrid == 'y') { ?> | |
| <script type="text/javascript"> | |
변경 전layout_order_view_order_info.php
| * | |
| * @author <bumyul2000@godo.co.kr> | |
| */ | |
| ?> | |
| <table class="table table-cols"> | |
| <colgroup> | |
| <tr> | |
| <th>주문자명</th> | |
| <td> | |
| <span class="text-primary"><?= gd_isset($withdrawnMembersPersonalData['orderName']) ? gd_isset($withdrawnMembersPersonalData['orderName']) : gd_isset($data['orderName']); ?></span> | |
| <?php if (empty($memInfo) === true) { ?> | |
| <?php if (empty($data['memNo']) === true) { ?> | |
| / <span class="text-primary">비회원</span> | |
| <?php } else { ?> | |
| / <span class="text-primary">탈퇴회원</span> | |
| <?php } ?> | |
| <?php } else { ?> | |
| / <span class="text-primary"><?= $memInfo['memId'] ?></span> | |
| <tr> | |
| <th>전화번호</th> | |
| <td> | |
| <span class="font-num"><?= ((empty($data['orderPhone']) === false && empty($data['isDefaultMall'])) ? '(' . gd_isset($data['orderPhonePrefix']) . ') ' : '') . (gd_isset($withdrawnMembersPersonalData['orderPhone']) ? gd_isset($withdrawnMembersPersonalData['orderPhone']) : gd_isset($data['orderPhone'])); ?></span> | |
| </td> | |
| </tr> | |
| <tr> | |
| <th>휴대폰번호</th> | |
| <td> | |
| <?php if (empty($data['orderCellPhone']) === false) { ?> | |
| <?= (empty($data['isDefaultMall']) ? '(' . gd_isset($data['orderCellPhonePrefix']) . ') ' : '') . gd_isset($data['orderCellPhone']) ?> | |
| <?php if (empty($data['isDefaultMall']) === false) { ?> | |
| <a class="btn btn-sm btn-gray" onclick="member_sms('<?=gd_isset($data['memNo'])?>','<?= urlencode($data['orderName']); ?>','<?= $data['orderCellPhone']; ?>', '<?=$data['smsFl']?>')">SMS 보내기</a> | |
| <?php } ?> | |
| <?php } else if (empty($withdrawnMembersPersonalData['orderCellPhone']) === false) { ?> | |
| <?= gd_isset($withdrawnMembersPersonalData['orderCellPhone']) ?> | |
| <?php } ?> | |
| </td> | |
| <th>이메일</th> | |
| <td><?= gd_isset($withdrawnMembersPersonalData['orderEmail']) ? gd_isset($withdrawnMembersPersonalData['orderEmail']) : gd_isset($data['orderEmail']); ?></td> | |
| </tr> | |
| <?php if (empty($data['orderAddress']) === false) { ?> | |
| <?php if (empty($data['isDefaultMall']) === true) { ?> | |
| <tr> | |
| <th>주소</th> | |
| <td> | |
| <div> | |
| [<?= gd_isset($data['orderZonecode']); ?>] | |
| </div> | |
| <?= gd_isset($data['orderCity']); ?>, | |
| <?= gd_isset($data['orderCountry']); ?> | |
| </div> | |
| </td> | |
| </tr> | |
| <?php } else { ?> | |
| <tr> | |
| <th>주소</th> | |
| <td> | |
| <div> | |
| [<?= gd_isset($data['orderZonecode']); ?>] | |
| <?php if (strlen($data['orderZipcode']) == 7) { | |
| } ?> | |
| </div> | |
| <div><?= gd_isset($data['orderAddress']); ?><br /><?= gd_isset($data['orderAddressSub']); ?></div> | |
| </td> | |
| </tr> | |
| <?php } ?> | |
| <?php } else if (empty($withdrawnMembersPersonalData['orderAddress']) === false) { ?> | |
| <tr> | |
| <th>주소</th> | |
| <td> | |
| <div> | |
| [<?= gd_isset($data['orderZonecode']); ?>] | |
| <?php if (strlen($data['orderZipcode']) == 7) { | |
| echo '(' . gd_isset($data['orderZipcode']) . ')'; | |
| } ?> | |
| </div> | |
| <div><?= gd_isset($withdrawnMembersPersonalData['orderAddress']); ?><br/><?= gd_isset($withdrawnMembersPersonalData['orderAddressSub']); ?></div> | |
| </td> | |
| </tr> | |
| <?php } ?> | |
변경 후layout_order_view_order_info.php
| * | |
| * @author <bumyul2000@godo.co.kr> | |
| */ | |
| // 분리 보관으로 표시 키가 '-' 로 덮여, 실제 값이 필요한 곳(노출 조건·SMS 발송)에 쓸 분리 원본을 따로 받는다 | |
| $orderPhoneSeparationOrigin = isset($data['orderPhoneSeparationOrigin']) ? $data['orderPhoneSeparationOrigin'] : $data['orderPhone']; | |
| $orderCellPhoneSeparationOrigin = isset($data['orderCellPhoneSeparationOrigin']) ? $data['orderCellPhoneSeparationOrigin'] : $data['orderCellPhone']; | |
| $orderAddressSeparationOrigin = isset($data['orderAddressSeparationOrigin']) ? $data['orderAddressSeparationOrigin'] : $data['orderAddress']; | |
| ?> | |
| <table class="table table-cols"> | |
| <colgroup> | |
| <tr> | |
| <th>주문자명</th> | |
| <td> | |
| <?php /* 주문자명(1A): 탈퇴/휴면 회원 주문이면 회원 유형 라벨("탈퇴회원"/"휴면회원") 표시, 일반 회원은 원본 표시 */ ?> | |
| <span class="text-primary"><?= gd_isset($orderMaskLabel) ?: (gd_isset($withdrawnMembersPersonalData['orderName']) ? gd_isset($withdrawnMembersPersonalData['orderName']) : gd_isset($data['orderName'])); ?></span> | |
| <?php if (empty($memInfo) === true) { ?> | |
| <?php if (empty($data['memNo']) === true) { ?> | |
| / <span class="text-primary">비회원</span> | |
| <?php } ?> | |
| <?php } else { ?> | |
| / <span class="text-primary"><?= $memInfo['memId'] ?></span> | |
| <tr> | |
| <th>전화번호</th> | |
| <td> | |
| <span class="font-num"><?= ((!empty($orderPhoneSeparationOrigin) && empty($data['isDefaultMall'])) ? '(' . gd_isset($data['orderPhonePrefix']) . ') ' : '') . (gd_isset($withdrawnMembersPersonalData['orderPhone']) ? gd_isset($withdrawnMembersPersonalData['orderPhone']) : gd_isset($data['orderPhone'])); ?></span> | |
| </td> | |
| </tr> | |
| <tr> | |
| <th>휴대폰번호</th> | |
| <td> | |
| <?php if (!empty($orderCellPhoneSeparationOrigin)) { ?> | |
| <?= (empty($data['isDefaultMall']) ? '(' . gd_isset($data['orderCellPhonePrefix']) . ') ' : '') . gd_isset($data['orderCellPhone']) ?> | |
| <?php if (!empty($data['isDefaultMall'])) { ?> | |
| <?php /* member_sms 인자는 SMS 발송 기능용 → 분리 원본 키 사용 */ ?> | |
| <a class="btn btn-sm btn-gray" onclick="member_sms('<?=gd_isset($data['memNo'])?>','<?= urlencode($data['orderName']); ?>','<?= $orderCellPhoneSeparationOrigin; ?>', '<?=$data['smsFl']?>')">SMS 보내기</a> | |
| <?php } ?> | |
| <?php } else if (!empty($withdrawnMembersPersonalData['orderCellPhone'])) { ?> | |
| <?= gd_isset($withdrawnMembersPersonalData['orderCellPhone']) ?> | |
| <?php } ?> | |
| </td> | |
| <th>이메일</th> | |
| <td><?= gd_isset($withdrawnMembersPersonalData['orderEmail']) ? gd_isset($withdrawnMembersPersonalData['orderEmail']) : gd_isset($data['orderEmail']); ?></td> | |
| </tr> | |
| <?php if (!empty($orderAddressSeparationOrigin) || !empty($withdrawnMembersPersonalData['orderAddress'])) { ?> | |
| <tr> | |
| <th>주소</th> | |
| <td> | |
| <?php /* 주소 구성요소가 각각 '-' 로 치환돼 하이픈이 반복되므로 칸 전체를 단일 '-' 로 표시 */ ?> | |
| <?php if (!empty($orderMaskLabel)) { ?> | |
| <?= $maskChar ?> | |
| <?php } else if (empty($data['isDefaultMall'])) { ?> | |
| <div> | |
| [<?= gd_isset($data['orderZonecode']); ?>] | |
| </div> | |
| <?= gd_isset($data['orderCity']); ?>, | |
| <?= gd_isset($data['orderCountry']); ?> | |
| </div> | |
| <?php } else { ?> | |
| <div> | |
| [<?= gd_isset($data['orderZonecode']); ?>] | |
| <?php if (strlen($data['orderZipcode']) == 7) { | |
| } ?> | |
| </div> | |
| <div><?= gd_isset($data['orderAddress']); ?><br /><?= gd_isset($data['orderAddressSub']); ?></div> | |
| <?php } ?> | |
| </td> | |
| </tr> | |
| <?php } ?> | |
변경 전layout_order_view_receiver_info.php
| * | |
| * @author <bumyul2000@godo.co.kr> | |
| */ | |
| ?> | |
| <table class="table table-cols"> | |
| <colgroup> | |
| </tr> | |
| <tr> | |
| <th>전화번호</th> | |
| <td><?= ((empty($data['receiverPhone']) === false && gd_count($data['receiverPhone']) > 1 && empty($data['isDefaultMall'])) ? '(' . gd_isset($data['receiverPhonePrefix']) . ') ' : '') . (gd_isset($withdrawnMembersPersonalData['receiverPhone']) ? gd_isset($withdrawnMembersPersonalData['receiverPhone']) : gd_isset(gd_implode("-", $data['receiverPhone']))); ?></td> | |
| </tr> | |
| <tr> | |
| <th>휴대폰번호</th> | |
| <td> | |
| <?= ((empty($data['receiverCellPhone']) === false && gd_count($data['receiverCellPhone']) > 1 && empty($data['isDefaultMall'])) ? '(' . gd_isset($data['receiverCellPhonePrefix']) . ') ' : '') . gd_isset(gd_implode("-",$data['receiverCellPhone'])); ?> | |
| <?php if ($data['orderTypeFl'] === "present") { ?> | |
| <?php if ($presentReceiver['sendSmsFl'] === "y") { ?> | |
| <a class="btn btn-sm btn-white" onclick="present_notification_resend()"><span>선물메시지 재발송</span></a> | |
| <?php } ?> | |
| <?php } ?> | |
| <?php if (empty($data['receiverCellPhone'][1]) === false && empty($data['isDefaultMall']) === false) { ?> | |
| <a class="btn btn-sm btn-gray" onclick="member_sms('','<?= urlencode($data['receiverName']); ?>','<?= gd_implode('-', $data['receiverCellPhone']); ?>')">SMS 보내기</a> | |
| <?php } else if (empty($withdrawnMembersPersonalData['receiverCellPhone']) === false) { ?> | |
| <?= gd_isset($withdrawnMembersPersonalData['receiverCellPhone']) ?> | |
| <?php } ?> | |
| </td> | |
| </tr> | |
| <tr> | |
| <th>안심번호</th> | |
| <td> | |
| <?php if ($data['receiverUseSafeNumberFl'] == 'w') { | |
| if ($safeNumberFl != 'off') { ?> | |
| 결제완료 시 발급됩니다. | |
| <?php } else { ?> | |
| <span class="text-danger">안심번호 서비스를 일시적으로 사용할 수 없습니다.</span> | |
| <?php } | |
| } else { | |
| echo $data['receiverSafeNumber']; | |
| if ($data['receiverUseSafeNumberFl'] == 'y') { | |
| if (empty($data['receiverSafeNumber'])) { | |
| if ($safeNumberFl != 'off') { ?> | |
| (발급대기) | |
| <input type="button" class="btn btn-sm btn-gray js-reset-safeNumber" value="수동발급" | |
| data-order-info-sno="<?= $data['infoSno'] ?>" | |
| data-receiver-cellphone="<?= gd_implode("", $data['receiverCellPhone']); ?>" | |
| data-use-safenumber-fl="<?= $data['receiverUseSafeNumberFl']; ?>"> | |
| <?php } else { ?> | |
| <span class="text-danger">안심번호 서비스를 일시적으로 사용할 수 없습니다.</span> | |
| <?php } | |
| } else { | |
| if ($safeNumberFl != 'off') {?> | |
| <input type="button" class="btn btn-sm btn-gray js-cancel-safeNumber" value="사용해지" data-order-info-sno="<?=$data['infoSno']?>" data-receiver-cellphone="<?=gd_implode("",$data['receiverCellPhone']);?>" data-safenumber="<?=$data['receiverSafeNumber'];?>"> | |
| <?php } | |
| } | |
| } else if ($data['receiverUseSafeNumberFl'] == 'c') { ?> | |
| <tr> | |
| <th>주소</th> | |
| <td> | |
| <?php if (empty($data['isDefaultMall']) === true) { ?> | |
| <!-- 멀티몰 --> | |
| <div> | |
| [<?= gd_isset($data['receiverZonecode']); ?>] | |
| </div> | |
| <div> | |
| <?= gd_isset($data['receiverAddressSub']); ?>, | |
| <?= gd_isset($data['receiverAddress']); ?>, | |
| <?= gd_isset($data['receiverState']); ?>, | |
| <?= gd_isset($data['receiverCity']); ?>, | |
| <?= gd_isset($data['receiverCountry']); ?> | |
| </div> | |
| <!-- 멀티몰 --> | |
| <?php } else { ?> | |
| <!-- 기준몰 --> | |
| <div> | |
| [<?= gd_isset($data['receiverZonecode']); ?>] | |
| <?php if (strlen($data['receiverZipcode']) == 7) { | |
| <div><?= gd_isset($withdrawnMembersPersonalData['receiverAddress']) ? gd_isset($withdrawnMembersPersonalData['receiverAddress']) : gd_isset($data['receiverAddress']); ?> | |
| <br/><?= gd_isset($withdrawnMembersPersonalData['receiverAddressSub']) ? gd_isset($withdrawnMembersPersonalData['receiverAddressSub']) : gd_isset($data['receiverAddressSub']); ?> | |
| </div> | |
| <!-- 기준몰 --> | |
| <?php } ?> | |
| </td> | |
| </tr> | |
| </colgroup> | |
| <tr> | |
| <th>방문 수령지 주소</th> | |
| <td><?php echo $data['visitDeliveryInfo']['address'][$data['infoSno']][0] . (gd_count($data['visitDeliveryInfo']['address'][$data['infoSno']]) > 1 ? '외 ' . (gd_count($data['visitDeliveryInfo']['address'][$data['infoSno']]) - 1) . '건 ' : ''); ?> <button type="button" class="btn btn-black btn-sm js-visit-address mgb5" data-order-no="<?php echo $data['orderNo']; ?>" data-goods-sno='<?php echo json_encode($data['visitDeliveryInfo']['goodsSno'][$data['infoSno']]);?>'>상품정보</button></td> | |
| </tr> | |
| <tr> | |
| <th>방문자 정보</th> | |
| <td><?php echo $data['visitName'] . ' / ' . $data['visitPhone']; ?></td> | |
| </tr> | |
| <tr> | |
| <th>메모</th> | |
변경 후layout_order_view_receiver_info.php
| * | |
| * @author <bumyul2000@godo.co.kr> | |
| */ | |
| // 분리 보관으로 표시 키가 '-' 로 덮여, 실제 값이 필요한 곳(노출 조건·SMS 발송·안심번호 전송)에 쓸 분리 원본을 따로 받는다 | |
| $receiverNameSeparationOrigin = isset($data['receiverNameSeparationOrigin']) ? $data['receiverNameSeparationOrigin'] : $data['receiverName']; | |
| $receiverPhoneSeparationOrigin = isset($data['receiverPhoneSeparationOrigin']) ? $data['receiverPhoneSeparationOrigin'] : $data['receiverPhone']; | |
| $receiverCellPhoneSeparationOrigin = isset($data['receiverCellPhoneSeparationOrigin']) ? $data['receiverCellPhoneSeparationOrigin'] : $data['receiverCellPhone']; | |
| ?> | |
| <table class="table table-cols"> | |
| <colgroup> | |
| </tr> | |
| <tr> | |
| <th>전화번호</th> | |
| <?php /* 전화/휴대폰 표시값: 마스킹 주문은 '-'(문자열), 그 외는 explode 배열 → 배열만 합쳐서 출력한다 */ ?> | |
| <td><?= ((!empty($receiverPhoneSeparationOrigin) && gd_count($receiverPhoneSeparationOrigin) > 1 && empty($data['isDefaultMall'])) ? '(' . gd_isset($data['receiverPhonePrefix']) . ') ' : '') . (gd_isset($withdrawnMembersPersonalData['receiverPhone']) ? gd_isset($withdrawnMembersPersonalData['receiverPhone']) : (is_array($data['receiverPhone']) ? gd_isset(gd_implode("-", $data['receiverPhone'])) : gd_isset($data['receiverPhone']))); ?></td> | |
| </tr> | |
| <tr> | |
| <th>휴대폰번호</th> | |
| <td> | |
| <?= ((!empty($receiverCellPhoneSeparationOrigin) && gd_count($receiverCellPhoneSeparationOrigin) > 1 && empty($data['isDefaultMall'])) ? '(' . gd_isset($data['receiverCellPhonePrefix']) . ') ' : '') . (is_array($data['receiverCellPhone']) ? gd_isset(gd_implode("-", $data['receiverCellPhone'])) : gd_isset($data['receiverCellPhone'])); ?> | |
| <?php if ($data['orderTypeFl'] === "present") { ?> | |
| <?php if ($presentReceiver['sendSmsFl'] === "y") { ?> | |
| <a class="btn btn-sm btn-white" onclick="present_notification_resend()"><span>선물메시지 재발송</span></a> | |
| <?php } ?> | |
| <?php } ?> | |
| <?php if (!empty($receiverCellPhoneSeparationOrigin[1]) && !empty($data['isDefaultMall'])) { ?> | |
| <?php /* member_sms 인자는 SMS 발송 기능용 → 분리 원본 키 사용 */ ?> | |
| <a class="btn btn-sm btn-gray" onclick="member_sms('','<?= urlencode($receiverNameSeparationOrigin); ?>','<?= gd_implode('-', $receiverCellPhoneSeparationOrigin); ?>')">SMS 보내기</a> | |
| <?php } ?> | |
| </td> | |
| </tr> | |
| <tr> | |
| <th>안심번호</th> | |
| <td> | |
| <?php | |
| // 안심번호 표시값: 탈퇴 분리주문은 $data 공백 → 별도 표시키(withdrawnMembersPersonalData) fallback (표시 전용, $data 원복 아님) | |
| // 휴면/일반은 $data 에 값 존재(휴면은 OrderViewController SAFE_NUMBER restore 로 $data 원복됨) | |
| $displaySafeNumber = !empty($data['receiverSafeNumber']) | |
| ? $data['receiverSafeNumber'] | |
| : gd_isset($withdrawnMembersPersonalData['receiverSafeNumber']); | |
| if ($data['receiverUseSafeNumberFl'] == 'w') { | |
| if ($safeNumberFl != 'off') { ?> | |
| 결제완료 시 발급됩니다. | |
| <?php } else { ?> | |
| <span class="text-danger">안심번호 서비스를 일시적으로 사용할 수 없습니다.</span> | |
| <?php } | |
| } else { | |
| echo $displaySafeNumber; | |
| if ($data['receiverUseSafeNumberFl'] == 'y') { | |
| if (empty($displaySafeNumber)) { | |
| if ($safeNumberFl != 'off') { ?> | |
| (발급대기) | |
| <input type="button" class="btn btn-sm btn-gray js-reset-safeNumber" value="수동발급" | |
| data-order-info-sno="<?= $data['infoSno'] ?>" | |
| data-receiver-cellphone="<?= gd_implode("", $receiverCellPhoneSeparationOrigin); ?>" | |
| data-use-safenumber-fl="<?= $data['receiverUseSafeNumberFl']; ?>"> | |
| <?php } else { ?> | |
| <span class="text-danger">안심번호 서비스를 일시적으로 사용할 수 없습니다.</span> | |
| <?php } | |
| } else { | |
| if ($safeNumberFl != 'off') {?> | |
| <input type="button" class="btn btn-sm btn-gray js-cancel-safeNumber" value="사용해지" data-order-info-sno="<?=$data['infoSno']?>" data-receiver-cellphone="<?=gd_implode("",$receiverCellPhoneSeparationOrigin);?>" data-safenumber="<?=$data['receiverSafeNumber'];?>"> | |
| <?php } | |
| } | |
| } else if ($data['receiverUseSafeNumberFl'] == 'c') { ?> | |
| <tr> | |
| <th>주소</th> | |
| <td> | |
| <?php /* 주소 구성요소가 각각 '-' 로 치환돼 하이픈이 반복되므로 칸 전체를 단일 '-' 로 표시 */ ?> | |
| <?php if (!empty($orderMaskLabel)) { ?> | |
| <?= $maskChar ?> | |
| <?php } else if (empty($data['isDefaultMall'])) { ?> | |
| <div> | |
| [<?= gd_isset($data['receiverZonecode']); ?>] | |
| </div> | |
| <div> | |
| <?= gd_isset($data['receiverAddressSub']); ?>, | |
| <?= gd_isset($data['receiverAddress']); ?>, | |
| <?= gd_isset($data['receiverState']); ?>, | |
| <?= gd_isset($data['receiverCity']); ?>, | |
| <?= gd_isset($data['receiverCountry']); ?> | |
| </div> | |
| <?php } else { ?> | |
| <div> | |
| [<?= gd_isset($data['receiverZonecode']); ?>] | |
| <?php if (strlen($data['receiverZipcode']) == 7) { | |
| <div><?= gd_isset($withdrawnMembersPersonalData['receiverAddress']) ? gd_isset($withdrawnMembersPersonalData['receiverAddress']) : gd_isset($data['receiverAddress']); ?> | |
| <br/><?= gd_isset($withdrawnMembersPersonalData['receiverAddressSub']) ? gd_isset($withdrawnMembersPersonalData['receiverAddressSub']) : gd_isset($data['receiverAddressSub']); ?> | |
| </div> | |
| <?php } ?> | |
| </td> | |
| </tr> | |
| </colgroup> | |
| <tr> | |
| <th>방문 수령지 주소</th> | |
| <td><?php echo !empty($orderMaskLabel) ? $maskChar : $data['visitDeliveryInfo']['address'][$data['infoSno']][0] . (gd_count($data['visitDeliveryInfo']['address'][$data['infoSno']]) > 1 ? '외 ' . (gd_count($data['visitDeliveryInfo']['address'][$data['infoSno']]) - 1) . '건 ' : ''); ?> <button type="button" class="btn btn-black btn-sm js-visit-address mgb5" data-order-no="<?php echo $data['orderNo']; ?>" data-goods-sno='<?php echo json_encode($data['visitDeliveryInfo']['goodsSno'][$data['infoSno']]);?>'>상품정보</button></td> | |
| </tr> | |
| <tr> | |
| <th>방문자 정보</th> | |
| <td><?php echo !empty($orderMaskLabel) ? $maskChar : $data['visitName'] . ' / ' . $data['visitPhone']; ?></td> | |
| </tr> | |
| <tr> | |
| <th>메모</th> | |
변경 전layout_order_view_receiver_info_modify.php
| * | |
| * @author <bumyul2000@godo.co.kr> | |
| */ | |
| ?> | |
| <table class="table table-cols"> | |
| <?php if (empty($data['isDefaultMall']) === true) { ?> | |
| <p><?= gd_select_box('receiverPhonePrefixCode', 'info[receiverPhonePrefixCode]', $countryPhone, null, $data['receiverPhonePrefixCode'], null, null, 'form-control'); ?></p> | |
| <?php } ?> | |
| <input type="text" name="info[receiverPhone]" value="<?= gd_isset(gd_implode("",$data['receiverPhone'])); ?>" maxlength="12" class="form-control js-number-only width-md"/> | |
| </div> | |
| </td> | |
| </tr> | |
| <p><?= gd_select_box('receiverCellPhonePrefixCode', 'info[receiverCellPhonePrefixCode]', $countryPhone, null, $data['receiverCellPhonePrefixCode'], null, null, 'form-control '); ?></p> | |
| <?php } else { | |
| if (gd_isset($safeNumberFl) && $data['receiverUseSafeNumberFl'] == 'y') { ?> | |
| <input type="hidden" name="info[receiverOriginCellPhone]" value="<?= gd_isset(gd_implode("",$data['receiverCellPhone'])); ?>"> | |
| <input type="hidden" name="info[receiverSafeNumber]" value="<?= gd_isset($data['receiverSafeNumber']); ?>"> | |
| <?php } ?> | |
| <?php } ?> | |
| <input type="text" name="info[receiverCellPhone]" value="<?= gd_isset(gd_implode("",$data['receiverCellPhone'])); ?>" maxlength="12" class="form-control js-number-only width-md"/> | |
| </div> | |
| </td> | |
| </tr> | |
| <th>방문자 정보</th> | |
| <td> | |
| <div class="form-inline"> | |
| <input type="text" name="info[visitName]" value="<?= gd_isset($data['visitName']); ?>" class="form-control"/> | |
| <input type="text" name="info[visitPhone]" value="<?= gd_isset($data['visitPhone']); ?>" class="form-control"/> | |
| </div> | |
| </td> | |
| </tr> | |
변경 후layout_order_view_receiver_info_modify.php
| * | |
| * @author <bumyul2000@godo.co.kr> | |
| */ | |
| // 분리 보관으로 표시 키가 '-' 로 덮여, 실제 값이 필요한 곳(수정 폼 전송값)에 쓸 분리 원본을 따로 받는다 | |
| $receiverPhoneSeparationOrigin = isset($data['receiverPhoneSeparationOrigin']) ? $data['receiverPhoneSeparationOrigin'] : $data['receiverPhone']; | |
| $receiverCellPhoneSeparationOrigin = isset($data['receiverCellPhoneSeparationOrigin']) ? $data['receiverCellPhoneSeparationOrigin'] : $data['receiverCellPhone']; | |
| $visitNameSeparationOrigin = isset($data['visitNameSeparationOrigin']) ? $data['visitNameSeparationOrigin'] : $data['visitName']; | |
| $visitPhoneSeparationOrigin = isset($data['visitPhoneSeparationOrigin']) ? $data['visitPhoneSeparationOrigin'] : $data['visitPhone']; | |
| ?> | |
| <table class="table table-cols"> | |
| <?php if (empty($data['isDefaultMall']) === true) { ?> | |
| <p><?= gd_select_box('receiverPhonePrefixCode', 'info[receiverPhonePrefixCode]', $countryPhone, null, $data['receiverPhonePrefixCode'], null, null, 'form-control'); ?></p> | |
| <?php } ?> | |
| <input type="text" name="info[receiverPhone]" value="<?= gd_isset(gd_implode("",$receiverPhoneSeparationOrigin)); ?>" maxlength="12" class="form-control js-number-only width-md"/> | |
| </div> | |
| </td> | |
| </tr> | |
| <p><?= gd_select_box('receiverCellPhonePrefixCode', 'info[receiverCellPhonePrefixCode]', $countryPhone, null, $data['receiverCellPhonePrefixCode'], null, null, 'form-control '); ?></p> | |
| <?php } else { | |
| if (gd_isset($safeNumberFl) && $data['receiverUseSafeNumberFl'] == 'y') { ?> | |
| <input type="hidden" name="info[receiverOriginCellPhone]" value="<?= gd_isset(gd_implode("",$receiverCellPhoneSeparationOrigin)); ?>"> | |
| <input type="hidden" name="info[receiverSafeNumber]" value="<?= gd_isset($data['receiverSafeNumber']); ?>"> | |
| <?php } ?> | |
| <?php } ?> | |
| <input type="text" name="info[receiverCellPhone]" value="<?= gd_isset(gd_implode("",$receiverCellPhoneSeparationOrigin)); ?>" maxlength="12" class="form-control js-number-only width-md"/> | |
| </div> | |
| </td> | |
| </tr> | |
| <th>방문자 정보</th> | |
| <td> | |
| <div class="form-inline"> | |
| <input type="text" name="info[visitName]" value="<?= gd_isset($visitNameSeparationOrigin); ?>" class="form-control"/> | |
| <input type="text" name="info[visitPhone]" value="<?= gd_isset($visitPhoneSeparationOrigin); ?>" class="form-control"/> | |
| </div> | |
| </td> | |
| </tr> | |
변경 전logistics_layout_order_goods_list.php
| <?php if (!$val['memNo']) { ?> | |
| <?php if (!$val['memNoCheck']) { ?> | |
| <span class="font-kor">(비회원)</span> | |
| <?php } else { ?> | |
| <span class="font-kor">(탈퇴회원)</span> | |
| <?php } ?> | |
| <?php } else { ?> | |
변경 후logistics_layout_order_goods_list.php
| <?php if (!$val['memNo']) { ?> | |
| <?php if (!$val['memNoCheck']) { ?> | |
| <span class="font-kor">(비회원)</span> | |
| <?php } elseif (empty($data[$orderNo]['orderMaskLabel'])) { ?> | |
| <span class="font-kor">(탈퇴회원)</span> | |
| <?php } ?> | |
| <?php } else { ?> | |
변경 전order_list_withdrawn_member.php
변경 후order_list_withdrawn_member.php
| <link rel="stylesheet" href="<?= gd_set_browser_cache(PATH_ADMIN_GD_SHARE . 'ncds/css/order/order-list-withdrawn-member.css') ?>"/> | |
| <script defer src="<?= gd_set_browser_cache(PATH_ADMIN_GD_SHARE . 'ncds/script/common/supply-combo-box.js') ?>"></script> | |
| <script src="<?= gd_set_browser_cache(PATH_ADMIN_GD_SHARE . 'script/orderList.js') ?>"></script> | |
| <article class="ncua-content order-list-withdrawn-member"> | |
| <header class="ncua-page-header page-header js-affix"> | |
| <h3><?= end($naviMenu->location); ?></h3> | |
| </header> | |
| <section class="ncua-card"> | |
| <header class="ncua-card__header"> | |
| <h4 class="ncua-card__title">주문 검색</h4> | |
| </header> | |
| <section class="ncua-card__body"> | |
| <form id="frmSearchDormantMember" method="get" class="js-form-enter-submit"> | |
| <div class="ncua-table ncua-table--vertical"> | |
| <table> | |
| <colgroup> | |
| <col class="search-keyword-table-th-width"/> | |
| <col/> | |
| </colgroup> | |
| <tbody> | |
| <tr> | |
| <th class="ncua-required"><div>주문자</div></th> | |
| <td> | |
| <div class="ncua-flex ncua-gap-4 search-keyword-wrap"> | |
| <div class="ncua-select ncua-select--xs"> | |
| <div class="ncua-select__content"> | |
| <select name="searchField" class="ncua-select__tag"> | |
| <option value="orderName" <?= $search['searchField'] === 'orderName' ? 'selected' : '' ?>>주문자명</option> | |
| <option value="orderNo" <?= $search['searchField'] === 'orderNo' ? 'selected' : '' ?>>주문번호</option> | |
| </select> | |
| </div> | |
| </div> | |
| <div class="ncua-input ncua-input--xs ncua-input-width-320"> | |
| <div class="ncua-input__content"> | |
| <div class="ncua-input__field ncua-input__field--xs"> | |
| <input type="text" name="searchWord" value="<?= htmlspecialchars($search['searchWord']) ?>" placeholder="검색어 전체를 정확히 입력하세요."/> | |
| </div> | |
| </div> | |
| </div> | |
| </div> | |
| </td> | |
| </tr> | |
| <tr> | |
| <th><div>상점 구분</div></th> | |
| <td> | |
| <div class="ncua-radio-field-group search-radio-group"> | |
| <label class="ncua-radio-field ncua-radio-field--xs has-text"> | |
| <span class="ncua-radio-input ncua-radio-input--xs ncua-radio-field__input"> | |
| <input type="radio" name="mallType" value="" <?= $search['mallType'] === '' ? 'checked' : '' ?>/> | |
| </span> | |
| <span class="ncua-radio-field__text">전체</span> | |
| </label> | |
| <?php foreach ((array) ($mallTypeOptions ?? []) as $mallDomainFl => $mallTypeLabel): ?> | |
| <label class="ncua-radio-field ncua-radio-field--xs has-text"> | |
| <span class="ncua-radio-input ncua-radio-input--xs ncua-radio-field__input"> | |
| <input type="radio" name="mallType" value="<?= $mallDomainFl ?>" <?= $search['mallType'] === $mallDomainFl ? 'checked' : '' ?>/> | |
| </span> | |
| <span class="ncua-radio-field__text"><?= $mallTypeLabel ?></span> | |
| </label> | |
| <?php endforeach; ?> | |
| </div> | |
| </td> | |
| </tr> | |
| <?php if (empty($isProvider)): // 공급사 계정은 공급사 구분 필터 미노출 ?> | |
| <tr> | |
| <th><div>공급사 구분</div></th> | |
| <td> | |
| <div class="supply-radio-group search-radio-group"> | |
| <label class="ncua-radio-field ncua-radio-field--xs has-text"> | |
| <span class="ncua-radio-input ncua-radio-input--xs ncua-radio-field__input"> | |
| <input type="radio" name="scmFl" value="all" <?= $search['scmFl'] === 'all' ? 'checked' : '' ?>/> | |
| </span> | |
| <span><span class="ncua-radio-field__text">전체</span></span> | |
| </label> | |
| <label class="ncua-radio-field ncua-radio-field--xs has-text"> | |
| <span class="ncua-radio-input ncua-radio-input--xs ncua-radio-field__input"> | |
| <input type="radio" name="scmFl" value="n" <?= $search['scmFl'] === 'n' ? 'checked' : '' ?>/> | |
| </span> | |
| <span><span class="ncua-radio-field__text">본사</span></span> | |
| </label> | |
| <label class="ncua-radio-field ncua-radio-field--xs has-text"> | |
| <span class="ncua-radio-input ncua-radio-input--xs ncua-radio-field__input"> | |
| <input type="radio" name="scmFl" value="y" <?= $search['scmFl'] === 'y' ? 'checked' : '' ?> data-type="scm" data-mode="checkbox"/> | |
| </span> | |
| <span><span class="ncua-radio-field__text">공급사</span></span> | |
| </label> | |
| </div> | |
| </td> | |
| </tr> | |
| <tr id="scmSelectRow" class="scm-select-row"> | |
| <th><div>공급사 선택</div></th> | |
| <td> | |
| <div class="scm-select-wrap"> | |
| <div id="ncua-combo-box-layer" class="ncua-input-width-320 scm-combobox-layer"></div> | |
| <div id="scmLayer" class="ncua-flex ncua-flex-wrap ncua-gap-4 selected-tag-list" style="display:none"></div> | |
| </div> | |
| </td> | |
| </tr> | |
| <?php endif; ?> | |
| <tr> | |
| <th><div>주문 구분</div></th> | |
| <td> | |
| <div class="ncua-radio-field-group search-radio-group"> | |
| <label class="ncua-radio-field ncua-radio-field--xs has-text"> | |
| <span class="ncua-radio-input ncua-radio-input--xs ncua-radio-field__input"> | |
| <input type="radio" name="memberType" value="" <?= $search['memberType'] === '' ? 'checked' : '' ?>/> | |
| </span> | |
| <span class="ncua-radio-field__text">전체</span> | |
| </label> | |
| <label class="ncua-radio-field ncua-radio-field--xs has-text"> | |
| <span class="ncua-radio-input ncua-radio-input--xs ncua-radio-field__input"> | |
| <input type="radio" name="memberType" value="withdrawn" <?= $search['memberType'] === 'withdrawn' ? 'checked' : '' ?>/> | |
| </span> | |
| <span class="ncua-radio-field__text">탈퇴회원 주문</span> | |
| </label> | |
| <label class="ncua-radio-field ncua-radio-field--xs has-text"> | |
| <span class="ncua-radio-input ncua-radio-input--xs ncua-radio-field__input"> | |
| <input type="radio" name="memberType" value="dormant" <?= $search['memberType'] === 'dormant' ? 'checked' : '' ?>/> | |
| </span> | |
| <span class="ncua-radio-field__text">휴면회원 주문</span> | |
| </label> | |
| </div> | |
| </td> | |
| </tr> | |
| <tr> | |
| <th><div>주문일</div></th> | |
| <td> | |
| <div id="datepicker-container"></div> | |
| </td> | |
| </tr> | |
| </tbody> | |
| </table> | |
| </div> | |
| <p class="ncua-btn-group ncua-align-right search-toolbar"> | |
| <button type="button" class="ncua-btn ncua-btn--xs has-underline ncua-btn--text js-btn-reset"> | |
| <span class="ncua-btn__label">초기화</span> | |
| </button> | |
| <button type="submit" class="ncua-btn ncua-btn--xs ncua-btn--secondary"> | |
| <span class="ncua-btn__label">검색</span> | |
| </button> | |
| </p> | |
| </form> | |
| <div class="ncua-search-result"> | |
| <div class="ncua-search-result__summary"> | |
| <p class="ncua-search-result__summary-count"> | |
| 검색 <strong><?= number_format($cnt['search'] ?? 0) ?></strong>개 / 전체 <strong><?= number_format($cnt['total'] ?? 0) ?></strong>개 | |
| </p> | |
| </div> | |
| <div class="ncua-search-result__content"> | |
| <div class="ncua-search-result__actions"> | |
| <div class="ncua-search-result__button-group"></div> | |
| <div class="ncua-search-result__actions-select"> | |
| <span class="ncua-select ncua-select--xs"> | |
| <span class="ncua-select__content"> | |
| <select id="pageSize" class="ncua-select__tag"> | |
| <?php | |
| $pageSizes = [10, 20, 30, 40, 50, 60, 70, 80, 90, 100, 200, 300, 500]; | |
| $currentPageSize = (int) ($pageSize ?? 0); | |
| foreach ($pageSizes as $size) { | |
| $selected = $currentPageSize === $size ? 'selected' : ''; | |
| echo "<option value=\"{$size}\" {$selected}>{$size}개씩 보기</option>"; | |
| } | |
| ?> | |
| </select> | |
| </span> | |
| </span> | |
| </div> | |
| </div> | |
| <div class="ncua-table ncua-table--horizontal"> | |
| <?php /* [보안] 검색결과 드래그/우클릭/선택 금지 */ ?> | |
| <table oncontextmenu="return false" ondragstart="return false" onselectstart="return false" style="-webkit-user-select:none;-ms-user-select:none;user-select:none;"> | |
| <colgroup> | |
| <col width="80px"/> | |
| <col width="120px"/> | |
| <?php if (empty($isProvider)): ?><col width="120px"/><?php endif; ?> | |
| <col width="120px"/> | |
| <col width="150px"/> | |
| <col/> | |
| <col/> | |
| </colgroup> | |
| <thead> | |
| <tr> | |
| <th><div>번호</div></th> | |
| <th><div>상점 구분</div></th> | |
| <?php if (empty($isProvider)): ?><th><div>공급사 구분</div></th><?php endif; ?> | |
| <th><div>주문 구분</div></th> | |
| <th><div>주문 번호</div></th> | |
| <th><div>주문자</div></th> | |
| <th><div>수령자</div></th> | |
| </tr> | |
| </thead> | |
| <tbody> | |
| <?php if (!empty($data['list'])): ?> | |
| <?php foreach ($data['list'] as $val): ?> | |
| <tr> | |
| <td><div><?= number_format($val['listNo']) ?></div></td> | |
| <td><div><?= $val['mallTypeStr'] ?? '-' ?></div></td> | |
| <?php if (empty($isProvider)): ?> | |
| <td> | |
| <div> | |
| <?= htmlspecialchars((string) ($val['scmNm'] ?? '본사')) ?> | |
| <?php if (!empty($val['scmSupplierNames'])): ?><br><?= nl2br(htmlspecialchars((string) $val['scmSupplierNames'])) ?><?php endif; ?> | |
| </div> | |
| </td> | |
| <?php endif; ?> | |
| <td><div><?= $val['memberTypeStr'] ?? '-' ?></div></td> | |
| <td> | |
| <div> | |
| <a href="#;" onclick="javascript:open_order_link('<?= $val['orderNo'] ?>', 'newTab', '<?= $isProvider ?>')" title="주문 상세"><?= $val['orderNo'] ?></a> | |
| </div> | |
| </td> | |
| <td> | |
| <div class="ncua-left-align"> | |
| 아이디 : <?= htmlspecialchars((string) ($val['memId'] ?? '-')) ?><br> | |
| 주문자명 : <?= htmlspecialchars((string) ($val['orderName'] ?? '-')) ?><br> | |
| 입금자명 : <?= htmlspecialchars((string) ($val['bankSender'] ?? '-')) ?><br> | |
| 주문자 휴대폰번호 : <?= htmlspecialchars((string) ($val['orderCellPhone'] ?? '-')) ?><br> | |
| 주문자 이메일 : <?= htmlspecialchars((string) ($val['orderEmail'] ?? '-')) ?> | |
| </div> | |
| </td> | |
| <td> | |
| <div class="ncua-left-align"> | |
| 수령자명 : <?= htmlspecialchars((string) ($val['receiverName'] ?? '-')) ?><br> | |
| 수령자 휴대폰번호 : <?= htmlspecialchars((string) ($val['receiverCellPhone'] ?? '-')) ?><br> | |
| <?php | |
| $zonecode = (string) ($val['receiverZonecode'] ?? ''); | |
| $addr = trim((string) ($val['receiverAddress'] ?? '') . ' ' . (string) ($val['receiverAddressSub'] ?? '')); | |
| $addrText = ($zonecode !== '' ? '(' . $zonecode . ') ' : '') . $addr; | |
| ?> | |
| 수령자 주소 : <?= htmlspecialchars($addrText) ?: '-' ?> | |
| </div> | |
| </td> | |
| </tr> | |
| <?php endforeach; ?> | |
| <?php else: ?> | |
| <tr> | |
| <td colspan="<?= empty($isProvider) ? 7 : 6 ?>"><div class="ncua-align-center">검색된 주문이 없습니다.</div></td> | |
| </tr> | |
| <?php endif; ?> | |
| </tbody> | |
| </table> | |
| </div> | |
| <div class="ncua-table-bottom"></div> | |
| </div> | |
| <div class="ncua-pagination"><?= $pagination ?? '' ?></div> | |
| </div> | |
| </section> | |
| </section> | |
| </article> | |
| <script> | |
| (() => { | |
| // 5년 이전 날짜 계산 (DatePicker minDate 제약 및 검증에 공통 사용) | |
| const fiveYearsAgo = new Date(); | |
| fiveYearsAgo.setFullYear(fiveYearsAgo.getFullYear() - 5); | |
| fiveYearsAgo.setHours(0, 0, 0, 0); | |
| // DatePicker 초기화 | |
| const datePicker = new ncua.DatePicker(document.querySelector('#datepicker-container'), { | |
| size: 'xs', | |
| buttons: [ | |
| { text: '오늘', period: 0, unit: 'days', isCurrent: false }, | |
| { text: '7일', period: 6, unit: 'days', isCurrent: true }, | |
| { text: '15일', period: 14, unit: 'days', isCurrent: false }, | |
| { text: '1개월', period: 29, unit: 'days', isCurrent: false }, | |
| { text: '3개월', period: 89, unit: 'days', isCurrent: false }, | |
| ], | |
| datePickerOptions: [ | |
| { | |
| element: 'start-date', | |
| attrName: 'orderDt[]', | |
| options: { defaultDate: '<?= htmlspecialchars($orderDt[0]) ?>', mode: 'single', static: true, dateFormat: 'Y-m-d', clickOpens: true, allowInput: true, locale: 'ko', minDate: fiveYearsAgo, maxDate: 'today' }, | |
| }, | |
| { | |
| element: 'end-date', | |
| attrName: 'orderDt[]', | |
| options: { defaultDate: '<?= htmlspecialchars($orderDt[1]) ?>', mode: 'single', static: true, dateFormat: 'Y-m-d', clickOpens: true, allowInput: true, locale: 'ko', minDate: fiveYearsAgo, maxDate: 'today' }, | |
| }, | |
| ], | |
| }); | |
| datePicker.setDate(["<?= htmlspecialchars($orderDt[0]) ?>", "<?= htmlspecialchars($orderDt[1]) ?>"]); | |
| // ------------------------------------------------------- | |
| // DatePicker 날짜 제약 검증 | |
| // - 출발일 > 종료일 불가 | |
| // - 5년 이전 날짜 설정 불가 (allowInput 직접 입력 우회 대비) | |
| // ------------------------------------------------------- | |
| let prevDates = datePicker.getDates(); | |
| document.querySelector('#datepicker-container').addEventListener('change', (e) => { | |
| if (!e.target.name?.includes('orderDt')) return; | |
| const dates = datePicker.getDates(); | |
| const startVal = dates[0]; | |
| const endVal = dates[1]; | |
| // 하나라도 비어 있으면 유효 상태로 저장 후 종료 | |
| if (!startVal || !endVal) { | |
| prevDates = dates; | |
| return; | |
| } | |
| const startDate = new Date(startVal); | |
| const endDate = new Date(endVal); | |
| // 출발일 > 종료일 차단 | |
| if (startDate > endDate) { | |
| const inputs = document.querySelectorAll('#datepicker-container input[name="orderDt[]"]'); | |
| const isStartChanged = e.target === inputs[0]; | |
| NCDSAlert({ | |
| message: isStartChanged | |
| ? '시작일자는 종료일자보다 이후일 수 없습니다.' | |
| : '종료일자는 시작일자보다 이전일 수 없습니다.', | |
| iconType: 'error', | |
| }); | |
| datePicker.setDate(prevDates); | |
| return; | |
| } | |
| prevDates = dates; | |
| }); | |
| // 공급사 선택 행 show/hide | |
| const scmSelectRow = document.getElementById('scmSelectRow'); | |
| const checkedScmFl = document.querySelector('.supply-radio-group input[name="scmFl"]:checked'); | |
| if (checkedScmFl?.value === 'y') { | |
| scmSelectRow.classList.remove('scm-select-row'); | |
| } | |
| document.querySelector('.supply-radio-group')?.addEventListener('change', (e) => { | |
| if (e.target.name === 'scmFl') { | |
| scmSelectRow.classList.toggle('scm-select-row', e.target.value !== 'y'); | |
| } | |
| }); | |
| // 공급사 콤보박스 초기화 | |
| const initSupplyComboBoxHandler = () => { | |
| if (typeof window.initSupplyComboBox === 'undefined') { | |
| setTimeout(initSupplyComboBoxHandler, 100); | |
| return; | |
| } | |
| const initData = []; | |
| <?php if ($search['scmFl'] === 'y' && !empty($search['scmNo'])): ?> | |
| <?php foreach ($search['scmNo'] as $k => $v): ?> | |
| initData.push({ id: <?= json_encode((string)$v) ?>, label: <?= json_encode($search['scmNoNm'][$k] ?? '') ?> }); | |
| <?php endforeach; ?> | |
| <?php endif; ?> | |
| const applySupplyComboBox = window.initSupplyComboBox({ | |
| scmLayerSelector: 'scmLayer', | |
| dataInputNm: 'scmNo', | |
| comboBoxLayerId: 'ncua-combo-box-layer', | |
| radioGroupClass: 'supply-radio-group', | |
| initData: initData, | |
| apiUrl: '../share/ncds/layer_scm.php', | |
| tagIdPrefix: 'info_scm', | |
| tagHiddenName: 'scmNoNm', | |
| }); | |
| window.applySupplyComboBox = applySupplyComboBox; | |
| }; | |
| initSupplyComboBoxHandler(); | |
| // ------------------------------------------------------- | |
| // 검색어 에러 표시 / 해제 헬퍼 | |
| // ------------------------------------------------------- | |
| const showSearchWordError = (input) => { | |
| const wrapper = input.closest('.ncua-input'); | |
| wrapper.classList.add('destructive'); | |
| if (window.NCDSValidator) NCDSValidator.addErrorIcon(input); | |
| let hint = wrapper.querySelector('.ncua-hint-text'); | |
| if (!hint) { | |
| hint = document.createElement('span'); | |
| hint.className = 'ncua-hint-text ncua-input__hint-text'; | |
| wrapper.appendChild(hint); | |
| } | |
| hint.classList.add('destructive'); | |
| hint.textContent = '검색어를 입력하세요.'; | |
| }; | |
| const clearSearchWordError = (input) => { | |
| const wrapper = input.closest('.ncua-input'); | |
| wrapper.classList.remove('destructive'); | |
| if (window.NCDSValidator) NCDSValidator.removeErrorIcon(input); | |
| const hint = wrapper.querySelector('.ncua-hint-text'); | |
| if (hint) hint.remove(); | |
| }; | |
| // 검색어 입력 시 실시간 에러 해제 | |
| const searchWordInput = document.querySelector('input[name="searchWord"]'); | |
| searchWordInput?.addEventListener('input', function () { | |
| if (this.value.trim()) clearSearchWordError(this); | |
| }); | |
| // ------------------------------------------------------- | |
| // 폼 제출 유효성 검사 | |
| // ------------------------------------------------------- | |
| const form = document.getElementById('frmSearchDormantMember'); | |
| form.addEventListener('submit', (e) => { | |
| e.preventDefault(); | |
| // 1. 검색어 미입력 검사 | |
| const searchInput = form.querySelector('input[name="searchWord"]'); | |
| if (!searchInput.value.trim()) { | |
| showSearchWordError(searchInput); | |
| searchInput.focus(); | |
| return; | |
| } | |
| clearSearchWordError(searchInput); | |
| // 2. 공급사 구분 '공급사' 선택 시 대상 공급사 미선택 검사 | |
| const scmFl = form.querySelector('input[name="scmFl"]:checked')?.value; | |
| if (scmFl === 'y' && form.querySelectorAll('input[name="scmNo[]"]').length === 0) { | |
| NCDSAlert({ message: '공급사를 선택해주세요.', iconType: 'error' }); | |
| return; | |
| } | |
| // 3. 날짜 유효성 검사 | |
| const dateInputs = form.querySelectorAll('input[name="orderDt[]"]'); | |
| const startVal = dateInputs[0]?.value; | |
| const endVal = dateInputs[1]?.value; | |
| if (startVal && endVal) { | |
| const startDate = new Date(startVal); | |
| const endDate = new Date(endVal); | |
| // 3개월(89일) 초과 검사 | |
| const diffDays = (endDate - startDate) / (1000 * 60 * 60 * 24); | |
| if (diffDays > 89) { | |
| NCDSAlert({ message: '3개월까지 검색하실 수 있습니다.', iconType: 'error' }); | |
| return; | |
| } | |
| // 최근 5년 이전 검사 (allowInput 우회 최종 방어) | |
| if (startDate < fiveYearsAgo) { | |
| NCDSAlert({ message: '최근 5년의 내역만 조회하실 수 있습니다.', iconType: 'error' }); | |
| return; | |
| } | |
| } | |
| // 유효성 통과 → 폼 제출 | |
| form.submit(); | |
| }); | |
| // ------------------------------------------------------- | |
| // pageSize 변경 시 폼 제출 | |
| // ------------------------------------------------------- | |
| document.getElementById('pageSize')?.addEventListener('change', function () { | |
| const pageSizeInput = document.createElement('input'); | |
| pageSizeInput.type = 'hidden'; | |
| pageSizeInput.name = 'pageSize'; | |
| pageSizeInput.value = this.value; | |
| form.appendChild(pageSizeInput); | |
| form.submit(); | |
| }); | |
| // ------------------------------------------------------- | |
| // 초기화 버튼 | |
| // ------------------------------------------------------- | |
| // native form.submit() 은 submit 이벤트를 건너뛰어 검색어 필수 검증을 우회하므로 페이지 재진입으로 되돌린다 | |
| document.querySelector('.js-btn-reset')?.addEventListener('click', () => { | |
| location.href = location.pathname; | |
| }); | |
| })(); | |
| </script> | |
변경 전order_print_customerReport.php
| <?php } // 상품코드 ?> | |
| <?php if($gridKey === 'receiverAddress'){ // 수령자 주소 ?> | |
| <?php if($data['useMultiShippingKey']){ ?> | |
| <?php if($rowMultiShipping === 0){ ?> | |
| <td <?= $orderMultiShippingRowSpan ?>> | |
| <?php if($val['receiverZonecode']){ echo "[".$val['receiverZonecode']."]"; } ?> | |
| <?php if($val['receiverZipcode']){ echo "(".$val['receiverZipcode'].")"; } ?> | |
| <br /> | |
| <?php if($val['receiverAddress']){ echo $val['receiverAddress']; } ?> | |
| <?php if($val['receiverAddressSub']){ echo " ".$val['receiverAddressSub']; } ?> | |
| </td> | |
| <?php } ?> | |
| <?php } else {?> | |
| <?php if($rowAll === 0){ ?> | |
| <td <?= $orderGoodsRowSpan ?>> | |
| <?php if($data['receiverZonecode']){ echo "[".$data['receiverZonecode']."]"; } ?> | |
| <?php if($data['receiverZipcode']){ echo "(".$data['receiverZipcode'].")"; } ?> | |
| <br /> | |
| <?php if($data['receiverAddress']){ echo $data['receiverAddress']; } ?> | |
| <?php if($data['receiverAddressSub']){ echo " ".$data['receiverAddressSub']; } ?> | |
| </td> | |
| <?php } ?> | |
| <?php } ?> | |
| <?php if (gd_isset($data['settle']['method']) == 'c') { ?> | |
| <tr> | |
| <th><?= __('카드사명'); ?></th> | |
| <td><?php echo gd_isset($data['pgSettleNm'][0]); ?></td> | |
| </tr> | |
| <?php if (gd_isset($data['pgSettleCd'][0]) != '' && gd_isset($data['pgSettleCd'][0]) != '0' && gd_isset($data['pgSettleCd'][0]) != '00') { ?> | |
| <tr> | |
| <?php } else if (gd_isset($data['settle']['method']) == 'v') { ?> | |
| <tr> | |
| <th><?= __('입금계좌'); ?></th> | |
| <td><?php echo gd_isset($data['pgSettleNm'][0]); ?> / <?php echo gd_isset($data['pgSettleNm'][1]); ?> / <?php echo gd_isset($data['pgSettleNm'][2]); ?></td> | |
| </tr> | |
| <tr> | |
| <th><?= __('입금기한'); ?></th> | |
| </tr> | |
| <tr> | |
| <th><?= __('배송지'); ?></th> | |
| <td colspan="3"> | |
| <div><?php echo gd_isset($multiShippingData['receiverAddress']); ?> <?php echo gd_isset($multiShippingData['receiverAddressSub']); ?></div> | |
| </td> | |
| </tr> | |
| <tr> | |
| </tr> | |
| <tr> | |
| <th><?= __('배송지'); ?></th> | |
| <td colspan="3"> | |
| <?php if (empty($data['isDefaultMall']) === true) { ?> | |
| <div><?php echo gd_isset($data['receiverAddressSub']); ?>, <?php echo gd_isset($data['receiverAddress']); ?>, <?php echo gd_isset($data['receiverState']); ?>, <?php echo gd_isset($data['receiverCity']); ?>, <?php echo gd_isset($data['receiverCountry']); ?></div> | |
| <?php } else { ?> | |
| <div><?php echo gd_isset($data['receiverAddress']); ?> <?php echo gd_isset($data['receiverAddressSub']); ?></div> | |
| <?php } ?> | |
| </td> | |
| </tr> | |
변경 후order_print_customerReport.php
| <?php } // 상품코드 ?> | |
| <?php if($gridKey === 'receiverAddress'){ // 수령자 주소 ?> | |
| <?php /* 주소 구성요소가 각각 '-' 로 치환돼 하이픈이 반복되므로 칸 전체를 단일 '-' 로 표시 */ ?> | |
| <?php if($data['useMultiShippingKey']){ ?> | |
| <?php if($rowMultiShipping === 0){ ?> | |
| <td <?= $orderMultiShippingRowSpan ?>> | |
| <?php if(!empty($data['orderMaskLabel'])){ echo $maskChar; } else { ?> | |
| <?php if($val['receiverZonecode']){ echo "[".$val['receiverZonecode']."]"; } ?> | |
| <?php if($val['receiverZipcode']){ echo "(".$val['receiverZipcode'].")"; } ?> | |
| <br /> | |
| <?php if($val['receiverAddress']){ echo $val['receiverAddress']; } ?> | |
| <?php if($val['receiverAddressSub']){ echo " ".$val['receiverAddressSub']; } ?> | |
| <?php } ?> | |
| </td> | |
| <?php } ?> | |
| <?php } else {?> | |
| <?php if($rowAll === 0){ ?> | |
| <td <?= $orderGoodsRowSpan ?>> | |
| <?php if(!empty($data['orderMaskLabel'])){ echo $maskChar; } else { ?> | |
| <?php if($data['receiverZonecode']){ echo "[".$data['receiverZonecode']."]"; } ?> | |
| <?php if($data['receiverZipcode']){ echo "(".$data['receiverZipcode'].")"; } ?> | |
| <br /> | |
| <?php if($data['receiverAddress']){ echo $data['receiverAddress']; } ?> | |
| <?php if($data['receiverAddressSub']){ echo " ".$data['receiverAddressSub']; } ?> | |
| <?php } ?> | |
| </td> | |
| <?php } ?> | |
| <?php } ?> | |
| <?php if (gd_isset($data['settle']['method']) == 'c') { ?> | |
| <tr> | |
| <th><?= __('카드사명'); ?></th> | |
| <?php /* pgSettleNm 은 카드사명·이체은행·가상계좌가 공유하는 키라 마스킹 대상 칸에서만 치환한다 */ ?> | |
| <td><?php if (!empty($data['orderMaskLabel'])) { echo $maskChar; } else { echo gd_isset($data['pgSettleNm'][0]); } ?></td> | |
| </tr> | |
| <?php if (gd_isset($data['pgSettleCd'][0]) != '' && gd_isset($data['pgSettleCd'][0]) != '0' && gd_isset($data['pgSettleCd'][0]) != '00') { ?> | |
| <tr> | |
| <?php } else if (gd_isset($data['settle']['method']) == 'v') { ?> | |
| <tr> | |
| <th><?= __('입금계좌'); ?></th> | |
| <?php /* 은행·계좌·예금주 3칸이 각각 '-' 로 치환돼 하이픈이 반복되므로 칸 전체를 단일 '-' 로 표시 */ ?> | |
| <td><?php if (!empty($data['orderMaskLabel'])) { echo $maskChar; } else { ?><?= gd_isset($data['pgSettleNm'][0]) ?> / <?= gd_isset($data['pgSettleNm'][1]) ?> / <?= gd_isset($data['pgSettleNm'][2]) ?><?php } ?></td> | |
| </tr> | |
| <tr> | |
| <th><?= __('입금기한'); ?></th> | |
| </tr> | |
| <tr> | |
| <th><?= __('배송지'); ?></th> | |
| <?php /* 주소 구성요소가 각각 '-' 로 치환돼 하이픈이 반복되므로 칸 전체를 단일 '-' 로 표시 */ ?> | |
| <td colspan="3"> | |
| <?php if (!empty($data['orderMaskLabel'])) { echo $maskChar; } else { ?> | |
| <div><?php echo gd_isset($multiShippingData['receiverAddress']); ?> <?php echo gd_isset($multiShippingData['receiverAddressSub']); ?></div> | |
| <?php } ?> | |
| </td> | |
| </tr> | |
| <tr> | |
| </tr> | |
| <tr> | |
| <th><?= __('배송지'); ?></th> | |
| <?php /* 주소 구성요소가 각각 '-' 로 치환돼 하이픈이 반복되므로 칸 전체를 단일 '-' 로 표시 */ ?> | |
| <td colspan="3"> | |
| <?php if (!empty($data['orderMaskLabel'])) { echo $maskChar; } else { ?> | |
| <?php if (empty($data['isDefaultMall'])) { ?> | |
| <div><?= gd_isset($data['receiverAddressSub']) ?>, <?= gd_isset($data['receiverAddress']) ?>, <?= gd_isset($data['receiverState']) ?>, <?= gd_isset($data['receiverCity']) ?>, <?= gd_isset($data['receiverCountry']) ?></div> | |
| <?php } else { ?> | |
| <div><?= gd_isset($data['receiverAddress']) ?> <?= gd_isset($data['receiverAddressSub']) ?></div> | |
| <?php } ?> | |
| <?php } ?> | |
| </td> | |
| </tr> | |
변경 전order_print_report.php
| <?php } //상품코드?> | |
| <?php if($gridKey === 'receiverAddress'){ //수령자 주소?> | |
| <?php if($data['useMultiShippingKey']){ ?> | |
| <?php if($rowMultiShipping === 0){ ?> | |
| <td <?= $orderMultiShippingRowSpan ?>> | |
| <?php if($val['receiverZonecode']){ echo "[".$val['receiverZonecode']."]"; } ?> | |
| <?php if($val['receiverZipcode']){ echo "(".$val['receiverZipcode'].")"; } ?> | |
| <br /> | |
| <?php if($val['receiverAddress']){ echo $val['receiverAddress']; } ?> | |
| <?php if($val['receiverAddressSub']){ echo " ".$val['receiverAddressSub']; } ?> | |
| </td> | |
| <?php } ?> | |
| <?php } else {?> | |
| <?php if($rowAll === 0){ ?> | |
| <td <?= $orderGoodsRowSpan ?>> | |
| <?php if($data['receiverZonecode']){ echo "[".$data['receiverZonecode']."]"; } ?> | |
| <?php if($data['receiverZipcode']){ echo "(".$data['receiverZipcode'].")"; } ?> | |
| <br /> | |
| <?php if($data['receiverAddress']){ echo $data['receiverAddress']; } ?> | |
| <?php if($data['receiverAddressSub']){ echo " ".$data['receiverAddressSub']; } ?> | |
| </td> | |
| <?php } ?> | |
| <?php } ?> | |
| <?php if (gd_isset($data['settle']['method']) == 'c') { ?> | |
| <tr> | |
| <th>카드사명</th> | |
| <td><?php echo gd_isset($data['pgSettleNm'][0]); ?></td> | |
| </tr> | |
| <?php if (gd_isset($data['pgSettleCd'][0]) != '' && gd_isset($data['pgSettleCd'][0]) != '0' && gd_isset($data['pgSettleCd'][0]) != '00') { ?> | |
| <tr> | |
| <?php } else if (gd_isset($data['settle']['method']) == 'v') { ?> | |
| <tr> | |
| <th>입금계좌</th> | |
| <td><?php echo gd_isset($data['pgSettleNm'][0]); ?> / <?php echo gd_isset($data['pgSettleNm'][1]); ?> / <?php echo gd_isset($data['pgSettleNm'][2]); ?></td> | |
| </tr> | |
| <tr> | |
| <th>입금기한</th> | |
| <?php if (empty($data['memInfo']) === true) { ?> | |
| <?php if (empty($data['memNo']) === true) { ?> | |
| / <span class="text-primary">비회원</span> | |
| <?php } else { ?> | |
| / <span class="text-primary">탈퇴회원</span> | |
| <?php } ?> | |
| <?php } else { ?> | |
| / <span class="text-primary"><?= $data['memInfo']['memId'] ?></span> | |
| </tr> | |
| <tr> | |
| <th>주소</th> | |
| <td> | |
| <div><?php echo gd_isset($data['receiverZonecode']); ?></div> | |
| <?php if (empty($data['isDefaultMall']) === true) { ?> | |
| <div><?php echo gd_isset($data['receiverAddressSub']); ?>, <?php echo gd_isset($data['receiverAddress']); ?>, <?php echo gd_isset($data['receiverState']); ?>, <?php echo gd_isset($data['receiverCity']); ?>, <?php echo gd_isset($data['receiverCountry']); ?></div> | |
| <?php } else { ?> | |
| <div><?php echo gd_isset($data['receiverAddress']); ?> <?php echo gd_isset($data['receiverAddressSub']); ?></div> | |
| <?php } ?> | |
| </td> | |
| </tr> | |
| </tr> | |
| <tr> | |
| <th>주소</th> | |
| <td> | |
| <div><?php echo gd_isset($multiShippingData['receiverZonecode']); ?></div> | |
| <div><?php echo gd_isset($multiShippingData['receiverAddress']); ?> <?php echo gd_isset($multiShippingData['receiverAddressSub']); ?></div> | |
| </td> | |
| </tr> | |
| <tr> | |
변경 후order_print_report.php
| <?php } //상품코드?> | |
| <?php if($gridKey === 'receiverAddress'){ //수령자 주소?> | |
| <?php /* 주소 구성요소가 각각 '-' 로 치환돼 하이픈이 반복되므로 칸 전체를 단일 '-' 로 표시 */ ?> | |
| <?php if($data['useMultiShippingKey']){ ?> | |
| <?php if($rowMultiShipping === 0){ ?> | |
| <td <?= $orderMultiShippingRowSpan ?>> | |
| <?php if(!empty($data['orderMaskLabel'])){ echo $maskChar; } else { ?> | |
| <?php if($val['receiverZonecode']){ echo "[".$val['receiverZonecode']."]"; } ?> | |
| <?php if($val['receiverZipcode']){ echo "(".$val['receiverZipcode'].")"; } ?> | |
| <br /> | |
| <?php if($val['receiverAddress']){ echo $val['receiverAddress']; } ?> | |
| <?php if($val['receiverAddressSub']){ echo " ".$val['receiverAddressSub']; } ?> | |
| <?php } ?> | |
| </td> | |
| <?php } ?> | |
| <?php } else {?> | |
| <?php if($rowAll === 0){ ?> | |
| <td <?= $orderGoodsRowSpan ?>> | |
| <?php if(!empty($data['orderMaskLabel'])){ echo $maskChar; } else { ?> | |
| <?php if($data['receiverZonecode']){ echo "[".$data['receiverZonecode']."]"; } ?> | |
| <?php if($data['receiverZipcode']){ echo "(".$data['receiverZipcode'].")"; } ?> | |
| <br /> | |
| <?php if($data['receiverAddress']){ echo $data['receiverAddress']; } ?> | |
| <?php if($data['receiverAddressSub']){ echo " ".$data['receiverAddressSub']; } ?> | |
| <?php } ?> | |
| </td> | |
| <?php } ?> | |
| <?php } ?> | |
| <?php if (gd_isset($data['settle']['method']) == 'c') { ?> | |
| <tr> | |
| <th>카드사명</th> | |
| <?php /* pgSettleNm 은 카드사명·이체은행·가상계좌가 공유하는 키라 마스킹 대상 칸에서만 치환한다 */ ?> | |
| <td><?php if (!empty($data['orderMaskLabel'])) { echo $maskChar; } else { echo gd_isset($data['pgSettleNm'][0]); } ?></td> | |
| </tr> | |
| <?php if (gd_isset($data['pgSettleCd'][0]) != '' && gd_isset($data['pgSettleCd'][0]) != '0' && gd_isset($data['pgSettleCd'][0]) != '00') { ?> | |
| <tr> | |
| <?php } else if (gd_isset($data['settle']['method']) == 'v') { ?> | |
| <tr> | |
| <th>입금계좌</th> | |
| <?php /* 은행·계좌·예금주 3칸이 각각 '-' 로 치환돼 하이픈이 반복되므로 칸 전체를 단일 '-' 로 표시 */ ?> | |
| <td><?php if (!empty($data['orderMaskLabel'])) { echo $maskChar; } else { ?><?= gd_isset($data['pgSettleNm'][0]) ?> / <?= gd_isset($data['pgSettleNm'][1]) ?> / <?= gd_isset($data['pgSettleNm'][2]) ?><?php } ?></td> | |
| </tr> | |
| <tr> | |
| <th>입금기한</th> | |
| <?php if (empty($data['memInfo']) === true) { ?> | |
| <?php if (empty($data['memNo']) === true) { ?> | |
| / <span class="text-primary">비회원</span> | |
| <?php } ?> | |
| <?php } else { ?> | |
| / <span class="text-primary"><?= $data['memInfo']['memId'] ?></span> | |
| </tr> | |
| <tr> | |
| <th>주소</th> | |
| <?php /* 주소 구성요소가 각각 '-' 로 치환돼 하이픈이 반복되므로 칸 전체를 단일 '-' 로 표시 */ ?> | |
| <td> | |
| <?php if (!empty($data['orderMaskLabel'])) { echo $maskChar; } else { ?> | |
| <div><?= gd_isset($data['receiverZonecode']) ?></div> | |
| <?php if (empty($data['isDefaultMall'])) { ?> | |
| <div><?= gd_isset($data['receiverAddressSub']) ?>, <?= gd_isset($data['receiverAddress']) ?>, <?= gd_isset($data['receiverState']) ?>, <?= gd_isset($data['receiverCity']) ?>, <?= gd_isset($data['receiverCountry']) ?></div> | |
| <?php } else { ?> | |
| <div><?= gd_isset($data['receiverAddress']) ?> <?= gd_isset($data['receiverAddressSub']) ?></div> | |
| <?php } ?> | |
| <?php } ?> | |
| </td> | |
| </tr> | |
| </tr> | |
| <tr> | |
| <th>주소</th> | |
| <?php /* 주소 구성요소가 각각 '-' 로 치환돼 하이픈이 반복되므로 칸 전체를 단일 '-' 로 표시 */ ?> | |
| <td> | |
| <?php if (!empty($data['orderMaskLabel'])) { echo $maskChar; } else { ?> | |
| <div><?= gd_isset($multiShippingData['receiverZonecode']) ?></div> | |
| <div><?= gd_isset($multiShippingData['receiverAddress']) ?> <?= gd_isset($multiShippingData['receiverAddressSub']) ?></div> | |
| <?php } ?> | |
| </td> | |
| </tr> | |
| <tr> | |
변경 전order_print_taxInvoice.php
| </tr> | |
| <tr height="38" align="center"> | |
| <td style="border-width: 0 1px 1px 0px;">사 업 장<br>소 재 지 </td> | |
| <td colspan="3" style="padding: 0 6px; border-bottom-width: 1px;" align="left"><?=$val['taxAddress']?> <?=$val['taxAddressSub']?></td> | |
| </tr> | |
| <tr height="38" align="center"> | |
| <td style="border-right-width: 1px;">업 태</td> | |
변경 후order_print_taxInvoice.php
| </tr> | |
| <tr height="38" align="center"> | |
| <td style="border-width: 0 1px 1px 0px;">사 업 장<br>소 재 지 </td> | |
| <?php /* 소재지 기본·상세가 각각 '-' 로 치환돼 하이픈이 반복되므로 칸 전체를 단일 '-' 로 표시 */ ?> | |
| <td colspan="3" style="padding: 0 6px; border-bottom-width: 1px;" align="left"><?php if (!empty($val['orderMaskLabel'])) { echo $maskChar; } else { ?><?=$val['taxAddress']?> <?=$val['taxAddressSub']?><?php } ?></td> | |
| </tr> | |
| <tr height="38" align="center"> | |
| <td style="border-right-width: 1px;">업 태</td> | |
변경 전order_view.php
| if($data['orderChannelFl'] == 'naverpay' ) { | |
| $claimElementDisabled = 'disabled'; | |
| } | |
| if (empty($data['gift']) === false) { | |
| ?> | |
| <table class="table table-cols"> | |
| <div class="table-title gd-help-manual"> | |
| <div class="flo-left">주문자 정보</div> | |
| <div class="flo-right"> | |
| <button type="button" class="btn btn-red btn-sm js-orderInfoBtn">정보수정</button> | |
| <button type="button" class="btn btn-red-box btn-sm js-orderInfoBtnSave js-orderViewInfoSave display-none" data-submit-mode="modifyOrderInfo">저장</button> | |
| </div> | |
| </div> | |
| ?> | |
| </div> | |
| <div class="flo-right"> | |
| <button type="button" class="btn btn-red btn-sm js-receiverInfoBtn">정보수정</button> | |
| <button type="button" class="btn btn-red-box btn-sm js-receiverInfoBtnSave js-orderViewInfoSave display-none" data-submit-mode="modifyReceiverInfo" data-order-info-sno="<?=$infoSno?>" data-use-safenumber-fl="<?=$data['receiverUseSafeNumberFl'];?>">저장</button> | |
| </div> | |
| </div> | |
| $data = gd_array_merge((array)$data, (array)$multiShippingData); | |
| $data['receiverCellPhone'] = explode("-", $data['receiverCellPhone']); | |
| $data['receiverPhone'] = explode("-", $data['receiverPhone']); | |
| $data['infoSno'] = $multiShippingData['sno']; | |
| ?> | |
| <?php if($multiShippingIndex === 1 || $multiShippingIndex%2 != 0){ ?><div class="row"><div class="col-xs-12"><?php } ?> | |
| 수령자 정보 - 추가 배송지<?=(int)$multiShippingData['orderInfoCd']-1?> | |
| </div> | |
| <div class="flo-right"> | |
| <button type="button" class="btn btn-red btn-sm js-receiverInfoBtn">정보수정</button> | |
| <button type="button" class="btn btn-red-box btn-sm js-receiverInfoBtnSave js-orderViewInfoSave display-none" data-submit-mode="modifyReceiverInfo" data-order-info-sno="<?=$multiShippingData['sno']?>" data-use-safenumber-fl="<?=$data['receiverUseSafeNumberFl'];?>">저장</button> | |
| </div> | |
| </div> | |
변경 후order_view.php
| if($data['orderChannelFl'] == 'naverpay' ) { | |
| $claimElementDisabled = 'disabled'; | |
| } | |
| // 분리보관(탈퇴/휴면) 주문은 개인정보를 되살려 고칠 수 없으므로 정보수정을 막는다 | |
| $withdrawnInfoDisabled = $orderMaskLabel !== null ? 'disabled' : ''; | |
| if (empty($data['gift']) === false) { | |
| ?> | |
| <table class="table table-cols"> | |
| <div class="table-title gd-help-manual"> | |
| <div class="flo-left">주문자 정보</div> | |
| <div class="flo-right"> | |
| <button type="button" class="btn btn-red btn-sm js-orderInfoBtn" <?= $withdrawnInfoDisabled ?>>정보수정</button> | |
| <button type="button" class="btn btn-red-box btn-sm js-orderInfoBtnSave js-orderViewInfoSave display-none" data-submit-mode="modifyOrderInfo">저장</button> | |
| </div> | |
| </div> | |
| ?> | |
| </div> | |
| <div class="flo-right"> | |
| <button type="button" class="btn btn-red btn-sm js-receiverInfoBtn" <?= $withdrawnInfoDisabled ?>>정보수정</button> | |
| <button type="button" class="btn btn-red-box btn-sm js-receiverInfoBtnSave js-orderViewInfoSave display-none" data-submit-mode="modifyReceiverInfo" data-order-info-sno="<?=$infoSno?>" data-use-safenumber-fl="<?=$data['receiverUseSafeNumberFl'];?>">저장</button> | |
| </div> | |
| </div> | |
| $data = gd_array_merge((array)$data, (array)$multiShippingData); | |
| $data['receiverCellPhone'] = explode("-", $data['receiverCellPhone']); | |
| $data['receiverPhone'] = explode("-", $data['receiverPhone']); | |
| // 마스킹 주문의 분리 원본 키는 배송지 행에서 문자열로 병합되므로 기능용 배열로 되돌린다 | |
| if (isset($data['receiverCellPhoneSeparationOrigin']) && is_string($data['receiverCellPhoneSeparationOrigin'])) { | |
| $data['receiverCellPhoneSeparationOrigin'] = explode("-", $data['receiverCellPhoneSeparationOrigin']); | |
| } | |
| if (isset($data['receiverPhoneSeparationOrigin']) && is_string($data['receiverPhoneSeparationOrigin'])) { | |
| $data['receiverPhoneSeparationOrigin'] = explode("-", $data['receiverPhoneSeparationOrigin']); | |
| } | |
| $data['infoSno'] = $multiShippingData['sno']; | |
| ?> | |
| <?php if($multiShippingIndex === 1 || $multiShippingIndex%2 != 0){ ?><div class="row"><div class="col-xs-12"><?php } ?> | |
| 수령자 정보 - 추가 배송지<?=(int)$multiShippingData['orderInfoCd']-1?> | |
| </div> | |
| <div class="flo-right"> | |
| <button type="button" class="btn btn-red btn-sm js-receiverInfoBtn" <?= $withdrawnInfoDisabled ?>>정보수정</button> | |
| <button type="button" class="btn btn-red-box btn-sm js-receiverInfoBtnSave js-orderViewInfoSave display-none" data-submit-mode="modifyReceiverInfo" data-order-info-sno="<?=$multiShippingData['sno']?>" data-use-safenumber-fl="<?=$data['receiverUseSafeNumberFl'];?>">저장</button> | |
| </div> | |
| </div> | |
변경 전popup_order_cash_receipt_reissue.php
| <input type="hidden" name="popupMode" value="y"> | |
| <input type="hidden" name="issueMode" value="a"> | |
| <input type="hidden" name="orderNo" value="<?=$data['orderNo'];?>"> | |
| <input type="hidden" name="requestNm" value="<?=$data['requestNm'];?>"> | |
| <input type="hidden" name="requestGoodsNm" value="<?=$data['requestGoodsNm'];?>"> | |
| <input type="hidden" name="requestEmail" value="<?=$data['requestEmail'];?>"> | |
| <input type="hidden" name="requestCellPhone" value="<?=$data['requestCellPhone'];?>"> | |
| <input type="hidden" name="useFl" value="<?=$data['useFl'];?>"> | |
| <input type="hidden" name="certFl" value="<?=$data['certFl'];?>"> | |
| <input type="hidden" name="certNo" value="<?=$certNo;?>"> | |
변경 후popup_order_cash_receipt_reissue.php
| <input type="hidden" name="popupMode" value="y"> | |
| <input type="hidden" name="issueMode" value="a"> | |
| <input type="hidden" name="orderNo" value="<?=$data['orderNo'];?>"> | |
| <?php /* 분리 원본 — 폼 전송값은 '-' 가 아니라 실제 값이어야 한다 */ ?> | |
| <input type="hidden" name="requestNm" value="<?= isset($data['requestNmSeparationOrigin']) ? $data['requestNmSeparationOrigin'] : $data['requestNm']; ?>"> | |
| <input type="hidden" name="requestGoodsNm" value="<?=$data['requestGoodsNm'];?>"> | |
| <input type="hidden" name="requestEmail" value="<?= isset($data['requestEmailSeparationOrigin']) ? $data['requestEmailSeparationOrigin'] : $data['requestEmail']; ?>"> | |
| <input type="hidden" name="requestCellPhone" value="<?= isset($data['requestCellPhoneSeparationOrigin']) ? $data['requestCellPhoneSeparationOrigin'] : $data['requestCellPhone']; ?>"> | |
| <input type="hidden" name="useFl" value="<?=$data['useFl'];?>"> | |
| <input type="hidden" name="certFl" value="<?=$data['certFl'];?>"> | |
| <input type="hidden" name="certNo" value="<?=$certNo;?>"> | |
변경 전popup_order_packet.php
| <td class="center"> | |
| <div onclick="javascript:order_view_popup('<?=$data['orderNo']?>', '<?=$isProvider?>');" class="hand" style="color:#117efa;"><?=$data['orderNo']?></div> | |
| <?php if ($packetAbleFl === false) { ?> | |
| <div><button type="button" class="btn btn-black btn-sm js-packet-receiver-info" data-order-no="<?=$data['orderNo']?>"/>수령자 정보변경</button></div> | |
| <?php } ?> | |
| </td> | |
| <td class="center"> | |
| } | |
| ?> | |
| </td> | |
| <td class="center"><?=$data['receiverName']?></td> | |
| <td class="center"> | |
| <div><?php echo (gd_count($data['receiverPhone']) > 0) ? gd_implode("-", $data['receiverPhone']) : '-'; ?></div> | |
| <div><?php echo (gd_count($data['receiverCellPhone']) > 0) ? gd_implode("-", $data['receiverCellPhone']) : '-'; ?></div> | |
| </td> | |
| <td class="center"> | |
| <?php if (empty($data['isDefaultMall']) === true) { ?> | |
| (<?=$data['receiverZonecode']?>) <?=$data['receiverAddressSub']?> <?=$data['receiverState']?> <?=$data['receiverCity']?> <?=$data['receiverAddress']?> <?=$data['receiverCountry']?> | |
| <?php } else { ?> | |
| (<?=$data['receiverZonecode']?>) <?=$data['receiverAddress']?> <?=$data['receiverAddressSub']?> | |
변경 후popup_order_packet.php
| <td class="center"> | |
| <div onclick="javascript:order_view_popup('<?=$data['orderNo']?>', '<?=$isProvider?>');" class="hand" style="color:#117efa;"><?=$data['orderNo']?></div> | |
| <?php if ($packetAbleFl === false) { ?> | |
| <div><button type="button" class="btn btn-black btn-sm js-packet-receiver-info" data-order-no="<?=$data['orderNo']?>" <?= isset($withdrawnMaskLabels[$data['orderNo']]) ? 'disabled' : '' ?>/>수령자 정보변경</button></div> | |
| <?php } ?> | |
| </td> | |
| <td class="center"> | |
| } | |
| ?> | |
| </td> | |
| <td class="center"><?= isset($withdrawnMaskLabels[$data['orderNo']]) ? $maskChar : $data['receiverName'] ?></td> | |
| <td class="center"> | |
| <?php if (isset($withdrawnMaskLabels[$data['orderNo']])) { ?> | |
| <div><?= $maskChar ?></div> | |
| <?php } else { ?> | |
| <div><?php echo (gd_count($data['receiverPhone']) > 0) ? gd_implode("-", $data['receiverPhone']) : '-'; ?></div> | |
| <div><?php echo (gd_count($data['receiverCellPhone']) > 0) ? gd_implode("-", $data['receiverCellPhone']) : '-'; ?></div> | |
| <?php } ?> | |
| </td> | |
| <td class="center"> | |
| <?php if (isset($withdrawnMaskLabels[$data['orderNo']])) { ?> | |
| <?= $maskChar ?> | |
| <?php } else if (empty($data['isDefaultMall']) === true) { ?> | |
| (<?=$data['receiverZonecode']?>) <?=$data['receiverAddressSub']?> <?=$data['receiverState']?> <?=$data['receiverCity']?> <?=$data['receiverAddress']?> <?=$data['receiverCountry']?> | |
| <?php } else { ?> | |
| (<?=$data['receiverZonecode']?>) <?=$data['receiverAddress']?> <?=$data['receiverAddressSub']?> | |
변경 전post_issue.php
| <?php if (!$val['memNo']) { ?> | |
| <?php if (!$val['memNoCheck']) { ?> | |
| <span class="font-kor">(비회원)</span> | |
| <?php } else { ?> | |
| <span class="font-kor">(탈퇴회원)</span> | |
| <?php } ?> | |
| <?php } else { ?> | |
변경 후post_issue.php
| <?php if (!$val['memNo']) { ?> | |
| <?php if (!$val['memNoCheck']) { ?> | |
| <span class="font-kor">(비회원)</span> | |
| <?php } elseif (empty($data[$orderNo]['orderMaskLabel'])) { ?> | |
| <span class="font-kor">(탈퇴회원)</span> | |
| <?php } ?> | |
| <?php } else { ?> | |
변경 전post_reserve.php
| <?php if (!$val['memNo']) { ?> | |
| <?php if (!$val['memNoCheck']) { ?> | |
| <span class="font-kor">(비회원)</span> | |
| <?php } else { ?> | |
| <span class="font-kor">(탈퇴회원)</span> | |
| <?php } ?> | |
| <?php } else { ?> | |
변경 후post_reserve.php
| <?php if (!$val['memNo']) { ?> | |
| <?php if (!$val['memNoCheck']) { ?> | |
| <span class="font-kor">(비회원)</span> | |
| <?php } elseif (empty($data[$orderNo]['orderMaskLabel'])) { ?> | |
| <span class="font-kor">(탈퇴회원)</span> | |
| <?php } ?> | |
| <?php } else { ?> | |
변경 전refund_do.php
| <tr id="refundBank" class="display-none"> | |
| <th>환불 계좌정보</th> | |
| <td class="form-inline" colspan="5"> | |
| <?php if ($statusFl) { ?> | |
| <?= gd_select_box(null, 'info[refundBankName]', $bankNm, null, $handleData['refundBankName'], '= 은행 선택 =') ?> | |
| <label class="control-label">계좌번호 :</label> | |
| <input type="text" name="info[refundAccountNumber]" value="<?= $handleData['refundAccountNumber'] ?>" class="form-control width-lg js-number" maxlength="30"/> | |
변경 후refund_do.php
| <tr id="refundBank" class="display-none"> | |
| <th>환불 계좌정보</th> | |
| <td class="form-inline" colspan="5"> | |
| <?php | |
| // 분리보관 주문은 수정 폼에서도 계좌를 노출·수정하지 않는다. PG환불에 필요한 계좌는 환불완료 처리 시 서버가 분리보관에서 복원한다 | |
| if (!empty($isRefundMaskTarget)) { | |
| echo $maskChar; | |
| } elseif ($statusFl) { ?> | |
| <?= gd_select_box(null, 'info[refundBankName]', $bankNm, null, $handleData['refundBankName'], '= 은행 선택 =') ?> | |
| <label class="control-label">계좌번호 :</label> | |
| <input type="text" name="info[refundAccountNumber]" value="<?= $handleData['refundAccountNumber'] ?>" class="form-control width-lg js-number" maxlength="30"/> | |
변경 전refund_do_new.php
| <tr id="refundBank" class="display-none"> | |
| <th>환불 계좌정보</th> | |
| <td class="form-inline" colspan="5"> | |
| <?php if ($statusFl) { ?> | |
| <?= gd_select_box(null, 'info[refundBankName]', $bankNm, null, $handleData['refundBankName'], '= 은행 선택 =') ?> | |
| <label class="control-label">계좌번호 :</label> | |
| <input type="text" name="info[refundAccountNumber]" value="<?= $handleData['refundAccountNumber'] ?>" class="form-control width-lg js-number" maxlength="30"/> | |
변경 후refund_do_new.php
| <tr id="refundBank" class="display-none"> | |
| <th>환불 계좌정보</th> | |
| <td class="form-inline" colspan="5"> | |
| <?php | |
| // 분리보관 주문은 수정 폼에서도 계좌를 노출·수정하지 않는다. PG환불에 필요한 계좌는 환불완료 처리 시 서버가 분리보관에서 복원한다 | |
| if (!empty($isRefundMaskTarget)) { | |
| echo $maskChar; | |
| } elseif ($statusFl) { ?> | |
| <?= gd_select_box(null, 'info[refundBankName]', $bankNm, null, $handleData['refundBankName'], '= 은행 선택 =') ?> | |
| <label class="control-label">계좌번호 :</label> | |
| <input type="text" name="info[refundAccountNumber]" value="<?= $handleData['refundAccountNumber'] ?>" class="form-control width-lg js-number" maxlength="30"/> | |
변경 전regular_order_view.php
| <div class="table-title"> | |
| 신청자 정보 | |
| <div class="flo-right"> | |
| <button type="button" class="btn btn-red btn-sm js-orderInfoBtn">정보수정</button> | |
| <button type="button" class="btn btn-red-box btn-sm js-orderInfoBtnSave js-orderViewInfoSave display-none" data-submit-mode="modify_applier_info">저장</button> | |
| </div> | |
| </div> | |
| <tr> | |
| <th>신청자명</th> | |
| <td class="text-left"> | |
| <span class="text-primary"><?= $applierInfo['applierName'] ?></span> / | |
| <?php if (!empty($applierInfo['memId'])): ?> | |
| <span class="text-primary"> <?= $applierInfo['memId'] ?> </span> / <span class="text-primary"> <?= $applierInfo['groupNm'] ?> </span> | |
| <?php else: ?> | |
| <span class="text-primary">탈퇴회원</span> | |
| <?php endif; ?> | |
| <?php if (!$isProvider && !empty($applierInfo['memId'])) { ?> | |
| <button type="button" class="btn btn-sm btn-gray js-layer-crm" data-member-no="<?= $applierInfo['memNo'] ?>">CRM 보기</button> | |
| <th>휴대폰번호</th> | |
| <td class="text-left"> | |
| <span><?= $applierInfo['applierCellPhone'] ?></span> | |
| <a class="btn btn-sm btn-gray" onclick="member_sms('<?=gd_isset($applierInfo['memNo'])?>','<?= urlencode($applierInfo['applierName']); ?>','<?= $applierInfo['applierCellPhone']; ?>', '<?=$applierInfo['smsFl']?>')">SMS 보내기</a> | |
| </td> | |
| </tr> | |
| <tr> | |
| <tr> | |
| <th>전화번호</th> | |
| <td class="text-left"> | |
| <input type="text" name="info[applierPhone]" value="<?= $applierInfo['applierPhone'] ?>" maxlength="20" class="form-control js-number-only width-md"/> | |
| </td> | |
| </tr> | |
| <tr> | |
| <th>휴대폰번호</th> | |
| <td class="text-left"> | |
| <input type="text" name="info[applierCellPhone]" value="<?= $applierInfo['applierCellPhone'] ?>" maxlength="20" class="form-control js-number-only width-md"/> | |
| </td> | |
| </tr> | |
| <tr> | |
| <th>이메일</th> | |
| <td class="text-left"> | |
| <div class="form-inline"> | |
| <input type="text" name="info[applierEmail]" value="<?= $applierInfo['applierEmail'] ?>" class="form-control width-md" /> | |
| <select id="emailDomain" class="form-control" style="width: 120px;"> | |
| <?php foreach($emailDomain as $key => $value){ ?> | |
| <option value="<?=$key?>"><?=$value?></option> | |
| 수령자 정보 | |
| <?php if (!$isProvider) : ?> | |
| <div class="flo-right"> | |
| <button type="button" class="btn btn-red btn-sm js-receiverInfoBtn">정보수정</button> | |
| <button type="button" class="btn btn-red-box btn-sm js-receiverInfoBtnSave js-orderViewInfoSave display-none" data-submit-mode="modifyReceiverInfo" data-order-info-sno="<?=$infoSno?>" data-use-safenumber-fl="<?=$data['receiverUseSafeNumberFl'];?>">저장</button> | |
| </div> | |
| <?php endif; ?> | |
| <th>휴대폰번호</th> | |
| <td class="text-left"> | |
| <span><?= $shippingInfo['shippingCellPhone'] ?></span> | |
| <a class="btn btn-sm btn-gray" onclick="member_sms('<?=gd_isset($shippingInfo['memNo'])?>','<?= urlencode($shippingInfo['shippingName']); ?>','<?= $shippingInfo['shippingCellPhone']; ?>', '<?=$shippingInfo['smsFl']?>')">SMS 보내기</a> | |
| </td> | |
| </tr> | |
| <tr> | |
| <th>주소</th> | |
| <td class="text-left"> | |
| <span>[<?= $shippingInfo['shippingZonecode']?>]<br/><?= $shippingInfo['shippingAddress']?><br/><?= $shippingInfo['shippingAddressSub']?></span> | |
| </td> | |
| </tr> | |
| <tr> | |
| <tr> | |
| <th>주소</th> | |
| <td class="text-left"> | |
| <span>[<?= $shippingInfo['shippingZonecode']?>]<br/><?= $shippingInfo['shippingAddress']?><br/><?= $shippingInfo['shippingAddressSub']?></span> | |
| </td> | |
| </tr> | |
| <tr> | |
변경 후regular_order_view.php
| <div class="table-title"> | |
| 신청자 정보 | |
| <div class="flo-right"> | |
| <?php // 분리보관(탈퇴/휴면) 신청서는 개인정보를 되살려 고칠 수 없으므로 정보수정을 막는다 ?> | |
| <button type="button" class="btn btn-red btn-sm js-orderInfoBtn" <?= $applierMaskLabel !== null ? 'disabled' : '' ?>>정보수정</button> | |
| <button type="button" class="btn btn-red-box btn-sm js-orderInfoBtnSave js-orderViewInfoSave display-none" data-submit-mode="modify_applier_info">저장</button> | |
| </div> | |
| </div> | |
| <tr> | |
| <th>신청자명</th> | |
| <td class="text-left"> | |
| <?php /* 신청자명(1A): 탈퇴/휴면 회원 신청서면 회원 유형 라벨("탈퇴회원"/"휴면회원") 표시, 일반 회원은 원본 표시 */ ?> | |
| <span class="text-primary"><?= gd_isset($applierMaskLabel) ?: $applierInfo['applierName'] ?></span> | |
| <?php if (!empty($applierInfo['memId'])): ?> | |
| / <span class="text-primary"> <?= $applierInfo['memId'] ?> </span> / <span class="text-primary"> <?= $applierInfo['groupNm'] ?> </span> | |
| <?php endif; ?> | |
| <?php if (!$isProvider && !empty($applierInfo['memId'])) { ?> | |
| <button type="button" class="btn btn-sm btn-gray js-layer-crm" data-member-no="<?= $applierInfo['memNo'] ?>">CRM 보기</button> | |
| <th>휴대폰번호</th> | |
| <td class="text-left"> | |
| <span><?= $applierInfo['applierCellPhone'] ?></span> | |
| <?php /* member_sms 인자는 SMS 발송 기능용 → 분리 원본 키 사용 */ ?> | |
| <a class="btn btn-sm btn-gray" onclick="member_sms('<?=gd_isset($applierInfo['memNo'])?>','<?= urlencode($applierInfo['applierName']); ?>','<?= isset($applierInfo['applierCellPhoneSeparationOrigin']) ? $applierInfo['applierCellPhoneSeparationOrigin'] : $applierInfo['applierCellPhone']; ?>', '<?=$applierInfo['smsFl']?>')">SMS 보내기</a> | |
| </td> | |
| </tr> | |
| <tr> | |
| <tr> | |
| <th>전화번호</th> | |
| <td class="text-left"> | |
| <?php /* 분리 원본 — 폼 전송값은 '-' 가 아니라 실제 값이어야 한다 */ ?> | |
| <input type="text" name="info[applierPhone]" value="<?= isset($applierInfo['applierPhoneSeparationOrigin']) ? $applierInfo['applierPhoneSeparationOrigin'] : $applierInfo['applierPhone'] ?>" maxlength="20" class="form-control js-number-only width-md"/> | |
| </td> | |
| </tr> | |
| <tr> | |
| <th>휴대폰번호</th> | |
| <td class="text-left"> | |
| <input type="text" name="info[applierCellPhone]" value="<?= isset($applierInfo['applierCellPhoneSeparationOrigin']) ? $applierInfo['applierCellPhoneSeparationOrigin'] : $applierInfo['applierCellPhone'] ?>" maxlength="20" class="form-control js-number-only width-md"/> | |
| </td> | |
| </tr> | |
| <tr> | |
| <th>이메일</th> | |
| <td class="text-left"> | |
| <div class="form-inline"> | |
| <input type="text" name="info[applierEmail]" value="<?= isset($applierInfo['applierEmailSeparationOrigin']) ? $applierInfo['applierEmailSeparationOrigin'] : $applierInfo['applierEmail'] ?>" class="form-control width-md" /> | |
| <select id="emailDomain" class="form-control" style="width: 120px;"> | |
| <?php foreach($emailDomain as $key => $value){ ?> | |
| <option value="<?=$key?>"><?=$value?></option> | |
| 수령자 정보 | |
| <?php if (!$isProvider) : ?> | |
| <div class="flo-right"> | |
| <button type="button" class="btn btn-red btn-sm js-receiverInfoBtn" <?= $applierMaskLabel !== null ? 'disabled' : '' ?>>정보수정</button> | |
| <button type="button" class="btn btn-red-box btn-sm js-receiverInfoBtnSave js-orderViewInfoSave display-none" data-submit-mode="modifyReceiverInfo" data-order-info-sno="<?=$infoSno?>" data-use-safenumber-fl="<?=$data['receiverUseSafeNumberFl'];?>">저장</button> | |
| </div> | |
| <?php endif; ?> | |
| <th>휴대폰번호</th> | |
| <td class="text-left"> | |
| <span><?= $shippingInfo['shippingCellPhone'] ?></span> | |
| <?php /* member_sms 인자는 SMS 발송 기능용 → 분리 원본 키 사용 */ ?> | |
| <a class="btn btn-sm btn-gray" onclick="member_sms('<?=gd_isset($shippingInfo['memNo'])?>','<?= urlencode(isset($shippingInfo['shippingNameSeparationOrigin']) ? $shippingInfo['shippingNameSeparationOrigin'] : $shippingInfo['shippingName']); ?>','<?= isset($shippingInfo['shippingCellPhoneSeparationOrigin']) ? $shippingInfo['shippingCellPhoneSeparationOrigin'] : $shippingInfo['shippingCellPhone']; ?>', '<?=$shippingInfo['smsFl']?>')">SMS 보내기</a> | |
| </td> | |
| </tr> | |
| <tr> | |
| <th>주소</th> | |
| <td class="text-left"> | |
| <?php /* 주소 구성요소가 각각 '-' 로 치환돼 하이픈이 반복되므로 칸 전체를 단일 '-' 로 표시 */ ?> | |
| <?php if (!empty($applierMaskLabel)) { ?> | |
| <span><?= $maskChar ?></span> | |
| <?php } else { ?> | |
| <span>[<?= $shippingInfo['shippingZonecode']?>]<br/><?= $shippingInfo['shippingAddress']?><br/><?= $shippingInfo['shippingAddressSub']?></span> | |
| <?php } ?> | |
| </td> | |
| </tr> | |
| <tr> | |
| <tr> | |
| <th>주소</th> | |
| <td class="text-left"> | |
| <?php /* 주소 구성요소가 각각 '-' 로 치환돼 하이픈이 반복되므로 칸 전체를 단일 '-' 로 표시 */ ?> | |
| <?php if (!empty($applierMaskLabel)) { ?> | |
| <span><?= $maskChar ?></span> | |
| <?php } else { ?> | |
| <span>[<?= $shippingInfo['shippingZonecode']?>]<br/><?= $shippingInfo['shippingAddress']?><br/><?= $shippingInfo['shippingAddressSub']?></span> | |
| <?php } ?> | |
| </td> | |
| </tr> | |
| <tr> | |
변경 전tax_invoice_request.php
| <input type="hidden" name="taxInvoiceData[<?= $val['orderNo'] ?>][taxZipcode]" value="<?php echo $val['taxZipcode'] ?>" /> | |
| <input type="hidden" name="taxInvoiceData[<?= $val['orderNo'] ?>][taxZonecode]" value="<?php echo $val['taxZonecode'] ?>" /> | |
| <input type="hidden" class="form-control width-xs" name="taxInvoiceData[<?= $val['orderNo'] ?>][taxPolicy]" value="<?= $val['taxPolicy'] ?>"/> | |
| <input type="hidden" class="form-control width-xs" name="taxInvoiceData[<?= $val['orderNo'] ?>][requestNm]" value="<?= $val['requestNm'] ?>"/> | |
| <input type="hidden" class="form-control width-xs" name="taxInvoiceData[<?= $val['orderNo'] ?>][requestGoodsNm]" value="<?= $val['requestGoodsNm'] ?>"/> | |
| <div class="form-inline business-information"> | |
변경 후tax_invoice_request.php
| <input type="hidden" name="taxInvoiceData[<?= $val['orderNo'] ?>][taxZipcode]" value="<?php echo $val['taxZipcode'] ?>" /> | |
| <input type="hidden" name="taxInvoiceData[<?= $val['orderNo'] ?>][taxZonecode]" value="<?php echo $val['taxZonecode'] ?>" /> | |
| <input type="hidden" class="form-control width-xs" name="taxInvoiceData[<?= $val['orderNo'] ?>][taxPolicy]" value="<?= $val['taxPolicy'] ?>"/> | |
| <?php /* 분리 원본 — 폼 전송값은 '-' 가 아니라 실제 값이어야 한다 */ ?> | |
| <input type="hidden" class="form-control width-xs" name="taxInvoiceData[<?= $val['orderNo'] ?>][requestNm]" value="<?= isset($val['requestNmSeparationOrigin']) ? $val['requestNmSeparationOrigin'] : $val['requestNm'] ?>"/> | |
| <input type="hidden" class="form-control width-xs" name="taxInvoiceData[<?= $val['orderNo'] ?>][requestGoodsNm]" value="<?= $val['requestGoodsNm'] ?>"/> | |
| <div class="form-inline business-information"> | |
변경 전_manage_permission_menu_list.php
| case 'memberMaskingUseFl': | |
| case 'boardMaskingUseFl': | |
| case 'messageMaskingUseFl': | |
| case 'withdrawnMembersOrderLimitViewFl': | |
| if ($adminMenuType == 'd' && $isSuper == 'y') { // 본사 최고운영자 수정 일 경우 | |
| $disabled['functionAuth'][$code] = 'disabled="disabled"'; | |
| } else if ($adminMenuType == 'd' && $isSuper != 'y') { // 본사 부운영자 등록/수정 일 경우 | |
| if ($disabled['settingItem'] != '') { | |
| $disabled['chk_3'][$subTreeKey][$lastTreeKey] = $disabled['permission_3'][$subTreeKey][$lastTreeKey] = $disabled['settingItem']; | |
| } | |
| $default = (isset($lastTreeVal['default']) === true ? $lastTreeVal['default'] : 'writable'); // 기본권한 정의 | |
| $defaulted[$default] = 'data-defaulted="defaulted"'; | |
| if (($adminMenuType == 'd' && $isSuper == 'y') || $permissionFl == 's') { // 본사 최고운영자 또는 전체권한 경우 기본권한 부여 | |
| $selected['permission_3'][$subTreeKey][$lastTreeKey][$default] = 'selected="selected"'; | |
| $selected['permission_3'][$subTreeKey][$lastTreeKey][''] = 'selected="selected"'; | |
| } | |
| // 특정 메뉴 권한에 대한 disabled 처리 기능 추가 | |
| $disabled = ['readonly' => [], 'writable' => []]; | |
| $disabledKeys = [ | |
| 'readonly' => ['godo02201'], | |
| 'writable' => [] | |
| ]; | |
| // 'readonly' 권한에서 특정 메뉴 키가 있을 경우 disabled 처리 | |
| $disabled['readonly'][$lastTreeKey] = in_array($lastTreeKey, $disabledKeys['readonly']) ? 'disabled' : ''; | |
| <select name="permission_3[<?= $menuTreeKey; ?>][<?= $subTreeKey; ?>][<?= $lastTreeKey; ?>]" id="permission_<?= $menuTreeKey; ?>_<?= $subTreeKey; ?>_<?= $lastTreeKey; ?>" <?= gd_isset($disabled['permission_3'][$subTreeKey][$lastTreeKey]); ?>> | |
| <option value="" <?= gd_isset($selected['permission_3'][$subTreeKey][$lastTreeKey]['']); ?> <?= gd_isset($defaulted['']); ?> <?= gd_isset($lastTreeVal['disabled']['']); ?>>권한없음</option> | |
| <option value="readonly" <?= $disabled['readonly'][$lastTreeKey] ?> <?= gd_isset($selected['permission_3'][$subTreeKey][$lastTreeKey]['readonly']); ?> <?= gd_isset($defaulted['readonly']); ?> <?= gd_isset($lastTreeVal['disabled']['readonly']); ?>>읽기</option> | |
| <option value="writable" <?= gd_isset($selected['permission_3'][$subTreeKey][$lastTreeKey]['writable']); ?> <?= gd_isset($defaulted['writable']); ?> <?= gd_isset($lastTreeVal['disabled']['writable']); ?>>읽기+쓰기</option> | |
| </select> | |
| </td> | |
| <td class="center"></td> | |
변경 후_manage_permission_menu_list.php
| case 'memberMaskingUseFl': | |
| case 'boardMaskingUseFl': | |
| case 'messageMaskingUseFl': | |
| if ($adminMenuType == 'd' && $isSuper == 'y') { // 본사 최고운영자 수정 일 경우 | |
| $disabled['functionAuth'][$code] = 'disabled="disabled"'; | |
| } else if ($adminMenuType == 'd' && $isSuper != 'y') { // 본사 부운영자 등록/수정 일 경우 | |
| if ($disabled['settingItem'] != '') { | |
| $disabled['chk_3'][$subTreeKey][$lastTreeKey] = $disabled['permission_3'][$subTreeKey][$lastTreeKey] = $disabled['settingItem']; | |
| } | |
| // 특정 메뉴 권한에 대한 disabled 처리 기능 추가 | |
| $disabledKeys = [ | |
| 'readonly' => ['godo02201'], | |
| 'writable' => ['godo00893', 'godo00894'] | |
| ]; | |
| // 조회 전용 메뉴는 '읽기+쓰기' 를 아예 노출하지 않는다 | |
| $isWritableLocked = in_array($lastTreeKey, $disabledKeys['writable']); | |
| $default = (isset($lastTreeVal['default']) === true ? $lastTreeVal['default'] : 'writable'); // 기본권한 정의 | |
| // 노출하지 않는 권한이 기본값이면 한 단계 내린다 | |
| if ($isWritableLocked && $default === 'writable') { | |
| $default = 'readonly'; | |
| } | |
| $defaulted = []; | |
| $defaulted[$default] = 'data-defaulted="defaulted"'; | |
| if (($adminMenuType == 'd' && $isSuper == 'y') || $permissionFl == 's') { // 본사 최고운영자 또는 전체권한 경우 기본권한 부여 | |
| $selected['permission_3'][$subTreeKey][$lastTreeKey][$default] = 'selected="selected"'; | |
| $selected['permission_3'][$subTreeKey][$lastTreeKey][''] = 'selected="selected"'; | |
| } | |
| $disabled = ['readonly' => [], 'writable' => []]; | |
| // 'readonly' 권한에서 특정 메뉴 키가 있을 경우 disabled 처리 | |
| $disabled['readonly'][$lastTreeKey] = in_array($lastTreeKey, $disabledKeys['readonly']) ? 'disabled' : ''; | |
| <select name="permission_3[<?= $menuTreeKey; ?>][<?= $subTreeKey; ?>][<?= $lastTreeKey; ?>]" id="permission_<?= $menuTreeKey; ?>_<?= $subTreeKey; ?>_<?= $lastTreeKey; ?>" <?= gd_isset($disabled['permission_3'][$subTreeKey][$lastTreeKey]); ?>> | |
| <option value="" <?= gd_isset($selected['permission_3'][$subTreeKey][$lastTreeKey]['']); ?> <?= gd_isset($defaulted['']); ?> <?= gd_isset($lastTreeVal['disabled']['']); ?>>권한없음</option> | |
| <option value="readonly" <?= $disabled['readonly'][$lastTreeKey] ?> <?= gd_isset($selected['permission_3'][$subTreeKey][$lastTreeKey]['readonly']); ?> <?= gd_isset($defaulted['readonly']); ?> <?= gd_isset($lastTreeVal['disabled']['readonly']); ?>>읽기</option> | |
| <?php if (!$isWritableLocked) : ?> | |
| <option value="writable" <?= gd_isset($selected['permission_3'][$subTreeKey][$lastTreeKey]['writable']); ?> <?= gd_isset($defaulted['writable']); ?> <?= gd_isset($lastTreeVal['disabled']['writable']); ?>>읽기+쓰기</option> | |
| <?php endif; ?> | |
| </select> | |
| </td> | |
| <td class="center"></td> | |
변경 전layer_handle_reason.php
| <th class="th">환불 계좌정보</th> | |
| <td colspan="3"> | |
| <?php | |
| if (empty($data['userRefundBankName']) === false) { | |
| echo $data['userRefundBankName'] . ' / ' . $data['userRefundAccountNumber'] . ' / ' . $data['userRefundDepositor']; | |
| } | |
| ?> | |
변경 후layer_handle_reason.php
| <th class="th">환불 계좌정보</th> | |
| <td colspan="3"> | |
| <?php | |
| if (!empty($isRefundMaskTarget)) { | |
| echo $maskChar; | |
| } elseif (empty($data['userRefundBankName']) === false) { | |
| echo $data['userRefundBankName'] . ' / ' . $data['userRefundAccountNumber'] . ' / ' . $data['userRefundDepositor']; | |
| } | |
| ?> | |
변경 전AdminLogDAO.php
| case 'crm_group_result.php': // CRM 그룹 리스트(엑셀다운로드)/CRM 그룹 상세보기(조회) | |
| case 'scheduled_send.php': // 예약/반복 발송 상세(검색) | |
| case 'layer_select_members_result.php': // 회원 선택 모달 접근/검색 | |
| $data[$lKey]['displayDetailLogFl'] = 'y'; | |
| break; | |
| case 'member_ps.php': | |
| $result['searchTargetMsg'] = $this->buildMaskedSearchTargetMessage($data['data']['searchData'], 'id'); // 처리 대상 핸들링 | |
| } | |
| break; | |
| default: | |
| break; | |
| } | |
| 'crm_group_create.php', | |
| 'scheduled_send.php', | |
| 'mobile_history_list.php', | |
| 'crm_group_result.php' | |
| ]; | |
| if (gd_in_array(end($fileUri), $exceptPage) === false) { | |
| $data['searchData'] = $rejectCellPhone; | |
| $data['searchCnt'] = $controller->getData('page')->recode['total']; | |
| break; | |
| default: | |
| break; | |
| } | |
변경 후AdminLogDAO.php
| case 'crm_group_result.php': // CRM 그룹 리스트(엑셀다운로드)/CRM 그룹 상세보기(조회) | |
| case 'scheduled_send.php': // 예약/반복 발송 상세(검색) | |
| case 'layer_select_members_result.php': // 회원 선택 모달 접근/검색 | |
| case 'order_list_withdrawn_member.php': // 휴면/탈퇴 회원 주문 리스트 | |
| $data[$lKey]['displayDetailLogFl'] = 'y'; | |
| break; | |
| case 'member_ps.php': | |
| $result['searchTargetMsg'] = $this->buildMaskedSearchTargetMessage($data['data']['searchData'], 'id'); // 처리 대상 핸들링 | |
| } | |
| break; | |
| case 'order_list_withdrawn_member.php': // 휴면/탈퇴 회원 주문 리스트 | |
| // 이 화면의 검색 폼은 공통부가 전제하는 key/keyword 가 아니라 searchField/searchWord 를 쓴다 | |
| $searchFieldValue = $data['data']['GET']['searchField'] ?? ''; | |
| $result['searchConditionMsg'] = '처리조건 : ' . ($searchFieldValue === 'orderNo' ? '주문번호' : '주문자명'); | |
| $result['searchViewCnt'] = '처리건수 : ' . number_format((int) $data['data']['searchCnt']) . '건'; | |
| $result['searchTargetMsg'] = '처리대상 : ' . $data['data']['searchData']; | |
| break; | |
| default: | |
| break; | |
| } | |
| 'crm_group_create.php', | |
| 'scheduled_send.php', | |
| 'mobile_history_list.php', | |
| 'crm_group_result.php', | |
| 'order_list_withdrawn_member.php', | |
| ]; | |
| if (gd_in_array(end($fileUri), $exceptPage) === false) { | |
| $data['searchData'] = $rejectCellPhone; | |
| $data['searchCnt'] = $controller->getData('page')->recode['total']; | |
| break; | |
| case 'order_list_withdrawn_member': // 휴면/탈퇴 회원 주문 리스트 | |
| // 기획상 처리대상은 조회된 주문이 아니라 관리자가 입력한 검색어다 | |
| $data['searchData'] = $data['GET']['searchWord'] ?? ''; | |
| $data['searchCnt'] = $controller->getData('cnt')['search'] ?? 0; | |
| break; | |
| default: | |
| break; | |
| } | |
변경 전AdminMenu.php
| 'bankdaManual' => '입금내역 주문서 수동매칭', | |
| 'orderReceiptProcess' => '현금영수증 처리(발급/거절/취소/삭제)', | |
| 'orderMaskingUseFl' => '개인정보조회 제한', | |
| 'withdrawnMembersOrderLimitViewFl' => '탈퇴회원거래내역조회 제한', | |
| ], | |
| 'godo00138' => [ | |
| 'memberHack' => '회원탈퇴', | |
변경 후AdminMenu.php
| 'bankdaManual' => '입금내역 주문서 수동매칭', | |
| 'orderReceiptProcess' => '현금영수증 처리(발급/거절/취소/삭제)', | |
| 'orderMaskingUseFl' => '개인정보조회 제한', | |
| ], | |
| 'godo00138' => [ | |
| 'memberHack' => '회원탈퇴', | |
변경 전CouponAdmin.php
| $sort['fieldName'] = 'mc.regDt'; | |
| $sort['sortMode'] = 'desc'; | |
| $this->db->strField = "mc.memberCouponNo, mc.couponNo, mc.couponSaveAdminId, mc.regDt, mc.memberCouponEndDate, mc.memberCouponUseDate, mc.memberCouponState, m.memNm, m.memId, m.groupSno"; | |
| $this->db->strJoin = 'LEFT JOIN es_member AS m ON mc.memNo = m.memNo LEFT JOIN es_memberSns AS ms ON m.memNo = ms.memNo'; | |
| $this->db->strWhere = gd_implode(' AND ', gd_isset($this->arrWhere)); | |
| $this->db->strOrder = $sort['fieldName'] . ' ' . $sort['sortMode']; | |
| if($arrData['whereFl'] == 'search') { | |
| if ($data['couponAuthType'] == 'n') { // 페이퍼 쿠폰 인증번호 타입 : 1개의 인증번호 | |
| $this->db->strField = "coc.couponOfflineCodeUser, mc.regDt, mc.memberCouponEndDate, mc.memberCouponUseDate, mc.memberCouponState, m.memId, m.memNm, m.groupSno "; | |
| $this->db->strJoin = " LEFT JOIN " . DB_COUPON_OFFLINE_CODE . " AS coc ON coc.couponNo = mc.couponNo LEFT JOIN " . DB_MEMBER . " AS m ON m.memNo = mc.memNo LEFT JOIN " . DB_MEMBER_SNS . " AS ms ON m.memNo = ms.memNo"; | |
| if($arrData['whereDetail']['keyword']){ | |
| if($arrData['whereDetail']['key'] == 'couponSaveAdminId'){ | |
| unset($arrBind); | |
| } else { // 페이퍼 쿠폰 인증번호 타입 : 회원별 인증번호 | |
| $this->db->strField = "coc.couponOfflineCodeUser, mc.regDt, mc.memberCouponEndDate, mc.memberCouponUseDate, mc.memberCouponState, m.memId, m.memNm, m.groupSno "; | |
| $this->db->strJoin = " LEFT JOIN " . DB_COUPON_OFFLINE_CODE . " AS coc ON coc.memberCouponNo = mc.memberCouponNo LEFT JOIN " . DB_MEMBER . " AS m ON m.memNo = mc.memNo LEFT JOIN " . DB_MEMBER_SNS . " AS ms ON m.memNo = ms.memNo"; | |
| if($arrData['whereDetail']['keyword']){ | |
| if($arrData['whereDetail']['key'] == 'couponSaveAdminId'){ | |
| unset($arrBind); | |
| } | |
| }else{ | |
| $this->db->strField = "coc.couponOfflineCodeUser, mc.regDt, mc.memberCouponEndDate, mc.memberCouponUseDate, mc.memberCouponState, m.memId, m.memNm, m.groupSno "; | |
| if($data['couponAuthType'] == 'n'){ | |
| $this->db->strJoin = " LEFT JOIN " . DB_COUPON_OFFLINE_CODE . " AS coc ON coc.couponNo = mc.couponNo LEFT JOIN " . DB_MEMBER . " AS m ON m.memNo = mc.memNo LEFT JOIN " . DB_MEMBER_SNS . " AS ms ON m.memNo = ms.memNo"; | |
| }else{ | |
변경 후CouponAdmin.php
| $sort['fieldName'] = 'mc.regDt'; | |
| $sort['sortMode'] = 'desc'; | |
| $this->db->strField = "mc.memNo, mc.memberCouponNo, mc.couponNo, mc.couponSaveAdminId, mc.regDt, mc.memberCouponEndDate, mc.memberCouponUseDate, mc.memberCouponState, m.memNm, m.memId, m.groupSno"; | |
| $this->db->strJoin = 'LEFT JOIN es_member AS m ON mc.memNo = m.memNo LEFT JOIN es_memberSns AS ms ON m.memNo = ms.memNo'; | |
| $this->db->strWhere = gd_implode(' AND ', gd_isset($this->arrWhere)); | |
| $this->db->strOrder = $sort['fieldName'] . ' ' . $sort['sortMode']; | |
| if($arrData['whereFl'] == 'search') { | |
| if ($data['couponAuthType'] == 'n') { // 페이퍼 쿠폰 인증번호 타입 : 1개의 인증번호 | |
| $this->db->strField = "coc.couponOfflineCodeUser, mc.memNo, mc.regDt, mc.memberCouponEndDate, mc.memberCouponUseDate, mc.memberCouponState, m.memId, m.memNm, m.groupSno "; | |
| $this->db->strJoin = " LEFT JOIN " . DB_COUPON_OFFLINE_CODE . " AS coc ON coc.couponNo = mc.couponNo LEFT JOIN " . DB_MEMBER . " AS m ON m.memNo = mc.memNo LEFT JOIN " . DB_MEMBER_SNS . " AS ms ON m.memNo = ms.memNo"; | |
| if($arrData['whereDetail']['keyword']){ | |
| if($arrData['whereDetail']['key'] == 'couponSaveAdminId'){ | |
| unset($arrBind); | |
| } else { // 페이퍼 쿠폰 인증번호 타입 : 회원별 인증번호 | |
| $this->db->strField = "coc.couponOfflineCodeUser, mc.memNo, mc.regDt, mc.memberCouponEndDate, mc.memberCouponUseDate, mc.memberCouponState, m.memId, m.memNm, m.groupSno "; | |
| $this->db->strJoin = " LEFT JOIN " . DB_COUPON_OFFLINE_CODE . " AS coc ON coc.memberCouponNo = mc.memberCouponNo LEFT JOIN " . DB_MEMBER . " AS m ON m.memNo = mc.memNo LEFT JOIN " . DB_MEMBER_SNS . " AS ms ON m.memNo = ms.memNo"; | |
| if($arrData['whereDetail']['keyword']){ | |
| if($arrData['whereDetail']['key'] == 'couponSaveAdminId'){ | |
| unset($arrBind); | |
| } | |
| }else{ | |
| $this->db->strField = "coc.couponOfflineCodeUser, mc.memNo, mc.regDt, mc.memberCouponEndDate, mc.memberCouponUseDate, mc.memberCouponState, m.memId, m.memNm, m.groupSno "; | |
| if($data['couponAuthType'] == 'n'){ | |
| $this->db->strJoin = " LEFT JOIN " . DB_COUPON_OFFLINE_CODE . " AS coc ON coc.couponNo = mc.couponNo LEFT JOIN " . DB_MEMBER . " AS m ON m.memNo = mc.memNo LEFT JOIN " . DB_MEMBER_SNS . " AS ms ON m.memNo = ms.memNo"; | |
| }else{ | |
변경 전DBTableField.php
| ['val' => 'fbPixelKey', 'typ' => 's', 'def' => null], // 페이스북 픽셀 쿠키값 | |
| ['val' => 'channelType', 'typ' => 's', 'def' => null], // 주문건 추적 채널타입 데이터 | |
| ['val' => 'refererUrl', 'typ' => 's', 'def' => null], // 주문 생성 접근 URL | |
| ]; | |
| // @formatter:on | |
변경 후DBTableField.php
| ['val' => 'fbPixelKey', 'typ' => 's', 'def' => null], // 페이스북 픽셀 쿠키값 | |
| ['val' => 'channelType', 'typ' => 's', 'def' => null], // 주문건 추적 채널타입 데이터 | |
| ['val' => 'refererUrl', 'typ' => 's', 'def' => null], // 주문 생성 접근 URL | |
| ['val' => 'separationStatus', 'typ' => 's', 'def' => ''], // 개인정보 분리보관 상태 (빈값: 미분리, hackout: 탈퇴회원 분리보관, sleep: 휴면회원 분리보관) | |
| ]; | |
| // @formatter:on | |
변경 전ExcelRequest.php
| use LogHandler; | |
| use Origin\DTO\Kafka\ShopDataExtractLogDTO; | |
| use Origin\Enum\Excel\ShopDataExtractTarget; | |
| use Origin\Enum\RegularDelivery\RegularGoods\DeliveryCycle; | |
| use Request; | |
| use Session; | |
| $data = $orderList[$i]; | |
| } | |
| foreach ($data as $key => $val) { | |
| $progress = ($totalNum == 1) ? 100 : round((100 / ($totalNum - 1)) * ($key + ($i * $this->excelPageNum))); | |
| if ($progress % 20 == 0 || $progress == '100') { | |
| unset($tmpScmDeliverySno); | |
| } | |
| $tmpData[] = "<tr>"; | |
| foreach ($excelField as $excelKey => $excelValue) { | |
| $setData = []; | |
| $setHedData[] = "<tr>"; | |
| foreach ($data as $k => $v) { | |
| $tmpData = []; | |
| foreach ($v as $key => $val) { | |
| $rowspan = $rowspanFix ?? gd_count($val['taxInvoiceInfo']); | |
| echo "<script> parent.progressExcel('" . $progressPercent . "'); </script>"; | |
| } | |
| $tmpData[] = "<tr>"; | |
| foreach ($excelField as $excelKey => $excelValue) { | |
| $setData = []; | |
| $setHedData[] = "<tr>"; | |
| foreach ($data as $k => $v) { | |
| $tmpData = []; | |
| foreach ($v as $key => $val) { | |
| $rowspan = $rowspanFix ?? gd_count($val['taxInvoiceInfo']); | |
| echo "<script> parent.progressExcel('" . $progressPercent . "'); </script>"; | |
| } | |
| $tmpData[] = "<tr>"; | |
| foreach ($excelField as $excelKey => $excelValue) { | |
| $setData = []; | |
| $setHedData[] = "<tr>"; | |
| foreach ($data as $k => $v) { | |
| $tmpData = []; | |
| foreach ($v as $key => $val) { | |
| if (($key % 20 == 0 && $key != '0') || $totalNum - 1 == $key) { | |
| $progressPercent = ($totalNum - 1) > 0 ? round((100 / ($totalNum - 1)) * $key) : 100; | |
| echo "<script> parent.progressExcel('" . $progressPercent . "'); </script>"; | |
| $setData = []; | |
| $setHedData[] = "<tr>"; | |
| foreach ($data as $k => $v) { | |
| $tmpData = []; | |
| foreach ($v as $key => $val) { | |
| if (($key % 20 == 0 && $key != '0') || $totalNum - 1 == $key) { | |
| $progressPercent = ($totalNum - 1) > 0 ? round((100 / ($totalNum - 1)) * $key) : 100; | |
| echo "<script> parent.progressExcel('" . $progressPercent . "'); </script>"; | |
| } else { | |
| $data = $orderList[$i]; | |
| } | |
| foreach ($data as $key => $val) { | |
| $progress = ($totalNum - 1) > 0 ? round((100 / ($totalNum - 1)) * ($key + ($i * $this->excelPageNum))) : 100; | |
| if ($progress % 20 == 0 || $progress == '100') { | |
| $val['goodsTotalWeightVolume'] = $val['goodsWeight'] . gd_isset(Globals::get('gWeight.unit'), 'kg') . '|' . $val['goodsVolume'] . gd_isset(Globals::get('gVolume.unit'), '㎖'); | |
| } | |
| $tmpData[] = "<tr>"; | |
| foreach ($excelField as $excelKey => $excelValue) { | |
| if (!$excelFieldName[$excelValue]) continue; | |
변경 후ExcelRequest.php
| use LogHandler; | |
| use Origin\DTO\Kafka\ShopDataExtractLogDTO; | |
| use Origin\Enum\Excel\ShopDataExtractTarget; | |
| use Origin\Service\Privacy\Masking\OrderExcelMaskingService; | |
| use Origin\Enum\RegularDelivery\RegularGoods\DeliveryCycle; | |
| use Request; | |
| use Session; | |
| $data = $orderList[$i]; | |
| } | |
| // 분리보관(탈퇴/휴면) 주문 판정 — 배열이면 페이지 단위로 1회만 조회하고, | |
| // 제너레이터는 주문번호를 미리 모을 수 없으므로 행이 실어 온 분리보관 상태값으로 판정한다 | |
| $excelMasking = \App::getInstance(OrderExcelMaskingService::class); | |
| $maskLabels = is_array($data) === true ? $excelMasking->resolveOrderLabels($data) : null; | |
| foreach ($data as $key => $val) { | |
| $progress = ($totalNum == 1) ? 100 : round((100 / ($totalNum - 1)) * ($key + ($i * $this->excelPageNum))); | |
| if ($progress % 20 == 0 || $progress == '100') { | |
| unset($tmpScmDeliverySno); | |
| } | |
| // 개인정보 치환은 셀 조합 직전에 수행한다(환불계좌 결합 등 가공이 끝난 최종 값 기준) | |
| $val = $excelMasking->maskOrderRow($val, $maskLabels); | |
| $tmpData[] = "<tr>"; | |
| foreach ($excelField as $excelKey => $excelValue) { | |
| $setData = []; | |
| $setHedData[] = "<tr>"; | |
| $excelMasking = \App::getInstance(OrderExcelMaskingService::class); | |
| foreach ($data as $k => $v) { | |
| // 분리보관(탈퇴/휴면) 주문 판정을 페이지 단위로 1회만 조회한다 | |
| $maskLabels = $excelMasking->resolveOrderLabels($v); | |
| $tmpData = []; | |
| foreach ($v as $key => $val) { | |
| $rowspan = $rowspanFix ?? gd_count($val['taxInvoiceInfo']); | |
| echo "<script> parent.progressExcel('" . $progressPercent . "'); </script>"; | |
| } | |
| $val = $excelMasking->maskTaxRow($val, $maskLabels); | |
| $tmpData[] = "<tr>"; | |
| foreach ($excelField as $excelKey => $excelValue) { | |
| $setData = []; | |
| $setHedData[] = "<tr>"; | |
| $excelMasking = \App::getInstance(OrderExcelMaskingService::class); | |
| foreach ($data as $k => $v) { | |
| // 분리보관(탈퇴/휴면) 주문 판정을 페이지 단위로 1회만 조회한다 | |
| $maskLabels = $excelMasking->resolveOrderLabels($v); | |
| $tmpData = []; | |
| foreach ($v as $key => $val) { | |
| $rowspan = $rowspanFix ?? gd_count($val['taxInvoiceInfo']); | |
| echo "<script> parent.progressExcel('" . $progressPercent . "'); </script>"; | |
| } | |
| $val = $excelMasking->maskTaxRow($val, $maskLabels); | |
| $tmpData[] = "<tr>"; | |
| foreach ($excelField as $excelKey => $excelValue) { | |
| $setData = []; | |
| $setHedData[] = "<tr>"; | |
| $excelMasking = \App::getInstance(OrderExcelMaskingService::class); | |
| foreach ($data as $k => $v) { | |
| // 분리보관(탈퇴/휴면) 회원 판정을 페이지 단위로 1회만 조회한다 | |
| $maskLabels = $excelMasking->resolveMemberLabels($v); | |
| $tmpData = []; | |
| foreach ($v as $key => $val) { | |
| $val = $excelMasking->maskCouponRow($val, $maskLabels); | |
| if (($key % 20 == 0 && $key != '0') || $totalNum - 1 == $key) { | |
| $progressPercent = ($totalNum - 1) > 0 ? round((100 / ($totalNum - 1)) * $key) : 100; | |
| echo "<script> parent.progressExcel('" . $progressPercent . "'); </script>"; | |
| $setData = []; | |
| $setHedData[] = "<tr>"; | |
| $excelMasking = \App::getInstance(OrderExcelMaskingService::class); | |
| foreach ($data as $k => $v) { | |
| // 분리보관(탈퇴/휴면) 회원 판정을 페이지 단위로 1회만 조회한다 | |
| $maskLabels = $excelMasking->resolveMemberLabels($v); | |
| $tmpData = []; | |
| foreach ($v as $key => $val) { | |
| $val = $excelMasking->maskCouponRow($val, $maskLabels); | |
| if (($key % 20 == 0 && $key != '0') || $totalNum - 1 == $key) { | |
| $progressPercent = ($totalNum - 1) > 0 ? round((100 / ($totalNum - 1)) * $key) : 100; | |
| echo "<script> parent.progressExcel('" . $progressPercent . "'); </script>"; | |
| } else { | |
| $data = $orderList[$i]; | |
| } | |
| // 분리보관(탈퇴/휴면) 주문 판정 — 배열이면 페이지 단위로 1회만 조회하고, | |
| // 제너레이터는 주문번호를 미리 모을 수 없으므로 행이 실어 온 분리보관 상태값으로 판정한다 | |
| $excelMasking = \App::getInstance(OrderExcelMaskingService::class); | |
| $maskLabels = is_array($data) === true ? $excelMasking->resolveOrderLabels($data) : null; | |
| foreach ($data as $key => $val) { | |
| $progress = ($totalNum - 1) > 0 ? round((100 / ($totalNum - 1)) * ($key + ($i * $this->excelPageNum))) : 100; | |
| if ($progress % 20 == 0 || $progress == '100') { | |
| $val['goodsTotalWeightVolume'] = $val['goodsWeight'] . gd_isset(Globals::get('gWeight.unit'), 'kg') . '|' . $val['goodsVolume'] . gd_isset(Globals::get('gVolume.unit'), '㎖'); | |
| } | |
| // 개인정보 치환은 셀 조합 직전에 수행한다(가공이 끝난 최종 값 기준) | |
| $val = $excelMasking->maskOrderRow($val, $maskLabels); | |
| $tmpData[] = "<tr>"; | |
| foreach ($excelField as $excelKey => $excelValue) { | |
| if (!$excelFieldName[$excelValue]) continue; | |
변경 전HackOutService.php
| use Framework\Utility\NumberUtils; | |
| use Framework\Utility\StringUtils; | |
| use Session; | |
| use Origin\Service\WebHook\MemberWebHookService; | |
| /** | |
| throw $e; | |
| } | |
| // 회원 탈퇴 완료 시 웹훅 발송 | |
| $memberWebHookService = \App::getInstance(MemberWebHookService::class); | |
| $memberWebHookService->sendWithdrawWebHook($member); | |
| throw $e; | |
| } | |
| // 회원 탈퇴 완료 시 웹훅 발송 | |
| $memberWebHookService = \App::getInstance(MemberWebHookService::class); | |
| foreach ($memberList as $member) { | |
| $memberWebHookService->sendWithdrawWebHook($member); | |
| } | |
| } | |
| throw $e; | |
| } | |
| // 회원 탈퇴 완료 시 웹훅 발송 | |
| $memberWebHookService = \App::getInstance(MemberWebHookService::class); | |
| $memberWebHookService->sendWithdrawWebHook($member); | |
| $this->hackOutDAO->insertHackOut(); | |
| } | |
| /** | |
| * 탈퇴회원 리스트 조회 | |
| * | |
변경 후HackOutService.php
| use Framework\Utility\NumberUtils; | |
| use Framework\Utility\StringUtils; | |
| use Session; | |
| use Origin\Enum\Privacy\Withdrawn\WithdrawnMemberType; | |
| use Origin\Service\Privacy\Withdrawn\WithdrawnMemberOrderSeparatorService; | |
| use Origin\Service\WebHook\MemberWebHookService; | |
| /** | |
| throw $e; | |
| } | |
| // 주문 PII 분리 | |
| $this->separateHackOutOrderPii((int) $memNo); | |
| // 회원 탈퇴 완료 시 웹훅 발송 | |
| $memberWebHookService = \App::getInstance(MemberWebHookService::class); | |
| $memberWebHookService->sendWithdrawWebHook($member); | |
| throw $e; | |
| } | |
| // 회원 탈퇴 완료 시 웹훅 발송 + 주문 PII 분리 | |
| $memberWebHookService = \App::getInstance(MemberWebHookService::class); | |
| foreach ($memberList as $member) { | |
| $memberWebHookService->sendWithdrawWebHook($member); | |
| $this->separateHackOutOrderPii((int) $member['memNo']); | |
| } | |
| } | |
| throw $e; | |
| } | |
| // 주문 PII 분리 | |
| $this->separateHackOutOrderPii((int) $memNo); | |
| // 회원 탈퇴 완료 시 웹훅 발송 | |
| $memberWebHookService = \App::getInstance(MemberWebHookService::class); | |
| $memberWebHookService->sendWithdrawWebHook($member); | |
| $this->hackOutDAO->insertHackOut(); | |
| } | |
| /** | |
| * 탈퇴 커밋 후 회원의 주문 PII 를 분리보관으로 옮긴다. 실패해도 탈퇴는 유지되고 D+1 배치가 보정한다. | |
| */ | |
| private function separateHackOutOrderPii(int $memNo): void | |
| { | |
| try { | |
| \App::getInstance(WithdrawnMemberOrderSeparatorService::class)->separate($memNo, WithdrawnMemberType::HACKOUT); | |
| } catch (\Throwable $e) { | |
| \App::getInstance('logger')->error('withdrawn hackout order separate failed', [ | |
| 'exception' => $e, | |
| 'memNo' => $memNo, | |
| ]); | |
| } | |
| } | |
| /** | |
| * 탈퇴회원 리스트 조회 | |
| * | |
변경 전MemberMasking.php
| namespace Bundle\Component\Member; | |
| /** | |
| * Class 회원 마스킹 처리 | |
| * @package Bundle\Component\Member | |
| */ | |
| public function masking($menu, $type, $string){ | |
| if ($menu == 'order') { | |
| if ($this->orderMaskingUseFl != 'y') { | |
| return $string; | |
변경 후MemberMasking.php
| namespace Bundle\Component\Member; | |
| use Origin\Service\Privacy\Masking\ColumnMaskingService; | |
| use Origin\Service\Privacy\Masking\MaskingTargetService; | |
| /** | |
| * Class 회원 마스킹 처리 | |
| * @package Bundle\Component\Member | |
| */ | |
| public function masking($menu, $type, $string){ | |
| // 이미 개인정보 은닉 처리된 값('-' 또는 "탈퇴회원"/"휴면회원")은 부분마스킹으로 덧칠하지 않는다 | |
| if ($string === ColumnMaskingService::DEFAULT_MASK || MaskingTargetService::isMaskLabel($string)) { | |
| return $string; | |
| } | |
| if ($menu == 'order') { | |
| if ($this->orderMaskingUseFl != 'y') { | |
| return $string; | |
변경 전MemberSleep.php
| $this->dao->updateMemberByEncrypt($sleepInfo, $this->sleepEncryptField); | |
| \DB::commit(); | |
| $return[] = $sleepInfo; | |
| } catch (Exception $e) { | |
| \DB::rollback(); | |
| try { | |
| \DB::begin_tran(); | |
| $this->dao->updateMemberByWake($wakeData); | |
| $this->dao->deleteSleepBySleepNo($wakeData['sleepNo']); | |
| \DB::commit(); | |
| } catch (Exception $e) { | |
| $db->begin_tran(); | |
| $this->dao->updateMemberByDecrypt($decryptInfo, $info['memNo']); | |
| $this->dao->deleteSleep($info['sleepNo']); | |
| if ($sleepPolicy->isExpireMileageWakeMember()) { | |
| $this->expireMileageByWakeMember($info['memNo']); | |
변경 후MemberSleep.php
| $this->dao->updateMemberByEncrypt($sleepInfo, $this->sleepEncryptField); | |
| \DB::commit(); | |
| // 주문 PII 분리 | |
| try { | |
| \App::getInstance(\Origin\Service\Privacy\Withdrawn\WithdrawnMemberOrderSeparatorService::class) | |
| ->separate((int) $info['memNo'], \Origin\Enum\Privacy\Withdrawn\WithdrawnMemberType::SLEEP); | |
| } catch (\Throwable $e) { | |
| \App::getInstance('logger')->error('withdrawn sleep order separate failed', [ | |
| 'exception' => $e, | |
| 'memNo' => $info['memNo'], | |
| ]); | |
| } | |
| $return[] = $sleepInfo; | |
| } catch (Exception $e) { | |
| \DB::rollback(); | |
| try { | |
| \DB::begin_tran(); | |
| $this->dao->updateMemberByWake($wakeData); | |
| // 분리보관된 주문 개인정보를 원본으로 복원(\DB 트랜잭션과 같은 단일 인스턴스 전달) | |
| (new \Origin\Service\Privacy\Withdrawn\WithdrawnOrderRestorerService(\App::getInstance('DB')))->restore((int) $wakeData['memNo']); | |
| $this->dao->deleteSleepBySleepNo($wakeData['sleepNo']); | |
| \DB::commit(); | |
| } catch (Exception $e) { | |
| $db->begin_tran(); | |
| $this->dao->updateMemberByDecrypt($decryptInfo, $info['memNo']); | |
| // 분리보관된 주문 개인정보를 원본으로 복원(wake 트랜잭션 공유 위해 같은 $db 전달) | |
| (new \Origin\Service\Privacy\Withdrawn\WithdrawnOrderRestorerService($db))->restore((int) $info['memNo']); | |
| $this->dao->deleteSleep($info['sleepNo']); | |
| if ($sleepPolicy->isExpireMileageWakeMember()) { | |
| $this->expireMileageByWakeMember($info['memNo']); | |
변경 전SleepDAO.php
| $this->db->set_insert_db(DB_MEMBER_SLEEP, $arrBind['param'], $arrBind['bind'], 'y'); | |
| } | |
| /** | |
| * 휴면번호 해당 휴면정보 삭제 | |
| * | |
변경 후SleepDAO.php
| $this->db->set_insert_db(DB_MEMBER_SLEEP, $arrBind['param'], $arrBind['bind'], 'y'); | |
| } | |
| /** | |
| * 전일 휴면 전환된 회원 목록(주문 PII 분리 배치용). | |
| * | |
| * @return array 회원 행 목록([{memNo}]) | |
| */ | |
| public function getSleepMembersAtYesterday(): array | |
| { | |
| $from = date('Y-m-d 00:00:00', strtotime('-1 day')); | |
| $to = date('Y-m-d 23:59:59', strtotime('-1 day')); | |
| $arrBind = []; | |
| $this->db->bind_param_push($arrBind, 's', $from); | |
| $this->db->bind_param_push($arrBind, 's', $to); | |
| $strSQL = 'SELECT memNo FROM ' . DB_MEMBER_SLEEP . ' WHERE sleepDt BETWEEN ? AND ? GROUP BY memNo'; | |
| return $this->db->secondary()->query_fetch($strSQL, $arrBind); | |
| } | |
| /** | |
| * 휴면번호 해당 휴면정보 삭제 | |
| * | |
변경 전SleepService.php
| use Component\Sms\SmsAutoCode; | |
| use Framework\Utility\DateTimeUtils; | |
| use Framework\Utility\StringUtils; | |
| /** | |
| * 휴면회원 | |
| $db->commit(); | |
| $this->sleepResult['success']++; | |
| // 추가로 당일 안내 SMS발송 | |
| $aMemInfo = $oMember->getMemberId($member['memNo']); | |
| $replace = [ | |
| $this->sleepDAO->updateMemberByEncrypt($sleepInfo, $this->sleepEncryptField); | |
| \DB::commit(); | |
| $return[] = $sleepInfo; | |
| } catch (\Exception $e) { | |
| \DB::rollback(); | |
| throw $e; | |
| } | |
| } | |
| /** | |
| * 휴면회원 sms 발송함 저장 | |
| * @deprecated 2017-02-06 yjwee MySQL 연결시간 초과 이슈 수정을 위해 사용하지 않습니다. | |
변경 후SleepService.php
| use Component\Sms\SmsAutoCode; | |
| use Framework\Utility\DateTimeUtils; | |
| use Framework\Utility\StringUtils; | |
| use Origin\Service\Privacy\Withdrawn\WithdrawnMemberOrderSeparatorService; | |
| use Origin\Enum\Privacy\Withdrawn\WithdrawnMemberType; | |
| /** | |
| * 휴면회원 | |
| $db->commit(); | |
| $this->sleepResult['success']++; | |
| // 주문 PII 분리 | |
| $this->separateSleepOrderPii((int) $member['memNo']); | |
| // 추가로 당일 안내 SMS발송 | |
| $aMemInfo = $oMember->getMemberId($member['memNo']); | |
| $replace = [ | |
| $this->sleepDAO->updateMemberByEncrypt($sleepInfo, $this->sleepEncryptField); | |
| \DB::commit(); | |
| $return[] = $sleepInfo; | |
| // 주문 PII 분리 | |
| $this->separateSleepOrderPii((int) $member['memNo']); | |
| } catch (\Exception $e) { | |
| \DB::rollback(); | |
| throw $e; | |
| } | |
| } | |
| /** | |
| * 휴면 전환 커밋 후 회원의 주문 PII 를 분리보관으로 옮긴다. 실패해도 전환은 유지되고 D+1 배치가 보정한다. | |
| */ | |
| private function separateSleepOrderPii(int $memNo): void | |
| { | |
| try { | |
| \App::getInstance(WithdrawnMemberOrderSeparatorService::class)->separate($memNo, WithdrawnMemberType::SLEEP); | |
| } catch (\Throwable $e) { | |
| \App::getInstance('logger')->error('withdrawn sleep order separate failed', [ | |
| 'exception' => $e, | |
| 'memNo' => $memNo, | |
| ]); | |
| } | |
| } | |
| /** | |
| * 전일 휴면 전환된 회원 목록(주문 PII 분리 D+1 배치용). | |
| * | |
| * @return array 회원 행 목록([{memNo}]) | |
| */ | |
| public function getSleepMembersAtYesterday(): array | |
| { | |
| return $this->sleepDAO->getSleepMembersAtYesterday(); | |
| } | |
| /** | |
| * 휴면회원 sms 발송함 저장 | |
| * @deprecated 2017-02-06 yjwee MySQL 연결시간 초과 이슈 수정을 위해 사용하지 않습니다. | |
변경 전Order.php
| use Component\Goods\MailStock; | |
| use Encryptor; | |
| use Exception; | |
| use Framework\Application\Bootstrap\Log; | |
| use Framework\Debug\Exception\AlertOnlyException; | |
| use Framework\Debug\Exception\AlertRedirectException; | |
| throw new Exception(self::TEXT_NOT_EXIST_ORDER_INFO); | |
| } | |
| // 남기실 내용 | |
| $getData['orderMemo'] = nl2br($getData['orderMemo']); | |
변경 후Order.php
| use Component\Goods\MailStock; | |
| use Encryptor; | |
| use Exception; | |
| use Origin\Enum\Privacy\Withdrawn\WithdrawnMemberType; | |
| use Origin\Enum\Privacy\Withdrawn\WithdrawnSection; | |
| use Origin\Service\Privacy\Withdrawn\WithdrawnOrderHydratorService; | |
| use Framework\Application\Bootstrap\Log; | |
| use Framework\Debug\Exception\AlertOnlyException; | |
| use Framework\Debug\Exception\AlertRedirectException; | |
| throw new Exception(self::TEXT_NOT_EXIST_ORDER_INFO); | |
| } | |
| // [휴면 복원] | |
| // - 원복 데이터: 주문자 PII(orderName·orderCellPhone·orderEmail 등) | |
| // - 용도: 주문상태 변경 등에서 발송되는 자동 SMS/메일의 수신자 정보 | |
| // - 대상: 휴면만(탈퇴는 레거시 D+1 배치가 이미 공백 처리하던 baseline 유지. 분리보관 완료 플래그로 판정해 일반 주문은 분리보관 조회 생략) | |
| if (($getData['separationStatus'] ?? '') === WithdrawnMemberType::SLEEP->value) { | |
| $getData = \App::getInstance(WithdrawnOrderHydratorService::class) | |
| ->restore($getData, WithdrawnSection::ORDER_INFO, WithdrawnMemberType::SLEEP, $orderNo); | |
| } | |
| // 남기실 내용 | |
| $getData['orderMemo'] = nl2br($getData['orderMemo']); | |
변경 전OrderAdmin.php
| namespace Bundle\Component\Order; | |
| use App; | |
| use Bundle\Component\Excel\Reader; | |
| use Component\Bankda\BankdaOrder; | |
| use Component\Database\DBTableField; | |
| $this->arrWhere[] = '(' . gd_implode(' OR ', $arrWhereAll) . ')'; | |
| unset($tmpWhere); | |
| } else { | |
| if ($this->search['key'] == 'o.orderNo') { //네이버페이 사용중이고 주문번호 단일 검색일 경우 주문번호는 equal 검색 | |
| if ($this->getNaverPayConfig('useYn') == 'y') { | |
| $this->arrWhere[] = '(' . $this->search['key'] . ' = ? OR apiOrderNo = ? )'; | |
| } | |
| } else if ($searchType == 'equalSearch') { | |
| if (strpos($this->search['key'], 'Phone') !== false) { | |
| $this->arrWhere[] = '(REPLACE(' . $this->search['key'] . ', "-", "") = ?)'; | |
| } else { | |
| $this->arrWhere[] = '(' . $this->search['key'] . ' = ?)'; | |
| } | |
| } else if ($searchType == 'endLikeSearch') { | |
| $this->arrWhere[] = '(' . $this->search['key'] . ' LIKE concat(?,\'%\'))'; | |
| } else { | |
| $keyword = $this->search['keyword']; | |
| } | |
| $this->db->bind_param_push($this->arrBind, 's', $keyword); | |
| } | |
| } | |
| } | |
| unset($tmpField, $tmpKey); | |
| // 현 페이지 결과 | |
| $this->db->strField = 'og.sno,og.orderNo,og.goodsNo,og.scmNo ,og.mallSno ,og.purchaseNo ,o.memNo, o.trackingKey, o.orderTypeFl, o.appOs, o.pushCode ,' . gd_implode(', ', $arrField) . ',og.orderDeliverySno'; | |
| // addGoods 필드 변경 처리 (goods와 동일해서) | |
| $this->db->strJoin = gd_implode('', $join); | |
| $data[$val['orderNo']]['goods'][] = $val; | |
| $data[$val['orderNo']]['adminOrdGoodsMemo'] = false; | |
| // 탈퇴회원의 개인정보 데이터 | |
| $withdrawnMembersOrderData = $this->getWithdrawnMembersOrderViewByOrderNo($val['orderNo']); | |
| $withdrawnMembersPersonalData = $withdrawnMembersOrderData['personalInfo'][0]; | |
| $data[$val['orderNo']]['withdrawnMembersPersonalData'] = $withdrawnMembersPersonalData; | |
| } | |
| } | |
| // 주문 상품 정보 | |
| $orderGoods = $this->getOrderGoodsData($orderNo, $orderGoodsNo, null, null, 'admin', true, true, null, $excludeStatus, false, $useMultiShippingKey); | |
| //복수배송지를 사용 중이며 리스트에서 노출시킬 목적으로만 사용중이면 주문데이터 배열의 scmNo 를 orderInfoSno로 대체한다. : true 일시 | |
| $getData['useMultiShippingKey'] = $useMultiShippingKey; | |
| 'o.orderChannelFl', | |
| 'o.apiOrderNo', | |
| 'o.memNo', | |
| 'o.orderChannelFl', | |
| 'o.orderGoodsNm', | |
| 'o.orderGoodsCnt', | |
| */ | |
| public function getWithdrawnMembersOrderViewByOrderNo($orderNo) | |
| { | |
| $arrBind = []; | |
| $this->db->bind_param_push($arrBind, 's', $orderNo); | |
| $strSQL = 'SELECT * FROM ' . DB_MEMBER_HACKOUT_ORDER . ' WHERE orderNo = ?'; | |
변경 후OrderAdmin.php
| namespace Bundle\Component\Order; | |
| use App; | |
| use Origin\Enum\Privacy\Withdrawn\WithdrawnMemberType; | |
| use Origin\Enum\Privacy\Withdrawn\WithdrawnSection; | |
| use Origin\Repository\Order\OrderRepository; | |
| use Origin\Service\Privacy\Withdrawn\WithdrawnOrderHydratorService; | |
| use Origin\Service\Privacy\Withdrawn\WithdrawnOrderSearchService; | |
| use Bundle\Component\Excel\Reader; | |
| use Component\Bankda\BankdaOrder; | |
| use Component\Database\DBTableField; | |
| $this->arrWhere[] = '(' . gd_implode(' OR ', $arrWhereAll) . ')'; | |
| unset($tmpWhere); | |
| } else { | |
| $withdrawnOrderNos = []; // 분리보관에서 정확일치로 찾은 주문번호 | |
| if ($this->search['key'] == 'o.orderNo') { //네이버페이 사용중이고 주문번호 단일 검색일 경우 주문번호는 equal 검색 | |
| if ($this->getNaverPayConfig('useYn') == 'y') { | |
| $this->arrWhere[] = '(' . $this->search['key'] . ' = ? OR apiOrderNo = ? )'; | |
| } | |
| } else if ($searchType == 'equalSearch') { | |
| if (strpos($this->search['key'], 'Phone') !== false) { | |
| $equalWhere = '(REPLACE(' . $this->search['key'] . ', "-", "") = ?)'; | |
| } else { | |
| $equalWhere = '(' . $this->search['key'] . ' = ?)'; | |
| } | |
| // [탈퇴/휴면 검색] | |
| // - 검색 매칭: 주문자명·수령자명·연락처·이메일·입금자명 정확일치 | |
| // - 용도: 분리보관으로 원본이 공백인 주문을 분리보관(암호문)에서 찾아 함께 조회 | |
| // - 대상: 탈퇴·휴면 둘 다 | |
| $withdrawnOrderNos = \App::getInstance(WithdrawnOrderSearchService::class) | |
| ->findOrderNosByOrderSearchKey((string) $this->search['key'], (string) $this->search['keyword']); | |
| if (empty($withdrawnOrderNos) === false) { | |
| $equalWhere = '(' . $equalWhere . ' OR o.orderNo IN (' . gd_implode(',', array_fill(0, count($withdrawnOrderNos), '?')) . '))'; | |
| } | |
| $this->arrWhere[] = $equalWhere; | |
| } else if ($searchType == 'endLikeSearch') { | |
| $this->arrWhere[] = '(' . $this->search['key'] . ' LIKE concat(?,\'%\'))'; | |
| } else { | |
| $keyword = $this->search['keyword']; | |
| } | |
| $this->db->bind_param_push($this->arrBind, 's', $keyword); | |
| foreach ($withdrawnOrderNos as $withdrawnOrderNo) { | |
| $this->db->bind_param_push($this->arrBind, 's', $withdrawnOrderNo); | |
| } | |
| } | |
| } | |
| } | |
| unset($tmpField, $tmpKey); | |
| // 현 페이지 결과 | |
| $this->db->strField = 'og.sno,og.orderNo,og.goodsNo,og.scmNo ,og.mallSno ,og.purchaseNo ,o.memNo, o.trackingKey, o.orderTypeFl, o.appOs, o.pushCode, o.separationStatus ,' . gd_implode(', ', $arrField) . ',og.orderDeliverySno'; | |
| // addGoods 필드 변경 처리 (goods와 동일해서) | |
| $this->db->strJoin = gd_implode('', $join); | |
| $data[$val['orderNo']]['goods'][] = $val; | |
| $data[$val['orderNo']]['adminOrdGoodsMemo'] = false; | |
| // [탈퇴 복원] | |
| // - 원복 데이터: 탈퇴회원 주문 PII 표시값(withdrawnMembersPersonalData) | |
| // - 용도: 주문/클레임 리스트 표기 | |
| // - 대상: 탈퇴만(분리보관 완료 플래그로 판정해 일반 주문은 분리보관 조회 생략) | |
| $withdrawnMembersPersonalData = null; | |
| if (($val['separationStatus'] ?? '') === WithdrawnMemberType::HACKOUT->value) { | |
| $withdrawnMembersOrderData = $this->getWithdrawnMembersOrderViewByOrderNo($val['orderNo']); | |
| $withdrawnMembersPersonalData = $withdrawnMembersOrderData['personalInfo'][0] ?? null; | |
| } | |
| $data[$val['orderNo']]['withdrawnMembersPersonalData'] = $withdrawnMembersPersonalData; | |
| } | |
| } | |
| // 주문 상품 정보 | |
| $orderGoods = $this->getOrderGoodsData($orderNo, $orderGoodsNo, null, null, 'admin', true, true, null, $excludeStatus, false, $useMultiShippingKey); | |
| // [탈퇴/휴면 복원] | |
| // - 원복 데이터: 환불계좌(refundBankName/refundDepositor + refundAccountNumber passthrough) | |
| // - 용도: 환불/반품 정보 탭 표기와 수정 폼 프리필. 수정 폼은 분리 전 값이 필요하고, 읽기 전용 표기는 뷰에서 하이픈으로 대체한다 | |
| // - 대상: 탈퇴·휴면 둘 다(분리보관 완료 플래그로 판정해 일반 주문은 분리보관 조회 생략) | |
| $refundSeparationType = WithdrawnMemberType::tryFrom($getData['separationStatus'] ?? ''); | |
| if (is_array($orderGoods) === true && $refundSeparationType !== null) { | |
| $withdrawnHydrator = \App::getInstance(WithdrawnOrderHydratorService::class); | |
| foreach ($orderGoods as $scmNo => $goodsRows) { | |
| if (is_array($goodsRows) === false) { | |
| continue; | |
| } | |
| foreach ($goodsRows as $goodsKey => $goodsRow) { | |
| if (is_array($goodsRow) === false || empty($goodsRow['handleSno']) === true) { | |
| continue; | |
| } | |
| $goodsRow = $withdrawnHydrator->restore($goodsRow, WithdrawnSection::REFUND, $refundSeparationType, $goodsRow['handleSno']); | |
| if (gd_str_length($goodsRow['refundAccountNumber']) > 50) { | |
| $goodsRow['refundAccountNumber'] = \Encryptor::decrypt($goodsRow['refundAccountNumber']); | |
| } | |
| $orderGoods[$scmNo][$goodsKey] = $goodsRow; | |
| } | |
| } | |
| } | |
| //복수배송지를 사용 중이며 리스트에서 노출시킬 목적으로만 사용중이면 주문데이터 배열의 scmNo 를 orderInfoSno로 대체한다. : true 일시 | |
| $getData['useMultiShippingKey'] = $useMultiShippingKey; | |
| 'o.orderChannelFl', | |
| 'o.apiOrderNo', | |
| 'o.memNo', | |
| 'o.separationStatus', | |
| 'o.orderChannelFl', | |
| 'o.orderGoodsNm', | |
| 'o.orderGoodsCnt', | |
| */ | |
| public function getWithdrawnMembersOrderViewByOrderNo($orderNo) | |
| { | |
| // 분리보관 완료 플래그(es_order.separationStatus)가 탈퇴가 아니면 분리보관 조회 없이 빈 결과(일반/휴면 주문 비용 절감) | |
| $separationStatusMap = \App::getInstance(OrderRepository::class)->findSeparationStatusByOrderNos([$orderNo]); | |
| if (($separationStatusMap[$orderNo] ?? '') !== WithdrawnMemberType::HACKOUT->value) { | |
| return ['personalInfo' => [], 'refundInfo' => []]; | |
| } | |
| $arrBind = []; | |
| $this->db->bind_param_push($arrBind, 's', $orderNo); | |
| $strSQL = 'SELECT * FROM ' . DB_MEMBER_HACKOUT_ORDER . ' WHERE orderNo = ?'; | |
변경 전OrderAdminNew.php
| use Framework\Utility\StringUtils; | |
| use Globals; | |
| use LogHandler; | |
| use Origin\Enum\Order\OrderHandleMode; | |
| use Origin\Enum\Order\OrderStatusCode; | |
| use Origin\Enum\Order\OrderStatusGroup; | |
| // 주문 상품 정보 | |
| $orderGoods = $this->getOrderGoodsData($orderNo, $orderGoodsNo, null, null, 'admin', true, true, null, $excludeStatus, false, $useMultiShippingKey); | |
| //복수배송지를 사용 중이며 리스트에서 노출시킬 목적으로만 사용중이면 주문데이터 배열의 scmNo 를 orderInfoSno로 대체한다. : true 일시 | |
| $getData['useMultiShippingKey'] = $useMultiShippingKey; | |
| */ | |
| public function getWithdrawnMembersOrderViewByOrderNo($orderNo) | |
| { | |
| $arrBind = []; | |
| $this->db->bind_param_push($arrBind, 's', $orderNo); | |
| $strSQL = 'SELECT * FROM ' . DB_MEMBER_HACKOUT_ORDER . ' WHERE orderNo = ?'; | |
변경 후OrderAdminNew.php
| use Framework\Utility\StringUtils; | |
| use Globals; | |
| use LogHandler; | |
| use Origin\Enum\Order\OrderSettleKind; | |
| use Origin\Enum\Privacy\Withdrawn\WithdrawnMemberType; | |
| use Origin\Enum\Privacy\Withdrawn\WithdrawnSection; | |
| use Origin\Repository\Order\OrderRepository; | |
| use Origin\Service\Privacy\Withdrawn\WithdrawnOrderHydratorService; | |
| use Origin\Enum\Order\OrderHandleMode; | |
| use Origin\Enum\Order\OrderStatusCode; | |
| use Origin\Enum\Order\OrderStatusGroup; | |
| // 주문 상품 정보 | |
| $orderGoods = $this->getOrderGoodsData($orderNo, $orderGoodsNo, null, null, 'admin', true, true, null, $excludeStatus, false, $useMultiShippingKey); | |
| // [탈퇴/휴면 복원] | |
| // - 원복 데이터: 환불계좌(refundBankName/refundDepositor + refundAccountNumber passthrough) | |
| // - 용도: 환불처리 폼/자동환불 조회(getRefundOrderView) 표기(폼 프리필) | |
| // - 대상: 휴면만(분리보관 완료 플래그로 판정해 일반 주문은 분리보관 조회 생략) | |
| if (is_array($orderGoods) | |
| && ($getData['separationStatus'] ?? '') === WithdrawnMemberType::SLEEP->value) { | |
| $withdrawnHydrator = \App::getInstance(WithdrawnOrderHydratorService::class); | |
| foreach ($orderGoods as $scmNo => $goodsRows) { | |
| if (is_array($goodsRows) === false) { | |
| continue; | |
| } | |
| foreach ($goodsRows as $goodsKey => $goodsRow) { | |
| if (is_array($goodsRow) === false || empty($goodsRow['handleSno']) === true) { | |
| continue; | |
| } | |
| $goodsRow = $withdrawnHydrator->restore($goodsRow, WithdrawnSection::REFUND, WithdrawnMemberType::SLEEP, $goodsRow['handleSno']); | |
| if (gd_str_length($goodsRow['refundAccountNumber']) > 50) { | |
| $goodsRow['refundAccountNumber'] = \Encryptor::decrypt($goodsRow['refundAccountNumber']); | |
| } | |
| $orderGoods[$scmNo][$goodsKey] = $goodsRow; | |
| } | |
| } | |
| } | |
| //복수배송지를 사용 중이며 리스트에서 노출시킬 목적으로만 사용중이면 주문데이터 배열의 scmNo 를 orderInfoSno로 대체한다. : true 일시 | |
| $getData['useMultiShippingKey'] = $useMultiShippingKey; | |
| */ | |
| public function getWithdrawnMembersOrderViewByOrderNo($orderNo) | |
| { | |
| // 분리보관 완료 플래그(es_order.separationStatus)가 탈퇴가 아니면 분리보관 조회 없이 빈 결과(일반/휴면 주문 비용 절감) | |
| $separationStatusMap = \App::getInstance(OrderRepository::class)->findSeparationStatusByOrderNos([$orderNo]); | |
| if (($separationStatusMap[$orderNo] ?? '') !== WithdrawnMemberType::HACKOUT->value) { | |
| return ['personalInfo' => [], 'refundInfo' => []]; | |
| } | |
| $arrBind = []; | |
| $this->db->bind_param_push($arrBind, 's', $orderNo); | |
| $strSQL = 'SELECT * FROM ' . DB_MEMBER_HACKOUT_ORDER . ' WHERE orderNo = ?'; | |
변경 전OrderDelete.php
| use Component\Mall\MallDAO; | |
| use Component\Member\Manager; | |
| use Framework\Utility\ArrayUtils; | |
| class OrderDelete | |
| { | |
| 'o.orderChannelFl', | |
| 'o.apiOrderNo', | |
| 'o.memNo', | |
| 'o.orderGoodsNm', | |
| 'o.orderGoodsCnt', | |
| 'o.settlePrice as totalSettlePrice', | |
| $this->_db->bind_param_push($arrOrderUserHandleBind, 's', $val['orderNo']); | |
| $this->_db->bind_query($strOrderUserHandleSQL, $arrOrderUserHandleBind); | |
| $strMemberHackoutOrderSQL = "DELETE FROM " . DB_MEMBER_HACKOUT_ORDER . " WHERE orderNo = ? "; | |
| $arrMemberHackoutOrderBind = []; | |
| $this->_db->bind_param_push($arrMemberHackoutOrderBind, 's', $val['orderNo']); | |
| $this->_db->bind_query($strMemberHackoutOrderSQL, $arrMemberHackoutOrderBind); | |
| $strMemberHackoutOrderHandleSQL = "DELETE FROM " . DB_MEMBER_HACKOUT_ORDER_HANDLE . " WHERE orderNo = ? "; | |
| $arrMemberHackoutOrderHandleBind = []; | |
| $this->_db->bind_param_push($arrMemberHackoutOrderHandleBind, 's', $val['orderNo']); | |
| $this->_db->bind_query($strMemberHackoutOrderHandleSQL, $arrMemberHackoutOrderHandleBind); | |
| } | |
| // 상태 업데이트 | |
변경 후OrderDelete.php
| use Component\Mall\MallDAO; | |
| use Component\Member\Manager; | |
| use Framework\Utility\ArrayUtils; | |
| use Origin\Enum\Privacy\Withdrawn\WithdrawnSection; | |
| class OrderDelete | |
| { | |
| 'o.orderChannelFl', | |
| 'o.apiOrderNo', | |
| 'o.memNo', | |
| 'o.separationStatus', | |
| 'o.orderGoodsNm', | |
| 'o.orderGoodsCnt', | |
| 'o.settlePrice as totalSettlePrice', | |
| $this->_db->bind_param_push($arrOrderUserHandleBind, 's', $val['orderNo']); | |
| $this->_db->bind_query($strOrderUserHandleSQL, $arrOrderUserHandleBind); | |
| // 분리보관 테이블에도 같은 주문의 개인정보가 남아 있으므로 함께 삭제한다 | |
| foreach (WithdrawnSection::orderMirrorTables() as $separatedTable => $separatedOrderColumn) { | |
| $strSeparatedSQL = "DELETE FROM " . $separatedTable . " WHERE " . $separatedOrderColumn . " = ? "; | |
| $arrSeparatedBind = []; | |
| $this->_db->bind_param_push($arrSeparatedBind, 's', $val['orderNo']); | |
| $this->_db->bind_query($strSeparatedSQL, $arrSeparatedBind); | |
| } | |
| } | |
| // 상태 업데이트 | |
변경 전OrderNew.php
| use Component\Goods\MailStock; | |
| use Encryptor; | |
| use Exception; | |
| use Framework\Application\Bootstrap\Log; | |
| use Framework\Debug\Exception\AlertOnlyException; | |
| use Framework\Debug\Exception\AlertRedirectException; | |
| throw new Exception(self::TEXT_NOT_EXIST_ORDER_INFO); | |
| } | |
| // 남기실 내용 | |
| $getData['orderMemo'] = nl2br($getData['orderMemo']); | |
변경 후OrderNew.php
| use Component\Goods\MailStock; | |
| use Encryptor; | |
| use Exception; | |
| use Origin\Enum\Privacy\Withdrawn\WithdrawnMemberType; | |
| use Origin\Enum\Privacy\Withdrawn\WithdrawnSection; | |
| use Origin\Service\Privacy\Withdrawn\WithdrawnOrderHydratorService; | |
| use Framework\Application\Bootstrap\Log; | |
| use Framework\Debug\Exception\AlertOnlyException; | |
| use Framework\Debug\Exception\AlertRedirectException; | |
| throw new Exception(self::TEXT_NOT_EXIST_ORDER_INFO); | |
| } | |
| // [휴면 복원] | |
| // - 원복 데이터: 주문자 PII(orderName·orderCellPhone·orderEmail 등) | |
| // - 용도: 주문상태 변경 등에서 발송되는 자동 SMS/메일의 수신자 정보 | |
| // - 대상: 휴면만(탈퇴는 레거시 D+1 배치가 이미 공백 처리하던 baseline 유지. 분리보관 완료 플래그로 판정해 일반 주문은 분리보관 조회 생략) | |
| if (($getData['separationStatus'] ?? '') === WithdrawnMemberType::SLEEP->value) { | |
| $getData = \App::getInstance(WithdrawnOrderHydratorService::class) | |
| ->restore($getData, WithdrawnSection::ORDER_INFO, WithdrawnMemberType::SLEEP, $orderNo); | |
| } | |
| // 남기실 내용 | |
| $getData['orderMemo'] = nl2br($getData['orderMemo']); | |
변경 전ReOrderCalculation.php
| use Framework\Utility\NumberUtils; | |
| use Globals; | |
| use Origin\Enum\Payment\Sunrate\SunrateCommonCode; | |
| use Origin\Service\WebHook\OrderWebHookService; | |
| use Origin\Enum\Statistics\Analytics\Order\ClaimType; | |
| use Origin\Service\Statistics\Analytics\Order\ClaimCompleteAnalyticsCollectorService; | |
| // 마일리지 배송비 패치여부 및 설정값 | |
| $mileageUseDeliveryFl = $orderAdmin->getOrderCurrentMileagePolicy($getData['orderNo'])['use']['mileageUseDeliveryFl']; | |
| // 이미 환불 완료인 경우 제외 (중복 환불 방지) | |
| if (empty($getData['refund']) === false) { | |
| $confirmRefundCompletion = $this->confirmRefundCompletion($getData['orderNo'], gd_array_keys($getData['refund'])); | |
| $updateHandleData[$handleSno]['handleDt'] = date('Y-m-d H:i:s'); // 환불완료 변경 플래그 | |
| $updateHandleData[$handleSno]['refundGroupCd'] = $refundGroupCd; // 환불그룹 코드 | |
| $updateHandleData[$handleSno]['refundMethod'] = $getData['info']['refundMethod']; | |
| $updateHandleData[$handleSno]['refundBankName'] = $getData['info']['refundBankName']; | |
| $updateHandleData[$handleSno]['refundAccountNumber'] = $getData['info']['refundAccountNumber']; | |
| $updateHandleData[$handleSno]['refundDepositor'] = $getData['info']['refundDepositor']; | |
| $updateHandleData[$handleSno]['refundCharge'] = $getData['refundCharge' . $handleSno]; | |
| $updateHandleData[$handleSno]['refundDeliveryInsuranceFee'] = $getData['check']['totalDeliveryInsuranceFee']; // 해외배송 보증금은 무조건 넣어줌 | |
| } | |
| public function completeRefundPrice($getData, $orderInfo, $refundRealTaxData) | |
| { | |
| try { | |
| // 현금환불 처리 | |
| if ($getData['info']['completeCashPrice'] > 0) { | |
| $completeCashPrice = gd_money_format($getData['info']['completeCashPrice'], false); | |
| $where = " WHERE orderNo = '" . $orderNo . "' AND claimStatus='" . $claimStatus . "' "; | |
| // 주문복원 | |
| $orderCommonColumns = $this->getCommonField(DB_ORDER, DB_ORDER_ORIGINAL); | |
| if(gd_count($orderCommonColumns) > 0){ | |
| $value[$field] = str_replace("\\'", "'", $value[$field]); | |
| } | |
| } | |
| $arrBind = $this->db->get_binding(DBTableField::tableOrder(), $value, 'insert'); | |
| try { | |
| $this->db->set_insert_db_query(DB_ORDER, $arrBind['param'], $arrBind['bind'], 'y', $value['regDt']); | |
| } | |
| } | |
| $arrBind = $this->db->get_binding(DBTableField::tableOrderGoods(), $value, 'insert'); | |
| $arrBind['param'][] = 'sno'; | |
| $this->db->bind_param_push($arrBind['bind'], 'i', $value['sno']); | |
| if(gd_count($orderCashReceiptOriginalData) > 0){ | |
| foreach($orderCashReceiptOriginalData as $key => $value){ | |
| $arrBind = $this->db->get_binding(DBTableField::tableOrderCashReceipt(), $value, 'insert'); | |
| $arrBind['param'][] = 'sno'; | |
| $this->db->bind_param_push($arrBind['bind'], 'i', $value['sno']); | |
변경 후ReOrderCalculation.php
| use Framework\Utility\NumberUtils; | |
| use Globals; | |
| use Origin\Enum\Payment\Sunrate\SunrateCommonCode; | |
| use Origin\Service\Privacy\Withdrawn\WithdrawnOrderSeparatorService; | |
| use Origin\Service\Privacy\Withdrawn\WithdrawnRefundAccountService; | |
| use Origin\Service\WebHook\OrderWebHookService; | |
| use Origin\Enum\Statistics\Analytics\Order\ClaimType; | |
| use Origin\Service\Statistics\Analytics\Order\ClaimCompleteAnalyticsCollectorService; | |
| // 마일리지 배송비 패치여부 및 설정값 | |
| $mileageUseDeliveryFl = $orderAdmin->getOrderCurrentMileagePolicy($getData['orderNo'])['use']['mileageUseDeliveryFl']; | |
| // [탈퇴/휴면 분리] | |
| // - 분리 데이터: 환불계좌(refundBankName/refundAccountNumber/refundDepositor) | |
| // - 용도: 분리보관 주문은 수정 폼에 계좌 입력칸이 없어 값이 비어 오므로, 그대로 기록하면 공백이어야 할 원본이 NULL 로 덮인다 | |
| // - 대상: 탈퇴·휴면 둘 다(분리보관 완료 플래그로 판정) | |
| $refundAccountColumns = \App::getInstance(WithdrawnRefundAccountService::class) | |
| ->buildHandleAccountColumns((string) $getData['orderNo'], $getData['info']); | |
| // 이미 환불 완료인 경우 제외 (중복 환불 방지) | |
| if (empty($getData['refund']) === false) { | |
| $confirmRefundCompletion = $this->confirmRefundCompletion($getData['orderNo'], gd_array_keys($getData['refund'])); | |
| $updateHandleData[$handleSno]['handleDt'] = date('Y-m-d H:i:s'); // 환불완료 변경 플래그 | |
| $updateHandleData[$handleSno]['refundGroupCd'] = $refundGroupCd; // 환불그룹 코드 | |
| $updateHandleData[$handleSno]['refundMethod'] = $getData['info']['refundMethod']; | |
| $updateHandleData[$handleSno] = array_merge($updateHandleData[$handleSno], $refundAccountColumns); | |
| $updateHandleData[$handleSno]['refundCharge'] = $getData['refundCharge' . $handleSno]; | |
| $updateHandleData[$handleSno]['refundDeliveryInsuranceFee'] = $getData['check']['totalDeliveryInsuranceFee']; // 해외배송 보증금은 무조건 넣어줌 | |
| } | |
| public function completeRefundPrice($getData, $orderInfo, $refundRealTaxData) | |
| { | |
| try { | |
| // [탈퇴/휴면 복원] | |
| // - 원복 데이터: 환불계좌(refundBankName/refundDepositor + refundAccountNumber passthrough) | |
| // - 용도: 가상계좌 PG환불 요청값. 분리보관 주문은 수정 폼에 계좌 입력칸이 없으므로 PG 호출 직전에만 복원하고 원본에는 다시 기록하지 않는다 | |
| // - 대상: 탈퇴·휴면 둘 다(분리보관 완료 플래그로 판정해 일반 주문은 분리보관 조회 생략) | |
| $getData['info'] = \App::getInstance(WithdrawnRefundAccountService::class) | |
| ->restoreForPgRefund((string) ($getData['orderNo'] ?? ''), (int) ($getData['handleSno'] ?? 0), $getData['info']); | |
| // 현금환불 처리 | |
| if ($getData['info']['completeCashPrice'] > 0) { | |
| $completeCashPrice = gd_money_format($getData['info']['completeCashPrice'], false); | |
| $where = " WHERE orderNo = '" . $orderNo . "' AND claimStatus='" . $claimStatus . "' "; | |
| // [탈퇴/휴면 분리] | |
| // - 분리 데이터: 클레임 원복 대상 원본 스냅샷(*Original) PII | |
| // - 용도: live 로 되돌리지 않고 공백 기록(분리무효화 방지, 값은 주문 PII 분리보관가 이미 보유) | |
| // - 대상: 탈퇴·휴면 둘 다 | |
| $withdrawnSeparator = \App::getInstance(WithdrawnOrderSeparatorService::class); | |
| $separationType = $withdrawnSeparator->resolveOrderMemberType($orderNo); | |
| $isSeparatedOrder = $separationType !== null; | |
| // 주문복원 | |
| $orderCommonColumns = $this->getCommonField(DB_ORDER, DB_ORDER_ORIGINAL); | |
| if(gd_count($orderCommonColumns) > 0){ | |
| $value[$field] = str_replace("\\'", "'", $value[$field]); | |
| } | |
| } | |
| // [탈퇴/휴면 분리] es_orderOriginal 분리 PII(DDL A-3)를 분리 주문이면 live 에 공백으로 기록 | |
| if ($isSeparatedOrder === true) { | |
| $value = $withdrawnSeparator->blankColumns($value, ['bankSender', 'orderEmail', 'bankdaManualMangerId']); | |
| } | |
| // 분리보관 완료 표시는 백업 시점 값이 아니라 되돌리는 시점의 현재 값으로 기록(과거 백업 복원으로 표시가 어긋나는 것 방지) | |
| $value['separationStatus'] = $separationType?->value ?? ''; | |
| $arrBind = $this->db->get_binding(DBTableField::tableOrder(), $value, 'insert'); | |
| try { | |
| $this->db->set_insert_db_query(DB_ORDER, $arrBind['param'], $arrBind['bind'], 'y', $value['regDt']); | |
| } | |
| } | |
| // [탈퇴/휴면 분리] es_orderGoodsOriginal 분리 PII(DDL A-4: visitAddress)를 분리 주문이면 live 에 공백으로 기록 | |
| if ($isSeparatedOrder === true) { | |
| $value = $withdrawnSeparator->blankColumns($value, ['visitAddress']); | |
| } | |
| $arrBind = $this->db->get_binding(DBTableField::tableOrderGoods(), $value, 'insert'); | |
| $arrBind['param'][] = 'sno'; | |
| $this->db->bind_param_push($arrBind['bind'], 'i', $value['sno']); | |
| if(gd_count($orderCashReceiptOriginalData) > 0){ | |
| foreach($orderCashReceiptOriginalData as $key => $value){ | |
| // [탈퇴/휴면 분리] es_orderCashReceiptOriginal 분리 PII(현금영수증 신청자 정보)를 분리 주문이면 live 에 공백으로 기록 | |
| if ($isSeparatedOrder === true) { | |
| $value = $withdrawnSeparator->blankColumns($value, ['requestNm', 'requestIP', 'requestEmail', 'requestCellPhone']); | |
| } | |
| $arrBind = $this->db->get_binding(DBTableField::tableOrderCashReceipt(), $value, 'insert'); | |
| $arrBind['param'][] = 'sno'; | |
| $this->db->bind_param_push($arrBind['bind'], 'i', $value['sno']); | |
변경 전Tax.php
| use Framework\Security\XXTEA; | |
| use Framework\SimpleCache\Lock\LockException; | |
| use Framework\SimpleCache\SimpleCache; | |
| /** | |
| $this->db->bind_param_push($_arrBind['bind'], 'i', $arrData['sno']); | |
| $this->db->set_update_db(DB_ORDER_TAX, $_arrBind['param'], 'sno = ?', $_arrBind['bind']); | |
| } else { | |
| // 로그 저장 | |
| $arrData['taxLog'] = $taxLog; | |
| $_arrBind = $this->db->get_binding(DBTableField::tableOrderTax(), $arrData, 'insert'); | |
| $this->db->set_insert_db(DB_ORDER_TAX, $_arrBind['param'], $_arrBind['bind'], 'y'); | |
| // 주문 정보 수정 | |
| $order = \App::load('\\Component\\Order\\OrderAdmin'); | |
| $order->setOrderReceiptRequest($arrData['orderNo'], 't'); | |
| $this->db->set_update_db(DB_ORDER_TAX, $_arrBind['param'], 'sno = ?', $_arrBind['bind']); | |
| unset($_arrBind); | |
| //발행관련 통계데이터 | |
| $taxIssueData['orderNo'] = $arrData['orderNo']; | |
| $taxIssueData['taxBusiNo'] = $arrData['taxBusiNo']; | |
| //주문상품명 재조합하기위한 테이터 | |
| $getData = $this->db->query_fetch($strSQL, $_arrBind, false); | |
| $excludeStatus = ['e1', 'e2', 'e3', 'e4', 'e5', 'c1', 'c2', 'c3', 'c4', 'c5', 'r1', 'r2', 'c3']; | |
| $orderGoodsData = $order->getOrderGoodsData($orderNo, null, null,null, null, true, false, null, $excludeStatus); | |
| if(gd_count($orderGoodsData) > 0){ | |
| // 키워드 검색 | |
| if ($this->_search['key'] && $this->_search['keyword']) { | |
| if ($this->_search['key'] == 'all') { | |
| $tmpWhere = gd_array_keys($this->_search['combineSearch']); | |
| array_shift($tmpWhere); | |
| $_arrWhereAll = []; | |
| //exit; | |
| $data = $this->db->query_fetch($strSQL, $this->_arrBind); | |
| $order = \App::load('\\Component\\Order\\OrderAdmin'); | |
| //계산관련 | |
| $setData['statusFl'] = "y"; | |
| $setData['godobillSend'] = "y"; | |
| try { | |
| $this->db->begin_tran(); | |
| $result = SimpleCache::init(SimpleCache::REDIS) | |
| // 주문 정보 | |
| $this->_arrWhere[] = 'o.orderNo = ?'; | |
| $this->db->bind_param_push($this->_arrBind, 's', $setData['orderNo']); | |
| $this->db->strField = 'o.orderGoodsNm, oi.orderEmail, oi.orderCellPhone'; | |
| $this->db->strJoin = ' INNER JOIN ' . DB_ORDER_INFO . ' oi ON o.orderNo = oi.orderNo AND oi.orderInfoCd = 1 '; | |
| $this->db->strWhere = gd_implode(' AND ', gd_isset($this->_arrWhere)); | |
| $query = $this->db->query_complete(); | |
| } | |
| unset($order, $orderGoodsCnt); | |
| $arrData['DMDER_BUSNID_TP_CD'] = '01'; // 사업자등록번호 구분코드(01 사업자등록번호,02 주민등록번호,03 외국인) | |
| $arrData['DMDER_BUSNID'] = str_replace('-', '', $setData['taxBusiNo']); // 사업자등록번호 | |
| $arrData['DMDER_SUB_BD_NO'] = ''; // 종사업자등록번호 | |
변경 후Tax.php
| use Framework\Security\XXTEA; | |
| use Framework\SimpleCache\Lock\LockException; | |
| use Framework\SimpleCache\SimpleCache; | |
| use Origin\Enum\Privacy\Withdrawn\WithdrawnMemberType; | |
| use Origin\Enum\Privacy\Withdrawn\WithdrawnSection; | |
| use Origin\Service\Privacy\Withdrawn\WithdrawnOrderHydratorService; | |
| use Origin\Service\Privacy\Withdrawn\WithdrawnOrderSearchService; | |
| use Origin\Service\Privacy\Withdrawn\WithdrawnOrderSeparatorService; | |
| /** | |
| $this->db->bind_param_push($_arrBind['bind'], 'i', $arrData['sno']); | |
| $this->db->set_update_db(DB_ORDER_TAX, $_arrBind['param'], 'sno = ?', $_arrBind['bind']); | |
| // [탈퇴/휴면 재분리] 수정 폼이 보낸 신청자 PII 가 원본에 되돌아오므로 분리보관에 반영하고 원본은 다시 공백 처리 | |
| \App::getInstance(WithdrawnOrderSeparatorService::class) | |
| ->separateOrderTax((string) $arrData['orderNo'], (int) $arrData['sno'], $arrData); | |
| } else { | |
| // 로그 저장 | |
| $arrData['taxLog'] = $taxLog; | |
| $_arrBind = $this->db->get_binding(DBTableField::tableOrderTax(), $arrData, 'insert'); | |
| $this->db->set_insert_db(DB_ORDER_TAX, $_arrBind['param'], $_arrBind['bind'], 'y'); | |
| // [탈퇴/휴면 재분리] 신규 신청건의 신청자 PII 는 평문으로 들어가므로 즉시 분리보관으로 옮기고 원본은 공백 처리 | |
| \App::getInstance(WithdrawnOrderSeparatorService::class) | |
| ->separateOrderTax((string) $arrData['orderNo'], (int) $this->db->insert_id(), $arrData); | |
| // 주문 정보 수정 | |
| $order = \App::load('\\Component\\Order\\OrderAdmin'); | |
| $order->setOrderReceiptRequest($arrData['orderNo'], 't'); | |
| $this->db->set_update_db(DB_ORDER_TAX, $_arrBind['param'], 'sno = ?', $_arrBind['bind']); | |
| unset($_arrBind); | |
| // [탈퇴/휴면 재분리] | |
| // - 위 UPDATE 는 발행 폼이 보낸 값을 그대로 쓰므로, 복원해 실어 보낸 신청자 PII 가 원본에 되돌아온다 | |
| // - 관리자가 화면에서 고친 값도 남겨야 하므로 저장값 기준으로 분리보관을 갱신하고 원본은 다시 공백 처리 | |
| // - 바깥(호출자) 트랜잭션에 편승한다 — 발행이 롤백되면 재분리도 함께 롤백 | |
| \App::getInstance(WithdrawnOrderSeparatorService::class) | |
| ->separateOrderTax((string) $arrData['orderNo'], (int) $arrData['sno'], $arrData); | |
| //발행관련 통계데이터 | |
| $taxIssueData['orderNo'] = $arrData['orderNo']; | |
| $taxIssueData['taxBusiNo'] = $arrData['taxBusiNo']; | |
| //주문상품명 재조합하기위한 테이터 | |
| $getData = $this->db->query_fetch($strSQL, $_arrBind, false); | |
| // [탈퇴/휴면 복원] | |
| // - 대상: 세금계산서 신청자 PII(사업장 주소 등). 분리보관으로 원본이 공백이라 | |
| // 수정 팝업 표시·변경 이력 비교·저장값이 모두 어긋난다 | |
| // - 대상 회원: 탈퇴·휴면 둘 다(분리보관 완료 플래그로 판정해 일반 주문은 분리보관 조회 생략) | |
| if (!empty($getData['sno'])) { | |
| $separationType = \App::getInstance(WithdrawnOrderSeparatorService::class) | |
| ->resolveOrderMemberType((string) $orderNo); | |
| if ($separationType !== null) { | |
| $getData = \App::getInstance(WithdrawnOrderHydratorService::class) | |
| ->restore($getData, WithdrawnSection::TAX, $separationType, $getData['sno']); | |
| } | |
| } | |
| $excludeStatus = ['e1', 'e2', 'e3', 'e4', 'e5', 'c1', 'c2', 'c3', 'c4', 'c5', 'r1', 'r2', 'c3']; | |
| $orderGoodsData = $order->getOrderGoodsData($orderNo, null, null,null, null, true, false, null, $excludeStatus); | |
| if(gd_count($orderGoodsData) > 0){ | |
| // 키워드 검색 | |
| if ($this->_search['key'] && $this->_search['keyword']) { | |
| if ($this->_search['key'] === 'requestNm' && $this->_search['searchKind'] === 'equalSearch') { | |
| // [탈퇴/휴면 검색] | |
| // - 검색 매칭: 세금계산서 요청인명(requestNm) | |
| // - 용도: 원본+분리보관 조회로 매칭 sno 치환(부분일치는 분리보관 불가라 제외) | |
| // - 대상: 탈퇴·휴면 둘 다 | |
| $withdrawnSearch = \App::getInstance(WithdrawnOrderSearchService::class); | |
| $matchedSnos = $withdrawnSearch->findTaxSnosByRequestNm((string) $this->_search['keyword']); | |
| if (empty($matchedSnos)) { | |
| $this->_arrSubWhere[] = 'ot.sno = 0'; // 매칭 없음 → 결과 없음 | |
| } else { | |
| $this->_arrSubWhere[] = 'ot.sno IN (' . implode(',', array_fill(0, count($matchedSnos), '?')) . ')'; | |
| foreach ($matchedSnos as $matchedSno) { | |
| $this->db->bind_param_push($this->_arrBind, 'i', $matchedSno); | |
| } | |
| } | |
| } else if ($this->_search['key'] == 'all') { | |
| $tmpWhere = gd_array_keys($this->_search['combineSearch']); | |
| array_shift($tmpWhere); | |
| $_arrWhereAll = []; | |
| //exit; | |
| $data = $this->db->query_fetch($strSQL, $this->_arrBind); | |
| // [탈퇴/휴면 복원] | |
| // - 대상: 세금계산서 신청자 PII(신청자명·사업장 주소 등). 리스트가 공백을 그대로 실어 나르면 | |
| // 발행 요청 폼이 그 공백을 전송해 발행 시 필수항목 검증에서 막힌다 | |
| // - 화면 노출은 조회 이후의 마스킹이 그대로 담당하므로 달라지지 않는다 | |
| if (!empty($data)) { | |
| $separationTypes = \App::getInstance(WithdrawnOrderSeparatorService::class) | |
| ->resolveOrderMemberTypes(array_column($data, 'orderNo')); | |
| if (!empty($separationTypes)) { | |
| $withdrawnHydrator = \App::getInstance(WithdrawnOrderHydratorService::class); | |
| foreach ($data as $k => $v) { | |
| if (empty($v['sno']) || !isset($separationTypes[$v['orderNo']])) { | |
| continue; | |
| } | |
| $data[$k] = $withdrawnHydrator->restore($v, WithdrawnSection::TAX, $separationTypes[$v['orderNo']], $v['sno']); | |
| } | |
| } | |
| } | |
| $order = \App::load('\\Component\\Order\\OrderAdmin'); | |
| //계산관련 | |
| $setData['statusFl'] = "y"; | |
| $setData['godobillSend'] = "y"; | |
| // [탈퇴/휴면 복원] | |
| // - 원복 데이터: 세금계산서 신청자 PII(requestNm/taxAddress/taxAddressSub) | |
| // - 용도: 고도빌 재전송 전 필수값 검증 통과(sendGodobill 내 복원보다 필수값 검증이 먼저) | |
| // - 대상: 탈퇴·휴면 둘 다(분리보관 완료 플래그로 판정해 일반 주문은 분리보관 조회 생략) | |
| $separationType = \App::getInstance(WithdrawnOrderSeparatorService::class) | |
| ->resolveOrderMemberType((string) $setData['orderNo']); | |
| if ($separationType !== null) { | |
| $withdrawnHydrator = \App::getInstance(WithdrawnOrderHydratorService::class); | |
| $setData = $withdrawnHydrator->restore($setData, WithdrawnSection::TAX, $separationType, $setData['sno']); | |
| } | |
| try { | |
| $this->db->begin_tran(); | |
| $result = SimpleCache::init(SimpleCache::REDIS) | |
| // 주문 정보 | |
| $this->_arrWhere[] = 'o.orderNo = ?'; | |
| $this->db->bind_param_push($this->_arrBind, 's', $setData['orderNo']); | |
| $this->db->strField = 'o.orderGoodsNm, oi.orderEmail, oi.orderCellPhone, o.separationStatus'; | |
| $this->db->strJoin = ' INNER JOIN ' . DB_ORDER_INFO . ' oi ON o.orderNo = oi.orderNo AND oi.orderInfoCd = 1 '; | |
| $this->db->strWhere = gd_implode(' AND ', gd_isset($this->_arrWhere)); | |
| $query = $this->db->query_complete(); | |
| } | |
| unset($order, $orderGoodsCnt); | |
| // [탈퇴/휴면 복원] | |
| // - 원복 데이터: 세금계산서 신청자 PII(requestNm/taxAddress/taxAddressSub) + 담당자 휴대전화(orderCellPhone) | |
| // - 용도: 고도빌 세금계산서 전송(sendGodobill) | |
| // - 대상: 신청자 PII=탈퇴·휴면 둘 다 / 담당자 휴대전화=휴면만(분리보관 완료 플래그로 판정해 일반 주문은 분리보관 조회 생략) | |
| $separationType = WithdrawnMemberType::tryFrom($getData['separationStatus'] ?? ''); | |
| if ($separationType !== null) { | |
| $withdrawnHydrator = \App::getInstance(WithdrawnOrderHydratorService::class); | |
| if (empty($setData['sno']) === false) { | |
| $setData = $withdrawnHydrator->restore($setData, WithdrawnSection::TAX, $separationType, $setData['sno']); | |
| } | |
| if ($separationType === WithdrawnMemberType::SLEEP) { | |
| $getData = $withdrawnHydrator->restore($getData, WithdrawnSection::ORDER_INFO, WithdrawnMemberType::SLEEP, $setData['orderNo']); | |
| } | |
| } | |
| $arrData['DMDER_BUSNID_TP_CD'] = '01'; // 사업자등록번호 구분코드(01 사업자등록번호,02 주민등록번호,03 외국인) | |
| $arrData['DMDER_BUSNID'] = str_replace('-', '', $setData['taxBusiNo']); // 사업자등록번호 | |
| $arrData['DMDER_SUB_BD_NO'] = ''; // 종사업자등록번호 | |
변경 전CashReceipt.php
| use Encryptor; | |
| use Origin\Service\Payment\Galaxia\PgReceiptUrl; | |
| use Origin\Enum\Payment\Galaxia\GalaxiaMoneyTreeCommonCode; | |
| /** | |
| * 현금영수증 관련 처리 | |
| // 키워드 검색 | |
| if ($search['key'] && $search['keyword']) { | |
| if ($search['key'] == 'all') { | |
| $tmpWhere = gd_array_keys($search['combineSearch']); | |
| array_shift($tmpWhere); | |
| $arrWhereAll = []; | |
| // 각 데이터 배열화 | |
| //$getData['data'] = gd_htmlspecialchars_stripslashes($data); | |
| if(empty($getValue['excelMode']) === false){ | |
| $getData['excelData'] = gd_htmlspecialchars_stripslashes($arrData); | |
| unset($getValue['excelMode']); | |
| } | |
| $getData = $this->db->query_fetch($strSQL, $arrBind['bind']); | |
| if (empty($getData) === true) { | |
| if ($modeStr === 'auto') { | |
| return false; | |
| $sno = $this->db->insert_id(); | |
| unset($arrBind); | |
| $res['mode'] = 'cash_receipt_reissue_request'; | |
| $res['result'] = true; | |
| $sno = $this->db->insert_id(); | |
| unset($arrBind); | |
| $res = $this->sendPgCashReceipt($arrData['orderNo'], 'auto', 'approval', '주문상세 현금영수증 재발행에 의한 즉시발급', 'y', ''); | |
| } | |
변경 후CashReceipt.php
| use Encryptor; | |
| use Origin\Service\Payment\Galaxia\PgReceiptUrl; | |
| use Origin\Enum\Payment\Galaxia\GalaxiaMoneyTreeCommonCode; | |
| use Origin\Enum\Privacy\Withdrawn\WithdrawnMemberType; | |
| use Origin\Enum\Privacy\Withdrawn\WithdrawnSection; | |
| use Origin\Repository\Order\OrderRepository; | |
| use Origin\Service\Privacy\Withdrawn\WithdrawnOrderHydratorService; | |
| use Origin\Service\Privacy\Withdrawn\WithdrawnOrderSearchService; | |
| use Origin\Service\Privacy\Withdrawn\WithdrawnOrderSeparatorService; | |
| /** | |
| * 현금영수증 관련 처리 | |
| // 키워드 검색 | |
| if ($search['key'] && $search['keyword']) { | |
| if ($search['key'] === 'requestNm' && $search['searchKind'] === 'equalSearch') { | |
| // [탈퇴/휴면 검색] | |
| // - 검색 매칭: 현금영수증 신청자명(requestNm) | |
| // - 용도: 원본+분리보관 조회로 매칭 sno 치환(부분일치는 분리보관 불가라 제외) | |
| // - 대상: 탈퇴·휴면 둘 다 | |
| $withdrawnSearch = \App::getInstance(WithdrawnOrderSearchService::class); | |
| $matchedSnos = $withdrawnSearch->findCashReceiptSnosByRequestNm((string) $search['keyword']); | |
| if (empty($matchedSnos)) { | |
| $arrWhere[] = 'r.sno = 0'; // 매칭 없음 → 결과 없음 | |
| } else { | |
| $arrWhere[] = 'r.sno IN (' . implode(',', array_fill(0, count($matchedSnos), '?')) . ')'; | |
| foreach ($matchedSnos as $matchedSno) { | |
| $this->db->bind_param_push($arrBind, 'i', $matchedSno); | |
| } | |
| } | |
| } else if ($search['key'] == 'all') { | |
| $tmpWhere = gd_array_keys($search['combineSearch']); | |
| array_shift($tmpWhere); | |
| $arrWhereAll = []; | |
| // 각 데이터 배열화 | |
| //$getData['data'] = gd_htmlspecialchars_stripslashes($data); | |
| if(empty($getValue['excelMode']) === false){ | |
| // 분리보관(탈퇴/휴면) 주문의 신청자 개인정보 치환. 화면용 $arrData 는 건드리지 않는다 | |
| $excelMasking = \App::getInstance(\Origin\Service\Privacy\Masking\OrderExcelMaskingService::class); | |
| $maskedData = $arrData; | |
| foreach ($maskedData as $orderNo => $receiptRows) { | |
| $maskLabels = $excelMasking->resolveOrderLabels($receiptRows); | |
| foreach ($receiptRows as $rowKey => $receiptRow) { | |
| $maskedData[$orderNo][$rowKey] = $excelMasking->maskCashReceiptRow($receiptRow, $maskLabels); | |
| } | |
| } | |
| $getData['excelData'] = gd_htmlspecialchars_stripslashes($maskedData); | |
| unset($getValue['excelMode']); | |
| } | |
| $getData = $this->db->query_fetch($strSQL, $arrBind['bind']); | |
| // [탈퇴/휴면 복원] | |
| // - 원복 데이터: 현금영수증 신청자 PII(requestNm/requestCellPhone/requestEmail/requestIP) | |
| // - 용도: PG 현금영수증 발급/취소 전송(sendPgCashReceipt) | |
| // - 대상: 탈퇴·휴면 둘 다(분리보관 완료 플래그를 주문 단위로 일괄 판정해 일반 주문은 분리보관 조회 생략) | |
| if (is_array($getData) === true) { | |
| $withdrawnHydrator = \App::getInstance(WithdrawnOrderHydratorService::class); | |
| $separationStatusMap = \App::getInstance(OrderRepository::class) | |
| ->findSeparationStatusByOrderNos(array_column($getData, 'orderNo')); | |
| foreach ($getData as $receiptKey => $receiptRow) { | |
| if (is_array($receiptRow) === false || empty($receiptRow['sno']) === true) { | |
| continue; | |
| } | |
| $separationType = WithdrawnMemberType::tryFrom($separationStatusMap[$receiptRow['orderNo'] ?? ''] ?? ''); | |
| if ($separationType === null) { | |
| continue; | |
| } | |
| $receiptRow = $withdrawnHydrator->restore($receiptRow, WithdrawnSection::CASH_RECEIPT, $separationType, $receiptRow['sno']); | |
| $getData[$receiptKey] = $receiptRow; | |
| } | |
| } | |
| if (empty($getData) === true) { | |
| if ($modeStr === 'auto') { | |
| return false; | |
| $sno = $this->db->insert_id(); | |
| unset($arrBind); | |
| // [탈퇴/휴면 분리] | |
| // - 분리 데이터: 재발행 신규 현금영수증 신청자 PII(requestNm/requestCellPhone/requestEmail/requestIP) | |
| // - 용도: 런타임 재분리(신규건 컨슈머/배치 트리거 없음) — 분리보관 INSERT + 원본 공백 | |
| // - 대상: 탈퇴·휴면 둘 다(일반/공백이면 no-op) | |
| \App::getInstance(WithdrawnOrderSeparatorService::class) | |
| ->separateIfWithdrawn(WithdrawnSection::CASH_RECEIPT, $arrData['orderNo'], (int) $sno); | |
| $res['mode'] = 'cash_receipt_reissue_request'; | |
| $res['result'] = true; | |
| $sno = $this->db->insert_id(); | |
| unset($arrBind); | |
| // [탈퇴/휴면 분리] | |
| // - 분리 데이터: 신규 재발행 현금영수증 신청자 PII | |
| // - 용도: 런타임 재분리(원본 공백) — 이후 발급은 분리보관 복원(#37)으로 정상 | |
| // - 대상: 탈퇴·휴면 둘 다 | |
| \App::getInstance(WithdrawnOrderSeparatorService::class) | |
| ->separateIfWithdrawn(WithdrawnSection::CASH_RECEIPT, $arrData['orderNo'], (int) $sno); | |
| $res = $this->sendPgCashReceipt($arrData['orderNo'], 'auto', 'approval', '주문상세 현금영수증 재발행에 의한 즉시발급', 'y', ''); | |
| } | |
변경 전Escrow.php
| use Message; | |
| use Exception; | |
| use Encryptor; | |
| /** | |
| * 에스크로 관련 처리 | |
| // --- 주문 데이타 | |
| $orderData = $order->getOrderData($orderNo); | |
| // 결제 방법 | |
| $settleGateway = substr($orderData['settleKind'], 0, 1); | |
변경 후Escrow.php
| use Message; | |
| use Exception; | |
| use Encryptor; | |
| use Origin\Enum\Privacy\Withdrawn\WithdrawnMemberType; | |
| use Origin\Enum\Privacy\Withdrawn\WithdrawnSection; | |
| use Origin\Service\Privacy\Withdrawn\WithdrawnOrderHydratorService; | |
| /** | |
| * 에스크로 관련 처리 | |
| // --- 주문 데이타 | |
| $orderData = $order->getOrderData($orderNo); | |
| // [휴면 복원] | |
| // - 원복 데이터: 주문자/수령자 PII(orderName·orderPhone·orderCellPhone·orderAddress·receiverName 등) | |
| // - 용도: PG 에스크로 배송등록 전송(sendPgEscrowDelivery) | |
| // - 대상: 휴면만(탈퇴는 레거시 D+1 배치가 이미 공백 처리하던 baseline 유지. 분리보관 완료 플래그로 판정해 일반 주문은 분리보관 조회 생략) | |
| if (($orderData['separationStatus'] ?? '') === WithdrawnMemberType::SLEEP->value) { | |
| $orderData = \App::getInstance(WithdrawnOrderHydratorService::class) | |
| ->restore($orderData, WithdrawnSection::ORDER_INFO, WithdrawnMemberType::SLEEP, $orderNo); | |
| } | |
| // 결제 방법 | |
| $settleGateway = substr($orderData['settleKind'], 0, 1); | |
변경 전PresentNotification.php
| use Framework\Utility\StringUtils; | |
| use Illuminate\Database\Capsule\Manager; | |
| use Origin\Enum\Crm\Message\KakaoAlimTalkSender; | |
| use Origin\Service\Crm\Message\KakaoAlimTalkSettingService; | |
| use Repository\Present\Order\PresentReceiverInfoRepository; | |
| class PresentNotification | |
| // 발송처리 | |
| $presentReceiver = $this->presentReceiverInfoRepository->findByOrderNoForNotification($orderNo); | |
| $receiverInfo = $this->getReceiverInfo($orderData, $presentReceiver); | |
| $recipientInfo = $this->getRecipientInfo($presentReceiver); | |
| $replaceArguments = $this->getReplaceArguments($orderData, $presentReceiver); | |
변경 후PresentNotification.php
| use Framework\Utility\StringUtils; | |
| use Illuminate\Database\Capsule\Manager; | |
| use Origin\Enum\Crm\Message\KakaoAlimTalkSender; | |
| use Origin\Enum\Privacy\Withdrawn\WithdrawnMemberType; | |
| use Origin\Enum\Privacy\Withdrawn\WithdrawnSection; | |
| use Origin\Service\Crm\Message\KakaoAlimTalkSettingService; | |
| use Origin\Service\Privacy\Withdrawn\WithdrawnOrderHydratorService; | |
| use Repository\Present\Order\PresentReceiverInfoRepository; | |
| class PresentNotification | |
| // 발송처리 | |
| $presentReceiver = $this->presentReceiverInfoRepository->findByOrderNoForNotification($orderNo); | |
| // [탈퇴/휴면 복원] | |
| // - 원복 데이터: 선물 수령자 PII(receiverName/phone/cellPhone). 주문자 PII는 getOrderDataSend 가 휴면 복원을 이미 수행 | |
| // - 용도: 선물 알림 SMS 발송(sendPresentInfo). 발송 시점 read-only만(write-back 복원 금지=분리무효화) | |
| // - 대상: 탈퇴·휴면 둘 다(분리보관 완료 플래그로 판정해 일반 주문은 분리보관 조회 생략) | |
| $separationType = WithdrawnMemberType::tryFrom($orderData['separationStatus'] ?? ''); | |
| if ($separationType !== null && is_array($presentReceiver) === true && empty($presentReceiver['sno']) === false) { | |
| $presentReceiver = \App::getInstance(WithdrawnOrderHydratorService::class) | |
| ->restore($presentReceiver, WithdrawnSection::PRESENT, $separationType, $presentReceiver['sno']); | |
| } | |
| $receiverInfo = $this->getReceiverInfo($orderData, $presentReceiver); | |
| $recipientInfo = $this->getRecipientInfo($presentReceiver); | |
| $replaceArguments = $this->getReplaceArguments($orderData, $presentReceiver); | |
변경 전RegularOrderAdminDetail.php
| use Repository\RegularDelivery\RegularOrder\RegularOrderLogRepository; | |
| use Repository\RegularDelivery\RegularOrder\RegularOrderStatusLogRepository; | |
| use Repository\RegularDelivery\RegularOrder\RegularOrderApplierRepository; | |
| /** | |
| * 관리자 정기결제 신청서 상세 페이지 조회 | |
| public function getRegularOrderShippingInfo(int $applyNo): array | |
| { | |
| $applierInfo = $this->regularOrderApplierRepository->findApplierInfoByApplyNo($applyNo); | |
| $shippingInfo = $this->regularOrderGoodsRepository->findShippingInfoByApplyNo($applyNo); | |
| return [ | |
| ]; | |
| } | |
| /** | |
| * 정기결제 신청서의 상담 메모 조회 | |
| * | |
변경 후RegularOrderAdminDetail.php
| use Repository\RegularDelivery\RegularOrder\RegularOrderLogRepository; | |
| use Repository\RegularDelivery\RegularOrder\RegularOrderStatusLogRepository; | |
| use Repository\RegularDelivery\RegularOrder\RegularOrderApplierRepository; | |
| use Origin\Enum\Privacy\Withdrawn\WithdrawnSection; | |
| use Origin\Service\Privacy\Withdrawn\WithdrawnOrderHydratorService; | |
| use Origin\Service\Privacy\Withdrawn\WithdrawnOrderSeparatorService; | |
| /** | |
| * 관리자 정기결제 신청서 상세 페이지 조회 | |
| public function getRegularOrderShippingInfo(int $applyNo): array | |
| { | |
| $applierInfo = $this->regularOrderApplierRepository->findApplierInfoByApplyNo($applyNo); | |
| // [탈퇴/휴면 복원] | |
| // - 원복 데이터: 정기결제 신청자 정보(applierName/applierPhone/applierCellPhone/applierEmail) | |
| // - 용도: 신청자 폼 프리필 표기·SMS 발송(공백 노출 시 저장으로 분리보관 값 손실 방지) | |
| // - 대상: 탈퇴·휴면 둘 다 | |
| $applierMemberType = \App::getInstance(WithdrawnOrderSeparatorService::class) | |
| ->resolveRegularApplierMemberType((string) ($applierInfo['applyGroupNo'] ?? '')); | |
| if ($applierMemberType !== null && isset($applierInfo['sno'])) { | |
| $applierInfo = \App::getInstance(WithdrawnOrderHydratorService::class) | |
| ->restore($applierInfo, WithdrawnSection::REGULAR_ORDER_APPLIER, $applierMemberType, (int) $applierInfo['sno']); | |
| } | |
| $shippingInfo = $this->regularOrderGoodsRepository->findShippingInfoByApplyNo($applyNo); | |
| return [ | |
| ]; | |
| } | |
| /** | |
| * 신청번호가 속한 신청그룹번호 조회 | |
| * | |
| * @param int $applyNo | |
| * @return string | |
| */ | |
| public function getApplyGroupNoByApplyNo(int $applyNo): string | |
| { | |
| return (string) $this->regularOrderGoodsRepository->findApplyGroupNoByApplyNo($applyNo); | |
| } | |
| /** | |
| * 정기결제 신청서의 상담 메모 조회 | |
| * | |
변경 전RegularOrderAdminDetailHandler.php
| use Repository\RegularDelivery\RegularOrder\RegularOrderAdminMemoRepository; | |
| use Component\RegularDelivery\RegularOrder\RegularOrderLog; | |
| use Framework\Utility\StringUtils; | |
| /** | |
| * 관리자 정기결제 신청서 상세 페이지 기능 핸들러 | |
| $updateValues['applierCellPhone'] = StringUtils::numberToPhone($updateValues['applierCellPhone']); | |
| $currentApplierInfo = $this->regularOrderApplierRepository->findApplierInfoByApplyNo($applyNo); | |
| // 변경된 항목 식별 | |
| $changedValuesWord = $this->getChangedFieldNames($currentApplierInfo, $updateValues); | |
| // 변경 항목 없으면 함수 종료 | |
| $this->manager->getConnection()->rollBack(); | |
| throw $e; | |
| } | |
| } | |
| /** | |
변경 후RegularOrderAdminDetailHandler.php
| use Repository\RegularDelivery\RegularOrder\RegularOrderAdminMemoRepository; | |
| use Component\RegularDelivery\RegularOrder\RegularOrderLog; | |
| use Framework\Utility\StringUtils; | |
| use Origin\Enum\Privacy\Withdrawn\WithdrawnSection; | |
| use Origin\Service\Privacy\Withdrawn\WithdrawnOrderHydratorService; | |
| use Origin\Service\Privacy\Withdrawn\WithdrawnOrderSeparatorService; | |
| /** | |
| * 관리자 정기결제 신청서 상세 페이지 기능 핸들러 | |
| $updateValues['applierCellPhone'] = StringUtils::numberToPhone($updateValues['applierCellPhone']); | |
| $currentApplierInfo = $this->regularOrderApplierRepository->findApplierInfoByApplyNo($applyNo); | |
| // [탈퇴/휴면 복원] | |
| // - 원복 데이터: 정기결제 신청자 정보 | |
| // - 용도: 저장 변경 판정 기준값(원본 공백과 비교 시 미변경 필드도 "변경" 오판→분리보관 값 손실 방지) | |
| // - 대상: 탈퇴·휴면 둘 다 | |
| $withdrawnSeparator = \App::getInstance(WithdrawnOrderSeparatorService::class); | |
| $applierMemberType = $withdrawnSeparator->resolveRegularApplierMemberType((string) ($currentApplierInfo['applyGroupNo'] ?? '')); | |
| if ($applierMemberType !== null && isset($currentApplierInfo['sno'])) { | |
| $currentApplierInfo = \App::getInstance(WithdrawnOrderHydratorService::class) | |
| ->restore($currentApplierInfo, WithdrawnSection::REGULAR_ORDER_APPLIER, $applierMemberType, (int) $currentApplierInfo['sno']); | |
| } | |
| // 변경된 항목 식별 | |
| $changedValuesWord = $this->getChangedFieldNames($currentApplierInfo, $updateValues); | |
| // 변경 항목 없으면 함수 종료 | |
| $this->manager->getConnection()->rollBack(); | |
| throw $e; | |
| } | |
| // [탈퇴/휴면 분리] | |
| // - 분리 데이터: 바뀐 정기결제 신청자 PII(applier*) | |
| // - 용도: 원본 UPDATE 커밋 직후 재분리(Eloquent↔godo raw 별개 PDO라 미커밋분 미조회) — 분리보관 갱신 + 원본 공백 | |
| // - 대상: 탈퇴·휴면 둘 다 | |
| if ($applierMemberType !== null && isset($currentApplierInfo['sno'])) { | |
| $withdrawnSeparator->separateRegularApplier( | |
| $applierMemberType, | |
| (string) ($currentApplierInfo['applyGroupNo'] ?? ''), | |
| (int) $currentApplierInfo['sno'], | |
| $updateValues | |
| ); | |
| } | |
| } | |
| /** | |
변경 전RegularOrderAdminList.php
| $regularOrderList[$index]['totalDcPrice'] = RegularOrderUtil::calculateRegularOrderOriginGoodsDiscountPrice($regularOrder); | |
| $regularOrderList[$index]['regularOrderTotalPrice'] = $regularOrderList[$index]['totalGoodsPrice'] - $regularOrderList[$index]['totalDcPrice']; | |
| // 마스킹 처리 | |
| $regularOrderList[$index]['applierName'] = $this->memberMasking->masking('order','name', $regularOrder['applierName']); | |
| $regularOrderList[$index]['applierCellPhone'] = $this->memberMasking->masking('order','tel', $regularOrder['applierCellPhone']); | |
| $regularOrderList[$index]['memId'] = $this->memberMasking->masking('order','id', $regularOrder['memId']); | |
| // 관리자 메모 | |
| $adminMemoList = $this->regularOrderAdminMemoRepository->findAdminMemoByApplyNo($regularOrder['applyNo']); | |
변경 후RegularOrderAdminList.php
| $regularOrderList[$index]['totalDcPrice'] = RegularOrderUtil::calculateRegularOrderOriginGoodsDiscountPrice($regularOrder); | |
| $regularOrderList[$index]['regularOrderTotalPrice'] = $regularOrderList[$index]['totalGoodsPrice'] - $regularOrderList[$index]['totalDcPrice']; | |
| // [개인정보 마스킹] applierName/applierCellPhone/memId/shippingName 은 RegularOrderListController 에서 | |
| // RegularOrderListMaskingService 로 '-' 치환(다른 주문 리스트와 동일 정책). 여기서는 원본 유지. | |
| // 관리자 메모 | |
| $adminMemoList = $this->regularOrderAdminMemoRepository->findAdminMemoByApplyNo($regularOrder['applyNo']); | |
변경 전RegularOrderAdminListExcel.php
| namespace Bundle\Component\RegularDelivery\RegularOrderAdmin; | |
| use Util\Order\RegularOrderUtil; | |
| use DTO\RegularDelivery\RegularOrder\RegularOrderSearchCondition; | |
| use Framework\Log\Logger; | |
| */ | |
| private $logger; | |
| public function __construct( | |
| RegularOrderRepository $regularOrderRepository, | |
| RegularOrderGiftRepository $regularOrderGiftRepository, | |
| RegularOrderAddGoodsRepository $regularOrderAddGoodsRepository, | |
| Logger $logger | |
| ) | |
| { | |
| $this->regularOrderRepository = $regularOrderRepository; | |
| $this->regularOrderGiftRepository = $regularOrderGiftRepository; | |
| $this->regularOrderAddGoodsRepository = $regularOrderAddGoodsRepository; | |
| $this->logger = $logger; | |
| } | |
| /** | |
| } | |
| } | |
| $this->logger->channel('regularOrderAdmin')->info('정기결제 엑셀 폼 데이터 : ', $regularOrderExcelList); | |
| // 엑셀 헤더 설정 | |
변경 후RegularOrderAdminListExcel.php
| namespace Bundle\Component\RegularDelivery\RegularOrderAdmin; | |
| use Origin\Service\Privacy\Masking\OrderExcelMaskingService; | |
| use Util\Order\RegularOrderUtil; | |
| use DTO\RegularDelivery\RegularOrder\RegularOrderSearchCondition; | |
| use Framework\Log\Logger; | |
| */ | |
| private $logger; | |
| /** | |
| * @var OrderExcelMaskingService | |
| */ | |
| private $orderExcelMaskingService; | |
| public function __construct( | |
| RegularOrderRepository $regularOrderRepository, | |
| RegularOrderGiftRepository $regularOrderGiftRepository, | |
| RegularOrderAddGoodsRepository $regularOrderAddGoodsRepository, | |
| Logger $logger, | |
| OrderExcelMaskingService $orderExcelMaskingService | |
| ) | |
| { | |
| $this->regularOrderRepository = $regularOrderRepository; | |
| $this->regularOrderGiftRepository = $regularOrderGiftRepository; | |
| $this->regularOrderAddGoodsRepository = $regularOrderAddGoodsRepository; | |
| $this->logger = $logger; | |
| $this->orderExcelMaskingService = $orderExcelMaskingService; | |
| } | |
| /** | |
| } | |
| } | |
| // 분리보관(탈퇴/휴면) 신청자 개인정보 치환. 로그에도 평문이 남지 않도록 로깅보다 먼저 수행한다 | |
| $maskLabels = $this->orderExcelMaskingService->resolveMemberLabels($regularOrderExcelList); | |
| foreach ($regularOrderExcelList as $index => $excelRow) { | |
| $regularOrderExcelList[$index] = $this->orderExcelMaskingService->maskRegularRow($excelRow, $maskLabels); | |
| } | |
| $this->logger->channel('regularOrderAdmin')->info('정기결제 엑셀 폼 데이터 : ', $regularOrderExcelList); | |
| // 엑셀 헤더 설정 | |
변경 전SafeNumber.php
| <?php | |
| /** | |
| * This is commercial software, only users who have purchased a valid license | |
| * and accept to the terms of the License Agreement can install and use this | |
| * program. | |
| * | |
| * Do not edit or add to this file if you wish to upgrade Godomall5 to newer | |
| * versions in the future. | |
| * | |
| * @copyright ⓒ 2016, NHN godo: Corp. | |
| * @link http://www.godo.co.kr | |
| */ | |
| namespace Bundle\Component\Service; | |
| use Component\Database\DBTableField; | |
| /** | |
| * 안심번호 | |
| * | |
| * @author haky <haky2@godo.co.kr> | |
| */ | |
| class SafeNumber extends \Component\AbstractComponent | |
| { | |
| // 안심번호 api 통신 모듈 | |
| private $_safeNumberApi = null; | |
| /** | |
| * 생성자 | |
| */ | |
| public function __construct() | |
| { | |
| parent::__construct(); | |
| $this->_safeNumberApi = \App::load('Component\\Godo\\GodoSafeNumberServerApi'); | |
| } | |
| /** | |
| * 안심번호 신청값 반환 | |
| * | |
| * @return bool | |
| */ | |
| public function getSafeNumberFl() | |
| { | |
| $orderBasic = gd_policy('order.basic'); | |
| if (empty($orderBasic['safeNumberFl']) || $orderBasic['safeNumberFl'] == 'n' || (isset($orderBasic['safeNumberServiceFl']) && $orderBasic['safeNumberServiceFl'] == 'off')) { | |
| return false; | |
| } else { | |
| return true; | |
| } | |
| } | |
| /** | |
| * 안심번호 설정값 반환 | |
| * | |
| * @return bool | |
| */ | |
| public function getSafeNumberUseFl() | |
| { | |
| $result = false; | |
| $orderBasic = gd_policy('order.basic'); | |
| if (empty($orderBasic['safeNumberFl']) || $orderBasic['safeNumberFl'] == 'n' || (isset($orderBasic['safeNumberServiceFl']) && $orderBasic['safeNumberServiceFl'] == 'off')) { | |
| return $result; | |
| } | |
| if ($orderBasic['useSafeNumberFl'] == 'y') { | |
| $result = true; | |
| } | |
| return $result; | |
| } | |
| /** | |
| * 주문정보 테이블의 안심번호 관련 정보 반환 | |
| * | |
| * @param mixed $orderNo 주문 번호 | |
| * | |
| * @return array | |
| */ | |
| public function getSafeNumberList($orderNo) | |
| { | |
| $arrBind = []; | |
| if (is_array($orderNo)) { | |
| $where = 'orderNo IN (' . gd_implode(',', array_fill(0, gd_count($orderNo), '?')) . ')'; | |
| foreach ($orderNo as $item) { | |
| $this->db->bind_param_push($arrBind, 's', $item); | |
| } | |
| } else { | |
| $where = 'orderNo = ?'; | |
| $this->db->bind_param_push($arrBind, 's', $orderNo); | |
| } | |
| $strSQL = 'SELECT sno, receiverCellPhone, receiverUseSafeNumberFl, receiverSafeNumber, receiverSafeNumberDt FROM ' . DB_ORDER_INFO . ' WHERE ' . $where; | |
| $safeNumberList = $this->db->query_fetch($strSQL, $arrBind); | |
| return $safeNumberList; | |
| } | |
| /** | |
| * 안심번호 신청 | |
| * | |
| * @param string $orderNo 주문 번호 | |
| * | |
| * @return mixed | |
| */ | |
| public function setUseSafeNumber($orderNo) | |
| { | |
| if ($this->getSafeNumberUseFl() == false) { | |
| return false; | |
| } | |
| $orderInfo = $this->getSafeNumberList($orderNo); | |
| // 휴대폰번호가 있고 발급대기인 경우 | |
| $cellPhoneList = []; | |
| foreach ($orderInfo as $oKey => $oVal) { | |
| if ($oVal['receiverUseSafeNumberFl'] == 'w' && empty($oVal['receiverCellPhone']) == false) { | |
| $cellPhoneList[$oVal['sno']] = str_replace('-', '', $oVal['receiverCellPhone']); | |
| } | |
| } | |
| if (empty($cellPhoneList) == false && gd_count($cellPhoneList) > 0) { | |
| // 안심번호 사용 업데이트 | |
| $arrUpdate['receiverUseSafeNumberFl'] = 'y'; | |
| $arrBind = $this->db->get_binding(DBTableField::tableOrderInfo(), $arrUpdate, 'update', gd_array_keys($arrUpdate)); | |
| if (is_array($cellPhoneList) && gd_count($cellPhoneList) > 1) { | |
| $where = 'sno IN (' . gd_implode(',', array_fill(0, gd_count($cellPhoneList), '?')) . ')'; | |
| foreach ($cellPhoneList as $cKey => $cVal) { | |
| $this->db->bind_param_push($arrBind['bind'], 'i', $cKey); | |
| } | |
| } else { | |
| $where = 'sno = ?'; | |
| $this->db->bind_param_push($arrBind['bind'], 'i', gd_array_keys($cellPhoneList)[0]); | |
| } | |
| $this->db->set_update_db(DB_ORDER_INFO, $arrBind['param'], $where, $arrBind['bind']); | |
| // 안심번호 발급 요청 | |
| $this->_safeNumberApi->safeNumberAPI('match', $cellPhoneList); | |
| } | |
| } | |
| /** | |
| * 안심번호 미발급건 재요청 (주문번호) | |
| * | |
| * @param mixed $orderNo 주문 번호 | |
| * | |
| * @return mixed | |
| */ | |
| public function resetSafeNumberByOrderNo($orderNo) | |
| { | |
| if ($this->getSafeNumberFl() == false) { | |
| return false; | |
| } | |
| $orderInfo = $this->getSafeNumberList($orderNo); | |
| // 휴대폰번호가 있고 사용상태이지만 안심번호 등록이 되지 않은 경우 | |
| $cellPhoneList = []; | |
| foreach ($orderInfo as $oKey => $oVal) { | |
| if ($oVal['receiverUseSafeNumberFl'] == 'y' && empty($oVal['receiverSafeNumber']) && empty($oVal['receiverCellPhone']) == false) { | |
| $cellPhoneList[$oVal['sno']] = str_replace('-', '', $oVal['receiverCellPhone']); | |
| } | |
| } | |
| if (empty($cellPhoneList) == false && gd_count($cellPhoneList) > 0) { | |
| $this->_resetSafeNumber($cellPhoneList); | |
| } | |
| } | |
| /** | |
| * 안심번호 미발급건 재요청 (주문정보) | |
| * | |
| * @param array $orderInfo 주문 정보 | |
| * | |
| * @return mixed | |
| */ | |
| public function resetSafeNumberByOrderInfo($orderInfo) | |
| { | |
| if ($this->getSafeNumberFl() == false) { | |
| return false; | |
| } | |
| // 휴대폰번호가 있고 사용상태이지만 안심번호 등록이 되지 않은 경우 | |
| if (empty($orderInfo['sno']) == false && $orderInfo['receiverUseSafeNumberFl'] == 'y' && empty($orderInfo['receiverSafeNumber']) && empty($orderInfo['receiverCellPhone']) == false) { | |
| $orderInfo['receiverCellPhone'] = str_replace('-', '', $orderInfo['receiverCellPhone']); | |
| $params[$orderInfo['sno']] = $orderInfo['receiverCellPhone']; | |
| $result = $this->_resetSafeNumber($params); | |
| } else { | |
| $result = false; | |
| } | |
| return $result; | |
| } | |
| /** | |
| * 안심번호 미발급건 재요청 | |
| * | |
| * @param array $data 재요청 정보 | |
| * | |
| * @return mixed | |
| */ | |
| private function _resetSafeNumber($data) | |
| { | |
| $result = $this->_safeNumberApi->safeNumberAPI('rematch', $data); | |
| $this->db->reconnect( | |
| function ($reconnectDatabase) use ($result) { | |
| if ($result['result'] == 'success' && empty($result['data']) == false && gd_count($result['data']) > 0) { | |
| foreach ($result['data'] as $sKey => $sVal) { | |
| $arrBind = []; | |
| $arrUpdate[] = 'receiverSafeNumber = ?'; | |
| $arrUpdate[] = 'receiverSafeNumberDt = now()'; | |
| $reconnectDatabase->bind_param_push($arrBind, 's', $sVal); | |
| $reconnectDatabase->bind_param_push($arrBind, 'i', $sKey); | |
| $reconnectDatabase->set_update_db(DB_ORDER_INFO, $arrUpdate, 'sno = ?', $arrBind); | |
| unset($arrBind, $arrUpdate); | |
| } | |
| } | |
| } | |
| ); | |
| return $result; | |
| } | |
| /** | |
| * 안심번호 수정 | |
| * | |
| * @param array $arrData 수정 정보 | |
| * | |
| * @return mixed | |
| */ | |
| public function modifySafeNumber($arrData) | |
| { | |
| if ($this->getSafeNumberFl() == false) { | |
| return false; | |
| } | |
| // 안심번호가 없이 수정을 요청할 경우 (ex.발급대기) 재매칭 통신 수행 | |
| if (empty($arrData['receiverSafeNumber'])) { | |
| $arrData['receiverCellPhone'] = $arrData['receiverOldCellPhone']; | |
| $resetData = $this->resetSafeNumberByOrderInfo($arrData); | |
| if ($resetData['result'] == 'success' && empty($resetData['data']) == false && gd_count($resetData['data']) > 0) { | |
| $arrData['receiverSafeNumber'] = $resetData['data'][$arrData['sno']]; | |
| } | |
| } | |
| if (empty($arrData['receiverSafeNumber']) || empty($arrData['receiverOldCellPhone']) || empty($arrData['receiverNewCellPhone'])) { | |
| $result = false; | |
| } else { | |
| $data['safeNumber'] = str_replace('-', '', $arrData['receiverSafeNumber']); | |
| $data['oldNumber'] = str_replace('-', '', $arrData['receiverOldCellPhone']); | |
| $data['phoneNumber'] = str_replace('-', '', $arrData['receiverNewCellPhone']); | |
| $result = $this->_safeNumberApi->safeNumberAPI('modify', $data); | |
| } | |
| return $result; | |
| } | |
| /** | |
| * 주문상세페이지 - 안심번호 사용해지 | |
| * | |
| * @param array $data 해지할 안심번호 정보 | |
| * | |
| * @return bool | |
| */ | |
| public function cancelSafeNumber($data) | |
| { | |
| if ($this->getSafeNumberFl() == false) { | |
| return false; | |
| } | |
| $data['safeNumber'] = str_replace('-', '', $data['safeNumber']); | |
| $data['phoneNumber'] = str_replace('-', '', $data['phoneNumber']); | |
| $result = $this->_safeNumberApi->safeNumberAPI('remove', $data); | |
| if ($result['result'] == 'success') { | |
| $updateData = [ | |
| 'receiverUseSafeNumberFl' => 'c' | |
| ]; | |
| $arrBind = $this->db->get_binding(DBTableField::tableOrderInfo(), $updateData, 'update', gd_array_keys($updateData)); | |
| $this->db->bind_param_push($arrBind['bind'], 'i', $data['sno']); | |
| $this->db->set_update_db(DB_ORDER_INFO, $arrBind['param'], 'sno = ?', $arrBind['bind']); | |
| } | |
| return $result; | |
| } | |
| /** | |
| * 안심번호 저장 | |
| * | |
| * @param array $data 안심번호 | |
| * | |
| * return bool | |
| */ | |
| public function setSafeNumber($data) | |
| { | |
| if ($this->getSafeNumberFl() == false) { | |
| return false; | |
| } | |
| foreach ($data as $sKey => $sVal) { | |
| $arrBind = []; | |
| $arrUpdate[] = 'receiverSafeNumber = ?'; | |
| $arrUpdate[] = 'receiverSafeNumberDt = now()'; | |
| $this->db->bind_param_push($arrBind, 's', $sVal); | |
| $this->db->bind_param_push($arrBind, 'i', $sKey); | |
| $this->db->set_update_db(DB_ORDER_INFO, $arrUpdate, 'sno = ?', $arrBind); | |
| unset($arrBind, $arrUpdate); | |
| } | |
| } | |
| } | |
변경 후SafeNumber.php
| <?php | |
| /** | |
| * This is commercial software, only users who have purchased a valid license | |
| * and accept to the terms of the License Agreement can install and use this | |
| * program. | |
| * | |
| * Do not edit or add to this file if you wish to upgrade Godomall5 to newer | |
| * versions in the future. | |
| * | |
| * @copyright ⓒ 2016, NHN godo: Corp. | |
| * @link http://www.godo.co.kr | |
| */ | |
| namespace Bundle\Component\Service; | |
| use Component\Database\DBTableField; | |
| use Framework\Security\Ciphers; | |
| use Origin\Enum\Privacy\Withdrawn\WithdrawnMemberType; | |
| use Origin\Enum\Privacy\Withdrawn\WithdrawnSection; | |
| use Origin\Repository\Member\MemberSleepOrderRepository; | |
| use Origin\Repository\Order\OrderRepository; | |
| use Origin\Service\Privacy\Withdrawn\WithdrawnOrderHydratorService; | |
| /** | |
| * 안심번호 | |
| * | |
| * @author haky <haky2@godo.co.kr> | |
| */ | |
| class SafeNumber extends \Component\AbstractComponent | |
| { | |
| // 안심번호 api 통신 모듈 | |
| private $_safeNumberApi = null; | |
| /** | |
| * 생성자 | |
| */ | |
| public function __construct() | |
| { | |
| parent::__construct(); | |
| $this->_safeNumberApi = \App::load('Component\\Godo\\GodoSafeNumberServerApi'); | |
| } | |
| /** | |
| * 안심번호 신청값 반환 | |
| * | |
| * @return bool | |
| */ | |
| public function getSafeNumberFl() | |
| { | |
| $orderBasic = gd_policy('order.basic'); | |
| if (empty($orderBasic['safeNumberFl']) || $orderBasic['safeNumberFl'] == 'n' || (isset($orderBasic['safeNumberServiceFl']) && $orderBasic['safeNumberServiceFl'] == 'off')) { | |
| return false; | |
| } else { | |
| return true; | |
| } | |
| } | |
| /** | |
| * 안심번호 설정값 반환 | |
| * | |
| * @return bool | |
| */ | |
| public function getSafeNumberUseFl() | |
| { | |
| $result = false; | |
| $orderBasic = gd_policy('order.basic'); | |
| if (empty($orderBasic['safeNumberFl']) || $orderBasic['safeNumberFl'] == 'n' || (isset($orderBasic['safeNumberServiceFl']) && $orderBasic['safeNumberServiceFl'] == 'off')) { | |
| return $result; | |
| } | |
| if ($orderBasic['useSafeNumberFl'] == 'y') { | |
| $result = true; | |
| } | |
| return $result; | |
| } | |
| /** | |
| * 주문정보 테이블의 안심번호 관련 정보 반환 | |
| * | |
| * @param mixed $orderNo 주문 번호 | |
| * | |
| * @return array | |
| */ | |
| public function getSafeNumberList($orderNo) | |
| { | |
| $arrBind = []; | |
| if (is_array($orderNo)) { | |
| $where = 'orderNo IN (' . gd_implode(',', array_fill(0, gd_count($orderNo), '?')) . ')'; | |
| foreach ($orderNo as $item) { | |
| $this->db->bind_param_push($arrBind, 's', $item); | |
| } | |
| } else { | |
| $where = 'orderNo = ?'; | |
| $this->db->bind_param_push($arrBind, 's', $orderNo); | |
| } | |
| $strSQL = 'SELECT sno, orderNo, receiverCellPhone, receiverUseSafeNumberFl, receiverSafeNumber, receiverSafeNumberDt FROM ' . DB_ORDER_INFO . ' WHERE ' . $where; | |
| $safeNumberList = $this->db->query_fetch($strSQL, $arrBind); | |
| return $this->restoreSeparatedSafeNumberList(is_array($safeNumberList) ? $safeNumberList : []); | |
| } | |
| /** | |
| * [휴면 복원] | |
| * - 원복 데이터: 수취인 연락처(receiverCellPhone) · 안심번호(receiverSafeNumber) | |
| * - 용도: 발급/재발급 판정이 두 값의 존재 여부로 갈리므로 분리 전과 동일하게 동작시킨다 | |
| * - 대상: 휴면만(탈퇴는 레거시 D+1 배치가 이미 공백 처리하던 baseline 유지. 분리보관 완료 플래그를 일괄 판정해 휴면 분리 주문만 분리보관 조회) | |
| * | |
| * @param array $safeNumberList getSafeNumberList 조회 결과 | |
| * @return array 공백이던 행만 분리보관값으로 채운 결과 | |
| */ | |
| private function restoreSeparatedSafeNumberList(array $safeNumberList): array | |
| { | |
| $candidateOrderNos = []; | |
| foreach ($safeNumberList as $row) { | |
| if (empty($row['orderNo'])) { | |
| continue; | |
| } | |
| if (empty($row['receiverCellPhone']) || empty($row['receiverSafeNumber'])) { | |
| $candidateOrderNos[] = $row['orderNo']; | |
| } | |
| } | |
| if (count($candidateOrderNos) === 0) { | |
| return $safeNumberList; | |
| } | |
| $separationStatusMap = \App::getInstance(OrderRepository::class)->findSeparationStatusByOrderNos($candidateOrderNos); | |
| $hydrator = \App::getInstance(WithdrawnOrderHydratorService::class); | |
| foreach ($safeNumberList as $key => $row) { | |
| if (empty($row['orderNo']) === true) { | |
| continue; | |
| } | |
| if (($separationStatusMap[$row['orderNo']] ?? '') !== WithdrawnMemberType::SLEEP->value) { | |
| continue; | |
| } | |
| if (empty($row['receiverCellPhone']) === false && empty($row['receiverSafeNumber']) === false) { | |
| continue; | |
| } | |
| if (empty($row['receiverCellPhone']) === true) { | |
| $orderInfo = $hydrator->hydrateOne(WithdrawnSection::ORDER_INFO, WithdrawnMemberType::SLEEP, $row['orderNo']); | |
| if (empty($orderInfo['receiverCellPhone']) === false) { | |
| $safeNumberList[$key]['receiverCellPhone'] = $orderInfo['receiverCellPhone']; | |
| } | |
| } | |
| if (empty($row['receiverSafeNumber']) === true) { | |
| $safeNumber = $hydrator->hydrateOne(WithdrawnSection::SAFE_NUMBER, WithdrawnMemberType::SLEEP, $row['orderNo']); | |
| if (empty($safeNumber['receiverSafeNumber']) === false) { | |
| $safeNumberList[$key]['receiverSafeNumber'] = $safeNumber['receiverSafeNumber']; | |
| } | |
| } | |
| } | |
| return $safeNumberList; | |
| } | |
| /** | |
| * 안심번호 신청 | |
| * | |
| * @param string $orderNo 주문 번호 | |
| * | |
| * @return mixed | |
| */ | |
| public function setUseSafeNumber($orderNo) | |
| { | |
| if ($this->getSafeNumberUseFl() == false) { | |
| return false; | |
| } | |
| $orderInfo = $this->getSafeNumberList($orderNo); | |
| // 휴대폰번호가 있고 발급대기인 경우 | |
| $cellPhoneList = []; | |
| foreach ($orderInfo as $oKey => $oVal) { | |
| if ($oVal['receiverUseSafeNumberFl'] == 'w' && empty($oVal['receiverCellPhone']) == false) { | |
| $cellPhoneList[$oVal['sno']] = str_replace('-', '', $oVal['receiverCellPhone']); | |
| } | |
| } | |
| if (empty($cellPhoneList) == false && gd_count($cellPhoneList) > 0) { | |
| // 안심번호 사용 업데이트 | |
| $arrUpdate['receiverUseSafeNumberFl'] = 'y'; | |
| $arrBind = $this->db->get_binding(DBTableField::tableOrderInfo(), $arrUpdate, 'update', gd_array_keys($arrUpdate)); | |
| if (is_array($cellPhoneList) && gd_count($cellPhoneList) > 1) { | |
| $where = 'sno IN (' . gd_implode(',', array_fill(0, gd_count($cellPhoneList), '?')) . ')'; | |
| foreach ($cellPhoneList as $cKey => $cVal) { | |
| $this->db->bind_param_push($arrBind['bind'], 'i', $cKey); | |
| } | |
| } else { | |
| $where = 'sno = ?'; | |
| $this->db->bind_param_push($arrBind['bind'], 'i', gd_array_keys($cellPhoneList)[0]); | |
| } | |
| $this->db->set_update_db(DB_ORDER_INFO, $arrBind['param'], $where, $arrBind['bind']); | |
| // 안심번호 발급 요청 | |
| $this->_safeNumberApi->safeNumberAPI('match', $cellPhoneList); | |
| } | |
| } | |
| /** | |
| * 안심번호 미발급건 재요청 (주문번호) | |
| * | |
| * @param mixed $orderNo 주문 번호 | |
| * | |
| * @return mixed | |
| */ | |
| public function resetSafeNumberByOrderNo($orderNo) | |
| { | |
| if ($this->getSafeNumberFl() == false) { | |
| return false; | |
| } | |
| $orderInfo = $this->getSafeNumberList($orderNo); | |
| // 휴대폰번호가 있고 사용상태이지만 안심번호 등록이 되지 않은 경우 | |
| $cellPhoneList = []; | |
| foreach ($orderInfo as $oKey => $oVal) { | |
| if ($oVal['receiverUseSafeNumberFl'] == 'y' && empty($oVal['receiverSafeNumber']) && empty($oVal['receiverCellPhone']) == false) { | |
| $cellPhoneList[$oVal['sno']] = str_replace('-', '', $oVal['receiverCellPhone']); | |
| } | |
| } | |
| if (empty($cellPhoneList) == false && gd_count($cellPhoneList) > 0) { | |
| $this->_resetSafeNumber($cellPhoneList); | |
| } | |
| } | |
| /** | |
| * 안심번호 미발급건 재요청 (주문정보) | |
| * | |
| * @param array $orderInfo 주문 정보 | |
| * | |
| * @return mixed | |
| */ | |
| public function resetSafeNumberByOrderInfo($orderInfo) | |
| { | |
| if ($this->getSafeNumberFl() == false) { | |
| return false; | |
| } | |
| // 휴대폰번호가 있고 사용상태이지만 안심번호 등록이 되지 않은 경우 | |
| if (empty($orderInfo['sno']) == false && $orderInfo['receiverUseSafeNumberFl'] == 'y' && empty($orderInfo['receiverSafeNumber']) && empty($orderInfo['receiverCellPhone']) == false) { | |
| $orderInfo['receiverCellPhone'] = str_replace('-', '', $orderInfo['receiverCellPhone']); | |
| $params[$orderInfo['sno']] = $orderInfo['receiverCellPhone']; | |
| $result = $this->_resetSafeNumber($params); | |
| } else { | |
| $result = false; | |
| } | |
| return $result; | |
| } | |
| /** | |
| * 안심번호 미발급건 재요청 | |
| * | |
| * @param array $data 재요청 정보 | |
| * | |
| * @return mixed | |
| */ | |
| private function _resetSafeNumber($data) | |
| { | |
| $result = $this->_safeNumberApi->safeNumberAPI('rematch', $data); | |
| $this->db->reconnect( | |
| function ($reconnectDatabase) use ($result) { | |
| if ($result['result'] == 'success' && empty($result['data']) == false && gd_count($result['data']) > 0) { | |
| foreach ($result['data'] as $sKey => $sVal) { | |
| // [휴면 분리보관] 분리 주문의 안심번호는 분리보관에 암호화 보관하고 원본은 공백을 유지한다(발급일시만 원본 기록) | |
| if ($this->saveSeparatedSafeNumber((int) $sKey, (string) $sVal) === true) { | |
| $arrBind = []; | |
| $reconnectDatabase->bind_param_push($arrBind, 'i', $sKey); | |
| $reconnectDatabase->set_update_db(DB_ORDER_INFO, ['receiverSafeNumberDt = now()'], 'sno = ?', $arrBind); | |
| unset($arrBind); | |
| continue; | |
| } | |
| $arrBind = []; | |
| $arrUpdate[] = 'receiverSafeNumber = ?'; | |
| $arrUpdate[] = 'receiverSafeNumberDt = now()'; | |
| $reconnectDatabase->bind_param_push($arrBind, 's', $sVal); | |
| $reconnectDatabase->bind_param_push($arrBind, 'i', $sKey); | |
| $reconnectDatabase->set_update_db(DB_ORDER_INFO, $arrUpdate, 'sno = ?', $arrBind); | |
| unset($arrBind, $arrUpdate); | |
| } | |
| } | |
| } | |
| ); | |
| return $result; | |
| } | |
| /** | |
| * 분리 주문(휴면)이면 새 안심번호를 분리보관에 암호화 기록한다. | |
| * | |
| * 원본(es_orderInfo.receiverSafeNumber)은 공백을 유지해야 분리보관이 무효화되지 않는다. | |
| * | |
| * @param int $orderInfoSno es_orderInfo.sno | |
| * @param string $safeNumber 발급된 안심번호(평문) | |
| * @return bool 분리보관에 기록했으면 true, 분리 주문이 아니면 false(호출부가 원본에 기록) | |
| */ | |
| private function saveSeparatedSafeNumber(int $orderInfoSno, string $safeNumber): bool | |
| { | |
| if ($safeNumber === '') { | |
| return false; | |
| } | |
| $orderNo = $this->getOrderNoByOrderInfoSno($orderInfoSno); | |
| if ($orderNo === '') { | |
| return false; | |
| } | |
| $sleepOrderRepository = \App::getInstance(MemberSleepOrderRepository::class); | |
| if ($sleepOrderRepository->existsByOrderNo($orderNo) === false) { | |
| return false; | |
| } | |
| $encryptor = \App::getInstance('encryptor'); | |
| $encryptor->setCipher(Ciphers::AES_256_CBC); | |
| return $sleepOrderRepository->updateSafeNumberByOrderNo($orderNo, $encryptor->mysqlAesEncrypt($safeNumber)); | |
| } | |
| /** | |
| * es_orderInfo.sno 로 주문번호를 조회한다(비 PII 컬럼). | |
| * | |
| * @return string 없으면 빈 문자열 | |
| */ | |
| private function getOrderNoByOrderInfoSno(int $orderInfoSno): string | |
| { | |
| $arrBind = []; | |
| $this->db->bind_param_push($arrBind, 'i', $orderInfoSno); | |
| $row = $this->db->query_fetch('SELECT orderNo FROM ' . DB_ORDER_INFO . ' WHERE sno = ?', $arrBind, false); | |
| return (string) ($row['orderNo'] ?? ''); | |
| } | |
| /** | |
| * 안심번호 수정 | |
| * | |
| * @param array $arrData 수정 정보 | |
| * | |
| * @return mixed | |
| */ | |
| public function modifySafeNumber($arrData) | |
| { | |
| if ($this->getSafeNumberFl() == false) { | |
| return false; | |
| } | |
| // 안심번호가 없이 수정을 요청할 경우 (ex.발급대기) 재매칭 통신 수행 | |
| if (empty($arrData['receiverSafeNumber'])) { | |
| $arrData['receiverCellPhone'] = $arrData['receiverOldCellPhone']; | |
| $resetData = $this->resetSafeNumberByOrderInfo($arrData); | |
| if ($resetData['result'] == 'success' && empty($resetData['data']) == false && gd_count($resetData['data']) > 0) { | |
| $arrData['receiverSafeNumber'] = $resetData['data'][$arrData['sno']]; | |
| } | |
| } | |
| if (empty($arrData['receiverSafeNumber']) || empty($arrData['receiverOldCellPhone']) || empty($arrData['receiverNewCellPhone'])) { | |
| $result = false; | |
| } else { | |
| $data['safeNumber'] = str_replace('-', '', $arrData['receiverSafeNumber']); | |
| $data['oldNumber'] = str_replace('-', '', $arrData['receiverOldCellPhone']); | |
| $data['phoneNumber'] = str_replace('-', '', $arrData['receiverNewCellPhone']); | |
| $result = $this->_safeNumberApi->safeNumberAPI('modify', $data); | |
| } | |
| return $result; | |
| } | |
| /** | |
| * 주문상세페이지 - 안심번호 사용해지 | |
| * | |
| * @param array $data 해지할 안심번호 정보 | |
| * | |
| * @return bool | |
| */ | |
| public function cancelSafeNumber($data) | |
| { | |
| if ($this->getSafeNumberFl() == false) { | |
| return false; | |
| } | |
| $data['safeNumber'] = str_replace('-', '', $data['safeNumber']); | |
| $data['phoneNumber'] = str_replace('-', '', $data['phoneNumber']); | |
| $result = $this->_safeNumberApi->safeNumberAPI('remove', $data); | |
| if ($result['result'] == 'success') { | |
| $updateData = [ | |
| 'receiverUseSafeNumberFl' => 'c' | |
| ]; | |
| $arrBind = $this->db->get_binding(DBTableField::tableOrderInfo(), $updateData, 'update', gd_array_keys($updateData)); | |
| $this->db->bind_param_push($arrBind['bind'], 'i', $data['sno']); | |
| $this->db->set_update_db(DB_ORDER_INFO, $arrBind['param'], 'sno = ?', $arrBind['bind']); | |
| } | |
| return $result; | |
| } | |
| /** | |
| * 안심번호 저장 | |
| * | |
| * @param array $data 안심번호 | |
| * | |
| * return bool | |
| */ | |
| public function setSafeNumber($data) | |
| { | |
| if ($this->getSafeNumberFl() == false) { | |
| return false; | |
| } | |
| foreach ($data as $sKey => $sVal) { | |
| $arrBind = []; | |
| $arrUpdate[] = 'receiverSafeNumber = ?'; | |
| $arrUpdate[] = 'receiverSafeNumberDt = now()'; | |
| $this->db->bind_param_push($arrBind, 's', $sVal); | |
| $this->db->bind_param_push($arrBind, 'i', $sKey); | |
| $this->db->set_update_db(DB_ORDER_INFO, $arrUpdate, 'sno = ?', $arrBind); | |
| unset($arrBind, $arrUpdate); | |
| } | |
| } | |
| } | |
변경 전SmsAdmin.php
| use Origin\Repository\Member\Sms\SmsContentsRepository; | |
| use Origin\Service\Crm\Message\SmsTemplateService; | |
| use Origin\Service\Sms\AutoSend\SaveAutoSendContentsService; | |
| /** | |
| * SMS 관리자 관련 처리 | |
| $orders = $service->getOrderListForAdmin($search, $search['searchPeriod'], $isUserHandle); | |
| unset($orders['data'], $orders['isUserHandle'], $orders['search'], $orders['checked'], $orders['amount']); | |
| $memberAdmin = \App::load('\\Component\\Member\\MemberAdmin'); | |
| foreach ($orders as $order) { | |
| if($receiverData['rejectSend'] == 'n') { | |
| if($order['memNo'] > 0) { | |
| $claimRefundPrice = $ordClaimData['dashBoardPrice']['refundPrice']; | |
| } | |
| StringUtils::strIsSet($order['orderCellPhone'], ''); | |
| if ($order['orderCellPhone'] !== '') { | |
| // 가상계좌 입금기한, 계좌번호 | |
| $getOrderReceivers = function (array $receiverKeys) use ($receiverData, $pgConfig, $orderPolicy) { | |
| $service = \App::load('Component\\Order\\Order'); | |
| $memberAdmin = \App::load('\\Component\\Member\\MemberAdmin'); | |
| $receivers = []; | |
| foreach ($receiverKeys as $key) { | |
| $order = $service->getOrderData($key); | |
| $claimRefundPrice = $ordClaimData['dashBoardPrice']['refundPrice']; | |
| if (\is_array($order)) { | |
| StringUtils::strIsSet($order['orderCellPhone'], ''); | |
| if ($order['orderCellPhone'] !== '') { | |
| // 가상계좌 입금기한, 계좌번호 | |
변경 후SmsAdmin.php
| use Origin\Repository\Member\Sms\SmsContentsRepository; | |
| use Origin\Service\Crm\Message\SmsTemplateService; | |
| use Origin\Service\Sms\AutoSend\SaveAutoSendContentsService; | |
| use Origin\Service\Privacy\Withdrawn\WithdrawnOrderHydratorService; | |
| use Origin\Enum\Privacy\Withdrawn\WithdrawnMemberType; | |
| use Origin\Enum\Privacy\Withdrawn\WithdrawnSection; | |
| /** | |
| * SMS 관리자 관련 처리 | |
| $orders = $service->getOrderListForAdmin($search, $search['searchPeriod'], $isUserHandle); | |
| unset($orders['data'], $orders['isUserHandle'], $orders['search'], $orders['checked'], $orders['amount']); | |
| $memberAdmin = \App::load('\\Component\\Member\\MemberAdmin'); | |
| $withdrawnHydrator = \App::getInstance(WithdrawnOrderHydratorService::class); | |
| foreach ($orders as $order) { | |
| if($receiverData['rejectSend'] == 'n') { | |
| if($order['memNo'] > 0) { | |
| $claimRefundPrice = $ordClaimData['dashBoardPrice']['refundPrice']; | |
| } | |
| // [휴면 복원] | |
| // - 원복 데이터: 주문자명(orderName)·orderCellPhone·입금자명(bankSender) | |
| // - 용도: 무통장 입금확인 SMS 발송(발송게이트/번호·본문 depositNm) | |
| // - 대상: 휴면만(분리보관 완료 플래그로 판정해 일반 주문은 분리보관 조회 생략) | |
| if (($order['separationStatus'] ?? '') === WithdrawnMemberType::SLEEP->value) { | |
| $order = $withdrawnHydrator->restore($order, WithdrawnSection::ORDER_INFO, WithdrawnMemberType::SLEEP, $order['orderNo']); | |
| $order = $withdrawnHydrator->restore($order, WithdrawnSection::BANK_SENDER, WithdrawnMemberType::SLEEP, $order['orderNo']); | |
| } | |
| StringUtils::strIsSet($order['orderCellPhone'], ''); | |
| if ($order['orderCellPhone'] !== '') { | |
| // 가상계좌 입금기한, 계좌번호 | |
| $getOrderReceivers = function (array $receiverKeys) use ($receiverData, $pgConfig, $orderPolicy) { | |
| $service = \App::load('Component\\Order\\Order'); | |
| $memberAdmin = \App::load('\\Component\\Member\\MemberAdmin'); | |
| $withdrawnHydrator = \App::getInstance(WithdrawnOrderHydratorService::class); | |
| $receivers = []; | |
| foreach ($receiverKeys as $key) { | |
| $order = $service->getOrderData($key); | |
| $claimRefundPrice = $ordClaimData['dashBoardPrice']['refundPrice']; | |
| if (\is_array($order)) { | |
| // [휴면 복원] | |
| // - 원복 데이터: 주문자명(orderName)·orderCellPhone·입금자명(bankSender) | |
| // - 용도: 무통장 입금확인 SMS 발송(발송게이트/번호·본문 depositNm) | |
| // - 대상: 휴면만(분리보관 완료 플래그로 판정해 일반 주문은 분리보관 조회 생략) | |
| if (($order['separationStatus'] ?? '') === WithdrawnMemberType::SLEEP->value) { | |
| $order = $withdrawnHydrator->restore($order, WithdrawnSection::ORDER_INFO, WithdrawnMemberType::SLEEP, $key); | |
| $order = $withdrawnHydrator->restore($order, WithdrawnSection::BANK_SENDER, WithdrawnMemberType::SLEEP, $key); | |
| } | |
| StringUtils::strIsSet($order['orderCellPhone'], ''); | |
| if ($order['orderCellPhone'] !== '') { | |
| // 가상계좌 입금기한, 계좌번호 | |
변경 전SmsSendPsController.php
| use Framework\Utility\StringUtils; | |
| use Origin\Enum\Crm\Message\SmsTemplateApprovalStatus; | |
| use Origin\Service\Crm\Message\SmsTemplateService; | |
| /** | |
| * Class SmsSendPsController | |
| if(gd_in_array($search['view'], ['exchange', 'back', 'refund'])) $isUserHandle = true; | |
| $orders = $service->getOrderListForAdmin($search, $search['searchPeriod'], $isUserHandle); | |
| $logger->info(__METHOD__ . ' search orders count[' . gd_count($orders) . ']'); | |
| foreach ($orders as $order) { | |
| if (is_array($order) === false) { | |
| continue; | |
| } | |
| StringUtils::strIsSet($order['orderCellPhone'], ''); | |
| if ($order['orderCellPhone'] === '') { | |
| continue; | |
변경 후SmsSendPsController.php
| use Framework\Utility\StringUtils; | |
| use Origin\Enum\Crm\Message\SmsTemplateApprovalStatus; | |
| use Origin\Service\Crm\Message\SmsTemplateService; | |
| use Origin\Service\Privacy\Withdrawn\WithdrawnOrderHydratorService; | |
| use Origin\Enum\Privacy\Withdrawn\WithdrawnMemberType; | |
| use Origin\Enum\Privacy\Withdrawn\WithdrawnSection; | |
| /** | |
| * Class SmsSendPsController | |
| if(gd_in_array($search['view'], ['exchange', 'back', 'refund'])) $isUserHandle = true; | |
| $orders = $service->getOrderListForAdmin($search, $search['searchPeriod'], $isUserHandle); | |
| $logger->info(__METHOD__ . ' search orders count[' . gd_count($orders) . ']'); | |
| $withdrawnHydrator = \App::getInstance(WithdrawnOrderHydratorService::class); | |
| foreach ($orders as $order) { | |
| if (is_array($order) === false) { | |
| continue; | |
| } | |
| // [휴면 복원] | |
| // - 원복 데이터: orderCellPhone | |
| // - 용도: 발송대상 수 미리보기 카운트(게이트 통과, 미리보기=실제 발송 수 일치) | |
| // - 대상: 휴면만(분리보관 완료 플래그로 판정해 일반 주문은 분리보관 조회 생략) | |
| if (($order['separationStatus'] ?? '') === WithdrawnMemberType::SLEEP->value) { | |
| $order = $withdrawnHydrator->restore($order, WithdrawnSection::ORDER_INFO, WithdrawnMemberType::SLEEP, $order['orderNo']); | |
| } | |
| StringUtils::strIsSet($order['orderCellPhone'], ''); | |
| if ($order['orderCellPhone'] === '') { | |
| continue; | |
변경 전CashReceiptListController.php
| use Component\Page\Page; | |
| use Component\Payment\CashReceipt; | |
| use Exception; | |
| /** | |
| * 현금영수증 신청 리스트 페이지 | |
| } | |
| // --- 관리자 디자인 템플릿 | |
| $this->setData('getData',$getData); | |
| $this->setData('search', $getData['search']); | |
| $this->setData('searchKindASelectBox', \Component\Member\Member::getSearchKindASelectBox()); | |
변경 후CashReceiptListController.php
| use Component\Page\Page; | |
| use Component\Payment\CashReceipt; | |
| use Exception; | |
| use Origin\Service\Privacy\Masking\CashReceiptListMaskingService; | |
| /** | |
| * 현금영수증 신청 리스트 페이지 | |
| } | |
| // --- 관리자 디자인 템플릿 | |
| $getData['data'] = \App::getInstance(CashReceiptListMaskingService::class) | |
| ->maskCashReceiptList($getData['data']); | |
| $this->setData('getData',$getData); | |
| $this->setData('search', $getData['search']); | |
| $this->setData('searchKindASelectBox', \Component\Member\Member::getSearchKindASelectBox()); | |
변경 전EpostReturnRequestController.php
| use DTO\Order\EpostReturnSearchDTO; | |
| use Framework\Debug\Exception\AlertBackException; | |
| use Origin\Service\Order\EpostReturnAccessLogService; | |
| use Request; | |
| /** | |
| } | |
| $targetList = \App::getInstance(EpostReturnAdmin::class)->getTargetList($getValue); | |
| $this->writeAccessLog($targetList['data'], $targetList['total']); | |
| // [수거 신청] 쓰기 권한 — 화면은 얼럿 판정 재료만 받고 최종 차단은 PS 서버 검증 | |
변경 후EpostReturnRequestController.php
| use DTO\Order\EpostReturnSearchDTO; | |
| use Framework\Debug\Exception\AlertBackException; | |
| use Origin\Service\Order\EpostReturnAccessLogService; | |
| use Origin\Service\Privacy\Masking\OrderListMaskingService; | |
| use Request; | |
| /** | |
| } | |
| $targetList = \App::getInstance(EpostReturnAdmin::class)->getTargetList($getValue); | |
| // 개인정보 마스킹(주문 리스트): 주문자명→회원유형, 주문자 휴대폰·ID·수령자명·입금자명·입금계좌→'-' | |
| $targetList = \App::getInstance(OrderListMaskingService::class)->maskOrderList($targetList); | |
| $this->writeAccessLog($targetList['data'], $targetList['total']); | |
| // [수거 신청] 쓰기 권한 — 화면은 얼럿 판정 재료만 받고 최종 차단은 PS 서버 검증 | |
변경 전FrameCashReceiptRegisterController.php
| use Globals; | |
| use Request; | |
| use Message; | |
| /** | |
| * 현금영수증 발급 요청 페이지 | |
| $order = \App::load('\\Component\\Order\\OrderAdmin'); | |
| // --- 주문 데이터 | |
| $orderData = $order->getOrderViewForReceipt(StringUtils::xssClean(Request::request()->get('orderNo'))); | |
| // --- 회원 데이터 | |
| if (empty($orderData['memNo']) == false) { | |
| $this->getView()->setPageName('order/frame_cash_receipt_register.php'); | |
| $this->setData('orderData', $orderData); | |
| $this->setData('pgConf', $pgConf); | |
| $this->setData('emailDomain', $emailDomain); | |
| } | |
변경 후FrameCashReceiptRegisterController.php
| use Globals; | |
| use Request; | |
| use Message; | |
| use Origin\Enum\Privacy\Withdrawn\WithdrawnMemberType; | |
| use Origin\Enum\Privacy\Withdrawn\WithdrawnSection; | |
| use Origin\Service\Privacy\Masking\MaskingTargetService; | |
| use Origin\Service\Privacy\Withdrawn\WithdrawnOrderHydratorService; | |
| /** | |
| * 현금영수증 발급 요청 페이지 | |
| $order = \App::load('\\Component\\Order\\OrderAdmin'); | |
| // --- 주문 데이터 | |
| $orderNo = StringUtils::xssClean(Request::request()->get('orderNo')); | |
| $orderData = $order->getOrderViewForReceipt($orderNo); | |
| // 신청자명은 화면에만 회원유형 라벨로 대체하고 저장값(hidden requestNm)은 실제 이름을 유지한다. | |
| // 저장값이 현금영수증 발급 명의로 PG 에 전송되므로 라벨이 담기면 라벨 명의로 발급된다. | |
| $orderMaskLabel = \App::getInstance(MaskingTargetService::class) | |
| ->resolveMaskLabelByOrderNo($orderNo); | |
| // 탈퇴는 분리 전에도 D+1 배치가 신청자명을 공백 처리하던 baseline 이라 복원하지 않는다. | |
| if (($orderData['separationStatus'] ?? '') === WithdrawnMemberType::SLEEP->value) { | |
| $orderData = \App::getInstance(WithdrawnOrderHydratorService::class) | |
| ->restore($orderData, WithdrawnSection::ORDER_INFO, WithdrawnMemberType::SLEEP, $orderNo); | |
| } | |
| // --- 회원 데이터 | |
| if (empty($orderData['memNo']) == false) { | |
| $this->getView()->setPageName('order/frame_cash_receipt_register.php'); | |
| $this->setData('orderData', $orderData); | |
| $this->setData('orderMaskLabel', $orderMaskLabel); | |
| $this->setData('pgConf', $pgConf); | |
| $this->setData('emailDomain', $emailDomain); | |
| } | |
변경 전FrameCashReceiptViewController.php
| use Request; | |
| use Encryptor; | |
| use Exception; | |
| /** | |
| * 현금영수증 요청 / 발급 정보 확인 | |
| $this->getView()->setDefine('layout', 'layout_layer.php'); | |
| $this->getView()->setDefine('layoutCashReceiptForm', Request::getDirectoryUri() . '/frame_cash_receipt_form.php'); | |
| $this->setData('data', gd_htmlspecialchars($getData)); | |
| $this->setData('pgConf', $pgConf); | |
| $this->setData('gPg', Globals::get('gPg')); | |
| $this->setData('orderStatus', $orderStatus); | |
변경 후FrameCashReceiptViewController.php
| use Request; | |
| use Encryptor; | |
| use Exception; | |
| use Origin\Service\Privacy\Masking\OrderDetailMaskingService; | |
| use Origin\Service\Privacy\Masking\ColumnMaskingService; | |
| use Origin\Service\Privacy\Masking\MaskingTargetService; | |
| /** | |
| * 현금영수증 요청 / 발급 정보 확인 | |
| $this->getView()->setDefine('layout', 'layout_layer.php'); | |
| $this->getView()->setDefine('layoutCashReceiptForm', Request::getDirectoryUri() . '/frame_cash_receipt_form.php'); | |
| // 개인정보 마스킹(현금영수증 확인): 신청자명·휴대폰·이메일·인증번호→'-' | |
| // 표시 키를 그대로 덮으므로 뷰가 튜닝돼 있어도 적용된다 | |
| $orderDetailMasking = \App::getInstance(OrderDetailMaskingService::class); | |
| $isMaskTarget = \App::getInstance(MaskingTargetService::class) | |
| ->isMaskTargetOrderNo(Request::get()->get('orderNo')); | |
| if ($isMaskTarget) { | |
| $getData = $orderDetailMasking->maskCashReceipt($getData); | |
| } | |
| $this->setData('data', gd_htmlspecialchars($getData)); | |
| // 인증번호는 인증종류와 한 칸에 결합 표시되므로 표시 문자열을 완성해 내린다. | |
| // 기획 대상(사업자번호 b·휴대폰번호 c)만 마스킹하고, 발급 옵션에서 제거된 유형(주민등록번호 l)은 기존 표시를 유지한다. | |
| $certFl = $getData['certFl']; | |
| $certFlLabel = isset($cashReceipt::CERT_NUM_TYPE[$certFl]) ? ' (' . $cashReceipt::CERT_NUM_TYPE[$certFl] . ')' : ''; | |
| $this->setData( | |
| 'displayCertNo', | |
| ($isMaskTarget && in_array($certFl, ['b', 'c'], true)) | |
| ? ColumnMaskingService::DEFAULT_MASK | |
| : $certNo . $certFlLabel | |
| ); | |
| $this->setData('pgConf', $pgConf); | |
| $this->setData('gPg', Globals::get('gPg')); | |
| $this->setData('orderStatus', $orderStatus); | |
변경 전FrameTaxInvoiceRegisterController.php
| use Message; | |
| use Globals; | |
| use Request; | |
| /** | |
| * 세금계산서 발급 요청 페이지 | |
| $orderData['requestGoodsNm'] = StringUtils::htmlSpecialCharsStripSlashes($orderData['requestGoodsNm']); | |
| $checked['statusFl'][$orderData['statusFl']] = 'checked="checked"'; | |
| if($orderData['taxEmail'] =='' && $orderData['orderEmail']) $orderData['taxEmail'] = $orderData['orderEmail']; | |
| } | |
| // mode 값이 없다면 오류 | |
| else { | |
변경 후FrameTaxInvoiceRegisterController.php
| use Message; | |
| use Globals; | |
| use Request; | |
| use Origin\Service\Privacy\Masking\MaskingTargetService; | |
| use Origin\Service\Privacy\Masking\OrderDetailMaskingService; | |
| /** | |
| * 세금계산서 발급 요청 페이지 | |
| $orderData['requestGoodsNm'] = StringUtils::htmlSpecialCharsStripSlashes($orderData['requestGoodsNm']); | |
| $checked['statusFl'][$orderData['statusFl']] = 'checked="checked"'; | |
| if($orderData['taxEmail'] =='' && $orderData['orderEmail']) $orderData['taxEmail'] = $orderData['orderEmail']; | |
| // 탈퇴/휴면 주문은 분리보관에서 복원된 신청자 정보가 채워지므로, 빈 입력칸으로 열고 관리자가 다시 입력하게 한다 | |
| if (\App::getInstance(MaskingTargetService::class)->isMaskTargetOrderNo((string) $orderData['orderNo'])) { | |
| $orderData = \App::getInstance(OrderDetailMaskingService::class)->blankTaxInvoice($orderData); | |
| } | |
| } | |
| // mode 값이 없다면 오류 | |
| else { | |
변경 전IncClaimViewController.php
| use Request; | |
| use Component\Naver\NaverPay; | |
| use Exception; | |
| /** | |
| * 배송 업체 리스트 페이지 | |
| $this->setData('data', $data); | |
| $this->setData('withdrawnMembersRefundData', $withdrawnMembersRefundData); | |
| // 템플릿 설정 | |
| $this->getView()->setDefine('layout', 'layout_layer.php'); | |
변경 후IncClaimViewController.php
| use Request; | |
| use Component\Naver\NaverPay; | |
| use Exception; | |
| use Origin\Service\Privacy\Masking\ColumnMaskingService; | |
| use Origin\Service\Privacy\Masking\MaskingTargetService; | |
| /** | |
| * 배송 업체 리스트 페이지 | |
| $this->setData('data', $data); | |
| $this->setData('withdrawnMembersRefundData', $withdrawnMembersRefundData); | |
| // 개인정보 마스킹(주문 상세 클레임): 환불계좌(은행·계좌번호·예금주)→'-' | |
| $isRefundMaskTarget = \App::getInstance(MaskingTargetService::class) | |
| ->isMaskTargetOrderNo(Request::request()->get('orderNo')); | |
| $this->setData('isRefundMaskTarget', $isRefundMaskTarget); | |
| // 환불계좌는 은행·계좌번호·예금주가 한 칸에 모이므로 뷰가 칸 전체를 이 값 하나로 대체한다 | |
| $this->setData('maskChar', ColumnMaskingService::DEFAULT_MASK); | |
| // 템플릿 설정 | |
| $this->getView()->setDefine('layout', 'layout_layer.php'); | |
변경 전LayerRefundViewController.php
| use Framework\Debug\Exception\LayerNotReloadException; | |
| use Request; | |
| use Exception; | |
| /** | |
| * 주문상세의 환불접수 리스트내 수정 레이어 | |
| // 환불상품 정보 | |
| $handleData = $order->getOrderGoodsData(Request::post()->get('orderNo'), null, Request::post()->get('handleSno'), null, 'admin', false); | |
| $this->setData('handleData', $handleData); | |
| // 취소사유 | |
| $cancelReasonCode = gd_array_change_key_value(gd_code('04001')); | |
변경 후LayerRefundViewController.php
| use Framework\Debug\Exception\LayerNotReloadException; | |
| use Request; | |
| use Exception; | |
| use Origin\Service\Privacy\Masking\ColumnMaskingService; | |
| use Origin\Service\Privacy\Masking\MaskingTargetService; | |
| use Origin\Enum\Privacy\Withdrawn\WithdrawnSection; | |
| use Origin\Service\Privacy\Withdrawn\WithdrawnOrderHydratorService; | |
| use Origin\Service\Privacy\Withdrawn\WithdrawnOrderSeparatorService; | |
| /** | |
| * 주문상세의 환불접수 리스트내 수정 레이어 | |
| // 환불상품 정보 | |
| $handleData = $order->getOrderGoodsData(Request::post()->get('orderNo'), null, Request::post()->get('handleSno'), null, 'admin', false); | |
| // [탈퇴/휴면 복원] | |
| // - 원복 데이터: 환불계좌(refundBankName/refundDepositor + refundAccountNumber passthrough) | |
| // - 용도: 환불접수 수정 폼 표기. 수정 폼은 분리 전 값이 필요하고, 읽기 전용 표기는 뷰에서 하이픈으로 대체한다 | |
| // - 대상: 탈퇴·휴면 둘 다(분리보관 완료 플래그로 판정해 일반 주문은 분리보관 조회 생략) | |
| $refundHandleSno = Request::post()->get('handleSno'); | |
| $refundSeparationType = \App::getInstance(WithdrawnOrderSeparatorService::class) | |
| ->resolveOrderMemberType((string) Request::post()->get('orderNo')); | |
| if (is_array($handleData) === true && $refundSeparationType !== null && empty($refundHandleSno) === false) { | |
| $handleData = \App::getInstance(WithdrawnOrderHydratorService::class) | |
| ->restore($handleData, WithdrawnSection::REFUND, $refundSeparationType, $refundHandleSno); | |
| if (gd_str_length($handleData['refundAccountNumber']) > 50) { | |
| $handleData['refundAccountNumber'] = \Encryptor::decrypt($handleData['refundAccountNumber']); | |
| } | |
| } | |
| $this->setData('handleData', $handleData); | |
| // 개인정보 마스킹(환불접수 수정): 환불계좌(은행·계좌번호·예금주)→'-' | |
| $isRefundMaskTarget = \App::getInstance(MaskingTargetService::class) | |
| ->isMaskTargetOrderNo(Request::post()->get('orderNo')); | |
| $this->setData('isRefundMaskTarget', $isRefundMaskTarget); | |
| // 환불계좌는 은행·계좌번호·예금주가 한 칸에 모이므로 뷰가 칸 전체를 이 값 하나로 대체한다 | |
| $this->setData('maskChar', ColumnMaskingService::DEFAULT_MASK); | |
| // 취소사유 | |
| $cancelReasonCode = gd_array_change_key_value(gd_code('04001')); | |
변경 전LayerRegularOrderController.php
| use Bundle\Controller\Admin\Controller; | |
| use DTO\RegularDelivery\RegularOrder\RegularOrderGiftConditionDTO; | |
| use Origin\Enum\RegularDelivery\RegularGoods\RegularGoodsGift; | |
| class LayerRegularOrderController extends Controller | |
| { | |
| $shippingList = $shippingInfo['list']; | |
| $pager = $shippingInfo['pager']; | |
| $this->setData('applyNo', $getValue['applyNo']); | |
| $this->setData('shippingInfo', $shippingList); | |
| $this->setData('memNo', $memNo); | |
| $this->setData('page', $pager); | |
변경 후LayerRegularOrderController.php
| use Bundle\Controller\Admin\Controller; | |
| use DTO\RegularDelivery\RegularOrder\RegularOrderGiftConditionDTO; | |
| use Origin\Enum\RegularDelivery\RegularGoods\RegularGoodsGift; | |
| use Origin\Service\Privacy\Masking\ColumnMaskingService; | |
| use Origin\Service\Privacy\Masking\MaskingTargetService; | |
| use Origin\Service\Privacy\Masking\RegularOrderDetailMaskingService; | |
| use Origin\Service\Privacy\Withdrawn\WithdrawnOrderSeparatorService; | |
| class LayerRegularOrderController extends Controller | |
| { | |
| $shippingList = $shippingInfo['list']; | |
| $pager = $shippingInfo['pager']; | |
| // 개인정보 마스킹(정기결제 배송지 목록): 받으실분/주소/연락처 → '-' | |
| // 저장은 shippingSno 만 전송하므로 원본이 필요 없다 | |
| // 판정 기준은 회원 테이블이 아니라 신청서의 분리보관 여부다(분리 후 회원 행만 사라지면 판정이 뒤집힌다) | |
| $shippingApplyGroupNo = \App::getInstance(\Component\RegularDelivery\RegularOrderAdmin\RegularOrderAdminDetail::class) | |
| ->getApplyGroupNoByApplyNo((int) $getValue['applyNo']); | |
| $shippingMemberType = \App::getInstance(WithdrawnOrderSeparatorService::class) | |
| ->resolveRegularApplierMemberType($shippingApplyGroupNo); | |
| $shippingMaskLabel = \App::getInstance(MaskingTargetService::class) | |
| ->resolveMaskLabelBySeparationStatus($shippingMemberType?->value); | |
| if ($shippingMaskLabel !== null) { // 탈퇴/휴면 회원 | |
| $regularOrderDetailMasking = \App::getInstance(RegularOrderDetailMaskingService::class); | |
| foreach ($shippingList as $shippingKey => $shippingRow) { | |
| $shippingList[$shippingKey] = $regularOrderDetailMasking->maskShippingInfo($shippingRow); | |
| } | |
| } | |
| $this->setData('applyNo', $getValue['applyNo']); | |
| $this->setData('shippingInfo', $shippingList); | |
| $this->setData('shippingMaskLabel', $shippingMaskLabel); | |
| // 배송지 주소는 구성요소가 한 칸에 모이므로 뷰가 칸 전체를 이 값 하나로 대체한다 | |
| $this->setData('maskChar', ColumnMaskingService::DEFAULT_MASK); | |
| $this->setData('memNo', $memNo); | |
| $this->setData('page', $pager); | |
변경 전LogisticsListController.php
| namespace Bundle\Controller\Admin\Order; | |
| use Exception; | |
| use App; | |
| use Framework\Debug\Exception\AlertBackException; | |
| // --- 리스트 설정 | |
| $getData = $order->getOrderListForAdmin($getValue, $data['searchPeriod']); | |
| //상품준비중 리스트에서 배송정보를 주문별로 처리 할 수 있는지 체크 상태 | |
| $orderInfoGroup = null; | |
| if (empty($getData['data']) === false && is_array($getData['data']) && $getValue['view'] !== 'orderGoods') { | |
변경 후LogisticsListController.php
| namespace Bundle\Controller\Admin\Order; | |
| use Origin\Service\Privacy\Masking\OrderListMaskingService; | |
| use Exception; | |
| use App; | |
| use Framework\Debug\Exception\AlertBackException; | |
| // --- 리스트 설정 | |
| $getData = $order->getOrderListForAdmin($getValue, $data['searchPeriod']); | |
| // 개인정보 마스킹(주문 리스트): 주문자명→회원유형, 주문자 휴대폰·ID·수령자명·입금자명·입금계좌→'-' | |
| $getData = \App::getInstance(OrderListMaskingService::class)->maskOrderList($getData); | |
| //상품준비중 리스트에서 배송정보를 주문별로 처리 할 수 있는지 체크 상태 | |
| $orderInfoGroup = null; | |
| if (empty($getData['data']) === false && is_array($getData['data']) && $getValue['view'] !== 'orderGoods') { | |
변경 전OrderListAllController.php
| */ | |
| namespace Bundle\Controller\Admin\Order; | |
| use Component\Order\OrderAdmin; | |
| use Exception; | |
| use Globals; | |
| $getValue['orderAdminGridMode'] = $orderAdminGrid->getOrderAdminGridMode($getValue['view']); | |
| $this->setData('orderAdminGridMode', $getValue['orderAdminGridMode']); | |
| // 탈퇴회원거래내역조회 제한(y)일 경우, 검색조건에 미포함 처리 | |
| $session = \App::getInstance('session'); | |
| $manager = \App::load('\\Component\\Member\\Manager'); | |
| $withdrawnMembersOrderLimitViewFl = $manager->getManagerFunctionAuth($session->get('manager.sno'))['functionAuth']['withdrawnMembersOrderLimitViewFl']; | |
| if ($withdrawnMembersOrderLimitViewFl == 'y' && $getValue['withdrawnMembersOrderChk'] != 'n') { | |
| $getValue['withdrawnMembersOrderChk'] = 'n'; | |
| } | |
| $getData = $orderAdmin->getOrderListForAdmin($getValue, 6); | |
| $this->setData('data', gd_isset($getData['data'])); | |
| $this->setData('search', $getData['search']); | |
| $this->setData('checked', $getData['checked']); | |
변경 후OrderListAllController.php
| */ | |
| namespace Bundle\Controller\Admin\Order; | |
| use Origin\Service\Privacy\Masking\OrderListMaskingService; | |
| use Component\Order\OrderAdmin; | |
| use Exception; | |
| use Globals; | |
| $getValue['orderAdminGridMode'] = $orderAdminGrid->getOrderAdminGridMode($getValue['view']); | |
| $this->setData('orderAdminGridMode', $getValue['orderAdminGridMode']); | |
| // [탈퇴회원 주문 필터 제거] 탈퇴회원거래내역조회 제한 권한 기반 검색조건 강제('n') 처리 제거 (OrderAdmin 공통 메소드 무수정) | |
| $getData = $orderAdmin->getOrderListForAdmin($getValue, 6); | |
| // 개인정보 마스킹(주문 리스트): 주문자명→회원유형, 주문자 휴대폰·ID·수령자명·입금자명·입금계좌→'-' | |
| $getData = \App::getInstance(OrderListMaskingService::class)->maskOrderList($getData); | |
| $this->setData('data', gd_isset($getData['data'])); | |
| $this->setData('search', $getData['search']); | |
| $this->setData('checked', $getData['checked']); | |
변경 전OrderListBackController.php
| */ | |
| namespace Bundle\Controller\Admin\Order; | |
| use Globals; | |
| use Request; | |
| use Exception; | |
| // --- 리스트 설정 | |
| $getData = $order->getOrderListForAdmin($getValue, $data['searchPeriod']); | |
| $this->setData('search', $getData['search']); | |
| $this->setData('checked', $getData['checked']); | |
| $this->setData('data', gd_isset($getData['data'])); | |
변경 후OrderListBackController.php
| */ | |
| namespace Bundle\Controller\Admin\Order; | |
| use Origin\Service\Privacy\Masking\OrderListMaskingService; | |
| use Globals; | |
| use Request; | |
| use Exception; | |
| // --- 리스트 설정 | |
| $getData = $order->getOrderListForAdmin($getValue, $data['searchPeriod']); | |
| // 개인정보 마스킹(주문 리스트): 주문자명→회원유형, 주문자 휴대폰·ID·수령자명·입금자명·입금계좌→'-' | |
| $getData = \App::getInstance(OrderListMaskingService::class)->maskOrderList($getData); | |
| $this->setData('search', $getData['search']); | |
| $this->setData('checked', $getData['checked']); | |
| $this->setData('data', gd_isset($getData['data'])); | |
변경 전OrderListCancelController.php
| */ | |
| namespace Bundle\Controller\Admin\Order; | |
| use Exception; | |
| use Globals; | |
| use Request; | |
| // --- 리스트 설정 | |
| $getData = $order->getOrderListForAdmin($getValue, $data['searchPeriod']); | |
| $this->setData('search', $getData['search']); | |
| $this->setData('checked', $getData['checked']); | |
| $this->setData('data', gd_isset($getData['data'])); | |
변경 후OrderListCancelController.php
| */ | |
| namespace Bundle\Controller\Admin\Order; | |
| use Origin\Service\Privacy\Masking\OrderListMaskingService; | |
| use Exception; | |
| use Globals; | |
| use Request; | |
| // --- 리스트 설정 | |
| $getData = $order->getOrderListForAdmin($getValue, $data['searchPeriod']); | |
| // 개인정보 마스킹(주문 리스트): 주문자명→회원유형, 주문자 휴대폰·ID·수령자명·입금자명·입금계좌→'-' | |
| $getData = \App::getInstance(OrderListMaskingService::class)->maskOrderList($getData); | |
| $this->setData('search', $getData['search']); | |
| $this->setData('checked', $getData['checked']); | |
| $this->setData('data', gd_isset($getData['data'])); | |
변경 전OrderListDeliveryController.php
| */ | |
| namespace Bundle\Controller\Admin\Order; | |
| use Exception; | |
| use Globals; | |
| use Request; | |
| // --- 리스트 설정 | |
| $getData = $order->getOrderListForAdmin($getValue, $data['searchPeriod']); | |
| $this->setData('search', $getData['search']); | |
| $this->setData('checked', $getData['checked']); | |
| $this->setData('data', gd_isset($getData['data'])); | |
변경 후OrderListDeliveryController.php
| */ | |
| namespace Bundle\Controller\Admin\Order; | |
| use Origin\Service\Privacy\Masking\OrderListMaskingService; | |
| use Exception; | |
| use Globals; | |
| use Request; | |
| // --- 리스트 설정 | |
| $getData = $order->getOrderListForAdmin($getValue, $data['searchPeriod']); | |
| // 개인정보 마스킹(주문 리스트): 주문자명→회원유형, 주문자 휴대폰·ID·수령자명·입금자명·입금계좌→'-' | |
| $getData = \App::getInstance(OrderListMaskingService::class)->maskOrderList($getData); | |
| $this->setData('search', $getData['search']); | |
| $this->setData('checked', $getData['checked']); | |
| $this->setData('data', gd_isset($getData['data'])); | |
변경 전OrderListDeliveryOkController.php
| namespace Bundle\Controller\Admin\Order; | |
| use Exception; | |
| use Globals; | |
| use Request; | |
| // --- 리스트 설정 | |
| $getData = $order->getOrderListForAdmin($getValue, $data['searchPeriod']); | |
| $this->setData('search', $getData['search']); | |
| $this->setData('checked', $getData['checked']); | |
| $this->setData('data', gd_isset($getData['data'])); | |
변경 후OrderListDeliveryOkController.php
| namespace Bundle\Controller\Admin\Order; | |
| use Origin\Service\Privacy\Masking\OrderListMaskingService; | |
| use Exception; | |
| use Globals; | |
| use Request; | |
| // --- 리스트 설정 | |
| $getData = $order->getOrderListForAdmin($getValue, $data['searchPeriod']); | |
| // 개인정보 마스킹(주문 리스트): 주문자명→회원유형, 주문자 휴대폰·ID·수령자명·입금자명·입금계좌→'-' | |
| $getData = \App::getInstance(OrderListMaskingService::class)->maskOrderList($getData); | |
| $this->setData('search', $getData['search']); | |
| $this->setData('checked', $getData['checked']); | |
| $this->setData('data', gd_isset($getData['data'])); | |
변경 전OrderListExchangeController.php
| */ | |
| namespace Bundle\Controller\Admin\Order; | |
| use Globals; | |
| use Request; | |
| use Exception; | |
| // --- 리스트 설정 | |
| $getData = $order->getOrderListForAdmin($getValue, $data['searchPeriod']); | |
| $this->setData('search', $getData['search']); | |
| $this->setData('checked', $getData['checked']); | |
| $this->setData('data', gd_isset($getData['data'])); | |
변경 후OrderListExchangeController.php
| */ | |
| namespace Bundle\Controller\Admin\Order; | |
| use Origin\Service\Privacy\Masking\OrderListMaskingService; | |
| use Globals; | |
| use Request; | |
| use Exception; | |
| // --- 리스트 설정 | |
| $getData = $order->getOrderListForAdmin($getValue, $data['searchPeriod']); | |
| // 개인정보 마스킹(주문 리스트): 주문자명→회원유형, 주문자 휴대폰·ID·수령자명·입금자명·입금계좌→'-' | |
| $getData = \App::getInstance(OrderListMaskingService::class)->maskOrderList($getData); | |
| $this->setData('search', $getData['search']); | |
| $this->setData('checked', $getData['checked']); | |
| $this->setData('data', gd_isset($getData['data'])); | |
변경 전OrderListFailController.php
| */ | |
| namespace Bundle\Controller\Admin\Order; | |
| use Exception; | |
| use Globals; | |
| use Request; | |
| // --- 리스트 설정 | |
| $getData = $order->getOrderListForAdmin($getValue, $data['searchPeriod']); | |
| $this->setData('search', $getData['search']); | |
| $this->setData('checked', $getData['checked']); | |
| $this->setData('data', gd_isset($getData['data'])); | |
변경 후OrderListFailController.php
| */ | |
| namespace Bundle\Controller\Admin\Order; | |
| use Origin\Service\Privacy\Masking\OrderListMaskingService; | |
| use Exception; | |
| use Globals; | |
| use Request; | |
| // --- 리스트 설정 | |
| $getData = $order->getOrderListForAdmin($getValue, $data['searchPeriod']); | |
| // 개인정보 마스킹(주문 리스트): 주문자명→회원유형, 주문자 휴대폰·ID·수령자명·입금자명·입금계좌→'-' | |
| $getData = \App::getInstance(OrderListMaskingService::class)->maskOrderList($getData); | |
| $this->setData('search', $getData['search']); | |
| $this->setData('checked', $getData['checked']); | |
| $this->setData('data', gd_isset($getData['data'])); | |
변경 전OrderListGoodsController.php
| */ | |
| namespace Bundle\Controller\Admin\Order; | |
| use Exception; | |
| use App; | |
| use Request; | |
| // --- 리스트 설정 | |
| $getData = $order->getOrderListForAdmin($getValue, $data['searchPeriod']); | |
| //상품준비중 리스트에서 배송정보를 주문별로 처리 할 수 있는지 체크 상태 | |
| if (empty($getData['data']) === false && is_array($getData['data']) && $getValue['view'] !== 'orderGoods') { | |
변경 후OrderListGoodsController.php
| */ | |
| namespace Bundle\Controller\Admin\Order; | |
| use Origin\Service\Privacy\Masking\OrderListMaskingService; | |
| use Exception; | |
| use App; | |
| use Request; | |
| // --- 리스트 설정 | |
| $getData = $order->getOrderListForAdmin($getValue, $data['searchPeriod']); | |
| // 개인정보 마스킹(주문 리스트): 주문자명→회원유형, 주문자 휴대폰·ID·수령자명·입금자명·입금계좌→'-' | |
| $getData = \App::getInstance(OrderListMaskingService::class)->maskOrderList($getData); | |
| //상품준비중 리스트에서 배송정보를 주문별로 처리 할 수 있는지 체크 상태 | |
| if (empty($getData['data']) === false && is_array($getData['data']) && $getValue['view'] !== 'orderGoods') { | |
변경 전OrderListOrderController.php
| */ | |
| namespace Bundle\Controller\Admin\Order; | |
| use Exception; | |
| use Globals; | |
| use Request; | |
| // --- 리스트 설정 | |
| $getData = $order->getOrderListForAdmin($getValue, $data['searchPeriod']); | |
| $this->setData('search', $getData['search']); | |
| $this->setData('checked', $getData['checked']); | |
| $this->setData('data', gd_isset($getData['data'])); | |
변경 후OrderListOrderController.php
| */ | |
| namespace Bundle\Controller\Admin\Order; | |
| use Origin\Service\Privacy\Masking\OrderListMaskingService; | |
| use Exception; | |
| use Globals; | |
| use Request; | |
| // --- 리스트 설정 | |
| $getData = $order->getOrderListForAdmin($getValue, $data['searchPeriod']); | |
| // 개인정보 마스킹(주문 리스트): 주문자명→회원유형, 주문자 휴대폰·ID·수령자명·입금자명·입금계좌→'-' | |
| $getData = \App::getInstance(OrderListMaskingService::class)->maskOrderList($getData); | |
| $this->setData('search', $getData['search']); | |
| $this->setData('checked', $getData['checked']); | |
| $this->setData('data', gd_isset($getData['data'])); | |
변경 전OrderListPayController.php
| */ | |
| namespace Bundle\Controller\Admin\Order; | |
| use Exception; | |
| use Globals; | |
| use Request; | |
| // --- 리스트 설정 | |
| $getData = $orderAdmin->getOrderListForAdmin($getValue, $data['searchPeriod']); | |
| $this->setData('search', $getData['search']); | |
| $this->setData('checked', $getData['checked']); | |
| $this->setData('data', gd_isset($getData['data'])); | |
변경 후OrderListPayController.php
| */ | |
| namespace Bundle\Controller\Admin\Order; | |
| use Origin\Service\Privacy\Masking\OrderListMaskingService; | |
| use Exception; | |
| use Globals; | |
| use Request; | |
| // --- 리스트 설정 | |
| $getData = $orderAdmin->getOrderListForAdmin($getValue, $data['searchPeriod']); | |
| // 개인정보 마스킹(주문 리스트): 주문자명→회원유형, 주문자 휴대폰·ID·수령자명·입금자명·입금계좌→'-' | |
| $getData = \App::getInstance(OrderListMaskingService::class)->maskOrderList($getData); | |
| $this->setData('search', $getData['search']); | |
| $this->setData('checked', $getData['checked']); | |
| $this->setData('data', gd_isset($getData['data'])); | |
변경 전OrderListRefundController.php
| */ | |
| namespace Bundle\Controller\Admin\Order; | |
| use Globals; | |
| use Request; | |
| use Framework\Utility\ArrayUtils; | |
| // --- 리스트 설정 | |
| $getData = $order->getOrderListForAdmin($getValue, $data['searchPeriod']); | |
| $this->setData('search', $getData['search']); | |
| $this->setData('checked', $getData['checked']); | |
| $this->setData('data', gd_isset($getData['data'])); | |
변경 후OrderListRefundController.php
| */ | |
| namespace Bundle\Controller\Admin\Order; | |
| use Origin\Service\Privacy\Masking\OrderListMaskingService; | |
| use Globals; | |
| use Request; | |
| use Framework\Utility\ArrayUtils; | |
| // --- 리스트 설정 | |
| $getData = $order->getOrderListForAdmin($getValue, $data['searchPeriod']); | |
| // 개인정보 마스킹(주문 리스트): 주문자명→회원유형, 주문자 휴대폰·ID·수령자명·입금자명·입금계좌→'-' | |
| $getData = \App::getInstance(OrderListMaskingService::class)->maskOrderList($getData); | |
| $this->setData('search', $getData['search']); | |
| $this->setData('checked', $getData['checked']); | |
| $this->setData('data', gd_isset($getData['data'])); | |
변경 전OrderListSettleController.php
| */ | |
| namespace Bundle\Controller\Admin\Order; | |
| use Exception; | |
| use Globals; | |
| use Request; | |
| // --- 리스트 설정 | |
| $getData = $order->getOrderListForAdmin($getValue, $data['searchPeriod']); | |
| $this->setData('search', $getData['search']); | |
| $this->setData('checked', $getData['checked']); | |
| $this->setData('data', gd_isset($getData['data'])); | |
변경 후OrderListSettleController.php
| */ | |
| namespace Bundle\Controller\Admin\Order; | |
| use Origin\Service\Privacy\Masking\OrderListMaskingService; | |
| use Exception; | |
| use Globals; | |
| use Request; | |
| // --- 리스트 설정 | |
| $getData = $order->getOrderListForAdmin($getValue, $data['searchPeriod']); | |
| // 개인정보 마스킹(주문 리스트): 주문자명→회원유형, 주문자 휴대폰·ID·수령자명·입금자명·입금계좌→'-' | |
| $getData = \App::getInstance(OrderListMaskingService::class)->maskOrderList($getData); | |
| $this->setData('search', $getData['search']); | |
| $this->setData('checked', $getData['checked']); | |
| $this->setData('data', gd_isset($getData['data'])); | |
변경 전OrderListUserExchangeController.php
| */ | |
| namespace Bundle\Controller\Admin\Order; | |
| use Globals; | |
| use Request; | |
| use Exception; | |
| // --- 리스트 설정 | |
| $getData = $order->getOrderListForAdmin($getValue, $data['searchPeriod'], true); | |
| $this->setData('checked', $getData['checked']); | |
| $this->setData('search', $getData['search']); | |
| $this->setData('data', gd_isset($getData['data'])); | |
변경 후OrderListUserExchangeController.php
| */ | |
| namespace Bundle\Controller\Admin\Order; | |
| use Origin\Service\Privacy\Masking\OrderListMaskingService; | |
| use Globals; | |
| use Request; | |
| use Exception; | |
| // --- 리스트 설정 | |
| $getData = $order->getOrderListForAdmin($getValue, $data['searchPeriod'], true); | |
| // 개인정보 마스킹(주문 리스트): 주문자명→회원유형, 주문자 휴대폰·ID·수령자명·입금자명·입금계좌→'-' | |
| $getData = \App::getInstance(OrderListMaskingService::class)->maskOrderList($getData); | |
| $this->setData('checked', $getData['checked']); | |
| $this->setData('search', $getData['search']); | |
| $this->setData('data', gd_isset($getData['data'])); | |
변경 전OrderListWithdrawnMemberController.php
변경 후OrderListWithdrawnMemberController.php
| <?php | |
| /* | |
| * Copyright (C) 2026 NHN COMMERCE. - All Rights Reserved | |
| * | |
| * Unauthorized copying or redistribution of this file in source and binary forms via any medium | |
| * is strictly prohibited. | |
| */ | |
| namespace Bundle\Controller\Admin\Order; | |
| use Request; | |
| use Component\Member\Manager; | |
| use Component\Page\Page; | |
| use Origin\DTO\Privacy\Withdrawn\WithdrawnOrderListSearchDTO; | |
| use Origin\Service\Privacy\Withdrawn\WithdrawnOrderListService; | |
| /** | |
| * 휴면/탈퇴 회원 주문 리스트 컨트롤러 | |
| */ | |
| class OrderListWithdrawnMemberController extends \Controller\Admin\Controller | |
| { | |
| public function index() | |
| { | |
| $this->callMenu('order', 'order', 'withdrawn_member'); | |
| // 공급사 계정 게이트: 공급사 로그인 시 공급사 구분 필터/컬럼 미노출 + 본인 공급사로 강제 | |
| $isProvider = Manager::isProvider(); | |
| $this->setData('isProvider', $isProvider); | |
| $searchDto = WithdrawnOrderListSearchDTO::fromRequest( | |
| Request::get()->all(), | |
| date('Y-m-d'), | |
| $isProvider, | |
| (int) \Session::get('manager.scmNo') | |
| ); | |
| /** @var WithdrawnOrderListService $withdrawnOrderListService */ | |
| $withdrawnOrderListService = \App::getInstance(WithdrawnOrderListService::class); | |
| $mallService = \App::load('Component\\Mall\\Mall'); | |
| $this->setData('mallTypeOptions', $withdrawnOrderListService->buildMallTypeOptions($mallService->getListByUseMall())); | |
| // 최초 진입 = 검색 미수행(보안). 주문자는 필수 검색 조건이므로 검색어까지 있어야 조회한다. | |
| // Request::getQueryString() 은 쿼리스트링이 비면 '' 가 아니라 null 을 돌려준다. | |
| // 공급사를 고르지 않은 '공급사' 검색은 조건 불충분이므로 조회하지 않는다(화면 우회 방어) | |
| $isSearched = !empty(Request::getQueryString()) | |
| && $searchDto->getSearchWord() !== '' | |
| && !$searchDto->isSupplierUnselected(); | |
| // 전체 건수는 검색 여부·검색 조건과 무관하게 항상 노출한다. | |
| $totalCount = $withdrawnOrderListService->getTotalCount($searchDto); | |
| $list = []; | |
| $searchCount = 0; | |
| $pagination = ''; | |
| $orderDt = $searchDto->getOrderDt(); | |
| if ($isSearched) { | |
| $result = $withdrawnOrderListService->getList($searchDto); | |
| $searchCount = $result['total']; | |
| $list = $this->buildListRows($result['list']); | |
| // 서비스가 보안 클램프한 실제 조회 기간을 화면 datepicker 에 되돌린다 | |
| $orderDt = $result['orderDt']; | |
| $pageObj = new Page($searchDto->page, $searchCount, $totalCount, $searchDto->pageSize); | |
| $pageObj->setPage(); | |
| $pageObj->setUrl(Request::getQueryString()); | |
| $pagination = $pageObj->getPage(); | |
| } | |
| $this->setData('data', ['list' => $list]); | |
| $this->setData('cnt', ['search' => $searchCount, 'total' => $totalCount]); | |
| $this->setData('pagination', $pagination); | |
| $this->setData('search', $searchDto->toSearchForm()); | |
| $this->setData('orderDt', $orderDt); | |
| $this->setData('pageSize', $searchDto->pageSize); | |
| $this->getView()->setPageName('order/order_list_withdrawn_member.php'); | |
| } | |
| /** | |
| * 조회 행을 뷰 노출 필드로 화이트리스트한다. | |
| * | |
| * @param array $rows WithdrawnOrderListService::getList() 의 list | |
| * @return array 각 원소: listNo/orderNo/mallTypeStr/scmNm/scmSupplierNames/memberTypeStr/ | |
| * memId/orderName/bankSender/orderCellPhone/orderEmail/ | |
| * receiverName/receiverCellPhone/receiverAddress/receiverAddressSub/receiverZonecode | |
| */ | |
| protected function buildListRows(array $rows): array | |
| { | |
| // 이 화면은 분리보관 원본을 복호화해 보여주므로, '개인정보조회 제한' 권한이 걸린 운영자에게는 | |
| // 식별 가능한 항목을 부분마스킹해 내보낸다(권한이 없으면 masking() 이 원본을 그대로 돌려준다) | |
| $memberMasking = \App::load('Component\\Member\\MemberMasking'); | |
| $list = []; | |
| foreach ($rows as $row) { | |
| $list[] = [ | |
| 'listNo' => $row['listNo'], | |
| 'orderNo' => $row['orderNo'], | |
| 'mallTypeStr' => $row['mallTypeStr'], // 상점 구분(domainFl → 기준/영문/중문/일문) | |
| 'scmNm' => $row['scmNm'], // 공급사 구분 라벨(본사/공급사) | |
| 'scmSupplierNames' => $row['scmSupplierNames'], // 공급사면 주문별 실제 공급사명 | |
| 'memberTypeStr' => $row['memberTypeStr'], | |
| // 주문자 PII(분리보관 복호화) | |
| 'memId' => $memberMasking->masking('order', 'id', $row['memId']), | |
| 'orderName' => $memberMasking->masking('order', 'name', $row['orderName']), | |
| 'bankSender' => $memberMasking->masking('order', 'name', $row['bankSender']), | |
| 'orderCellPhone' => $memberMasking->masking('order', 'tel', $row['orderCellPhone']), | |
| 'orderEmail' => $memberMasking->masking('order', 'email', $row['orderEmail']), | |
| // 수령자 PII(분리보관 복호화) + 우편번호(원본 비PII) | |
| 'receiverName' => $memberMasking->masking('order', 'name', $row['receiverName']), | |
| 'receiverCellPhone' => $memberMasking->masking('order', 'tel', $row['receiverCellPhone']), | |
| 'receiverAddress' => $memberMasking->masking('order', 'address', $row['receiverAddress']), | |
| 'receiverAddressSub' => $memberMasking->masking('order', 'address', $row['receiverAddressSub']), | |
| 'receiverZonecode' => $row['receiverZonecode'], | |
| ]; | |
| } | |
| return $list; | |
| } | |
| } | |
변경 전OrderPrintController.php
| use Framework\Utility\NumberUtils; | |
| use Framework\Utility\StringUtils; | |
| use Component\Member\Manager; | |
| /** | |
| * 주문내역서/간이영수증/거래명세서/세금계산서 출력 팝업 | |
| // throw new AlertOnlyException('관련 정보가 존재하지 않습니다.', null, null, 'parent.close();'); | |
| // } | |
| $this->setData('orderData', gd_htmlspecialchars(gd_isset($orderData))); | |
| // 거래명세서, 주문내역서 (고객용) 번역 | |
| if (Request::post()->get('orderPrintMode') == 'particular' || Request::post()->get('orderPrintMode') == 'customerReport') { | |
변경 후OrderPrintController.php
| use Framework\Utility\NumberUtils; | |
| use Framework\Utility\StringUtils; | |
| use Component\Member\Manager; | |
| use Origin\Service\Privacy\Masking\ColumnMaskingService; | |
| use Origin\Service\Privacy\Masking\MaskingTargetService; | |
| use Origin\Service\Privacy\Masking\OrderPrintMaskingService; | |
| /** | |
| * 주문내역서/간이영수증/거래명세서/세금계산서 출력 팝업 | |
| // throw new AlertOnlyException('관련 정보가 존재하지 않습니다.', null, null, 'parent.close();'); | |
| // } | |
| // 개인정보 마스킹(주문 출력물): 주문자명→회원유형, 주문자·수령자 연락처/주소·입금자명·입금계좌·세금계산서 공급받는자 성명/주소→'-' | |
| if (is_array($orderData)) { | |
| // 출력물 종류에 따라 주문번호가 배열 키이거나(세금계산서) 행 안에 있어(그 외) 둘 다 본다 | |
| $maskOrderNos = []; | |
| foreach ($orderData as $orderKey => $orderRow) { | |
| $maskOrderNos[] = is_array($orderRow) && !empty($orderRow['orderNo']) | |
| ? (string) $orderRow['orderNo'] | |
| : (string) $orderKey; | |
| } | |
| $maskLabels = \App::getInstance(MaskingTargetService::class) | |
| ->resolveMaskLabelsByOrderNos($maskOrderNos); | |
| $orderData = \App::getInstance(OrderPrintMaskingService::class) | |
| ->maskByMode($orderData, Request::post()->get('orderPrintMode'), $maskLabels); | |
| } | |
| $this->setData('orderData', gd_htmlspecialchars(gd_isset($orderData))); | |
| // 주소·계좌처럼 구성요소가 한 칸에 모이는 항목은 뷰가 칸 전체를 이 값 하나로 대체한다 | |
| $this->setData('maskChar', ColumnMaskingService::DEFAULT_MASK); | |
| // 거래명세서, 주문내역서 (고객용) 번역 | |
| if (Request::post()->get('orderPrintMode') == 'particular' || Request::post()->get('orderPrintMode') == 'customerReport') { | |
변경 전OrderViewController.php
| use Framework\Security\Token; | |
| use Globals; | |
| use Origin\Service\Coupon\UpdateCouponService; | |
| use Session; | |
| use Request; | |
| $data = $order->getOrderView($request->get()->get('orderNo'), null, null, null, $excludeStatus, null); | |
| $data['visitDeliveryInfo'] = $delivery->getVisitDeliveryInfo($data); | |
| $withdrawnMembersOrderData = $order->getWithdrawnMembersOrderViewByOrderNo($data['orderNo']); | |
| $withdrawnMembersPersonalData = $withdrawnMembersOrderData['personalInfo'][0]; | |
| $withdrawnMembersOrderFl = !empty($withdrawnMembersPersonalData) ? 'y' : 'n'; | |
| $this->setData('withdrawnMembersOrderFl', $withdrawnMembersOrderFl); | |
| //최초 주문정보 | |
| $orderReorderCalculation = \App::load('\\Component\\Order\\ReOrderCalculation'); | |
| $data['orderTypeFlNm'] = '수기주문'; | |
| } | |
| // 템플릿 데이터 설정 | |
| $this->setData('order', $order); | |
| if ($data['orderChannelFl'] == 'naverpay') { | |
| } else { | |
| $this->setData('data', gd_htmlspecialchars(gd_isset($data))); | |
| } | |
| $this->setData('withdrawnMembersPersonalData', gd_isset($withdrawnMembersPersonalData)); | |
| $this->setData('addFieldData', gd_isset($addFieldData)); | |
| $this->setData('orderStatusCode', gd_isset($orderStatusCode)); | |
| $this->setData('_delivery', Globals::get('gDelivery')); | |
| throw $e; | |
| } | |
| } | |
| } | |
변경 후OrderViewController.php
| use Framework\Security\Token; | |
| use Globals; | |
| use Origin\Service\Coupon\UpdateCouponService; | |
| use Origin\Service\Privacy\Masking\ColumnMaskingService; | |
| use Origin\Service\Privacy\Masking\MaskingTargetService; | |
| use Origin\Service\Privacy\Masking\OrderDetailMaskingService; | |
| use Origin\Service\Privacy\Withdrawn\WithdrawnOrderHydratorService; | |
| use Origin\Enum\Privacy\Withdrawn\WithdrawnMemberType; | |
| use Origin\Enum\Privacy\Withdrawn\WithdrawnSection; | |
| use Session; | |
| use Request; | |
| $data = $order->getOrderView($request->get()->get('orderNo'), null, null, null, $excludeStatus, null); | |
| $data['visitDeliveryInfo'] = $delivery->getVisitDeliveryInfo($data); | |
| $separationStatus = $data['separationStatus'] ?? ''; | |
| $withdrawnHydrator = \App::getInstance(WithdrawnOrderHydratorService::class); | |
| $withdrawnMembersPersonalData = null; | |
| // [휴면 복원] | |
| // - 원복 데이터: 주문자/수령자 PII(orderName·연락처·주소 등) | |
| // - 용도: 주문상세 표기·기능(SMS·안심번호 해지/수정) | |
| // - 대상: 휴면만(탈퇴는 별도키 유지=원복 안 함. 분리보관 완료 플래그로 판정해 일반 주문은 분리보관 조회 생략) | |
| if ($separationStatus === WithdrawnMemberType::SLEEP->value) { | |
| $sleepType = WithdrawnMemberType::SLEEP; | |
| $data = $withdrawnHydrator->restore($data, WithdrawnSection::ORDER_INFO, $sleepType, $data['orderNo']); | |
| // 안심번호(receiverSafeNumber): 해지/수정 폼이 $data['receiverSafeNumber'] 를 사용 → 동일 동작 위해 복원 | |
| $data = $withdrawnHydrator->restore($data, WithdrawnSection::SAFE_NUMBER, $sleepType, $data['orderNo']); | |
| } | |
| // [탈퇴 복원] | |
| // - 원복 데이터: 표시 별도키(withdrawnMembersPersonalData) + 안심번호(receiverSafeNumber) | |
| // - 용도: 주문상세 표기(표시 별도키에 병합, decryptData 13컬럼 미포함이라 SAFE_NUMBER 별도 복호화) | |
| // - 대상: 탈퇴만(발급/해지 버튼은 baseline 미동작. 분리보관 완료 플래그로 판정해 일반 주문은 분리보관 조회 생략) | |
| if ($separationStatus === WithdrawnMemberType::HACKOUT->value) { | |
| $withdrawnMembersOrderData = $order->getWithdrawnMembersOrderViewByOrderNo($data['orderNo']); | |
| $withdrawnMembersPersonalData = $withdrawnMembersOrderData['personalInfo'][0] ?? null; | |
| $hackoutSafeNumber = $withdrawnHydrator->hydrateOne(WithdrawnSection::SAFE_NUMBER, WithdrawnMemberType::HACKOUT, $data['orderNo']); | |
| if (empty($hackoutSafeNumber['receiverSafeNumber']) === false) { | |
| $withdrawnMembersPersonalData['receiverSafeNumber'] = $hackoutSafeNumber['receiverSafeNumber']; | |
| } | |
| } | |
| // [탈퇴회원 주문 필터 제거] withdrawnMembersOrderFl setData 제거 → 탈퇴주문 상세 접근차단 해제(마스킹 표시는 유지) | |
| //최초 주문정보 | |
| $orderReorderCalculation = \App::load('\\Component\\Order\\ReOrderCalculation'); | |
| $data['orderTypeFlNm'] = '수기주문'; | |
| } | |
| // 개인정보 마스킹(주문 상세): 주문자명→회원유형, 주문자·수령자 연락처/주소·구매자IP·입금자명·입금계좌→'-' | |
| // 표시 키를 그대로 덮으므로 뷰가 튜닝돼 있어도 적용되고, 기능에 필요한 값만 분리 원본 키로 남는다 | |
| $orderDetailMasking = \App::getInstance(OrderDetailMaskingService::class); | |
| $orderMaskLabel = \App::getInstance(MaskingTargetService::class) | |
| ->resolveMaskLabelByOrderNo(gd_isset($data['orderNo'])); | |
| $isMaskTarget = $orderMaskLabel !== null; // 탈퇴/휴면 회원 주문 | |
| if ($isMaskTarget && is_array($data)) { | |
| $data = $orderDetailMasking->maskDetail($data); | |
| // 복수배송지 행은 뷰가 $data 에 병합해 같은 수령자 화면을 다시 그리므로 행마다 같은 치환이 필요하다 | |
| if (isset($data['multiShippingList']) && is_array($data['multiShippingList'])) { | |
| foreach ($data['multiShippingList'] as $shippingKey => $multiShippingRow) { | |
| if (is_array($multiShippingRow)) { | |
| $data['multiShippingList'][$shippingKey] = $orderDetailMasking->maskDetail($multiShippingRow); | |
| } | |
| } | |
| } | |
| } | |
| // 템플릿 데이터 설정 | |
| $this->setData('order', $order); | |
| if ($data['orderChannelFl'] == 'naverpay') { | |
| } else { | |
| $this->setData('data', gd_htmlspecialchars(gd_isset($data))); | |
| } | |
| // 주문자명: 탈퇴/휴면=회원유형 라벨, 일반 회원=null | |
| $this->setData('orderMaskLabel', $orderMaskLabel); | |
| // 주소는 우편번호·기본·상세·시도·시군구가 각각 '-' 로 치환돼 한 칸에 모이면 하이픈이 반복된다. | |
| // 그래서 뷰가 주소 칸 전체를 이 값 하나로 대체한다. | |
| $this->setData('maskChar', ColumnMaskingService::DEFAULT_MASK); | |
| // 탈퇴회원 분리보관 표시값도 동일 마스킹 | |
| $this->setData('withdrawnMembersPersonalData', $orderDetailMasking->maskDetail(is_array($withdrawnMembersPersonalData) ? $withdrawnMembersPersonalData : [])); | |
| $this->setData('addFieldData', gd_isset($addFieldData)); | |
| $this->setData('orderStatusCode', gd_isset($orderStatusCode)); | |
| $this->setData('_delivery', Globals::get('gDelivery')); | |
| throw $e; | |
| } | |
| } | |
| } | |
변경 전PopupOrderCashReceiptReissueController.php
| use Request; | |
| use Encryptor; | |
| use Exception; | |
| /** | |
| * 현금영수증 재발행 | |
| // --- 관리자 디자인 템플릿 | |
| $this->getView()->setDefine('layout', 'layout_blank.php'); | |
| $this->setData('ordData', gd_htmlspecialchars($data)); | |
| $this->setData('data', gd_htmlspecialchars($getData)); | |
| $this->setData('checked', $checked); | |
변경 후PopupOrderCashReceiptReissueController.php
| use Request; | |
| use Encryptor; | |
| use Exception; | |
| use Origin\Service\Privacy\Masking\MaskingTargetService; | |
| use Origin\Service\Privacy\Masking\OrderDetailMaskingService; | |
| /** | |
| * 현금영수증 재발행 | |
| // --- 관리자 디자인 템플릿 | |
| $this->getView()->setDefine('layout', 'layout_blank.php'); | |
| // 표시 키를 그대로 덮으므로 뷰가 튜닝돼 있어도 적용된다. | |
| // 재발행 전송값은 뷰가 분리 원본 키로 원본을 보낸다 | |
| $isMaskTarget = \App::getInstance(MaskingTargetService::class) | |
| ->isMaskTargetOrderNo(Request::get()->get('orderNo')); | |
| if ($isMaskTarget) { | |
| $getData = \App::getInstance(OrderDetailMaskingService::class)->maskCashReceipt($getData); | |
| } | |
| $this->setData('ordData', gd_htmlspecialchars($data)); | |
| $this->setData('data', gd_htmlspecialchars($getData)); | |
| $this->setData('checked', $checked); | |
변경 전PopupOrderPacketController.php
| use Request; | |
| use Framework\Debug\Exception\AlertCloseException; | |
| use Component\Member\Manager; | |
| /** | |
| * Class PopupOrderPacketController | |
| $packetAbleFl = true; | |
| } | |
| $this->setData('orderData', $orderData); | |
| $this->setData('packetAbleFl', $packetAbleFl); | |
| $this->setData('orderNoStr', $getValue['orderNoStr']); | |
변경 후PopupOrderPacketController.php
| use Request; | |
| use Framework\Debug\Exception\AlertCloseException; | |
| use Component\Member\Manager; | |
| use Origin\Service\Privacy\Masking\ColumnMaskingService; | |
| use Origin\Service\Privacy\Masking\MaskingTargetService; | |
| /** | |
| * Class PopupOrderPacketController | |
| $packetAbleFl = true; | |
| } | |
| // 분리보관(탈퇴/휴면) 주문은 개인정보를 되살려 고칠 수 없으므로 수령자 정보변경을 막는다 | |
| $this->setData( | |
| 'withdrawnMaskLabels', | |
| \App::getInstance(MaskingTargetService::class)->resolveMaskLabelsByOrderNos($orderNoArr) | |
| ); | |
| // 수령자명·연락처·주소는 각각 한 칸에 모이므로 뷰가 칸 전체를 이 값 하나로 대체한다 | |
| $this->setData('maskChar', ColumnMaskingService::DEFAULT_MASK); | |
| $this->setData('orderData', $orderData); | |
| $this->setData('packetAbleFl', $packetAbleFl); | |
| $this->setData('orderNoStr', $getValue['orderNoStr']); | |
변경 전PostIssueController.php
| */ | |
| namespace Bundle\Controller\Admin\Order; | |
| use Component\Order\EpostReturnAdmin; | |
| use Exception; | |
| use Framework\Debug\Exception\AlertBackException; | |
| $getValue['statusMode'] = "p,g"; | |
| $getData = $order->getOrderGodoPostListForAdmin($getValue, $data['searchPeriod']); | |
| unset($getData['search']['combineSearch']['pu.purchaseNm']); //우체국 택배에서는 매입처 검색 제외 | |
| $this->setData('data', gd_isset($getData['data'])); | |
변경 후PostIssueController.php
| */ | |
| namespace Bundle\Controller\Admin\Order; | |
| use Origin\Service\Privacy\Masking\OrderListMaskingService; | |
| use Component\Order\EpostReturnAdmin; | |
| use Exception; | |
| use Framework\Debug\Exception\AlertBackException; | |
| $getValue['statusMode'] = "p,g"; | |
| $getData = $order->getOrderGodoPostListForAdmin($getValue, $data['searchPeriod']); | |
| // 개인정보 마스킹(주문 리스트): 주문자명→회원유형, 주문자 휴대폰·ID·수령자명·입금자명·입금계좌→'-' | |
| $getData = \App::getInstance(OrderListMaskingService::class)->maskOrderList($getData); | |
| unset($getData['search']['combineSearch']['pu.purchaseNm']); //우체국 택배에서는 매입처 검색 제외 | |
| $this->setData('data', gd_isset($getData['data'])); | |
변경 전PostReserveController.php
| */ | |
| namespace Bundle\Controller\Admin\Order; | |
| use Component\Order\EpostReturnAdmin; | |
| use Exception; | |
| use Framework\Debug\Exception\AlertBackException; | |
| $getValue['invoiceReserveFl'] = "n"; | |
| $getValue['view'] = "orderGoods"; | |
| $getData = $order->getOrderGodoPostListForAdmin($getValue, '365',true); | |
| $this->setData('data', gd_isset($getData['data'])); | |
| $this->setData('search', $getData['search']); | |
변경 후PostReserveController.php
| */ | |
| namespace Bundle\Controller\Admin\Order; | |
| use Origin\Service\Privacy\Masking\OrderListMaskingService; | |
| use Component\Order\EpostReturnAdmin; | |
| use Exception; | |
| use Framework\Debug\Exception\AlertBackException; | |
| $getValue['invoiceReserveFl'] = "n"; | |
| $getValue['view'] = "orderGoods"; | |
| $getData = $order->getOrderGodoPostListForAdmin($getValue, '365',true); | |
| // 개인정보 마스킹(주문 리스트): 주문자명→회원유형, 주문자 휴대폰·ID·수령자명·입금자명·입금계좌→'-' | |
| $getData = \App::getInstance(OrderListMaskingService::class)->maskOrderList($getData); | |
| $this->setData('data', gd_isset($getData['data'])); | |
| $this->setData('search', $getData['search']); | |
변경 전RefundViewController.php
| use Exception; | |
| use Globals; | |
| use Session; | |
| /** | |
| * 환불 완료 리스트 페이지 | |
| throw new AlertCloseException(__('처리 할 주문상품이 없습니다.')); | |
| } | |
| // 해외상점의 경우 무조건 전체 반품/교환/환불처리하도록 함 | |
| if ($getData['mallSno'] > DEFAULT_MALL_NUMBER && $handleSno !== null) { | |
| throw new AlertCloseException(__('해외상점 취소/교환/반품/환불은 전체 처리만 가능합니다.')); | |
변경 후RefundViewController.php
| use Exception; | |
| use Globals; | |
| use Session; | |
| use Origin\Service\Privacy\Masking\ColumnMaskingService; | |
| use Origin\Service\Privacy\Masking\MaskingTargetService; | |
| /** | |
| * 환불 완료 리스트 페이지 | |
| throw new AlertCloseException(__('처리 할 주문상품이 없습니다.')); | |
| } | |
| // 개인정보 마스킹(환불 계좌정보): 은행·계좌번호·예금주 → '-' | |
| $this->setData('isRefundMaskTarget', \App::getInstance(MaskingTargetService::class) | |
| ->isMaskTargetOrderNo($getValue['orderNo'])); | |
| // 환불계좌는 은행·계좌번호·예금주가 한 칸에 모이므로 뷰가 칸 전체를 이 값 하나로 대체한다 | |
| $this->setData('maskChar', ColumnMaskingService::DEFAULT_MASK); | |
| // 해외상점의 경우 무조건 전체 반품/교환/환불처리하도록 함 | |
| if ($getData['mallSno'] > DEFAULT_MALL_NUMBER && $handleSno !== null) { | |
| throw new AlertCloseException(__('해외상점 취소/교환/반품/환불은 전체 처리만 가능합니다.')); | |
변경 전RefundViewNewController.php
| use Exception; | |
| use Globals; | |
| use Session; | |
| /** | |
| * 환불 완료 리스트 페이지 | |
| throw new AlertCloseException(__('처리 할 주문상품이 없습니다.')); | |
| } | |
| // 해외상점의 경우 무조건 전체 반품/교환/환불처리하도록 함 | |
| if ($getData['mallSno'] > DEFAULT_MALL_NUMBER && $handleSno !== null) { | |
| throw new AlertCloseException(__('해외상점 취소/교환/반품/환불은 전체 처리만 가능합니다.')); | |
변경 후RefundViewNewController.php
| use Exception; | |
| use Globals; | |
| use Session; | |
| use Origin\Service\Privacy\Masking\ColumnMaskingService; | |
| use Origin\Service\Privacy\Masking\MaskingTargetService; | |
| /** | |
| * 환불 완료 리스트 페이지 | |
| throw new AlertCloseException(__('처리 할 주문상품이 없습니다.')); | |
| } | |
| // 개인정보 마스킹(환불 계좌정보): 은행·계좌번호·예금주 → '-' | |
| $this->setData('isRefundMaskTarget', \App::getInstance(MaskingTargetService::class) | |
| ->isMaskTargetOrderNo($getValue['orderNo'])); | |
| // 환불계좌는 은행·계좌번호·예금주가 한 칸에 모이므로 뷰가 칸 전체를 이 값 하나로 대체한다 | |
| $this->setData('maskChar', ColumnMaskingService::DEFAULT_MASK); | |
| // 해외상점의 경우 무조건 전체 반품/교환/환불처리하도록 함 | |
| if ($getData['mallSno'] > DEFAULT_MALL_NUMBER && $handleSno !== null) { | |
| throw new AlertCloseException(__('해외상점 취소/교환/반품/환불은 전체 처리만 가능합니다.')); | |
변경 전RegularOrderListController.php
| namespace Bundle\Controller\Admin\Order; | |
| use Origin\Enum\RegularDelivery\RegularOrder\RegularOrderStatus; | |
| use Request; | |
| class RegularOrderListController extends \Origin\Controller\Admin\Controller | |
| // 검색 값으로 조회 | |
| // 신청서 정보 | |
| $regularOrderList = $regularOrderAdminList->getRegularOrderList($getValue, $orderGridConfigList); | |
| $this->setData('regularOrderList', $regularOrderList['list']); | |
| $totalRegularOrderCount = $regularOrderAdminList->getTotalCountRegularOrderList($getValue, $orderGridConfigList); | |
| // 페이지 설정 | |
변경 후RegularOrderListController.php
| namespace Bundle\Controller\Admin\Order; | |
| use Origin\Enum\RegularDelivery\RegularOrder\RegularOrderStatus; | |
| use Origin\Service\Privacy\Masking\RegularOrderListMaskingService; | |
| use Request; | |
| class RegularOrderListController extends \Origin\Controller\Admin\Controller | |
| // 검색 값으로 조회 | |
| // 신청서 정보 | |
| $regularOrderList = $regularOrderAdminList->getRegularOrderList($getValue, $orderGridConfigList); | |
| // 개인정보 마스킹(정기결제 신청 리스트): 신청자명·신청자 휴대폰·ID·수령자명→'-' | |
| $maskedRegularOrderList = \App::getInstance(RegularOrderListMaskingService::class)->maskRegularOrderList($regularOrderList['list']); | |
| $this->setData('regularOrderList', $maskedRegularOrderList); | |
| $totalRegularOrderCount = $regularOrderAdminList->getTotalCountRegularOrderList($getValue, $orderGridConfigList); | |
| // 페이지 설정 | |
변경 전RegularOrderViewController.php
| use Bundle\Controller\Admin\Controller; | |
| use Component\Member\Manager; | |
| use Origin\Enum\RegularDelivery\RegularOrder\RegularOrderStatus; | |
| class RegularOrderViewController extends Controller | |
| { | |
| // 정기결제 신청서 신청자 및 수령자 정보 | |
| $regularOrderShippingInfo = $regularOrderAdminDetail->getRegularOrderShippingInfo($applyNo); | |
| $this->setData('applierInfo', $regularOrderShippingInfo['applierInfo']); | |
| $this->setData('shippingInfo', $regularOrderShippingInfo['shippingInfo']); | |
| // 정기결제 신청서 상담 및 관리자 메모 정보 | |
| $consultMemo = $regularOrderAdminDetail->getRegularOrderConsultMemo($applyNo); | |
변경 후RegularOrderViewController.php
| use Bundle\Controller\Admin\Controller; | |
| use Component\Member\Manager; | |
| use Origin\Enum\RegularDelivery\RegularOrder\RegularOrderStatus; | |
| use Origin\Service\Privacy\Masking\ColumnMaskingService; | |
| use Origin\Service\Privacy\Masking\MaskingTargetService; | |
| use Origin\Service\Privacy\Masking\RegularOrderDetailMaskingService; | |
| use Origin\Service\Privacy\Withdrawn\WithdrawnOrderSeparatorService; | |
| class RegularOrderViewController extends Controller | |
| { | |
| // 정기결제 신청서 신청자 및 수령자 정보 | |
| $regularOrderShippingInfo = $regularOrderAdminDetail->getRegularOrderShippingInfo($applyNo); | |
| // 개인정보 마스킹(정기결제 상세): 신청자 연락처/구매자IP·수령자명/연락처/주소→'-' | |
| // 표시 키를 그대로 덮으므로 뷰가 튜닝돼 있어도 적용되고, 기능에 필요한 값만 분리 원본 키로 남는다 | |
| $applierInfo = is_array($regularOrderShippingInfo['applierInfo']) ? $regularOrderShippingInfo['applierInfo'] : []; | |
| $shippingInfo = is_array($regularOrderShippingInfo['shippingInfo']) ? $regularOrderShippingInfo['shippingInfo'] : []; | |
| $regularOrderDetailMasking = \App::getInstance(RegularOrderDetailMaskingService::class); | |
| // 마스킹 여부는 분리보관 여부로 판정한다. 회원 테이블(es_memberHackout·sleepFl) 기준은 복원 근거와 축이 달라, | |
| // 분리는 끝났는데 회원 행만 사라지면 복원된 원본이 마스킹 없이 노출된다 | |
| $applierMemberType = \App::getInstance(WithdrawnOrderSeparatorService::class) | |
| ->resolveRegularApplierMemberType((string) ($applierInfo['applyGroupNo'] ?? '')); | |
| $applierMaskLabel = \App::getInstance(MaskingTargetService::class) | |
| ->resolveMaskLabelBySeparationStatus($applierMemberType?->value); | |
| if ($applierMaskLabel !== null) { // 탈퇴/휴면 회원 신청서 | |
| $applierInfo = $regularOrderDetailMasking->maskApplierInfo($applierInfo); | |
| $shippingInfo = $regularOrderDetailMasking->maskShippingInfo($shippingInfo); | |
| // 카드번호는 표시 전용이라(폼·파라미터 미사용) 원본을 남기지 않고 덮는다 | |
| $this->setData('cardNo', ColumnMaskingService::DEFAULT_MASK); | |
| } | |
| $this->setData('applierInfo', $applierInfo); | |
| $this->setData('shippingInfo', $shippingInfo); | |
| // 신청자명(1A): 탈퇴/휴면이면 회원 유형 라벨로 표시(뷰: applierMaskLabel ?: 기존식). 일반 회원=null. | |
| $this->setData('applierMaskLabel', $applierMaskLabel); | |
| // 배송지처럼 구성요소가 한 칸에 모이는 항목은 뷰가 칸 전체를 이 값 하나로 대체한다 | |
| $this->setData('maskChar', ColumnMaskingService::DEFAULT_MASK); | |
| // 정기결제 신청서 상담 및 관리자 메모 정보 | |
| $consultMemo = $regularOrderAdminDetail->getRegularOrderConsultMemo($applyNo); | |
변경 전TaxInvoiceListController.php
| namespace Bundle\Controller\Admin\Order; | |
| use Exception; | |
| use Request; | |
| class TaxInvoiceListController extends \Controller\Admin\Controller | |
| } | |
| // --- 관리자 디자인 템플릿 | |
| $this->setData('data', $getData['data']); | |
| $this->setData('taxStats', $getData['taxStats']); | |
| $this->setData('search', $getData['search']); | |
| $this->setData('searchKindASelectBox', \Component\Member\Member::getSearchKindASelectBox()); | |
변경 후TaxInvoiceListController.php
| namespace Bundle\Controller\Admin\Order; | |
| use Exception; | |
| use Origin\Service\Privacy\Masking\TaxInvoiceListMaskingService; | |
| use Request; | |
| class TaxInvoiceListController extends \Controller\Admin\Controller | |
| } | |
| // --- 관리자 디자인 템플릿 | |
| $this->setData('data', \App::getInstance(TaxInvoiceListMaskingService::class)->maskIssuedList($getData['data'])); | |
| $this->setData('taxStats', $getData['taxStats']); | |
| $this->setData('search', $getData['search']); | |
| $this->setData('searchKindASelectBox', \Component\Member\Member::getSearchKindASelectBox()); | |
변경 전TaxInvoiceRequestController.php
| <?php | |
| /** | |
| * This is commercial software, only users who have purchased a valid license | |
| * and accept to the terms of the License Agreement can install and use this | |
| * program. | |
| * | |
| * Do not edit or add to this file if you wish to upgrade Godomall5 to newer | |
| * versions in the future. | |
| * | |
| * @copyright ⓒ 2016, NHN godo: Corp. | |
| * @link http://www.godo.co.kr | |
| */ | |
| namespace Bundle\Controller\Admin\Order; | |
| use Exception; | |
| use Request; | |
| /** | |
| * 세금계산서 요청 페이지 | |
| * [관리자 모드] 세금계산서 신청 리스트 페이지 | |
| * | |
| * @author artherot | |
| * @version 1.0 | |
| * @since 1.0 | |
| * @copyright ⓒ 2016, NHN godo: Corp. | |
| */ | |
| class TaxInvoiceRequestController extends \Controller\Admin\Controller | |
| { | |
| /** | |
| * {@inheritdoc} | |
| * | |
| * @author Jong-tae Ahn <qnibus@godo.co.kr> | |
| */ | |
| public function index() | |
| { | |
| // --- 메뉴 설정 | |
| $this->callMenu('order', 'taxInvoice', 'request'); | |
| // --- 모듈 호출 | |
| $tax = \App::load('\\Component\\Order\\Tax'); | |
| $order = \App::load('\\Component\\Order\\OrderAdmin'); | |
| // --- 세금계산서 데이터 | |
| try { | |
| $searchDateFl = gd_isset(Request::get()->get('searchDateFl'), 'regDt'); | |
| Request::get()->set('searchDateFl',$searchDateFl); | |
| Request::get()->set('statusFl','r'); | |
| $getData = $tax->getListTaxInvoice(); | |
| $page = \App::load('\\Component\\Page\\Page'); // 페이지 재설정 | |
| // 세금계산서 사용여부 | |
| $taxInfo = $tax->getTaxConf(); | |
| } catch (Exception $e) { | |
| } | |
| // --- 관리자 디자인 템플릿 | |
| $this->setData('data', $getData['data']); | |
| $this->setData('search', $getData['search']); | |
| $this->setData('searchKindASelectBox', \Component\Member\Member::getSearchKindASelectBox()); | |
| $this->setData('sort', $getData['sort']); | |
| $this->setData('checked', $checked = $getData['checked']); | |
| $this->setData('page', $page); | |
| $this->setData('taxInfo', $taxInfo); | |
| $this->setData('tax', $tax); | |
| $this->setData('statusSearchableRange', $order->getOrderStatusAdmin()); | |
| } | |
| } | |
변경 후TaxInvoiceRequestController.php
| <?php | |
| /** | |
| * This is commercial software, only users who have purchased a valid license | |
| * and accept to the terms of the License Agreement can install and use this | |
| * program. | |
| * | |
| * Do not edit or add to this file if you wish to upgrade Godomall5 to newer | |
| * versions in the future. | |
| * | |
| * @copyright ⓒ 2016, NHN godo: Corp. | |
| * @link http://www.godo.co.kr | |
| */ | |
| namespace Bundle\Controller\Admin\Order; | |
| use Exception; | |
| use Origin\Service\Privacy\Masking\TaxInvoiceListMaskingService; | |
| use Request; | |
| /** | |
| * 세금계산서 요청 페이지 | |
| * [관리자 모드] 세금계산서 신청 리스트 페이지 | |
| * | |
| * @author artherot | |
| * @version 1.0 | |
| * @since 1.0 | |
| * @copyright ⓒ 2016, NHN godo: Corp. | |
| */ | |
| class TaxInvoiceRequestController extends \Controller\Admin\Controller | |
| { | |
| /** | |
| * {@inheritdoc} | |
| * | |
| * @author Jong-tae Ahn <qnibus@godo.co.kr> | |
| */ | |
| public function index() | |
| { | |
| // --- 메뉴 설정 | |
| $this->callMenu('order', 'taxInvoice', 'request'); | |
| // --- 모듈 호출 | |
| $tax = \App::load('\\Component\\Order\\Tax'); | |
| $order = \App::load('\\Component\\Order\\OrderAdmin'); | |
| // --- 세금계산서 데이터 | |
| try { | |
| $searchDateFl = gd_isset(Request::get()->get('searchDateFl'), 'regDt'); | |
| Request::get()->set('searchDateFl',$searchDateFl); | |
| Request::get()->set('statusFl','r'); | |
| $getData = $tax->getListTaxInvoice(); | |
| $page = \App::load('\\Component\\Page\\Page'); // 페이지 재설정 | |
| // 세금계산서 사용여부 | |
| $taxInfo = $tax->getTaxConf(); | |
| } catch (Exception $e) { | |
| } | |
| // --- 관리자 디자인 템플릿 | |
| $this->setData('data', \App::getInstance(TaxInvoiceListMaskingService::class)->maskRequestList($getData['data'])); | |
| $this->setData('search', $getData['search']); | |
| $this->setData('searchKindASelectBox', \Component\Member\Member::getSearchKindASelectBox()); | |
| $this->setData('sort', $getData['sort']); | |
| $this->setData('checked', $checked = $getData['checked']); | |
| $this->setData('page', $page); | |
| $this->setData('taxInfo', $taxInfo); | |
| $this->setData('tax', $tax); | |
| $this->setData('statusSearchableRange', $order->getOrderStatusAdmin()); | |
| } | |
| } | |
변경 전CouponManageController.php
| use Exception; | |
| use Framework\Debug\Exception\LayerException; | |
| use Origin\Service\Coupon\UpdateCouponService; | |
| use Request; | |
| class CouponManageController extends \Controller\Admin\Controller | |
| $this->setData('getData', gd_isset($getData)); | |
| $this->setData('getConvertData', gd_isset($getConvertData)); | |
| $this->setData('getGroupData', gd_isset($getGroupData)); | |
| $this->setData('getMemberData', gd_isset($getMemberData['data'])); | |
| $this->setData('getMemberBarcode', gd_isset($getMemberData['barcode'])); | |
| $this->setData('search', gd_isset($getMemberData['search'])); | |
| $this->setData('searchKindASelectBox', \Component\Member\Member::getSearchKindASelectBox()); | |
변경 후CouponManageController.php
| use Exception; | |
| use Framework\Debug\Exception\LayerException; | |
| use Origin\Service\Coupon\UpdateCouponService; | |
| use Origin\Service\Privacy\Masking\CouponListMaskingService; | |
| use Request; | |
| class CouponManageController extends \Controller\Admin\Controller | |
| $this->setData('getData', gd_isset($getData)); | |
| $this->setData('getConvertData', gd_isset($getConvertData)); | |
| $this->setData('getGroupData', gd_isset($getGroupData)); | |
| $this->setData('getMemberData', \App::getInstance(CouponListMaskingService::class) | |
| ->maskCouponList((array) gd_isset($getMemberData['data']))); | |
| $this->setData('getMemberBarcode', gd_isset($getMemberData['barcode'])); | |
| $this->setData('search', gd_isset($getMemberData['search'])); | |
| $this->setData('searchKindASelectBox', \Component\Member\Member::getSearchKindASelectBox()); | |
변경 전CouponOfflineManageController.php
| use Exception; | |
| use Framework\Debug\Exception\LayerException; | |
| use Origin\Service\Coupon\UpdateCouponService; | |
| use Request; | |
| class CouponOfflineManageController extends \Controller\Admin\Controller | |
| $this->setData('getData', gd_isset($getData)); | |
| $this->setData('getConvertData', gd_isset($getConvertData)); | |
| $this->setData('getGroupData', gd_isset($getGroupData)); | |
| $this->setData('getMemberData', gd_isset($getMemberData['data'])); | |
| $this->setData('search', gd_isset($getMemberData['search'])); | |
| $this->setData('page', $page); | |
| } | |
변경 후CouponOfflineManageController.php
| use Exception; | |
| use Framework\Debug\Exception\LayerException; | |
| use Origin\Service\Coupon\UpdateCouponService; | |
| use Origin\Service\Privacy\Masking\CouponListMaskingService; | |
| use Request; | |
| class CouponOfflineManageController extends \Controller\Admin\Controller | |
| $this->setData('getData', gd_isset($getData)); | |
| $this->setData('getConvertData', gd_isset($getConvertData)); | |
| $this->setData('getGroupData', gd_isset($getGroupData)); | |
| $this->setData('getMemberData', \App::getInstance(CouponListMaskingService::class) | |
| ->maskCouponList((array) gd_isset($getMemberData['data']))); | |
| $this->setData('search', gd_isset($getMemberData['search'])); | |
| $this->setData('page', $page); | |
| } | |
변경 전OrderListWithdrawnMemberController.php
변경 후OrderListWithdrawnMemberController.php
| <?php | |
| /** | |
| * This is commercial software, only users who have purchased a valid license | |
| * and accept to the terms of the License Agreement can install and use this | |
| * program. | |
| * | |
| * Do not edit or add to this file if you wish to upgrade Godomall5 to newer | |
| * versions in the future. | |
| * | |
| * @copyright ⓒ 2016, NHN godo: Corp. | |
| * @link http://www.godo.co.kr | |
| */ | |
| namespace Bundle\Controller\Admin\Provider\Order; | |
| use Component\Member\Manager; | |
| /** | |
| * 휴면/탈퇴 회원 주문 리스트 | |
| * | |
| * @package Bundle\Controller\Admin\Provider\Order | |
| */ | |
| class OrderListWithdrawnMemberController extends \Controller\Admin\Order\OrderListWithdrawnMemberController | |
| { | |
| /** | |
| * {@inheritdoc} | |
| */ | |
| public function index() | |
| { | |
| // 공급사 정보 설정 | |
| $isProvider = Manager::isProvider(); | |
| $this->setData('isProvider', $isProvider); | |
| parent::index(); | |
| } | |
| } | |
변경 전LayerComebackCouponResultController.php
| use Component\Sms\Sms; | |
| use Exception; | |
| /** | |
| * 컴백쿠폰 SMS발송 결과 레이어 페이지 | |
| $this->setData('mode', gd_isset($getValue['mode'], 'search')); | |
| $this->setData('disabled', gd_isset($getValue['disabled'], '')); | |
| $this->setData('callFunc', gd_isset($getValue['callFunc'], '')); | |
| $this->setData('data', gd_isset($aComebackCouponMemberList['data'])); | |
| $this->setData('getValue', gd_isset($getValue)); | |
| $this->setData('title', gd_isset($getData['title'])); | |
| $this->setData('couponName', gd_isset($getCouponData['couponNm'])); | |
변경 후LayerComebackCouponResultController.php
| use Component\Sms\Sms; | |
| use Exception; | |
| use Origin\Service\Privacy\Masking\CouponListMaskingService; | |
| /** | |
| * 컴백쿠폰 SMS발송 결과 레이어 페이지 | |
| $this->setData('mode', gd_isset($getValue['mode'], 'search')); | |
| $this->setData('disabled', gd_isset($getValue['disabled'], '')); | |
| $this->setData('callFunc', gd_isset($getValue['callFunc'], '')); | |
| $this->setData('data', \App::getInstance(CouponListMaskingService::class) | |
| ->maskCouponList((array) gd_isset($aComebackCouponMemberList['data']))); | |
| $this->setData('getValue', gd_isset($getValue)); | |
| $this->setData('title', gd_isset($getData['title'])); | |
| $this->setData('couponName', gd_isset($getCouponData['couponNm'])); | |
변경 전LayerHandleReasonController.php
| use Component\Order\OrderAdmin; | |
| use Component\Member\Manager; | |
| /** | |
| * @author <kookoo135@godo.co.kr> | |
| $this->setData('handleMode', $getValue['handleMode']); | |
| $this->setData('goodsNm', $getValue['goodsNm']); | |
| $this->setData('data', $data); | |
| $this->getView()->setDefine('layout', 'layout_layer.php'); | |
| } | |
| } | |
변경 후LayerHandleReasonController.php
| use Component\Order\OrderAdmin; | |
| use Component\Member\Manager; | |
| use Origin\Service\Privacy\Masking\ColumnMaskingService; | |
| use Origin\Service\Privacy\Masking\MaskingTargetService; | |
| /** | |
| * @author <kookoo135@godo.co.kr> | |
| $this->setData('handleMode', $getValue['handleMode']); | |
| $this->setData('goodsNm', $getValue['goodsNm']); | |
| $this->setData('data', $data); | |
| // 개인정보 마스킹(고객 반품/환불신청 메모): 환불계좌(은행·계좌번호·예금주)→'-' | |
| $this->setData('isRefundMaskTarget', \App::getInstance(MaskingTargetService::class) | |
| ->isMaskTargetOrderNo($getValue['orderNo'])); | |
| // 환불계좌는 은행·계좌번호·예금주가 한 칸에 모이므로 뷰가 칸 전체를 이 값 하나로 대체한다 | |
| $this->setData('maskChar', ColumnMaskingService::DEFAULT_MASK); | |
| $this->getView()->setDefine('layout', 'layout_layer.php'); | |
| } | |
| } | |
변경 전SetNaverpayController.php
| use Component\Present\Order\PresentOrder; | |
| use Framework\Security\XXTEA; | |
| use Framework\Utility\StringUtils; | |
| use Origin\Service\Statistics\Acecounter\Order\AcecounterOrderReportService; | |
| use Origin\Service\Statistics\Analytics\Order\OrderCompleteAnalyticsCollectorService; | |
| use Origin\Enum\Statistics\Analytics\Order\ClaimType; | |
| } | |
| //주문자 & 수령자 정보 저장 | |
| $this->updateOrderInfo(); | |
| //주문정보 저장 | |
| $this->updateOrder(); | |
| return $result; | |
| } | |
| protected function updateOrderInfo() | |
| { | |
| //배송지 정보 저장 | |
| $saveOrderInfoData['orderName'] = $this->naverOrderData['OrdererName'];//주문자명 | |
| $saveOrderInfoData['receiverCellPhone'] = $this->naverOrderGoodsData['ShippingAddressTel1'];//핸드폰 | |
| $saveOrderInfoData['orderMemo'] = $this->naverOrderGoodsData['ShippingMemo'];//주문시 남기는 글 | |
| //주소정보 저장 | |
| $compareField = gd_array_keys($saveOrderInfoData); | |
| $arrBind = $this->db->get_binding(DBTableField::tableOrderInfo(), $saveOrderInfoData, 'update', $compareField); | |
변경 후SetNaverpayController.php
| use Component\Present\Order\PresentOrder; | |
| use Framework\Security\XXTEA; | |
| use Framework\Utility\StringUtils; | |
| use Origin\Service\Privacy\Withdrawn\WithdrawnOrderSeparatorService; | |
| use Origin\Service\Statistics\Acecounter\Order\AcecounterOrderReportService; | |
| use Origin\Service\Statistics\Analytics\Order\OrderCompleteAnalyticsCollectorService; | |
| use Origin\Enum\Statistics\Analytics\Order\ClaimType; | |
| } | |
| //주문자 & 수령자 정보 저장 | |
| $this->updateOrderInfo($getOrderData['separationStatus'] ?? null); | |
| //주문정보 저장 | |
| $this->updateOrder(); | |
| return $result; | |
| } | |
| protected function updateOrderInfo($separationStatus = null) | |
| { | |
| //배송지 정보 저장 | |
| $saveOrderInfoData['orderName'] = $this->naverOrderData['OrdererName'];//주문자명 | |
| $saveOrderInfoData['receiverCellPhone'] = $this->naverOrderGoodsData['ShippingAddressTel1'];//핸드폰 | |
| $saveOrderInfoData['orderMemo'] = $this->naverOrderGoodsData['ShippingMemo'];//주문시 남기는 글 | |
| // 분리보관 주문은 개인정보를 원본에 되돌리면 분리가 무효화되고 재분리 경로가 없다. | |
| // 분리보관에 암호화해 반영하고 원본에는 나머지 값만 기록한다. | |
| $saveOrderInfoData = \App::getInstance(WithdrawnOrderSeparatorService::class) | |
| ->separateOrderInfo((string) $this->orderNo, $saveOrderInfoData, $separationStatus); | |
| if (empty($saveOrderInfoData)) { | |
| return; | |
| } | |
| //주소정보 저장 | |
| $compareField = gd_array_keys($saveOrderInfoData); | |
| $arrBind = $this->db->get_binding(DBTableField::tableOrderInfo(), $saveOrderInfoData, 'update', $compareField); | |
변경 전SyncController.php
| use Component\Present\Order\PresentOrder; | |
| use Framework\Security\XXTEA; | |
| use Framework\Utility\StringUtils; | |
| use Origin\Service\Statistics\Acecounter\Order\AcecounterOrderReportService; | |
| use Origin\Service\Statistics\Analytics\Order\OrderCompleteAnalyticsCollectorService; | |
| use Origin\Enum\Statistics\Analytics\Order\ClaimType; | |
| } | |
| //주문자 & 수령자 정보 저장 | |
| $this->updateOrderInfo(); | |
| //주문정보 저장 | |
| $this->updateOrder(); | |
| return $result; | |
| } | |
| protected function updateOrderInfo() | |
| { | |
| //배송지 정보 저장 | |
| $saveOrderInfoData['orderName'] = $this->naverOrderData['OrdererName'];//주문자명 | |
| $saveOrderInfoData['receiverCellPhone'] = $this->naverOrderGoodsData['ShippingAddressTel1'];//핸드폰 | |
| $saveOrderInfoData['orderMemo'] = $this->naverOrderGoodsData['ShippingMemo'];//주문시 남기는 글 | |
| //주소정보 저장 | |
| $compareField = gd_array_keys($saveOrderInfoData); | |
| $arrBind = $this->db->get_binding(DBTableField::tableOrderInfo(), $saveOrderInfoData, 'update', $compareField); | |
변경 후SyncController.php
| use Component\Present\Order\PresentOrder; | |
| use Framework\Security\XXTEA; | |
| use Framework\Utility\StringUtils; | |
| use Origin\Service\Privacy\Withdrawn\WithdrawnOrderSeparatorService; | |
| use Origin\Service\Statistics\Acecounter\Order\AcecounterOrderReportService; | |
| use Origin\Service\Statistics\Analytics\Order\OrderCompleteAnalyticsCollectorService; | |
| use Origin\Enum\Statistics\Analytics\Order\ClaimType; | |
| } | |
| //주문자 & 수령자 정보 저장 | |
| $this->updateOrderInfo($getOrderData['separationStatus'] ?? null); | |
| //주문정보 저장 | |
| $this->updateOrder(); | |
| return $result; | |
| } | |
| protected function updateOrderInfo($separationStatus = null) | |
| { | |
| //배송지 정보 저장 | |
| $saveOrderInfoData['orderName'] = $this->naverOrderData['OrdererName'];//주문자명 | |
| $saveOrderInfoData['receiverCellPhone'] = $this->naverOrderGoodsData['ShippingAddressTel1'];//핸드폰 | |
| $saveOrderInfoData['orderMemo'] = $this->naverOrderGoodsData['ShippingMemo'];//주문시 남기는 글 | |
| // 분리보관 주문은 개인정보를 원본에 되돌리면 분리가 무효화되고 재분리 경로가 없다. | |
| // 분리보관에 암호화해 반영하고 원본에는 나머지 값만 기록한다. | |
| $saveOrderInfoData = \App::getInstance(WithdrawnOrderSeparatorService::class) | |
| ->separateOrderInfo((string) $this->orderNo, $saveOrderInfoData, $separationStatus); | |
| if (empty($saveOrderInfoData)) { | |
| return; | |
| } | |
| //주소정보 저장 | |
| $compareField = gd_array_keys($saveOrderInfoData); | |
| $arrBind = $this->db->get_binding(DBTableField::tableOrderInfo(), $saveOrderInfoData, 'update', $compareField); | |
변경 전AutoOrderCancelJob.php
| use Framework\Command\JobScheduler\AbstractJob; | |
| use App; | |
| /** | |
| * 관리자 메인 접속시 처리하던 로직으로 | |
| */ | |
| protected function execute() | |
| { | |
| $this->_setDefinePath(); | |
| /** @var \Bundle\Component\Order\OrderAdmin $order */ | |
변경 후AutoOrderCancelJob.php
| use Framework\Command\JobScheduler\AbstractJob; | |
| use App; | |
| use Origin\Service\Privacy\Withdrawn\WithdrawnJobRunningFlagService; | |
| /** | |
| * 관리자 메인 접속시 처리하던 로직으로 | |
| */ | |
| protected function execute() | |
| { | |
| // 분리보관 이관이 이 Job 실행 중에는 비켜 가도록 실행 표시를 남긴다(이관 종료 후 제거) | |
| (new WithdrawnJobRunningFlagService())->markRunningUntilExit(WithdrawnJobRunningFlagService::JOB_KEY_AUTO_CANCEL); | |
| $this->_setDefinePath(); | |
| /** @var \Bundle\Component\Order\OrderAdmin $order */ | |
변경 전AutoOrderStatusDeliveryJob.php
| use Framework\Command\JobScheduler\AbstractJob; | |
| use Component\Worker\AutomaticDeliveryComplete; | |
| use Core\Base\Controller\DefineTrait; | |
| /** | |
| * 관리자 메인 접속시 처리하던 로직으로 | |
| */ | |
| protected function execute() | |
| { | |
| // PG 관련 경로 설정 | |
| $this->_setDefinePath(); | |
변경 후AutoOrderStatusDeliveryJob.php
| use Framework\Command\JobScheduler\AbstractJob; | |
| use Component\Worker\AutomaticDeliveryComplete; | |
| use Core\Base\Controller\DefineTrait; | |
| use Origin\Service\Privacy\Withdrawn\WithdrawnJobRunningFlagService; | |
| /** | |
| * 관리자 메인 접속시 처리하던 로직으로 | |
| */ | |
| protected function execute() | |
| { | |
| // 분리보관 이관이 이 Job 실행 중에는 비켜 가도록 실행 표시를 남긴다(이관 종료 후 제거) | |
| (new WithdrawnJobRunningFlagService())->markRunningUntilExit(WithdrawnJobRunningFlagService::JOB_KEY_AUTO_DELIVERY); | |
| // PG 관련 경로 설정 | |
| $this->_setDefinePath(); | |
변경 전AutoOrderStatusJob.php
| use Component\Worker\AutomaticPurchaseConfirm; | |
| use Origin\Service\Worker\AutomaticPurchaseConfirmService; | |
| use Core\Base\Controller\DefineTrait; | |
| /** | |
| * 관리자 메인 접속시 처리하던 로직으로 | |
| */ | |
| protected function execute() | |
| { | |
| // PG 관련 경로 설정 | |
| $this->_setDefinePath(); | |
변경 후AutoOrderStatusJob.php
| use Component\Worker\AutomaticPurchaseConfirm; | |
| use Origin\Service\Worker\AutomaticPurchaseConfirmService; | |
| use Core\Base\Controller\DefineTrait; | |
| use Origin\Service\Privacy\Withdrawn\WithdrawnJobRunningFlagService; | |
| /** | |
| * 관리자 메인 접속시 처리하던 로직으로 | |
| */ | |
| protected function execute() | |
| { | |
| // 분리보관 이관이 이 Job 실행 중에는 비켜 가도록 실행 표시를 남긴다(이관 종료 후 제거) | |
| (new WithdrawnJobRunningFlagService())->markRunningUntilExit(WithdrawnJobRunningFlagService::JOB_KEY_AUTO_CONFIRM); | |
| // PG 관련 경로 설정 | |
| $this->_setDefinePath(); | |
변경 전LapseOrderDeleteJob.php
| use Framework\Command\JobScheduler\AbstractJob; | |
| use Component\Order\OrderDelete; | |
| use Exception; | |
| /** | |
| * 5년 경과 주문 삭제 스케줄러 | |
| */ | |
| protected function execute() | |
| { | |
| $logger = \App::getInstance('logger')->channel('orderDelete'); | |
| try { | |
변경 후LapseOrderDeleteJob.php
| use Framework\Command\JobScheduler\AbstractJob; | |
| use Component\Order\OrderDelete; | |
| use Exception; | |
| use Origin\Service\Privacy\Withdrawn\WithdrawnJobRunningFlagService; | |
| /** | |
| * 5년 경과 주문 삭제 스케줄러 | |
| */ | |
| protected function execute() | |
| { | |
| // 분리보관 이관이 이 Job 실행 중에는 비켜 가도록 실행 표시를 남긴다(이관 종료 후 제거) | |
| (new WithdrawnJobRunningFlagService())->markRunningUntilExit(WithdrawnJobRunningFlagService::JOB_KEY_LAPSE); | |
| $logger = \App::getInstance('logger')->channel('orderDelete'); | |
| try { | |
변경 전MemberHackoutOrderJob.php
| use Framework\Application\Bootstrap\Log; | |
| use Framework\Command\JobScheduler\AbstractJob; | |
| use Framework\Utility\ArrayUtils; | |
| use Exception; | |
| /** | |
| * 탈퇴회원 주문내역 분리 | |
| */ | |
| protected function execute() | |
| { | |
| $logger = \App::getInstance('logger')->channel(Log::CHANNEL_SCHEDULER); | |
| $logger->info(sprintf('Execute job name is %s.', __CLASS__)); | |
| try { | |
| /** @var \Bundle\Component\Member\HackOut\HackOutService $hackOutService */ | |
| $hackOutService = \App::load('Component\\Member\\HackOut\\HackOutService'); | |
| /** @var \Bundle\Component\Order\OrderAdmin $order */ | |
| $order = \App::load('\\Component\\Order\\OrderAdmin'); | |
| //전일자 탈퇴회원 조회 | |
| $newWithdrawnMembersList = $hackOutService->_getWithdrawnMembersAtYesterday(); | |
| if (gd_count($newWithdrawnMembersList) > 0) { | |
| $arrMemNo = ArrayUtils::getSubArrayByKey($newWithdrawnMembersList, 'memNo'); | |
| } else { | |
| $arrMemNo = []; | |
| } | |
| if (gd_count($arrMemNo) > 0) { | |
| $maxJobCount = 100; | |
| $splitArrayMemNo = array_chunk($arrMemNo, $maxJobCount); | |
| $memberOrderInfo = []; | |
| foreach ($splitArrayMemNo as $memNoArr) { | |
| $WithdrawnMembersOrderData = $order->getWithdrawnMembersOrderView($memNoArr); | |
| // 탈퇴회원의 주문내역 이동처리 | |
| foreach ($WithdrawnMembersOrderData['personalInfo'] as $personalData) { | |
| $hackOutService->_moveWithdrawnMembersOrderData($personalData); | |
| $memberOrderInfo[$personalData['memNo']] = $personalData['orderNo']; | |
| $logger->info(sprintf('Moving order history of withdrawal member : memNo [%s], orderNo [%s]', $personalData['memNo'], $personalData['orderNo'])); | |
| } | |
| // 환불내역이 있는 경우 탈퇴회원의 계좌정보 이동처리 | |
| if ($WithdrawnMembersOrderData['refundInfo']) { | |
| foreach ($WithdrawnMembersOrderData['refundInfo'] as $refundData) { | |
| $hackOutService->_moveWithdrawnMembersRefundAccountData($refundData); // 이동처리 | |
| $logger->info(sprintf('Moving refund details for withdrawal members : memNo [%s], orderNo [%s]', gd_array_search($refundData['orderNo'], $memberOrderInfo), $refundData['orderNo'])); | |
| } | |
| } | |
| } | |
| unset($newWithdrawnMembersList, $arrMemNo, $splitArrayMemNo, $WithdrawnMembersOrderData); | |
| } | |
| $logger->info(__CLASS__ . ', end'); | |
| return true; | |
| } catch (Exception $e) { | |
변경 후MemberHackoutOrderJob.php
| use Framework\Application\Bootstrap\Log; | |
| use Framework\Command\JobScheduler\AbstractJob; | |
| use Origin\Enum\Privacy\Withdrawn\WithdrawnMemberType; | |
| use Origin\Service\Privacy\Withdrawn\WithdrawnMemberOrderSeparatorService; | |
| use Exception; | |
| use Origin\Service\Privacy\Withdrawn\WithdrawnJobRunningFlagService; | |
| /** | |
| * 탈퇴회원 주문내역 분리 | |
| */ | |
| protected function execute() | |
| { | |
| // 분리보관 이관이 이 Job 실행 중에는 비켜 가도록 실행 표시를 남긴다(이관 종료 후 제거) | |
| (new WithdrawnJobRunningFlagService())->markRunningUntilExit(WithdrawnJobRunningFlagService::JOB_KEY_HACKOUT_ORDER); | |
| $logger = \App::getInstance('logger')->channel(Log::CHANNEL_SCHEDULER); | |
| $logger->info(sprintf('Execute job name is %s.', __CLASS__)); | |
| try { | |
| /** @var \Bundle\Component\Member\HackOut\HackOutService $hackOutService */ | |
| $hackOutService = \App::load('Component\\Member\\HackOut\\HackOutService'); | |
| $separator = \App::getInstance(WithdrawnMemberOrderSeparatorService::class); | |
| // 전일자 탈퇴회원 조회 → 회원별 주문 PII 분리 | |
| $newWithdrawnMembersList = $hackOutService->_getWithdrawnMembersAtYesterday(); | |
| foreach ((array) $newWithdrawnMembersList as $member) { | |
| $memNo = (int) $member['memNo']; | |
| $separator->separate($memNo, WithdrawnMemberType::HACKOUT); | |
| $logger->info(sprintf('Separating order PII of withdrawal member : memNo [%s]', $memNo)); | |
| } | |
| $logger->info(__CLASS__ . ', end'); | |
| return true; | |
| } catch (Exception $e) { | |
변경 전MemberSleepJob.php
| use Component\Member\Sleep\SleepService; | |
| use Framework\Application\Bootstrap\Log; | |
| use Framework\Command\JobScheduler\AbstractJob; | |
| /** | |
| * Class MemberSleepJob | |
| */ | |
| protected function execute() | |
| { | |
| $logger = \App::getInstance('logger')->channel(Log::CHANNEL_SCHEDULER); | |
| $logger->info(sprintf('Execute job name is %s.', __CLASS__)); | |
| try { | |
변경 후MemberSleepJob.php
| use Component\Member\Sleep\SleepService; | |
| use Framework\Application\Bootstrap\Log; | |
| use Framework\Command\JobScheduler\AbstractJob; | |
| use Origin\Service\Privacy\Withdrawn\WithdrawnJobRunningFlagService; | |
| /** | |
| * Class MemberSleepJob | |
| */ | |
| protected function execute() | |
| { | |
| // 분리보관 이관이 이 Job 실행 중에는 비켜 가도록 실행 표시를 남긴다(이관 종료 후 제거) | |
| (new WithdrawnJobRunningFlagService())->markRunningUntilExit(WithdrawnJobRunningFlagService::JOB_KEY_SLEEP); | |
| $logger = \App::getInstance('logger')->channel(Log::CHANNEL_SCHEDULER); | |
| $logger->info(sprintf('Execute job name is %s.', __CLASS__)); | |
| try { | |
변경 전MemberSleepOrderJob.php
변경 후MemberSleepOrderJob.php
| <?php | |
| /** | |
| * This is commercial software, only users who have purchased a valid license | |
| * and accept to the terms of the License Agreement can install and use this | |
| * program. | |
| * | |
| * Do not edit or add to this file if you wish to upgrade Godomall to newer | |
| * versions in the future. | |
| * | |
| * @copyright ⓒ 2026, NHN COMMERCE Corp. | |
| * @link https://www.nhn-commerce.com/ | |
| */ | |
| namespace Bundle\Job; | |
| use Framework\Application\Bootstrap\Log; | |
| use Framework\Command\JobScheduler\AbstractJob; | |
| use Origin\Enum\Privacy\Withdrawn\WithdrawnMemberType; | |
| use Origin\Service\Privacy\Withdrawn\WithdrawnMemberOrderSeparatorService; | |
| use Exception; | |
| use Origin\Service\Privacy\Withdrawn\WithdrawnJobRunningFlagService; | |
| /** | |
| * 휴면회원 주문내역 분리(전일 전환분 D+1 보정) | |
| * 전환 즉시 분리에서 누락된 건을 하루 뒤 보정한다. | |
| * | |
| * @usage setCronSchedule 설정 사용 | |
| * - - - - - - | |
| * | | | | | | | |
| * | | | | | + year [optional] | |
| * | | | | +----- day of week (0 - 7) (Sunday=0 or 7) | |
| * | | | +---------- month (1 - 12) | |
| * | | +--------------- day of month (1 - 31) | |
| * | +-------------------- hour (0 - 23) | |
| * +------------------------- min (0 - 59) | |
| * | |
| * @package Godo_Job_Schedule | |
| */ | |
| class MemberSleepOrderJob extends AbstractJob | |
| { | |
| /** | |
| * Job 실행 전 처리 로직 | |
| * | |
| * @param object $config JobConfig 객체 | |
| */ | |
| protected function setup($config) | |
| { | |
| $config | |
| ->setCronSchedule('0 3 * * *') | |
| ->setName('member_sleep_order') | |
| ->setIgnoreUserAbort(true) | |
| ->setMaxExecuteTime(0) | |
| ->setMaxMemoryLimit('-1') | |
| ->setRangeExecuteTime(null) | |
| ->setDevelopment(true) | |
| ->setSendGms(false) | |
| ->setForceRun(false); | |
| } | |
| /** | |
| * Job 실행 | |
| * | |
| * @return boolean 실행 성공 여부 | |
| */ | |
| protected function execute() | |
| { | |
| // 분리보관 이관이 이 Job 실행 중에는 비켜 가도록 실행 표시를 남긴다(이관 종료 후 제거) | |
| (new WithdrawnJobRunningFlagService())->markRunningUntilExit(WithdrawnJobRunningFlagService::JOB_KEY_SLEEP_ORDER); | |
| $logger = \App::getInstance('logger')->channel(Log::CHANNEL_SCHEDULER); | |
| $logger->info(sprintf('Execute job name is %s.', __CLASS__)); | |
| try { | |
| /** @var \Bundle\Component\Member\Sleep\SleepService $sleepService */ | |
| $sleepService = \App::load('Component\\Member\\Sleep\\SleepService'); | |
| $separator = \App::getInstance(WithdrawnMemberOrderSeparatorService::class); | |
| $members = $sleepService->getSleepMembersAtYesterday(); | |
| foreach ((array) $members as $member) { | |
| $memNo = (int) $member['memNo']; | |
| $separator->separate($memNo, WithdrawnMemberType::SLEEP); | |
| $logger->info(sprintf('Separating order PII of sleep member : memNo [%s]', $memNo)); | |
| } | |
| $logger->info(__CLASS__ . ', end'); | |
| return true; | |
| } catch (Exception $e) { | |
| $logger->error(__METHOD__ . ', ' . $e->getFile() . '[' . $e->getLine() . '], ' . $e->getMessage(), $e->getTrace()); | |
| return false; | |
| } | |
| } | |
| /** | |
| * @param boolean $isSuccess | |
| */ | |
| protected function complete($isSuccess) | |
| { | |
| if ($isSuccess) { | |
| $this->logMessage('OK', __CLASS__ . ' job is success!'); | |
| } else { | |
| $this->logMessage('FAIL', __CLASS__ . 'this job is failure!'); | |
| } | |
| } | |
| /** | |
| * Shutdown 예외처리 | |
| * | |
| * @param string $code 시스템 다운 코드 | |
| * @param string $message 시스템 다운 메시지 | |
| */ | |
| protected function shutdown($code, $message) | |
| { | |
| switch ($code) { | |
| case self::SHUTDOWN_NOT_ENOUGH_MEMORY: | |
| break; | |
| case self::SHUTDOWN_CONNECTION_TIMEOUT: | |
| break; | |
| case self::SHUTDOWN_CONNECTION_ABORTED: | |
| break; | |
| case self::SHUTDOWN_CONNECTION_TIMEOUT_ABORTED: | |
| break; | |
| case self::SHUTDOWN_CONNECTION_UNKNOWN_ERROR: | |
| break; | |
| default: | |
| break; | |
| } | |
| } | |
| } | |
변경 전OrderGoodsRepository.php
| use Origin\Enum\Order\OrderChannel; | |
| use Origin\Enum\Order\OrderStatusCode; | |
| use Origin\Model\Order\OrderGoods; | |
| /** | |
| * 주문상품(es_orderGoods) 조회 | |
| if ($search->isLikeMatch()) { | |
| $query->where($column, 'LIKE', '%' . addcslashes($search->getKeyword(), '%_\\') . '%'); | |
| } else { | |
| $query->where($column, $search->getKeyword()); | |
| } | |
| } | |
| } | |
변경 후OrderGoodsRepository.php
| use Origin\Enum\Order\OrderChannel; | |
| use Origin\Enum\Order\OrderStatusCode; | |
| use Origin\Model\Order\OrderGoods; | |
| use Origin\Service\Privacy\Withdrawn\WithdrawnOrderSearchService; | |
| /** | |
| * 주문상품(es_orderGoods) 조회 | |
| if ($search->isLikeMatch()) { | |
| $query->where($column, 'LIKE', '%' . addcslashes($search->getKeyword(), '%_\\') . '%'); | |
| return; | |
| } | |
| // 분리보관된 주문은 원본 컬럼이 공백이라 평문 정확일치로 찾히지 않아, 암호문에서 찾은 주문번호를 함께 건다 | |
| $withdrawnOrderNos = \App::getInstance(WithdrawnOrderSearchService::class) | |
| ->findOrderNosByOrderSearchKey($column, $search->getKeyword()); | |
| if (empty($withdrawnOrderNos)) { | |
| $query->where($column, $search->getKeyword()); | |
| return; | |
| } | |
| $query->where(function (Builder $where) use ($column, $search, $withdrawnOrderNos) { | |
| $where->where($column, $search->getKeyword()) | |
| ->orWhereIn('og.orderNo', $withdrawnOrderNos); | |
| }); | |
| } | |
| } | |
변경 전RegularOrderApplierRepository.php
| 'es_regularOrderApplier.*', | |
| 'es_member.memId', | |
| 'es_member.memNo', | |
| 'es_member.smsFl', | |
| 'es_memberGroup.groupNm' | |
| ]) | |
변경 후RegularOrderApplierRepository.php
| 'es_regularOrderApplier.*', | |
| 'es_member.memId', | |
| 'es_member.memNo', | |
| // 탈퇴 시 es_member 행이 삭제되어 es_member.memNo 가 NULL 이 되므로, 탈퇴/휴면 마스킹 판정용 원본 회원번호를 별도 확보 | |
| 'es_regularOrder.memNo as rawMemNo', | |
| 'es_member.smsFl', | |
| 'es_memberGroup.groupNm' | |
| ]) | |
변경 전ContainerDefinitionsBundle.php
| $this->app[\Repository\RegularDelivery\RegularOrder\RegularOrderRepository::class], | |
| $this->app[\Repository\RegularDelivery\RegularOrder\RegularOrderGiftRepository::class], | |
| $this->app[\Repository\RegularDelivery\RegularOrder\RegularOrderAddGoodsRepository::class], | |
| $this->app['logger'] | |
| ); | |
| }, | |
| \Component\RegularDelivery\RegularOrderAdmin\RegularOrderAdminDetail::class => function () { | |
변경 후ContainerDefinitionsBundle.php
| $this->app[\Repository\RegularDelivery\RegularOrder\RegularOrderRepository::class], | |
| $this->app[\Repository\RegularDelivery\RegularOrder\RegularOrderGiftRepository::class], | |
| $this->app[\Repository\RegularDelivery\RegularOrder\RegularOrderAddGoodsRepository::class], | |
| $this->app['logger'], | |
| $this->app[\Origin\Service\Privacy\Masking\OrderExcelMaskingService::class] | |
| ); | |
| }, | |
| \Component\RegularDelivery\RegularOrderAdmin\RegularOrderAdminDetail::class => function () { | |
변경 전ContainerDefinitionsOrigin.php
| use Origin\Repository\Member\KakaoAlrim\KakaoAlrimCloudRepository; | |
| use Origin\Repository\Member\KakaoSync\KakaoSyncRepository; | |
| use Origin\Repository\Member\ManagerRepository; | |
| use Origin\Repository\Member\MemberHackOutRepository; | |
| use Origin\Repository\Member\MemberCouponRepository; | |
| use Origin\Repository\Member\MemberGroupRepository; | |
| use Origin\Service\Member\Group\MemberGroupCouponService; | |
| use Origin\Service\Member\Group\MemberGroupService; | |
| use Origin\Repository\Member\MemberRepository; | |
| use Origin\Repository\Base\LogLegalRequirementsRepository; | |
| use Origin\Repository\Order\OrderInfoRepository; | |
| use Origin\DAO\Statistics\Analytics\Order\AnalyticsOrderDAO; | |
| use Origin\Service\Script\GodomallSdk\GodomallSdkService; | |
| use Origin\Service\Script\ScriptService; | |
| use Origin\Service\Session\ManagerSessionService; | |
| use Origin\Service\Ssl\FreeSslService; | |
| use Origin\Service\Ssl\PaidSslService; | |
| use Origin\Service\Ssl\SslService; | |
| $this->app[AnalyticsOrderDAO::class], | |
| ); | |
| }, | |
| ChannelTypeService::class => function () { | |
| return new ChannelTypeService( | |
| $this->app['session'], | |
| OrderRepository::class => function () { | |
| return new OrderRepository($this->app['DB']); | |
| }, | |
| OrderGoodsRepository::class => function () { | |
| return new OrderGoodsRepository($this->app['DB']); | |
| }, | |
| return new StockLogRepository(); | |
| }, | |
| RegularOrderRepository::class => function () { | |
| return new RegularOrderRepository(); | |
| }, | |
| RegularOrderGoodsRepository::class => function () { | |
| return new RegularOrderGoodsRepository(); | |
| return new RegularOrderGoodsOptionRepository(); | |
| }, | |
| RegularOrderApplierRepository::class => function () { | |
| return new RegularOrderApplierRepository(); | |
| }, | |
| RegularOrderGiftRepository::class => function () { | |
| return new RegularOrderGiftRepository(); | |
| return new OrderDeliveryRepository(); | |
| }, | |
| OrderInfoRepository::class => function () { | |
| return new OrderInfoRepository(); | |
| }, | |
| AnalyticsOrderDAO::class => function () { | |
| return new AnalyticsOrderDAO($this->app['DB']); | |
변경 후ContainerDefinitionsOrigin.php
| use Origin\Repository\Member\KakaoAlrim\KakaoAlrimCloudRepository; | |
| use Origin\Repository\Member\KakaoSync\KakaoSyncRepository; | |
| use Origin\Repository\Member\ManagerRepository; | |
| use Origin\Repository\Member\MemberHackOutOrderRepository; | |
| use Origin\Repository\Member\MemberHackOutOrderCashReceiptOriginalRepository; | |
| use Origin\Repository\Member\MemberHackOutOrderExchangeHandleRepository; | |
| use Origin\Repository\Member\MemberHackOutOrderGoodsOriginalRepository; | |
| use Origin\Repository\Member\MemberHackOutOrderOriginalRepository; | |
| use Origin\Repository\Member\MemberHackOutOrderUserHandleRepository; | |
| use Origin\Repository\Member\MemberSleepOrderCashReceiptOriginalRepository; | |
| use Origin\Repository\Member\MemberSleepOrderExchangeHandleRepository; | |
| use Origin\Repository\Member\MemberSleepOrderGoodsOriginalRepository; | |
| use Origin\Repository\Member\MemberSleepOrderOriginalRepository; | |
| use Origin\Repository\Member\MemberSleepOrderUserHandleRepository; | |
| use Origin\Repository\Order\OrderCashReceiptOriginalRepository; | |
| use Origin\Repository\Order\OrderGoodsOriginalRepository; | |
| use Origin\Repository\Order\OrderHandleRepository; | |
| use Origin\Repository\Order\OrderOriginalRepository; | |
| use Origin\Repository\Order\OrderUserHandleRepository; | |
| use Origin\Repository\Order\PresentReceiverInfoRepository; | |
| use Origin\Repository\Member\MemberSleepOrderRepository; | |
| use Origin\Repository\Member\MemberHackOutOrderHandleRepository; | |
| use Origin\Repository\Member\MemberSleepOrderHandleRepository; | |
| use Origin\Repository\Member\MemberHackOutOrderCashReceiptRepository; | |
| use Origin\Repository\Member\MemberSleepOrderCashReceiptRepository; | |
| use Origin\Repository\Member\MemberHackOutOrderTaxRepository; | |
| use Origin\Repository\Member\MemberSleepOrderTaxRepository; | |
| use Origin\Repository\Member\MemberHackOutPresentReceiverInfoRepository; | |
| use Origin\Repository\Member\MemberSleepPresentReceiverInfoRepository; | |
| use Origin\Repository\Member\MemberHackOutRegularOrderApplierRepository; | |
| use Origin\Repository\Member\MemberSleepRegularOrderApplierRepository; | |
| use Origin\Repository\Member\MemberHackOutRepository; | |
| use Origin\Repository\Member\MemberCouponRepository; | |
| use Origin\Repository\Member\MemberGroupRepository; | |
| use Origin\Service\Member\Group\MemberGroupCouponService; | |
| use Origin\Service\Member\Group\MemberGroupService; | |
| use Origin\Repository\Member\MemberRepository; | |
| use Origin\Repository\Order\OrderCashReceiptRepository; | |
| use Origin\Repository\Order\OrderTaxRepository; | |
| use Origin\Service\Privacy\Withdrawn\WithdrawnMemberOrderSeparatorService; | |
| use Origin\Service\Privacy\Withdrawn\WithdrawnOrderHydratorService; | |
| use Origin\Service\Privacy\Withdrawn\WithdrawnOrderSearchService; | |
| use Origin\Service\Privacy\Withdrawn\WithdrawnOrderSeparatorService; | |
| use Origin\Service\Privacy\Withdrawn\WithdrawnOrderListService; | |
| use Origin\Service\Privacy\Withdrawn\WithdrawnOrderRestorerService; | |
| use Origin\Service\Privacy\Withdrawn\WithdrawnRefundAccountService; | |
| use Origin\Repository\Base\LogLegalRequirementsRepository; | |
| use Origin\Repository\Order\OrderInfoRepository; | |
| use Origin\DAO\Statistics\Analytics\Order\AnalyticsOrderDAO; | |
| use Origin\Service\Script\GodomallSdk\GodomallSdkService; | |
| use Origin\Service\Script\ScriptService; | |
| use Origin\Service\Session\ManagerSessionService; | |
| use Origin\Service\Privacy\Masking\CashReceiptListMaskingService; | |
| use Origin\Service\Privacy\Masking\CouponListMaskingService; | |
| use Origin\Service\Privacy\Masking\ColumnMaskingService; | |
| use Origin\Service\Privacy\Masking\MaskingTargetService; | |
| use Origin\Service\Privacy\Masking\OrderExcelMaskingService; | |
| use Origin\Service\Privacy\Masking\OrderListMaskingService; | |
| use Origin\Service\Privacy\Masking\OrderDetailMaskingService; | |
| use Origin\Service\Privacy\Masking\RegularOrderListMaskingService; | |
| use Origin\Service\Privacy\Masking\RegularOrderDetailMaskingService; | |
| use Origin\Service\Privacy\Masking\OrderPrintMaskingService; | |
| use Origin\Service\Privacy\Masking\TaxInvoiceListMaskingService; | |
| use Origin\Service\Ssl\FreeSslService; | |
| use Origin\Service\Ssl\PaidSslService; | |
| use Origin\Service\Ssl\SslService; | |
| $this->app[AnalyticsOrderDAO::class], | |
| ); | |
| }, | |
| ColumnMaskingService::class => function () { | |
| return new ColumnMaskingService(); | |
| }, | |
| WithdrawnOrderHydratorService::class => function () { | |
| return new WithdrawnOrderHydratorService( | |
| $this->app[MemberHackOutOrderRepository::class], | |
| $this->app[MemberSleepOrderRepository::class], | |
| $this->app[MemberHackOutOrderHandleRepository::class], | |
| $this->app[MemberSleepOrderHandleRepository::class], | |
| $this->app[MemberHackOutOrderCashReceiptRepository::class], | |
| $this->app[MemberSleepOrderCashReceiptRepository::class], | |
| $this->app[MemberHackOutOrderTaxRepository::class], | |
| $this->app[MemberSleepOrderTaxRepository::class], | |
| $this->app[MemberHackOutPresentReceiverInfoRepository::class], | |
| $this->app[MemberSleepPresentReceiverInfoRepository::class], | |
| $this->app[MemberHackOutRegularOrderApplierRepository::class], | |
| $this->app[MemberSleepRegularOrderApplierRepository::class] | |
| ); | |
| }, | |
| WithdrawnOrderSearchService::class => function () { | |
| return new WithdrawnOrderSearchService( | |
| $this->app[OrderCashReceiptRepository::class], | |
| $this->app[OrderTaxRepository::class], | |
| $this->app[MemberHackOutOrderRepository::class], | |
| $this->app[MemberSleepOrderRepository::class], | |
| $this->app[MemberHackOutOrderCashReceiptRepository::class], | |
| $this->app[MemberSleepOrderCashReceiptRepository::class], | |
| $this->app[MemberHackOutOrderTaxRepository::class], | |
| $this->app[MemberSleepOrderTaxRepository::class] | |
| ); | |
| }, | |
| WithdrawnOrderSeparatorService::class => function () { | |
| return new WithdrawnOrderSeparatorService( | |
| $this->app['DB'], | |
| $this->app[OrderRepository::class], | |
| $this->app[OrderCashReceiptRepository::class], | |
| $this->app[MemberHackOutOrderCashReceiptRepository::class], | |
| $this->app[MemberSleepOrderCashReceiptRepository::class], | |
| $this->app[MemberHackOutOrderRepository::class], | |
| $this->app[MemberSleepOrderRepository::class], | |
| $this->app[OrderTaxRepository::class], | |
| $this->app[MemberHackOutOrderTaxRepository::class], | |
| $this->app[MemberSleepOrderTaxRepository::class], | |
| $this->app[RegularOrderApplierRepository::class], | |
| $this->app[MemberHackOutRegularOrderApplierRepository::class], | |
| $this->app[MemberSleepRegularOrderApplierRepository::class] | |
| ); | |
| }, | |
| WithdrawnMemberOrderSeparatorService::class => function () { | |
| return new WithdrawnMemberOrderSeparatorService($this->app['DB']); | |
| }, | |
| WithdrawnOrderRestorerService::class => function () { | |
| return new WithdrawnOrderRestorerService($this->app['DB']); | |
| }, | |
| WithdrawnOrderListService::class => function () { | |
| return new WithdrawnOrderListService( | |
| $this->app[OrderRepository::class], | |
| $this->app[WithdrawnOrderHydratorService::class], | |
| $this->app[WithdrawnOrderSearchService::class] | |
| ); | |
| }, | |
| WithdrawnRefundAccountService::class => function () { | |
| return new WithdrawnRefundAccountService( | |
| $this->app[WithdrawnOrderSeparatorService::class], | |
| $this->app[WithdrawnOrderHydratorService::class] | |
| ); | |
| }, | |
| MaskingTargetService::class => function () { | |
| return new MaskingTargetService( | |
| $this->app[OrderRepository::class], | |
| $this->app[MemberRepository::class], | |
| $this->app[MemberHackOutRepository::class], | |
| $this->app[MemberHackOutRegularOrderApplierRepository::class], | |
| $this->app[MemberSleepRegularOrderApplierRepository::class] | |
| ); | |
| }, | |
| OrderExcelMaskingService::class => function () { | |
| return new OrderExcelMaskingService( | |
| $this->app[ColumnMaskingService::class], | |
| $this->app[MaskingTargetService::class] | |
| ); | |
| }, | |
| OrderListMaskingService::class => function () { | |
| return new OrderListMaskingService( | |
| $this->app[ColumnMaskingService::class], | |
| $this->app[MaskingTargetService::class] | |
| ); | |
| }, | |
| TaxInvoiceListMaskingService::class => function () { | |
| return new TaxInvoiceListMaskingService( | |
| $this->app[ColumnMaskingService::class], | |
| $this->app[MaskingTargetService::class] | |
| ); | |
| }, | |
| CashReceiptListMaskingService::class => function () { | |
| return new CashReceiptListMaskingService( | |
| $this->app[ColumnMaskingService::class], | |
| $this->app[MaskingTargetService::class] | |
| ); | |
| }, | |
| CouponListMaskingService::class => function () { | |
| return new CouponListMaskingService( | |
| $this->app[ColumnMaskingService::class], | |
| $this->app[MaskingTargetService::class] | |
| ); | |
| }, | |
| OrderDetailMaskingService::class => function () { | |
| return new OrderDetailMaskingService($this->app[ColumnMaskingService::class]); | |
| }, | |
| RegularOrderListMaskingService::class => function () { | |
| return new RegularOrderListMaskingService( | |
| $this->app[ColumnMaskingService::class], | |
| $this->app[MaskingTargetService::class] | |
| ); | |
| }, | |
| RegularOrderDetailMaskingService::class => function () { | |
| return new RegularOrderDetailMaskingService($this->app[ColumnMaskingService::class]); | |
| }, | |
| OrderPrintMaskingService::class => function () { | |
| return new OrderPrintMaskingService($this->app[ColumnMaskingService::class]); | |
| }, | |
| ChannelTypeService::class => function () { | |
| return new ChannelTypeService( | |
| $this->app['session'], | |
| OrderRepository::class => function () { | |
| return new OrderRepository($this->app['DB']); | |
| }, | |
| MemberHackOutOrderRepository::class => function () { | |
| return new MemberHackOutOrderRepository($this->app['DB']); | |
| }, | |
| MemberSleepOrderRepository::class => function () { | |
| return new MemberSleepOrderRepository($this->app['DB']); | |
| }, | |
| MemberHackOutOrderHandleRepository::class => function () { | |
| return new MemberHackOutOrderHandleRepository($this->app['DB']); | |
| }, | |
| MemberSleepOrderHandleRepository::class => function () { | |
| return new MemberSleepOrderHandleRepository($this->app['DB']); | |
| }, | |
| MemberHackOutOrderCashReceiptRepository::class => function () { | |
| return new MemberHackOutOrderCashReceiptRepository($this->app['DB']); | |
| }, | |
| MemberSleepOrderCashReceiptRepository::class => function () { | |
| return new MemberSleepOrderCashReceiptRepository($this->app['DB']); | |
| }, | |
| MemberHackOutOrderTaxRepository::class => function () { | |
| return new MemberHackOutOrderTaxRepository($this->app['DB']); | |
| }, | |
| MemberSleepOrderTaxRepository::class => function () { | |
| return new MemberSleepOrderTaxRepository($this->app['DB']); | |
| }, | |
| MemberHackOutPresentReceiverInfoRepository::class => function () { | |
| return new MemberHackOutPresentReceiverInfoRepository($this->app['DB']); | |
| }, | |
| MemberSleepPresentReceiverInfoRepository::class => function () { | |
| return new MemberSleepPresentReceiverInfoRepository($this->app['DB']); | |
| }, | |
| MemberHackOutRegularOrderApplierRepository::class => function () { | |
| return new MemberHackOutRegularOrderApplierRepository($this->app['DB'], $this->app['logger']); | |
| }, | |
| MemberSleepRegularOrderApplierRepository::class => function () { | |
| return new MemberSleepRegularOrderApplierRepository($this->app['DB'], $this->app['logger']); | |
| }, | |
| MemberHackOutOrderOriginalRepository::class => function () { | |
| return new MemberHackOutOrderOriginalRepository($this->app['DB']); | |
| }, | |
| MemberSleepOrderOriginalRepository::class => function () { | |
| return new MemberSleepOrderOriginalRepository($this->app['DB']); | |
| }, | |
| MemberHackOutOrderGoodsOriginalRepository::class => function () { | |
| return new MemberHackOutOrderGoodsOriginalRepository($this->app['DB']); | |
| }, | |
| MemberSleepOrderGoodsOriginalRepository::class => function () { | |
| return new MemberSleepOrderGoodsOriginalRepository($this->app['DB']); | |
| }, | |
| MemberHackOutOrderUserHandleRepository::class => function () { | |
| return new MemberHackOutOrderUserHandleRepository($this->app['DB']); | |
| }, | |
| MemberSleepOrderUserHandleRepository::class => function () { | |
| return new MemberSleepOrderUserHandleRepository($this->app['DB']); | |
| }, | |
| MemberHackOutOrderExchangeHandleRepository::class => function () { | |
| return new MemberHackOutOrderExchangeHandleRepository($this->app['DB']); | |
| }, | |
| MemberSleepOrderExchangeHandleRepository::class => function () { | |
| return new MemberSleepOrderExchangeHandleRepository($this->app['DB']); | |
| }, | |
| MemberHackOutOrderCashReceiptOriginalRepository::class => function () { | |
| return new MemberHackOutOrderCashReceiptOriginalRepository($this->app['DB']); | |
| }, | |
| MemberSleepOrderCashReceiptOriginalRepository::class => function () { | |
| return new MemberSleepOrderCashReceiptOriginalRepository($this->app['DB']); | |
| }, | |
| OrderHandleRepository::class => function () { | |
| return new OrderHandleRepository($this->app['DB']); | |
| }, | |
| OrderOriginalRepository::class => function () { | |
| return new OrderOriginalRepository($this->app['DB']); | |
| }, | |
| OrderGoodsOriginalRepository::class => function () { | |
| return new OrderGoodsOriginalRepository($this->app['DB']); | |
| }, | |
| OrderUserHandleRepository::class => function () { | |
| return new OrderUserHandleRepository($this->app['DB']); | |
| }, | |
| OrderCashReceiptOriginalRepository::class => function () { | |
| return new OrderCashReceiptOriginalRepository($this->app['DB']); | |
| }, | |
| PresentReceiverInfoRepository::class => function () { | |
| return new PresentReceiverInfoRepository($this->app['DB']); | |
| }, | |
| OrderCashReceiptRepository::class => function () { | |
| return new OrderCashReceiptRepository($this->app['DB']); | |
| }, | |
| OrderTaxRepository::class => function () { | |
| return new OrderTaxRepository($this->app['DB']); | |
| }, | |
| OrderGoodsRepository::class => function () { | |
| return new OrderGoodsRepository($this->app['DB']); | |
| }, | |
| return new StockLogRepository(); | |
| }, | |
| RegularOrderRepository::class => function () { | |
| return new RegularOrderRepository($this->app['DB']); | |
| }, | |
| RegularOrderGoodsRepository::class => function () { | |
| return new RegularOrderGoodsRepository(); | |
| return new RegularOrderGoodsOptionRepository(); | |
| }, | |
| RegularOrderApplierRepository::class => function () { | |
| return new RegularOrderApplierRepository($this->app['DB']); | |
| }, | |
| RegularOrderGiftRepository::class => function () { | |
| return new RegularOrderGiftRepository(); | |
| return new OrderDeliveryRepository(); | |
| }, | |
| OrderInfoRepository::class => function () { | |
| return new OrderInfoRepository($this->app['DB']); | |
| }, | |
| AnalyticsOrderDAO::class => function () { | |
| return new AnalyticsOrderDAO($this->app['DB']); | |