Product
Bot detection for sign-ups, trials and claims
Scripted sign-ups and claims are the cheapest way to abuse a free offer. FingerPrint Checker flags automated and tampered clients and suspicious networks when a claim is made, and answers allow, a human check or deny. Every event also says whether the visit is a good bot, a bad bot or not detected, and names the bot when we recognise it. It protects the moments where something is given away, not every page view.
What is caught
- Automated and headless browsers, including common automation frameworks.
- Clients whose reported details do not agree with each other or with the network they come from.
- Traffic from datacenter networks and the Tor network.
- Tampered or replayed requests: every attestation is single-use and bound to your project and purpose.
- In apps, requests that do not come from your genuine app on a genuine device (Play Integrity on Android, App Attest and DeviceCheck on Apple).
Good bots and bad bots
Not every bot is unwelcome. Each event is marked good bot, bad bot or not detected. A good bot is a named crawler or agent from the bot directory that we can confirm is really operated by who it says it is. A bot that claims a name we can confirm but cannot prove it is reported as spoofed, and counts as a bad bot. A named bot that we cannot confirm is also a bad bot, because anyone can type its name.
The directory lists 142 named bots. Allow or block any of them by name or category in your rules.
A human check where it matters
A device’s first claim always needs a human check. Proof-of-work is the default: the web agent and the SDKs solve it in the background in about one to two seconds, with nothing to show the user. If you prefer Cloudflare Turnstile, create your own widget and choose it in the project settings, or allow either.
Decisions, not only scores
Your backend gets one answer per claim: allow, pow, turnstile or deny, with a reason. Rule names and scoring details are not sent to clients, so an attacker cannot use the response to learn what to change.
What this is not
This is not a web application firewall, a DDoS shield or a page-view bot filter. It decides whether this device may claim this thing now.
Act on the answer
From your backend, after the app sends the attestation:
const d = await (await fetch('https://api.fpchecker.com/v1/eligibility', {
method: 'POST',
headers: { 'content-type': 'application/json', 'X-Secret-Key': process.env.FPCHECKER_SECRET_KEY },
body: JSON.stringify({ attestation, email, claim: true, kind: 'trial', clientIp }),
})).json();
if (d.action === 'pow') { /* ask the client to identify again with d.powDifficulty, then resend */ }
else if (d.eligible) { /* grant the trial */ }
else { /* refuse: d.reason says why */ }Frequently asked questions
Do I need a CAPTCHA?
No. Proof-of-work is the default human check and needs no widget. Cloudflare Turnstile is optional.
Does it block bots on my whole site?
No. It decides at the moment of a claim, such as a trial or coupon. It is not a site-wide bot filter.
Can I allow Googlebot and block other bots?
Yes. Write a rule that allows the bot by name and another that denies bad bots. The first rule that matches decides, so put the allow rule first. The "block crawlers" request filter runs before rules and blocks self-declared crawlers, including Googlebot, so leave it off if you want rules to allow Googlebot.
Do you detect VPN users?
Yes. Each event carries a VPN signal with the reasons it was raised, next to separate proxy, datacenter and Tor fields. A VPN alone is still not a reason to deny: many honest visitors use one, so weigh it with other evidence in your rules.
Try it on your own sign-up flow
Every new account gets 2,000 free checks. No card required.