RAG · 벡터 검색 · 임베딩

RAG의 색인과 검색·생성 분리하기

문서를 벡터로 색인하는 준비 단계와 질문 시 관련 문맥을 검색해 답을 만드는 실행 단계를 구분합니다.

무료 공개 · 최근 수정

모델 밖의 문서를 답변에 사용하기

언어 모델이 학습한 지식에는 시점과 범위의 한계가 있습니다. 오늘 바뀐 사내 규정, 사용자의 비공개 문서나 제품의 최신 장애 기록은 모델 가중치 안에 없을 수 있습니다. 긴 문서를 통째로 프롬프트에 넣는 방법도 있지만 비용과 컨텍스트 한계가 커지고, 질문과 무관한 내용이 답변을 방해합니다. 필요한 부분만 찾아 제공하는 검색 계층이 필요한 이유입니다.

검색 증강 생성(Retrieval-Augmented Generation; RAG)은 질문과 관련된 문서를 먼저 검색하고 그 문맥을 모델 입력에 붙이는 방식입니다. 모델을 다시 학습시키지 않고도 자료를 추가하거나 교체할 수 있고, 답의 근거가 된 문서 조각을 함께 제시할 수 있습니다. 다만 RAG는 모델에 지식을 영구히 주입하는 학습 방식이 아니라, 질문할 때 참고 자료를 골라 넣는 실행 구조입니다.

문서를 나누고 임베딩해 저장하는 색인 단계와 질문에 가까운 조각을 검색해 LLM에 전달하는 실행 단계

그림: 색인은 미리 수행하고, 질문마다 검색과 생성을 실행합니다.

색인 단계는 문서 로딩, 청킹, 임베딩, 벡터 저장으로 이어집니다. 청킹은 문서를 검색 가능한 조각으로 나누는 일이며 제목, 출처, 날짜와 접근 등급 같은 메타데이터도 함께 저장합니다. 임베딩은 텍스트의 의미적 특징을 숫자 배열인 벡터로 표현하는 과정입니다. 문서가 추가되거나 내용이 바뀌면 해당 조각을 다시 색인해야 합니다.

질문이 들어오는 실행 단계에서는 질문도 호환되는 임베딩 모델로 변환하고, 벡터 사이의 유사도를 계산해 가까운 문서 조각을 찾습니다. 필요하면 날짜나 사용 권한으로 후보를 먼저 제한하고, 상위 결과를 재정렬한 뒤 질문과 함께 LLM에 전달합니다. 따라서 정확한 키워드가 일치하지 않아도 의미가 가까운 자료를 찾을 수 있습니다. 색인과 실행을 분리해야 문서 변경 시 무엇을 다시 계산할지, 질문마다 어떤 비용이 드는지 판단할 수 있습니다.

작은 검색으로 원리 확인하기

다음 예제는 외부 라이브러리 없이 단어 집합의 겹침으로 검색 원리만 보여 줍니다.

documents = [
    "Ollama는 로컬에서 모델을 실행한다",
    "LangSmith는 실행 추적을 관찰한다",
    "LangGraph는 상태 기반 흐름을 구성한다",
]
question = "로컬에서 모델을 실행하려면?"
keywords = "로컬 모델 실행".split()
 
ranked = sorted(
    documents,
    key=lambda text: sum(keyword in text for keyword in keywords),
    reverse=True,
)
context = ranked01. Prompt = f"참고 문맥: {context}\n질문: {question}\n문맥을 바탕으로 답해 줘."
print(prompt)

출력의 참고 문맥에는 Ollama 문장이 들어갑니다. context까지가 검색 결과이고, prompt는 검색된 문맥과 질문을 생성 모델에 넘기는 접점입니다. 이 코드는 경계만 확인하는 문자열 예제이므로 실제 모델은 호출하지 않습니다. 실제 RAG에서는 단어가 직접 일치하지 않아도 의미가 가까운 문장을 찾도록 임베딩 유사도와 벡터 저장소를 사용합니다.

실제 시스템에서는 청크가 너무 작으면 답에 필요한 앞뒤 문맥을 잃고, 너무 크면 관련 없는 내용까지 모델에 전달됩니다. 문단과 제목 구조를 보존해 나누고 일부 겹침을 두는 이유가 여기에 있습니다. 모든 문서에 같은 크기가 정답은 아니므로 FAQ, API 문서, 회의록처럼 자료 성격별로 검색 결과를 점검해야 합니다.

검색 결과도 검증하기

RAG가 환각을 없애는 것은 아닙니다. 관련 없는 조각을 검색하거나 필요한 조각을 놓칠 수 있고, 모델이 제공된 문맥을 잘못 해석할 수도 있습니다. 그래서 검색과 생성을 나눠 평가합니다. 먼저 정답 근거가 상위 검색 결과에 포함되는지 보고, 그다음 근거가 주어졌을 때 답변이 사실을 따르는지 확인합니다. 최종 답만 평가하면 검색기와 생성기 중 무엇을 고쳐야 할지 알기 어렵습니다.

청크 크기, 검색 개수, 메타데이터 필터와 답변 근거를 대표 질문 묶음으로 검증합니다. 검색된 출처와 수정일을 사용자에게 보여 주고, 근거가 부족할 때는 추측 대신 모른다고 답하는 규칙도 필요합니다. 비밀 문서는 검색 권한 단계에서 차단해야 하며 프롬프트 지시만으로 접근을 통제하지 않습니다.

다음으로 LangSmith 실행 추적을 사용하면 검색과 모델 호출 중 어디에서 잘못된 결과가 생겼는지 구분할 수 있습니다.

참고 문서

설명이 어렵거나 잘못된 부분을 발견하셨나요?

문서 수정 의견 보내기