Skip to content

scream4ik/MemState

MemState — Transactional Memory for AI Agents

Keeps SQL and Vector DBs in sync. No drift. No ghost data. ACID-like consistency for agent state.

PyPI version PyPI Downloads Python versions License Tests


Why MemState exists

AI agents usually store memory in two places:

  • SQL (structured facts)
  • Vector DB (semantic search context)

These two drift easily:

❌ Example of real-world corruption

# Step 1: SQL write succeeds
db.update("user_city", "London")

# Step 2: Vector DB update fails (timeout)
vectors.upsert("User lives in London")  # ❌ failed

# Final state:
SQL: London
Vectors: New YorkAgent retrieves stale context and behaves unpredictably

Failures, crashes, retries, malformed payloads — all silently accumulate “ghost vectors” and inconsistent state.

Vector DBs don't have transactions. JSON memory has no schema. Agents drift over time.


What MemState does

MemState makes all memory operations atomic:

SQL write + Vector upsert
→ succeed together or rollback together

Also provides:

  • Rollback: undo N steps (SQL + vectors)
  • Type safety: Pydantic schema validation
  • Append-only Fact Log: full version history
  • Crash safety: WAL replay for vector sync


Demo: Without MemState → memory gets inconsistent ❌   |   With MemState → atomic, type-safe, rollbackable agent state ✅
All demo scripts are available in the examples/ folder for reproducibility.


Minimal example (copy–paste)

pip install memstate[chromadb]
from memstate import MemoryStore, Fact, SQLiteStorage
from memstate.integrations.chroma import ChromaSyncHook
import chromadb

# Storage
sqlite = SQLiteStorage("state.db")
chroma = chromadb.Client()

# Hook: sync vectors atomically with SQL
hook = ChromaSyncHook(
    client=chroma,
    collection_name="memory",
    text_field="content",
    metadata_fields=["role"]
)

mem = MemoryStore(sqlite)
mem.add_hook(hook)

# Atomic commit: SQL + Vectors
mem.commit(Fact(
    type="profile_update",
    payload={"content": "User prefers vegetarian", "role": "preference"}
))

# Rollback: removes SQL row + vector entry
mem.rollback(1)

How MemState compares

Operation Without MemState With MemState
Vector DB write fails ❌ SQL+Vector diverge ✔ auto-rollback
Partial workflow crash ❌ ghost vectors ✔ consistent
LLM outputs malformed JSON ❌ corrupt state ✔ schema validation
Need to undo last N actions ❌ impossible ✔ rollback()
Need deterministic behavior ❌ drift ✔ ACID-like

Ideal for

  • Long-running agents
  • LangGraph projects needing reliable state
  • RAG systems where DB data must match embeddings
  • Local-first setups (SQLite + Chroma/Qdrant/FAISS)

LangGraph integration

from memstate.integrations.langgraph import MemStateCheckpointer

checkpointer = MemStateCheckpointer(memory=mem)
app = workflow.compile(checkpointer=checkpointer)

Storage backends

  • SQLite (JSON1)
  • Redis
  • In-memory
  • Custom backends via simple interface

Vector sync hooks: ChromaDB (more coming)


Status

Alpha. API stable enough for prototypes and local agents. Semantic Versioning.


License

Licensed under the Apache 2.0 License.


Contributing

Issues and PRs welcome. See CONTRIBUTING.md for details.