
Somebody rebuilt Aperture. Not a mockup, not a Figma tribute — a working, non-destructive photo manager with a library database, adjustment stacks, and a browser that doesn’t stutter at 40,000 RAWs, shipped in about a week by one developer driving Claude Code from a terminal. The thread hit in the last 72 hours and it’s still climbing, because it lands on a nerve a lot of us have been nursing since Apple killed Aperture in 2014: the app you loved is gone, the source is gone, and the replacement is worse. The news isn’t the nostalgia — it’s that the workflow is reproducible. If you want to rebuild Aperture with Claude Code (or Aperture’s spiritual cousin, or whatever dead tool you’re still bitter about), the exact plan-mode prompts and scaffolding are copyable. Here’s that recipe, plus the parts of the story people are glossing over.
What’s actually new about rebuilding Aperture with Claude Code
The build itself isn’t magic. It’s a SwiftUI macOS app with a SQLite-backed library, an image pipeline over Core Image, and an adjustments model that stores edits as a stack of parameters rather than baking them into pixels. Any competent Mac developer could have written that. The claim that made it spread is the timeline: roughly seven days, evenings and weekends, from empty directory to something the author uses on their actual photo library. The scarce resource wasn’t knowledge of Swift. It was the sheer volume of mechanical implementation work between “I know how this should work” and “it works” — the exact gap agentic coding closed this year.
Three things in the workflow did the heavy lifting, and they’re the transferable part. First, plan mode: the author refused to let the agent write a line until it produced a written architecture doc it had to defend. Second, a serious CLAUDE.md — not a two-line README, but a living constitution covering module boundaries, the non-destructive editing invariant, the forbidden shortcuts, and how to run the test suite. Third, subagents scoped to single subsystems, so the RAW decoding work never touched the library schema and the two never fought over the same files.
The caveat the author states and the retweets drop: this is not Aperture. There’s no Faces, no Places, no plugin API, no print module, and the RAW rendering is Apple’s, not the original Aperture pipeline people actually miss. What exists is the 80% of Aperture that 95% of its users touched daily. That’s the real lesson — agentic coding is extraordinary at rebuilding the well-understood core of a dead app, and still mediocre at reinventing the parts that were genuinely novel.
Why it matters
- Abandonware just became a starting point, not a tombstone. Any app with a documented feature set and no exotic algorithms is now a weekend-to-fortnight project for one motivated person with an agentic coding workflow.
- The bottleneck moved from typing to specifying. The developers winning at this in 2026 can describe a system precisely. Implementation speed stopped being the constraint; taste and architecture became it.
- Native desktop is back on the table for solo devs. Electron won the last decade largely because native meant learning a platform’s whole idiom. An agent that already knows AppKit, SwiftUI, and Core Image erases most of that tax.
- Vendor abandonment carries less leverage. When “we’re sunsetting this” means “someone will clone the core in a month,” the calculus around depending on a small vendor’s tool shifts.
- Prompt scaffolding is the new build system. CLAUDE.md, plan mode discipline, and subagent boundaries are becoming a portable engineering practice with the same weight a Makefile used to carry.
- The legal line got sharper, not blurrier. Rebuilding functionality is fine. Copying icons, assets, trade dress, or a trademarked name is not. “Aperture-style” is a description; shipping something called Aperture is a problem.
How to use it today: the plan-mode workflow
This is the replicable version of that build. Substitute your own dead app anywhere it says Aperture.
-
Install and start clean. An empty directory keeps the agent from inheriting someone else’s architecture.
npm install -g @anthropic-ai/claude-code mkdir ~/dev/lightbox && cd ~/dev/lightbox git init claude -
Do the archaeology before the architecture. You cannot rebuild what you can’t describe. Spend twenty minutes writing a feature inventory from memory and screenshots, then have the agent research the gaps. Press Shift+Tab twice to enter plan mode — this is one of the highest-value Claude Code plan mode prompts you’ll write:
Research the Aperture 3 photo management app (discontinued 2014). Produce a feature inventory grouped into: (a) library/catalog, (b) browsing and culling, (c) non-destructive editing, (d) output and export. For each feature, note whether a modern macOS implementation can use an Apple framework (Core Image, ImageIO, Photos.framework) or needs custom work. Do not write code. Output the inventory as a markdown table and flag the five features that carry the most technical risk. -
Force an architecture argument in plan mode. Make the agent commit to boundaries and defend them before a single file exists. People skip this step, and it’s why their builds collapse at week two.
Still in plan mode. Design a SwiftUI macOS app implementing tiers (a), (b), and (c) from that inventory. Constraints: - Non-destructive editing is an invariant. Original files are never modified. Adjustments are a serialized parameter stack. - Library metadata in SQLite via GRDB. Never store image binaries in the database. - The browser must stay responsive at 50,000 assets. Assume a thumbnail cache on disk with an LRU eviction policy. - Strict module boundaries: Library, Importer, RenderPipeline, UI. Modules communicate through protocols, not concrete types. For each module give me: responsibility, public interface, and the single hardest problem it faces. Then argue the case against your own design and tell me where it breaks first. -
Write CLAUDE.md before writing code. Correct Claude Code CLAUDE.md setup separates a codebase that stays coherent for a week from one that drifts by Wednesday. Keep it short enough to actually be read every turn.
# Lightbox — a non-destructive photo manager for macOS ## Invariants (never violate) 1. Original image files are read-only. Full stop. 2. Every adjustment is a value in an `AdjustmentStack`, applied at render time. Nothing is ever baked into a stored image. 3. No image binaries in SQLite. Paths and metadata only. 4. UI never blocks on decode. All image work is off the main actor. ## Modules - `Library/` — GRDB schema, asset records, albums, queries - `Importer/` — file ingest, EXIF via ImageIO, checksums - `Render/` — Core Image chain, thumbnail cache, export - `App/` — SwiftUI views. No business logic here. Cross-module calls go through protocols in `Core/Contracts.swift`. ## Commands - Build: `xcodebuild -scheme Lightbox -destination 'platform=macOS' build` - Test: `xcodebuild test -scheme Lightbox -destination 'platform=macOS'` - Lint: `swiftlint --strict` ## Rules for you - Read `Core/Contracts.swift` before changing any module interface. - New behavior requires a test in the same commit. - Never add a dependency without asking. We have GRDB. That is it. - If a task spans two modules, stop and tell me. Do not do both. -
Build the schema and the importer first — nothing else. The catalog is the foundation; if it’s wrong, everything above it is wrong. Exit plan mode and scope the agent tightly.
Implement the Library module only, per CLAUDE.md. Deliver: GRDB migrations for assets, albums, keywords, and adjustment_stacks; the Asset record type; and a LibraryStore protocol in Core/Contracts.swift with a GRDB-backed implementation. Write tests covering: migration from empty, inserting 10,000 assets under 2 seconds, and querying by date range. Do not touch Render/ or App/. Stop when tests pass. -
Run subsystems as parallel subagents. Once contracts are frozen, the RAW decode work and the browser UI proceed independently. Scoping Claude Code subagents desktop app work by module keeps two agents from stepping on the same files.
Spawn two subagents against the frozen Contracts.swift: Subagent A — Render/: Core Image pipeline applying an AdjustmentStack (exposure, contrast, highlights, shadows, white balance, crop). Disk thumbnail cache, 256px and 1024px, LRU eviction at 2 GB. Subagent B — App/: the browser grid. Lazy loading against LibraryStore, keyboard culling (arrow keys, 1-5 ratings, X to reject), and a filmstrip. Mock the renderer. Neither may modify Contracts.swift. If either needs an interface change, stop and report it to me. -
Test against a real library, not fixtures. Every one of these builds looks perfect on 200 sample images and falls over on 40,000. Point it at the actual folder early — this step separates an AI photo manager app build from a demo.
Import ~/Pictures/Masters (about 38,000 files, mixed RAW/JPEG). Instrument it. Report: total import time, p50 and p99 thumbnail generation, peak memory, and scroll frame drops in the grid. Then fix the worst bottleneck only. One change. Re-measure. -
Commit at every green test and keep the agent honest. The best habit in this agentic coding workflow 2026 is small verified commits, because it makes rollback cheap when the agent confidently ships something broken.
git add -A && git commit -m "Library: GRDB schema + importer, tests green"
How it compares
If your goal is just to manage photos, building your own is the worst option on time-to-value and the best on control. Be honest about which one you’re optimizing for.
| Option | Cost | Non-destructive | Owns your library | Effort to get running |
|---|---|---|---|---|
| Self-built with Claude Code | Your time + a Claude subscription | Yes, by design | Fully — local files, local DB | 1-2 weeks of real evenings |
| Lightroom Classic | Subscription, ongoing | Yes | Local catalog, cloud-adjacent | Minutes |
| Capture One | Subscription or perpetual | Yes | Local sessions/catalogs | Minutes |
| darktable | Free, open source | Yes | Fully local | Minutes to install, weeks to like |
| Apple Photos | Free with macOS | Partial | Opaque library bundle | Already installed |
The self-built column wins on exactly one axis that matters to the people doing this: nothing changes unless you change it. No subscription price hike, no forced cloud migration, no feature you rely on getting sunset. That’s the itch Aperture’s death left, and it’s why “vibe coding a macOS app” turned out to be a durable motivation rather than a weekend novelty.
What’s next
Expect the pattern to generalize fast. The obvious next targets share Aperture’s profile: well-documented, widely loved, technically unexotic, and dead. Think Sherlock-style local search, the pre-Catalina iTunes library manager, Quicksilver, older Mac RSS readers, Windows tools orphaned by their vendors. Watch for the first community-maintained repository of these rebuilds — the moment someone publishes a shared CLAUDE.md and contracts scaffold for “resurrect a desktop app,” the effort curve drops again.
The harder question is maintenance. Shipping a working app in a week is a demo; keeping it alive across OS releases, RAW format additions, and your own changing taste is the actual cost. Agentic coding compresses the build but not the upkeep, and a codebase you understand only through the agent that wrote it is a liability the first time something breaks at 11pm. The teams doing this well treat the agent’s output as code they own, read it, and keep the test suite mandatory.
Legally and culturally, the pressure will come from vendors. Functional reimplementation is well-established ground, but expect louder objections as these rebuilds get closer to the originals — particularly anywhere trade dress, icons, or file format reverse-engineering are involved. Build the features, not the brand. Name your app something else, draw your own icon, and you’re on solid footing.
Frequently Asked Questions
Can I really rebuild Aperture with Claude Code if I’m not a Swift developer?
Partially. You’ll get further than you expect and stall sooner than you’d like. The agent writes the Swift; you still have to read it, judge whether the architecture is sane, and diagnose failures the agent can’t see — Xcode signing problems, memory pressure, frame drops. Intermediate developers in any language do fine. Complete beginners tend to produce something that runs and can’t be maintained.
How much does this cost to build?
The dominant cost is your time. On the tooling side, a week of heavy agentic work on a project this size fits comfortably inside a standard Claude subscription tier. Check current plan limits before you commit to a schedule — that’s the variable most likely to bite you mid-build.
Is it legal to clone a discontinued commercial app?
Reimplementing functionality from scratch is generally permitted; copying code, assets, icons, or the trademarked name is not. Since Aperture’s source was never public, there’s nothing to accidentally copy — you’re building from a feature description. Use your own name and your own artwork and you avoid the actual risks. This is general information, not legal advice.
Why plan mode instead of just describing the app and letting it build?
A one-shot description produces a plausible app with an architecture you didn’t choose, and you discover that at day five when two modules are fused together. Plan mode forces the design decisions into a document you can argue with before any code exists. The half hour it costs saves days.
Do I need subagents, or is one session enough?
One session is enough to start and stays fine through the first module. Subagents earn their keep once you have frozen interfaces and genuinely independent subsystems — a render pipeline and a browser UI, for instance. Split too early and you’ll spend your time reconciling contradictory assumptions instead of building.
What’s the single biggest failure mode?
Skipping the real data test. Everything works on a fixture folder. Point the importer at your actual 40,000-image library in the first few days, measure it, and let the numbers drive your architecture — not the other way around.
Go deeper than this article
This article covers the essentials. Our premium eguide library gives you the full step-by-step playbooks — prompts, workflows, and copy-paste recipes you can put to work today.