구매요청_품의서관리 결재완료시 -> 구매관리_품의서관리에,, 그 후 프로세스 통합

This commit is contained in:
2026-01-19 16:41:44 +09:00
parent 8d14504861
commit f3823dae40
7 changed files with 796 additions and 61 deletions

View File

@@ -879,10 +879,15 @@
SELECT
SRP.OBJID,
SRP.PART_OBJID,
SRP.QTY,
COALESCE(SRP.PO_QTY, SRP.QTY::NUMERIC, 0) AS ORDER_QTY, -- 발주수량 (PO_QTY 우선, 없으면 QTY)
SRP.UNIT_PRICE AS PARTNER_PRICE,
SRP.TOTAL_PRICE,
COALESCE(NULLIF(SRP.QTY::VARCHAR, ''), '0') AS QTY,
-- 발주수량: PO_QTY가 있고 0보다 크면 사용, 아니면 QTY 사용
CASE
WHEN SRP.PO_QTY IS NOT NULL AND SRP.PO_QTY::NUMERIC > 0 THEN SRP.PO_QTY::VARCHAR
WHEN SRP.QTY IS NOT NULL THEN SRP.QTY::VARCHAR
ELSE '0'
END AS ORDER_QTY,
COALESCE(SRP.UNIT_PRICE, 0) AS PARTNER_PRICE,
COALESCE(SRP.TOTAL_PRICE, 0) AS TOTAL_PRICE,
SRP.VENDOR_PM AS PARTNER_OBJID,
PM.PART_NO,
PM.PART_NAME,
@@ -3317,7 +3322,7 @@ SELECT POM.OBJID
ON POM.CONTRACT_MGMT_OBJID = CM.OBJID
left outer join SALES_REQUEST_MASTER as SRM
on POM.SALES_REQUEST_OBJID = SRM.OBJID
and SRM.DOC_TYPE = 'PROPOSAL'
and SRM.DOC_TYPE IN ('PROPOSAL', 'PURCHASE_REG_PROPOSAL')
<!-- 230907 outer join으로 변경
,PROJECT_MGMT AS CM
WHERE POM.CONTRACT_MGMT_OBJID = CM.OBJID

View File

@@ -721,7 +721,8 @@ VALUES
COALESCE(NULLIF(SRM.AREA_CD, ''), SM.AREA_CD) AS AREA_CD, -- 국내/해외
COALESCE(NULLIF(SRM.CUSTOMER_OBJID, ''), SM.OBJID::VARCHAR) AS CUSTOMER_OBJID, -- 고객사
COALESCE(NULLIF(SRM.PAID_TYPE, ''), CM.PAID_TYPE) AS PAID_TYPE, -- 유/무상
CM.CATEGORY_CD AS CATEGORY_CD -- 제품유형 코드 ID (드롭다운 선택용)
CM.CATEGORY_CD AS CATEGORY_CD, -- 제품유형 코드 ID (드롭다운 선택용)
SRM.DOC_TYPE -- 문서유형 (PURCHASE_REQUEST, PURCHASE_REG, PROPOSAL 등)
-- 품번/품명: 첫 번째 품목 + 외 N건 형태
<!-- (SELECT
CASE
@@ -3484,7 +3485,7 @@ ORDER BY V.PATH2
<select id="getNextProposalNo" resultType="string">
SELECT 'P'||TO_CHAR(NOW(),'YYYYMMDD')||'-'||LPAD((COALESCE(MAX(SUBSTR(REQUEST_MNG_NO,11,3))::INTEGER, 0)+1)::TEXT,3,'0')
FROM SALES_REQUEST_MASTER
WHERE DOC_TYPE = 'PROPOSAL'
WHERE DOC_TYPE IN ('PROPOSAL', 'PURCHASE_REG_PROPOSAL')
AND REQUEST_MNG_NO LIKE 'P'||TO_CHAR(NOW(),'YYYYMMDD')||'%'
</select>
@@ -3789,7 +3790,7 @@ ORDER BY V.PATH2
'create',
#{WRITER},
NOW(),
'PROPOSAL'
#{DOC_TYPE}
)
</insert>
@@ -4108,7 +4109,11 @@ ORDER BY V.PATH2
) A ON SRM.OBJID::VARCHAR = A.TARGET_OBJID::VARCHAR
WHERE 1=1
AND SRM.STATUS IN ('create', 'approvalRequest', 'approvalComplete', 'reject')
AND SRM.DOC_TYPE = 'PROPOSAL'
<!-- PROPOSAL은 모두 조회, PURCHASE_REG_PROPOSAL은 결재완료만 조회 -->
AND (
SRM.DOC_TYPE = 'PROPOSAL'
OR (SRM.DOC_TYPE = 'PURCHASE_REG_PROPOSAL' AND A.ROUTE_STATUS = 'complete')
)
<if test="SEARCH_PROPOSAL_NO != null and !''.equals(SEARCH_PROPOSAL_NO)">
AND SRM.REQUEST_MNG_NO LIKE '%${SEARCH_PROPOSAL_NO}%'
</if>
@@ -4138,6 +4143,130 @@ ORDER BY V.PATH2
ORDER BY SRM.REGDATE DESC
</select>
<!-- 구매요청_품의서 목록 조회 (PURCHASE_REG_PROPOSAL) -->
<select id="getPurchaseRegProposalMngGridList" parameterType="map" resultType="map">
SELECT
SRM.OBJID,
SRM.REQUEST_MNG_NO AS PROPOSAL_NO,
SRM.PROJECT_NO,
(SELECT PROJECT_NO FROM PROJECT_MGMT PM WHERE PM.OBJID = SRM.PROJECT_NO) AS PROJECT_NUMBER,
SRM.PURCHASE_TYPE,
(SELECT CODE_NAME FROM COMM_CODE CC WHERE CC.CODE_ID = SRM.PURCHASE_TYPE) AS PURCHASE_TYPE_NAME,
COALESCE(
(SELECT PM.CATEGORY_CD FROM PROJECT_MGMT PM WHERE PM.OBJID::VARCHAR = SRM.PROJECT_NO),
SRM.ORDER_TYPE
) AS ORDER_TYPE,
CODE_NAME(COALESCE(
(SELECT PM.CATEGORY_CD FROM PROJECT_MGMT PM WHERE PM.OBJID::VARCHAR = SRM.PROJECT_NO),
SRM.ORDER_TYPE
)) AS ORDER_TYPE_NAME,
SRM.PRODUCT_NAME,
CODE_NAME(SRM.PRODUCT_NAME) AS PRODUCT_NAME_TITLE,
(
SELECT
CASE
WHEN COUNT(*) > 1 THEN
COALESCE((SELECT PM.PART_NO FROM PART_MNG PM WHERE PM.OBJID::VARCHAR = (SELECT PART_OBJID FROM SALES_REQUEST_PART WHERE SALES_REQUEST_MASTER_OBJID = SRM.OBJID ORDER BY REGDATE LIMIT 1)), '') || ' 외 ' || (COUNT(*) - 1)::TEXT || '건'
ELSE
COALESCE((SELECT PM.PART_NO FROM PART_MNG PM WHERE PM.OBJID::VARCHAR = (SELECT PART_OBJID FROM SALES_REQUEST_PART WHERE SALES_REQUEST_MASTER_OBJID = SRM.OBJID ORDER BY REGDATE LIMIT 1)), '')
END
FROM SALES_REQUEST_PART
WHERE SALES_REQUEST_MASTER_OBJID = SRM.OBJID
) AS PART_NO,
(
SELECT
CASE
WHEN COUNT(*) > 1 THEN
COALESCE((SELECT PM.PART_NAME FROM PART_MNG PM WHERE PM.OBJID::VARCHAR = (SELECT PART_OBJID FROM SALES_REQUEST_PART WHERE SALES_REQUEST_MASTER_OBJID = SRM.OBJID ORDER BY REGDATE LIMIT 1)), '') || ' 외 ' || (COUNT(*) - 1)::TEXT || '건'
ELSE
COALESCE((SELECT PM.PART_NAME FROM PART_MNG PM WHERE PM.OBJID::VARCHAR = (SELECT PART_OBJID FROM SALES_REQUEST_PART WHERE SALES_REQUEST_MASTER_OBJID = SRM.OBJID ORDER BY REGDATE LIMIT 1)), '')
END
FROM SALES_REQUEST_PART
WHERE SALES_REQUEST_MASTER_OBJID = SRM.OBJID
) AS PART_NAME,
CASE
WHEN A.ROUTE_STATUS = 'complete' THEN 'approvalComplete'
WHEN A.ROUTE_STATUS = 'inProcess' THEN 'inProcess'
WHEN A.ROUTE_STATUS = 'reject' THEN 'reject'
ELSE SRM.STATUS
END AS STATUS,
CASE
WHEN A.APPR_STATUS IS NOT NULL THEN A.APPR_STATUS
WHEN SRM.STATUS = 'create' THEN '작성중'
ELSE ''
END AS STATUS_TITLE,
SRM.WRITER,
(SELECT DEPT_NAME||' '||USER_NAME FROM USER_INFO WHERE USER_ID = SRM.WRITER) AS WRITER_NAME,
SRM.REGDATE,
TO_CHAR(SRM.REGDATE,'YYYY-MM-DD') AS REGDATE_TITLE,
A.APPROVAL_OBJID,
A.ROUTE_OBJID
FROM
SALES_REQUEST_MASTER SRM
LEFT OUTER JOIN (
SELECT
B.OBJID AS ROUTE_OBJID,
B.STATUS AS ROUTE_STATUS,
CASE B.STATUS
WHEN 'inProcess' THEN '결재중'
WHEN 'complete' THEN '결재완료'
WHEN 'reject' THEN '반려'
ELSE ''
END APPR_STATUS,
A.OBJID AS APPROVAL_OBJID,
A.TARGET_OBJID,
B.ROUTE_SEQ
FROM
APPROVAL A,
(
SELECT
T1.*
FROM
(
SELECT
TARGET_OBJID,
MAX(T.ROUTE_SEQ) AS ROUTE_SEQ
FROM
ROUTE T
GROUP BY
T.TARGET_OBJID
) T,
ROUTE T1
WHERE
T.TARGET_OBJID = T1.TARGET_OBJID
AND T.ROUTE_SEQ = T1.ROUTE_SEQ
) B
WHERE A.OBJID = B.APPROVAL_OBJID
AND TARGET_TYPE IN ('PROPOSAL', 'SALES_REQUEST')
) A ON SRM.OBJID::VARCHAR = A.TARGET_OBJID::VARCHAR
WHERE 1=1
AND SRM.STATUS IN ('create', 'approvalRequest', 'approvalComplete', 'reject')
AND SRM.DOC_TYPE = 'PURCHASE_REG_PROPOSAL'
<if test="SEARCH_PROPOSAL_NO != null and !''.equals(SEARCH_PROPOSAL_NO)">
AND SRM.REQUEST_MNG_NO LIKE '%${SEARCH_PROPOSAL_NO}%'
</if>
<if test="SEARCH_PROJECT_NO != null and !''.equals(SEARCH_PROJECT_NO)">
AND (SELECT PROJECT_NO FROM PROJECT_MGMT PM WHERE PM.OBJID = SRM.PROJECT_NO) LIKE '%${SEARCH_PROJECT_NO}%'
</if>
<if test="SEARCH_STATUS != null and !''.equals(SEARCH_STATUS)">
AND (
CASE
WHEN A.ROUTE_STATUS = 'complete' THEN 'approvalComplete'
WHEN A.ROUTE_STATUS = 'inProcess' THEN 'inProcess'
WHEN A.ROUTE_STATUS = 'reject' THEN 'reject'
ELSE SRM.STATUS
END
) = #{SEARCH_STATUS}
</if>
<if test="regdate_start != null and !''.equals(regdate_start)">
AND SRM.REGDATE::DATE <![CDATA[ >= ]]> #{regdate_start}::DATE
</if>
<if test="regdate_end != null and !''.equals(regdate_end)">
AND SRM.REGDATE::DATE <![CDATA[ <= ]]> #{regdate_end}::DATE
</if>
ORDER BY SRM.REGDATE DESC
</select>
<!-- 품의서 상세 조회 -->
<select id="getProposalInfo" parameterType="map" resultType="map">
SELECT
@@ -4693,4 +4822,164 @@ ORDER BY V.PATH2
WHERE OBJID = #{QUOTATION_REQUEST_MASTER_OBJID}::NUMERIC
</update>
<!-- ==================== 구매요청서 품의서 생성 (PURCHASE_REG 전용) ==================== -->
<!-- 구매요청서 품의서 대상 품목 조회 (단가+공급업체 입력, 품의서 미생성) -->
<select id="getProposalTargetPartsFromPurchaseReg" parameterType="map" resultType="com.pms.common.UpperKeyMap">
SELECT
SRP.OBJID,
SRP.PART_OBJID,
PM.PART_NO,
PM.PART_NAME,
SRP.QTY,
COALESCE(SRP.UNIT_PRICE, NULLIF(SRP.PARTNER_PRICE, '')::NUMERIC, 0) AS UNIT_PRICE,
SRP.TOTAL_PRICE,
COALESCE(SRP.VENDOR_PM, SRP.PARTNER_OBJID) AS VENDOR_PM,
CASE
WHEN COALESCE(SRP.VENDOR_PM, SRP.PARTNER_OBJID) LIKE 'C_%' THEN (SELECT CLIENT_NM FROM CLIENT_MNG WHERE 'C_' || OBJID::VARCHAR = COALESCE(SRP.VENDOR_PM, SRP.PARTNER_OBJID))
ELSE (SELECT SUPPLY_NAME FROM ADMIN_SUPPLY_MNG WHERE OBJID::VARCHAR = COALESCE(SRP.VENDOR_PM, SRP.PARTNER_OBJID))
END AS VENDOR_NAME,
SRP.NET_QTY,
SRP.PO_QTY
FROM
SALES_REQUEST_PART SRP
LEFT JOIN PART_MNG PM ON SRP.PART_OBJID::VARCHAR = PM.OBJID::VARCHAR
WHERE
SRP.SALES_REQUEST_MASTER_OBJID = #{SALES_REQUEST_MASTER_OBJID}
-- 단가가 입력되어 있고 (UNIT_PRICE 또는 PARTNER_PRICE)
AND (
(SRP.UNIT_PRICE IS NOT NULL AND SRP.UNIT_PRICE > 0)
OR (SRP.PARTNER_PRICE IS NOT NULL AND SRP.PARTNER_PRICE != '' AND SRP.PARTNER_PRICE::NUMERIC > 0)
)
-- 공급업체가 입력되어 있고 (VENDOR_PM 또는 PARTNER_OBJID)
AND (
(SRP.VENDOR_PM IS NOT NULL AND SRP.VENDOR_PM != '')
OR (SRP.PARTNER_OBJID IS NOT NULL AND SRP.PARTNER_OBJID != '')
)
-- 품의서가 생성되지 않은 품목만
AND SRP.PROPOSAL_DATE IS NULL
ORDER BY SRP.REGDATE
</select>
<!-- 구매요청서 품의서 제외 품목 조회 (단가O, 공급업체X) -->
<select id="getProposalExcludedPartsFromPurchaseReg" parameterType="map" resultType="com.pms.common.UpperKeyMap">
SELECT
SRP.OBJID,
SRP.PART_OBJID,
PM.PART_NO,
PM.PART_NAME,
SRP.QTY,
COALESCE(SRP.UNIT_PRICE, NULLIF(SRP.PARTNER_PRICE, '')::NUMERIC, 0) AS UNIT_PRICE
FROM
SALES_REQUEST_PART SRP
LEFT JOIN PART_MNG PM ON SRP.PART_OBJID::VARCHAR = PM.OBJID::VARCHAR
WHERE
SRP.SALES_REQUEST_MASTER_OBJID = #{SALES_REQUEST_MASTER_OBJID}
-- 단가가 입력되어 있지만 (UNIT_PRICE 또는 PARTNER_PRICE)
AND (
(SRP.UNIT_PRICE IS NOT NULL AND SRP.UNIT_PRICE > 0)
OR (SRP.PARTNER_PRICE IS NOT NULL AND SRP.PARTNER_PRICE != '' AND SRP.PARTNER_PRICE::NUMERIC > 0)
)
-- 공급업체가 없는 품목 (VENDOR_PM, PARTNER_OBJID 둘 다 없음)
AND (SRP.VENDOR_PM IS NULL OR SRP.VENDOR_PM = '')
AND (SRP.PARTNER_OBJID IS NULL OR SRP.PARTNER_OBJID = '')
-- 품의서가 생성되지 않은 품목만
AND SRP.PROPOSAL_DATE IS NULL
ORDER BY SRP.REGDATE
</select>
<!-- 구매요청서 품의서 생성 (SALES_REQUEST_MASTER에 INSERT) -->
<insert id="insertProposalFromPurchaseReg" parameterType="map">
INSERT INTO SALES_REQUEST_MASTER (
OBJID,
REQUEST_MNG_NO,
PROJECT_NO,
PURCHASE_TYPE,
ORDER_TYPE,
PRODUCT_NAME,
AREA_CD,
CUSTOMER_OBJID,
PAID_TYPE,
REQUEST_USER_ID,
DELIVERY_REQUEST_DATE,
STATUS,
WRITER,
REGDATE,
DOC_TYPE
) VALUES (
#{OBJID},
#{REQUEST_MNG_NO},
#{PROJECT_NO},
#{PURCHASE_TYPE},
#{ORDER_TYPE},
#{PRODUCT_NAME},
#{AREA_CD},
#{CUSTOMER_OBJID},
#{PAID_TYPE},
#{REQUEST_USER_ID},
#{DELIVERY_REQUEST_DATE},
'create',
#{WRITER},
NOW(),
'PURCHASE_REG_PROPOSAL'
)
</insert>
<!-- 구매요청서 품의서용 SALES_REQUEST_PART 생성 (품목 복사) -->
<insert id="insertProposalPartFromPurchaseReg" parameterType="map">
INSERT INTO SALES_REQUEST_PART (
OBJID,
SALES_REQUEST_MASTER_OBJID,
PART_OBJID,
QTY,
UNIT_PRICE,
TOTAL_PRICE,
VENDOR_PM,
NET_QTY,
PO_QTY,
USE_YN,
PROPOSAL_DATE,
WRITER,
REGDATE
)
SELECT
#{NEW_OBJID},
#{PROPOSAL_MASTER_OBJID},
PART_OBJID,
QTY,
CASE
WHEN UNIT_PRICE IS NOT NULL AND UNIT_PRICE > 0 THEN UNIT_PRICE
WHEN PARTNER_PRICE IS NOT NULL AND PARTNER_PRICE != '' THEN PARTNER_PRICE::NUMERIC
ELSE 0
END AS UNIT_PRICE,
CASE
WHEN TOTAL_PRICE IS NOT NULL AND TOTAL_PRICE > 0 THEN TOTAL_PRICE
ELSE COALESCE(QTY::NUMERIC, 0) *
CASE
WHEN UNIT_PRICE IS NOT NULL AND UNIT_PRICE > 0 THEN UNIT_PRICE
WHEN PARTNER_PRICE IS NOT NULL AND PARTNER_PRICE != '' THEN PARTNER_PRICE::NUMERIC
ELSE 0
END
END AS TOTAL_PRICE,
COALESCE(NULLIF(VENDOR_PM, ''), PARTNER_OBJID) AS VENDOR_PM,
NET_QTY,
COALESCE(QTY::NUMERIC, 0) AS PO_QTY, -- 발주수량에 QTY 값 저장
USE_YN,
NOW() AS PROPOSAL_DATE,
#{WRITER},
NOW()
FROM SALES_REQUEST_PART
WHERE OBJID = #{SOURCE_OBJID}
</insert>
<!-- 구매요청서 품의서 생성 후 원본 PROPOSAL_DATE 업데이트 -->
<update id="updateProposalDateForPurchaseRegParts" parameterType="map">
UPDATE SALES_REQUEST_PART
SET PROPOSAL_DATE = NOW()
WHERE OBJID IN
<foreach collection="PART_OBJIDS" item="objid" open="(" separator="," close=")">
#{objid}
</foreach>
</update>
</mapper>

View File

@@ -1337,6 +1337,24 @@ public class SalesMngController {
return paramMap;
}
/**
* 구매요청_품의서 관리 - 목록 화면
*/
@RequestMapping("/salesMng/purchaseRegProposalMngList.do")
public String purchaseRegProposalMngList(HttpServletRequest request, @RequestParam Map paramMap){
return "/salesMng/purchaseRegProposalMngList";
}
/**
* 구매요청_품의서 관리 - 목록 조회 (페이징)
*/
@ResponseBody
@RequestMapping("/salesMng/purchaseRegProposalMngGridList.do")
public Map getPurchaseRegProposalMngGridList(HttpServletRequest request, @RequestParam Map<String, Object> paramMap){
commonService.selectListPagingNew("salesMng.getPurchaseRegProposalMngGridList", request, paramMap);
return paramMap;
}
/**
* 품의서 상세 팝업
* @param request
@@ -1783,4 +1801,22 @@ public class SalesMngController {
public Map sendQuotationRequestMail(HttpServletRequest request, @RequestParam Map<String, Object> paramMap){
return salesMngService.sendQuotationRequestMail(request, paramMap);
}
/**
* 구매요청서 품의서 대상 품목 조회
*/
@ResponseBody
@RequestMapping("/salesMng/getProposalTargetPartsFromPurchaseReg.do")
public Map getProposalTargetPartsFromPurchaseReg(HttpServletRequest request, @RequestParam Map<String, Object> paramMap){
return salesMngService.getProposalTargetPartsFromPurchaseReg(request, paramMap);
}
/**
* 구매요청서 품의서 생성
*/
@ResponseBody
@RequestMapping("/salesMng/createProposalFromPurchaseReg.do")
public Map createProposalFromPurchaseReg(HttpServletRequest request, @RequestParam Map<String, Object> paramMap){
return salesMngService.createProposalFromPurchaseReg(request, paramMap);
}
}

View File

@@ -13,6 +13,7 @@ import java.io.FileInputStream;
import java.util.ArrayList;
import java.util.Date;
import java.util.HashMap;
import java.util.LinkedHashMap;
import java.util.List;
import java.util.Map;
@@ -1974,6 +1975,10 @@ public class SalesMngService {
List<Map> materialExcludedParts = null; // 소재 제외 (공급업체 미입력)
List<Map> processingExcludedParts = null; // 가공 제외 (가공업체 미입력)
// DOC_TYPE 확인 (PURCHASE_REG는 가공 컬럼이 없음)
String docType = CommonUtils.checkNull(purchaseRequestInfo.get("DOC_TYPE"));
boolean isPurchaseReg = "PURCHASE_REG".equals(docType);
if(!mbomHeaderObjid.isEmpty()) {
// M-BOM 기반 -> MBOM_DETAIL에서 조회
Map mbomParam = new HashMap();
@@ -1992,9 +1997,14 @@ public class SalesMngService {
materialTargetParts = sqlSession.selectList("salesMng.getProposalTargetPartsFromManual", paramMap);
materialExcludedParts = sqlSession.selectList("salesMng.getProposalExcludedPartsFromManual", paramMap);
// 가공 품의서 대상
processingTargetParts = sqlSession.selectList("salesMng.getProposalTargetPartsFromManualProcessing", paramMap);
processingExcludedParts = sqlSession.selectList("salesMng.getProposalExcludedPartsFromManualProcessing", paramMap);
// 가공 품의서 대상 (PURCHASE_REG는 가공 컬럼이 없으므로 제외)
if(!isPurchaseReg) {
processingTargetParts = sqlSession.selectList("salesMng.getProposalTargetPartsFromManualProcessing", paramMap);
processingExcludedParts = sqlSession.selectList("salesMng.getProposalExcludedPartsFromManualProcessing", paramMap);
} else {
processingTargetParts = new ArrayList<Map>();
processingExcludedParts = new ArrayList<Map>();
}
}
materialTargetParts = CommonUtils.keyChangeUpperList(materialTargetParts);
@@ -2138,6 +2148,11 @@ public class SalesMngService {
proposalMaster.put("WRITER", userId);
proposalMaster.put("PROPOSAL_TYPE", proposalType); // 소재/가공 구분
// 원본 DOC_TYPE에 따라 품의서 DOC_TYPE 결정
String sourceDocType = CommonUtils.checkNull(purchaseRequestInfo.get("DOC_TYPE"));
String proposalDocType = "PURCHASE_REG".equals(sourceDocType) ? "PURCHASE_REG_PROPOSAL" : "PROPOSAL";
proposalMaster.put("DOC_TYPE", proposalDocType);
sqlSession.insert("salesMng.insertProposal", proposalMaster);
// 3. 품의서용 SALES_REQUEST_PART 생성 (대상 품목 복사)
@@ -2701,4 +2716,176 @@ public class SalesMngService {
return resultMap;
}
/**
* 구매요청서 품의서 대상 품목 조회
*/
public Map getProposalTargetPartsFromPurchaseReg(HttpServletRequest request, Map paramMap) {
SqlSession sqlSession = null;
Map resultMap = new HashMap();
try {
sqlSession = SqlMapConfig.getInstance().getSqlSession();
String salesRequestMasterObjid = CommonUtils.checkNull(paramMap.get("SALES_REQUEST_MASTER_OBJID"));
Map param = new HashMap();
param.put("SALES_REQUEST_MASTER_OBJID", salesRequestMasterObjid);
// 대상 품목 조회
List<Map> targetParts = sqlSession.selectList("salesMng.getProposalTargetPartsFromPurchaseReg", param);
// 제외 품목 조회 (공급업체 미입력)
List<Map> excludedParts = sqlSession.selectList("salesMng.getProposalExcludedPartsFromPurchaseReg", param);
if(targetParts != null && !targetParts.isEmpty()) {
resultMap.put("resultFlag", "S");
resultMap.put("data", targetParts);
resultMap.put("excludedParts", excludedParts);
} else {
resultMap.put("resultFlag", "F");
resultMap.put("message", "품의서 생성 대상 품목이 없습니다.\n(단가+공급업체 입력, 품의서 미생성 품목만 대상)");
resultMap.put("excludedParts", excludedParts);
}
} catch(Exception e) {
e.printStackTrace();
resultMap.put("resultFlag", "F");
resultMap.put("message", "조회 중 오류가 발생했습니다: " + e.getMessage());
} finally {
if(sqlSession != null) sqlSession.close();
}
return resultMap;
}
/**
* 구매요청서 품의서 생성 (PURCHASE_REG 전용) - 업체별로 분리 생성
*/
public Map createProposalFromPurchaseReg(HttpServletRequest request, Map paramMap) {
SqlSession sqlSession = null;
Map resultMap = new HashMap();
try {
sqlSession = SqlMapConfig.getInstance().getSqlSession(false);
HttpSession session = request.getSession();
PersonBean person = (PersonBean)session.getAttribute(Constants.PERSON_BEAN);
String userId = CommonUtils.checkNull(person.getUserId());
String salesRequestMasterObjid = CommonUtils.checkNull(paramMap.get("SALES_REQUEST_MASTER_OBJID"));
if(salesRequestMasterObjid.isEmpty()) {
resultMap.put("resultFlag", "F");
resultMap.put("message", "구매요청서 정보가 없습니다.");
return resultMap;
}
// 1. 구매요청서 마스터 정보 조회
Map masterParam = new HashMap();
masterParam.put("SALES_REQUEST_MASTER_OBJID", salesRequestMasterObjid);
Map purchaseRequestInfo = (Map)sqlSession.selectOne("salesMng.getSalesRequestMasterInfo", masterParam);
purchaseRequestInfo = CommonUtils.toUpperCaseMapKey(purchaseRequestInfo);
// 2. 대상 품목 조회
List<Map> targetParts = sqlSession.selectList("salesMng.getProposalTargetPartsFromPurchaseReg", masterParam);
if(targetParts == null || targetParts.isEmpty()) {
resultMap.put("resultFlag", "F");
resultMap.put("message", "품의서 생성 대상 품목이 없습니다.");
return resultMap;
}
// 3. 업체별로 품목 그룹화
Map<String, List<Map>> partsByVendor = new LinkedHashMap<String, List<Map>>();
for(Map part : targetParts) {
String vendorPm = CommonUtils.checkNull(part.get("VENDOR_PM"));
if(vendorPm.isEmpty()) {
vendorPm = CommonUtils.checkNull(part.get("vendor_pm"));
}
if(!partsByVendor.containsKey(vendorPm)) {
partsByVendor.put(vendorPm, new ArrayList<Map>());
}
partsByVendor.get(vendorPm).add(part);
}
// 4. 업체별로 품의서 생성
List<String> createdProposalNos = new ArrayList<String>();
List<String> allSourceObjids = new ArrayList<String>();
for(String vendorPm : partsByVendor.keySet()) {
List<Map> vendorParts = partsByVendor.get(vendorPm);
// 품의서 번호 생성
String proposalNo = (String)sqlSession.selectOne("salesMng.getNextProposalNo");
createdProposalNos.add(proposalNo);
// 품의서 마스터 생성
Map proposalMaster = new HashMap();
String proposalMasterObjid = CommonUtils.createObjId();
proposalMaster.put("OBJID", proposalMasterObjid);
proposalMaster.put("REQUEST_MNG_NO", proposalNo);
proposalMaster.put("PROJECT_NO", purchaseRequestInfo.get("PROJECT_NO"));
proposalMaster.put("PURCHASE_TYPE", purchaseRequestInfo.get("PURCHASE_TYPE"));
proposalMaster.put("ORDER_TYPE", purchaseRequestInfo.get("ORDER_TYPE"));
proposalMaster.put("PRODUCT_NAME", purchaseRequestInfo.get("PRODUCT_NAME"));
proposalMaster.put("AREA_CD", purchaseRequestInfo.get("AREA_CD"));
proposalMaster.put("CUSTOMER_OBJID", purchaseRequestInfo.get("CUSTOMER_OBJID"));
proposalMaster.put("PAID_TYPE", purchaseRequestInfo.get("PAID_TYPE"));
proposalMaster.put("DELIVERY_REQUEST_DATE", purchaseRequestInfo.get("DELIVERY_REQUEST_DATE"));
proposalMaster.put("REQUEST_USER_ID", userId);
proposalMaster.put("WRITER", userId);
sqlSession.insert("salesMng.insertProposalFromPurchaseReg", proposalMaster);
// 해당 업체의 품목 생성
for(Map part : vendorParts) {
String sourceObjid = CommonUtils.checkNull(part.get("OBJID"));
if(sourceObjid.isEmpty()) {
sourceObjid = CommonUtils.checkNull(part.get("objid"));
}
allSourceObjids.add(sourceObjid);
Map partParam = new HashMap();
partParam.put("NEW_OBJID", CommonUtils.createObjId());
partParam.put("PROPOSAL_MASTER_OBJID", proposalMasterObjid);
partParam.put("SOURCE_OBJID", sourceObjid);
partParam.put("WRITER", userId);
sqlSession.insert("salesMng.insertProposalPartFromPurchaseReg", partParam);
}
}
// 5. 원본 품목 PROPOSAL_DATE 업데이트
if(!allSourceObjids.isEmpty()) {
Map updateParam = new HashMap();
updateParam.put("PART_OBJIDS", allSourceObjids);
sqlSession.update("salesMng.updateProposalDateForPurchaseRegParts", updateParam);
}
sqlSession.commit();
// 결과 메시지 생성
String message = "품의서가 " + createdProposalNos.size() + "건 생성되었습니다.\n";
StringBuilder sb = new StringBuilder();
for(int i = 0; i < createdProposalNos.size(); i++) {
if(i > 0) sb.append(", ");
sb.append(createdProposalNos.get(i));
}
message += sb.toString();
resultMap.put("resultFlag", "S");
resultMap.put("message", message);
resultMap.put("proposalNos", createdProposalNos);
} catch(Exception e) {
if(sqlSession != null) sqlSession.rollback();
e.printStackTrace();
resultMap.put("resultFlag", "F");
resultMap.put("message", "품의서 생성 중 오류가 발생했습니다: " + e.getMessage());
} finally {
if(sqlSession != null) sqlSession.close();
}
return resultMap;
}
}

View File

@@ -1839,8 +1839,9 @@ public class PurchaseOrderService {
String docType = CommonUtils.checkNull((String) salesRequestInfo.get("doc_type"));
System.out.println("docType: " + docType);
// 품의서(PROPOSAL)인 경우 VENDOR_PM 사용, 구매요청서는 PARTNER_OBJID 사용
String queryId = "PROPOSAL".equals(docType)
// 품의서(PROPOSAL, PURCHASE_REG_PROPOSAL)인 경우 VENDOR_PM 사용, 구매요청서는 PARTNER_OBJID 사용
boolean isProposal = "PROPOSAL".equals(docType) || "PURCHASE_REG_PROPOSAL".equals(docType);
String queryId = isProposal
? "purchaseOrder.getVendorListByProposalObjid"
: "purchaseOrder.grtPartnerObjidBySalesRequestObjid";
System.out.println("queryId: " + queryId);
@@ -1881,7 +1882,7 @@ public class PurchaseOrderService {
sqlSession.update("purchaseOrder.mergePurchaseOrderMasterBySalesRequest", masterParam);
// 해당 공급업체의 품목 조회
String partQueryId = "PROPOSAL".equals(docType)
String partQueryId = isProposal
? "purchaseOrder.getProposalPartsByVendor"
: "purchaseOrder.getSalesRequestPartsByVendor";
@@ -1898,16 +1899,28 @@ public class PurchaseOrderService {
partParam.put("PURCHASE_ORDER_MASTER_OBJID", purchaseOrderMasterObjid);
partParam.put("PART_OBJID", CommonUtils.checkNull((String) partMap.get("part_objid")));
// 수량 처리
String qtyStr = CommonUtils.checkNull(partMap.get("qty"), "0");
String orderQtyStr = CommonUtils.checkNull(partMap.get("order_qty"), "0");
// 수량 처리 (Object 타입 대응)
Object qtyObj = partMap.get("qty");
Object orderQtyObj = partMap.get("order_qty");
String qtyStr = (qtyObj != null) ? String.valueOf(qtyObj).trim() : "0";
if("".equals(qtyStr)) qtyStr = "0";
String orderQtyStr = (orderQtyObj != null) ? String.valueOf(orderQtyObj).trim() : "";
// ORDER_QTY가 없거나 빈값/0이면 QTY 사용
if("".equals(orderQtyStr) || "0".equals(orderQtyStr)) {
orderQtyStr = qtyStr;
}
partParam.put("QTY", qtyStr);
partParam.put("ORDER_QTY", orderQtyStr);
// 단가 정보
String partnerPrice = CommonUtils.checkNull(partMap.get("partner_price"), "0");
String totalPrice = CommonUtils.checkNull(partMap.get("total_price"), "0");
// 단가 정보 (Object 타입 대응)
Object partnerPriceObj = partMap.get("partner_price");
Object totalPriceObj = partMap.get("total_price");
String partnerPrice = (partnerPriceObj != null) ? String.valueOf(partnerPriceObj).trim() : "0";
if("".equals(partnerPrice)) partnerPrice = "0";
String totalPrice = (totalPriceObj != null) ? String.valueOf(totalPriceObj).trim() : "0";
if("".equals(totalPrice)) totalPrice = "0";
partParam.put("PARTNER_PRICE", partnerPrice);