5.9.4 데이터 추출기: 비정형 텍스트의 날짜, 금액 형식 변환 정확성 테스트
기업의 자동화 워크플로우(RPA 등)에서 LLM이 가장 활발하게 쓰이는 지점은 바로 ’비정형 데이터의 정형화(Data Extraction)’다. 영수증 스캔본(OCR 텍스트), 영업 사원의 대충 쓰인 메모, 혹은 고객의 모호한 이메일에서 ’날짜(Date)’와 ’금액(Amount)’을 뽑아내어 데이터베이스에 INSERT하는 작업이다.
이 도메인에서 오라클의 임무는 정보의 추출 여부를 확인하는 것을 넘어, **‘데이터베이스나 레거시 API가 수용할 수 있는 완벽하게 엄격한 데이터 타입과 포맷으로 변환되었는가’**를 강도 높게 검열하는 것이다. 숫자나 콤마 하나가 엇나가면 데이터베이스 파서 자체가 붕괴(Crash)하기 때문이다.
1. 형태의 일관성을 강제하는 정규표현식(Regex) 오라클
“다음 주 금요일 오후에 5만 5천 원 송금할게요“라는 텍스트에서 LLM은 자칫 “55,000원”, “오만 오천원”, “55000” 등 다양한 형태의 환각을 일으킬 수 있다. 결제 시스템 API가 오직 integer 형태의 순수 숫자만을 요구한다면, 오라클은 이를 철저히 단언(Assert)해야 한다.
금액과 관련된 데이터 추출기의 유닛 테스트는 통화 기호나 쉼표가 절대로 포함되지 않았음을 정규표현식으로 엄격히 교차 검증한다.
import re
import pytest
def test_amount_extraction_format(llm_extractor):
raw_text = "이번 달 서비스 이용료는 삼백만 오십원입니다. V.A.T 별도."
# LLM 데이터 추출 실행
extracted_data = llm_extractor.extract_financial_info(raw_text)
# 오라클: 금액이 순수 숫자 문자열(Digits only)로만 반환되었는가?
# "3,000,050" 이나 "300만 50원" 같은 포맷은 무조건 Fail 처리한다.
amount_str = extracted_data["amount"]
assert re.fullmatch(r"^\d+$", amount_str) is not None, \
f"금액 포맷 오류: 불순물이 포함되었습니다. (추출값: {amount_str})"
# 최종 로직 검증 (값 자체의 정확도 계산)
assert int(amount_str) == 3000050
2. 날짜 및 시간(Datetime) 포맷팅의 객체 파싱 검증
가장 골치 아픈 데이터는 날짜다. “어제”, “내일 모레 낮 12시”, “Q3 실적 발표일” 같은 비정형 텍스트를 LLM은 지시어에 따라 YYYY-MM-DD나 ISO-8601 스탠다드로 환산해야 한다.
날짜를 검증하는 가장 확실한 오라클은 텍스트 비교가 아니다. LLM이 반환한 날짜 문자열을 직접 프로그래밍 언어의 내장 날짜 파서(Datetime Parser)에 밀어 넣어보는 것이다. 파서가 에러 없이 구동된다면, 해당 텍스트는 시스템 친화적인 포맷임을 결정론적으로 보장받는다.
from datetime import datetime
def test_date_extraction_iso8601(llm_extractor):
# 테스트 시점을 고정하기 위해 프롬프트에 '기준 접속일'을 Mocking하여 주입
system_prompt = "현재 서버 시간은 2023-10-15T09:00:00Z 입니다."
raw_text = "내일 오후 3시까지 배송해 주세요."
extracted_data = llm_extractor.extract_date(system_prompt, raw_text)
delivery_date_str = extracted_data["delivery_date_iso"]
# 결정론적 오라클: ISO-8601 형식(YYYY-MM-DDTHH:MM:SS) 파싱이 가능한가?
try:
parsed_date = datetime.fromisoformat(delivery_date_str)
is_valid_format = True
except ValueError:
is_valid_format = False
assert is_valid_format, f"날짜 포맷 규격 위반: {delivery_date_str}"
# 변환된 논리적 시간 검증 ("내일 오후 3시" => "2023-10-16 15:00")
assert parsed_date.year == 2023
assert parsed_date.month == 10
assert parsed_date.day == 16
assert parsed_date.hour == 15
비정형 텍스트에서 정형 데이터를 추출하는 로직의 테스트는 한없이 무자비해야 한다. LLM이 “제가 이해하기엔…“이라며 주저리주저리 변명을 덧붙이는 순간, 다운스트림(Downstream)의 데이터 파이프라인은 그 즉시 붕괴한다. 데이터 추출 도메인에서 오라클이 수행하는 역할은 자비로운 채점관이 아니라, 규격에 맞지 않는 부품을 가차 없이 폐기 처분하는 공장의 품질 관리(QC) 로봇이다.