PFM - Pure Fucking Magic. AI agent output container format.
Project description
.pfm — Pure Fucking Magic
A universal container format for AI agent output.
The AI ecosystem has a format problem. Agents spit out markdown, JSON, YAML, plain text, structured logs — all different, all incompatible, all missing context. .pfm fixes that.
One file. Every agent. All the context.
#!PFM/1.0
#@meta
id: 7a3f9c21-...
agent: claude-code
model: claude-opus-4-6
created: 2026-02-16T20:02:37Z
checksum: 049dcea0...
#@index
content 329 398
chain 735 330
tools 1073 188
#@content
Your actual agent output goes here.
Full multiline content, any format.
#@chain
User: Analyze this codebase
Agent: I'll examine the structure...
#@tools
search(query="authentication")
read_file("auth/handler.py")
#!END
That's it. Human readable. Machine parseable. Indexed for speed.
Why PFM Exists
Every AI agent today outputs differently:
- ChatGPT gives you markdown blobs
- Claude gives you structured text
- AutoGPT dumps JSON logs
- LangChain has its own trace format
- CrewAI, Autogen, Semantic Kernel — all different
There's no standard way to capture what an agent produced, how it got there, what tools it used, and whether the output is trustworthy. If you want to share agent output, audit it, chain it, or verify it — you're on your own.
.pfm is the container that wraps it all:
| What | Where |
|---|---|
| The actual output | content section |
| The conversation that produced it | chain section |
| Tool calls made | tools section |
| Agent reasoning | reasoning section |
| Performance data | metrics section |
| Anything else | Custom sections |
Installation
pip install . # From source
pip install get-pfm # From PyPI
Quick Start
Python API
from pfm import PFMDocument, PFMReader
# Create
doc = PFMDocument.create(agent="my-agent", model="claude-opus-4-6")
doc.add_section("content", "The analysis shows 3 critical findings...")
doc.add_section("chain", "User: Analyze the repo\nAgent: Starting analysis...")
doc.add_section("tools", "grep(pattern='TODO', path='src/')")
doc.write("report.pfm")
# Read (full parse)
doc = PFMReader.read("report.pfm")
print(doc.content) # "The analysis shows..."
print(doc.agent) # "my-agent"
print(doc.chain) # "User: Analyze the repo..."
# Read (indexed — O(1) section access, only reads what you need)
with PFMReader.open("report.pfm") as reader:
content = reader.get_section("content") # Jumps directly by byte offset
print(reader.meta["agent"])
print(reader.section_names)
CLI
pip install get-pfm # Python
npm install -g get-pfm # Node.js — both install the `pfm` command
# Create a .pfm file
pfm create -a "my-agent" -m "gpt-4" -c "Hello world" -o output.pfm
# Pipe from stdin
echo "Hello" | pfm create -a cli -o hello.pfm
# Inspect metadata and sections
pfm inspect output.pfm
# Read a specific section
pfm read output.pfm content
# Validate structure and checksum
pfm validate output.pfm
# Quick file identification
pfm identify output.pfm
# Convert formats
pfm convert to json output.pfm -o output.json
pfm convert to md output.pfm -o output.md
pfm convert from json data.json -o imported.pfm
pfm convert from csv data.csv -o imported.pfm
Spells
Every CLI command has a Harry Potter spell alias. Run pfm spells for the full spellbook.
pfm accio report.pfm content # Summon a section
pfm polyjuice report.pfm json # Transform to another format
pfm fidelius report.pfm # Encrypt (Fidelius Charm)
pfm revelio report.pfm.enc # Decrypt (Revelio)
pfm unbreakable-vow report.pfm # Sign (Unbreakable Vow)
pfm vow-kept report.pfm # Verify signature
pfm prior-incantato report.pfm # Full provenance + integrity check
from pfm.spells import accio, polyjuice, fidelius, revelio, unbreakable_vow
content = accio("report.pfm", "content")
json_str = polyjuice(doc, "json")
encrypted = fidelius(doc, "password")
decrypted = revelio(encrypted, "password")
unbreakable_vow(doc, "signing-key")
Chrome Extension
Capture AI conversations directly from your browser. Available on the Chrome Web Store (in review).
Supports ChatGPT, Claude, Gemini, Grok, and OpenClaw. One-click capture with optional encryption.
Features:
- Captures conversations from ChatGPT, Claude, and Gemini as .pfm files
- Popup with Capture tab (save current conversation) and View/Convert tab (drop files)
- Full-tab .pfm viewer with sidebar, search, keyboard shortcuts, and export
- Zero dependencies — pure browser APIs only
Converters
Every format goes both ways:
from pfm import converters, PFMReader
doc = PFMReader.read("report.pfm")
# To other formats
json_str = converters.to_json(doc)
csv_str = converters.to_csv(doc)
txt_str = converters.to_txt(doc)
md_str = converters.to_markdown(doc)
# From other formats
doc = converters.from_json(json_str)
doc = converters.from_csv(csv_str)
doc = converters.from_txt("raw text", agent="importer")
doc = converters.from_markdown(md_str)
Security
from pfm.security import sign, verify, encrypt_document, decrypt_document
# Sign (HMAC-SHA256)
doc = PFMDocument.create(agent="trusted-agent")
doc.add_section("content", "verified output")
sign(doc, secret="your-signing-key")
doc.write("signed.pfm")
# Verify
loaded = PFMReader.read("signed.pfm")
assert verify(loaded, "your-signing-key") # True if untampered
# Encrypt (AES-256-GCM, PBKDF2 key derivation)
encrypted = encrypt_document(doc, password="strong-password")
with open("secret.pfm.enc", "wb") as f:
f.write(encrypted)
# Decrypt
data = open("secret.pfm.enc", "rb").read()
decrypted = decrypt_document(data, password="strong-password")
print(decrypted.content)
Format Design Priorities
In this exact order:
1. Speed
- Magic byte check in first 64 bytes (instant file identification)
- Index with byte offsets for O(1) section jumping (no scanning)
- Two-pass writer pre-computes all offsets
- Lazy reader only loads sections you request
2. Indexing
- Every section has a byte offset and length in the
#@indexblock - Readers can seek directly to any section without parsing the whole file
- Multiple sections with the same name are supported and independently indexed
3. Human Readability
- 100% UTF-8 text (no binary blobs)
- Open it in any text editor and immediately understand the structure
- Section markers (
#@) are visually distinct and greppable - Magic line (
#!PFM/1.0) is self-documenting
4. AI Usefulness
- Structured metadata (agent, model, timestamps)
- Prompt chain preservation (full conversation context)
- Tool call logging (reproducibility)
- Arbitrary custom sections (extend without breaking the spec)
PFM vs Other Formats
| Feature | .pfm | .json | .md | .yaml | .csv |
|---|---|---|---|---|---|
| Human readable | Yes | Somewhat | Yes | Yes | Somewhat |
| Indexed sections | Yes (O(1)) | No | No | No | No |
| Agent metadata | Built-in | Manual | No | Manual | No |
| Prompt chain | Built-in | Manual | No | Manual | No |
| Tool call logs | Built-in | Manual | No | Manual | No |
| Checksum integrity | Built-in | No | No | No | No |
| HMAC signing | Built-in | No | No | No | No |
| Encryption | AES-256-GCM | No | No | No | No |
| Multiline content | Natural | Escaped | Natural | Indented | Escaped |
| File identification | 64 bytes | Parse whole file | No | Parse whole file | No |
| Custom sections | Unlimited | N/A | N/A | N/A | N/A |
| Bidirectional conversion | JSON, CSV, TXT, MD | — | — | — | — |
Pros
- Purpose-built for AI — not a general-purpose format retrofitted for agent output
- Self-contained — one file has everything: output, context, metadata, provenance
- Fast — indexed byte offsets mean you don't parse what you don't need
- Secure — signing and encryption are first-class, not afterthoughts
- Extensible — add any section you want, the format doesn't care
- Convertible — round-trips cleanly to/from JSON, CSV, TXT, Markdown
Cons
- New format — no existing ecosystem (yet)
- Text-based — not as compact as binary formats for large payloads
- Section markers in content — content containing
#@or#!on a line start requires\escaping (handled automatically by the library) - Streaming write — streaming mode uses trailing index, requires post-processing for full index
- Young spec — v1.0, will evolve
What It Solves
- Agent output portability — Share agent results between tools, platforms, and teams in one format
- Provenance tracking — Know which agent, model, and prompt produced any output
- Output verification — Checksums and signatures prove content hasn't been tampered with
- Audit trails — Chain and tool sections preserve the full generation context
- Selective reading — Index-based access means you can grab just the section you need from large files
- Format interop — Convert to/from JSON, CSV, TXT, MD without losing structure
Project Structure
pfm/
├── pyproject.toml # Package config, CLI entry point
├── pfm/ # Python library
│ ├── spec.py # Format specification and constants
│ ├── document.py # PFMDocument in-memory model
│ ├── writer.py # Serializer with two-pass offset calculation
│ ├── reader.py # Full parser + indexed lazy reader
│ ├── stream.py # Streaming writer for real-time output
│ ├── converters.py # JSON, CSV, TXT, Markdown (both directions)
│ ├── security.py # HMAC signing, AES-256-GCM encryption
│ ├── spells.py # Harry Potter spell aliases (accio, fidelius, etc.)
│ ├── cli.py # Command-line interface (+ spell commands)
│ ├── __main__.py # python -m pfm support
│ ├── tui/ # Terminal viewer (Textual)
│ └── web/ # Web viewer generator + local server
├── pfm-js/ # npm package (TypeScript)
│ └── src/ # Parser, serializer, converters, checksum, CLI
├── pfm-vscode/ # VS Code extension
│ └── src/ # Syntax, preview, outline, hover, CodeLens
├── pfm-chrome/ # Chrome extension (MV3)
│ ├── content/ # AI site scrapers (ChatGPT, Claude, Gemini)
│ ├── popup/ # Extension popup UI
│ ├── viewer/ # Full-tab .pfm viewer
│ └── shared/ # PFM core (parser, serializer, converters)
├── docs/ # GitHub Pages SPA (viewer & converter)
├── tests/ # 123 Python tests + conformance vectors
└── examples/
└── hello.pfm # Example file
123 Python tests. 55 JS tests. 178 total. All passing.
The Name
Yes, PFM stands for Pure Fucking Magic.
It's a 20-year joke. Someone in 2046 will google "what does .pfm stand for," find this page, and laugh. Then they'll realize the format actually works, and they'll keep using it.
That's the plan. And honestly? The way AI agent data gets moved around today with zero standardization? The fact that it works at all is pure fucking magic.
License
MIT
Built in one session. Shipped before the hype cycle ended.
Project details
Release history Release notifications | RSS feed
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distribution
Built Distribution
Filter files by name, interpreter, ABI, and platform.
If you're not sure about the file name format, learn more about wheel file names.
Copy a direct link to the current filters
File details
Details for the file get_pfm-0.1.4.tar.gz.
File metadata
- Download URL: get_pfm-0.1.4.tar.gz
- Upload date:
- Size: 61.3 kB
- Tags: Source
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.13.3
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
0d76d375aff7dee0204b6f6095f1558c77c7c735c50e516056d5218133c43065
|
|
| MD5 |
d97376d00792f7282fab8fe25e2be6b3
|
|
| BLAKE2b-256 |
dc785834e1db1a3910045adb6534e03ff4fb129900be52cedcdc036d09166000
|
File details
Details for the file get_pfm-0.1.4-py3-none-any.whl.
File metadata
- Download URL: get_pfm-0.1.4-py3-none-any.whl
- Upload date:
- Size: 49.8 kB
- Tags: Python 3
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.13.3
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
c5a3d8b120dfd6f10b8b2068e8ddab5217982282cfb1ad93c6cc59edee6daa7f
|
|
| MD5 |
ad0a3692f839e76699a5eb49466aaa2d
|
|
| BLAKE2b-256 |
8a5745cba1da0f7c06176dfdedc93f45e49433eb143efff848317e69893e95d3
|