LLMRanker

LLMRanker

쿼리에 대한 문서 순위를 LLM으로 매겨주는 컴포넌트예요. LLM을 쿼리와 문서 내용으로 프롬프팅해서, 관련성이 높은 순에서 낮은 순으로 정렬된 문서 인덱스를 담은 JSON 객체를 반환하도록 기대해요. 쿼리 파이프라인에서 Retriever처럼 문서 목록을 반환하는 컴포넌트 뒤에 두면 돼요.

출처: LLMRanker

본문

개요

LLMRanker는 LLM을 사용해 문서를 쿼리와의 관련성 순으로 재정렬해요. 크로스-인코더 랭커와 달리 관련성을 의미론적 추론 작업으로 취급해서, 복잡하거나 다단계인 쿼리에서 더 나은 결과를 낼 수 있어요. 컴포넌트는 쿼리와 문서 내용을 LLM에 보내고 응답을 JSON으로 파싱해요. index 필드(1부터 시작하는 문서 위치)를 가진 객체 배열이에요. LLM이 이 목록에 포함시킨 문서만 주어진 순서대로 반환돼요.

랭킹 전에 중복 문서가 제거돼요. top_k로 반환되는 문서 수를 제한할 수 있어요. 생성이나 파싱이 실패하면, 랭커는 예외를 발생시키거나(raise_on_failure=True), 입력 문서를 원래 순서대로 반환해요(raise_on_failure=False, 기본값).

구조화된 JSON 출력을 지원하는 어떤 Haystack ChatGenerator든 전달할 수 있어요. chat_generator를 생략하면 랭킹 응답용 JSON 스키마가 있는 기본 OpenAIChatGenerator(예: gpt-4.1-mini)를 사용해요. 이 ChatGenerator를 위해 OPENAI_API_KEY를 제공해야 해요. 커스텀 prompt 템플릿도 제공할 수 있어요. 정확히 query와 documents 변수만 포함해야 하고, LLM에게 1부터 시작하는 랭킹 문서 인덱스를 JSON으로 반환하도록 지시해야 해요.

사용법

단독 사용 예시예요. 기본 OpenAIChatGenerator로 문서 두 개의 순위를 매겨요. 랭커는 LLM이 지정한 순서대로 문서를 반환해요.

from haystack import Document
from haystack.components.rankers import LLMRanker

ranker = LLMRanker()

documents = [
    Document(id="paris", content="Paris is the capital of France."),
    Document(id="berlin", content="Berlin is the capital of Germany."),
]

result = ranker.run(query="capital of Germany", documents=documents)
print(result["documents"][0].id) # "berlin"

커스텀 채팅 생성기와 함께:

JSON 출력용으로 구성된 자체 채팅 생성기를 전달할 수 있어요(예: response_format/JSON 스키마로 모델이 기대하는 documents 배열을 index 필드와 함께 반환하도록).

from haystack import Document
from haystack.components.generators.chat import OpenAIChatGenerator
from haystack.components.rankers import LLMRanker

chat_generator = OpenAIChatGenerator(
    model="gpt-4.1-mini",
    generation_kwargs={
        "temperature": 0.0,
        "response_format": {
            "type": "json_schema",
            "json_schema": {
                "name": "document_ranking",
                "schema": {
                    "type": "object",
                    "properties": {
                        "documents": {
                            "type": "array",
                            "items": {
                                "type": "object",
                                "properties": {"index": {"type": "integer"}},
                                "required": ["index"],
                                "additionalProperties": False,
                            },
                        },
                    },
                    "required": ["documents"],
                    "additionalProperties": False,
                },
            },
        },
    },
)

ranker = LLMRanker(chat_generator=chat_generator)
documents = [
    Document(content="Paris is the capital of France."),
    Document(content="Berlin is the capital of Germany."),
]
result = ranker.run(query="capital of Germany", documents=documents, top_k=1)

파이프라인 안에서:

아래는 InMemoryBM25Retriever로 문서를 검색한 뒤 LLMRanker로 순위를 매기는 파이프라인 예시예요.

from haystack import Document, Pipeline
from haystack.components.retrievers.in_memory import InMemoryBM25Retriever
from haystack.components.rankers import LLMRanker
from haystack.document_stores.in_memory import InMemoryDocumentStore

docs = [
    Document(content="Paris is in France."),
    Document(content="Berlin is in Germany."),
    Document(content="Lyon is in France."),
]
document_store = InMemoryDocumentStore()
document_store.write_documents(docs)

retriever = InMemoryBM25Retriever(document_store=document_store)
ranker = LLMRanker(top_k=2)

pipeline = Pipeline()
pipeline.add_component(instance=retriever, name="retriever")
pipeline.add_component(instance=ranker, name="ranker")

pipeline.connect("retriever.documents", "ranker.documents")

query = "Cities in France"
result = pipeline.run(
    data={
        "retriever": {"query": query, "top_k": 3},
        "ranker": {"query": query, "top_k": 2},
    },
)

top_k 파라미터

Retriever의 top_k는 문서를 몇 개 검색할지 제어해요. Ranker의 top_k는 랭킹 후 그중 몇 개를 반환할지 제한해요. 비용과 지연 시간을 최적화하려면 Ranker에 같거나 더 작은 top_k를 설정할 수 있어요.

더 알아보기 (Learn more)