Docs · Discord · Query language · Issues
Fraise is a memory database for AI agents. One they query directly, in a language built for tokens, not humans.
remember 'acme moved to annual billing' topic:billing entity:acme
recall billing entity:acme since:30d top:5
Two verbs. Sub-millisecond recall. No infrastructure to run.
- A query language agents can actually write. FQL has two verbs —
rememberandrecall— and one way to say each thing. Fewer degrees of freedom means fewer ways for a model to get it wrong, and fewer tokens spent saying it. - Hybrid retrieval. Facts are indexed for full-text, graph, and (optionally) vector search. One query, ranked across all three.
- Temporal by default. Recent memories outrank older ones, so recall is recency-aware without asking for it.
- Fast enough to sit inside a turn. Recall in tens of microseconds, writes in low milliseconds — remember mid-step, while the user waits.
- No infrastructure. A single binary. No database to provision, no service to stand up beside it.
- Open source, MIT.
Fraise is early and pre-v0.1.0. It runs, and the core loop works end to end —
but the API and the query language may still change between minor versions.
Storage, remember / recall, graph traversal |
working |
Full-text search, ranking, top / depth / time filters |
working |
| Python + TypeScript SDKs | in progress |
| Vector / semantic search | in progress |
| BM25 ranking, ANN index | planned for v0.2.0 |
| Persistence | not yet — Fraise is in-memory only |
Not production-ready. Good for experimenting with agent memory today.
Fraise stores knowledge as a temporal memory graph built from three kinds of node:
- facts — the things you remember, one statement each
- entities — who or what a fact mentions
- topics — what a fact is about
Edges connect facts to the entities they mention and the topics they're about, so
a query can start from either side. A recall finds seed facts by text (and
optionally by vector similarity), expands through shared entities and topics up to
depth hops, ranks by relevance and recency, and returns the best top results.
A single Fraise instance holds several independent memory graphs (8 by default),
addressed with @N — one per user, per session, per agent, however you like.
docker run -p 127.0.0.1:9876:9876 ghcr.io/ronsenbergvi/fraise:latestgit clone https://github.com/RonsenbergVI/fraise
cd fraise
make runcurl -X POST localhost:9876/api/v1/q \
-H 'content-type: application/json' \
-d '{"query": "remember 'the parrot is turquoise' topic:color"}'
curl -X POST localhost:9876/api/v1/q \
-H 'content-type: application/json' \
-d '{"query": "recall parrot"}'{
"results": {
"count": 1,
"hits": [
{ "value": "the parrot is turquoise", "timestamp": "...", "score": 1 }
]
}
}Prefer to talk to Fraise from your own code? Official clients wrap the query
endpoint behind two verbs — remember and recall — with optional vector
embeddings and agent-framework tools.
Python (sdk/python):
pip install fraise-sdkfrom fraise_sdk import FraiseClient
with FraiseClient("http://localhost:9876") as fraise:
fraise.remember("the parrot is turquoise", topics=["color"])
for hit in fraise.recall("parrot", top=5):
print(hit.value, hit.score)TypeScript (sdk/typescript):
npm install fraise-sdkimport { FraiseClient } from "fraise-sdk";
const fraise = new FraiseClient({ baseUrl: "http://localhost:9876" });
await fraise.remember("the parrot is turquoise", { topics: ["color"] });
const result = await fraise.recall(["parrot"], { top: 5 });
for (const hit of result.hits) console.log(hit.value, hit.score);Both are dependency-light and support vector search when you supply an embedder. See each SDK's README for embeddings and the full API.
The Python SDK ships memory tools for the Claude Agent SDK, exposed as an in-process MCP server so the agent decides what to store and recall:
from claude_agent_sdk import ClaudeAgentOptions
from fraise_sdk import FraiseClient
from fraise_sdk.integrations.claude_agents import memory_server, allowed_tools
fraise = FraiseClient("http://localhost:9876")
options = ClaudeAgentOptions(
system_prompt="Remember durable facts the user shares, and recall them when relevant.",
mcp_servers={"fraise_memory": memory_server(fraise)},
allowed_tools=allowed_tools(),
)A complete, Docker-runnable agent lives in
examples/claude-agent-sdk.
Both SDKs ship tools for the OpenAI Agents
SDK. memory_tools(client) returns bound
recall and remember tools:
from agents import Agent, Runner
from fraise_sdk import FraiseClient
from fraise_sdk.integrations.openai_agents import memory_tools
fraise = FraiseClient("http://localhost:9876")
agent = Agent(
name="Assistant",
instructions="Remember durable facts the user shares, and recall them when relevant.",
tools=memory_tools(fraise),
)
result = Runner.run_sync(agent, "My favourite colour is orange.")
print(result.final_output)The TypeScript equivalent is memoryTools(client) from
fraise-sdk/integrations/openai-agents. Complete, Docker-runnable agents live in
examples/openai-agents.
Contributions are welcome — see CONTRIBUTING.md for how to build, test, and submit changes.
This project follows the Contributor Covenant.
Questions, ideas, or building something with Fraise? Join the Discord. Bugs and feature requests belong in issues so they don't get lost.
MIT — see LICENSE.
