Skip to content
devchaenPublic

About

Scalable long-term memory for AI agents — a from-scratch reimplementation of the Mem0 paper (arXiv:2504.19413)

Resources

Stars

0 stars

Watchers

0 watching

Forks

Latest commit

 

History

6 Commits

Folders and files

Repository files navigation

memoir 🧠

나를 기억하는 회고 컴패니언 — Mem0 논문(arXiv:2504.19413)의 장기 기억 아키텍처를 학습 목적으로 재구현한 개인 프로젝트입니다.

매일의 회고를 대화로 남기면, memoir가 핵심 사실만 추출해 기억하고 —

"작년 이맘때 나 무슨 고민 했었지?" "요즘 운동 얼마나 자주 했어?"

같은 질문에 타임스탬프 기반 시간 추론으로 답합니다. 모순되는 새 정보가 오면(이직, 취향 변화, 이사) 기존 기억을 스스로 갱신·무효화합니다.

데모

나 › 요즘은 디카페인만 마셔. 카페인 때문에 잠을 못 자겠더라

memoir › 커피를 좋아하셨는데 디카페인으로 바꾸셨군요. 수면이 좀 나아졌나요?

╭─ 🧠 메모리 연산 ──────────────────────────────────────╮
│ ↻ UPDATE  사용자는 커피를 좋아한다                      │
│           → 사용자는 커피를 좋아하며 디카페인만 마신다   │
│ + ADD    사용자는 2026-07경 카페인으로 수면 문제를 겪음 │
╰──────────────────────────────────────────────────────╯

턴마다 ADD / UPDATE / DELETE / NOOP 연산 로그가 표시되어, 논문의 메모리 파이프라인이 실제로 어떻게 동작하는지 볼 수 있습니다.

아키텍처 (논문 ↔ 코드 대응)

대화 (mₜ₋₁, mₜ)
   │
   ▼ [쓰기 경로]
① Extraction  ── 요약 S + 최근 m개 메시지 컨텍스트로 사실 추출 ── pipeline/extraction.py
② Update      ── 유사 메모리 top-s 검색 → LLM tool call로       ── pipeline/update.py
                 ADD/UPDATE/DELETE/NOOP 선택 (Algorithm 1)
   │
   ▼
Qdrant (벡터, 로컬) + SQLite (대화·이력·요약)
   ▲
   │ [읽기 경로]
③ Retrieval   ── 의미 검색 → 타임스탬프 포함 컨텍스트로 응답    ── retrieval + cli.py
논문 이 구현 비고
추출 프롬프트 P = (S, 최근 m개, 쌍) pipeline/extraction.py m=10 (논문 설정)
비동기 요약 갱신 모듈 pipeline/summary.py N턴마다 asyncio.create_task
Tool call 기반 4연산 (Algorithm 1) pipeline/update.py s=10, tool_choice="required"
DELETE (물리 삭제) soft delete로 변경 LLM 오판 복구 가능 (Mem0ᵍ의 invalid 방식 차용)
GPT-4o-mini 동일 temperature=0
OpenAI 임베딩 bge-m3 로컬 (dim=1024) 한국어 성능, 무료·오프라인
벡터 DB Qdrant 로컬 임베디드 모드 서버·도커 불필요
Mem0ᵍ 2단계 추출 (엔티티→관계) graph/pipeline.py 취향 그래프: (사용자)-[prefers]->(디카페인)
노드 해소 (유사도 ≥ t) GraphMemory._resolve_node t=0.85
충돌 감지 → invalid 표시 LLM update resolver 물리 삭제 없음, temporal 보존
이중 검색 (entity-centric + semantic triplet) GraphMemory.search 결과 병합
Neo4j NetworkX 기본 + Neo4j 옵셔널 같은 BaseGraphStore 인터페이스, 백엔드 교체 가능

원 논문과 달리 한국어 상대 시간 정규화("지지난주", "재작년" → 절대 날짜)를 추출 단계에 내장했습니다. 논문에서 OpenAI 메모리가 temporal 질문에서 J<15%로 폭락한 원인이 타임스탬프 누락이었기 때문에, 시간 정보 보존을 1급 요구사항으로 다룹니다.

시작하기

# Python 3.10+
pip install -e ".[dev]"

cp .env.example .env   # OPENAI_API_KEY 입력

memoir                 # 챗 시작 (최초 실행 시 bge-m3 모델 ~2GB 다운로드)

명령어: /memories 저장된 기억 · /graph 관계 그래프 · /stats p50/p95 지연 통계 · /history <id> 변경 이력 · /forget <id> 삭제 · /exit

옵션 (.env):

  • MEMOIR_ASYNC_WRITE=1 — 쓰기(추출·갱신)를 백그라운드 큐로 분리 (Phase 3, 응답 지연 최소화)
  • MEMOIR_GRAPH_ENABLED=0 — 그래프 메모리 끄기 (턴당 LLM 호출·비용 절감)
  • MEMOIR_GRAPH_BACKEND=neo4j — Neo4j 백엔드로 전환:
pip install -e ".[graph]"
docker compose up -d        # http://localhost:7474 에서 그래프 시각화

웹 UI

채팅 + 기억 카드 + 관계 그래프 시각화(vis-network) + 지연 통계를 브라우저에서:

pip install -e ".[web]"
memoir-web                  # http://127.0.0.1:8787

Qdrant 로컬 모드는 단일 프로세스 전용이라 웹 UI와 CLI를 동시에 띄울 수 없습니다.

테스트

가짜 LLM/임베더로 파이프라인 로직을 검증합니다 (API 키·torch 불필요):

pytest
  • 중복 사실 → NOOP (중복 방지)
  • 모순 정보 → soft DELETE, 검색 제외 + 데이터 보존
  • UPDATE → 병합 + ADD→UPDATE 감사 이력
  • LLM이 존재하지 않는 memory_id 지목(환각) → 안전한 NOOP 폴백
  • user_id 격리 — 다른 사용자 메모리가 검색·갱신 후보에 절대 노출되지 않음

평가 (Phase 5)

한국어 회고 시나리오 페르소나 5개 × 20문항 = 100문항 (single-hop / temporal / multi-hop / preference 각 25개). 시나리오별로 다른 user_id로 주입해 격리를 겸사겸사 검증하며, 세션 주입 → 답변 생성 → LLM-as-a-Judge(논문 부록 A) 채점 → 유형별·시나리오별 J + 95% 신뢰구간 + 오답 목록 + 지연 리포트를 출력합니다:

python -m eval.run_eval --runs 3         # Mem0ᵍ (그래프 포함), judge 3회
python -m eval.run_eval --no-graph      # Mem0 기본형과 비교
python -m eval.run_eval --scenario eval/scenarios/01_developer.json  # 단일 시나리오
python -m eval.judge cases.jsonl         # 임의 QA 채점

100문항 기준 표본 95% CI는 약 ±8%p — "유형별 난이도 패턴이 논문과 일치한다" 수준의 주장이 가능한 규모입니다. 논문의 Mem0 vs Mem0ᵍ 2%p 차이 검증에는 LOCOMO 규모(~2,000문항)가 필요합니다. 평가 데이터는 임시 디렉토리에 격리되어 개인 메모리를 오염시키지 않습니다.

로드맵

  • Phase 1 — 추출 + 저장 + 검색 (동작하는 기억 챗봇)
  • Phase 2 — 갱신 파이프라인 (ADD/UPDATE/DELETE/NOOP, 요약 비동기 갱신, 감사 로그)
  • Phase 3 — 쓰기 경로 큐 분리 (BackgroundWriter), p50/p95 지연 계측 (/stats)
  • Phase 4 — 취향 그래프 (Mem0ᵍ): 2단계 추출, 노드 해소, 충돌 무효화, 이중 검색 (NetworkX 기본 + Neo4j 옵셔널)
  • Phase 5 — 한국어 평가셋 100문항 + LLM-as-a-Judge 러너 (J 77% → 프롬프트 개선 → 93%)
  • LOCOMO 서브셋 평가 연동 (python -m eval.locomo) — 논문 수치와 직접 비교
  • 웹 UI (memoir-web) — 채팅·기억 카드·그래프 시각화·지연 통계

참고

  • 논문: Chhikara et al., Mem0: Building Production-Ready AI Agents with Scalable Long-Term Memory (2025)
  • 원저자 공식 구현: mem0ai/mem0 — 본 프로젝트는 학습·커스터마이징 목적의 독립 재구현입니다

License

MIT

About

Scalable long-term memory for AI agents — a from-scratch reimplementation of the Mem0 paper (arXiv:2504.19413)

Resources

Stars

0 stars

Watchers

0 watching

Forks

Releases

Packages

Contributors

Languages