Browser fingerprinting, explained
· 10 min read
What a browser fingerprint is, which surfaces it is built from, why entropy and stability both matter, and why an incoherent disguise is worse than none.
· 10 min read · Lobster Browser team
An anti-detect browser is a browser that presents a different, controllable device identity per profile: one profile looks like a Windows desktop in Berlin, another like a different Windows desktop in São Paulo, and the two are not linkable by the signals a website can read. They are used by people who legitimately operate many separate accounts — agencies running client advertising, marketplace sellers, QA teams testing localized experiences — and, inevitably, by people doing things their platforms forbid.
This post is about the engineering, not the ethics: the two fundamentally different ways these tools change a fingerprint, why one leaves traces the other does not, what farbling is and why stability matters as much as noise, where cross-session and cross-device consistency falls apart, which automation tells have nothing to do with fingerprinting, and how to evaluate a product here without relying on its marketing. Our earlier piece on browser fingerprinting supplies the vocabulary.
The problem is linkage. Ten accounts on one platform opened from one machine are trivially one person: the canvas hash, the graphics renderer, the font set and the network address are the same across all ten. Separate browser profiles do not help, because profiles separate storage, not hardware. Separate virtual machines do help, and are expensive at any scale.
An anti-detect browser tries to give each profile the observable properties of a distinct machine on a distinct network, cheaply, on one computer. Every design decision in the category follows from that goal, and so does every way these tools are caught.
Almost every product in this space is a modified Chromium. The meaningful difference is where the modification sits.
The browser injects a script into every page before the page's own code runs, and that script redefines the properties a fingerprinting library reads: the getter for the platform string, the canvas readback methods, the graphics parameter function. It is quick to build, easy to update when a new surface appears, and it works against a straightforward collection script.
The browser's own source is modified so the value the engine computes is already the intended one: the rendering path produces the intended canvas output, the graphics layer reports the intended adapter, the network stack sends the intended headers and client hints. Nothing is patched at runtime because nothing needs to be — the engine is not lying about its state, its state is different.
| Property | JavaScript overlay | Native engine change |
|---|---|---|
| Where the value comes from | A replacement function in page script | The engine itself |
| Detectable by function inspection | Yes, unless every trace is hidden — and there are many | Nothing to inspect |
| Covers non-JavaScript surfaces | No: headers, TLS behavior and media pipelines are outside its reach | Yes, if the implementation covers them |
| Survives a new detection technique | Only after the overlay is updated | Usually, because the change is upstream of the technique |
| Cost to build and maintain | Low | High: it means maintaining a browser |
Detecting an overlay is not exotic. It is a set of well-known checks any competent script performs, and they exist because JavaScript is introspectable by design.
// A native function stringifies to a specific form. A replacement does not,
// unless the replacement also patched toString - which is itself detectable.
Function.prototype.toString.call(navigator.hardwareConcurrency);
// Where does the property live, and is it an own property when it should be
// inherited from the prototype?
Object.getOwnPropertyDescriptor(Navigator.prototype, 'platform');
Object.getOwnPropertyNames(navigator);
// A patched accessor usually adds a frame with a different script origin.
try { null.f(); } catch (e) { inspect(e.stack); }
// A fresh realm has a pristine copy of everything. If the overlay only patched
// the main window, the iframe tells the truth.
const frame = document.createElement('iframe');
document.body.append(frame);
frame.contentWindow.navigator.platform;Farbling is the deliberate introduction of small, deterministic distortions into high-entropy readbacks — a few pixels nudged in a canvas image, the lowest bits of audio samples perturbed — so the value collected is not the machine's true one. The term comes from the privacy-browser world, where the goal is to prevent cross-site linking; anti-detect browsers use the same mechanism to give each profile its own consistent value.
The subtlety is in the key. Noise must be derived from something stable, or the cure is worse than the disease.
There is also a magnitude question: distortion large enough to be visible, or to produce a value no real hardware would, is itself a signal. Good farbling is imperceptible, invariant for the profile, and inside the range real devices produce.
Getting individual surfaces right is the easy half. The half that fails in practice is keeping them consistent with each other, and consistent over time.
A profile claiming to be a particular Windows machine should have the font set that system ships, canvas output rasterized the way that platform rasterizes, a graphics renderer string belonging to hardware that exists, the extension list that renderer supports, a plausible processor count, matching client hints, and a time zone and locale that agree with the network address. Each is checkable independently, and a mismatch between any two is a stronger signal than an unusual value in any one.
The same profile must present the same device next week. That includes surviving a browser update: if the engine moves to a new version and the declared browser version moves with it while everything else stays put, the story still holds — real browsers update. What does not hold is a canvas hash that changes because the tool regenerated its seed, or a font list that grows because the host machine installed something.
This is the one that surprises teams. Use a profile from a second computer and everything the tool does not control leaks the difference: the real screen geometry, the host's fonts if the engine falls back to them, the graphics stack if the profile's values derive from the host, and the network path. A genuinely portable profile has to carry its whole identity — storage, cookies and declared hardware — and the tool has to apply it the same way on both machines.
“My fingerprint is detected” and “my automation is detected” are different problems, and a perfect fingerprint does not help with the second.
The practical consequence: evaluate the fingerprint and the automation surface separately, because a product can be excellent at one and irrelevant to the other.
Marketing here is unusually unfalsifiable: “undetectable” is a claim about every website that exists, present and future. Replace it with tests you can run.
For completeness, since we build one: Lobster Browser is an anti-detect browser built on a modified Chromium engine, and it takes the native approach described above. A profile's device identity is produced inside the engine rather than by a script injected into pages, and the same identity is applied to the surfaces page script can read and to the ones it cannot, such as request headers and client hints; each profile keeps its own storage and its own network route, and its values are stable across restarts. That describes the design, not any particular site's detection — the honest position in this category is that an implementation can be internally coherent and current, and that whether a given site accepts a given profile is that site's decision.
Spoofing changes an answer. Coherence changes the device that gives the answers, and only the second survives a collector that cross-checks. Overlays are cheap, leave introspectable traces, and cannot reach the network and platform surfaces at all; engine-level changes cost far more to build and remove those traces by construction. Farbling is useful only when its key is stable for exactly as long as the profile is. Consistency across sessions and machines is where most deployments fail, automation tells are a separate problem no fingerprint solves, and any product here should be judged by tests you run yourself.
Named rather than linked, on purpose: specifications move and URLs rot, while a title and an author survive a search.
· 10 min read
What a browser fingerprint is, which surfaces it is built from, why entropy and stability both matter, and why an incoherent disguise is worse than none.
· 10 min read
Perception, action spaces, settling, verification and safety boundaries — how an agent operates a browser, and why a real browser beats a headless scraper.
· 10 min read
A framework for model selection: capability axes, what benchmarks can and cannot show, latency and cost, reasoning modes, and open-weight versus hosted.
· 9 min read
What separates an agent from a chatbot: tool use, the planning loop, memory, evaluation and guardrails — and the places agents still reliably fail.