Skip to content

LangChain

This guide shows how to use xmemory as a persistent memory layer for a LangChain agent. Two approaches are covered:

  • MCP — connect LangChain to the xmemory MCP server via langchain-mcp-adapters; the agent gets write and read tools automatically.
  • HTTP API — call the REST API directly from custom LangChain tools; useful when you want full control.

API key: To use xmemory APIs or integrations, you need an API key. Get one from the xmemory console. Copy and securely store the key. Never share your API key publicly.


Terminal window
pip install langchain langchain-anthropic xmemory-ai pyyaml

For the MCP approach (Part 3), also install:

Terminal window
pip install langchain-mcp-adapters

xmemory stores data in typed instances. Each instance has a schema that describes the objects and relations you want to track. Describe what you want to remember in plain language — xmemory generates a typed schema from that free-text description and returns it ready for instance creation.

This is a one-time setup script. Save the returned instance ID (e.g. in an environment variable) and reuse it in your agent.

import os
import yaml
from xmemory import XmemoryClient, SchemaType
API_KEY = os.environ["XMEM_API_KEY"]
# 1. Connect and pick a cluster
client = XmemoryClient(api_key=API_KEY)
clusters = client.admin.list_clusters()
cluster_id = clusters[0].id
# 2. Generate a schema from a plain-language description
schema_response = client.admin.generate_schema(
cluster_id,
"Track contacts with name, email, company, and notes.",
)
# 3. Create the instance
inst = client.admin.create_instance(
cluster_id=cluster_id,
name="contacts",
schema_text=yaml.dump(schema_response.data_schema, allow_unicode=True),
schema_type=SchemaType.YML,
)
print(f"Created instance: {inst.id}")
# → store this in INSTANCE_ID and reuse it on subsequent runs

The instance ID is a UUID string. Keep it — you’ll use it to get an instance handle on subsequent runs.


Part 2 — Agent with custom xmemory tools (HTTP API)

Section titled “Part 2 — Agent with custom xmemory tools (HTTP API)”

Wrap write and read as LangChain tools so the agent can store and recall information during a conversation.

import asyncio
import os
from langchain.agents import create_agent
from langchain_core.tools import tool
from xmemory import XmemoryClient
API_KEY = os.environ["XMEM_API_KEY"]
INSTANCE_ID = os.environ["XMEM_INSTANCE_ID"] # from Part 1
client = XmemoryClient(api_key=API_KEY)
inst = client.instance(INSTANCE_ID)
@tool
def remember(text: str) -> str:
"""Store information in long-term memory."""
# Sync write so a follow-up `recall` sees it immediately. In production,
# prefer inst.write_async(text) for fire-and-forget writes you won't read
# back right away, then poll inst.write_status(write_id) if you need to.
result = inst.write(text)
return f"Stored (write_id={result.write_id})."
@tool
def recall(query: str) -> str:
"""Retrieve information from long-term memory."""
result = inst.read(query)
return result.reader_result.get("answer", str(result.reader_result))
agent = create_agent(
"anthropic:claude-sonnet-4-6",
tools=[remember, recall],
system_prompt=(
"You are a helpful assistant with access to a persistent memory store. "
"Use `remember` to save new information and `recall` to look things up."
),
)
async def main():
# Store something
result = await agent.ainvoke(
{"messages": "Remember that Alice Johnson works at Acme Corp, her email is alice@acme.com."}
)
print(result["messages"][-1].content)
# Recall it later
result = await agent.ainvoke(
{"messages": "What do you know about Alice?"}
)
print(result["messages"][-1].content)
if __name__ == "__main__":
asyncio.run(main())

The read method supports three modes via read_mode:

read_mode reader_result shape When to use
"single-answer" {"answer": "..."} Natural-language question → plain text answer
"xresponse" {"objects": [...], "relations": [...]} Get structured objects back
"raw-tables" {"tables": [...]} Raw SQL result sets

Part 3 — MCP approach (fewer lines of code)

Section titled “Part 3 — MCP approach (fewer lines of code)”

LangChain supports MCP servers via the langchain-mcp-adapters package. The xmemory MCP server exposes write and read (and more) as ready-made tools — no boilerplate needed.

This headless flow sends your account API key directly as the Bearer token on the /instance/<instance_id> shortcut path — no OAuth exchange needed. The instance is bound by the URL path, so you don’t pass instance_id explicitly in tool calls. See the MCP guide for the other connection options.

import asyncio
import os
from langchain.agents import create_agent
from langchain_mcp_adapters.client import MultiServerMCPClient
API_KEY = os.environ["XMEM_API_KEY"]
INSTANCE_ID = os.environ["XMEM_INSTANCE_ID"] # from Part 1
client = MultiServerMCPClient(
{
"xmemory": {
"transport": "http",
"url": f"https://mcp.xmemory.ai/instance/{INSTANCE_ID}",
"headers": {
"Authorization": f"Bearer {API_KEY}",
},
},
}
)
async def main():
tools = await client.get_tools()
agent = create_agent(
"anthropic:claude-sonnet-4-6",
tools=tools,
system_prompt=(
"You have access to a persistent memory store via the xmemory tools. "
"Use `write` to remember things and `read` to look them up."
),
)
result = await agent.ainvoke(
{"messages": "Remember that Bob Smith is a senior engineer at Globex. "
"Then tell me what you know about Bob."}
)
print(result["messages"][-1].content)
if __name__ == "__main__":
asyncio.run(main())

Available MCP tools (instance connection type)

Section titled “Available MCP tools (instance connection type)”

The instance connection exposes 9 default tools — 6 bound (get_instance_id, get_instance_schema, write, write_async, write_status, read) and the 3-tool schema-evolution suggestion engine (review_suggestions, decide_suggestions, apply_pending_decisions) — plus an opt-in Schema management group (5 more). See the MCP — Tools reference for full parameter and return-shape details.