멀티모달 입력과 출력
멀티모달 입력과 출력 (Multimodal inputs and outputs)
Deep Agents는 모델이 멀티모달 입력과 도구 결과를 받아들이거나 멀티모달 출력을 반환할 때 멀티모달 워크플로우를 지원해요. 사용자 메시지에 이미지와 기타 미디어를 붙이고, 내장 read_file 도구로 비텍스트 파일을 읽고, 커스텀 도구에서 멀티모달 콘텐츠를 반환할 수 있어요. 다만 내장 컨텍스트 컴프레션은 주로 텍스트 중심이라, 큰 미디어는 백엔드에 저장하고 가능하면 참조를 넘기는 방식으로 멀티모달 워크로드를 계획하는 게 좋아요.
출처: 공식문서
멀티모달 사용자 입력 (Multimodal user input)
에이전트에 보내는 messages에 LangChain 채팅 모델과 동일한 표준 콘텐츠 블록을 사용해 멀티모달 콘텐츠를 전달해요.
result = agent.invoke({
"messages": [{
"role": "user",
"content": [
{"type": "text", "text": "What is in this screenshot?"},
{"type": "image", "url": "https://example.com/screenshot.png"},
],
}],
})
블록 타입, 프로바이더별 요구사항, 추가 예제(PDF, 오디오, 비디오)는 Multimodal messages 문서를 참고해요.
내장 read_file 도구
하네스 read_file 도구는 지원되는 멀티모달 파일에 대해 일반 텍스트 대신 표준 콘텐츠 블록을 반환해요. 선택한 모델이 해당 모달리티를 지원하면 에이전트가 자체 파일시스템에 저장된 이미지, 문서, 미디어를 검사할 수 있어요. 모델이 지원하는 MIME 타입은 프로바이더 문서를 확인해요.
지원되는 멀티모달 파일 확장자
| 타입 | 확장자 |
|---|---|
| 이미지 | .png, .jpg, .jpeg, .gif, .webp, .heic, .heif |
| 비디오 | .mp4, .mpeg, .mov, .avi, .flv, .mpg, .webm, .wmv, .3gpp |
| 오디오 | .wav, .mp3, .aiff, .aac, .ogg, .flac |
| 파일 | .pdf, .ppt, .pptx |
커스텀 도구 출력 (Custom tool outputs)
커스텀 도구는 이미지 같은 멀티모달 파일을 포함할 수 있어요.
from langchain.tools import tool
@tool
def capture_screenshot() -> list[dict]:
"""Capture a screenshot of the current page."""
return [
{"type": "text", "text": "Screenshot of the current page:"},
{"type": "image", "url": "https://example.com/page.png"},
]
반환 값은 다음 턴에 모델이 읽는 ToolMessage로 변환돼요. 결과 메시지의 content_blocks로 정규화된 표현에 접근할 수 있어요. 반환 타입 옵션, 직렬화 동작, MCP 예제는 Multimodal content 문서를 참고해요.
도구가 이미지나 다른 큰 바이너리 데이터를 만들면 아티팩트를 백엔드에 저장하고 간결한 텍스트 설명 + 경로나 URL을 반환하는 걸 권장해요. 그러면 메시지 기록이 작게 유지되고 컨텍스트 컴프레션과도 잘 어울려요.
컨텍스트 컴프레션과 멀티모달 콘텐츠
내장 오프로딩과 요약은 텍스트와 메시지 기록에 최적화돼 있어요.
- **오프로딩(Offloading)**은 텍스트 토큰만 측정해요. 비텍스트 블록(이미지 포함)은 컴프레스되는 대신 교체 메시지에서 보존돼요. 이미지만 있는 메시지는 이미지 크기만으로는 오프로딩되지 않아요.
- **요약(Summarization)**은 오래된 메시지를 텍스트 전용 요약으로 컴팩트해요. 그 범위의 이미지·오디오·비디오·파일 블록은 앞으로 전달되지 않아요 — 모델은 요약기가 그에 대해 쓴 내용만 볼 수 있어요. keep 기준 아래 최근 메시지는 변경 없이 남아요.
요약이 실행되면 오래된 턴의 미디어 블록이 활성 컨텍스트에서 빠져나와요.
# 이전 — 모델이 오래된 턴의 이미지 블록을 받음
[
HumanMessage(
content=[
{"type": "text", "text": "What trends do you see in this chart?"},
{"type": "image", "base64": IMG, "mime_type": "image/png"},
]
),
ToolMessage(
content=[
{"type": "text", "text": "Updated chart:"},
{"type": "image", "base64": IMG, "mime_type": "image/png"},
],
tool_call_id="call_chart_1",
),
AIMessage(content="Revenue rose in Q3 based on the chart trend."),
HumanMessage(content="Reply with one sentence summarizing our analysis."),
]
# 이후 — 해당 턴이 텍스트로 접히고 이미지 블록은 사라짐
{"content": (
"User asked about trends in a chart screenshot. "
"Tool returned an updated chart. Agent identified Q3 revenue growth."
)}
원래 대화는 여전히 파일시스템에 텍스트로 기록돼요. 트리거, keep 기준, 전체 흐름은 Summarization 문서를 참고해요.
멀티모달이 많은 워크로드를 위한 조언:
- 이미지, 스크린샷, 차트는 파일시스템 백엔드나 외부 객체 스토리지에 저장하고 메시지로 경로나 URL을 전달해요.
- 오래 지속되는 대화에서는 base64 인코딩 이미지 블록보다 참조를 선호해요.
- 이미지가 많은 검사는
subagents를 사용해 메인 에이전트는 간결한 텍스트 결과만 받도록 해요. - 프로바이더가 이미지에 많은 토큰을 청구한다면 요약 기준을 조정하거나 커스텀 토큰 카운터를 제공해요.
오프로딩 기준, 요약 트리거, 커스터마이징 옵션은 Context compression 문서를 참고해요.
더 알아보기 (Learn more)
- Multimodal messages — 콘텐츠 블록 타입과 프로바이더 요구사항
- Multimodal content — 커스텀 도구 출력 직렬화
- Context compression — 오프로딩/요약 튜닝
- 딥 에이전트 개요 (Deep Agents overview)