KillBot предоставляет два API, которые можно использовать:
- АПИ с оплатой за клиента. Это могут делать партнеры-провайдеры. Партнёру-провайдеру предоставляется менеджерский аккаунт в Килбот где он может управлять своими клиентами (создавать аккаунты, назначать подписки и т.п.). Стоимость подписки в этом случае составит 50% от публичных тарифов. Можно интегрировать KillBot в свой сервис с входом по кнопке в личный персонализированный кабинет килбота. Для получения доступа в аккаунт менеджера обратитесь в поддержку.
- АПИ с оплатой за запросы (тарифицируются только запросы которые классифицированы как пользователи. Стоимость смотрите на странице подписок: https://killbot.ru/subscriptions). Это JS API для программного получения информации, кому принадлежит визит - пользователю или боту. Можете встраивать в своё антифрод или любое другое решение.
API с оплатой за запросы для коммерческого использования (тариф API)
Если вы хотите интегрировать алгоритмы выявления ботов в своё решение, используйте API ниже.
Пример данных которые можно получить по АПИ тут: https://killbot.ru/snpsht.html - это живое JS демо, можно открыть исходный код и скопировать себе.
Идея
Подключение антифрода KillBot по API осуществляется размещением JS-кода на сайте. Код собирает браузерные данные и отправляет их на сервер KillBot. Результат проверки можно получить двумя способами:
- рекомендуется: событие
kbDataReceived— результат приходит автоматически после обработки данных; - альтернатива: GET-запрос на
/r/get.phpс номером сессии.
Для сбора данных подключается скрипт /js/cn.js с одного из серверов KillBot. Скрипт отправляет данные несколькими запросами, общий объём — 5–15 KB.
Скрипт KillBot не собирает персональные данные, не собирает данные ввода форм, не запрашивает доступ к микрофону, геолокации, видеокамере и другим де-идентифицирующим объектам.
Важно: для стабильной работы страница со скриптом Килбота должна открываться по HTTPS.
Самый минимальный вариант: только отправка браузерных данных на сервер Килбота (без ожидания) подключение cn.js . Результат можно запросить в ТЕЧЕНИЕ 5 минут.
Если вам не нужно сразу получать результат в JS — достаточно подключить cn.js. Он сам соберёт и отправит данные на сервер KillBot. Результат проверки можно запросить позже через get.php, когда это понадобится.
Результат проверки на бота нужно запросить в течение 300 секунд после отправки запроса, по истечению этого времени килбот результат проверки НЕ отдаст.
const kbKey = 'YOUR_KEY'; /* ключ из личного кабинета KillBot */
const kbUserID = Math.floor(Math.random() * 900000000);
const kbSessionID = (Date.now() * 10000) + (Math.floor(Math.random() * (99999 - 10000)) + 10000);
const s = document.createElement('script');
s.async = true;
s.src = 'https://data.killbot.ru/js/cn.js?hash_str=' + encodeURIComponent(kbKey)
+ '&r=' + btoa(document.referrer || '')
+ '&url=' + btoa(location.href)
+ '&c=' + kbSessionID
+ '&kbUserID=' + kbUserID
+ '&v=0&rmd' + Math.random();
document.head.appendChild(s);
// kbSessionID и kbUserID сохраните (cookie / localStorage / сервер) —
// по kbSessionID позже можно запросить результат через get.php
Когда нужно проверить результат — сделайте GET-запрос (с JS или с бэкенда):
// kbSessionID — тот же, что передавали в cn.js как параметр c=
fetch('https://data.killbot.ru/r/get.php?waf=1&c=' + kbSessionID)
.then(function(r) { return r.json(); })
.then(function(data) {
if (data.error) {
console.log('ошибка:', data.m);
return;
}
if (data.l === false) {
console.log('данные ещё не готовы, повторите запрос через 1–2 сек');
return;
}
console.log('bot:', data.bot, 'snsht:', data.snsht, data);
});
Если l === false или ответ пустой — данные ещё обрабатываются, повторите запрос через 1–2 секунды (обычно хватает 2–5 попыток).
Когда использовать какой вариант:
- только cn.js + get.php — минимум кода, результат можно получить с задержкойне более 5 минут;
- cn.js + kbDataReceived — результат нужен сразу после проверки на стороне JS;
- fetch + выбор сервера + kbDataReceived — production-интеграция с fallback при блокировках (см. пример выше).
Полный пример: выбор самого быстрого и рабочего сервера + kbDataReceived
Рекомендуемый способ интеграции:
- выбрать самый быстрый доступный сервер из списка (запрос
/ping); - загрузить
cn.jsчерезfetchи выполнить как inline-скрипт (не через<script src>— так надёжнее при блокировках); - при ошибке загрузки переключиться на следующий сервер из списка;
- получить результат в обработчике события
kbDataReceived.
const kbKey = 'YOUR_KEY'; /* ключ из личного кабинета KillBot — параметра kbKey в JS коде килбота (интеграция как JS)*/
const kbServers = [
'https://10052024.ru',
'https://r1.kill-bot.ru',
'https://data.killbot.ru',
'https://r3.nl.kill-bot.ru',
'https://r4.us.kill-bot.ru',
'https://r6.sg.kill-bot.net'
];
const kbSliderTimeout = 5000;
let kbServerURL = '';
let kbRes = null;
async function kbGetFastestServer(servers) {
return new Promise(function(resolve) {
let resolved = false;
const fallback = 'https://data.killbot.ru';
let pending = servers.length;
servers.forEach(function(url) {
const ctrl = new AbortController();
const t = setTimeout(function() { ctrl.abort(); }, 6000);
fetch(url + '/ping', { cache: 'no-store', mode: 'cors', signal: ctrl.signal })
.then(function(r) {
if (!resolved && r.status === 200) {
resolved = true;
resolve(url);
}
})
.catch(function() {})
.finally(function() {
clearTimeout(t);
pending--;
if (!resolved && pending <= 0) resolve(fallback);
});
});
setTimeout(function() {
if (!resolved) resolve(fallback);
}, 6050);
});
}
function kbFireTimeout() {
setTimeout(function() {
if (kbRes != null) return;
document.dispatchEvent(new CustomEvent('kbDataReceived', {
detail: JSON.stringify({ error: true, m: 'timeout' })
}));
}, 2 * kbSliderTimeout + 5000);
}
document.addEventListener('kbDataReceived', function(event) {
if (kbRes != null) return;
try {
if (event.detail) kbRes = JSON.parse(event.detail);
} catch (e) {
kbRes = null;
}
// Обрабатываем kbRes: bot, fraud, snsht, waf и т.д.
console.log('KillBot result:', kbRes);
});
(async function kbStart() {
kbServerURL = await kbGetFastestServer(kbServers);
const kbUserID = Math.floor(Math.random() * 900000000);
const kbSessionID = (Date.now() * 10000) + (Math.floor(Math.random() * (99999 - 10000)) + 10000);
kbFireTimeout();
const uri = '/js/cn.js?hash_str=' + encodeURIComponent(kbKey)
+ '&p=' + btoa('')
+ '&r=' + btoa(document.referrer || '')
+ '&url=' + btoa(location.href)
+ '&c=' + kbSessionID
+ '&kbUserID=' + kbUserID
+ '&v=0&rmd' + Math.random();
fetch(kbServerURL + uri)
.then(function(r) { return r.text(); })
.then(function(text) {
const s = document.createElement('script');
s.text = text;
s.id = 'kb-c';
document.head.appendChild(s);
})
.catch(function(e) {
document.dispatchEvent(new CustomEvent('kbDataReceived', {
detail: JSON.stringify({ error: true, m: e.message || 'cn.js load failed' })
}));
});
})();
Живая демо-страница с полной версией (fallback по серверам, pretty-print JSON, описание полей): https://killbot.ru/snpsht.html — можно открыть исходный код и скопировать себе.
Альтернатива: получение результата через get.php
Для надёжности финальный ответ лучше проверять и на бэкенде, в теории бот может подменить ответ JS-запроса - но на практике поведенческие боты так не делают - не встречал таких случаев на практике.
Результат можно опрашивать GET-запросом:
https://data.killbot.ru/r/get.php?c={{kbSessionID}}
Ниже пример GET запроса для получения результата средствами JS.
const kbTimeout = 2000;
const kbMaxRequests = 10;
let response = null;
let requestCount = 0;
function makeRequest() {
if (requestCount >= kbMaxRequests) {
response ? complete(response) : fail();
return;
}
requestCount++;
const xhr = new XMLHttpRequest();
xhr.open('GET', kbServerURL + '/r/get.php?c=' + kbSessionID, true);
xhr.timeout = 15000;
xhr.onreadystatechange = function() {
if (xhr.readyState !== 4) return;
if (xhr.status === 200) {
try {
response = JSON.parse(xhr.responseText);
if (!response || response.error === true || response.l === false) {
setTimeout(makeRequest, kbTimeout);
} else {
complete(response);
}
} catch (e) {
setTimeout(makeRequest, kbTimeout);
}
} else {
setTimeout(makeRequest, kbTimeout);
}
};
xhr.send();
}
function complete(response) {
// успех
}
function fail() {
// ошибка / таймаут
}
Пример ответа сервера
{
"bot": false, // итог проверки: true — бот / подозрительный визит
"fraud": false, // то же, что bot
"l": true, // скрипт полностью загружен и все слепки собраны
"bl": false, // слепок в чёрном списке (известные боты)
"wl": true, // слепок в белом списке (известные браузеры)
"d": false, // deny: true — запретить доступ на сайт
"capt": 0, // капча: 0 — нет; 1 — капча; 2 — слайдер; 3/31 — alert; 4 — hang; 6 — deny
"snsht": 2969538378, // основной слепок браузера (999999 — сгруппированный бот)
"net_id": 2696850341, // идентификатор сети
"net_t": "home", // тип сети: home, mob, corp, vpn
"os": "Windows", // ОС посетителя
"sess": "45786830545786830", // ID сессии (kbSessionID)
"UserID": "468073784468073784", // ID пользователя (kbUserID)
"ip": "51.158.237.65", // IP визита
"t": true, // показывать метрику: false — не грузить код метрики
"act": "1", // подписка активена
"cv": "abc123...", // checksum для серверной проверки ответа
"metr": "44537875", // ID счётчика Яндекс.Метрики (если настроен)
"utm": "is_bot", // имя HTTP-параметра для передачи результата проверки в URL (из настроек)
"url": "", // URL редиректа (если задан WAF правилом)
"waf": { /* см. ниже */ }
}
WAF-данные
С их помощью можно создавать правила фильтрации:
killbot:
UserID: 429434077125846125 // уникальный ID пользователя
UserID2: 429434077125846125 // альтернативный ID (cross-check)
bot: false // визит от бота?
capt: 0 // тип капчи для визита (см. capt выше)
metr: true // показывать метрику
deny: false // блокировка доступа
man_act: true // для слепка задано ручное действие
solved_early: false // ранее решал капчу на этом сайте
solved_early_killbot: false // ранее решал капчу в экосистеме KillBot
vpn: false // VPN / proxy
snsht: 65519223 // слепок браузера
snsht_org: 695851122 // исходный snsht до группировки ботов
net_id: 3957945795 // идентификатор сети
net_t: home // home — домашняя; mob — мобильная; corp — корпоративная
bl: false // слепок в blacklist
wl: true // слепок в whitelist
ffp: 3329686866 // fingerprint шрифтов
host: data.killbot.ru // сервер, обработавший запрос
adt: false // признаки anti-detect / spoofing
not_solved: false // часто видит капчу, но не решает
shows_count: 8 // сколько раз показывалась капча UserID
solved_count: 0 // сколько раз UserID решал капчу
new_user_killbot: true // новый UserID в KillBot
new_user_website: true // новый UserID на этом сайте
tm: 0 // время обработки (сек)
user:
timezone: Asia/Novosibirsk // часовой пояс браузера
locale: ru // локаль браузера
net:
ip: 94.237.108.10 // IP пользователя
host: 94-237-108-10.example.host // reverse DNS
asn: 202053 // ASN
country: FI // страна по IP
ports: [] // открытые порты (WebRTC scan)
ping: true // IP пингуется
ttlOS: Linux // ОС по TTL
ttl: 54
ttl_b: 52
rtt: 93.25 // round-trip time (мс)
request:
user-agent: Mozilla/5.0 ...
accept-language: ru-RU,ru;q=0.9
url: https://example.com/page // URL, с которого вызван KillBot
referer: // referer
browser:
name: Chrome
language: ru-RU
webdriver: false // true — automation (бот)
innerheight: 919
innerwidth: 1920
outerheight: 1040
outerwidth: 1920
device:
width: 1920
height: 1080
os: Windows
gc: ANGLE (NVIDIA, ...) // GPU / WebGL renderer
fps: 63 // FPS (requestAnimationFrame)
Ошибочный ответ
{
"error": true,
"error_code": 100, // 100 — сессия не найдена; 200 — другая ошибка
"m": "KillBot session does not exist kbSessionID=255483105"
}