snapWONDERS has spent the last couple of months modernising in public — new SDKs, a rebuilt upload flow, more of the plumbing exposed for developers to build on. Visitor traffic climbed along with it, which is exactly the outcome we wanted. It also meant more of the site was visible to more traffic than before, automated included.
- The Fix Everyone Reaches For, and Why It Was Disqualified
- Why Fingerprinting Fails the Visitors Who Matter Most
- What Proof of Work Actually Proves
- Proof of Work Has Been Solving This Exact Problem Since 1997
- Tor and I2P Are Not the Same Network
- More Than One Signal, Applied Across the Site
- The General Lesson
The signup form already had an image CAPTCHA in front of it — this wasn’t an open door. But a static image code is a known, solvable target, and starting in late July, daily signups ran well above our normal baseline, almost entirely scripted traffic working straight through it. Then, over two days in mid-August, the newsletter form took a similar hit — hundreds of subscribe attempts, overwhelmingly from a single free-mail domain, almost none of them ever confirmed. Two different forms, two different weeks, the same shape: something automated was working through the parts of the site that asked the least of it, and an image CAPTCHA on its own wasn’t enough to change that.
The standard advice for this is “just add reCAPTCHA.” I didn’t trial it. Here’s why, and what I built instead.
The Fix Everyone Reaches For, and Why It Was Disqualified
snapWONDERS and snapWONDERS Vaultify don’t serve one network. They serve clearnet, Tor, and I2P at the same time, to the same features, on purpose — privacy-conscious visitors and the forensics/steganography audience overlap heavily, and a meaningful share of both arrive over a darknet.
Every mainstream bot-defence service — reCAPTCHA, hCaptcha, Cloudflare Turnstile — works the same way under the hood: the visitor’s browser has to reach that provider’s own infrastructure to fetch and solve the challenge, and the result is verified against a fingerprint of that browser. Both halves of that are a problem for us. A third-party call from a Tor or I2P client either fails outright or defeats the whole reason the visitor chose that network in the first place — routing a real request straight to an external company that can log it. And fingerprinting, on its own terms, is the wrong tool for a meaningful slice of the audience we’re trying to protect, which the next section gets into.
This wasn’t a build-vs-buy decision we agonised over. The obvious fix was disqualified by the site’s own architecture before it got as far as a trial.
Why Fingerprinting Fails the Visitors Who Matter Most
Most bot defences lean on some mix of canvas fingerprinting, font enumeration, WebGL parameters, and other quiet signals that make one browser install distinguishable from another. It works, in the ordinary case, because most browsers really are distinguishable from each other.
Tor Browser is deliberately built to be the exception. Its entire design goal is to make every install look identical to every other install — same fonts, same canvas output, same reported hardware, on purpose, so that fingerprinting can’t be used to de-anonymise anyone. A bot-defence system that scores visitors on fingerprint uniqueness isn’t just weaker against a Tor visitor. It’s pointed directly at a signal Tor Browser exists specifically to erase, for the exact users we most want to keep on the site without friction.
That’s a genuine conflict of purpose, not a tuning problem. You can’t get better bot-detection out of a fingerprinting-based system by trying harder on Tor traffic; the traffic is engineered to defeat exactly that approach.
What Proof of Work Actually Proves
The alternative we built doesn’t try to answer “who is this visitor.” It answers a narrower question: did a real browser just spend real computation solving a puzzle we handed it.
The browser is asked to do a small, verifiable amount of computational work before a form submission is accepted. A real browser does the work in a reasonable amount of time. A script farming out thousands of submissions a minute has to pay that same cost thousands of times over — which is exactly the lever that makes the attack uneconomical without needing to know anything about who’s behind it.
No third-party call. No fingerprint. No account of who the visitor is, what device they’re on, or what network they arrived from — only proof that computation happened. The same mechanism behaves the same shape on clearnet, Tor, and I2P, because it was never built to tell them apart.

Proof of Work Has Been Solving This Exact Problem Since 1997
This isn’t a new idea. It’s the reuse of a much older one.
Adam Back designed Hashcash in 1997, years before spam filtering existed as a serious discipline. The premise was blunt: before a mail client could send a message, it had to compute a hash meeting a specific, deliberately hard-to-satisfy condition and stamp the result in the header. Finding that hash cost a real, measurable slice of CPU time. Checking it, on the receiving end, cost almost nothing. Sending one email cost a fraction of a second of computation. Sending a million of them — the entire economics of spam — cost a million times that. Hashcash never once asked who was sending the mail. It only asked whether they’d paid the toll.
The same idea resurfaced more than a decade later in a completely different context. Bitcoin’s proof-of-work consensus, launched in 2009, borrowed the Hashcash approach directly — Satoshi Nakamoto’s whitepaper cites it by name. Bitcoin scaled the same mechanism up to secure a distributed ledger instead of a single email, but the underlying principle didn’t change: work that’s expensive to produce and cheap to verify is what makes the system trustworthy, without anyone needing to know who’s on the other end of it.
What we built is the same idea, one more hop removed. Swap the email header for a form submission and the mining puzzle for a browser challenge, and it’s the same 1997 mechanism doing the same job in a new place. A real visitor pays the cost once, in a fraction of a second, without noticing. A script trying to submit thousands of forms a minute pays it thousands of times over — the same asymmetry Hashcash aimed at spam, aimed now at a different form.
Tor and I2P Are Not the Same Network
This is the part that made the build non-trivial rather than a weekend script, and it’s easy to miss if you treat “darknet” as one category.
A .onion address is treated by Tor Browser as a secure browsing context — the same class of trust the browser gives an HTTPS clearnet site. That means the fast, native cryptographic primitives a browser normally has available are available there too, so the proof-of-work computation runs at roughly the speed you’d expect.
I2P over plain HTTP doesn’t get that same treatment. Without a secure context, a browser withholds some of the faster native crypto APIs, so a client on I2P is stuck computing the same class of proof through a much slower fallback path. Tune the challenge for Tor’s speed and an I2P visitor waits far too long for something that should be near-instant. Tune it for I2P’s speed and the challenge stops doing any real work against a script running on ordinary infrastructure. The two networks aren’t interchangeable just because neither of them is clearnet — the actual engineering problem was making one mechanism behave fairly on both, not picking one number and shipping it everywhere.

More Than One Signal, Applied Across the Site
Worth saying plainly rather than getting into specifics: proof of work isn’t the whole defence, and it isn’t limited to one form. It’s applied across the parts of snapWONDERS and snapWONDERS Vaultify where automated abuse could actually do harm — account creation, contact and recovery flows, the exposed parts of the upload pipeline — as one layer among several. No single check carries that weight alone; proof of work sits alongside other signals, each doing a different job.
The exact mix isn’t something worth publishing. That’s the kind of detail that helps someone looking for the soft spot more than it helps someone reading for the idea.
The General Lesson
The industry-default answer to a problem can be actively wrong for a product whose legitimate users include exactly the population that default was never built to see. reCAPTCHA and its competitors were designed against an assumption — that a browser can always reach a third party, and that being distinguishable from other browsers is normal, even desirable, for scoring trust. Neither assumption survives contact with a Tor or I2P visitor, and a product that serves both networks by design can’t quietly inherit a defence built on top of them.
The right control follows the threat model in front of you. Ours needed to work identically whether it never left our own infrastructure — which ruled out the third-party call — and identically whether the browser in front of it was trying to be indistinguishable from every other browser on purpose — which ruled out fingerprinting. What was left wasn’t a compromise between those two. It was a different question entirely: not who is asking, but whether they paid the cost of asking.
If you’re not already reaching snapWONDERS over Tor or I2P and want to, snapWONDERS’ browsing safely page has the address for each network and a plain explanation of what you get from choosing one over another.
If you want to see what a file gives away once it’s in front of forensic analysis rather than a signup form, that’s what snapWONDERS forensic analysis is for — clearnet, Tor, or I2P, no account required.
The fix wasn’t a friendlier CAPTCHA. It was not caring who’s asking at all — only whether they paid the computational cost.
Kenneth Springer is the founder of snapWONDERS, a digital forensic analysis platform for images and video, and built snapWONDERS Vaultify, its steganography platform. Both serve clearnet, Tor, and I2P simultaneously — which is the reason the standard bot-defence playbook needed rethinking rather than adopting. snapWONDERS forensic analysis — no account required.

