Antidetect browser platform
Run thousands of browser profiles.Each one its own device.
Every profile carries its own canvas, WebGL, audio and font signature, its own proxy, and its own isolated storage. Drive them with the automation you already have. Browsers run on your machines, and you can self-host the entire fleet.
Pick a plan and start today, or talk to us about enterprise from $5,000 once the fleet itself is the job.
- Device targets
- Windows · macOS · Linux · Android
- Browser
- Chrome 135 to 150
- Per-profile proxy
- HTTP · HTTPS · SOCKS5 · SOCKS5H
- Drive it with
- Puppeteer · Playwright · Selenium · REST · SDK · CLI
01First profile
Getting started
Four steps to a running profile
- 01
Get your organisation key
One value, issued with your organisation whichever way you buy. It is the only thing the installer asks for and the only credential the platform needs to identify you. - 02
Describe the device you want
An operating system target, a Chrome major between 135 and 150, an optional Android model, and a proxy. The platform matches a browser build to that description and pins it to the profile, so it presents the same device on every launch. - 03
Run a worker on a machine you already have
Browsers execute on your hardware, not ours. One container on one host is enough to start; the same worker image is what a fleet is made of later. - 04
Launch
Open the profile from the dashboard for a window you can use, or launch it over the API and get back a CDP endpoint for Puppeteer, Playwright or Selenium.
What you do not do
- No fingerprint values to assemble by hand
- No timezone, locale or language to keep in sync
- No per-page script to re-apply
- No infrastructure to design before the first profile runs
The whole path is public documentation, so you can read exactly what a deployment involves before anyone asks you for a decision.
02Capabilities
What you get
Around 45 signals, already agreeing with each other
Profilesselect one
Launching ads-us-01
- 01RequestPOST /launch · { "profileId": "ads-us-01" }One call, from your code or the dashboard.
- 02Bundle pinnedWindows 11 · Chrome 148Canvas, WebGL, WebGPU, audio and fonts come from this build, identically on every launch.
- 03Route attachedsocks5h://us-res-04:1080This profile's proxy alone, and DNS resolved at the exit.
- 04Region derivedAmerica/New_York · en-USRead from the proxy exit at launch, along with the language list and geolocation.
- 05Endpoint returnedws://127.0.0.1:38923/devtools/browser/<id>Attach Puppeteer, Playwright or Selenium, or drive it from the dashboard window.
The device
- Rendering signatures
- Canvas, WebGL, WebGPU, audio, client-rect and text-rect readings come from the build. The reported GPU and the pixels it produces agree, because they are the same device.
- Fonts across systems
- Embedded platform font engines for Windows, macOS, Linux and Android. A macOS profile enumerates macOS fonts while running on a Linux worker, and the host's own fonts stay out of it.
- Client hints and device metrics
- UA-CH headers, device memory, pixel ratio, hardware concurrency and media devices match their JavaScript counterparts, so header and script readings cannot be played against each other.
- Android device profiles
- A first-class target, not a preview. Real device models, touch simulation, mobile metrics, orientation and a mobile keyboard viewport.
- Stable, not random
- One profile is one device for as long as it exists. Nothing is recomputed per launch, which is what stops an identity drifting into a cluster of near-identical ones.
The network
- A proxy per profile
- HTTP, HTTPS, SOCKS5 and SOCKS5H, assigned per profile rather than per machine, so two identities never share an exit address by accident.
- Remote DNS over socks5hOurs alone
- With
socks5hthe hostname is resolved at the exit, so your resolver never sees the lookup. No other antidetect platform ships it, and the comparison page cites the page and date behind that. - Region follows the exit IP
- Timezone, locale, language list and geolocation are read from the proxy at launch. Standard across the category; the point is that it is correct here without anyone remembering to update it.
- WebRTC leak prevention
- On by default. The candidate set reflects the proxy route rather than the host, and it is a coherent set rather than an empty one, because no candidates at all is its own tell.
- QUIC and STUN tunnelled
- Both run over UDP, which does not travel through an HTTP proxy. They are tunnelled over SOCKS5 so they cannot carry the host's real position out around the session.
Automation
- The tools you have
- Puppeteer, Playwright and Selenium connect over CDP. Every launch returns a debugger endpoint; nothing needs a bespoke driver.
- REST API and typed SDK
- Provision profiles, launch sessions and read usage over HTTP, with a per-plan request rate you can see before you buy.
- Command line
- Drive profiles and sessions from a terminal or a CI job without opening the dashboard.
Teams and fleet
- Roles
- Owner, admin and member, enforced on the API and not just in the interface. Members are invited by email against a plan limit.
- Bulk operations
- Delete profiles in bulk, and copy one into a new identity with a single call. Creation is one profile per request, so a hundred of them is a loop rather than one call.
- Cluster mode
- One WebSocket endpoint in front of every worker. Automation connects to a single URL and the fleet decides which machine serves it.
Every capability above is documented in the same detail it is described in here, so it can be checked against your own requirements before a conversation starts.
03Scale
Concurrency
One URL in front of every machine you own
Routes the fleet answers
- /launch
- A new session, placed on the least busy machine
- /launch/:referenceId
- A new session against a stored profile
- /browsers/:id
- Attach to a session already running
- /w/<worker-id>/
- Anything you want pinned to one machine
Shipped defaults
- Distribution
- least connections, not round robin
- Upstream retries
- 3 candidates before failing
- Endpoints to configure
- 1
- To add concurrency
- add a host
How many profiles run at once is bounded by the machines you point at the endpoint, and by your plan, or by the volume an enterprise deployment is sized for.
The size of the fleet is one of the things that sets the price, so it is worth knowing the number before the pricing section.
04Pricing
What it costs
Plans start with a card. Enterprise starts at $5,000.
Where you start
Plans
Sign up, choose a plan, pay by card, run profiles the same day. Profiles, seats and API rate are set by the plan, and the amounts on the pricing page are read from the live plan records rather than retyped into a marketing table.
See the plansStarting at
$5,000
Enterprise
Fleet size, seats and the support around them set the rest. No billing period is stated on the number, because what you are deploying decides it.
You talk to someone first, and a demo is arranged with sales. Neither plans nor enterprise carry a free trial.
What enterprise includes
- The platform, on your machines
- Browser builds, profile bundles, workers and the fleet manager, deployed on infrastructure you provision.
- Profiles at the volume you need
- Sized to the operation rather than metered into a plan. Concurrency follows the machines you run.
- Team access and roles
- Seats, role separation enforced on the API, and audited operations for every change to the fleet.
- Engineers on the other end
- The people who built the thing you are deploying, during deployment and afterwards.
What decides the number
- How many profiles you hold, and how many run at once
- How many machines the fleet spans, and who provisions them
- How many seats need rights separated from each other
- API volume
- Whether we deploy alongside you or hand over the documentation
Bring the fleet you intend to run and the platforms you intend to run it against, and the first call ends with a number and a demo rather than a brochure. If the fleet is not the job yet, a plan needs no call at all.
05Self-hosting
The part nobody else offers
Or run the entire platform yourself
$ curl -fsSL https://veilbrowser.net/install.sh | VEIL_KEY=<org-key> bashOne value to supply. The installer derives the docker group, the internal key and an auth secret.
Then five steps, in this order
- 01An admin account, with no default password to rotate later
- 02The cluster name and the hostnames the edge will answer for
- 03HTTPS from Let's Encrypt, a Cloudflare origin certificate, or your own key pair
- 04The first worker, joined to the cluster network
- 05Review, and the config is rendered and stamped
Before the last step
The origin lock stays off and port 80 serves the wizard until setup is stamped complete, so a misconfigured lock cannot shut you out of your own installation.
What stays yours, and what does not
Browsers, sessions and egress run on your hardware. Your organisation, plans, profile metadata and licence checks live in ours. That is the whole split, and it is drawn rather than described because a security review will ask for the drawing anyway.
- 1Licence and plan verificationoutbound
- 2Encrypted profile bundlesinbound
- 3Browser build downloadsinbound
The self-hosting documentation goes further than these drawings do, and the installer above is the one it describes.
06Operations
At three in the morning
What the fleet does when nobody is watching
01A dead host and a dead API are not the same incidentEvery host is polled every 30 seconds. A failed status request opens a plain TCP connection before deciding what is wrong, and hosts you stopped on purpose are skipped rather than reported.
Recorded
reachable: true · activeSessions, load and version stored
The status body is kept as the snapshot, so the fleet view is never older than 30 seconds.
02A rejected config never reaches trafficLoad balancer changes are rendered from the database, tested by the same binary that will serve them, and moved into place by one atomic rename. A validation failure ends the operation with the previous file still serving.
- operation
- kind: "render-config"
- status
- succeeded
- authority
- admin only
03Workers drain before they rollAn update leaves the launch pool first, waits up to 120 seconds for the sessions already running, and does not receive traffic again until it reports healthy.
Operation steps
step ids as recorded: drain, sessions, pull, replace, address, health, re-enable, refresh
01 Drain trafficThe worker is taken out of the launch pool first, so no new session can land on a machine that is about to be replaced.
04The origin does not explain itself to scannersRequests that skip the proxy are closed with no response at all, and a handshake for a hostname the cluster does not serve gets a certificate with nothing to do with your domain.
05Every mutating action is a record you can readApplying a config, rolling a worker, issuing a certificate: each writes a record before it starts and streams its log while it runs. Roles are enforced on the API, not only in the interface.
- 15:04:02steprender started
- 15:04:02log1 server block, 3 upstream servers
- 15:04:02steprender ok
- 15:04:02stepvalidate started
- 15:04:03logconfiguration file test is successful
- 15:04:03stepvalidate ok
- 15:04:03stepswap started
- 15:04:03lognginx.conf.staging renamed onto nginx.conf
- 15:04:03stepswap ok
- 15:04:04stepreload started
- 15:04:04logreload signal accepted
- 15:04:04statussucceeded
Example stream from a config apply. Four event types are sent: log, step, progress and status.
| Capability | admin | operator | viewer |
|---|---|---|---|
| Read the fleet, operations and configuration | Allowed | Allowed | Allowed |
| Change cluster and fleet settings | Allowed | Allowed | Not allowed |
| Stop, start and update workers | Allowed | Allowed | Not allowed |
| Preview a rendered config | Allowed | Allowed | Not allowed |
| Apply a rendered config | Allowed | Not allowed | Not allowed |
| Manage users and TLS | Allowed | Not allowed | Not allowed |
If a security questionnaire is waiting on the other side of this decision, the answers are in the documentation rather than in a call.
07Limits
Not finished
Two things a review will find
- Not yet
Automated remote worker provisioning
The interface does not provision workers on other machines for you. Workers on the manager's own host are created and replaced for you. A worker on a separate machine is started there first and then registered, which means adding capacity to a second host is still a task with a human in it. - Off by default
The self-update sidecar
The component that updates the manager itself ships as a compose profile that the default installer does not turn on. Until you enable it, the manager will not replace its own container, and updating it is something you do rather than something that happens.
Both are operational rather than structural, and both are on the roadmap we will walk you through rather than discover together later.
Bring us the fleet you want to run.
How many profiles, on how many machines, against which platforms. The first call answers the commercial question and shows you the thing running, and nothing on this page needs a call to verify.
- Entry
- Plans, or enterprise from $5,000
- To evaluate
- Sign up on a plan, or arrange a demo with sales
- To read first
- The installer and every default, documented publicly
Every interval, limit and exclusion on this page is the shipped one.