---
title: "LangGraph memory: checkpointers, stores, and time"
description: "LangGraph memory uses checkpointers for thread state and stores for cross-thread records. Compare these functions with validity periods, supersession, and temporal recall."
canonical: https://past.dev/integrations/langgraph
last-updated: 2026-08-31
---
# Memory for LangGraph agents

Source: https://past.dev/integrations/langgraph

LangGraph persistence has two native layers. Checkpointers save graph state per thread for resume and replay. Stores keep key-value and vector memories across threads. Neither layer records fact validity periods or supersession by default. This guide shows how to call a temporal memory API from a node or tool.

## Checkpointers and stores, precisely

The [persistence documentation](https://langchain-ai.github.io/langgraph/concepts/persistence/) defines the split. A checkpointer snapshots the graph state at every super-step of a thread: perfect resume, replay and time travel for one conversation. The store is the cross-thread layer: namespaced keys, optionally embedded for semantic lookup, used directly or through the [LangMem SDK](https://langchain-ai.github.io/langmem/).

- Checkpointer time travel replays a thread's steps. It does not record the validity periods of facts outside that thread.
- Store entries are current-state by design: writing a key replaces its value, and the old value is gone.
- Neither layer resolves entities across threads or sources; a customer is whatever key you chose.

## The failure that shows up in production

A support graph stores a customer's plan as a key-value entry. Updating the key removes the earlier value. A later billing dispute cannot retrieve the plan that applied when the charge occurred. Thread replay may retain the conversation, but the store has no [validity windows](/glossary/validity-window), [supersession](/glossary/fact-supersession), or point-in-time query.

## The pattern: a memory node backed by the API

```python
import os, requests

BASE = "https://api.past.dev/api/v1"
HEADERS = {"Authorization": f"Bearer {os.environ['PAST_API_KEY']}"}

def memory_node(state: dict) -> dict:
    """Recall history relevant to the user's question, with dates and status."""
    r = requests.post(f"{BASE}/recall", headers=HEADERS, json={
        "query": state["question"],
    }).json()
    # r["status"]: Supported | Conflicted | NoKnownSupport
    # r["evidence"]: ranked, dated, with sources
    return {"memory": r}

def observe_node(state: dict) -> dict:
    """Persist durable facts produced by this run, at their event time."""
    for fact in state.get("new_facts", []):
        requests.post(f"{BASE}/ingest", headers=HEADERS, json={
            "content": fact["text"],
            "timestamp": fact["happened_at"],
        })
    return {}
```

Run `memory_node` before generation and `observe_node` after it. The checkpointer stores thread state. The API stores facts, dates, and previous values.

Applications can route on `status`. `Supported` means the evidence establishes the answer. `Conflicted` returns evidence from credible sources that disagree. `NoKnownSupport` means the stored evidence does not establish an answer. `UnknownBecauseDegraded` means retrieval could not complete and should be treated as an unknown result.

## Choosing the right layer per requirement

| Requirement | Checkpointer | Store / LangMem | past.dev |
| --- | --- | --- | --- |
| Resume and replay a thread | Yes | No | No |
| Small per-user preferences | No | Yes | Yes |
| Current fact after updates | No | Last write wins, silently | Supersession with history kept |
| What was true on a date | No | No | Point-in-time recall |
| Conflicting sources surfaced | No | No | Conflicted status with evidence |
| Backfilled history on original dates | No | No | Timestamped ingestion |

The [quickstart](/docs/memory-api/quickstart) is four calls; [benchmarks](/benchmarks) document recall measurement; [context engineering](/context-engineering) covers assembling recalled evidence into prompts.

## Frequently asked questions

### Should I drop the checkpointer if I add a memory API?

No. The checkpointer handles thread resume and replay. The memory API retains facts across threads and sessions.

### How is this different from putting embeddings in the LangGraph store?

Embeddings make store entries findable by similarity. They do not add validity dates, supersession, entity resolution or an abstention signal. Retrieval improves; the temporal model is still absent.

## Related

- [Memory for LangChain](https://past.dev/integrations/langchain)
- [past.dev and LangMem](https://past.dev/compare/langmem)
- [Point-in-time recall](https://past.dev/glossary/point-in-time-recall)
- [What is agent memory?](https://past.dev/what-is-agent-memory)
- [Quickstart](https://past.dev/docs/memory-api/quickstart)