headcleaner
Allows reversing a Notion workspace export into OKF concepts via headcleaner notion-import.
Adds Obsidian-compatible frontmatter fields and outputs directly into an Obsidian vault for seamless sync.
Sends conversion run manifests to a Slack webhook URL via headcleaner watch, enabling progress notifications.
Click on "Install Server".
Wait a few minutes for the server to deploy. Once ready, it will show a "Started" state.
In the chat, type
@followed by the MCP server name and your instructions, e.g., "@headcleanerconvert my downloads folder to markdown"
That's it! The server will respond to your query, and you can continue using it as needed.
Here is a step-by-step guide with screenshots.
headcleaner
Walk a folder, convert every document to Markdown (with frontmatter), OKF v0.2 (with frontmatter), or both — with an omp-style animated TUI.
headcleaner convert ~/Documents/inbox --format both --output ~/Documents/inbox.cleanheadcleaner is a Python CLI that scans a directory you provide, identifies each document by extension, runs the appropriate extraction engine (OfficeCLI for Office formats, pdfplumber for PDFs, BeautifulSoup for HTML, etc.), and emits clean normalized output — either side-by-side Markdown and OKF, or just one.
Output formats:
--format md(Markdown),--format okf(OKF v0.2 bundle),--format both(default)Engine coverage: 7 formats out of the box (XLSX, DOCX, PPTX, PDF, HTML, HTM, TXT) — see docs/FORMAT_MATRIX.md for the 16-format v1.0 roadmap
TUI: omp-inspired animated terminal (box-drawing panels, neon palette, powerline separators)
Linter:
headcleaner lintreviews the converted Markdown / OKF for formatting issuesPer-message PST: one OKF concept per email (via readpst) so review/sign-off works file-by-file
office_oxide backend: Pure-Rust Python bindings for Office formats (~100x faster than OfficeCLI)
Heuristic cleanup:
headcleaner convert --cleanruns a 12-stage any2md-inspired cleanup pipelineall2md fallback: Auto-handles 38 extra formats (Jupyter, LaTeX, reST, sourcecode, etc.) when all2md is installed
headcleaner mcp: Run headcleaner as an MCP server exposing 14okf_*tools to any MCP agent host (Claude Code, Cursor, etc.) — install withuv pip install "headcleaner[mcp]"Diagnostics:
headcleaner doctorchecks Python, PATH, OfficeCLI, output permissions, and the@slugregistry, then prints a GO/NO-GO verdictAdapter plugins: Third-party packages register formats through the
headcleaner_pluginentry-point groupzsv CSV: World's-fastest SIMD CSV parser (~10-100x stdlib) when
zsvis on PATHTrust attestation:
headcleaner attestbuilds a Merkle root + ed25519 signature;verifychecks itLocal browse:
headcleaner serve <bundle>exposes a FastAPI UI for browsing + searchHonest defaults: OKF trust fields filled with
unverified/human:pending, never invented
Install
# 1. The Office engine — single binary, no Office install needed
npm install -g @officecli/officecli
# 2. The CLI itself (Python ≥3.12, uv-managed)
uv tool install headcleaner
# Or for development:
git clone <this repo>
cd headcleaner-cli
uv sync
uv run headcleaner --helpFor other install methods (curl | bash, pip, brew, Windows PowerShell), see docs/INSTALL.md.
Quick start
headcleaner ~/Documents/inbox --format both --output ./cleanThis produces:
clean/
├── manifest.json # run summary: per-file status, engine, sha256
├── REPORT.md # count, average time, and error rate by engine
├── _md/ # plain Markdown (one file per source)
│ ├── notes.docx.md
│ ├── q3.pdf.md
│ └── ...
└── okf/ # OKF v0.2 bundle (one concept per source)
├── index.md # auto-generated directory index
├── notes.md # OKF concept: type=Document
├── q3.pdf.md
└── ...CLI reference
headcleaner convert <INPUT_DIR> [OPTIONS]
Options:
-f, --format {md,okf,both} Output format(s) [default: both]
-o, --output DIR Output directory [default: ./out]
--ocr Enable Tesseract OCR for scanned PDFs
--officecli-timeout <secs> Timeout per OfficeCLI subprocess call (default: 60)
--include, -i GLOB Include glob (may be repeated)
--exclude, -e GLOB Exclude glob (may be repeated)
--jobs, -j N Parallel worker processes (default: 1 = sequential)
--no-cache Re-convert every file (skip the SHA-256 cache)
--no-continue-on-error Stop on the first failure
--obsidian-compat Add Obsidian-friendly flat fields to OKF frontmatter
--clean Run the 12-stage heuristic cleanup pipeline (any2md-inspired) on each body
--tui / --no-tui Force / disable the animated TUI (default: auto-detect TTY)
--no-okf-index Skip OKF directory index.md generationOther commands: headcleaner doctor [--output-dir DIR] Run install and permission diagnostics headcleaner templates List supported formats headcleaner agents Show engine install status headcleaner watch IN [--webhook-url URL] Re-convert on file changes (Ctrl+C to stop) headcleaner lint Review converted Markdown / OKF for formatting issues headcleaner lint --fix Auto-repair safe issues to .fixed/ headcleaner serve Local HTTP browser for the OKF bundle headcleaner notion-import <EXPORT.zip> Reverse a Notion workspace export headcleaner attest Compute Merkle root + optional ed25519 signature headcleaner verify Verify an attestation against the bundle
## Why OKF?
OKF (Open Knowledge Format, v0.2) is just **markdown + YAML frontmatter in a directory hierarchy**. That means:
- Every concept is a single `.md` file you can `cat`, `grep`, edit in any text editor
- Bundles live in git — pull requests, diffs, blame all work
- Obsidian, Notion, MkDocs, Hugo, Jekyll all consume OKF natively
- Required frontmatter key is just `type` — anything beyond that is producer freedom
See [docs/OKF_NOTES.md](docs/OKF_NOTES.md) for the OKF v0.2 specifics this CLI emits.
## Trust stance (honest defaults)
We never auto-claim review. Every emitted OKF concept gets:
- `status: unverified`
- `verified: human:pending`
- `generated: human:<user>@<host>` (OKF §7 actor convention)
- `stale_after: <today + 180d>`
- `sources: [{uri: file://..., sha256: ...}]`
A human can grep `human:pending` later to find concepts needing review. See [docs/OKF_NOTES.md](docs/OKF_NOTES.md) for the full contract.
## Supported formats
See [docs/FORMAT_MATRIX.md](docs/FORMAT_MATRIX.md) for the full engine × library table. At a glance:
| Format | Engine | Library |
|---|---|---|
| `.docx`, `.xlsx`, `.pptx` | OfficeCLI binary | (native DOM) |
| `.pdf` | pdfplumber (text-layer), pytesseract if `--ocr` | pdfplumber / pytesseract |
| `.html`, `.htm` | BeautifulSoup | beautifulsoup4 |
| `.txt` | chardet + read | chardet |
| `.md`, `.markdown` | pass-through + frontmatter inject | stdlib |
| `.csv`, `.tsv` | Sniffer dialect + GFM table (zsv SIMD when installed) | stdlib `csv` (or `zsv` binary) |
| `.json` | pretty-print + fenced block | stdlib `json` |
| `.eml` | headers + text/html body + attachments | stdlib `email` |
| `.epub` | per-chapter HTML → MD | ebooklib (+ bs4 fallback) |
| `.rtf` | control-word stripping | striprtf (+ regex fallback) |
| `.odt`, `.ods`, `.odp` | paragraph/row extraction + GFM tables | odfpy (+ raw-XML fallback) |
| `.msg` | Outlook headers + body + attachments | extract-msg |
| `.pst` | **per-message** (one OKF concept per email) | readpst (libpst) + libpff-python fallback |
| `.docx`, `.xlsx`, `.pptx` | **office_oxide** (primary, ~100x faster), OfficeCLI binary (fallback) | office_oxide 0.1.8 (PyO3) |
| `.ipynb`, `.latex`, `.rst`, sourcecode, `.enex`, `.chm`, etc. (38 formats) | all2md (when installed) | all2md 1.12 |
| `.doc`, `.xls`, `.ppt` | clear error path | needs `libreoffice --convert-to` first |
## Live mode
```bash
headcleaner watch ~/inbox --output ~/out --webhook-url https://hooks.slack.com/...Re-runs the conversion automatically when files change under ~/inbox.
Each re-run POSTs the manifest to the webhook URL (optional). Press
Ctrl+C to stop.
Obsidian vault sync
headcleaner convert ~/inbox --format okf \
--output ~/Documents/MyVault/Concepts \
--obsidian-compatAdds Obsidian-friendly flat fields (source, sha256, generated_by,
verified_by, stale_on) to the OKF frontmatter so the concept shows
up correctly in Obsidian's property panel. Original OKF fields stay
intact for round-tripping.
Review (human sign-off)
Auto-conversion sets verified: human:pending. The headcleaner review
TUI walks every pending concept in a bundle and lets a human flip each
to:
approved →
verified: human:reviewed,status: verified,reviewed_at,reviewed_by,reviewed_viarejected →
verified: human:rejected,status: rejected, optionalrejection_reasons[]skipped → leaves the concept as
pending
headcleaner review ./out/okf
# Textual TUI: a=approve, r=reject, s=skip, n=next, p=prev, q=quitIf Textual isn't available (e.g. headless CI), a plain-mode REPL falls back automatically.
Distribution
PyPI:
pip install headcleaner(built via uv, published via OIDC trusted publishing on tag push)Homebrew:
brew install headcleaner(formula inpackaging/homebrew/)Docker:
docker pull ghcr.io/local/headcleaner(multi-stage image with tesseract)Windows:
winget install headcleaner,scoop install headcleaner,choco install headcleanerStatic binary:
pip install pyinstaller && pyinstaller packaging/pyinstaller/headcleaner.spec
Full release checklist in RELEASE.md.
CLI surface
headcleaner view <bundle> (add --tui to browse in the terminal) renders an OKF bundle as a single self-contained HTML graph (no backend, opens in any browser). See docs/VIEWER.md for full options.
headcleaner convert IN_DIR [flags] # walk + convert
headcleaner watch IN_DIR [flags] # live mode + webhooks
headcleaner review BUNDLE # human sign-off TUI/REPL
headcleaner attest BUNDLE [--private-key PEM] # Merkle root + optional ed25519 sig
headcleaner verify BUNDLE [--public-key PEM] # verify an attestation
headcleaner serve BUNDLE [--host] [--port] # local HTTP browser for the bundle
headcleaner glob DIR # interactive include REPL (Textual)
headcleaner notion-import EXPORT.zip OUT # reverse a Notion workspace export
headcleaner lint DIR [--fix] # OKF + MD rule checks
headcleaner doctor [--output-dir] # dependency and permission preflight
headcleaner agents [stdout] # emit AGENTS.md
headcleaner templates # list supported formatsDocumentation
Document | Purpose |
this file — install, quick start, CLI reference | |
all install paths (curl, pip, brew, PowerShell, uv, Docker) | |
detailed usage guide with worked examples | |
how the pipeline fits together, where to extend | |
every supported format × engine × library | |
OKF v0.2 contract this CLI emits + trust policy | |
OKF frontmatter JSON Schema and editor/CI integration | |
third-party adapter entry-point protocol | |
common errors and fixes | |
frequently asked questions | |
how to add a new format / engine / emitter | |
release history | |
44+ shipped enhancements + future ideas | |
HeadCleaner VS Code extension (Concept Explorer + Trust Inspector) |
Troubleshooting
officecli not found — install with npm install -g @officecli/officecli. Run headcleaner agents to verify.
PDF with no extractable text — your PDF is image-only. Re-run with --ocr (requires pytesseract + Tesseract binary on PATH).
Hidden files skipped — intentional. Files starting with . are dropped by the walker.
OKF index.md missing for root — auto-generated when the bundle has ≥1 concept. Use --no-okf-index to opt out.
More — see docs/TROUBLESHOOTING.md.
Development
git clone <this repo>
cd headcleaner-cli
uv sync
uv run pytest # 314 tests, ~14s
uv run headcleaner convert ./tests/fixtures --format both --output ./outArchitecture
src/headcleaner/
├── walk.py # recursive folder walker
├── router.py # extension → engine dispatch
├── normalize.py # CanonicalDoc + OKF/MD frontmatter builders
├── lint.py # post-conversion linter (OKF + Markdown)
├── run.py # pipeline orchestrator
├── cli.py # Click CLI (headcleaner command)
├── tui.py # Textual TUI (omp-style)
├── engines/
│ ├── base.py # Adapter ABC
│ ├── officecli.py
│ ├── pdf.py
│ ├── html.py
│ └── txt.py
└── emit/
├── markdown.py
├── okf.py
├── okf_index.py
└── manifest.pyAdding a new format: drop a module in engines/, register the adapter in router.py, add a row to docs/FORMAT_MATRIX.md. See docs/CONTRIBUTING.md for the full extension guide.
License
Apache-2.0
This server cannot be installed
Maintenance
Resources
Unclaimed servers have limited discoverability.
Looking for Admin?
If you are the server author, to access and configure the admin panel.
Related MCP Connectors
Markdown in, any format out. PDFs merged, split, watermarked. Runs on our own doc engines.
Markdown utilities MCP.
MCP server for AgentDocs (agentdocs.eu): read, search, write, comment on & share Markdown docs.
Latest Blog Posts
- Who's Calling? MCP Hosts Are an Identity Blind Spot (And the Spec Knows It)By Om-Shree-0709 on .mcpAgent IdentityOAuth 2.1
- Your AI Chatbot Just Exposed Your CEO's Salary to an InternBy Om-Shree-0709 on .Agent IdentityMCP SecurityOAuth Delegation
- Why MCP Servers Need Execution Sandboxing (And Why Your Current Stack Isn't Enough)By Om-Shree-0709 on .Agentic AiPrompt InjectionWebAssembly
MCP directory API
We provide all the information about MCP servers via our MCP API.
curl -X GET 'https://glama.ai/api/mcp/v1/servers/jamesdsizemore/headcleaner-cli'
If you have feedback or need assistance with the MCP directory API, please join our Discord server