More anonymity for readers: Feedlane now ships a media proxy
Simon
When you read an article, more happens behind the scenes than you'd think. The text comes from the feed and gets served cleanly through Feedlane. The images in the article aren't bundled into the feed though. The publisher only sends a pointer to where each picture lives on their own server, so your browser fetches every one of them directly from the publisher. You don't notice it day-to-day, but from a privacy standpoint it's not ideal: the publisher (and any ad network sitting next to them) sees your IP, your User-Agent, the timestamp, and tracking pixels do exactly what they're built to do. An article can contain several images, and often invisible 1×1 tracking pixels are in the mix as well. For a reader that promises "privacy-first", that's a gap to me, and so far not solved well.
What changed
From now on, all article images and feed favicons go through the Feedlane server. Your browser no longer asks publisher.com for an image, it asks feedlane.app. We fetch the bytes server-side and stream them back to you. The publisher only ever sees one IP, namely ours, no matter how many users are reading. Tracking pixels become worthless: they look identical for every reader, so they can't be tied back to a specific person.
You won't notice much while reading. In the best case, nothing at all. Images still load, often slightly faster because we set aggressive cache headers and repeat views come straight from the browser cache. A nice side effect: HTTP images on HTTPS pages (the dreaded "mixed content") are no longer a problem, because everything is now served over our HTTPS endpoint.
How it works
Every image URL in an article gets rewritten at parse time to an HMAC-signed proxy URL (/api/v1/img?u=…&s=…). On the way out, the server verifies the signature, validates the target (no localhost, no private IPs, so SSRF protection) and streams the image through. Cookies and other fingerprinting headers are stripped in both directions. SVG is explicitly blocked because SVG files can carry JavaScript. Max 10 MB per image, 30-day browser cache.
Favicons work a little differently, because they get loaded millions of times. Every sidebar entry is one. Instead of proxying them on each request, Feedlane downloads each favicon once when a feed is added, stores the bytes in the database, and serves them from cache. A background job keeps the cache up to date. If a site changes its favicon, Feedlane picks up the new version automatically on the next refresh.
The whole thing also works for mobile apps that hook into Feedlane via the Fever API. Images and favicons go through our server there the same way. If you read Feedlane through an app like Reeder or Unread, you get the same protection.
