"""Stage 3 — LLM 출력 스키마 (docs/logic-chunk-design.md). pydantic 검증. - ProgramSummary : 프로그램 1건 요약 (unit 추출의 문맥으로도 쓰임) - UnitExtraction : unit 하나에서 LLM 이 골라낸 로직 조각 목록 + unit 한 줄 요약 - LogicChunk : 로직 조각 하나 — 인덱스의 1차 단위 """ from __future__ import annotations from pydantic import BaseModel, Field CHUNK_KINDS = ( "sql_select", # DB 조회 (SELECT / OPEN CURSOR) "db_write", # DB 갱신 (INSERT / UPDATE / MODIFY / DELETE / COMMIT) "fm_call", # BAPI · 펑션모듈 · RFC · 메서드 호출로 업무 처리 "aggregation", # 내부테이블 집계 · 가공 · 병합 (LOOP / COLLECT / SORT …) "validation", # 입력 검증 · 권한 체크 · 존재 확인 "calculation", # 금액 · 수량 · 환율 · 날짜 계산 "output", # ALV · 리스트 · 화면 · 파일 · 메일 출력 "interface", # 외부 시스템 송수신 (파일 · IDoc · HTTP · RFC destination) "control_flow", # 처리 흐름 분기 · 하위 로직 호출 순서 "other", ) class LogicChunk(BaseModel): """LLM 이 반환하는 조각. line_* 는 include 기준 줄 번호(코드에 붙여 준 번호 그대로).""" line_start: int line_end: int first_line: str = "" # line_start 줄의 코드 원문 — 줄 번호 검증용 앵커 kind: str = "other" purpose_ko: str purpose_en: str = "" keywords_ko: list[str] = Field(default_factory=list) keywords_en: list[str] = Field(default_factory=list) sap_objects: list[str] = Field(default_factory=list) # 테이블 · FM · BAPI · 클래스 · T-Code confidence: float = 0.5 class UnitExtraction(BaseModel): unit_purpose_ko: str = "" # unit 한 줄 요약 — 얇은 색인용 (조각이 없어도 채운다) chunks: list[LogicChunk] = Field(default_factory=list) unclear: list[str] = Field(default_factory=list) class SelectionParam(BaseModel): name: str desc_ko: str = "" class KeyInternalTable(BaseModel): name: str filled_by: list[str] = Field(default_factory=list) consumed_by: list[str] = Field(default_factory=list) desc_ko: str = "" class ProgramSummary(BaseModel): program: str title_ko: str = "" business_purpose_ko: str = "" business_purpose_en: str = "" main_flow: list[str] = Field(default_factory=list) selection_screen: list[SelectionParam] = Field(default_factory=list) key_internal_tables: list[KeyInternalTable] = Field(default_factory=list) tables_read: list[str] = Field(default_factory=list) # 파서 값으로 덮어씀 tables_write: list[str] = Field(default_factory=list) # 파서 값으로 덮어씀 external_calls: list[str] = Field(default_factory=list) # 파서 값으로 덮어씀 output_type: list[str] = Field(default_factory=list) business_tags: list[str] = Field(default_factory=list) proposed_tags: list[str] = Field(default_factory=list) sap_module: str = "" keywords_ko: list[str] = Field(default_factory=list) keywords_en: list[str] = Field(default_factory=list) related_tcodes: list[str] = Field(default_factory=list) notes: list[str] = Field(default_factory=list) confidence: float = 0.5 unclear: list[str] = Field(default_factory=list) prompt_version: int = 0