Akamai Bot Manager · BMP
Generate sensor headers for the mobile SDK flow. Collect the native application's package and BMP SDK version. Device and opaque session values let later tasks continue the same mobile identity.
{
"clientKey": "capzy_YOUR_API_KEY",
"task": {
"type": "AntiAkamaiBMPTaskProxyLess",
"packageName": "com.target.app",
"version": "3.3.4",
"deviceId": "samsung-SM-A202F-fed1"
}
}Illustrative values. Replace the inputs with values from your current integration.
Match the app's SDK configuration.
Collect the native application's package and BMP SDK version. Device and opaque session values let later tasks continue the same mobile identity.
Your API key authenticates Capzy.
Provider keys, challenge IDs, images, and session values belong inside task.
Match package, platform, and SDK version.
- Read packageName from Android applicationId or the iOS bundle identifier in your app's build configuration.
- Read the BMP dependency version from the Gradle/APK dependency or CocoaPod configuration. Choose a supported version matching the platform.
- Set platform to android or ios as appropriate. Read appVersion and language from the host app/device when providing those overrides.
{
"packageName": "com.example.app",
"version": "YOUR_SUPPORTED_BMP_VERSION",
"platform": "android",
"appVersion": "YOUR_APP_VERSION",
"language": "en-US"
}The BMP SDK version and your appVersion are different values; do not substitute one for the other.
How Akamai Bot Manager · BMP works
Akamai's Bot Manager Premier (BMP) ships as a native SDK that Android and iOS apps embed alongside Akamai-protected API calls. Each outbound request is signed with an `X-acf-sensor-data` header derived from a per-device sensor payload — the same algorithm family as the web `_abck` cookie, but emitted by the mobile SDK rather than a JS bundle. The sensor payload encodes device identity (`deviceId`), the host app's `packageName` and version, the BMP SDK version, and a stream of hardware signals (accelerometer, gyroscope, battery, locale, screen). Akamai validates the payload against its model and either lets the API call through or returns a 4xx with a re-challenge marker. Use this product whenever you're replaying a native mobile app's API call — not when you're scraping the website. For the web/desktop variant (bmak JS bundle, _abck cookie) see /solvers/akamai-web.
Capzy runs a proprietary sensor generation engine that produces valid BMP payloads on demand — no device emulator, no browser. Send `packageName` and `version`; we return a `deviceId`, the matching `useragent`, and `sensors[]` ready to drop into the `X-acf-sensor-data` header. Both Android and iOS 4.2.x are fully supported. Each solve creates a pinnable device session. Pass the returned `session` back on the next call to keep the same device identity and key material across a multi-step flow — Akamai scores it as one returning device. Use a fresh `deviceId` (or omit it) when you need a new identity. Drop-in compatible with the industry-standard CapSolver `AntiAkamaiBMPTask` — point your existing client at `https://api.capzy.ai` with `type: AntiAkamaiBMPTaskProxyLess` and it works without any other change. No proxy needed.
- Native Rust runtime for Android + iOS 4.2.x — no emulator, no browser, sub-second per sensor
- iOS 4.2.0 / 4.2.1 fully supported — CFNetwork UA + real IDFV device fingerprint, live-verified
- Session pinning for Android 4.2.1 + iOS 4.2.x — reuse device identity and cryptographic keys across requests
- Batch via `count` — up to 50 sensors per call, all from the same device
- Drop-in compatible with `AntiAkamaiBMPTask` — change one URL + one key to migrate from CapSolver
Supported devices & BMP versions
Every solve mints its sensor from a genuine Android device fingerprint (model, screen, hardware sensors, build). Search for your app’s target handset below to confirm coverage and preview the exact User-Agent we pair with it — the API returns that UA with every solve, and you must send it on the same request as the sensor. Click any UA to copy it.
Akamai BMP SDK versions
Loading device list
Know what goes in.
Choose a field to see its purpose, where to get it, and its place in the request. Optional values omitted from the example can be added when your flow uses them.
Default. Returns a Dalvik User-Agent and an Android device fingerprint. All BMP versions supported.
Request authentication
Required task inputs
Optional context
packageName
stringRequiredNative app's bundle identifier. Android: reverse-domain like `com.target.app`. iOS: same format, e.g. `com.pozitron.pegasus`. Must match what the real app ships — Akamai validates package against the sensor.
Read your Android applicationId/package or iOS bundle identifier from the app's build configuration.
Open the input guidecom.target.app{
"clientKey": "capzy_YOUR_API_KEY",
"task": {
"type": "AntiAkamaiBMPTaskProxyLess",
"packageName": "com.target.app",
"version": "3.3.4",
"deviceId": "samsung-SM-A202F-fed1"
}
}The selected field is highlighted when present. Preserve the declared value type and current challenge context.
Make your first request.
Create the task, keep its taskId, and poll until status is ready. Then read the selected variant's solution.
- Create the task
Send
clientKeyand the selectedtaskto/createTaskfrom your server. Keep the returnedtaskId. - Wait for the solution
Send that same key and ID to
/getTaskResult. While processing, wait two seconds before checking again. Stop on Ready or an error. - Apply the result
Submit solution.sensors in your application's BMP transport in the returned order. Preserve solution.deviceId, solution.session, and solution.useragent for the next sensor request.
import json, os, time
import requests
API = "https://api.capzy.ai"
KEY = os.environ["CAPZY_API_KEY"]
task = json.loads("{\"type\":\"AntiAkamaiBMPTaskProxyLess\",\"packageName\":\"com.target.app\",\"version\":\"3.3.4\",\"deviceId\":\"samsung-SM-A202F-fed1\"}")
def call(path, payload):
response = requests.post(f"{API}/{path}", json={"clientKey": KEY, **payload}, timeout=30)
response.raise_for_status()
data = response.json()
if data.get("errorId", 0) or data.get("status") == "failed":
raise RuntimeError(data.get("errorDescription") or data.get("errorCode") or "Task failed")
return data
created = call("createTask", {"task": task})
for attempt in range(60):
result = call("getTaskResult", {"taskId": created["taskId"]})
if result.get("status") == "ready":
solution = result["solution"]
print(solution)
break
time.sleep(2)
else:
raise TimeoutError("Task is still processing; keep the taskId to check it later.")
Before runningReplace all illustrative inputs with your captured values. Set CAPZY_API_KEY in your environment. Install requests with pip install requests.
Polling and failuresThe example checks HTTP/API failures, uses 30-second request timeouts, and stops after 60 result checks. Retain taskId if your task is still processing.
Understand what comes back.
Follow this task from creation to completion. Response fields and usage follow your selected request variant.
Mobile sensor payloads
Submit solution.sensors in your application's BMP transport in the returned order. Preserve solution.deviceId, solution.session, and solution.useragent for the next sensor request.
- array
- Array of sensor payload strings, one per requested `count`. Each is single-use: set `sensors[0]` as the `X-acf-sensor-data` header value on your next request, then discard it. When empty, solve again.
- string
- The device the sensors were minted from. Reuse this exact value on your next call to keep the same device. For iOS, this is a UUID (IDFV format).
- string
- Exact User-Agent the BMP SDK sets on the request. Always send this alongside the sensor — Akamai cross-checks UA against the device fingerprint.
- string
- Opaque session token encoding the device identity and AES/HMAC keys. Pass this as `session` on your next call to reuse the same cryptographic context. Present for Android 4.2.1 and iOS 4.2.0 / 4.2.1.
- string
- Echo of the BMP SDK version.
{
"errorId": 0,
"status": "ready",
"solution": {
"sensors": [
"<sensor payload — single-use>",
"<sensor payload — single-use>"
],
"deviceId": "samsung-SM-A202F-fed1",
"useragent": "Dalvik/2.1.0 (Linux; U; Android 13; SM-A202F Build/TQ3A.230901.001)",
"session": "<opaque session token — pass back to reuse this device>",
"version": "3.3.4"
}
}Illustrative values. Additional metadata may be returned; only Ready contains a completed solution.
Send the sensor
Each string in sensors[] is one X-acf-sensor-data header value. Send it with the returned useragent — the payload binds to that device fingerprint.
Execution context result is the parsed Ready response from the polling example. session, when referenced, is your existing requests.Session (or browser-compatible session) with the original cookie jar, headers, and solving proxy configured in session.proxies for both http and https. Keep this client for the complete flow. task is the task object you submitted. For Shape, action_body is the original protected request body as bytes or a string, with its original Content-Type in session.headers. Install curl_cffi when the fragment imports it; match the target's required browser/TLS identity.
# Step 3 — send each sensor as the X-acf-sensor-data header on the app's API call
sol = result["solution"]
for sensor in sol["sensors"]:
requests.post("https://api.example.com/mobile/endpoint", headers={
"X-acf-sensor-data": sensor,
"User-Agent": sol["useragent"], # MUST match the device the sensor was minted for
})When something doesn't work.
Check your captured values, the selected variant, and the response before starting another task.
Do I need a proxy for BMP?
No. The BMP sensor binds to `deviceId` + `packageName`, not an IP address. `AntiAkamaiBMPTask` (with proxy params) exists for API symmetry only — the proxy fields are accepted but ignored.
Which BMP SDK versions are supported?
Android: 2.1.2, 2.2.2, 3.1.0, 3.2.3, 3.3.0, 3.3.1, 3.3.4, 3.3.9, 4.0.2, 4.2.0, 4.2.1 (default 3.3.4). iOS: 4.2.0 and 4.2.1 only. Pin `version` to whatever the production app ships with. If your version isn't listed, contact us.
How do I use the sensors[] array?
Each element is a single-use sensor string. Set `sensors[0]` as the `X-acf-sensor-data` header value on your next request, then discard it. When the array is empty, solve again. Requesting `count: 3` upfront is the cheapest way to absorb a burst.
What is the session field for?
Passing `session` back on your next call reuses the same device identity AND the same AES/HMAC cryptographic keys as the previous solve. Apps that track session continuity (most 4.x targets) need this to avoid re-challenge. Available for Android 4.2.1 and iOS 4.2.0 / 4.2.1. Omit it to start a fresh session.
How do I pin one device across a multi-step flow?
Use the `session` field (Android 4.2.1 / iOS 4.2.x) or pass the same `deviceId` on every call. `session` is stronger because it preserves the cryptographic key material; `deviceId` alone keeps the same hardware fingerprint and UA but allows the keys to rotate. For a login + action + action flow, always pin the session.
How do I find my app's BMP SDK version?
Android: open the APK with apktool and grep for `akamai` in the smali or check `akamai-bmp-android` in your Gradle manifest. iOS: check the BMP CocoaPod version in the app's Podfile.lock. Versions look like `3.3.4` or `4.2.1`.
Web vs BMP — which do I need?
Web (`AntiAkamaiWebTask`) is for scraping the website in a browser. BMP is for replaying native mobile-app API calls. If you need the `X-acf-sensor-data` header, use BMP. If you're scraping the website, use Web.
Integration checks for Akamai Bot Manager · BMP
- Use the userAgent we return. Akamai's mobile BMP path correlates the UA with the deviceId and the sensor signature. Override it with your own UA string and the sensor is rejected on the very first replay.
- Send the EXACT packageName your app ships with (e.g. `com.target.app`, not just `app`). BMP's server-side validator scopes each sensor to the package; sending a mismatched name returns 4xx immediately.
- BMP SDK versions matter. Akamai retires older versions on rotation — pin `version` to whatever your app's bundle ships with, and watch for `429 / 403` returning suddenly when the customer's app upgrades.
- This is the mobile SDK variant. If you're scraping the website (browser-style), the X-acf-sensor-data header doesn't apply — use Akamai Web at /solvers/akamai-web instead.
Connect Akamai Bot Manager · BMP to your workflow.
Get your Capzy API key and use this guide's integration.
AntiAkamaiBMPTaskProxyLess · Live configuration