How it works

Privacy & data

Blamely is local-first. Every piece of data it writes stays on your machine. This page is the complete inventory.

What Blamely never does

  • Does not send telemetry, analytics, or usage data anywhere.
  • Does not require an account or network access to function.
  • Does not store file contents — only line numbers, ranges, and metadata.
  • Does not open a routable network port. The daemon binds to 127.0.0.1 only, on a random ephemeral port.

What Blamely writes

ArtifactLocationStays local?
Edit event database~/.blamely/db.sqliteYes — always
Daemon log~/.blamely/daemon.logYes
Daemon port file~/.blamely/daemon.portYes
Exclude list~/.blamely/excludeYes
CLI binary~/.blamely/bin/blamelyYes
Global git hooks~/.blamely/git-hooks/Yes
AI tool hook configs~/.claude/, ~/.cursor/, ~/.codex/, ~/.copilot/, ~/.gemini/Yes
Per-commit attribution notesrefs/notes/blamely in your repoYes — unless you explicitly push notes

What’s in an edit event (SQLite)

Each row in db.sqlite is one observed edit. It contains:

FieldExample
File path (repo-relative)src/auth/middleware.go
Repo identifier/Users/you/project
Toolclaude, cursor, copilot, codex, gemini, copypaste
Gen typechat, completion, cli, human
Model nameclaude-opus-4-7, composer-2.5 (when the tool exposes it)
Token countsinput, output, cache read, cache write (when exposed)
Line rangesstart line → end line + content SHA
Timestampnanosecond precision
Raw metadata{"session_id":"…","transcript_path":"…"}
Suggested lineslines the AI originally proposed (before user edits)
Confidencehigh, medium, or low

File contents are never stored

Only the line numbers and a SHA of the content at record time. The actual text lives in your working tree and git history.

The transcript_path field in raw metadata is the local path to a Claude Code session transcript JSONL file. Blamely reads that file at commit time (locally) to extract the last few conversation turns; the path itself is the only thing stored in the database.

What’s in a git note

One JSON note is attached to each commit under refs/notes/blamely. It contains:

FieldContents
commit, branch, messageCommit metadata
coding_time_nanosWall-clock time from first edit to commit
totalsai_lines, human_lines, deleted_lines, files, token totals, per-model line counts
by_toolPer-tool: lines, model, token breakdown, suggested vs accepted lines
by_gen_typechat / completion / cli / human line counts
files[].linesAttribution ranges: start, end, type (add/delete), author_type (AI/Human), tool, model, gen_type
conversationLast ≤ 10 user/assistant turns from the AI session transcript (Claude Code, Cursor)

No file contents — just line numbers and metadata. The conversation field contains the text of your prompts and the AI’s replies from the transcript JSONL, truncated to 300 characters per turn. It is attached only when a transcript path was captured in the corresponding edit records (Claude Code and Cursor sessions).

What Blamely reads (but does not write)

The daemon’s background watchers read these files to detect AI activity. They are read-only — Blamely never modifies them:

SourceWhat it reads
Cursor logs~/Library/Application Support/Cursor/logs/ extension-host log files
Claude Desktop logs~/Library/Logs/Claude/ (coworkd.log, main.log) — cowork sandbox file edits, macOS only
VS Code logs~/Library/Application Support/Code/logs/ Copilot plugin logs
JetBrains logs~/Library/Logs/JetBrains/<IDE>/ Copilot plugin logs
Copilot chat sessionsworkspaceStorage/<hash>/chatSessions/*.jsonl — for model discovery
Claude/Cursor transcriptsThe JSONL path stored in the edit record’s raw_meta field
Codex sessions~/.codex/sessions/*.jsonl
Devin IDE sessions~/Library/Application Support/devin/User/acp-messages/*.db (macOS; ~/.config/devin/… on Linux, %APPDATA%\devin\… on Windows) — opened read-only
Commit messagesCo-Authored-By trailers of pulled commits, to credit Devin Cloud work
Cursor File History~/Library/Application Support/Cursor/User/History/ (for session activity)

Clipboard access (editor plugins only)

The VS Code, Cursor, and JetBrains plugins read the clipboard only when a completion candidate is detected, to determine whether the insert is a paste rather than an AI completion. The clipboard content is:

  • Read in-memory at detection time.
  • Never stored — not in the database, not in git notes, not in any file.
  • Used only to classify the current event as copypaste vs completion.

Sharing notes with the team

Notes are local by default. To push them:

terminal
git push origin refs/notes/blamely

To fetch on another machine:

terminal
git fetch origin refs/notes/blamely:refs/notes/blamely

Before pushing to a public remote

There is no auto-push hook. The decision to share is always yours. If you push notes, the conversation turns (prompts and AI replies) stored in the note travel with them — consider this before pushing to a public remote.

Opting out

Per repo — disable the global hook for one repo:

terminal
git config core.hooksPath ""

Undo:

terminal
git config --unset core.hooksPath

Per file type — add patterns to ~/.blamely/exclude. See Excluding files.

Fully — see Uninstall.

Removing everything

terminal
blamely uninstall   # removes daemon, hooks, PATH entry, binary
rm -rf ~/.blamely   # removes database, logs, exclude file

To remove attribution notes from a repo:

terminal
git update-ref -d refs/notes/blamely

To remove notes from a remote (only if you pushed them):

terminal
git push origin :refs/notes/blamely

Next

Something unclear or wrong? Tell us.