5 AI Models, 1 Project Spec: Who Decomposes Best?
We gave the same HTTPS Security Checker spec to Codex/GPT-5.3, Claude Opus, Kimi, GLM-5, and MiniMax-25. Here's how they scored across 17 criteria — and what every plan missed.

One. That is the tool count in most screenshot MCP servers on GitHub. One take_screenshot, base64 in, base64 out, and the README calls it done.
We counted before building ours. Our server ended up with 23 tools, and seven of them capture pixels. The other sixteen exist because capture turned out to be the easy part. Naming, finding, marking, reading: that is where the work went.
Language models live in text. Work happens on a screen. The gap shows up on a schedule:
All four are the same missing capability. The screen holds the truth, and the agent needs a sanctioned, predictable way to look at it. Plus a way to manage what it looked at.
A pile of unnamed PNGs is a junk drawer, not a library.
Credit where due: the space isn't empty. Peekaboo pioneered agent screenshots on macOS, a CLI-first tool built around capture-and-analyze vision QA, and it does that job well. On a Mac, for a command-line bridge between the screen and a vision model, it earns its place.
GitHub also hosts dozens of small "screenshot MCP" repos. Most wrap a single capture call, return the image as base64, and stop. They prove the demand. They also mark the ceiling of the one-tool approach: no library, no naming, no annotation, no memory of anything before this session.
"Minimal" is the selling word in those READMEs. Translate it. Minimal means the server does the least possible and the agent improvises the rest in prose, every session, from scratch. That's not minimalism. It's the job left half-described.
Lazy Shot starts from the other end. A full screenshot application first: capture, annotate, blur, beautify, a searchable library, on macOS and Windows. The MCP server exposes the same application headlessly. Same capture engine. Same library with search and soft delete. Same marker system. Same files on disk.
The human works in the overlay. The agent works through 23 tools. Both look at one library.
That single decision is what turns "the agent can take a screenshot" into "the agent can run a screenshot workflow." The server isn't a demo bolted onto the app. It's the app with the windows turned off.
The tools split into four groups, on purpose. Capture makes pixels. Manage makes them findable. Markers make them explainable. And OCR reads the ones nobody explained.
Headless, silent except for a brief flash notification. No overlay pops up; the human keeps typing.
| Tool | What it does |
|---|---|
capture_region | Pixel-exact coordinates on any display |
capture_window | Fuzzy-match a window by title or process name |
capture_display | A whole monitor, by index or name |
capture_active_window | Whatever has focus right now |
capture_tracked_window | A window from the recent-focus stack, "the one I was just in" |
list_displays | Monitor geometry, for multi-display math |
list_tracked_windows | The recently-focused-windows stack (opt-in Window Activity Tracker) |
capture_tracked_window needs one more paragraph. The Window Activity Tracker is an opt-in feature flag in Settings → Experimental, off by default. When on, Lazy Shot keeps an LRU stack of recently focused windows, capacity 20. So "grab the window I was just looking at" maps to a tool call instead of a guessing game.
| Tool | What it does |
|---|---|
list_screenshots | Browse the library with filters and sorting |
search_screenshots | Full-text search by keyword or filename, date ranges |
get_screenshot | Metadata for one screenshot |
open_screenshot | Open it in the viewer, bring the window forward |
assign_keyword | Give a capture a short, memorable name |
delete_screenshot | Soft delete, nothing is ever destroyed |
get_app_status | Version, counts, storage, settings |
show_window | Bring the app's main window forward |
assign_keyword is the one that pays off later. Agents name each capture with a short word: login-bug, rabbit, checkout-step-3. Not a UUID, not a timestamp. Collisions get a numeric suffix, login-bug-2, and the tool returns the final keyword, which the agent uses from then on. Days later, in a different session, "find login-bug" just works.
| Tool | What it does |
|---|---|
add_markers | Place numbered markers, on a copy |
edit_screenshot | Apply edits to a saved screenshot, on a copy |
list_marker_presets | Saved marker layouts |
get_marker_preset | One preset in detail |
search_marker_presets | Find presets by name |
The rule that matters: markers fork, never mutate. An agent that annotates a screenshot gets an annotated copy. The original stays pristine. Nobody loses the clean evidence because an agent decided to draw on it.
| Tool | What it does |
|---|---|
ocr_screenshot | Text out of a screenshot already in the library |
ocr_image_path | Text out of any image file by path |
list_ocr_languages | The OCR languages available on this machine |
One caveat before the FAQ gets there first: OCR over MCP runs on macOS only right now. Phase 1. The rest of the server is cross-platform; these three are not, yet.
Every minimal screenshot MCP ships the same thing: one take_screenshot returning base64. The demo looks great. Then the first real session starts, and real sessions are mostly not capture. They are "find the shot from Tuesday," "name this so we can talk about it," "mark steps 1 to 3 on a copy," "which monitor is the browser on." One tool forces the agent to improvise all of that in prose.
Handing an agent one capture tool and no library is giving a carpenter a saw and no workbench. The cut isn't the job.
Capture doesn't need twenty-three tools. Workflows do.
Narrow tools with obvious names are also the ones agents call correctly on the first try.
The taxonomy is the interface.
Beyond tools, the server publishes auto-updating MCP resources: screenshots://recent for the live tail of the library, config://displays and config://settings for current geometry and preferences, and per-screenshot metadata at screenshots://{id}/metadata. Clients that support resources get ambient context without spending a tool call. The agent can know what was just captured before deciding to look.
Two workflow prompts ship in the box: document-ui-flow and batch-capture. Both encode the multi-step routines people request most, so nobody has to prompt-engineer them by hand. Both show up below.
Five decisions shape how the server behaves. They have their own article: file-path-first MCP design. Here is the summary.
file_path, not an inline blob. A path costs about 20 tokens. A base64 blob isn't an answer. It's a bill the context window keeps paying for the rest of the session. The agent reads pixels only when the task requires looking.heretic-lazy-shot_<timestamp>.log in ~/.heretic-lazy-shot/logs/. Rotation at 10 MB or 24 hours, whichever comes first. MCP lines carry an [MCP] tag, so one grep isolates the agent's trail. When an agent misbehaves, the log says what happened. Reading beats guessing.The switch lives in Settings → MCP. The default endpoint is http://localhost:5055/mcp, streamable-http. If 5055 is busy, the server tries the next port, up to 10 attempts, and shows the real endpoint in the UI.
The server binds to 127.0.0.1 out of the box, because local agents are the target. Rebinding to 0.0.0.0 takes one toggle in Settings → MCP. Flip it with open eyes: the screenshots on that machine become reachable from whatever network the machine sits on.
Claude Desktop. Add to claude_desktop_config.json:
{
"mcpServers": {
"heretic-lazy-shot": { "url": "http://localhost:5055/mcp" }
}
}
Claude Code. One command:
claude mcp add --transport http heretic-lazy-shot http://localhost:5055/mcp
n8n (self-hosted). MCP Client node:
{ "serverUrl": "http://localhost:5055/mcp", "transport": "streamable-http" }
Restart the client and ask what MCP tools it has. The answer should list 23.
The built-in document-ui-flow prompt runs the loop documentation teams do by hand. Capture each step of a flow, keyword it (onboarding-step-1, onboarding-step-2, and so on), then place numbered markers on the elements worth explaining. Markers land on annotated copies; originals stay untouched. The output is a set of named, ordered, annotated images ready for docs. After the next release, the agent re-captures the same keyword list and reapplies the same marker preset. Documentation screenshots become build artifacts instead of files that rot.
The second built-in prompt, batch-capture, pairs list_tracked_windows with a capture loop: list the recently focused windows, capture each, keyword each. One agent run turns "screenshot every screen before the release" from a skipped chore into a checklist with file paths. The same pattern sweeps every monitor via list_displays plus capture_display. Dashboards, ops walls, and whatever else counts as a monitor.
The smallest example and the most-used one. Here it is as it happens.
Late afternoon. We're in the editor, and an error toast pops up in the app window behind it. No alt-tab. One sentence into Claude Code: grab the window I was just in and tell me what that error means. The agent calls capture_tracked_window, gets a file path back, reads the image. CORS failure on api.example.dev, preflight rejected. The evidence lands in the library under a keyword, searchable next week.
What made that work was the file-path contract. The tool response was a 20-token path, not a payload. The agent chose to read the pixels because the question required it. In a bookkeeping call, "capture and file this for later," it would not have. Multiply that decision across a 30-step session and it separates an agent that finishes from an agent that drowns in its own screenshots.
A whole book of these patterns lives in the Lazy Shot Cookbook on GitHub: a self-verifying UI loop for Claude Code, visual bug-fixing, pairing with Playwright, n8n monitoring. Public recipes, copy-paste prompts, a drop-in CLAUDE.md.
Honesty section, because the gaps are findable anyway. Lazy Shot's MCP doesn't click, type, or drive a browser. Eyes, not hands. Pair it with Playwright MCP or any computer-use tool for actions. No scrolling capture. No video recording. The file-path contract ties the server to agents on the same machine: Claude Desktop, Claude Code, Cursor, self-hosted n8n. Remote SaaS runners can't read the disk, so the paths mean nothing to them.
"Eyes, not hands" isn't modesty. It's a boundary. Three of the 23 tools respect another one: OCR runs on macOS only for now, and the Windows side is on the list, not in the build.
Does the agent see my screen all the time? No. Nothing is ambient. Every capture is an explicit tool call, and every capture fires a visible flash notification. No call, no capture.
Do screenshots leave my machine? Not through Lazy Shot. Capture, storage, search, and OCR all run locally, and the app phones home for nothing. No telemetry exists to disable. If the agent reads a screenshot with a cloud model, those pixels go to that model's provider. That's the agent's behavior, and worth knowing.
Which clients work? Anything speaking MCP over streamable-http: Claude Desktop, Claude Code, Cursor, n8n's MCP Client node, and the growing rest.
Can two agents use it at once? Yes. A local HTTP server, one shared library. One agent captures during a session; another finds the evidence next week.
What about Peekaboo? Different thesis, honest respect. Peekaboo is CLI-first, macOS-only, centered on capture-and-analyze vision QA. Lazy Shot is a GUI app for humans that agents share, cross-platform, centered on the library and workflows. Some people run both.
What if port 5055 is taken? The server tries the next port, up to 10 attempts, and shows the actual endpoint in Settings → MCP. Point the client at what the UI says, not at what a blog post says.
Does it work with local models? Yes. The server doesn't care what brain sits on the other end. Captures never leave the machine, and reading happens wherever the model runs. A local model makes the whole pipeline end-to-end offline.
Something failed. Where do I look?
~/.heretic-lazy-shot/logs/ first. One rotating file, heretic-lazy-shot_<timestamp>.log, MCP lines tagged [MCP]. For a bug report, Settings → System has a copy system info button. Agents can check get_app_status themselves before retrying.
Heretic Lazy Shot is the app this server lives in. macOS and Windows. One-time license: €14.99 for one device, €29.99 for three. No subscription. No account. No telemetry. The trial ships inside the download.
If your agent still asks you to paste screenshots, that part is fixable.
We gave the same HTTPS Security Checker spec to Codex/GPT-5.3, Claude Opus, Kimi, GLM-5, and MiniMax-25. Here's how they scored across 17 criteria — and what every plan missed.
Announcing VibeCoder Heretic, an autonomous coding agent boilerplate that runs on your infrastructure. Full workflow with PRs, Kanban boards, and real-time visibility.