Skip to content
xmemoryxmemory Website

xmemory vs Hindsight

Hindsight is the most cognitively ambitious system on these pages. Its paper (December 2025) modelled memory the way psychology does, with four networks: world facts about the environment, the agent’s own experience, opinions carrying a confidence that strengthened or weakened with evidence, and observations synthesised from the rest. The product today, per its current docs, exposes three memory types, world, experience and observation, where observations do the consolidating work the paper spread across two networks. Either way, the distinction this page is about holds: Hindsight types a memory by what kind of memory it is; xmemory types a memory by what it is about.

Documentation reviewed 23 October 2026: the Hindsight paper, and the current docs on recall, observations, reflect, memory operations and MCP and deployment; on our side How xmemory works, XMD and the API.

retain runs an LLM over a transcript and extracts a handful of narrative facts, each with an occurrence interval and a mention time (relative references like “last week” are resolved to absolute dates), links the entities they mention, and types each as world or experience. A background step then compares new facts with existing observations, “deduplicated, evidence-grounded beliefs the bank has built up from multiple memories”, each citing its supporting facts with a proof count. New evidence refines an observation rather than overwriting it; a contradiction is reconciled inline, so an observation can read “works at Meta (previously thought to work at Google)”. Raw facts are always kept, and the memory API lets you edit, invalidate and restore individual memories or clear observations for re-synthesis.

recall runs semantic, BM25, graph and temporal retrieval in parallel, fuses and reranks them, and trims to a token budget. reflect is an agentic loop: it searches user-curated mental models first, then observations, then raw facts, applies the bank’s disposition (skepticism, literalism, empathy, each 1 to 5) and any hard directives, and answers with citations; pass a response_schema and it also returns a structured_output extracted from the prose answer in a second pass. It runs as one Docker image over PostgreSQL with pgvector, exposes MCP, scopes memory into isolated banks, and is open source with a managed cloud.

The paper reports 91.4% on LongMemEval-S and 89.61% on LoCoMo with a Gemini 3 Pro backbone, and 83.6% on LongMemEval with a 20B open model against 39.0% for the same model given the full context. Those are strong results on recall over long conversations.

Types about your domain, not about memory. Hindsight’s records are typed, but the type is the system’s: world or experience; text, embedding, three timestamps, entity links. A customer’s plan is a world fact whose text happens to mention a plan, and an observation about the customer may mention it too. In an XMD schema the plan is Customer.plan, from an enum you declared, on a record keyed by the customer. “Which customers are currently on Pro” is a filter over all matching stored records, not a recall. This is the argument of Schema as the Core of Reliability, and it is the difference between a memory that knows a lot about a customer and one that knows the customer’s state.

Field replacement by key, not evidence consolidation. Hindsight’s answer to a changed fact is careful: the raw facts stay, the observation is refined to incorporate the change and note the earlier understanding, its refresh history and supporting evidence are kept and exposed through the API, and you can invalidate or edit memories by hand with an audit trail. That is a good design for narrative memory. It is also consolidation the system does after the fact, over evidence, with history attached to the observation. In xmemory “the plan is now Pro” matches the customer’s record by key, replaces plan, and keeps the old value as lineage, inside the write. Nothing to consolidate, and the history is the previous value of a field rather than the revision history of a belief.

Inference you asked for. Hindsight’s observations are the system’s conclusions from evidence, and reflect reasons over them with a disposition you set; if you want an agent that forms beliefs and holds a point of view, that is a real feature, and xmemory does not have it. xmemory’s inference is grounded and bounded by field descriptions: a value is derived only where the schema says it may be and the text supports it. If your workflow wants confidence or judgement, model it as a field with a rule, as the schema below does, and it becomes something you can query and audit rather than something the system synthesised.

Queries over stored records, not structured answers generated from them. reflect can hand code a structured_output, which is useful; it is an LLM’s answer, extracted from its prose, over the evidence it chose to gather, and the docs say the extraction can fail and return prose alone. xmemory answers a question as SQL over typed records and returns the rows, so joins, counts and “which required facts are still missing” are computed over all matching stored records without a model in between.

On evidence. Hindsight’s numbers are on LongMemEval and LoCoMo, which measure recall over long conversations; we have not run Hindsight on our benchmarks and will not quote figures we do not have. Our four-domain and Splitwise tasks test updates, deletions, relation changes, aggregation and arithmetic over stored facts (white paper; Chasing AI memory SOTA), which is where a declared key and a SQL-backed store should matter most. If you evaluate both, run the same write sequences through each and count duplicate inserts, incorrect updates, missed updates and incomplete answers, and test Hindsight separately on the recall workloads it was built for.

Deployment is close to parity. Both run over Postgres, both expose MCP, both scope memory per bank or instance. Hindsight is open source; xmemory is not, and runs in our cloud or yours.

Choose Hindsight when the agent’s job is to remember long conversations well, consolidate what it has seen into cited beliefs, and reason with a consistent disposition, and you want all of that open source and self-contained. Choose xmemory when the memory is the state a workflow runs on: typed by domain, updated by key, queried by code, with inference only where the schema permits it. Hindsight’s memory types are a good checklist for what your schema should cover; the difference is that in xmemory each of them becomes a shape you chose.

Hindsight’s memory types as an XMD schema

Section titled “Hindsight’s memory types as an XMD schema”

Here is a support agent’s memory with each of Hindsight’s current types mapped to something a schema can hold. World facts become fields on the customer. Experiences become keyless interaction records. Observations, the consolidated judgements, become an application-defined assessment with an explicit confidence and the evidence behind it; this deliberately has no evidence reinforcement or automatic consolidation, because in this model the agent states its judgement and the schema records it.

xmd_version: v1
title: Support memory
description: Customers, what the agent did with them, and the agent's current assessment of each, with confidence stated as a field.
objects:
Customer:
description: One customer, identified by the customer id supplied with the input. Statements about plan or status update the record.
fields:
customer_id: { type: str, required: true, description: "Supplied with the input; do not invent one." }
name: { type: str, required: false }
plan: { type: str, required: false, enum: [free, team, pro, enterprise] }
churn_risk:
type: str
required: false
enum: [low, medium, high]
description: >-
Set only from an explicit assessment statement ("I'd now rate them high risk");
never inferred from a single complaint.
primary_key: [customer_id]
Interaction:
description: >-
One thing the agent did for a customer, in the first person, with the outcome.
Each interaction is its own record and is never updated.
fields:
customer_id: { type: str, required: true }
occurred_on: { type: str, required: false, description: "YYYY-MM-DD, resolved from relative references using the input date." }
action: { type: str, required: true, description: "What I did, in one or two sentences." }
outcome: { type: str, required: true, enum: [resolved, escalated, pending, failed] }
primary_key: []
Assessment:
description: >-
The agent's current judgement about a customer on one topic, with how sure it is
and why. A new judgement on the same topic replaces the record; confidence is
whatever the text states or the rule below derives, not a running score.
fields:
customer_id: { type: str, required: true }
topic: { type: str, required: true, enum: [renewal_likelihood, expansion_fit, support_burden] }
judgement: { type: str, required: true }
confidence:
type: float
required: false
description: >-
0 to 1. Take a stated figure when given; otherwise 0.9 for "certain" or
equivalent wording ("certainly", "definitely", "for sure"), 0.7 for "likely"
or "probably", 0.5 for "possibly" or "might", and leave empty when nothing
is stated.
basis: { type: str, required: false, description: "The evidence cited for the judgement, in the text's words." }
primary_key: [customer_id, topic]
relations:
about:
description: Connect an Interaction to its Customer.
objects:
customer: { type: Customer, on_delete: cascade }
interaction: { type: Interaction, on_delete: cascade }
keys:
one_customer_per_interaction: [interaction]
assessed:
description: Connect an Assessment to its Customer.
objects:
customer: { type: Customer, on_delete: cascade }
assessment: { type: Assessment, on_delete: cascade }
keys:
one_customer_per_assessment: [assessment]

“Customer cust_7781 (Acme): I think they’re likely to renew; no tickets since the migration” writes an Assessment on (cust_7781, renewal_likelihood) with confidence 0.7 and the stated basis. A later “cust_7781 is certainly renewing, the PO arrived” replaces it at 0.9, with the earlier judgement in lineage. That is a judgement as a record you can query (“which customers are rated likely or better to renew”) and audit, with the confidence rule in the schema. What Hindsight would synthesise as an observation about Acme is here a read: “what do we know about cust_7781” joins the three objects at query time.

Why we think this matters, and for whom

xmemory works well for short-running agents, and it is at its best for repeated tasks, where each run adds to a body of knowledge the next run can use. Long-horizon agents deserve a special mention, because there is very little objective evidence yet about what memory design works for them. Our working belief, and the reason xmemory exists: an agent running a long, multi-step task does better on structured state than on accumulated context. A schema gives it an explicit feedback loop at write time (what was accepted, what was rejected, what changed), so memory is updated rather than bloated and the trajectory stays on course: fewer re-reads, faster steps, more reliable outcomes.

If that is your workload, try xmemory on it. We are building objective measurements for this claim. The Toloka evaluation is our first independent measurement of the benefits of structured memory; evaluating changing working state over long-horizon tasks is next, and we would welcome collaborators on it. Write to info@xmemory.ai.