A TLS fingerprint that agrees with the user agent
Before a page runs any JavaScript, the TLS handshake has already described the client. Clearcote's handshake is Chromium's own, and the few fields that change between Chrome versions follow the version the persona claims, so the network layer and the user agent tell the same story.
In every tier, on by default. There's nothing to configure.
The default is already right
import { launch } from "clearcote";
// default: the ClientHello follows the persona's claimed Chrome major
const browser = await launch({ fingerprint: "account-42", tlsProfile: "match-persona" });
// or pin a major, or leave the build's own TLS untouched:
// tlsProfile: "chrome-149"
// tlsProfile: "native"Highlights
Chromium's own handshake
BoringSSL as Chrome ships it: the cipher list, version bounds and per-connection extension order are the real thing, not a reimplementation.
Follows the claimed version
Only the fields that change between Chrome versions move, such as the post-quantum key-share group and the ALPS codepoint, so an older Chrome persona also shakes hands like one.
No seam between layers
The JavaScript surface and the handshake come from one browser, so there's no mismatch between a patched user agent and an unpatched network stack.
HTTP/2 from the same stack
SETTINGS, window updates and header order come from Chromium's own HTTP/2 implementation, not a separate client library.
The brand lives in headers
Edge, Opera and Vivaldi share Chromium's handshake; the brand is carried in the user agent and client hints, not in the ClientHello.
Configurable, rarely needed
The default suits almost everyone. The option exists so you never pin a version that contradicts your brand version.
Why the handshake matters
A TLS fingerprint (JA3, and its successor JA4) summarises the ClientHello: which versions, ciphers, extensions and groups a client offers, and in what form. HTTP/2 adds another layer: the SETTINGS frame, window sizes and pseudo-header order. Both are read on the server, before any script runs, and both are cheap to compare with the user agent.
That comparison is where many automation stacks come apart. An HTTP library with a Chrome user agent still sends its own library's handshake, and a JavaScript stealth layer changes what the page reads but not what the network sent. Clearcote is Chromium from end to end, so there's no second client underneath.
What Clearcote adds is version coherence. Each Chrome release changes a few handshake details. When a persona claims a different Chrome version from the build it runs on, match-persona adjusts just those fields to the claimed major and leaves everything else as Chromium generates it.
A spoofed user agent next to Clearcote
What people use it for
Sites that score the handshake
Many edge networks read JA3 or JA4 before the page loads. A coherent handshake removes one contradiction from the picture.
Older Chrome personas
Present an earlier Chrome major without a handshake from the future giving it away.
Network research
Compare handshakes across Chrome majors with the same binary.
Clearcote is built for privacy, testing, research and lawful automation. You're responsible for how you use it and for following the terms of the sites you visit.
Which plan includes it
In every tier, on the default setting.
Compare plansFAQ
What is a JA3 or JA4 fingerprint?
A compact summary of a client's TLS ClientHello: its versions, cipher suites, extensions and supported groups. Servers use it to tell browsers from HTTP libraries and to check that a client is what its user agent says. See the Q&A on JA3 and JA4.
Does Clearcote randomise the TLS fingerprint?
No. Random handshakes don't match any real browser, which makes them easy to spot. Chrome itself shuffles the order of its TLS extensions on every connection, and Clearcote keeps that behaviour exactly as Chrome does it.
Does an Edge or Opera persona change the ClientHello?
No. Those browsers are Chromium underneath and share its handshake. The brand is carried in the user agent, client hints and headers, which is where Clearcote sets it.
When would I change tlsProfile?
Almost never. match-persona already follows the brand version you claim. Pin chrome-<major> only if you set the brand version some other way, and use native to leave the build's handshake exactly as compiled.
Go deeper in the docs
Related features
Canvas, WebGL, WebGPU, audio, fonts, screen, hardware and locale set in the C++ engine from one seed, so every surface agrees with every other.
Set a proxy with geoip on and the timezone, languages and WebRTC follow the exit IP. SOCKS5 with a username and password works directly.
A drop-in Chromium for Playwright and Puppeteer: one import change in Python, Node or .NET, with the browser downloaded and SHA-256 verified for you.
Run Clearcote as a standing CDP endpoint from the official Docker image, serve() or a CLI, and attach any framework with no code change.
Related reading
Try Clearcote
Open source, a drop-in for Playwright & Puppeteer, and coherent down to the TLS handshake.
Free for one browser with GitHub. No card.