diff --git a/src/main/java/com/interplug/qcast/batch/JobLauncherController.java b/src/main/java/com/interplug/qcast/batch/JobLauncherController.java index 6783f14e..0e97a73f 100644 --- a/src/main/java/com/interplug/qcast/batch/JobLauncherController.java +++ b/src/main/java/com/interplug/qcast/batch/JobLauncherController.java @@ -2,6 +2,7 @@ package com.interplug.qcast.batch; import java.util.Date; import java.util.Map; +import lombok.RequiredArgsConstructor; import org.springframework.batch.core.Job; import org.springframework.batch.core.JobParameters; import org.springframework.batch.core.JobParametersBuilder; @@ -15,7 +16,6 @@ import org.springframework.scheduling.annotation.Scheduled; import org.springframework.web.bind.annotation.GetMapping; import org.springframework.web.bind.annotation.PathVariable; import org.springframework.web.bind.annotation.RestController; -import lombok.RequiredArgsConstructor; @RestController @RequiredArgsConstructor @@ -38,16 +38,22 @@ public class JobLauncherController { * @throws JobRestartException */ @GetMapping("/batch/job/{jobName}") // Path Variable로 jobName을 받음 - public String launchJob(@PathVariable String jobName) throws JobInstanceAlreadyCompleteException, - JobExecutionAlreadyRunningException, JobParametersInvalidException, JobRestartException { + public String launchJob(@PathVariable String jobName) + throws JobInstanceAlreadyCompleteException, + JobExecutionAlreadyRunningException, + JobParametersInvalidException, + JobRestartException { Job job = jobs.get(jobName); if (job == null) { return "Job " + jobName + " not found"; } - JobParameters jobParameters = new JobParametersBuilder().addString("jobName", jobName) - .addDate("time", new Date()).toJobParameters(); + JobParameters jobParameters = + new JobParametersBuilder() + .addString("jobName", jobName) + .addDate("time", new Date()) + .toJobParameters(); jobLauncher.run(job, jobParameters); @@ -65,8 +71,11 @@ public class JobLauncherController { */ // @Scheduled(cron = "*/5 * * * * *") @Scheduled(cron = "0 55 23 * * *") - public String storeAdditionalInfoJob() throws JobInstanceAlreadyCompleteException, - JobExecutionAlreadyRunningException, JobParametersInvalidException, JobRestartException { + public String storeAdditionalInfoJob() + throws JobInstanceAlreadyCompleteException, + JobExecutionAlreadyRunningException, + JobParametersInvalidException, + JobRestartException { String jobName = "storeAdditionalJob"; Job job = jobs.get(jobName); @@ -92,8 +101,11 @@ public class JobLauncherController { * @throws JobRestartException */ @Scheduled(cron = "0 30 02 * * *") - public String materialJob() throws JobInstanceAlreadyCompleteException, - JobExecutionAlreadyRunningException, JobParametersInvalidException, JobRestartException { + public String materialJob() + throws JobInstanceAlreadyCompleteException, + JobExecutionAlreadyRunningException, + JobParametersInvalidException, + JobRestartException { String jobName = "materialJob"; Job job = jobs.get(jobName); @@ -120,8 +132,11 @@ public class JobLauncherController { * @throws JobRestartException */ @Scheduled(cron = "0 40 02 * * *") - public String bomJob() throws JobInstanceAlreadyCompleteException, - JobExecutionAlreadyRunningException, JobParametersInvalidException, JobRestartException { + public String bomJob() + throws JobInstanceAlreadyCompleteException, + JobExecutionAlreadyRunningException, + JobParametersInvalidException, + JobRestartException { String jobName = "bomJob"; Job job = jobs.get(jobName); @@ -149,8 +164,11 @@ public class JobLauncherController { * @throws JobRestartException */ @Scheduled(cron = "0 40 03 * * *") - public String businessChargerJob() throws JobInstanceAlreadyCompleteException, - JobExecutionAlreadyRunningException, JobParametersInvalidException, JobRestartException { + public String businessChargerJob() + throws JobInstanceAlreadyCompleteException, + JobExecutionAlreadyRunningException, + JobParametersInvalidException, + JobRestartException { String jobName = "businessChargerJob"; Job job = jobs.get(jobName); @@ -178,8 +196,11 @@ public class JobLauncherController { * @throws JobRestartException */ @Scheduled(cron = "0 0 01 * * *") - public String adminUserJob() throws JobInstanceAlreadyCompleteException, - JobExecutionAlreadyRunningException, JobParametersInvalidException, JobRestartException { + public String adminUserJob() + throws JobInstanceAlreadyCompleteException, + JobExecutionAlreadyRunningException, + JobParametersInvalidException, + JobRestartException { String jobName = "adminUserJob"; Job job = jobs.get(jobName); @@ -207,8 +228,11 @@ public class JobLauncherController { * @throws JobRestartException */ @Scheduled(cron = "0 0 0 * * *") - public String priceJob() throws JobInstanceAlreadyCompleteException, - JobExecutionAlreadyRunningException, JobParametersInvalidException, JobRestartException { + public String priceJob() + throws JobInstanceAlreadyCompleteException, + JobExecutionAlreadyRunningException, + JobParametersInvalidException, + JobRestartException { String jobName = "priceJob"; Job job = jobs.get(jobName); @@ -236,8 +260,11 @@ public class JobLauncherController { * @throws JobRestartException */ @Scheduled(cron = "0 10 03 * * *") - public String commonCodeJob() throws JobInstanceAlreadyCompleteException, - JobExecutionAlreadyRunningException, JobParametersInvalidException, JobRestartException { + public String commonCodeJob() + throws JobInstanceAlreadyCompleteException, + JobExecutionAlreadyRunningException, + JobParametersInvalidException, + JobRestartException { String jobName = "commonCodeJob"; Job job = jobs.get(jobName); @@ -264,8 +291,11 @@ public class JobLauncherController { * @throws JobRestartException */ @Scheduled(cron = "0 30 23 * * *") - public String specialNoteDispItemAdditionalInfoJob() throws JobInstanceAlreadyCompleteException, - JobExecutionAlreadyRunningException, JobParametersInvalidException, JobRestartException { + public String specialNoteDispItemAdditionalInfoJob() + throws JobInstanceAlreadyCompleteException, + JobExecutionAlreadyRunningException, + JobParametersInvalidException, + JobRestartException { String jobName = "specialNoteDispItemAdditionalJob"; Job job = jobs.get(jobName); if (job == null) { @@ -282,4 +312,67 @@ public class JobLauncherController { return "OK"; } + /** + * Plan Confrim 동기화 배치 + * + * @return + * @throws JobInstanceAlreadyCompleteException + * @throws JobExecutionAlreadyRunningException + * @throws JobParametersInvalidException + * @throws JobRestartException + */ + @Scheduled(cron = "1 0 0 * * *") + public String planConfirmJob() + throws JobInstanceAlreadyCompleteException, + JobExecutionAlreadyRunningException, + JobParametersInvalidException, + JobRestartException { + + String jobName = "planConfirmJob"; + Job job = jobs.get(jobName); + if (job == null) { + return "Job " + jobName + " not found"; + } + + if ("Y".equals(System.getProperty("spring.profiles.scheduler"))) { + JobParameters jobParameters = + new JobParametersBuilder().addDate("time", new Date()).toJobParameters(); + + jobLauncher.run(job, jobParameters); + } + + return "OK"; + } + + /** + * 견적서 전송 동기화 배치 + * + * @return + * @throws JobInstanceAlreadyCompleteException + * @throws JobExecutionAlreadyRunningException + * @throws JobParametersInvalidException + * @throws JobRestartException + */ + @Scheduled(cron = "1 20 0 * * *") + public String estimateSyncJob() + throws JobInstanceAlreadyCompleteException, + JobExecutionAlreadyRunningException, + JobParametersInvalidException, + JobRestartException { + + String jobName = "estimateSyncJob"; + Job job = jobs.get(jobName); + if (job == null) { + return "Job " + jobName + " not found"; + } + + if ("Y".equals(System.getProperty("spring.profiles.scheduler"))) { + JobParameters jobParameters = + new JobParametersBuilder().addDate("time", new Date()).toJobParameters(); + + jobLauncher.run(job, jobParameters); + } + + return "OK"; + } } diff --git a/src/main/java/com/interplug/qcast/batch/estimate/EstimateSyncConfiguration.java b/src/main/java/com/interplug/qcast/batch/estimate/EstimateSyncConfiguration.java new file mode 100644 index 00000000..e6a340c6 --- /dev/null +++ b/src/main/java/com/interplug/qcast/batch/estimate/EstimateSyncConfiguration.java @@ -0,0 +1,83 @@ +package com.interplug.qcast.batch.estimate; + +import com.interplug.qcast.biz.estimate.EstimateService; +import com.interplug.qcast.biz.estimate.dto.EstimateSyncResponse; +import com.interplug.qcast.biz.estimate.dto.PlanSyncResponse; +import com.interplug.qcast.util.InterfaceQsp; +import java.util.Collections; +import java.util.List; +import org.springframework.batch.core.Job; +import org.springframework.batch.core.JobExecutionListener; +import org.springframework.batch.core.Step; +import org.springframework.batch.core.configuration.annotation.StepScope; +import org.springframework.batch.core.job.builder.JobBuilder; +import org.springframework.batch.core.repository.JobRepository; +import org.springframework.batch.core.step.builder.StepBuilder; +import org.springframework.batch.item.ItemProcessor; +import org.springframework.batch.item.ItemWriter; +import org.springframework.batch.item.support.ListItemReader; +import org.springframework.beans.factory.annotation.Value; +import org.springframework.context.annotation.Bean; +import org.springframework.context.annotation.Configuration; +import org.springframework.http.HttpMethod; +import org.springframework.transaction.PlatformTransactionManager; + +/** Plan 확정 Item 마스터 동기화 배치 */ +@Configuration +public class EstimateSyncConfiguration implements JobExecutionListener { + private final EstimateService estimateService; + + private final InterfaceQsp interfaceQsp; + + EstimateSyncResponse estimateSyncResponse; + + @Value("${qsp.estimate-sync-batch-url}") + private String qspInterfaceUrl; + + public EstimateSyncConfiguration(EstimateService estimateService, InterfaceQsp interfaceQsp) { + this.estimateService = estimateService; + this.interfaceQsp = interfaceQsp; + } + + @Bean + public Job estimateSyncJob(JobRepository jobRepository, Step estimateSyncStep) { + return new JobBuilder("estimateSyncJob", jobRepository).start(estimateSyncStep).build(); + } + + @Bean + public Step estimateSyncStep( + JobRepository jobRepository, PlatformTransactionManager transactionManager) throws Exception { + return new StepBuilder("estimateSyncStep", jobRepository) + .chunk(100, transactionManager) + .reader(estimateSyncReader()) + .processor(estimateSyncProcessor()) + .writer(estimateSyncWriter()) + .build(); + } + + @Bean + @StepScope + public ListItemReader estimateSyncReader() throws Exception { + this.estimateSyncResponse = + interfaceQsp.callApiData( + HttpMethod.POST, + qspInterfaceUrl, + estimateService.selectEstimateSyncFailList(), + EstimateSyncResponse.class); + return (estimateSyncResponse != null) + ? new ListItemReader<>(estimateSyncResponse.getSuccessList()) + : new ListItemReader<>(Collections.emptyList()); + } + + @Bean + public ItemProcessor estimateSyncProcessor() { + return item -> item; + } + + @Bean + public ItemWriter estimateSyncWriter() { + return items -> { + estimateService.setEstimateSyncSave((List) items.getItems()); + }; + } +} diff --git a/src/main/java/com/interplug/qcast/batch/estimate/PlanConfrimConfiguration.java b/src/main/java/com/interplug/qcast/batch/estimate/PlanConfrimConfiguration.java new file mode 100644 index 00000000..36afa1fb --- /dev/null +++ b/src/main/java/com/interplug/qcast/batch/estimate/PlanConfrimConfiguration.java @@ -0,0 +1,80 @@ +package com.interplug.qcast.batch.estimate; + +import com.fasterxml.jackson.core.type.TypeReference; +import com.interplug.qcast.biz.estimate.EstimateService; +import com.interplug.qcast.biz.estimate.dto.PlanSyncResponse; +import com.interplug.qcast.util.InterfaceQsp; +import java.util.Collections; +import java.util.List; +import org.springframework.batch.core.Job; +import org.springframework.batch.core.JobExecutionListener; +import org.springframework.batch.core.Step; +import org.springframework.batch.core.configuration.annotation.StepScope; +import org.springframework.batch.core.job.builder.JobBuilder; +import org.springframework.batch.core.repository.JobRepository; +import org.springframework.batch.core.step.builder.StepBuilder; +import org.springframework.batch.item.ItemProcessor; +import org.springframework.batch.item.ItemWriter; +import org.springframework.batch.item.support.ListItemReader; +import org.springframework.beans.factory.annotation.Value; +import org.springframework.context.annotation.Bean; +import org.springframework.context.annotation.Configuration; +import org.springframework.http.HttpMethod; +import org.springframework.transaction.PlatformTransactionManager; + +/** Plan 확정 Item 마스터 동기화 배치 */ +@Configuration +public class PlanConfrimConfiguration implements JobExecutionListener { + private final EstimateService estimateService; + + private final InterfaceQsp interfaceQsp; + + List planSyncList; + + @Value("${qsp.estimate-plan-confirm-batch-url}") + private String qspInterfaceUrl; + + public PlanConfrimConfiguration(EstimateService estimateService, InterfaceQsp interfaceQsp) { + this.estimateService = estimateService; + this.interfaceQsp = interfaceQsp; + } + + @Bean + public Job planConfirmJob(JobRepository jobRepository, Step planConfirmStep) { + return new JobBuilder("planConfirmJob", jobRepository).start(planConfirmStep).build(); + } + + @Bean + public Step planConfirmStep( + JobRepository jobRepository, PlatformTransactionManager transactionManager) throws Exception { + return new StepBuilder("planConfirmStep", jobRepository) + .chunk(100, transactionManager) + .reader(planConfirmReader()) + .processor(planConfirmProcessor()) + .writer(planConfirmWriter()) + .build(); + } + + @Bean + @StepScope + public ListItemReader planConfirmReader() throws Exception { + this.planSyncList = + interfaceQsp.callApiData( + HttpMethod.GET, qspInterfaceUrl, null, new TypeReference>() {}); + return (planSyncList != null) + ? new ListItemReader<>(planSyncList) + : new ListItemReader<>(Collections.emptyList()); + } + + @Bean + public ItemProcessor planConfirmProcessor() { + return item -> item; + } + + @Bean + public ItemWriter planConfirmWriter() { + return items -> { + estimateService.setPlanConfirmSyncSave((List) items.getItems()); + }; + } +} diff --git a/src/main/java/com/interplug/qcast/biz/displayItem/dto/ItemSyncResponse.java b/src/main/java/com/interplug/qcast/biz/displayItem/dto/ItemSyncResponse.java index df702636..14589ee4 100644 --- a/src/main/java/com/interplug/qcast/biz/displayItem/dto/ItemSyncResponse.java +++ b/src/main/java/com/interplug/qcast/biz/displayItem/dto/ItemSyncResponse.java @@ -136,6 +136,18 @@ public class ItemSyncResponse extends DefaultResponse { @Schema(description = "PKG Material Flg") String pkgMaterialFlg; + @Schema(description = "Temp Loss") + String tempLoss; + + @Schema(description = "Temperature Coefficient") + String tempCoeff; + + @Schema(description = "AMP") + String amp; + + @Schema(description = "Conversion Efficiency") + String cnvEff; + @Schema(description = "Status Code(A, D)") String statCd; diff --git a/src/main/java/com/interplug/qcast/biz/estimate/EstimateController.java b/src/main/java/com/interplug/qcast/biz/estimate/EstimateController.java index 4552609b..6e6dd1ea 100644 --- a/src/main/java/com/interplug/qcast/biz/estimate/EstimateController.java +++ b/src/main/java/com/interplug/qcast/biz/estimate/EstimateController.java @@ -34,6 +34,13 @@ public class EstimateController { return estimateService.selectItemPriceList(priceRequest); } + @Operation(description = "견적서 특이사항 타이틀 목록을 조회한다.") + @GetMapping("/special-note-title-list") + @ResponseStatus(HttpStatus.OK) + public List selectSpecialNoteTitleList(NoteRequest noteRequest) throws Exception { + return estimateService.selectSpecialNoteTitleList(noteRequest); + } + @Operation(description = "견적서 특이사항 목록을 조회한다.") @GetMapping("/special-note-list") @ResponseStatus(HttpStatus.OK) @@ -59,9 +66,9 @@ public class EstimateController { @Operation(description = "견적서를 복사한다.") @PostMapping("/save-estimate-copy") @ResponseStatus(HttpStatus.CREATED) - public EstimateResponse insertEstimateCopy(@RequestBody EstimateRequest estimateRequest) + public EstimateResponse insertEstimateCopy(@RequestBody EstimateCopyRequest estimateCopyRequest) throws Exception { - return estimateService.insertEstimateCopy(estimateRequest); + return estimateService.insertEstimateCopy(estimateCopyRequest); } @Operation(description = "견적서를 엑셀로 다운로드한다.") diff --git a/src/main/java/com/interplug/qcast/biz/estimate/EstimateMapper.java b/src/main/java/com/interplug/qcast/biz/estimate/EstimateMapper.java index 5bce0c41..18591801 100644 --- a/src/main/java/com/interplug/qcast/biz/estimate/EstimateMapper.java +++ b/src/main/java/com/interplug/qcast/biz/estimate/EstimateMapper.java @@ -15,6 +15,9 @@ public interface EstimateMapper { // 견적서 API 상세 확인 public EstimateSendResponse selectEstimateApiDetail(EstimateRequest estimateRequest); + // 견적서 API 실패 목록 조회 + public List selectEstimateApiFailList(); + // 견적서 아이템 목록 조회 public List selectEstimateItemList(EstimateRequest estimateRequest); @@ -30,12 +33,18 @@ public interface EstimateMapper { // 견적서 지붕재 목록 조회 public List selectEstimateRoofList(EstimateRequest estimateRequest); + // 견적서 지붕재 아이템 목록 조회 + public List selectEstimateRoofItemList(EstimateRequest estimateRequest); + // 견적서 지붕재 PC 목록 조회 public List selectEstimateRoofPcList(EstimateRequest estimateRequest); // 견적서 지붕재 용량 목록 조회 public List selectEstimateRoofVolList(EstimateRequest estimateRequest); + // 견적서 특이사항 타이틀 목록 조회 + public List selectEstimateNoteTitleList(NoteRequest noteRequest); + // 견적서 특이사항 목록 조회 public List selectEstimateNoteList(NoteRequest noteRequest); @@ -76,5 +85,8 @@ public interface EstimateMapper { public int deleteEstimateItemList(EstimateRequest estimateRequest); // 견적서 복사 - public int insertEstimateCopy(EstimateRequest estimateRequest); + public int insertEstimateCopy(EstimateCopyRequest estimateCopyRequest); + + // Plan 확정 동기화 + public int updatePlanConfirmSync(PlanSyncResponse planSyncData); } diff --git a/src/main/java/com/interplug/qcast/biz/estimate/EstimateService.java b/src/main/java/com/interplug/qcast/biz/estimate/EstimateService.java index f6d6108a..eb7c83f4 100644 --- a/src/main/java/com/interplug/qcast/biz/estimate/EstimateService.java +++ b/src/main/java/com/interplug/qcast/biz/estimate/EstimateService.java @@ -1,14 +1,27 @@ package com.interplug.qcast.biz.estimate; import com.fasterxml.jackson.databind.DeserializationFeature; -import com.interplug.qcast.biz.estimate.dto.*; +import com.interplug.qcast.biz.estimate.dto.EstimateApiResponse; +import com.interplug.qcast.biz.estimate.dto.EstimateCopyRequest; +import com.interplug.qcast.biz.estimate.dto.EstimateRequest; +import com.interplug.qcast.biz.estimate.dto.EstimateResponse; +import com.interplug.qcast.biz.estimate.dto.EstimateSendRequest; +import com.interplug.qcast.biz.estimate.dto.EstimateSendResponse; +import com.interplug.qcast.biz.estimate.dto.ItemRequest; +import com.interplug.qcast.biz.estimate.dto.ItemResponse; +import com.interplug.qcast.biz.estimate.dto.NoteRequest; +import com.interplug.qcast.biz.estimate.dto.NoteResponse; +import com.interplug.qcast.biz.estimate.dto.PlanSyncResponse; +import com.interplug.qcast.biz.estimate.dto.PriceRequest; +import com.interplug.qcast.biz.estimate.dto.RoofInfoResponse; +import com.interplug.qcast.biz.estimate.dto.RoofRequest; +import com.interplug.qcast.biz.estimate.dto.RoofResponse; import com.interplug.qcast.biz.file.FileMapper; import com.interplug.qcast.biz.file.dto.FileRequest; import com.interplug.qcast.biz.file.dto.FileResponse; import com.interplug.qcast.biz.object.ObjectMapper; +import com.interplug.qcast.biz.object.dto.ObjectRequest; import com.interplug.qcast.biz.object.dto.ObjectResponse; -import com.interplug.qcast.biz.object.dto.PlanRequest; -import com.interplug.qcast.biz.object.dto.PlanResponse; import com.interplug.qcast.biz.pwrGnrSimulation.PwrGnrSimService; import com.interplug.qcast.biz.pwrGnrSimulation.dto.PwrGnrSimGuideResponse; import com.interplug.qcast.biz.pwrGnrSimulation.dto.PwrGnrSimRequest; @@ -21,19 +34,21 @@ import com.interplug.qcast.util.InterfaceQsp; import com.interplug.qcast.util.PdfUtil; import jakarta.servlet.http.HttpServletRequest; import jakarta.servlet.http.HttpServletResponse; -import java.beans.BeanInfo; -import java.beans.Introspector; -import java.beans.PropertyDescriptor; +import java.io.ByteArrayInputStream; +import java.io.ByteArrayOutputStream; import java.io.IOException; -import java.lang.reflect.Field; -import java.lang.reflect.Method; +import java.io.InputStream; import java.math.BigDecimal; import java.text.SimpleDateFormat; -import java.util.*; +import java.util.ArrayList; +import java.util.Date; import java.util.List; +import java.util.Map; import lombok.RequiredArgsConstructor; import lombok.extern.slf4j.Slf4j; import org.apache.commons.lang3.StringUtils; +import org.apache.poi.ss.usermodel.Workbook; +import org.apache.poi.ss.usermodel.WorkbookFactory; import org.jsoup.nodes.Document; import org.jsoup.nodes.Element; import org.springframework.beans.factory.annotation.Autowired; @@ -50,6 +65,9 @@ public class EstimateService { @Autowired Messages message; + @Value("${file.ini.root.path}") + private String baseDirPath; + @Value("${qsp.url}") private String QSP_API_URL; @@ -160,6 +178,17 @@ public class EstimateService { return response; } + /** + * 견적 특이사항 타이틀 목록 조회 + * + * @param noteRequest 견적 특이사항 조회 정보 + * @return List 견적 특이사항 목록 + * @throws Exception + */ + public List selectSpecialNoteTitleList(NoteRequest noteRequest) throws Exception { + return estimateMapper.selectEstimateNoteTitleList(noteRequest); + } + /** * 견적 특이사항 목록 조회 * @@ -601,104 +630,194 @@ public class EstimateService { } } catch (Exception e) { e.printStackTrace(); + throw new QcastException(ErrorCode.INTERNAL_SERVER_ERROR); } } /** * 견적서 복사 * - * @param estimateRequest 견적서 복사 정보 + * @param estimateCopyRequest 견적서 복사 정보 * @return EstimateResponse 견적서 복사 후 상세 정보 * @throws Exception */ - public EstimateResponse insertEstimateCopy(EstimateRequest estimateRequest) throws Exception { + public EstimateResponse insertEstimateCopy(EstimateCopyRequest estimateCopyRequest) + throws Exception { // Validation - if (StringUtils.isEmpty(estimateRequest.getObjectNo())) { + if (StringUtils.isEmpty(estimateCopyRequest.getObjectNo())) { throw new QcastException( ErrorCode.INVALID_INPUT_VALUE, message.getMessage("common.message.required.data", "Object No")); } - if (StringUtils.isEmpty(estimateRequest.getPlanNo())) { + if (StringUtils.isEmpty(estimateCopyRequest.getPlanNo())) { throw new QcastException( ErrorCode.INVALID_INPUT_VALUE, message.getMessage("common.message.required.data", "Plan No")); } - + // 응답 객체 EstimateResponse response = new EstimateResponse(); - // [1]. 총 플랜 목록 조회 및 제약조건 처리 (플랜 10개까지만 등록) - PlanRequest planRequest = new PlanRequest(); - planRequest.setObjectNo(estimateRequest.getObjectNo()); - List planList = objectMapper.selectPlanList(planRequest); - if (planList.size() > 9) { - throw new QcastException( - ErrorCode.INTERNAL_SERVER_ERROR, message.getMessage("common.message.plan.save.limit")); - } + try { - List itemList = new ArrayList(); - List estimateItemList = estimateMapper.selectEstimateItemList(estimateRequest); - for (ItemResponse itemResponse : estimateItemList) { - ItemRequest itemRequest = new ItemRequest(); - itemRequest.setItemId(itemResponse.getItemId()); - itemRequest.setAmount(itemResponse.getAmount()); + ObjectRequest objectRequest = new ObjectRequest(); + objectRequest.setSaleStoreId(estimateCopyRequest.getCopySaleStoreId()); + objectRequest.setReceiveUser( + StringUtils.defaultString(estimateCopyRequest.getCopyReceiveUser())); + objectRequest.setDelFlg("0"); + objectRequest.setTempFlg("0"); + objectRequest.setTempDelFlg("0"); + objectRequest.setUserId(estimateCopyRequest.getUserId()); - itemList.add(itemRequest); - } + // [1]. 신규 물건번호 생성 + objectMapper.insertObjectNo(objectRequest); + objectRequest.setObjectNo(estimateCopyRequest.getObjectNo()); + objectRequest.setCopyObjectNo(objectMapper.selectObjectNo(objectRequest)); - // [2]. 아이템 관련 데이터 셋팅 (복사 시 정가 셋팅) - String[] arrItemId = new String[itemList.size()]; - int i = 0; - for (ItemRequest itemRequest : itemList) { - arrItemId[i++] = itemRequest.getItemId(); - } - estimateRequest.setArrItemId(arrItemId); - // 아이템의 마스터 정보 및 정가 정보 조회 - List itemResponseList = estimateMapper.selectItemMasterList(estimateRequest); + // [2]. 물건정보 복사 + objectRequest.setContentsPath(baseDirPath + "\\\\" + objectRequest.getCopyObjectNo()); + objectMapper.insertObjectCopy(objectRequest); + objectRequest.setObjectNo(objectRequest.getCopyObjectNo()); + objectMapper.updateObjectDelivery(objectRequest); - int j = 1; - for (ItemRequest itemRequest : itemList) { - itemRequest.setDispOrder(String.valueOf(j++)); + // [3]. 아이템 관련 데이터 셋팅 (복사 시 정가 셋팅) + EstimateRequest estimateRequest = new EstimateRequest(); + estimateRequest.setObjectNo(estimateCopyRequest.getObjectNo()); + estimateRequest.setPlanNo(estimateCopyRequest.getPlanNo()); - for (ItemResponse itemResponse : itemResponseList) { - if (itemRequest.getItemId().equals(itemResponse.getItemId())) { - itemRequest.setItemNo(itemResponse.getItemNo()); - itemRequest.setItemName(itemResponse.getItemName()); - itemRequest.setUnit(itemResponse.getUnit()); - itemRequest.setPnowW(itemResponse.getPnowW()); - itemRequest.setSpecification(itemResponse.getPnowW()); - itemRequest.setUnitPrice(itemResponse.getSalePrice()); - itemRequest.setSalePrice(itemResponse.getSalePrice()); - itemRequest.setPkgMaterialFlg(itemResponse.getPkgMaterialFlg()); - itemRequest.setItemGroup(itemResponse.getItemGroup()); + List itemList = new ArrayList(); + List estimateItemList = estimateMapper.selectEstimateItemList(estimateRequest); + for (ItemResponse itemResponse : estimateItemList) { + ItemRequest itemRequest = new ItemRequest(); + itemRequest.setDispOrder(itemResponse.getDispOrder()); + itemRequest.setPaDispOrder(itemResponse.getPaDispOrder()); + itemRequest.setItemId(itemResponse.getItemId()); + itemRequest.setAmount(itemResponse.getAmount()); + itemRequest.setBomAmount(itemResponse.getBomAmount()); + itemRequest.setSpecialNoteCd(itemResponse.getSpecialNoteCd()); + itemRequest.setItemChangeFlg("0"); - break; + itemList.add(itemRequest); + } + + String[] arrItemId = new String[itemList.size()]; + int i = 0; + for (ItemRequest itemRequest : itemList) { + arrItemId[i++] = itemRequest.getItemId(); + } + estimateRequest.setArrItemId(arrItemId); + // 아이템의 마스터 정보 및 정가 정보 조회 + List itemResponseList = estimateMapper.selectItemMasterList(estimateRequest); + + for (ItemRequest itemRequest : itemList) { + for (ItemResponse itemResponse : itemResponseList) { + if (itemRequest.getItemId().equals(itemResponse.getItemId())) { + itemRequest.setItemNo(itemResponse.getItemNo()); + itemRequest.setItemName(itemResponse.getItemName()); + itemRequest.setUnit(itemResponse.getUnit()); + itemRequest.setPnowW(itemResponse.getPnowW()); + itemRequest.setSpecification(itemResponse.getPnowW()); + itemRequest.setUnitPrice(itemResponse.getSalePrice()); + itemRequest.setSalePrice(itemResponse.getSalePrice()); + itemRequest.setPkgMaterialFlg(itemResponse.getPkgMaterialFlg()); + itemRequest.setFileUploadFlg(itemResponse.getFileUploadFlg()); + itemRequest.setItemGroup(itemResponse.getItemGroup()); + + break; + } } } + + // [4]. 견적서 복사 + estimateCopyRequest.setCopyObjectNo(objectRequest.getObjectNo()); + estimateCopyRequest.setCopyPlanNo("1"); + estimateMapper.insertEstimateCopy(estimateCopyRequest); + + // [5]. 견적서 아이템 복사 + for (ItemRequest itemRequest : itemList) { + itemRequest.setObjectNo(estimateCopyRequest.getCopyObjectNo()); + itemRequest.setPlanNo(estimateCopyRequest.getCopyPlanNo()); + itemRequest.setPartAdd( + !StringUtils.isEmpty(itemRequest.getPartAdd()) ? itemRequest.getPartAdd() : "0"); + itemRequest.setItemChangeFlg( + !StringUtils.isEmpty(itemRequest.getItemChangeFlg()) + ? itemRequest.getItemChangeFlg() + : "0"); + itemRequest.setUserId(estimateCopyRequest.getUserId()); + + estimateMapper.insertEstimateItem(itemRequest); + } + + // [6]. 견적서 지붕재 복사 + List roofList = estimateMapper.selectEstimateRoofList(estimateRequest); + List roofItemList = estimateMapper.selectEstimateRoofItemList(estimateRequest); + + for (RoofResponse roofResponse : roofList) { + List roofItemList2 = new ArrayList(); + + // 현재 매칭되는 지붕재 아이템 축출 + for (RoofResponse roofItemResponse : roofItemList) { + if (roofResponse.getRoofNo().equals(roofItemResponse.getRoofNo())) { + roofItemList2.add(roofItemResponse); + } + } + + RoofRequest roofRequest = new RoofRequest(); + roofRequest.setObjectNo(estimateCopyRequest.getCopyObjectNo()); + roofRequest.setPlanNo(estimateCopyRequest.getCopyPlanNo()); + roofRequest.setRoofSurface(roofResponse.getRoofSurface()); + roofRequest.setRoofMaterialId(roofResponse.getRoofMaterialId()); + roofRequest.setSupportMethodId(roofResponse.getSupportMethodId()); + roofRequest.setConstructSpecification(roofResponse.getConstructSpecification()); + roofRequest.setSlope(roofResponse.getSlope()); + roofRequest.setAngle(roofResponse.getAngle()); + roofRequest.setClassType(roofResponse.getClassType()); + roofRequest.setAzimuth(roofResponse.getAzimuth()); + roofRequest.setUserId(estimateCopyRequest.getUserId()); + + estimateMapper.insertEstimateRoof(roofRequest); + + for (RoofResponse roofItemResponse : roofItemList2) { + ItemRequest itemRequest = new ItemRequest(); + itemRequest.setRoofNo(roofRequest.getRoofNo()); + itemRequest.setObjectNo(estimateCopyRequest.getCopyObjectNo()); + itemRequest.setPlanNo(estimateCopyRequest.getCopyPlanNo()); + itemRequest.setItemId(roofItemResponse.getItemId()); + itemRequest.setItemNo(roofItemResponse.getItemNo()); + itemRequest.setItemName(roofItemResponse.getItemName()); + itemRequest.setSpecification(roofItemResponse.getSpecification()); + itemRequest.setAmount(roofItemResponse.getAmount()); + itemRequest.setPcItemId(roofItemResponse.getPcItemId()); + itemRequest.setCircuit(roofItemResponse.getCircuit()); + + estimateMapper.insertEstimateRoofItem(itemRequest); + } + } + + // [7]. 견적서 도면 복사 (추후 개발 필요) + + // [8]. QSP Q.CAST SEND API + List resultList = new ArrayList(); + estimateRequest.setObjectNo(estimateCopyRequest.getCopyObjectNo()); + estimateRequest.setPlanNo(estimateCopyRequest.getCopyPlanNo()); + resultList = this.sendEstimateApi(estimateRequest); + // API에서 받은 문서번호 업데이트 + for (EstimateSendResponse result : resultList) { + estimateRequest.setObjectNo(result.getObjectNo()); + estimateRequest.setPlanNo(result.getPlanNo()); + estimateRequest.setDocNo(result.getDocNo()); + estimateRequest.setSyncFlg(result.getSyncFlg()); + estimateRequest.setUserId(estimateCopyRequest.getUserId()); + + estimateMapper.updateEstimateApi(estimateRequest); + } + + } catch (Exception e) { + throw new QcastException(ErrorCode.INTERNAL_SERVER_ERROR); } - // 견적서 복사 - estimateMapper.insertEstimateCopy(estimateRequest); - - // 견적서 아이템 복사 - for (ItemRequest itemRequest : itemList) { - itemRequest.setObjectNo(estimateRequest.getObjectNo()); - itemRequest.setPlanNo(estimateRequest.getCopyPlanNo()); - itemRequest.setPartAdd( - !StringUtils.isEmpty(itemRequest.getPartAdd()) ? itemRequest.getPartAdd() : "0"); - itemRequest.setItemChangeFlg( - !StringUtils.isEmpty(itemRequest.getItemChangeFlg()) - ? itemRequest.getItemChangeFlg() - : "0"); - itemRequest.setUserId(estimateRequest.getUserId()); - - estimateMapper.insertEstimateItem(itemRequest); - } - - // 도면 복사 (추후 개발 필요) - - // 리턴 - response.setObjectNo(estimateRequest.getObjectNo()); - response.setPlanNo(estimateRequest.getCopyPlanNo()); + // [9]. 최종 생성 물건번호 리턴 + response.setObjectNo(estimateCopyRequest.getCopyObjectNo()); + response.setPlanNo(estimateCopyRequest.getCopyPlanNo()); return response; } @@ -835,13 +954,15 @@ public class EstimateService { estimateResponse.setTotPrice( String.format("%1$,.0f", Double.parseDouble(estimateResponse.getTotPrice()))); - // 발전시뮬레이션 계산 + // 발전시뮬레이션 계산 PwrGnrSimRequest pwrGnrSimRequest = new PwrGnrSimRequest(); pwrGnrSimRequest.setObjectNo(estimateResponse.getObjectNo()); pwrGnrSimRequest.setPlanNo(estimateResponse.getPlanNo()); PwrGnrSimResponse pwrGnrSimResponse = pwrGnrSimService.selectPwrGnrSimulation(pwrGnrSimRequest); + pwrGnrSimResponse.setPwrGnrSimType(estimateRequest.getPwrGnrSimType()); + if (pwrGnrSimResponse != null) { try { // 발전시뮬레이션 안내사항 조회 @@ -857,7 +978,7 @@ public class EstimateService { estimateResponse.setPwrGnrSim(pwrGnrSimResponse); if ("PDF".equals(estimateRequest.getSchDownload())) { // PDF 다운로드 - String[] arrSection = new String[5]; // TODO Section 갯수 넣기 + String[] arrSection = new String[6]; int iSection = 0; String templateFilePath = "pdf_download_quotation_detail_template.html"; @@ -865,27 +986,38 @@ public class EstimateService { // 템플릿 html 조회 Document doc = PdfUtil.getPdfDoc(request, templateFilePath); - // 삭제하려는 element - Element elm; - - arrSection[iSection] = "div.section1"; - iSection++; - arrSection[iSection] = "div.section2"; - iSection++; - // 견적서 상세 pdf Html 생성 doc = this.estimatePdfHtml(doc, estimateResponse, estimateItemList); - if ("1".equals(estimateRequest.getSchDrawingFlg())) { - arrSection[iSection] = "div.section3"; - iSection++; - arrSection[iSection] = "div.section4"; - iSection++; - arrSection[iSection] = "div.section5"; - iSection++; + // 발전시뮬레이션 pdf Html 생성 + doc = pwrGnrSimService.pwrGnrSimPdfHtml(doc, pwrGnrSimResponse); - // 발전시뮬레이션 pdf Html 생성 - doc = pwrGnrSimService.pwrGnrSimPdfHtml(doc, pwrGnrSimResponse); + // SchDrawingFlg (1 : 견적서,2 : 발전시뮬레이션, 3 : 도면, 4 : 가대) + // ex) 1|2|3|4 + if (!StringUtils.isEmpty(estimateRequest.getSchDrawingFlg())) { + if (estimateRequest.getSchDrawingFlg().indexOf("1") > -1) { + arrSection[iSection] = "div.section1"; + iSection++; + arrSection[iSection] = "div.section2"; + iSection++; + } + + if (estimateRequest.getSchDrawingFlg().indexOf("2") > -1) { + arrSection[iSection] = "div.section3"; // 발전시뮬레이션 + iSection++; + } + + if (estimateRequest.getSchDrawingFlg().indexOf("3") > -1) { + arrSection[iSection] = "div.section4"; // 도면 + iSection++; + arrSection[iSection] = "div.section5"; // 도면 + iSection++; + } + + if (estimateRequest.getSchDrawingFlg().indexOf("4") > -1) { + arrSection[iSection] = "div.section6"; + iSection++; + } } // pdf 다운로드 @@ -893,20 +1025,56 @@ public class EstimateService { } else { + Workbook workbook = null; + String excelTemplateNam = "excel_download_quotation_detail_template.xlsx"; ExcelUtil excelUtil = new ExcelUtil(); - excelUtil.download( - request, - response, - this.convertVoToMap(estimateResponse), - this.convertListToMap(estimateItemList), - estimateRequest.getFileName(), - excelTemplateNam); + byte[] excelBytes = + excelUtil.download( + request, + response, + excelUtil.convertVoToMap(estimateResponse), + excelUtil.convertListToMap(estimateItemList), + excelTemplateNam); + + InputStream in = new ByteArrayInputStream(excelBytes); + workbook = WorkbookFactory.create(in); // JXLS POI 엑셀로 재변환 + + // SchDrawingFlg (1 : 견적서,2 : 발전시뮬레이션, 3 : 도면, 4 : 가대) + // ex) 1|2|3|4 + if (!StringUtils.isEmpty(estimateRequest.getSchDrawingFlg())) { + if (estimateRequest.getSchDrawingFlg().indexOf("1") < 0) { + workbook.removeSheetAt(workbook.getSheetIndex("見積書")); + workbook.removeSheetAt(workbook.getSheetIndex("特異事項")); + } + + if (estimateRequest.getSchDrawingFlg().indexOf("2") < 0) { + workbook.removeSheetAt(workbook.getSheetIndex("発電シミュレーション")); + } + + if (estimateRequest.getSchDrawingFlg().indexOf("3") < 0) { + workbook.removeSheetAt(workbook.getSheetIndex("割付図・系統図")); + workbook.removeSheetAt(workbook.getSheetIndex("架台図")); + } + } + + // 추후 개발 (가대중량표) + if (estimateRequest.getSchDrawingFlg().indexOf("4") < 0) {} + + ByteArrayOutputStream byteArrayOutputStream = new ByteArrayOutputStream(); + workbook.write(byteArrayOutputStream); + excelBytes = byteArrayOutputStream.toByteArray(); + + response.setHeader( + "Content-Disposition", + "attachment; filename=\"" + estimateRequest.getFileName() + ".xlsx\""); + response.addHeader("Access-Control-Expose-Headers", "Content-Disposition"); + response.getOutputStream().write(excelBytes); } } catch (Exception e) { - e.printStackTrace(); + throw new QcastException(ErrorCode.INTERNAL_SERVER_ERROR); } } @@ -1034,8 +1202,8 @@ public class EstimateService { estimateSendResponse.setSaveType("3"); estimateSendResponse.setSyncFlg("0"); estimateSendResponse.setConstructSpecification( - !StringUtils.isEmpty(estimateRequest.getConstructSpecification()) - ? estimateRequest.getConstructSpecification().split("、")[0] + !StringUtils.isEmpty(estimateSendResponse.getConstructSpecification()) + ? estimateSendResponse.getConstructSpecification().split("、")[0] : ""); estimateSendResponse.setDelFlg("1".equals(estimateSendResponse.getDelFlg()) ? "Y" : "N"); @@ -1061,7 +1229,7 @@ public class EstimateService { /* [1]. QSP API CALL -> Response */ String strResponse = interfaceQsp.callApi( - HttpMethod.POST, QSP_API_URL + "/api/master/qcastQuotationSave", estimateSendRequest); + HttpMethod.POST, QSP_API_URL + "/api/order/qcastQuotationSave", estimateSendRequest); if (!"".equals(strResponse)) { com.fasterxml.jackson.databind.ObjectMapper om = @@ -1078,7 +1246,7 @@ public class EstimateService { for (EstimateSendResponse data : quoteList) { if (data.getObjectNo().equals(succ.get("objectNo")) && data.getPlanNo().equals(succ.get("planNo"))) { - data.setSyncFlg("1"); + data.setSyncFlg(String.valueOf(succ.get("syncFlg"))); data.setDocNo(String.valueOf(succ.get("docNo"))); } } @@ -1438,56 +1606,90 @@ public class EstimateService { } /** - * Object => Map 변환 함수 + * Plan 확정 정보 동기화 * - * @param vo Object - * @return Map Map 변환 정보 + * @param planSyncList Plan 목록 + * @return + * @throws Exception */ - public Map convertVoToMap(Object vo) { - Map result = new HashMap(); - - try { - BeanInfo info = Introspector.getBeanInfo(vo.getClass()); - for (PropertyDescriptor pd : info.getPropertyDescriptors()) { - Method reader = pd.getReadMethod(); - if (reader != null) { - result.put(pd.getName(), reader.invoke(vo)); - } - } - } catch (Exception e) { - log.error("convertVoToMap >>> " + e.getMessage()); + public int setPlanConfirmSyncSave(List planSyncList) throws Exception { + int cnt = 0; + for (PlanSyncResponse planSyncData : planSyncList) { + // Plan 확정 처리 + cnt += estimateMapper.updatePlanConfirmSync(planSyncData); } - return result; + return cnt; } /** - * List => List 변환 함수 + * QSP Q.CAST 견적서 동기화 실패 목록 * - * @param target List - * @return List> List 변환 정보 + * @return EstimateSendRequest 견적서 실패 목록 + * @throws Exception */ - public static List> convertListToMap(Collection target) { - List> resultList = new ArrayList>(); + public EstimateSendRequest selectEstimateSyncFailList() throws Exception { + EstimateSendRequest estimateSendRequest = new EstimateSendRequest(); + List quoteList = new ArrayList(); + String docNo = ""; - for (T element : target) { - Map resultMap = new HashMap(); - Field[] fieldList = element.getClass().getDeclaredFields(); - if (fieldList != null && fieldList.length > 0) { - try { - for (int i = 0; i < fieldList.length; i++) { - String curInsName = fieldList[i].getName(); - Field field = element.getClass().getDeclaredField(curInsName); - field.setAccessible(true); - Object targetValue = field.get(element); + // 견적서 동기화 실패 목록 조회 + List estimateSendListResponse = + estimateMapper.selectEstimateApiFailList(); - resultMap.put(curInsName, targetValue); - } - resultList.add(resultMap); - } catch (Exception e) { - log.error("convertListToMap >>> " + e.getMessage()); - } - } + for (EstimateSendResponse estimateSendResponse : estimateSendListResponse) { + EstimateRequest estimateRequest = new EstimateRequest(); + estimateRequest.setObjectNo(estimateSendResponse.getObjectNo()); + estimateRequest.setPlanNo(estimateSendResponse.getPlanNo()); + + estimateSendResponse.setSaveType("3"); + estimateSendResponse.setSyncFlg("0"); + estimateSendResponse.setConstructSpecification( + !StringUtils.isEmpty(estimateSendResponse.getConstructSpecification()) + ? estimateSendResponse.getConstructSpecification().split("、")[0] + : ""); + estimateSendResponse.setDelFlg("1".equals(estimateSendResponse.getDelFlg()) ? "Y" : "N"); + + // 아이템 목록 조회 + estimateRequest.setSchBomNotExist("1"); + List estimateItemList = estimateMapper.selectEstimateItemList(estimateRequest); + estimateSendResponse.setItemList(estimateItemList); + + // 첨부파일 목록 조회 + FileRequest fileDeleteReq = new FileRequest(); + fileDeleteReq.setObjectNo(estimateRequest.getObjectNo()); + fileDeleteReq.setPlanNo(estimateRequest.getPlanNo()); + fileDeleteReq.setCategory("10"); + + List fileList = fileMapper.selectFileList(fileDeleteReq); + estimateSendResponse.setFileList(fileList); + + quoteList.add(estimateSendResponse); + estimateSendRequest.setQuoteList(quoteList); } - return resultList; + + return estimateSendRequest; + } + + /** + * 견적서 정보 QSP 동기화 + * + * @param planSyncList Plan 목록 + * @return + * @throws Exception + */ + public int setEstimateSyncSave(List planSyncList) throws Exception { + int cnt = 0; + for (PlanSyncResponse planSyncData : planSyncList) { + EstimateRequest estimateRequest = new EstimateRequest(); + estimateRequest.setObjectNo(planSyncData.getObjectNo()); + estimateRequest.setPlanNo(planSyncData.getPlanNo()); + estimateRequest.setDocNo(planSyncData.getDocNo()); + estimateRequest.setSyncFlg(planSyncData.getSyncFlg()); + estimateRequest.setUserId("system"); + + // 견적서 동기화 여부 처리 + cnt += estimateMapper.updateEstimateApi(estimateRequest); + } + return cnt; } } diff --git a/src/main/java/com/interplug/qcast/biz/estimate/dto/EstimateCopyRequest.java b/src/main/java/com/interplug/qcast/biz/estimate/dto/EstimateCopyRequest.java new file mode 100644 index 00000000..e90d5442 --- /dev/null +++ b/src/main/java/com/interplug/qcast/biz/estimate/dto/EstimateCopyRequest.java @@ -0,0 +1,31 @@ +package com.interplug.qcast.biz.estimate.dto; + +import io.swagger.v3.oas.annotations.media.Schema; +import lombok.Data; + +@Data +public class EstimateCopyRequest { + @Schema(description = "물건번호") + private String objectNo; + + @Schema(description = "플랜번호") + private String planNo; + + @Schema(description = "판매점ID") + private String saleStoreId; + + @Schema(description = "복사 판매점 ID") + private String copySaleStoreId; + + @Schema(description = "복사 물건번호") + private String copyObjectNo; + + @Schema(description = "복사 플랜번호") + private String copyPlanNo; + + @Schema(description = "복사 담당자명") + private String copyReceiveUser; + + @Schema(description = "사용자아이디") + private String userId; +} diff --git a/src/main/java/com/interplug/qcast/biz/estimate/dto/EstimateRequest.java b/src/main/java/com/interplug/qcast/biz/estimate/dto/EstimateRequest.java index d7d9073f..7058d14a 100644 --- a/src/main/java/com/interplug/qcast/biz/estimate/dto/EstimateRequest.java +++ b/src/main/java/com/interplug/qcast/biz/estimate/dto/EstimateRequest.java @@ -156,9 +156,6 @@ public class EstimateRequest { @Schema(description = "비고") private String remarks; - @Schema(description = "복사 플랜번호") - private String copyPlanNo; - @Schema(description = "아이템번호 목록") private String[] arrItemId; @@ -193,4 +190,7 @@ public class EstimateRequest { @Schema(description = "다운로드 파일명") private String fileName; + + @Schema(description = "발전시뮬레이션 타입") + private String pwrGnrSimType; } diff --git a/src/main/java/com/interplug/qcast/biz/estimate/dto/EstimateSyncResponse.java b/src/main/java/com/interplug/qcast/biz/estimate/dto/EstimateSyncResponse.java new file mode 100644 index 00000000..b1ddf18e --- /dev/null +++ b/src/main/java/com/interplug/qcast/biz/estimate/dto/EstimateSyncResponse.java @@ -0,0 +1,14 @@ +package com.interplug.qcast.biz.estimate.dto; + +import io.swagger.v3.oas.annotations.media.Schema; +import java.util.List; +import lombok.Data; + +@Data +public class EstimateSyncResponse { + @Schema(description = "실패목록") + private List failList; + + @Schema(description = "성공목록") + private List successList; +} diff --git a/src/main/java/com/interplug/qcast/biz/estimate/dto/ItemRequest.java b/src/main/java/com/interplug/qcast/biz/estimate/dto/ItemRequest.java index cdaf6adf..960a29a7 100644 --- a/src/main/java/com/interplug/qcast/biz/estimate/dto/ItemRequest.java +++ b/src/main/java/com/interplug/qcast/biz/estimate/dto/ItemRequest.java @@ -71,6 +71,9 @@ public class ItemRequest { @Schema(description = "PC 아이템 ID") private String pcItemId; + @Schema(description = "회로") + private String circuit; + @Schema(description = "W") private String pnowW; diff --git a/src/main/java/com/interplug/qcast/biz/estimate/dto/NoteResponse.java b/src/main/java/com/interplug/qcast/biz/estimate/dto/NoteResponse.java index 49c931e6..1ff5d000 100644 --- a/src/main/java/com/interplug/qcast/biz/estimate/dto/NoteResponse.java +++ b/src/main/java/com/interplug/qcast/biz/estimate/dto/NoteResponse.java @@ -16,4 +16,7 @@ public class NoteResponse { @Schema(description = "견적특이사항") private String remarks; + + @Schema(description = "특이사항 묶음 여부") + private String pkgYn; } diff --git a/src/main/java/com/interplug/qcast/biz/estimate/dto/PlanSyncResponse.java b/src/main/java/com/interplug/qcast/biz/estimate/dto/PlanSyncResponse.java new file mode 100644 index 00000000..71ff1652 --- /dev/null +++ b/src/main/java/com/interplug/qcast/biz/estimate/dto/PlanSyncResponse.java @@ -0,0 +1,22 @@ +package com.interplug.qcast.biz.estimate.dto; + +import io.swagger.v3.oas.annotations.media.Schema; +import lombok.Data; + +@Data +public class PlanSyncResponse { + @Schema(description = "물건번호") + private String objectNo; + + @Schema(description = "플랜번호") + private String planNo; + + @Schema(description = "견적서번호") + private String docNo; + + @Schema(description = "동기화여부") + private String syncFlg; + + @Schema(description = "메시지") + private String message; +} diff --git a/src/main/java/com/interplug/qcast/biz/estimate/dto/RoofRequest.java b/src/main/java/com/interplug/qcast/biz/estimate/dto/RoofRequest.java index 4aebc2c5..1a2aedcc 100644 --- a/src/main/java/com/interplug/qcast/biz/estimate/dto/RoofRequest.java +++ b/src/main/java/com/interplug/qcast/biz/estimate/dto/RoofRequest.java @@ -48,6 +48,9 @@ public class RoofRequest { @Schema(description = "각도") private String angle; + @Schema(description = "경사각 선택코드") + private String classType; + @Schema(description = "방위각") private String azimuth; diff --git a/src/main/java/com/interplug/qcast/biz/estimate/dto/RoofResponse.java b/src/main/java/com/interplug/qcast/biz/estimate/dto/RoofResponse.java index 77b9c447..927a570a 100644 --- a/src/main/java/com/interplug/qcast/biz/estimate/dto/RoofResponse.java +++ b/src/main/java/com/interplug/qcast/biz/estimate/dto/RoofResponse.java @@ -77,12 +77,24 @@ public class RoofResponse { @Schema(description = "아이템 번호") private String itemNo; + @Schema(description = "아이템명") + private String itemName; + + @Schema(description = "W") + private String specification; + @Schema(description = "매수") private String amount; @Schema(description = "용량") private String volKw; + @Schema(description = "PC 아이템 ID") + private String pcItemId; + + @Schema(description = "회로") + private String circuit; + @Schema(description = "Pc 모듈 매수") private String pcModuleAmount; } diff --git a/src/main/java/com/interplug/qcast/biz/module/ModuleInfoController.java b/src/main/java/com/interplug/qcast/biz/module/ModuleInfoController.java deleted file mode 100644 index 907628ac..00000000 --- a/src/main/java/com/interplug/qcast/biz/module/ModuleInfoController.java +++ /dev/null @@ -1,24 +0,0 @@ -package com.interplug.qcast.biz.module; - -import com.interplug.qcast.biz.module.dto.ModuleInfoResponse; -import io.swagger.v3.oas.annotations.Operation; -import io.swagger.v3.oas.annotations.tags.Tag; -import java.util.List; -import lombok.RequiredArgsConstructor; -import org.springframework.web.bind.annotation.*; - -@RestController -@RequestMapping("/api/module/module-infos") -@RequiredArgsConstructor -@Tag(name = "ModuleInfoController", description = "모듈 정보 API") -public class ModuleInfoController { - private final ModuleInfoService moduleService; - - @Operation(description = "지붕재 ID와 가대 ID에 따라 설치 가능한 모듈 목록을 조회한다.") - @GetMapping - public List getModulesByRoofMaterialIdAndTrestleId( - @RequestParam("roofMaterialId") Integer roofMaterialId, - @RequestParam("trestleId") Integer trestleId) { - return moduleService.getModulesByRoofMaterialIdAndTrestleId(roofMaterialId, trestleId); - } -} diff --git a/src/main/java/com/interplug/qcast/biz/module/ModuleInfoMapper.java b/src/main/java/com/interplug/qcast/biz/module/ModuleInfoMapper.java deleted file mode 100644 index 394f01a8..00000000 --- a/src/main/java/com/interplug/qcast/biz/module/ModuleInfoMapper.java +++ /dev/null @@ -1,13 +0,0 @@ -package com.interplug.qcast.biz.module; - -import com.interplug.qcast.biz.module.dto.ModuleInfoResponse; -import java.util.List; -import org.apache.ibatis.annotations.Mapper; -import org.apache.ibatis.annotations.Param; - -@Mapper -public interface ModuleInfoMapper { - - List getModulesByRoofMaterialIdAndTrestleId( - @Param("roofMaterialId") Integer roofMaterialId, @Param("trestleId") Integer trestleId); -} diff --git a/src/main/java/com/interplug/qcast/biz/module/ModuleInfoService.java b/src/main/java/com/interplug/qcast/biz/module/ModuleInfoService.java deleted file mode 100644 index f0442d26..00000000 --- a/src/main/java/com/interplug/qcast/biz/module/ModuleInfoService.java +++ /dev/null @@ -1,18 +0,0 @@ -package com.interplug.qcast.biz.module; - -import com.interplug.qcast.biz.module.dto.ModuleInfoResponse; -import java.util.List; -import lombok.RequiredArgsConstructor; -import org.springframework.stereotype.Service; - -@Service -@RequiredArgsConstructor -public class ModuleInfoService { - - private final ModuleInfoMapper moduleMapper; - - public List getModulesByRoofMaterialIdAndTrestleId( - Integer roofMaterialId, Integer trestleId) { - return moduleMapper.getModulesByRoofMaterialIdAndTrestleId(roofMaterialId, trestleId); - } -} diff --git a/src/main/java/com/interplug/qcast/biz/module/dto/ModuleInfoResponse.java b/src/main/java/com/interplug/qcast/biz/module/dto/ModuleInfoResponse.java deleted file mode 100644 index f2b265f2..00000000 --- a/src/main/java/com/interplug/qcast/biz/module/dto/ModuleInfoResponse.java +++ /dev/null @@ -1,15 +0,0 @@ -package com.interplug.qcast.biz.module.dto; - -import lombok.AllArgsConstructor; -import lombok.Getter; -import lombok.NoArgsConstructor; -import lombok.Setter; - -@Getter -@Setter -@AllArgsConstructor -@NoArgsConstructor -public class ModuleInfoResponse { - private Integer id; - private String name; -} diff --git a/src/main/java/com/interplug/qcast/biz/object/ObjectMapper.java b/src/main/java/com/interplug/qcast/biz/object/ObjectMapper.java index 00b9bb7c..1d7fb162 100644 --- a/src/main/java/com/interplug/qcast/biz/object/ObjectMapper.java +++ b/src/main/java/com/interplug/qcast/biz/object/ObjectMapper.java @@ -43,6 +43,9 @@ public interface ObjectMapper { // 물건정보 등록 public int insertObject(ObjectRequest objectRequest); + // 물건정보 복사 + public int insertObjectCopy(ObjectRequest objectRequest); + // 물건정보 수정 public int updateObject(ObjectRequest objectRequest); diff --git a/src/main/java/com/interplug/qcast/biz/object/ObjectService.java b/src/main/java/com/interplug/qcast/biz/object/ObjectService.java index a0e9e5b5..d4f7bd23 100644 --- a/src/main/java/com/interplug/qcast/biz/object/ObjectService.java +++ b/src/main/java/com/interplug/qcast/biz/object/ObjectService.java @@ -60,18 +60,46 @@ public class ObjectService { private final StoreFavoriteService storeFavoriteService; + /** + * 도도부현 목록 조회 + * + * @return List 도도부현 목록 + * @throws Exception + */ public List selectPrefList() throws Exception { return objectMapper.selectPrefList(); } + /** + * 발전시뮬레이션 지역 목록 조회 + * + * @param prefId 도도부현 코드 + * @return List 발전시뮬레이션 지역 목록 + * @throws Exception + */ public List selectPrefAreaList(String prefId) throws Exception { return objectMapper.selectPrefAreaList(prefId); } + /** + * 기준 풍속 목록 조회 + * + * @param city 지역코드 + * @return List 기준 풍속 목록 + * @throws Exception + */ public List selectWindSpeedList(String city) throws Exception { return objectMapper.selectWindSpeedList(city); } + /** + * 1차점 판매점 목록 조회 + * + * @param saleStoreId 1차점 판매점 아이디 + * @param userId 유저 아이디 + * @return List 1차점 판매점 목록 + * @throws Exception + */ public List selectFirstSaleStoreList(String saleStoreId, String userId) throws Exception { // Validation @@ -96,6 +124,15 @@ public class ObjectService { return storeList; } + /** + * 하위 판매점 목록 조회 + * + * @param saleStoreId 판매점 아이디 + * @param firstFlg 1차점 판매점 여부 + * @param userId 유저 아이디 + * @return List 하위 판매점 목록 + * @throws Exception + */ public List selectSaleStoreList( String saleStoreId, String firstFlg, String userId) throws Exception { // Validation @@ -117,14 +154,35 @@ public class ObjectService { return storeList; } + /** + * 판매점 정보 상세 조회 + * + * @param saleStoreId 판매점 아이디 + * @return SaleStoreResponse 판매점 상세 정보 + * @throws Exception + */ public SaleStoreResponse selectSaleStoreInfo(String saleStoreId) throws Exception { return objectMapper.selectSaleStoreInfo(saleStoreId); } + /** + * 물건정보 목록 조회 + * + * @param objectRequest 물건정보 검색어 정보 + * @return List 물건정보 목록 + * @throws Exception + */ public List selectObjectList(ObjectRequest objectRequest) throws Exception { return objectMapper.selectObjectList(objectRequest); } + /** + * 물건정보 상세 조회 + * + * @param objectNo 물건번호 + * @return ObjectResponse 물건정보 상세 + * @throws Exception + */ public ObjectResponse selectObjectDetail(String objectNo) throws Exception { // object 상세 정보 조회 ObjectResponse objectResponse = objectMapper.selectObjectDetail(objectNo); @@ -141,6 +199,13 @@ public class ObjectService { return objectResponse; } + /** + * 물건정보 저장 + * + * @param objectRequest 물건정보 + * @return ObjectResponse 물건정보 저장 결과 값 + * @throws Exception + */ public ObjectResponse insertObject(ObjectRequest objectRequest) throws Exception { int result = 0; String objectNo = ""; @@ -157,9 +222,12 @@ public class ObjectService { message.getMessage("common.message.required.data", "Sale Store Level")); } + objectRequest.setSourceOrigin("QCAST_III"); + // 물건번호 등록/조회 if ("0".equals(objectRequest.getTempFlg())) { - objectRequest.setDelFlg("0"); + objectRequest.setDelFlg("1"); + objectRequest.setOrgDelFlg("0"); objectRequest.setTempFlg("0"); objectRequest.setTempDelFlg("0"); @@ -167,6 +235,7 @@ public class ObjectService { objectNo = objectMapper.selectObjectNo(objectRequest); } else if ("1".equals(objectRequest.getTempFlg())) { objectRequest.setDelFlg("1"); + objectRequest.setOrgDelFlg("1"); objectRequest.setTempFlg("1"); objectRequest.setTempDelFlg("0"); @@ -183,10 +252,7 @@ public class ObjectService { // 물건정보 등록 objectRequest.setAddress( - objectRequest.getPrefName() - + ((!StringUtils.isEmpty(objectRequest.getAddress())) - ? objectRequest.getAddress() - : "")); + ((!StringUtils.isEmpty(objectRequest.getAddress())) ? objectRequest.getAddress() : "")); objectRequest.setAddresseeCompanyName( objectRequest.getObjectName() + ' ' + objectRequest.getObjectNameOmit()); objectRequest.setAddresseeCompanyNameOmit(objectRequest.getObjectNameOmit()); @@ -243,6 +309,13 @@ public class ObjectService { return objectResponse; } + /** + * 물건정보 수정 + * + * @param objectRequest 물건정보 + * @return ObjectResponse 물건정보 수정 결과 값 + * @throws Exception + */ public ObjectResponse updateObject(ObjectRequest objectRequest) throws Exception { int result = 0; boolean tempChgFlg = false; @@ -273,10 +346,7 @@ public class ObjectService { // 물건정보 수정 objectRequest.setAddress( - objectRequest.getPrefName() - + ((!StringUtils.isEmpty(objectRequest.getAddress())) - ? objectRequest.getAddress() - : "")); + ((!StringUtils.isEmpty(objectRequest.getAddress())) ? objectRequest.getAddress() : "")); objectRequest.setAddresseeCompanyName( objectRequest.getObjectName() + ' ' + objectRequest.getObjectNameOmit()); objectRequest.setAddresseeCompanyNameOmit(objectRequest.getObjectNameOmit()); @@ -327,6 +397,13 @@ public class ObjectService { return objectResponse; } + /** + * 물건정보 삭제 + * + * @param objectRequest 물건정보 + * @return int 결과 값 + * @throws Exception + */ public int deleteObject(ObjectRequest objectRequest) throws Exception { int result = 0; @@ -376,6 +453,13 @@ public class ObjectService { return result; } + /** + * 신규 플랜정보 추가 + * + * @param planRequest 플랜정보 + * @return String 추가 플랜번호 + * @throws Exception + */ public String insertPlan(PlanRequest planRequest) throws Exception { // Validation if (StringUtils.isEmpty(planRequest.getObjectNo())) { @@ -404,6 +488,12 @@ public class ObjectService { return planRequest.getPlanNo(); } + /** + * 플랜정보 삭제 + * + * @param planRequest 플랜정보 + * @throws Exception + */ public void deletePlan(PlanRequest planRequest) throws Exception { // Validation if (StringUtils.isEmpty(planRequest.getObjectNo())) { @@ -428,6 +518,13 @@ public class ObjectService { objectMapper.deletePlan(planRequest); } + /** + * 설계의뢰 목록 조회 + * + * @param planReqRequest 설계의뢰 요청 정보 + * @return PlanReqResponse 설계의뢰 응답 정보 + * @throws Exception + */ public PlanReqResponse selectPlanReqList(PlanReqRequest planReqRequest) throws Exception { // Validation @@ -512,6 +609,14 @@ public class ObjectService { return response; } + /** + * 물건정보 첨부파일 다운로드 + * + * @param request Request + * @param response Response + * @param uploadRequest 첨부파일 요청 정보 + * @throws Exception + */ public void fileDownload( HttpServletRequest request, HttpServletResponse response, UploadRequest uploadRequest) throws Exception { diff --git a/src/main/java/com/interplug/qcast/biz/object/dto/ObjectRequest.java b/src/main/java/com/interplug/qcast/biz/object/dto/ObjectRequest.java index d9a36cbe..a443f622 100644 --- a/src/main/java/com/interplug/qcast/biz/object/dto/ObjectRequest.java +++ b/src/main/java/com/interplug/qcast/biz/object/dto/ObjectRequest.java @@ -90,6 +90,9 @@ public class ObjectRequest { @Schema(description = "컨텐츠 파일경로") private String contentsPath; + @Schema(description = "소스 원본") + private String sourceOrigin; + @Schema(description = "임시저장여부") private String tempFlg; @@ -102,6 +105,9 @@ public class ObjectRequest { @Schema(description = "삭제여부") private String delFlg; + @Schema(description = "원본 삭제여부") + private String orgDelFlg; + @Schema(description = "사용자아이디") private String userId; @@ -152,6 +158,9 @@ public class ObjectRequest { @Schema(description = "검색 - 정렬순서") private String schSortType; + @Schema(description = "복사 물건번호") + private String copyObjectNo; + // 페이징정보 @Schema(description = "시작 Row") private String startRow; diff --git a/src/main/java/com/interplug/qcast/biz/pwrGnrSimulation/PwrGnrSimService.java b/src/main/java/com/interplug/qcast/biz/pwrGnrSimulation/PwrGnrSimService.java index c9272407..6763e65b 100644 --- a/src/main/java/com/interplug/qcast/biz/pwrGnrSimulation/PwrGnrSimService.java +++ b/src/main/java/com/interplug/qcast/biz/pwrGnrSimulation/PwrGnrSimService.java @@ -113,8 +113,12 @@ public class PwrGnrSimService { // 데이터가 없어서 오류가 발생한 경우, 빈값으로 리턴 PwrGnrSimResponse exceptionRes = new PwrGnrSimResponse(); - int[] exceptionData = new int[13]; - exceptionRes.setFrcPwrGnrList(exceptionData); + double[] dExceptionData = new double[13]; + String[] strExceptionData = formatAndPrintArray(dExceptionData); + exceptionRes.setHatsudenryouAll(strExceptionData); + exceptionRes.setHatsudenryouAllSnow(strExceptionData); + exceptionRes.setHatsudenryouPeakcutAll(strExceptionData); + exceptionRes.setHatsudenryouPeakcutAllSnow(strExceptionData); // 견적서 정보를 조회한다. PwrGnrSimPlanResponse planInfo = pwrGnrSimMapper.selectPlanInfo(pwrGnrSimRequest); @@ -274,7 +278,6 @@ public class PwrGnrSimService { pwrGnrSimRes.setPlanNo(planInfo.getPlanNo()); pwrGnrSimRes.setDrawingEstimateCreateDate(planInfo.getDrawingEstimateCreateDate()); pwrGnrSimRes.setCapacity(String.valueOf(dSpecification)); - pwrGnrSimRes.setAnlFrcsGnrt(pwrGnrSimRes.getFrcPwrGnrList()[12]); pwrGnrSimRes.setPrefName(planInfo.getPrefName()); pwrGnrSimRes.setAreaName(planInfo.getAreaName()); pwrGnrSimRes.setSnowfall(planInfo.getSnowfall()); @@ -437,10 +440,10 @@ public class PwrGnrSimService { double sekisairitsu = module_youryou_total / (pcs_youryou_total * 1000); // 피크 컷 및 발전량 배열 선언 - int[] hatsudenryou_all = new int[13]; // 피크 컷 없음 발전량(적설 고려 없음) - // double[] hatsudenryou_all_snow = new double[12]; // 피크 컷 없음 발전량(적설 고려 있음) - // double[] hatsudenryou_peakcut_all = new double[12]; // 피크 컷 있음 발전량(적설 고려 없음) - // double[] hatsudenryou_peakcut_all_snow = new double[12]; // 피크 컷 있음 발전량(적설 고려 있음) + double[] hatsudenryou_all = new double[13]; // 피크 컷 없음 발전량(적설 고려 없음) + double[] hatsudenryou_all_snow = new double[13]; // 피크 컷 없음 발전량(적설 고려 있음) + double[] hatsudenryou_peakcut_all = new double[13]; // 피크 컷 있음 발전량(적설 고려 없음) + double[] hatsudenryou_peakcut_all_snow = new double[13]; // 피크 컷 있음 발전량(적설 고려 있음) if (sekisairitsu <= 3) { @@ -522,19 +525,21 @@ public class PwrGnrSimService { for (int i = 0; i < roofLength; i++) { hatsudenryou_all[j] += (int) Math.round(hatsudenryou[i][j]); - // hatsudenryou_peakcut_all[j] += hatsudenryou_peakcut[i][j]; + hatsudenryou_peakcut_all[j] += hatsudenryou_peakcut[i][j]; } - // hatsudenryou_all_snow[j] = - // hatsudenryou_all[j] * (1 - (snow[(simulationPointNumber * 12) + j])); - // hatsudenryou_peakcut_all_snow[j] = - // hatsudenryou_peakcut_all[j] * (1 - (snow[(simulationPointNumber * 12) + - // j])); + hatsudenryou_all_snow[j] = + hatsudenryou_all[j] * (1 - (snow[(simulationPointNumber * 12) + j])); + hatsudenryou_peakcut_all_snow[j] = + hatsudenryou_peakcut_all[j] * (1 - (snow[(simulationPointNumber * 12) + j])); } } // 마지막에 총합계 추가 hatsudenryou_all[12] = Arrays.stream(hatsudenryou_all).sum(); + hatsudenryou_all_snow[12] = Arrays.stream(hatsudenryou_all_snow).sum(); + hatsudenryou_peakcut_all[12] = Arrays.stream(hatsudenryou_peakcut_all).sum(); + hatsudenryou_peakcut_all_snow[12] = Arrays.stream(hatsudenryou_peakcut_all_snow).sum(); } // 결과 확인용 @@ -548,15 +553,21 @@ public class PwrGnrSimService { // Arrays.toString(hatsudenryou_peakcut_all_snow)); PwrGnrSimResponse pwrGnrSimRes = new PwrGnrSimResponse(); - // pwrGnrSimRes.setSekisairitsu(sekisairitsu); - pwrGnrSimRes.setFrcPwrGnrList(hatsudenryou_all); - // pwrGnrSimRes.setHatsudenryouAllSnow(hatsudenryou_all_snow); - // pwrGnrSimRes.setHatsudenryouPeakcutAll(hatsudenryou_peakcut_all); - // pwrGnrSimRes.setHatsudenryouPeakcutAllSnow(hatsudenryou_peakcut_all_snow); - + pwrGnrSimRes.setHatsudenryouAll(formatAndPrintArray(hatsudenryou_all)); + pwrGnrSimRes.setHatsudenryouAllSnow(formatAndPrintArray(hatsudenryou_all_snow)); + pwrGnrSimRes.setHatsudenryouPeakcutAll(formatAndPrintArray(hatsudenryou_peakcut_all)); + pwrGnrSimRes.setHatsudenryouPeakcutAllSnow(formatAndPrintArray(hatsudenryou_peakcut_all_snow)); return pwrGnrSimRes; } + // 배열 변환 및 포맷 처리 메서드 + private static String[] formatAndPrintArray(double[] doubleArray) { + return Arrays.stream(doubleArray) + .mapToInt(d -> (int) d) // double -> int 변환 + .mapToObj(i -> String.format("%,d", i)) + .toArray(String[]::new); // String[]로 변환 + } + // 설치면의 사면 일사량 계산 public static double[] peakcut( int simulationPointNumber, @@ -1372,6 +1383,18 @@ public class PwrGnrSimService { public static Document pwrGnrSimPdfHtml(Document doc, PwrGnrSimResponse data) throws IOException, QcastException { + + String[] pwrGnrSimList = new String[13]; + if ("A".equals(data.getPwrGnrSimType())) { + pwrGnrSimList = data.getHatsudenryouAll(); + } else if ("B".equals(data.getPwrGnrSimType())) { + pwrGnrSimList = data.getHatsudenryouAllSnow(); + } else if ("C".equals(data.getPwrGnrSimType())) { + pwrGnrSimList = data.getHatsudenryouPeakcutAll(); + } else if ("D".equals(data.getPwrGnrSimType())) { + pwrGnrSimList = data.getHatsudenryouPeakcutAllSnow(); + } + Element elm; // 상단 요약정보 @@ -1393,7 +1416,7 @@ public class PwrGnrSimService { elm.text(StringUtils.defaultString(data.getCapacity())); elm = doc.getElementById("anlFrcsGnrt"); - elm.text(StringUtils.defaultString(String.valueOf(data.getAnlFrcsGnrt()))); + elm.text(StringUtils.defaultString(String.valueOf(pwrGnrSimList[12]))); elm = doc.getElementById("snowfall"); elm.text(StringUtils.defaultString(data.getSnowfall())); @@ -1401,10 +1424,13 @@ public class PwrGnrSimService { elm = doc.getElementById("standardWindSpeedId"); elm.text(StringUtils.defaultString(data.getStandardWindSpeedId())); - if (data.getFrcPwrGnrList() != null && data.getFrcPwrGnrList().length > 0) { + boolean isUnchanged = Arrays.stream(pwrGnrSimList).allMatch(value -> value == "00"); + if (!isUnchanged) { // 변경된값 확인 int[] onlyData = - Arrays.copyOfRange(data.getFrcPwrGnrList(), 0, data.getFrcPwrGnrList().length - 1); + Arrays.stream(Arrays.copyOfRange(pwrGnrSimList, 0, pwrGnrSimList.length - 1)) + .mapToInt(Integer::parseInt) + .toArray(); int referenceValue = 300; // table 높이 int orgMaxValue = @@ -1485,28 +1511,27 @@ public class PwrGnrSimService { } // 예측발전량 - if (data.getFrcPwrGnrList() != null && data.getFrcPwrGnrList().length > 0) { - StringBuilder sb = new StringBuilder(); - for (int i = 0; i < 13; i++) { - sb.append( - "" - + StringUtils.defaultString(String.valueOf(data.getFrcPwrGnrList()[i])) - + ""); - } - - elm = doc.getElementById("frcPwrGnrList_detail"); - elm.append(sb.toString()); + StringBuilder sb = new StringBuilder(); + for (int i = 0; i < 13; i++) { + sb.append("" + StringUtils.defaultString(pwrGnrSimList[i]) + ""); } + elm = doc.getElementById("frcPwrGnrList_detail"); + elm.append(sb.toString()); + // 모듈 list if (data.getRoofModuleList() != null && data.getRoofModuleList().size() > 0) { - StringBuilder sb = new StringBuilder(); + sb = new StringBuilder(); for (int i = 0; i < data.getRoofModuleList().size(); i++) { PwrGnrSimRoofResponse listItem = data.getRoofModuleList().get(i); sb.append(""); sb.append("" + StringUtils.defaultString(listItem.getRoofSurface()) + ""); - sb.append("" + StringUtils.defaultString(listItem.getSlopeAngle()) + ""); + sb.append( + "" + + StringUtils.defaultString(listItem.getSlopeAngle()) + + (listItem.getClassType() == 0 ? "寸" : "º") + + ""); sb.append("" + StringUtils.defaultString(listItem.getAzimuth()) + ""); sb.append("" + StringUtils.defaultString(listItem.getItemNo()) + ""); sb.append("" + StringUtils.defaultString(listItem.getAmount()) + ""); @@ -1519,7 +1544,7 @@ public class PwrGnrSimService { // pcs list if (data.getPcsList() != null && data.getPcsList().size() > 0) { - StringBuilder sb = new StringBuilder(); + sb = new StringBuilder(); for (int i = 0; i < data.getPcsList().size(); i++) { PwrGnrSimRoofResponse listItem = data.getPcsList().get(i); diff --git a/src/main/java/com/interplug/qcast/biz/pwrGnrSimulation/dto/PwrGnrSimRequest.java b/src/main/java/com/interplug/qcast/biz/pwrGnrSimulation/dto/PwrGnrSimRequest.java index cb22305d..b87df87d 100644 --- a/src/main/java/com/interplug/qcast/biz/pwrGnrSimulation/dto/PwrGnrSimRequest.java +++ b/src/main/java/com/interplug/qcast/biz/pwrGnrSimulation/dto/PwrGnrSimRequest.java @@ -12,11 +12,8 @@ public class PwrGnrSimRequest { @Schema(description = "플랜번호") private String planNo; - // @Schema(description = "도도부현") - // private String prefecture; - // - // @Schema(description = "관측지점") - // private String simulationPoint; + @Schema(description = "list 종류") + private String pwrGnrSimType; @Schema(description = "관측지점 번호") private int simulationPointNumber; diff --git a/src/main/java/com/interplug/qcast/biz/pwrGnrSimulation/dto/PwrGnrSimResponse.java b/src/main/java/com/interplug/qcast/biz/pwrGnrSimulation/dto/PwrGnrSimResponse.java index 16bbf332..0ab67a65 100644 --- a/src/main/java/com/interplug/qcast/biz/pwrGnrSimulation/dto/PwrGnrSimResponse.java +++ b/src/main/java/com/interplug/qcast/biz/pwrGnrSimulation/dto/PwrGnrSimResponse.java @@ -9,18 +9,20 @@ public class PwrGnrSimResponse { @Schema(description = "적재율") private double sekisairitsu; - @Schema(description = "예측발전량 리스트") - private int[] frcPwrGnrList; + @Schema(description = "적설 고려 없음 (피크 컷 없음 발전량) Type : A") + private String[] hatsudenryouAll; - // - // @Schema(description = "") - // private double[] hatsudenryouAllSnow; - // - // @Schema(description = "") - // private double[] hatsudenryouPeakcutAll; - // - // @Schema(description = "") - // private double[] hatsudenryouPeakcutAllSnow; + @Schema(description = "적설 고려 있음 (피크 컷 없음 발전량) Type : B") + private String[] hatsudenryouAllSnow; + + @Schema(description = "적설 고려 없음 (피크 컷 있음 발전량) Type : C") + private String[] hatsudenryouPeakcutAll; + + @Schema(description = "적설 고려 있음 (피크 컷 있음 발전량) Type : D") + private String[] hatsudenryouPeakcutAllSnow; + + @Schema(description = "list 종류") + private String pwrGnrSimType; @Schema(description = "물건번호") private String objectNo; @@ -34,9 +36,6 @@ public class PwrGnrSimResponse { @Schema(description = "시스템용량") private String capacity; - @Schema(description = "연간예측발전량") - private int anlFrcsGnrt; - @Schema(description = "도도부현") private int prefId; diff --git a/src/main/java/com/interplug/qcast/biz/roofmaterial/RoofMaterialInfoController.java b/src/main/java/com/interplug/qcast/biz/roofmaterial/RoofMaterialInfoController.java deleted file mode 100644 index cb3f7ce6..00000000 --- a/src/main/java/com/interplug/qcast/biz/roofmaterial/RoofMaterialInfoController.java +++ /dev/null @@ -1,33 +0,0 @@ -package com.interplug.qcast.biz.roofmaterial; - -import com.interplug.qcast.biz.roofmaterial.dto.RoofMaterialInfoResponse; -import com.interplug.qcast.biz.trestle.dto.TrestleInfoResponse; -import io.swagger.v3.oas.annotations.Operation; -import io.swagger.v3.oas.annotations.tags.Tag; -import java.util.List; -import lombok.RequiredArgsConstructor; -import org.springframework.web.bind.annotation.GetMapping; -import org.springframework.web.bind.annotation.PathVariable; -import org.springframework.web.bind.annotation.RequestMapping; -import org.springframework.web.bind.annotation.RestController; - -@RestController -@RequiredArgsConstructor -@RequestMapping("/api/roof-material/roof-material-infos") -@Tag(name = "RoofMaterialInfoController", description = "지붕재 정보 API") -public class RoofMaterialInfoController { - private final RoofMaterialInfoService roofMaterialInfoService; - - @Operation(description = "지붕재 목록들을 조회한다.") - @GetMapping - public List getRoofMaterials() { - return roofMaterialInfoService.getRoofMaterials(); - } - - @Operation(description = "지붕재ID에 따라 설치 가능한 가대 목록을 가져온다.") - @GetMapping("/{roofMaterialId}/trestles") - public List getTrestlesByRoofMaterialId( - @PathVariable Integer roofMaterialId) { - return roofMaterialInfoService.getTrestlesByRoofMaterialId(roofMaterialId); - } -} diff --git a/src/main/java/com/interplug/qcast/biz/roofmaterial/RoofMaterialInfoMapper.java b/src/main/java/com/interplug/qcast/biz/roofmaterial/RoofMaterialInfoMapper.java deleted file mode 100644 index 8098ddcb..00000000 --- a/src/main/java/com/interplug/qcast/biz/roofmaterial/RoofMaterialInfoMapper.java +++ /dev/null @@ -1,10 +0,0 @@ -package com.interplug.qcast.biz.roofmaterial; - -import com.interplug.qcast.biz.roofmaterial.dto.RoofMaterialInfoResponse; -import java.util.List; -import org.apache.ibatis.annotations.Mapper; - -@Mapper -public interface RoofMaterialInfoMapper { - List getRoofMaterials(); -} diff --git a/src/main/java/com/interplug/qcast/biz/roofmaterial/RoofMaterialInfoService.java b/src/main/java/com/interplug/qcast/biz/roofmaterial/RoofMaterialInfoService.java deleted file mode 100644 index 4b115446..00000000 --- a/src/main/java/com/interplug/qcast/biz/roofmaterial/RoofMaterialInfoService.java +++ /dev/null @@ -1,23 +0,0 @@ -package com.interplug.qcast.biz.roofmaterial; - -import com.interplug.qcast.biz.roofmaterial.dto.RoofMaterialInfoResponse; -import com.interplug.qcast.biz.trestle.TrestleInfoService; -import com.interplug.qcast.biz.trestle.dto.TrestleInfoResponse; -import java.util.List; -import lombok.RequiredArgsConstructor; -import org.springframework.stereotype.Service; - -@Service -@RequiredArgsConstructor -public class RoofMaterialInfoService { - private final RoofMaterialInfoMapper roofMapper; - private final TrestleInfoService trestleInfoService; - - public List getRoofMaterials() { - return roofMapper.getRoofMaterials(); - } - - public List getTrestlesByRoofMaterialId(Integer roofMaterialId) { - return trestleInfoService.getTrestlesByRoofMaterialId(roofMaterialId); - } -} diff --git a/src/main/java/com/interplug/qcast/biz/roofmaterial/dto/RoofMaterialInfoResponse.java b/src/main/java/com/interplug/qcast/biz/roofmaterial/dto/RoofMaterialInfoResponse.java deleted file mode 100644 index 155367de..00000000 --- a/src/main/java/com/interplug/qcast/biz/roofmaterial/dto/RoofMaterialInfoResponse.java +++ /dev/null @@ -1,16 +0,0 @@ -package com.interplug.qcast.biz.roofmaterial.dto; - -import lombok.AllArgsConstructor; -import lombok.Getter; -import lombok.NoArgsConstructor; -import lombok.Setter; - -@Getter -@Setter -@NoArgsConstructor -@AllArgsConstructor -public class RoofMaterialInfoResponse { - - private Integer id; - private String name; -} diff --git a/src/main/java/com/interplug/qcast/biz/trestle/TrestleInfoMapper.java b/src/main/java/com/interplug/qcast/biz/trestle/TrestleInfoMapper.java deleted file mode 100644 index c124d5b1..00000000 --- a/src/main/java/com/interplug/qcast/biz/trestle/TrestleInfoMapper.java +++ /dev/null @@ -1,10 +0,0 @@ -package com.interplug.qcast.biz.trestle; - -import com.interplug.qcast.biz.trestle.dto.TrestleInfoResponse; -import java.util.List; -import org.apache.ibatis.annotations.Mapper; - -@Mapper -public interface TrestleInfoMapper { - List getTrestlesByRoofMaterialId(Integer roofMaterialId); -} diff --git a/src/main/java/com/interplug/qcast/biz/trestle/TrestleInfoService.java b/src/main/java/com/interplug/qcast/biz/trestle/TrestleInfoService.java deleted file mode 100644 index 03a69e9b..00000000 --- a/src/main/java/com/interplug/qcast/biz/trestle/TrestleInfoService.java +++ /dev/null @@ -1,17 +0,0 @@ -package com.interplug.qcast.biz.trestle; - -import com.interplug.qcast.biz.trestle.dto.TrestleInfoResponse; -import java.util.List; -import lombok.RequiredArgsConstructor; -import org.springframework.stereotype.Service; - -@Service -@RequiredArgsConstructor -public class TrestleInfoService { - - private final TrestleInfoMapper trestleMapper; - - public List getTrestlesByRoofMaterialId(Integer roofMaterialId) { - return trestleMapper.getTrestlesByRoofMaterialId(roofMaterialId); - } -} diff --git a/src/main/java/com/interplug/qcast/biz/trestle/dto/TrestleInfoResponse.java b/src/main/java/com/interplug/qcast/biz/trestle/dto/TrestleInfoResponse.java deleted file mode 100644 index 542d5035..00000000 --- a/src/main/java/com/interplug/qcast/biz/trestle/dto/TrestleInfoResponse.java +++ /dev/null @@ -1,17 +0,0 @@ -package com.interplug.qcast.biz.trestle.dto; - -import lombok.AllArgsConstructor; -import lombok.Getter; -import lombok.NoArgsConstructor; -import lombok.Setter; - -@Getter -@Setter -@AllArgsConstructor -@NoArgsConstructor -public class TrestleInfoResponse { - private Integer id; - private String name; - private Integer manufacturerId; - private String manufacturerName; -} diff --git a/src/main/java/com/interplug/qcast/util/ExcelUtil.java b/src/main/java/com/interplug/qcast/util/ExcelUtil.java index 37ed9e7b..bfc1c3df 100644 --- a/src/main/java/com/interplug/qcast/util/ExcelUtil.java +++ b/src/main/java/com/interplug/qcast/util/ExcelUtil.java @@ -3,9 +3,13 @@ package com.interplug.qcast.util; import com.fasterxml.jackson.databind.exc.InvalidFormatException; import jakarta.servlet.http.HttpServletRequest; import jakarta.servlet.http.HttpServletResponse; +import java.beans.BeanInfo; +import java.beans.Introspector; +import java.beans.PropertyDescriptor; import java.io.*; -import java.util.List; -import java.util.Map; +import java.lang.reflect.Field; +import java.lang.reflect.Method; +import java.util.*; import lombok.RequiredArgsConstructor; import lombok.extern.slf4j.Slf4j; import net.sf.jxls.exception.ParsePropertyException; @@ -18,6 +22,50 @@ import org.springframework.stereotype.Component; @RequiredArgsConstructor public class ExcelUtil { + /** + * jxls을 이용한 엑셀데이터 축출 + * + * @param request HttpServletRequest + * @param response HttpServletResponse + * @param map 엑셀 출력데이터 + * @param list 엑셀 출력 목록 데이터 + * @param templateFileName 템플릿 파일명 + * @throws ParsePropertyException + * @throws InvalidFormatException + */ + public byte[] download( + HttpServletRequest request, + HttpServletResponse response, + Map map, + List> list, + String templateFileName) + throws ParsePropertyException, InvalidFormatException { + + byte[] excelBytes = null; + + try { + + String templateFilePath = "template/excel/" + templateFileName; + InputStream templateStream = + PdfUtil.class.getClassLoader().getResourceAsStream(templateFilePath); + + try (InputStream is = new BufferedInputStream(templateStream)) { + Context context = new Context(); + context.putVar("data", map); + context.putVar("list", list); + + ByteArrayOutputStream byteArrayOutputStream = new ByteArrayOutputStream(); + JxlsHelper.getInstance().processTemplate(is, byteArrayOutputStream, context); + + excelBytes = byteArrayOutputStream.toByteArray(); + } + } catch (Exception e) { + log.debug(e.getMessage()); + } + + return excelBytes; + } + /** * jxls을 이용한 엑셀다운로드 * @@ -26,7 +74,7 @@ public class ExcelUtil { * @param map 엑셀 출력데이터 * @param list 엑셀 출력 목록 데이터 * @param fileName 다운로드 파일명 - * @param templateFileName + * @param templateFileName 템플릿 파일명 * @throws ParsePropertyException * @throws InvalidFormatException */ @@ -60,4 +108,58 @@ public class ExcelUtil { log.debug(e.getMessage()); } } + + /** + * Object => Map 변환 함수 + * + * @param vo Object + * @return Map Map 변환 정보 + */ + public Map convertVoToMap(Object vo) { + Map result = new HashMap(); + + try { + BeanInfo info = Introspector.getBeanInfo(vo.getClass()); + for (PropertyDescriptor pd : info.getPropertyDescriptors()) { + Method reader = pd.getReadMethod(); + if (reader != null) { + result.put(pd.getName(), reader.invoke(vo)); + } + } + } catch (Exception e) { + log.error("convertVoToMap >>> " + e.getMessage()); + } + return result; + } + + /** + * List => List 변환 함수 + * + * @param target List + * @return List> List 변환 정보 + */ + public static List> convertListToMap(Collection target) { + List> resultList = new ArrayList>(); + + for (T element : target) { + Map resultMap = new HashMap(); + Field[] fieldList = element.getClass().getDeclaredFields(); + if (fieldList != null && fieldList.length > 0) { + try { + for (int i = 0; i < fieldList.length; i++) { + String curInsName = fieldList[i].getName(); + Field field = element.getClass().getDeclaredField(curInsName); + field.setAccessible(true); + Object targetValue = field.get(element); + + resultMap.put(curInsName, targetValue); + } + resultList.add(resultMap); + } catch (Exception e) { + log.error("convertListToMap >>> " + e.getMessage()); + } + } + } + return resultList; + } } diff --git a/src/main/resources/config/application-dev.yml b/src/main/resources/config/application-dev.yml index 8542fa29..a40b715d 100644 --- a/src/main/resources/config/application-dev.yml +++ b/src/main/resources/config/application-dev.yml @@ -51,6 +51,8 @@ qsp: auto.login.aes256.key: _autoL!! system-commonCode-batch-url: /api/system/commonCodeListData master-special-note-disp-item-batch-url: /api/master/quotationDispItemInfo + estimate-plan-confirm-batch-url: /api/order/planConfirmListData + estimate-sync-batch-url: /api/order/qcastQuotationSave #File file: root.path: C:\\ diff --git a/src/main/resources/config/application-local.yml b/src/main/resources/config/application-local.yml index 7ed6345e..d8500c4c 100644 --- a/src/main/resources/config/application-local.yml +++ b/src/main/resources/config/application-local.yml @@ -39,7 +39,7 @@ spring: #QSP qsp: - url: http://1.248.227.176:8120 + url: http://localhost:8120 master-store-batch-url: /api/master/storeAdditionalInfo master-material-batch-url: /api/master/materialList master-bom-batch-url: /api/master/bomList @@ -51,6 +51,8 @@ qsp: auto.login.aes256.key: _autoL!! system-commonCode-batch-url: /api/system/commonCodeListData master-special-note-disp-item-batch-url: /api/master/quotationDispItemInfo + estimate-plan-confirm-batch-url: /api/order/planConfirmListData + estimate-sync-batch-url: /api/order/qcastQuotationSave #File file: root.path: C:\\ diff --git a/src/main/resources/config/application-prd.yml b/src/main/resources/config/application-prd.yml index c620bc40..351d2dd3 100644 --- a/src/main/resources/config/application-prd.yml +++ b/src/main/resources/config/application-prd.yml @@ -51,6 +51,8 @@ qsp: auto.login.aes256.key: _autoL!! system-commonCode-batch-url: /api/system/commonCodeListData master-special-note-disp-item-batch-url: /api/master/quotationDispItemInfo + estimate-plan-confirm-batch-url: /api/order/planConfirmListData + estimate-sync-batch-url: /api/order/qcastQuotationSave #File file: root.path: C:\\ diff --git a/src/main/resources/mappers/displayItem/displayItemMapper.xml b/src/main/resources/mappers/displayItem/displayItemMapper.xml index 22c63523..157836c3 100644 --- a/src/main/resources/mappers/displayItem/displayItemMapper.xml +++ b/src/main/resources/mappers/displayItem/displayItemMapper.xml @@ -181,6 +181,10 @@ , GUAR_EXCEPT_FLG = CASE WHEN #{guarExceptFlg} = 'FALSE' THEN 0 ELSE 1 END , COLD_ZONE_FLG = CASE WHEN #{coldZoneFlg} = 'FALSE' THEN 0 ELSE 1 END , PKG_MATERIAL_FLG = CASE WHEN #{pkgMaterialFlg} = 'FALSE' THEN 0 ELSE 1 END + , TEMP_LOSS = #{tempLoss} + , TEMP_COEFF = #{tempCoeff} + , AMP = #{amp} + , CNV_EFF = #{cnvEff} , LAST_EDIT_DATETIME = GETDATE() WHEN NOT MATCHED THEN INSERT ( @@ -225,6 +229,10 @@ , GUAR_EXCEPT_FLG , COLD_ZONE_FLG , PKG_MATERIAL_FLG + , TEMP_LOSS + , TEMP_COEFF + , AMP + , CNV_EFF , LAST_EDIT_DATETIME ) VALUES ( #{itemId} @@ -268,6 +276,10 @@ , CASE WHEN #{guarExceptFlg} = 'FALSE' THEN 0 ELSE 1 END , CASE WHEN #{coldZoneFlg} = 'FALSE' THEN 0 ELSE 1 END , CASE WHEN #{pkgMaterialFlg} = 'FALSE' THEN 0 ELSE 1 END + , #{tempLoss} + , #{tempCoeff} + , #{amp} + , #{cnvEff} , GETDATE() ); diff --git a/src/main/resources/mappers/estimate/estimateMapper.xml b/src/main/resources/mappers/estimate/estimateMapper.xml index 3b1c8d38..62ddbfc6 100644 --- a/src/main/resources/mappers/estimate/estimateMapper.xml +++ b/src/main/resources/mappers/estimate/estimateMapper.xml @@ -119,6 +119,49 @@ ON T.CREATE_SALE_STORE_ID = SS2.SALE_STORE_ID + + + + + + - SELECT B.ID - , B.NAME - FROM TB_MAP_ROOF_MATERIAL_TRESTLE_MODULE A - JOIN TB_MODULE B - ON A.MODULE_ID = B.ID - WHERE A.ROOF_MATERIAL_ID = #{roofMaterialId} - AND A.TRESTLE_ID = #{trestleId} - - \ No newline at end of file diff --git a/src/main/resources/mappers/object/objectMapper.xml b/src/main/resources/mappers/object/objectMapper.xml index 3d890072..3a7ce3dc 100644 --- a/src/main/resources/mappers/object/objectMapper.xml +++ b/src/main/resources/mappers/object/objectMapper.xml @@ -213,7 +213,8 @@ INNER JOIN SALES_STORE_CTE T ON S.SALE_STORE_ID = T.SALE_STORE_ID - WHERE (O.DEL_FLG = '0' OR (O.TEMP_FLG = '1' AND O.TEMP_DEL_FLG = '0')) + WHERE O.SOURCE_ORIGIN = 'QCAST_III' + AND (O.ORG_DEL_FLG = '0' OR (O.TEMP_FLG = '1' AND O.TEMP_DEL_FLG = '0')) AND O.OBJECT_NO LIKE '%' + #{schObjectNo} + '%' @@ -316,7 +317,8 @@ LEFT OUTER JOIN M_PREFECTURE_AREA PA ON O.AREA_ID = PA.AREA_ID WHERE O.OBJECT_NO = #{objectNo} - AND (O.DEL_FLG = '0' OR (O.TEMP_FLG = '1' AND O.TEMP_DEL_FLG = '0')) + AND O.SOURCE_ORIGIN = 'QCAST_III' + AND (O.ORG_DEL_FLG = '0' OR (O.TEMP_FLG = '1' AND O.TEMP_DEL_FLG = '0')) - SELECT ID - , NAME - FROM TB_ROOF_MATERIAL - - \ No newline at end of file diff --git a/src/main/resources/mappers/trestle/TrestleInfoMapper.xml b/src/main/resources/mappers/trestle/TrestleInfoMapper.xml deleted file mode 100644 index 6b1ca1f3..00000000 --- a/src/main/resources/mappers/trestle/TrestleInfoMapper.xml +++ /dev/null @@ -1,18 +0,0 @@ - - - - - - \ No newline at end of file diff --git a/src/main/resources/template/excel/excel_download_quotation_detail_template.xlsx b/src/main/resources/template/excel/excel_download_quotation_detail_template.xlsx index e7d0fac3..325d7ff7 100644 Binary files a/src/main/resources/template/excel/excel_download_quotation_detail_template.xlsx and b/src/main/resources/template/excel/excel_download_quotation_detail_template.xlsx differ