나의 에이전트 시스템은 밤에 꿈을 꾸며, 그곳에서 기억이 만들어진다
요약
에이전트의 지속 가능한 메모리 구축을 위해 뇌의 수면 과정을 모방한 '꿈꾸기(dreaming)' 시스템을 제안합니다. 오프라인에서 데이터를 클러스터링하고 성찰하여 가치 있는 정보를 장기 저장소로 승격시키는 구조를 설명합니다.
핵심 포인트
- 에이전트가 직접 메모리에 쓰지 않고 오프라인 통합 과정을 거침
- 스케줄러 기반의 일회성 프로세스로 데몬 방식의 오버헤드 방지
- 단일 작성자(Single-writer) 모델을 통한 데이터 충돌 방지
- 엄격한 토큰 예산을 설정하여 LLM 비용을 효율적으로 통제
원문은 olund.dev에 게시되었습니다.
이 시리즈의 처음 네 포스트는 에이전트가 세션 전반에 걸쳐 회상하는 지속 가능한 사실(durable facts)에 대해 계속 언급합니다. 그 사실들 중 그 어떤 것도 에이전트가 작업 도중에 "이것은 영원히 기억할 가치가 있다"라고 결정해서 저장된 것이 아닙니다. 에이전트가 그 순간 기억할 만하다고 생각하는 거의 모든 것은 일주일 뒤에는 노이즈(noise)가 되며, 에이전트에게 지속 가능한 메모리(durable memory)로의 직접적인 쓰기 경로를 제공하면 에이전트는 확신에 찬 쓰레기(confident junk)로 그곳을 채워버릴 것입니다.
대신, 나의 시스템은 뇌가 하는 방식을 따릅니다. 즉, 오프라인에서 통합(consolidates offline)합니다. 하루에 두 번, 타이머에 맞춰 프로세스가 깨어나 마지막 실행 이후에 일어난 일을 읽고, 게이트(gates)를 통해 무엇이 살아남을 가치가 있는지 천천히 결정합니다. 나는 이것을 꿈꾸기(dreaming)라고 부르며, 이 이름은 단순한 농담 이상임이 밝혀졌습니다. 설계 질문들이 진정으로 수면의 형태를 띠고 있기 때문입니다. 무엇을 다시 재생(replay)할 것인가? 무엇을 장기 저장소(long-term storage)로 승격시킬 것인가? 무엇을 폐기할 것인가? 그리고 프로세스가 오작동하면 어떻게 되는가?
형태: 데몬(daemon)이 아닌 타이머
꿈꾸기는 스케줄러(scheduler)에 의해 실행되는 일회성 프로세스입니다. 가벼운 작업(추천, "주의가 필요한 사항")을 위한 오전 사이클과, 무거운 메모리 승격(memory-promotion) 단계를 위한 저녁 사이클이 있습니다. 상주하는 데몬(resident daemon)도, 큐 서비스(queue service)도 없습니다. 각 실행은 파일을 읽고, 생각하고, 파일을 쓰고, 종료되는 새로운 프로세스입니다. 나의 스택(stack)에 있는 모든 것은 파일 시스템 우선(filesystem-first)이며, 통합(consolidation)도 예외는 아닙니다. 만약 기기가 꺼져 있다면, 해당 사이클은 건너뛰어지며 다음 사이클이 처리되지 않은 범위를 이어받습니다.
스케줄보다 더 중요한 두 가지 운영 규칙이 있습니다:
정확히 하나의 기기만이 꿈을 꿉니다. 나의 상태(state)는 기기 간에 동기화되며, 두 개의 통합기(consolidators)가 동일한 지속 가능한 파일(durable files)을 쓰는 것은 끝없는 충돌을 일으킬 것입니다. 하나의 기기가 꿈꾸기를 소유하며, 다른 기기들은 그 결과를 읽습니다. 단일 작성자(Single-writer) 모델은 존재하는 가장 저렴한 동시성 모델(concurrency model)이며, 여기서 이 모델을 선택함으로써 병합(merge) 문제가 발생하기도 전에 한 범주의 문제들을 통째로 제거했습니다.
모든 사이클에는 엄격한 토큰 예산(token budget)이 있습니다. 성찰(reflection) 단계는 LLM을 호출하며, 바쁜 하루의 이벤트들에 대해 제한 없는 루프를 돌리는 것은 제한 없는 청구서와 같습니다. 각 사이클은 고정된 입력 및 출력 제한(cap)을 가집니다. 사이클 중간에 제한에 도달하면, 이미 생성된 내용을 마무리하여 게이팅(gating)하고, 초과분을 기록한 뒤, 다음 사이클이 그 지점부터 계속되도록 합니다. 통제 불능의 하루가 발생하더라도 비용은 알려진 최대치 내로 제한됩니다. 일일 지출은 약 1~3달러 정도이며, 스스로 유지되는 메모리 시스템 치고는 저렴하다고 생각합니다.
파이프라인: 클러스터링(cluster), 성찰(reflect), 점수 산정(score), 게이팅(gate)
저녁 단계에서는 하루의 에피소드 이벤트(도구 호출(tool calls), 세션 요약, 포착된 생각 등)를 다음과 같은 고정된 순서로 실행합니다:
- 클러스터링 (Cluster). 이벤트들은 임베딩(embedded)되어 밀도(density)에 따라 그룹화됩니다. 지속적인 사실(durable fact)은 거의 단일 이벤트에서 나오지 않습니다. 그것은 여러 세션에 걸쳐 나타나는 동일한 주제로부터 나옵니다.
- 성찰 (Reflect). LLM이 각 클러스터를 읽고 후보를 제안합니다: "이 이벤트들은 X라는 사실을 뒷받침합니다." 각 후보는 이를 뒷받침하는 이벤트의 ID를 포함하므로, 전체 과정 동안 출처(provenance)가 유지됩니다.
- 점수 산정 (Score). 후보들은 신뢰도 점수(confidence score)를 부여받고 구조적 검사(structural checks)를 통과해야 합니다: 충분히 구별되는 뒷받침 이벤트가 있는지, 충분한 시간에 걸쳐 분포되어 있는지, 이미 알고 있는 내용의 재진술은 아닌지 등을 확인합니다.
- 판단 (Judge). 기존 메모리를 대상으로 두 가지 LLM 기반 검사가 실행됩니다: 이것이 저장된 사실과 모순되는가, 그리고 중복되는가?
- 승격 또는 대기열 (Promote or queue). 신뢰도가 높고 충분히 입증된 후보는 자동으로 지속 가능한 메모리(durable memory)에 기록될 수 있습니다. 그 외의 모든 것은 검토 대기열(review queue)의 카드 형태로 남으며, 저는 키 입력 한 번으로 이를 수락하거나 거절합니다. 수락된 항목을 적용하면 git 커밋(git commit)이 생성됩니다. 즉, 메모리 파일의 히스토리 자체가 감사 로그(audit log)가 됩니다.
가장 중요한 단 하나의 설계적 사실은 다음과 같습니다: 흥미로운 엔지니어링은 전적으로 3단계에서 5단계 사이에 존재합니다. 후보(candidates)를 생성하는 것은 쉽습니다. 어떤 이벤트 로그(event log)에 대해서든 어떤 LLM이라도 기꺼이 메모리를 제안할 것입니다. 시스템의 품질은 무엇을 기록하기를 거부하느냐에 따라 결정됩니다. 지속적인 메모리 오염(memory pollution)은 복리로 쌓입니다. 잘못된 사실이 회상되고, 믿어지고, 인용되며, 수십 개의 미래 세션에서 그 위에 구축됩니다. 따라서 쓰기 게이트(write gate)야말로 편집증(paranoia)이 필요한 곳입니다.
구체적으로는 다음과 같습니다: 자동 승격(auto-promotion)을 위해서는 신뢰도 임계값(confidence threshold)과 최소 3개의 뒷받침하는 이벤트(supporting events)가 모두 필요합니다. 두 개의 지지자를 가진 후보는 리플렉터(reflector)에 의해 진정으로 지속 가능한 것으로 판단될 수 있지만, 여전히 관리 없이 메모리에 진입할 수는 없습니다. 대신 검토 대기열(review queue)로 라우팅됩니다. 규칙은 "두 개의 이벤트는 증거가 아니다"가 아니라, "두 개의 이벤트는 인간을 건너뛰기에 충분한 증거가 아니다"입니다.
수업료를 지불할 가치가 있는 두 가지 실패 사례
조용한 하한선 불일치(The silent floor mismatch). 한동안 클러스터링(clustering) 단계에서는 두 개의 이벤트로 구성된 클러스터를 형성할 수 있도록 허용되었으나, 스코어링(scoring) 단계에서 세 개 미만의 뒷받침하는 이벤트가 있는 모든 후보를 조용히 탈락시켰습니다. 리플렉터가 지속 가능하다고 판단한 모든 두 이벤트 클러스터는 구조적으로 폐기되었습니다. 이유와 함께 거절된 것이 아니라, 그냥 사라진 것입니다. 파이프라인은 건강해 보였습니다. 사이클은 정상(green)으로 돌아갔고, 승격도 일어났으며, 오류도 없었습니다. 단지 있어야 할 것보다 조용했을 뿐이며, 조용함은 알아차리기 가장 어려운 결함입니다. 해결책은 점수 하한선을 클러스터 하한선에 맞게 낮추고, 세 개의 이벤트 규칙을 원래 있어야 할 곳인 자동 승격 경계(auto-promote boundary)로 옮기는 것이었습니다. 이제 후보는 검토 대기열까지 살아남아 인간이 이를 볼 수 있게 되었습니다. 일반적인 교훈은 다음과 같습니다: 파이프라인의 두 단계가 임계값에 대해 의견이 다를 때, 그 불일치는 오류를 발생시키지 않습니다. 대신 조용히 출력을 축소시키며, 당신은 몇 달 동안 그 조용함을 "한가한 주간" 때문이라고 생각하게 될 것입니다.
꿈을 중단시킨 판정자들. 모순(contradiction)과 중복(duplicate)을 판정하는 프로세스가 원래는 심각한 LLM 오류—서비스 중단이나 할당량(quota) 문제—를 발생시키면, 즉시 전체 사이클을 중단하고 그 이전에 수행된 모든 클러스터링(clustering)과 성찰(reflection) 작업을 폐기해 버렸습니다. 반면, 깨진(garbled) LLM 응답은 보수적인 기본값(default)을 사용하여 우아하게 처리되었습니다. 이러한 비대칭성은 말이 되지 않았습니다. 일시적인 네트워크 오류가 손상된 답변보다 더 파괴적이었기 때문입니다. 이제 정책은 통일되었습니다. LLM을 기반으로 하는 모든 단계에서 심각한 오류가 발생하면, 보수적인 기본값(모순을 찾지 못함, 새로운 것으로 간주)으로 강등(degrade)되어 사이클을 완료합니다. 야간 배치 프로세스(nightly batch process)에서는 엄격함보다 회복 탄력성(resilience)이 더 중요합니다. 보수적인 기본값은 검토 큐에 중복된 카드 하나를 남길 위험이 있지만, 중단은 하루 치의 작업을 폐기해 버립니다.
통합은 사실뿐만 아니라 기술을 성장시킨다
내가 계획하지 않았지만 현재 가장 가치 있게 여기는 부분은 다음과 같습니다. 지속적인 사실을 찾아내는 것과 동일한 클러스터링(clustering)이 반복되는 작업(recurring work) 또한 찾아낸다는 점입니다. 사이클이 특정 기술(skill)로 커버되지 않는 동일한 종류의 절차가 여러 날에 걸쳐 최소 세 번 이상의 사례에서 수행되는 것을 감지하면, 시스템은 새로운 기술을 제안합니다. 그리고 신뢰도 임계값(confidence threshold)을 넘으면 초안 기술 파일(draft skill file)을 자동으로 작성합니다. 이 초안은 비활성 상태입니다. 내가 명시적으로 승격(promote)시키기 전까지는 모든 에이전트 하네스(agent harness)에 보이지 않습니다. 인간의 관문(human gate)이 사라진 것은 아닙니다. 다만
- 작업 경로(work path)에서 쓰기 경로(write path)를 분리하십시오. 작업 중인 에이전트는 내구성(durability)을 판단하기에 가장 부적절한 주체입니다. 에이전트가 추가 전용 로그(append-only log)에 자유롭게 기록하게 하되, 무엇을 영구적으로 남길지는 더 느리고 게이트가 있는 프로세스(gated process)가 결정하도록 하십시오.
- 거부(refusal) 단계에 엔지니어링 역량을 집중하십시오. 후보 생성(candidate generation)은 비용이 들지 않지만, 메모리 오염(memory pollution)은 복리로 쌓입니다. 교차 검증(corroboration floors), 모순 체크(contradiction checks), 그리고 기준치 미달인 모든 항목에 대한 인간 큐(human queue)가 곧 제품입니다.
- 인간 관문(human gates)을 가장 비용이 적게 드는 체크포인트로 이동시키되, 삭제하지 마십시오. 자동 초안 작성(auto-draft) 후 수동 활성화(manual activate)하는 방식이 모든 것을 수동으로 하는 방식이나 완전 자율 방식보다 뛰어납니다.
- 배치 프로세스(batch processes)는 성능이 저하되어야지, 중단되어서는 안 됩니다. 보수적인 기본 설정은 약간의 낭비를 초래하지만, 중단된 사이클은 하루를 통째로 낭비하게 만듭니다.
- 조용한 불일치(silent disagreements)가 있는지 파이프라인을 감사하십시오. 일관되지 않은 임계값(thresholds)을 가진 두 단계는 에러를 발생시키지 않고 그저 조용히 넘어갈 뿐입니다. 각 단계에 들어오고 나가는 양을 측정하고, 구조적인 급감(structural drops)이 발생하면 경보를 울리십시오.
- 지출을 구조적으로 제한하십시오. 우아한 초과 허용(graceful overrun) 기능이 포함된 사이클당 토큰 상한선(token ceiling)을 설정하면, "무제한 입력에 대한 LLM 루프"라는 위험 요소를 관리 가능한 항목(line item)으로 바꿀 수 있습니다.
이 시리즈의 모든 계층은 이 계층에 기여합니다. 세션(sessions)은 이벤트를 기록하고, 존재 계층(presence layer)은 그 기록의 귀속성을 유지하며, 문서 표준(docs standard)은 결정을 기록하고, 코드 맵(code map)은 발자취를 소비합니다. 그리고 꿈꾸기(dreaming)는 이 모든 하루의 과정을 보존할 가치가 있는 몇 문장으로 바꾸는 하단의 느린 프로세스입니다.
AI 자동 생성 콘텐츠
본 콘텐츠는 Dev.to AI tag의 원문을 AI가 자동으로 요약·번역·분석한 것입니다. 원 저작권은 원저작자에게 있으며, 정확한 내용은 반드시 원문을 확인해 주세요.
원문 바로가기