Should I vibe code
Save readable pages locally across Apple devices with tags and highlights
Saving a link is not saving an article. Store the HTML at save time or your archive is a list of 404s.
?
Their verdict, the Premium (Annual Feature Upgrade) price and the build-time estimate come from their entry, MIT-licensed. Checked 2026-08-04.
?
Our verdict, the regret score and everything below it. Editorial and unsponsored — nobody can pay to be moved.
The honest answer
why the verdict is what it is
A local database with a good reader on top, and both halves are honest weekend work: Readability extracts the article, SQLite holds the list, a share sheet puts things into it. Build it. The one decision that matters is made on day one — saving a URL is not saving an article. The page you meant to read will be paywalled, rewritten or gone by the time you get to it, and a read-later app whose archive turns out to be a list of dead links is a bookmark bar with better typography.
What actually breaks
not "if". the specific failures.
- Extraction, on exactly the sites that need it most: paywalls, cookie walls, JS-rendered pages, newsletter archives
- Link rot, if you stored the URL and not the page — half a decade-old reading list is already gone
- Sync, the first time two devices edit the same item offline and last-write-wins quietly eats a highlight
- Search, which is the only feature that matters at two thousand saved items and the one nobody builds first
- The iOS share extension's memory budget, which is smaller than the page you are trying to save
- Your reading list itself, which is a more revealing document than it feels like while you are making it
Is that you?
the verdict is a default, not a law
- The saved HTML is stored at save time, not fetched again at read time
- Everything lives on your device, or in your own storage, and syncs through something you already trust
- There is an export to Markdown and JSON, and you have run it
- You are the only user and nobody else's reading is in the database
- Sync is a shared table with no conflict rule, because the conflict is coming
- You are hosting other people's reading lists, which is a far more sensitive dataset than it looks
- The reader fetches and executes the original page's scripts in order to render it
- The only copy of five years of highlights is a SQLite file that has never been backed up
If you build it anyway
the checklist, then the prompt that enforces it
- Store the extracted article HTML at the moment of saving, and keep the raw response too. Re-fetching later is how a reading list becomes an obituary.
- Sanitise before you render. Reader mode that runs the page's own scripts is a browser with none of a browser's protections.
- Give every item a stable id and a last-modified timestamp, and define the merge rule for conflicting edits before you enable sync on the second device.
- Build full-text search early, over the stored article text rather than titles. It is the difference between an archive and a pile.
- Export to Markdown plus a JSON index on a schedule, so the app is never the only way to read your own highlights.
- Treat the reading list as personal data even though it is only yours — it is a record of what you were worried about, month by month. Encrypt the sync payload.
I am building a personal read-later app: save a page, read it cleanly, tag it, highlight it. Local-first. Apply these constraints. 1. On save, fetch and store the article HTML immediately, and keep the raw response alongside the extracted version. Never design a flow that re-fetches the URL at read time — link rot is this app's defining failure. 2. Sanitise stored HTML before rendering: strip scripts, iframes, event handlers and remote form targets. Reader mode must never execute the source page. 3. Build the export before the reading UI. One Markdown file per item with the canonical URL, save date, tags, highlights and notes, plus a JSON index. Give me a command that runs it and tell me to try it before I rely on the app. 4. Everything is local by default: SQLite plus a files directory. If I ask for sync, do it as encrypted blobs through storage I control, and make me define the conflict rule before you write any sync code. 5. Give every record a stable UUID and a modified timestamp from the start. Retrofitting identity onto a synced dataset is not possible in practice. 6. Add full-text search over stored article text, not just titles, once there are more than a few hundred items — before any theming or animation work. 7. The share extension runs under a hard memory limit. Do the fetch and the extraction in the main app, not the extension: the extension's only job is to write a URL and return. 8. Do not add accounts, a server, or any analytics. If a feature needs a server, tell me what it would cost me to run for ten years before you build it. 9. Out of scope: social sharing, public profiles, recommendations, and anything that sends my reading list anywhere.
That one keeps you out of trouble. For the prompt that actually builds it, canivibecodeit.com has one.
their build prompt ↗Or don’t build it
the boring option, and the way back out
$9.99 once for the universal app plus $4.99 a year for the feature upgrade is the cheapest thing on this site — call it forty cents a month for an app that is actively developed and syncs through iCloud without you owning a server. Build your own because you want the archive in your own files and formats, not to save money, because you are not saving any.
$0.42/mo is cheaper than your weekend.
A folder on disk: one HTML file and one Markdown file per saved item, named by date and title, plus a JSON index carrying tags, highlights and notes. That is a read-later archive that needs no application at all, which is the only kind that survives a phone upgrade, an OS deprecation and your own loss of interest in the project.
Self-hosted read-later that stores article content rather than links, with mobile clients and exports.
Mozilla's article extraction library — the reader-mode engine you would otherwise try to write.
Questions
Is extraction really a solved problem?
Mostly. Mozilla's Readability handles a good majority of the web and is what a lot of shipping products lean on. The remaining fraction is the annoying part: paywalls, consent interstitials, pages that render their body in JavaScript, and sites that deliberately break reader mode. Budget for a manual paste-the-text fallback rather than an ever-growing pile of per-site rules.
Why is data-loss the risk tag on such a harmless app?
Because the value is cumulative and invisible until it is gone. Two thousand saved articles with highlights across six years is a real personal archive, it lives in one SQLite file, and nobody backs up an app's container directory. The failure is not dramatic — it is a restored phone and a fresh empty list.
Does the iCloud versus my-own-sync choice matter?
Operationally, a lot. GoodLinks uses iCloud, which means no server for the developer and no account for you. If you build your own, sync is the single hardest part of the project and the only part that can lose data silently. If you can live with one device, one device is a legitimate answer.
Every week, someone ships something they shouldn’t have.
New verdicts, the worst thing that landed in the trap, and the occasional incident report. No other email, ever.
Import your own highlights, resurface them on a schedule. Genuinely a small program.
Save a URL, tag it, search it. This has been a solved weekend since 2004.
A reader is a polite HTTP loop and a table. The only way to get this wrong is to skip the polite part.
last reviewed 2026-08-05 · verdict is editorial and unsponsored · shared entry data from canivibecodeit under MIT · not legal advice