Context Engineering

TMT

https://blog.langchain.com/context-engineering-for-agents/

TL;DR

에이전트는 작업을 수행하기 위해 컨텍스트가 필요합니다. 컨텍스트 엔지니어링은 에이전트의 경로 각 단계에서 컨텍스트 윈도우를 적절한 정보로 채우는 예술이자 과학입니다. 이 글에서는 다양한 인기 에이전트와 논문을 검토하며 컨텍스트 엔지니어링의 일반적인 전략 — 작성, 선택, 압축, 분리 — 을 설명합니다. 그리고 LangGraph가 이러한 전략을 어떻게 지원하도록 설계되었는지 설명합니다!

또한, 컨텍스트 엔지니어링에 관한 저희 영상도 참고하세요.

Image

Context Engineering

Andrej Karpathy는 LLM이 새로운 종류의 운영체제와 같다고 말합니다. LLM은 CPU와 같고, 그 컨텍스트 윈도우는 RAM과 같아서 모델의 작업 메모리 역할을 합니다. RAM처럼 LLM의 컨텍스트 윈도우는 다양한 컨텍스트 소스를 처리할 수 있는 용량이 제한되어 있습니다. 운영체제가 CPU의 RAM에 무엇을 넣을지 관리하듯, “컨텍스트 엔지니어링”도 비슷한 역할을 한다고 볼 수 있습니다. Karpathy는 이를 다음과 같이 잘 요약합니다:

[Context engineering is the] ”…다음 단계에 필요한 정보를 컨텍스트 윈도우에 정확히 채워 넣는 섬세한 예술이자 과학입니다.”

Image

LLM 애플리케이션을 구축할 때 관리해야 하는 컨텍스트 유형에는 어떤 것들이 있을까요? 컨텍스트 엔지니어링은 다음과 같은 여러 컨텍스트 유형에 적용되는 우산 개념입니다:

  • Instructions(지시문) – 프롬프트, 메모리, few-shot 예시, 툴 설명 등
  • Knowledge(지식) – 사실, 메모리 등
  • Tools(도구) – 툴 호출에서 얻은 피드백

에이전트를 위한 컨텍스트 엔지니어링

올해 들어 LLM의 추론툴 호출 능력이 향상되면서 에이전트에 대한 관심이 크게 증가했습니다. 에이전트LLM 호출과 툴 호출을 번갈아 수행하며, 종종 장시간 작업을 처리합니다. 에이전트는 LLM 호출과 툴 호출을 교차하며, 툴 피드백을 바탕으로 다음 단계를 결정합니다.

Image

하지만 장시간 작업과 툴 호출에서 누적되는 피드백 때문에 에이전트는 많은 토큰을 사용하게 됩니다. 이로 인해 컨텍스트 윈도우 크기를 초과하거나, 비용/지연이 증가하거나, 에이전트 성능이 저하되는 등 여러 문제가 발생할 수 있습니다. Drew Breunig은 긴 컨텍스트가 성능 문제를 일으키는 구체적인 사례를 잘 정리했습니다:

Image

이 점을 고려해 Cognition은 컨텍스트 엔지니어링의 중요성을 강조했습니다:

“컨텍스트 엔지니어링”은 사실상 AI 에이전트를 구축하는 엔지니어의 가장 중요한 역할입니다.

Anthropic도 명확하게 설명했습니다:

에이전트는 수백 번의 턴에 걸친 대화를 진행하므로, 신중한 컨텍스트 관리 전략이 필요합니다.

그렇다면 현재 이 과제를 어떻게 해결하고 있을까요? 에이전트 컨텍스트 엔지니어링의 일반적인 전략을 네 가지로 분류했습니다 — 쓰기, 선택, 압축, 분리 — 그리고 인기 있는 에이전트 제품과 논문에서 각 전략의 예시를 소개합니다. 이후 LangGraph가 이를 어떻게 지원하는지 설명합니다!

Image

컨텍스트 쓰기

컨텍스트 쓰기는 에이전트가 작업을 수행하는 데 도움이 되도록 컨텍스트 윈도우 외부에 저장하는 것을 의미합니다.

스크래치패드

사람이 문제를 해결할 때, 우리는 노트를 작성하고 미래의 관련 작업을 위해 기억합니다. 에이전트도 이러한 기능을 점점 갖추고 있습니다! “스크래치패드”를 통한 노트 작성은 에이전트가 작업을 수행하는 동안 정보를 컨텍스트 윈도우 외부에 저장하는 한 방법입니다. 이 아이디어는 정보를 컨텍스트 윈도우 밖에 저장해 에이전트가 사용할 수 있도록 하는 것입니다. Anthropic의 멀티 에이전트 연구자는 다음과 같이 명확한 예시를 들었습니다:

LeadResearcher는 접근 방식을 고민한 뒤, 계획을 Memory에 저장해 컨텍스트를 유지합니다. 컨텍스트 윈도우가 200,000 토큰을 초과하면 잘리기 때문에, 계획을 유지하는 것이 중요합니다.

스크래치패드는 여러 방식으로 구현할 수 있습니다. 단순히 파일에 쓰는 툴 호출일 수도 있고, 세션 동안 유지되는 런타임 상태 객체의 필드일 수도 있습니다. 어떤 방식이든, 스크래치패드는 에이전트가 작업을 수행하는 데 도움이 되는 유용한 정보를 저장할 수 있게 해줍니다.

메모리

스크래치패드는 에이전트가 한 세션(또는 스레드) 내에서 문제를 해결하는 데 도움을 주지만, 때로는 에이전트가 여러 세션에 걸쳐 기억하는 것이 더 유리할 때도 있습니다! Reflexion은 각 에이전트 턴 이후에 자기반성을 하고, 이 자기생성 메모리를 재사용하는 아이디어를 도입했습니다. Generative Agents는 과거 에이전트 피드백 모음에서 주기적으로 메모리를 합성하는 방식을 사용했습니다.

Image

이러한 개념은 ChatGPT, Cursor, Windsurf 등 인기 제품에도 적용되어, 사용자-에이전트 상호작용을 기반으로 세션 간에 자동으로 장기 메모리를 생성하는 메커니즘을 갖추고 있습니다.

컨텍스트 선택

컨텍스트 선택은 에이전트가 작업을 수행하는 데 도움이 되도록 컨텍스트 윈도우로 불러오는 것을 의미합니다.

스크래치패드

스크래치패드에서 컨텍스트를 선택하는 방식은 구현 방법에 따라 다릅니다. 이라면 에이전트가 툴 호출로 읽을 수 있습니다. 에이전트의 런타임 상태 일부라면, 개발자가 각 단계마다 어떤 상태를 에이전트에 노출할지 세밀하게 제어할 수 있습니다. 이를 통해 LLM에 스크래치패드 컨텍스트를 후속 턴에 노출하는 정밀한 제어가 가능합니다.

메모리

에이전트가 메모리를 저장할 수 있다면, 수행 중인 작업에 관련된 메모리를 선택할 수 있어야 합니다. 이는 여러 이유로 유용할 수 있습니다. 에이전트는 원하는 행동의 예시(에피소드 메모리), 행동을 유도하는 지시문(절차적 메모리), 작업 관련 사실(시맨틱 메모리) 등을 선택할 수 있습니다.

Image

문제는 관련 메모리를 어떻게 선택하느냐입니다. 일부 인기 에이전트는 항상 컨텍스트에 불러오는 좁은 범위의 파일만 사용합니다. 예를 들어, 많은 코드 에이전트는 지시문(“절차적” 메모리)이나 예시(“에피소드” 메모리)를 저장하는 특정 파일을 사용합니다. Claude Code는 ‎⁠CLAUDE.md⁠를 사용하고, CursorWindsurf는 규칙 파일을 사용합니다.

하지만 에이전트가 더 많은 사실이나 관계(예: 시맨틱 메모리) 모음을 저장한다면, 선택이 더 어려워집니다. ChatGPT는 사용자별로 많은 메모리를 저장하고 선택하는 대표적인 인기 제품입니다.

메모리 인덱싱을 위해 임베딩이나 지식 그래프가 흔히 사용됩니다. 그래도 메모리 선택은 여전히 어렵습니다. AIEngineer World’s Fair에서 Simon Willison은 선택이 잘못된 사례를 공유했습니다: ChatGPT가 그의 위치 정보를 메모리에서 가져와 요청한 이미지에 예상치 못하게 삽입한 것입니다. 이런 예기치 않거나 원치 않는 메모리 검색은 사용자가 컨텍스트 윈도우가 “더 이상 내 것이 아니다” 라고 느끼게 만들 수 있습니다!

에이전트는 툴을 사용하지만, 너무 많은 툴이 제공되면 과부하가 발생할 수 있습니다. 이는 툴 설명이 겹쳐서 모델이 어떤 툴을 써야 할지 혼란스러워지기 때문입니다. 한 가지 방법은 RAG(검색 기반 생성)를 툴 설명에 적용해 작업에 가장 적합한 툴만 가져오는 것입니다. 최근 논문에서는 이 방식이 툴 선택 정확도를 3배 향상시킨다고 밝혔습니다.

지식

RAG는 매우 중요한 주제이며, 컨텍스트 엔지니어링의 핵심 과제가 될 수 있습니다. 코드 에이전트는 대규모 프로덕션에서 RAG를 잘 활용하는 대표적인 사례입니다. Windsurf의 Varun은 이러한 과제를 다음과 같이 잘 설명합니다:

코드 인덱싱 ≠ 컨텍스트 검색 … [우리는 인덱싱 & 임베딩 검색을 하고 있습니다 … AST 파싱 코드와 의미론적으로 중요한 경계로 청킹 … 코드베이스가 커질수록 임베딩 검색은 검색 휴리스틱으로서 신뢰도가 떨어집니다 … grep/파일 검색, 지식 그래프 기반 검색, 그리고 [컨텍스트]를 관련성 순으로 재정렬하는 단계 등 다양한 기법을 조합해야 합니다.

컨텍스트 압축

컨텍스트 압축은 작업 수행에 필요한 토큰만 유지하는 것을 의미합니다.

컨텍스트 요약

에이전트 상호작용은 수백 번의 턴과 토큰이 많이 드는 툴 호출로 이어질 수 있습니다. 요약은 이러한 문제를 관리하는 일반적인 방법입니다. Claude Code를 사용해본 적 있다면, 이를 직접 경험했을 것입니다. Claude Code는 컨텍스트 윈도우가 95%를 초과하면 “자동 압축”을 실행해 사용자-에이전트 상호작용 전체를 요약합니다. 이런 에이전트 경로 전체를 압축하는 방식에는 재귀적 또는 계층적 요약 등 다양한 전략이 있습니다.

Image

에이전트 설계의 특정 지점에 요약을 추가하는 것도 유용할 수 있습니다. 예를 들어, 토큰이 많이 드는 툴 호출(예: 검색 툴) 결과를 후처리할 때 요약을 사용할 수 있습니다. 두 번째 예로, Cognition은 에이전트 간 경계에서 요약을 사용해 지식 전달 시 토큰을 줄인다고 언급했습니다. 요약은 특정 이벤트나 결정을 반드시 포착해야 할 때 어려울 수 있습니다. Cognition은 이를 위해 미세 조정된 모델을 사용하며, 이 단계에 많은 노력이 들어간다는 점을 보여줍니다.

컨텍스트 트리밍

요약이 LLM을 활용해 가장 중요한 컨텍스트만 추출한다면, 트리밍은 종종 필터링이나 Drew Breunig이 말한 “가지치기”를 의미합니다. 이는 오래된 메시지를 목록에서 제거하는 등 하드코딩된 휴리스틱을 사용할 수 있습니다. Drew는 Provence라는 Question-Answering용 훈련된 컨텍스트 프루너도 언급했습니다.

컨텍스트 분리

컨텍스트 분리는 작업 수행을 돕기 위해 컨텍스트를 분할하는 것을 의미합니다.

멀티 에이전트

컨텍스트를 분리하는 가장 인기 있는 방법 중 하나는 여러 하위 에이전트에 분산하는 것입니다. OpenAI Swarm 라이브러리의 동기는 역할 분담이었으며, 에이전트 팀이 특정 하위 작업을 처리할 수 있도록 했습니다. 각 에이전트는 특정 툴, 지시문, 그리고 자체 컨텍스트 윈도우를 갖습니다.

Image

Anthropic의 멀티 에이전트 연구자는 다음과 같이 설명합니다: 분리된 컨텍스트를 가진 여러 에이전트가 단일 에이전트보다 더 좋은 성능을 보였는데, 각 하위 에이전트의 컨텍스트 윈도우가 더 좁은 하위 작업에 할당될 수 있기 때문입니다. 블로그에서는 다음과 같이 말했습니다:

[Subagents operate] 각자의 컨텍스트 윈도우로 병렬로 작동하며, 질문의 다양한 측면을 동시에 탐구합니다.

물론 멀티 에이전트의 과제도 있습니다. 예를 들어, Anthropic은 채팅보다 최대 15배 더 많은 토큰을 사용한다고 보고했으며, 하위 에이전트 작업 계획을 위한 프롬프트 엔지니어링과 하위 에이전트 간의 조율이 필요합니다.

환경을 통한 컨텍스트 분리

HuggingFace의 딥 리서처는 컨텍스트 분리의 또 다른 흥미로운 예시를 보여줍니다. 대부분의 에이전트는 툴 호출 API를 사용하며, 이는 툴에 전달할 수 있는 JSON 객체(툴 인자)를 반환합니다(예: 검색 API). 툴 피드백(예: 검색 결과)을 얻기 위해 툴에 인자를 전달합니다. HuggingFace는 CodeAgent를 사용하며, 툴 호출이 포함된 출력을 생성합니다. 코드는 샌드박스에서 실행됩니다. 툴 호출의 선택된 컨텍스트(예: 반환값)는 다시 LLM에 전달됩니다.

Image

이 방식은 환경에서 LLM과 분리된 컨텍스트를 관리할 수 있게 해줍니다. Hugging Face는 특히 토큰이 많이 드는 객체를 분리하는 데 이 방식이 유용하다고 언급했습니다:

[Code Agents allow for] 상태를 더 잘 관리할 수 있습니다 … 이미지/오디오/기타를 나중에 사용하려면? 문제 없습니다, 상태에 변수로 할당하고 나중에 사용하면 됩니다.

상태

에이전트의 런타임 상태 객체도 컨텍스트를 분리하는 데 매우 유용합니다. 이는 샌드박싱과 동일한 목적을 수행할 수 있습니다. 상태 객체는 컨텍스트를 기록할 수 있는 스키마로 설계할 수 있습니다. 스키마의 한 필드(예: ‎⁠messages⁠)는 에이전트의 각 턴마다 LLM에 노출할 수 있지만, 다른 필드에 정보를 분리해 더 선택적으로 사용할 수 있습니다.

LangSmith / LangGraph를 활용한 컨텍스트 엔지니어링

이 아이디어를 어떻게 적용할 수 있을까요? 시작하기 전에 도움이 되는 두 가지 기본 요소가 있습니다. 첫째, 데이터와 에이전트의 토큰 사용량을 추적할 수 있는 방법을 마련하세요. 이는 컨텍스트 엔지니어링에 노력을 집중할 지점을 파악하는 데 도움이 됩니다. LangSmith에이전트 추적/관찰에 적합하며, 이를 쉽게 할 수 있습니다. 둘째, 컨텍스트 엔지니어링이 에이전트 성능에 악영향을 주는지 개선하는지 간단히 테스트할 수 있는 방법을 마련하세요. LangSmith는 컨텍스트 엔지니어링의 영향을 테스트할 수 있는 에이전트 평가 기능을 제공합니다.

컨텍스트 쓰기

LangGraph는 스레드 범위(단기)와 장기 메모리를 모두 지원하도록 설계되었습니다. 단기 메모리는 체크포인팅을 통해 에이전트 상태를 모든 단계에 걸쳐 유지합니다. 이는 “스크래치패드”로 매우 유용하며, 정보를 상태에 기록하고 에이전트 경로의 어느 단계에서든 가져올 수 있습니다.

LangGraph의 장기 메모리는 에이전트와 여러 세션에 걸쳐 컨텍스트를 저장할 수 있습니다. 유연하게 설계되어, 사용자 프로필이나 규칙 같은 작은 파일 집합이나 더 큰 메모리 모음도 저장할 수 있습니다. 또한 LangMem은 LangGraph 메모리 관리를 돕는 다양한 추상화를 제공합니다.

컨텍스트 선택

LangGraph 에이전트의 각 노드(단계)에서 상태를 가져올 수 있습니다. 이를 통해 각 에이전트 단계마다 LLM에 어떤 컨텍스트를 제공할지 세밀하게 제어할 수 있습니다.

또한 LangGraph의 장기 메모리는 각 노드에서 접근할 수 있으며, 다양한 검색 방식(예: 파일 검색, 메모리 모음에 대한 임베딩 기반 검색)을 지원합니다. 장기 메모리에 대한 개요는 Deeplearning.ai 강좌에서 확인할 수 있습니다. 특정 에이전트에 메모리를 적용하는 예시는 Ambient Agents 강좌에서 확인할 수 있습니다. 이 강좌에서는 LangGraph 메모리를 활용해 이메일을 관리하고 사용자 피드백을 학습하는 장기 에이전트를 만드는 방법을 보여줍니다.

Image

툴 선택을 위해 LangGraph Bigtool 라이브러리는 툴 설명에 대한 의미론적 검색을 적용할 수 있습니다. 이는 많은 툴을 다룰 때 작업에 가장 적합한 툴을 선택하는 데 도움이 됩니다. 마지막으로, LangGraph에서 다양한 RAG 유형을 사용하는 방법을 보여주는 튜토리얼과 영상도 다수 제공하고 있습니다.

컨텍스트 압축

LangGraph는 저수준 오케스트레이션 프레임워크이므로, 에이전트를 여러 노드로 구성하고 각 노드의 로직을 정의하며, 노드 간에 전달되는 상태 객체를 정의할 수 있습니다. 이 제어권을 통해 여러 방식으로 컨텍스트를 압축할 수 있습니다.

일반적인 방법은 메시지 목록을 에이전트 상태로 사용하고, 내장 유틸리티를 활용해 주기적으로 요약하거나 트리밍하는 것입니다. 또한 툴 호출이나 에이전트 작업 단계의 결과를 후처리하는 로직을 추가할 수도 있습니다. 특정 지점에 요약 노드를 추가하거나, 툴 호출 노드에 요약 로직을 추가해 특정 툴 호출의 출력을 압축할 수도 있습니다.

컨텍스트 분리

LangGraph는 상태 객체를 중심으로 설계되어, 상태 스키마를 지정하고 각 에이전트 단계마다 상태에 접근할 수 있습니다. 예를 들어, 툴 호출에서 얻은 컨텍스트를 상태의 특정 필드에 저장해 LLM에서 분리할 수 있습니다. 상태 외에도 LangGraph는 컨텍스트 분리를 위한 샌드박스 사용을 지원합니다. E2B 샌드박스를 활용한 LangGraph 에이전트 예시는 해당 저장소에서 확인할 수 있습니다. Pyodide를 활용한 샌드박싱 예시는 해당 영상에서 확인할 수 있으며, 상태를 영속적으로 저장할 수 있습니다. LangGraph는 supervisorswarm 라이브러리 등 멀티 에이전트 아키텍처 구축도 폭넓게 지원합니다. 멀티 에이전트 활용법은 해당 영상(1, 2, 3에서 더 자세히 확인할 수 있습니다.

결론

컨텍스트 엔지니어링은 에이전트 개발자가 반드시 익혀야 할 기술로 자리잡고 있습니다. 여기서는 오늘날 인기 있는 다양한 에이전트에서 볼 수 있는 몇 가지 일반적인 패턴을 소개했습니다:

  • 컨텍스트 쓰기 – 에이전트가 작업을 수행하는 데 도움이 되도록 컨텍스트 윈도우 외부에 저장
  • 컨텍스트 선택 – 에이전트가 작업을 수행하는 데 도움이 되도록 컨텍스트 윈도우로 불러오기
  • 컨텍스트 압축 – 작업 수행에 필요한 토큰만 유지
  • 컨텍스트 분리 – 작업 수행을 돕기 위해 컨텍스트를 분할

LangGraph는 각 패턴을 쉽게 구현할 수 있도록 하며, LangSmith는 에이전트 테스트와 컨텍스트 사용량 추적을 쉽게 할 수 있도록 지원합니다. LangGraph와 LangSmith를 함께 사용하면, 컨텍스트 엔지니어링의 최적 적용 지점을 찾고, 구현하고, 테스트하고, 반복하는 선순환을 만들 수 있습니다.

Edit this page