LeanX

프롬프트 템플릿: 질문의 틀 만들기

프롬프트 템플릿은 자주 쓰는 질문의 틀에 변수 구멍을 뚫어 둔 것으로, ChatPromptTemplate로 역할(system/human)을 나누고 few-shot으로 예시를 심으면 답변 품질이 크게 올라갑니다.

매번 프롬프트를 통째로 새로 쓰는 것은 비효율적입니다. 프롬프트 템플릿은 '초대장 양식'과 같습니다. '___님을 ___에 초대합니다'라는 틀을 만들어 두고, 이름과 장소만 바꿔 끼우는 거죠. 이렇게 하면 프롬프트 품질을 한 곳에서 관리할 수 있습니다.

변수 끼우기: 중괄호 하나면 됩니다

기본 템플릿: 변수 하나 끼우기

from langchain_core.prompts import ChatPromptTemplate

# {product} 자리가 변수 구멍입니다
prompt = ChatPromptTemplate.from_template(
    '{product}를 홍보하는 SNS 문구를 3개 만들어줘. 각각 20자 이내로.'
)

# 템플릿에 값을 채우면 완성된 프롬프트가 됩니다
filled = prompt.invoke({'product': '수제 딸기잼'})
print(filled.to_string())

ChatPromptTemplate: 역할을 나눠서 지시하기

채팅 모델은 메시지에 역할이 있습니다. system은 'AI에게 부여하는 정체성과 규칙'(무대 뒤 감독 지시), human은 '사용자의 실제 질문'입니다. 역할을 나누면 AI가 지시를 훨씬 안정적으로 따릅니다.

system + human 메시지로 만드는 템플릿

from langchain.chat_models import init_chat_model
from langchain_core.prompts import ChatPromptTemplate
from langchain_core.output_parsers import StrOutputParser

prompt = ChatPromptTemplate.from_messages([
    # system: AI의 역할과 규칙을 정합니다 (감독 지시)
    ('system', '너는 {role} 전문가야. 초등학생도 이해할 수 있게 설명해.'),
    # human: 사용자의 질문 (배우의 대사)
    ('human', '{question}'),
])

chain = prompt | init_chat_model('openai:gpt-4o-mini') | StrOutputParser()

result = chain.invoke({
    'role': '경제',
    'question': '인플레이션이 뭐야?',
})
print(result)

Few-shot: 예시를 보여주면 흉내 냅니다

AI에게 원하는 출력 형식을 말로 설명하는 것보다, 예시 2~3개를 직접 보여주는 것이 훨씬 효과적입니다. 신입사원에게 보고서 양식을 말로 설명하는 대신 잘 쓴 보고서 샘플을 건네주는 것과 같습니다. 이것을 few-shot 프롬프팅이라고 합니다.

few-shot: 예시로 출력 형식 가르치기

from langchain_core.prompts import ChatPromptTemplate, FewShotChatMessagePromptTemplate

# 1. 보여줄 예시들 (모범 답안 샘플)
examples = [
    {'word': '바다', 'antonym': '육지'},
    {'word': '뜨겁다', 'antonym': '차갑다'},
]

# 2. 예시 하나를 어떤 대화 형태로 보여줄지 정의
example_prompt = ChatPromptTemplate.from_messages([
    ('human', '{word}'),
    ('ai', '{antonym}'),
])

# 3. 예시들을 자동으로 나열해 주는 few-shot 템플릿
few_shot = FewShotChatMessagePromptTemplate(
    examples=examples,
    example_prompt=example_prompt,
)

# 4. 최종 프롬프트에 예시를 끼워 넣기
final_prompt = ChatPromptTemplate.from_messages([
    ('system', '단어의 반대말을 한 단어로만 답해.'),
    few_shot,  # 여기에 예시 대화가 펼쳐집니다
    ('human', '{word}'),
])

print(final_prompt.invoke({'word': '시작'}).to_string())
상황추천 방법
간단한 단일 질문from_template (변수만 끼우기)
AI에게 역할·규칙 부여from_messages + system 메시지
출력 형식을 정확히 맞춰야 할 때few-shot으로 예시 2~3개 제공
이전 대화를 기억해야 할 때MessagesPlaceholder로 대화 기록 끼우기

프롬프트에 진짜 중괄호를 쓰고 싶다면 두 번 겹쳐 쓰세요. 'JSON 예시: {{"key": "value"}}'처럼 쓰면 변수로 해석되지 않습니다.

few-shot 예시가 많다고 무조건 좋은 게 아닙니다. 예시가 늘어날수록 토큰 비용이 커지고, 편향된 예시는 오히려 답변을 망칩니다. 2~5개의 다양한 예시가 적당합니다.