I read a lot of non-fiction. Popular science, negotiation theory, cosmology, whatever looks interesting. I highlight passages, scribble notes, feel productive. A month later I remember maybe five percent of the book.
The Ebbinghaus forgetting curve doesn't care about good intentions. Without active review, most of what you read evaporates. To actually retain things you need to go back to your notes, build summaries, run flashcards. But to review your notes, you first need to get them out of wherever they're stored.
And if you use Apple Books, that's where the fun begins.
The Apple Books problem
I read in Apple Books. Highlight on the phone, everything syncs across devices. The reading experience is fine. The moment you want to do anything with your highlights outside the app, it falls apart.
There's no export. No API. No menu option. You can tap a highlight, copy it, paste it somewhere. One highlight at a time. I have hundreds of highlights across dozens of books. That was never going to work.
Where your highlights actually live
The annoying part is that the data is right there on your Mac. Two SQLite databases, buried in containers:
~/Library/Containers/com.apple.iBooksX/Data/Documents/BKLibrary/
~/Library/Containers/com.apple.iBooksX/Data/Documents/AEAnnotation/
BKLibrary stores book metadata: titles, authors, asset IDs. AEAnnotation has the actual highlights and notes. Standard SQLite, standard schema. Asset IDs link books to their annotations, each record holds the selected text, your note if you wrote one, a timestamp, position data.
Your data sits in a perfectly readable format, two directories deep. Apple just never built an export button.
So I built one.
ibooks_notes_exporter
A Go CLI, single binary, no dependencies. I wrote it a few years ago when the manual copying finally drove me to spend a weekend on it. Published to Homebrew, open-sourced on GitHub, moved on with life.
Install
brew tap 57uff3r/mac-apps
brew install 57uff3r/mac-apps/ibooks_notes_exporter
Works on Intel and Apple Silicon.
List your books
ibooks_notes_exporter books
Output:
+----------------------------------+-------+------------------------------+------------------+
| BOOK ID | NOTES | TITLE | AUTHOR |
+----------------------------------+-------+------------------------------+------------------+
| 4BAE5DA3C95788753173EAE8C63E6034 | 47 | Thinking, Fast and Slow | Daniel Kahneman |
| 7F2A1BC4D89E12345678ABCDEF012345 | 23 | The Art of Strategy | Avinash Dixit |
+----------------------------------+-------+------------------------------+------------------+
Export highlights from a book
ibooks_notes_exporter export \
--book_id 4BAE5DA3C95788753173EAE8C63E6034 > thinking_fast_slow.md
The output is clean Markdown. Each highlight as a quote block, your handwritten notes underneath if you left any. Pipe it to a file, drop it into Obsidian, feed it to whatever tool you use for knowledge management.
Got a book with hundreds of highlights and want to skip the ones you've already processed?
ibooks_notes_exporter export \
--book_id 4BAE5DA3C95788753173EAE8C63E6034 \
--skip_first_x_notes 20
Three commands, no config files, no authentication, no API keys. It reads two SQLite databases and gives you Markdown.
The project went quiet. Then MCP happened.
People started using it, filed issues, asked for features. I merged what I could, then ran out of time and the project sat idle for a while.
Recently I came back. Updated Go to 1.23, switched from the CGO-dependent SQLite driver to a pure Go one (modernc.org/sqlite, which means no C compiler needed for building and cross-compilation works cleanly), fixed a bug where iBooks sync created duplicate highlights.
But the dependency update wasn't why I came back.
MCP server
MCP (Model Context Protocol) is a standard for connecting AI assistants to external data sources. Your LLM sends a structured request, the server responds with data. No file shuffling, no copy-paste, no "export to markdown then paste into chat." The AI reads your data directly.
I added an MCP server to the exporter with three tools:
| Tool | What it does |
|---|---|
list_books |
Lists all books with highlights. Returns IDs, titles, authors, annotation counts |
get_notes |
Exports highlights and notes from a specific book as Markdown |
search_notes |
Cross-book keyword search across all annotations, case-insensitive |
All read-only. The server doesn't touch your iBooks data.
Start it:
ibooks_notes_exporter mcp
Connect it to your editor
The config is the same JSON block everywhere. One binary, one argument.
Claude Desktop / Claude Code
Claude Desktop: ~/Library/Application Support/Claude/claude_desktop_config.json
Claude Code: .mcp.json in your project root
{
"mcpServers": {
"ibooks": {
"command": "ibooks_notes_exporter",
"args": ["mcp"]
}
}
}
Cursor
Settings → MCP Servers → Add Server. Or drop this into .cursor/mcp.json:
{
"mcpServers": {
"ibooks": {
"command": "ibooks_notes_exporter",
"args": ["mcp"]
}
}
}
VS Code (GitHub Copilot)
In settings.json:
{
"mcp": {
"servers": {
"ibooks": {
"command": "ibooks_notes_exporter",
"args": ["mcp"]
}
}
}
}
ChatGPT Desktop: same format, file at ~/.config/chatgpt/mcp.json.
Windsurf: same format, file at ~/.codeium/windsurf/mcp_config.json.
Five editors, one config pattern. One thing I appreciate about MCP as a protocol: the server doesn't care who's calling. Build once, connect anywhere.
What you can do with AI + your highlights
Once connected, your AI assistant has direct access to your reading notes. Not to summaries scraped from the internet or training data. To your highlights, the passages you found worth marking.
Build a summary of what you highlighted. Not a summary of the book (any LLM can generate that from training data). A summary of what caught your attention. Different readers highlight different things in the same book, and that difference is the whole point.
Generate spaced repetition flashcards. The AI reads your highlights and creates question-answer pairs for Anki or whatever system you use. Based on what you actually marked as important, not what an algorithm decided matters.
Search across books. "What did I highlight about decision-making across all my books?" The search_notes tool does cross-book keyword search. The AI gets raw results, synthesizes them, groups by source, finds patterns across different authors, spots contradictions you didn't notice.
Compare authors on the same topic. If you've highlighted passages about risk in both "Thinking, Fast and Slow" and "Antifragile," the AI pulls both sets and lays them side by side. Your reading becomes a connected knowledge base instead of isolated annotations per book.
None of this is impossible without MCP. You could export to Markdown, paste into a chat window, ask the same questions. But friction matters enormously. When your AI can just read your notes without you doing anything, you actually use it. When it takes three manual steps, you don't.
I've been calling this setup an exocortex for reading. Your AI agent augments your memory with your own annotations, locally, without anything leaving your machine.
Local-first, no cloud
The SQLite databases live on your Mac (Apple syncs them via iCloud, but the tool reads from local copies). The MCP server runs locally. Your highlights never leave your machine unless you explicitly choose to send them somewhere.
No account creation, no API keys, no tracking. One binary on your disk, reading two databases on your disk.
Limitations
Because there are things this doesn't do:
- EPUB only. PDFs in Apple Books store annotations differently. The tool doesn't handle them yet.
- macOS only. The SQLite databases live in macOS containers. No iOS-only access, but Apple syncs annotations from iOS to Mac, so if you read on iPhone and have a Mac, you're covered.
- No write operations. Can't create or edit highlights, only read them. By design. I don't want to risk corrupting the iBooks database.
Try it
If you read non-fiction and use Apple Books:
brew tap 57uff3r/mac-apps
brew install 57uff3r/mac-apps/ibooks_notes_exporter
# see your books
ibooks_notes_exporter books
# export highlights
ibooks_notes_exporter export --book_id <id> > notes.md
# or connect to your AI assistant
ibooks_notes_exporter mcp
⭐ Star on GitHub if this is useful.
Top comments (0)