구조화된 출력 (Structured Outputs)

구조화된 출력 — 지정한 JSON 스키마로 모델 응답 강제하기

모델이 그냥 자연어를 돌려주는 대신, 여러분이 정한 JSON 스키마에 정확히 맞는 텍스트를 내도록 만들 수 있어요. 이게 바로 구조화된 출력(structured outputs)이에요. 신뢰할 수 있는 데이터 추출과 제어된 텍스트 생성을 가능하게 해 주죠. Model APIs가 이를 지원하고, 자체 배포 모델은 BIS-LLM이나 Engine-Builder-LLM 같은 Baseten 엔진, 그리고 vLLM·SGLang 같은 추론 프레임워크에서도 쓸 수 있어요.

구조화된 출력에는 두 가지 요소가 필요해요. 원하는 출력 형태를 정의하는 Pydantic 스키마와, 그 스키마를 강제하는 API 호출이죠. 스키마를 한 번 정의해 두면 같은 형태의 출력을 계속 뽑아낼 수 있어서, 응답 파싱 코드를 따로 유지할 필요가 없어집니다.

출처: Baseten - Structured outputs

스키마 정의와 생성

먼저 Pydantic 모델로 출력 형태를 정의해요.

from pydantic import BaseModel

class Task(BaseModel):
    title: str
    priority: str  # "low", "medium", "high"
    due_date: str
    description: str

Model APIs라면 클라이언트를 https://inference.baseten.co/v1로 두고 지원되는 모델 슬러그를 넘기면서 response_format=Task로 호출하면 돼요. 자체 배포라면 https://model-xxxxxx.api.baseten.co/environments/production/sync/v1을 base URL로 쓰고 모델 필드를 지정하지 않습니다.

from openai import OpenAI
import os

client = OpenAI(
    api_key=os.environ['BASETEN_API_KEY'],
    base_url="https://inference.baseten.co/v1"
)
response = client.beta.chat.completions.parse(
    model="moonshotai/Kimi-K2.6",
    messages=[{"role": "user", "content": "Create a task for: Review the quarterly report by next Friday"}],
    response_format=Task,
)

LangChain과 함께 쓰기

Baseten은 OpenAI 호환 엔드포인트를 제공하므로, LangChain의 ChatOpenAIwith_structured_output를 붙여도 동작해요.

from langchain_openai import ChatOpenAI
import os

llm = ChatOpenAI(
    api_key=os.environ["BASETEN_API_KEY"],
    base_url="https://inference.baseten.co/v1",
    model="moonshotai/Kimi-K2.6",
)
structured_llm = llm.with_structured_output(Task)
task = structured_llm.invoke("Create a task for: Review the quarterly report by next Friday")

엔진 지원과 베스트 프랙티스

Engine-Builder-LLM은 Lookahead speculative decoding을 켠 경우, BIS-LLM은 overlap scheduler가 활성화된 일부 구성에서 구조화된 출력을 제외합니다. 그 외에는 두 엔진의 모든 모델이 추가 설정 없이 지원해요.

스키마 설계는 23단계 중첩을 넘지 않게 단순하게, 가능하면 str·int·float·bool 같은 기본 타입을 쓰고, 선택 필드에는 기본값을 두는 게 좋아요. 프롬프트 쪽에서는 일관된 출력을 위해 온도를 0.10.3으로 낮추고, 복잡한 스키마라면 모델 스키마와 few-shot 예시를 컨텍스트에 넣어 주면 도움이 됩니다.

더 알아보기