컨텍스트가 길어질수록 에이전트가 나빠지는 이유
컨텍스트 부패(context rot)를 구체적으로. 한 턴은 모델에 보내는 하나의 자기완결적 요청이며, 그 요청이 길거나 도구 호출로 불어나면 답변의 정확도가 측정 가능한 수준으로 떨어집니다. 그 요청에 무엇이 담기는지, 담기지 않을 때 무엇부터 버리는지, 그리고 도구 결과를 요약시키는 대신 답을 쓰기 전에 요청을 다시 조립하는 이유.
월요일에 잘 답하던 에이전트가 금요일에는 두루뭉술하게 답합니다. 스무 개 메시지 전에는 지키던 지시를 더 이상 지키지 않습니다. 도구를 호출해 올바른 데이터를 받고도, 그 절반을 무시한 답을 씁니다. 오류도 없고 로그도 남지 않으며 대화는 멀쩡해 보입니다. 이를 보통 context rot(컨텍스트 부패) 라고 부르는데, 흔한 설명인 "컨텍스트 창이 꽉 찼다"는 우리가 측정한 결과와 다릅니다.
한 턴, 처음부터 끝까지
턴은 하나의 요청으로 시작해, 도구가 도는 동안 불어나고, 답을 쓰기 전에 다시 조립됩니다. 볼 만한 것은 가운데 상태입니다. 대부분의 에이전트가 바로 그 상태에서 답을 씁니다.
모든 턴은 하나의 자기완결적 요청
모델은 턴과 턴 사이에 아무것도 보관하지 않습니다. 반대편에는 세션이 없고, 한 시간 전에 무슨 말을 했는지에 대한 기억도 없으며, 건네받지 않은 것을 스스로 찾아볼 방법도 없습니다. 매 턴 플랫폼이 완전한 요청을 조립해 통째로 보내고, 답변은 오직 그 요청에서만 생성됩니다.
네트워크 감각이 있다면 이것은 데이터그램에 가깝습니다. 자기완결적이고, 한 번 보내지며, 수신 측이 필요로 하는 모든 것을 담고, 송신 측이 지켜야 하는 크기 한도가 있습니다. 비유가 깨지는 지점이 둘 있고, 둘 다 중요합니다.
- 전송 중에 잃는 것은 없습니다. 보낸 것은 전부 도착합니다. 달라지는 것은 모델이 실제로 얼마나 주의를 기울이는가입니다 — 손실은 선로가 아니라 수신 측 내부에서 일어납니다.
- 배치가 답을 바꿉니다. 라우터는 페이로드를 재배열했다고 다르게 동작하지 않지만 모델은 다르게 동작합니다. 같은 사실을 같은 요청 안에 두 가지 방식으로 배치했더니, 한쪽은 정답을, 다른 쪽은 오답을 냈습니다. 이후 내용의 대부분이 이 결과에서 나옵니다.
요청에는 무엇이 들어 있나
순서는 모델이 보는 순서 그대로입니다. 유지/잘림 열은 요청이 들어가지 않을 때 플랫폼이 적용하는 우선순위이며, 순위는 상대적인 것이지 정해진 개수의 블록을 버린다는 뜻이 아닙니다.
히스토리 위쪽은 전부 하나의 시스템 메시지입니다. 의도적입니다. 에이전트의 경계, 내 지식 베이스, 답변 언어는 대화가 아니며, 모델은 그것들이 어디에 놓였는지에 따라 다르게 다룹니다.
들어가지 않을 때 무엇부터 버리나
예산을 넘긴 요청은 끝에서부터 잘리지 않습니다. 들어갈 때까지 우선순위 순서로 블록이 버려집니다.
- 가장 오래된 히스토리부터 — 그리고 버려진 턴은 폐기되지 않고 롤링 요약으로 압축되므로, 표현은 남지 않아도 나눈 내용은 남습니다.
- 점수가 낮은 기억, 그다음 점수가 낮은 검색 구절 — 꼬리부터 버리므로 가장 관련 있는 자료가 마지막까지 남습니다.
- 프로필, 그다음 요약.
- 에이전트의 지시, 내 지식 베이스, 질문은 절대 버리지 않습니다. 질문 하나만으로 예산을 넘기면 잘라내되 잘렸다고 표시합니다 — 문장이 왜 단어 중간에서 끊겼는지 모델이 짐작하게 두지 않고 알려 줍니다.
이 순서가 컨텍스트 예산에서 정직한 부분입니다. 무언가는 반드시 나가야 하고, 무엇이 나가는지 말하지 않는 시스템은 마침 마지막에 있던 것을 조용히 버립니다.
들어가는 것과 읽히는 것은 다르다
놀란 지점이 여기입니다. 답하는 데 필요한 사실이 모든 조건에서 온전히 존재하는 테스트를 만들었습니다. 아무것도 버려지지 않았고, 잘리지 않았으며, 어디에도 정보가 빠지지 않았습니다. 바뀐 것은 요청의 배치뿐입니다. 수백 건의 레코드에 대한 다중 조건 필터링을, 우리 로컬 모델과 클라우드 모델 각각에 대해 여러 번:
| 같은 사실을 어떻게 배치했는가 | 정답 |
|---|---|
| 관련 있는 행만 담은 깨끗한 메시지 하나 | 8 / 8 |
| 완전히 같은 행을 도구 결과로 돌려준 경우 | 0 / 8 |
| 전체 레코드에 무관한 도구 결과 다섯 건을 더한 경우 | 0 / 6 |
| 그 누적을 깨끗한 메시지 하나로 다시 조립한 경우 | 8 / 8 |
두 개의 대조가 뻔한 해석을 걸러냅니다. 깨끗한 요청을 같은 총량의 메시지 둘로 나눠도 여전히 8 / 8이었으니 변수는 길이가 아닙니다. 추린 행을 도구 결과로 되돌려 주면 여전히 0 / 8이었으니 "데이터가 질문에 더 가까이 있어야 한다"도 아닙니다. 도구 발판과 무관한 자료는 어디에 놓이든 모델의 주의를 두고 경쟁합니다.
클라우드 모델은 더 견고했지만 면역은 아니었습니다. 대부분의 과제에서 버텼지만, 한 턴 분량의 누적된 도구 결과가 요청에 들어가자 단일 값 조회에서 0 / 3까지 떨어졌습니다.
솔직히 밝혀 둘 한계가 둘 있습니다. 이것은 우리 과제에 대한 우리 자신의 테스트이지 공개 벤치마크가 아닙니다. 그리고 모델의 상한을 올리지는 못합니다. 같은 과제를 한 단계 어렵게 만들자 모든 배치에서 0점이었습니다. 그 모델이 애초에 해내지 못하는 일이었기 때문입니다. 요청을 다시 배치하는 것은 배치 때문에 잃고 있던 정확도를 되찾는 일이지, 모델에 없는 능력을 사 오는 일이 아닙니다.
그래서 한 턴에는 두 단계가 있습니다: 작업, 그리고 답변
이것이 페이지 맨 위 애니메이션이 보여 주는 갈림입니다.
작업에는 지저분한 요청이 필요합니다. 모델은 다음 도구를 부를지 결정하기 위해 자신의 도구 호출과 원본 결과를 봐야 합니다. 이 단계는 그대로입니다.
답변에는 필요 없습니다. 도구가 끝나면 플랫폼은 새 요청을 조립합니다 — 같은 시스템 지시, 대화의 짧은 요약, 이번 턴에 실제로 찾아낸 사실, 그리고 질문. 여러분이 받는 답변은 거기서 생성됩니다. 도구 호출, 원본 페이로드, 중간 추론은 그 안에 나타나지 않습니다.
요약을 남기는 이유는 실제 질문이 흔히 "네" 또는 "그럼 두 번째는요?"이기 때문입니다. 가장 좋은 결과를 낸 단일 메시지 배치는 한 턴짜리이고 대화는 그렇지 않습니다. 요약은 별도의 턴으로 복원되는 대신 같은 메시지 안으로 접혀 들어가며, 측정 가능한 비용은 없고 지시어는 계속 풀립니다.
우리가 의도적으로 하지 않는 것
도구 출력이 컨텍스트 창을 넘칠 때 흔한 해법은 모델에게 결과마다 요약을 시키는 것입니다. 우리는 그렇게 하지 않으며, 이유는 위의 테스트입니다. 만점을 받은 배치는 원본 데이터를 다시 조립한 것이었고, 정확도를 되찾는 데 요약 단계는 필요하지 않았습니다. 그것을 더한다는 것은 어떤 사실이 중요한지를 모델이 정하게 한다는 뜻인데, 이 시스템의 설계 원칙은 코드가 정확히 해내는 일을 모델에 맡기지 않는 것입니다. 고객이 물어본 바로 그 숫자를 떨어뜨린 요약기는 소리 없이 실패하면서 좋은 답처럼 보입니다.
사실이 정말로 들어가지 않을 때는 잘라내되, 잘렸다는 사실을 요청 안에 명시하고 빠진 부분을 지어내지 말라는 지시를 함께 넣습니다. "앞의 마흔 건까지만 볼 수 있었습니다"라고 말하는 에이전트가, 나머지를 자신 있게 지어내는 에이전트보다 값집니다.
이것이 의미하는 바
설정할 것은 없습니다. 위의 내용이 이 플랫폼에서 모든 에이전트가 동작하는 방식입니다.
실제로 달라지는 점:
- 긴 대화가 계속 쓸 만합니다. 스무 번째 턴도 첫 턴과 같은 방식으로 조립되고, 창에서 밀려난 것은 사라지는 대신 요약으로 남습니다.
- 많은 데이터를 돌려주는 도구가 답변을 오염시키지 않습니다. 결과에는 상한이 있고, 최종 답변은 원본 페이로드를 더 이상 지니지 않는 요청에서 쓰입니다.
- 도구를 쓴 턴은 모델 호출이 한 번 늘어납니다 — 짧은 답변에서 약 1초. 그동안 채팅은 침묵하지 않고 무엇을 하고 있는지 보여 줍니다.
분명히 건넨 것을 에이전트가 무시한다고 느낀다면, 유용한 질문은 "컨텍스트 창이 너무 작은가"가 아니라 "그것이 어느 블록에 있었고, 그 요청에 무엇이 함께 실려 있었는가"입니다. 대화는 턴과 턴 사이에 어디에 있나가 이 페이지의 나머지 절반 — 모델이 아무것도 보관하지 않는다면 우리 쪽에는 무엇이 있고 요청은 무엇으로부터 조립되는가 — 에 답합니다. 근거 있는 답변은 무엇이 검색되는지, 고객별 기억은 무엇이 기억되는지, 도구와 MCP는 도구 결과 하나가 창 전체를 차지하지 못하게 하는 예산을 다룹니다.