Add a bot check
Run AbuseZero's bot check when a person submits a claim, and decide how each benefit treats automation.
The bot check gives AbuseZero Automation Defense a verification taken at the moment the person submits a claim. It runs in the browser, and AbuseZero verifies it inside the evaluation that follows. You then decide, benefit by benefit, how detected automation is treated. For the bigger picture, see Bots and AI agents.
Before you begin
- Browser protection is set up, and your server sends
identifiers.device_tokenwith every evaluation. - A server key with the scopes
benefits:read,benefits:write,policies:read,evaluations:createandevaluations:read.
Run the bot check on submit
Call prepareBotObservation instead of observe in your submit handler. It takes the same options and returns the same deviceToken. Wait for it to finish before you send the form.
import { prepareBotObservation } from "abusezero/browser";
export async function submitTrial(claimId: string, email: string) {
const { deviceToken } = await prepareBotObservation({ key: "pk_…", claimId });
await fetch("/api/trial", {
method: "POST",
headers: { "Content-Type": "application/json" },
body: JSON.stringify({ claimId, email, deviceToken }),
});
}Call it on submit, not when the page loads. The result is tied to this claim and this moment.
Evaluate within 2 minutes
Send the deviceToken to AbuseZero as identifiers.device_token within 2 minutes, in evaluate() or POST /v1/evaluations. Your server code doesn't change.
- A token sent later than that can't be verified. When the benefit requires a bot check, the evaluation returns
BOT_EVIDENCE_REQUIRED. Run the bot check again and resubmit. - Each token belongs to one claim. Reusing it for another claim returns
DEVICE_TOKEN_USED(conflict).
Choose how the benefit treats automation
Two benefit settings control automation. Change them on the Benefits page of the dashboard, with PATCH /v1/benefits/{id} in the AbuseZero REST API, with abusezero benefits update in the AbuseZero CLI, or with abusezero_update_benefit on the AbuseZero MCP server. Both are described in the Automation settings reference.
| Setting | Value | Effect |
|---|---|---|
automation | assess (default) | Detected automation counts toward the AbuseZero Risk Score. |
deny | Detected automation is denied, with the reason automation. | |
allow | Detected automation doesn't count against the claim. | |
bot_evidence | optional (default) | Evaluations run with or without a bot check. |
required | An evaluation without a usable bot check returns an error instead of a result. |
Recognized AI agents that you allow on the benefit are exempt from both settings. See Verify AI agents.
A benefit update sends the benefit's full settings with its current revision. This helper reads the benefit and its policy with the SDK's additional methods, applies your changes and saves it:
import { abusezero } from "./abusezero";
type Benefit = {
name: string;
policy: string;
mode: "protect" | "observe";
revision: number;
config: Record<string, unknown>;
};
export async function updateBenefitConfig(benefitId: string, changes: Record<string, unknown>) {
const benefit = await abusezero.getBenefit(benefitId) as Benefit;
const policy = await abusezero.getPolicy(benefit.policy) as { key: string };
const config = Object.fromEntries(Object.entries(benefit.config).filter(([, value]) => value !== null));
return abusezero.updateBenefit(benefitId, {
name: benefit.name,
policy_key: policy.key,
protection_mode: benefit.mode,
config: { ...config, ...changes },
revision: benefit.revision,
}, `benefit:${benefitId}:revision:${benefit.revision}`);
}await updateBenefitConfig("ben_6f1d2c3b-4a5e-4f60-8b7c-9d0e1f2a3b4c", {
automation: "deny",
bot_evidence: "required",
});If someone else saved the benefit since you read it, the update returns BENEFIT_CONFLICT (conflict). Read it again and retry.
Handle bot check errors
When bot_evidence is required, two errors mean the evaluation didn't run:
| Code | Status | What to do |
|---|---|---|
BOT_EVIDENCE_REQUIRED | 422 | The claim had no usable bot check. Run prepareBotObservation again and resubmit with the new token. |
BOT_EVIDENCE_UNAVAILABLE | 503 | The bot check couldn't be verified this time. The error is retryable: collect fresh evidence and retry shortly. See unavailable errors. |
The AbuseZero Node.js SDK always throws these errors, even when outage is "allow" or "deny". A missing bot check never becomes a local decision.
import { AbuseZeroError, type EvaluationRequest } from "abusezero/server";
import { abusezero } from "./abusezero";
export async function evaluateWithBotCheck(input: EvaluationRequest, attempt: number) {
try {
return await abusezero.evaluate(input, `evaluate:${input.claim_id}:${attempt}`);
} catch (error) {
if (error instanceof AbuseZeroError && error.code.startsWith("BOT_EVIDENCE_")) {
return { status: "run_bot_check_again" as const };
}
throw error;
}
}The resubmitted claim keeps its claim_id but carries a new token, so it needs a new Idempotency-Key. Here the key includes an attempt number.
Verify your integration
Submit a claim from your page, then open its evaluation with GET /v1/evaluations/{id}.
curl https://api.abusezero.com/v1/evaluations/eval_3f6c2a1e-8b4d-4c7a-9e2f-5d1b7a0c4e93 \
-H "Authorization: Bearer $ABUSEZERO_SECRET_KEY"browser_dataiscollected.- In the evaluation's evidence or the dashboard, the
automationfamily has an assessment other thanunavailable.
With automation set to deny, a claim submitted by automation is denied with the reason automation.
How is this guide?
Last updated on