diff --git a/resources/tester/test_est_quantity_workflow.py b/resources/tester/test_est_quantity_workflow.py new file mode 100644 index 000000000..dd480185d --- /dev/null +++ b/resources/tester/test_est_quantity_workflow.py @@ -0,0 +1,30 @@ +from test_est_rea_parity import run + + +def test_quantity_apply_requires_one_detail_row_per_code(): + result = run( + "math", + """(()=>{ + function apply(rows,items=[{Code:'r1',GN:7,TargetCode:'X'}]){ + const handlers={}; + globalThis.document={addEventListener:(name,fn)=>handlers[name]=fn}; + const sheet={Code:'Q',rows:[],items,options:{}}; + const state={quantitySheet:'Q',project:{quantitySheets:[sheet],tables:{EstMainDat:rows}}}; + globalThis.EstApp={state,change:fn=>fn(),render:()=>{}}; + EstQuantity.install();handlers.click({target:{closest:()=>true}}); + return {rows,notice:state.notice||''}; + } + return {duplicate:apply([{Code:'X',Level:0,GN:1},{Code:'X',Level:0,GN:2}]), + heading:apply([{Code:'X',Level:1,GN:1}]), + valid:apply([{Code:'X',Level:1,GN:1},{Code:'X',Level:0,GN:2}]), + partial:apply([{Code:'X',Level:0,GN:1}],[{Code:'r1',GN:7,TargetCode:'X'},{Code:'r2',GN:4,TargetCode:'missing'}])}; + })()""", + ) + assert [r["GN"] for r in result["duplicate"]["rows"]] == [1, 2] + assert result["duplicate"]["notice"] + assert result["heading"]["rows"][0]["GN"] == 1 + assert result["heading"]["notice"] + assert [r["GN"] for r in result["valid"]["rows"]] == [1, 7] + assert result["valid"]["notice"] == "" + assert result["partial"]["rows"][0]["GN"] == 1 + assert result["partial"]["notice"] diff --git a/tools/est-test/README.md b/tools/est-test/README.md index ad2b4842e..74ca5417f 100644 --- a/tools/est-test/README.md +++ b/tools/est-test/README.md @@ -25,6 +25,8 @@ Ctrl+S는 입력 중인 셀도 확정한 뒤 저장합니다. 연속 저장 요 초기 자료는 기술정보 DB의 실제 REA 저장 샘플입니다. `REA 샘플 대조`에서 원본 저장값과 275개 계산 결과를 비교합니다. 기존 ESTX의 기본 수량 연결은 문서·항목 코드와 내역 코드가 유일한 경우 화면에 표시하며, 중복·다른 모드는 원문에 보존하고 경고합니다. 원본 연결 데이터 실자료 검증과 새 연결의 ESTX 쓰기는 아직 지원하지 않습니다. 테스트용 임의 요율을 원본 기본값으로 넣지 않습니다. 새 원가 서식의 요율은 사용자가 입력합니다. +수량산출서에서 내역에 수량을 반영할 때 연결 코드에 해당하는 상세 내역이 정확히 하나여야 합니다. 코드가 없거나 중복되면 다른 항목을 포함해 반영을 중단하고 오류를 표시합니다. + ## 검증과 남은 범위 기계 성분·합계 48건, 일위 41건, 내역 37건, 산출 결과 118건과 호표 8건, 원가 수식 23건을 대조합니다. 원가 도급액 고정 반복 차이 `324 → -32 → 3 → 0`을 재현합니다. 단가 갱신 후 전체 재계산과 반복 계산의 안정성도 시험합니다. diff --git a/tools/est-test/native-quantity.cjs b/tools/est-test/native-quantity.cjs index 553cda4d5..257bd9265 100644 --- a/tools/est-test/native-quantity.cjs +++ b/tools/est-test/native-quantity.cjs @@ -164,8 +164,11 @@ const EstQuantity = (() => { for (const item of output.items) if (item.TargetCode || item.LinkCode) { const code = item.TargetCode || item.LinkCode; - if (!state.project.tables.EstMainDat.some((r) => r.Code === code)) - throw Error(`연결 내역코드 없음: ${code}`); + const targets = state.project.tables.EstMainDat.filter( + (r) => r.Code === code && !Number(r.Level), + ); + if (!targets.length) throw Error(`연결 내역코드 없음: ${code}`); + if (targets.length > 1) throw Error(`연결 내역코드 중복: ${code}`); quantities.set(code, (quantities.get(code) || 0) + Number(item.GN || 0)); } if (!quantities.size) throw Error("연결할 내역코드를 먼저 입력하세요.");