Satelit Shield
Останавливайте ботов и парсеры, а не людей
Shield распознаёт автоматизацию, антидетект-браузеры и парсеры, на странице и на сервере; человек видит самое большее проверку, которая проходит сама примерно за секунду.
Первые 7 дней: пробный период, 100 000 проверок.
Проверяем браузер
Сенсор Shield работает на этой странице, как на сайте клиента.
Настоящий браузербалл …/100
Нет признаков автоматизации или поддельного отпечатка. На защищённом сайте страницы открываются как обычно.
Несколько признаков рискабалл …/100
Слабые признаки, не точные. На защищённом сайте вы увидели бы самое большее проверку, которая проходит сама.
Найдена автоматизациябалл …/100
Точные признаки автоматизации или маскировки. На защищённом сайте доступ был бы остановлен.
Поисковый роботбалл …/100
Заявленный робот. Проверенных, таких как Google и Bing, не останавливают никогда.
Браузер прошёл
Shield не запросил у этого браузера никакой проверки.
Тест не ответил
Блокировщик контента или медленная сеть остановили скрипт. Через first-party прокси он идёт с вашего домена.
Что увидел сенсор
Признаки появятся после первого отчёта сенсора.
Это ID проверок в том виде, в каком их отправляет сенсор. Что значит каждый, написано в панели Shield.
Тот же скрипт, что вы ставите на сайт. Он отправляет только ID проверок: без координат, клавиш и текста.
- Проверка проходит сама примерно за секунду. Человек ничего не нажимает.
- Сначала наблюдение: видно, что остановил бы Shield, потом включаете защиту.
- Проверенные поисковые роботы не затрагиваются никогда.
Что останавливает
Автоматизация, поддельные отпечатки, парсеры и злоупотребления
Каждая карточка говорит, что ищет Shield и какие правила решают.
-
Автоматизация браузера
Selenium, Puppeteer, Playwright, Cypress, TestCafe и headless Chrome, узнаваемые по следам, которые они оставляют на странице.
automation -
Stealth-плагины и сборки «undetected»
Автоматизация, залатанная, чтобы казаться человеком. Shield ищет сами заплатки: подменённые функции, отсоединённые окна, Chromium, который выдаёт себя за Chrome.
stealth -
Антидетект-браузеры
Поддельные отпечатки. Shield сравнивает, что браузер заявляет, с тем, что делает его движок: экран, часовой пояс, язык, шрифты, рисунок на canvas.
antidetectbrowser-soft -
HTML-парсеры
Программы, которые запрашивают страницы, не выполняя их: ни одного отчёта сенсора, слишком много страниц, слишком часто.
no-proofratewalk -
Поддельный Googlebot
Имени робота верят, только если его подтверждают официальный список IP и обратный DNS. Проверенные роботы проходят всегда.
fake-crawlerrobotstrap -
Пулы адресов и дата-центры
Браузеры из хостинговых сетей, лживые User-Agent, несовпадающие заголовки. IPv6 считается по сети /64.
datacenterua-claimclient-hintsstale-browser -
Фальшивые голоса, комментарии и регистрации
Форма отправляет токен сенсора, а ваш сервер проверяет его один раз, в течение 300 секунд. При проверке с адресом посетителя токен, скопированный на другой адрес, отклоняется.
POST /verify{ "success": true, "verdict": "human", "score": 3, "action": "allow", "age_s": 4 }
Как это работает
Два слоя, одно решение
Сенсор видит браузер, ваш сервер видит запросы. Shield сводит их для каждого адреса и решает один раз.
-
На странице
Сенсор
- Один скрипт ES5 на ваших страницах, загружается async: не задерживает показ страницы.
- Отправляет только ID проверок: без координат, клавиш, текста и хеша отпечатка.
- Решает страницу проверки: доказательство работы на 14 бит.
- Хранит пропуск 12 часов, в cookie на вашем домене.
-
На сервере
Запросы
- Ваш сервер или edge сообщает, какие запросы приходят: по одному в
/assess, пакетами в/ingest. - Shield считает по адресу: IPv4 или сеть /64 для IPv6.
- Имя робота проверяется по официальному списку IP и через обратный DNS.
- Заголовки Sec-Fetch, Client Hints и User-Agent должны говорить одно и то же.
- Ваш сервер или edge сообщает, какие запросы приходят: по одному в
Три возможных исхода
- 200 Проходит Люди и проверенные роботы. Ничего не меняется.
- 429 Проверка на секунду Слабые признаки: страница, которая проходит сама. Человек ничего не нажимает.
- 403 Остановлен Точные признаки: 24 часа, затем 7 дней, затем 30 дней при повторе в течение 90 дней.
Сначала наблюдение, потом защита
У каждого правила есть режим: off, shadow (наблюдение: Shield только отмечает, что сделал бы) или enforce (защита). Новый сайт начинает со всеми правилами в наблюдении; вы переводите их в защиту по одному.
Проверенные роботы проходят всегда
Google, Bing, Apple, Yandex, DuckDuckGo, Baidu, OpenAI, Perplexity, Anthropic и другие: никаких решений, никогда. То же для вашего списка разрешённых.
Установка
Три шага, первый в одну строку
Ключ сайта (shp_…) публичный и стоит на странице. Секрет (shs_…) хранится только на сервере; вы видите его один раз.
-
Поставьте сенсор на страницы
Напрямую: одна строка на странице. Рекомендуем через first-party прокси, с вашего домена. Никаких запросов к третьим сторонам, работает при
script-src 'self', а блокировщики рекламы его не видят.<!-- in every page, direct --> <script src="https://api.satelit.md/shield/v1/sensor.js" data-site="shp_XXXXXXXXXXXXXXXXXXXXXXXX" async></script># Caddyfile: /_sh/* goes to Shield, with your secret and the visitor's address example.md { handle_path /_sh/* { rewrite * /shield/v1{uri} reverse_proxy https://api.satelit.md { header_up Host {upstream_hostport} header_up X-Shield-Secret {env.SHIELD_SECRET} header_up X-Shield-Client-IP {client_ip} header_up -Cookie header_up -Authorization } } # ... the rest of your site } # in every page: # <script src="/_sh/sensor.js" data-site="shp_XXXXXXXXXXXXXXXXXXXXXXXX" data-base="/_sh" async></script># nginx: /_sh/ goes to Shield, with your secret and the visitor's address location /_sh/ { proxy_pass https://api.satelit.md/shield/v1/; proxy_ssl_server_name on; proxy_set_header Host api.satelit.md; proxy_set_header X-Shield-Secret "shs_..."; # keep this file out of your repository proxy_set_header X-Shield-Client-IP $remote_addr; # behind Cloudflare: $http_cf_connecting_ip proxy_set_header Cookie ""; proxy_set_header Authorization ""; } # in every page: # <script src="/_sh/sensor.js" data-site="shp_XXXXXXXXXXXXXXXXXXXXXXXX" data-base="/_sh" async></script> -
Проверяйте токен в формах
При голосовании, комментарии или регистрации страница берёт токен через
SatelitShield.token()и отправляет его с формой. Ваш сервер проверяет его один раз, в течение 300 секунд.// a fresh token goes with the form, in a hidden field form.addEventListener("submit", function (e) { e.preventDefault(); SatelitShield.token(function (token) { form.elements.shield_token.value = token; form.submit(); }); });curl https://api.satelit.md/shield/v1/verify \ -H "Authorization: Bearer $SHIELD_SECRET" \ -H "Content-Type: application/json" \ -d '{ "token": "<the token from the form>", "ip": "203.0.113.9" }'// Node 18+: the token came with the form, ip is the visitor's address async function fromPerson(token, ip) { const res = await fetch("https://api.satelit.md/shield/v1/verify", { method: "POST", headers: { Authorization: `Bearer ${process.env.SHIELD_SECRET}`, "Content-Type": "application/json" }, body: JSON.stringify({ token, ip }), }); const v = await res.json(); return v.success === true && v.action !== "block"; }import json, os, urllib.request def from_person(token, ip): req = urllib.request.Request( "https://api.satelit.md/shield/v1/verify", data=json.dumps({"token": token, "ip": ip}).encode(), headers={"Authorization": f"Bearer {os.environ['SHIELD_SECRET']}", "Content-Type": "application/json"}, ) with urllib.request.urlopen(req, timeout=5) as res: v = json.load(res) return v.get("success") is True and v.get("action") != "block"<?php function from_person(string $token, string $ip): bool { $ch = curl_init("https://api.satelit.md/shield/v1/verify"); curl_setopt_array($ch, [ CURLOPT_RETURNTRANSFER => true, CURLOPT_POST => true, CURLOPT_TIMEOUT => 5, CURLOPT_HTTPHEADER => ["Authorization: Bearer " . getenv("SHIELD_SECRET"), "Content-Type: application/json"], CURLOPT_POSTFIELDS => json_encode(["token" => $token, "ip" => $ip]), ]); $v = json_decode(curl_exec($ch), true); curl_close($ch); return ($v["success"] ?? false) === true && ($v["action"] ?? "") !== "block"; } -
Перенесите решение на сервер
По желанию, для всего сайта. Middleware держит решения в памяти, читает их из
/decisionsраз в 15–30 секунд и отправляет запросы пакетами в/ingest. Ни один запрос посетителя не ждёт сеть.// Satelit Shield in a Node server: Express or any (req, res, next) stack. Node 18+, no packages. // The decisions stay in memory and are read again every 20 s, so a visitor's request never waits for the network. // Every request is sent to /ingest in batches. /_sh/ (the sensor) is served by the proxy in front, step 1. import { clientKey, passValid } from "./shield-pass.mjs"; const API = process.env.SHIELD_API || "https://api.satelit.md/shield/v1"; const SECRET = process.env.SHIELD_SECRET; // shs_..., never in a page const SITE = process.env.SHIELD_SITE; // shp_..., the public site key const HEADERS = { Authorization: `Bearer ${SECRET}`, "Content-Type": "application/json" }; const decisions = new Map(); // client key -> { a: "b" | "g", rule, until } const lines = []; let cursor = "0"; export async function poll() { const res = await fetch(`${API}/decisions?since=${cursor}`, { headers: HEADERS }); if (!res.ok) return; const body = await res.json(); if (body.full) decisions.clear(); for (const d of body.items) { if (d.a === "-") decisions.delete(d.key); else decisions.set(d.key, d); } cursor = body.cursor; } export async function flush() { while (lines.length) { const batch = lines.splice(0, 500); await fetch(`${API}/ingest`, { method: "POST", headers: HEADERS, body: JSON.stringify({ lines: batch }) }).catch(() => {}); } } export function start() { const quiet = (job) => () => job().catch(() => {}); quiet(poll)(); setInterval(quiet(poll), 20_000).unref(); setInterval(quiet(flush), 5_000).unref(); } const cookie = (req, name) => new RegExp(`(?:^|;\\s*)${name}=([^;]*)`).exec(req.headers.cookie ?? "")?.[1] ?? ""; const page = (mode, text) => `<!doctype html><html data-shield="${mode}"><head><meta charset="utf-8">` + `<meta content="noindex" name="robots"><meta name="viewport" content="width=device-width">` + `<script src="/_sh/sensor.js" data-site="${SITE}" data-base="/_sh" async></script></head><body><p>${text}</p></body></html>`; export function shield(req, res, next) { const ip = req.ip ?? req.socket.remoteAddress; // behind a proxy: Express's "trust proxy" gives the visitor's address const ua = req.headers["user-agent"] ?? ""; const path = (req.originalUrl ?? req.url).split("?")[0]; const shp = cookie(req, "__shp"); const pass = !shp ? 0 : passValid(shp, SECRET, ip, ua) ? 1 : 2; const d = decisions.get(clientKey(ip)); const on = d && (!d.until || Date.parse(d.until) > Date.now()) ? d.a : ""; // a ban is a 403; a check is a 429 unless the browser holds a valid pass (a pass never opens a ban) const gate = on === "b" ? 403 : on === "g" && pass !== 1 ? 429 : 0; res.on("finish", () => { const type = String(res.getHeader("content-type") ?? ""); const kind = /\.(css|js|mjs|png|jpe?g|gif|svg|webp|avif|ico|woff2?)$/i.test(path) ? "asset" : /json/.test(type) ? "api" : "html"; const h = (name) => req.headers[name] ?? ""; lines.push({ t: Date.now(), ip, ua, m: req.method, p: path, s: res.statusCode, k: kind, h: { sfs: h("sec-fetch-site"), chua: h("sec-ch-ua"), chm: h("sec-ch-ua-mobile"), chp: h("sec-ch-ua-platform"), al: h("accept-language"), ref: h("referer") }, pass, seen: cookie(req, "__shs") === "1" ? 1 : 0, g: gate === 429 ? 1 : 0, }); }); if (!gate) return next(); res.statusCode = gate; res.setHeader("Content-Type", "text/html; charset=utf-8"); res.setHeader("Cache-Control", "no-store"); res.end(gate === 429 ? page("check", "Checking your browser.") : page("ban", "Access blocked.")); }// Satelit Shield: check a pass (the __shp cookie) on your own server, with no call to Shield. Node 18+. // A pass is p1.{exp}.{token}.{sig}; sig is the first 22 characters of // base64url(HMAC-SHA256(pass key, "p1|{exp}|{token}|{client key}|{User-Agent}")). import { createHash, createHmac, timingSafeEqual } from "node:crypto"; // The pass key: HMAC-SHA256 with the key sha256_hex(secret) over "satelit-shield-pass-v1", in hex. export function passKey(secret) { const key = createHash("sha256").update(secret).digest("hex"); return createHmac("sha256", key).update("satelit-shield-pass-v1").digest("hex"); } // The client key: an IPv4 address as it is, an IPv6 address as its /64 (the first four groups and "::"). export function clientKey(ip) { const v4 = /^(?:::ffff:)?(\d{1,3}(?:\.\d{1,3}){3})$/i.exec(ip); if (v4) return v4[1]; const [head, tail = ""] = ip.toLowerCase().split("%")[0].split("::"); const a = head ? head.split(":") : []; const b = tail ? tail.split(":") : []; const groups = [...a, ...Array(Math.max(0, 8 - a.length - b.length)).fill("0"), ...b]; return groups.slice(0, 4).map((g) => parseInt(g, 16).toString(16)).join(":") + "::"; } // True when the pass has not expired and was signed for this address and this browser. export function passValid(pass, secret, ip, userAgent, now = Date.now() / 1000) { const m = /^p1\.(\d+)\.([0-9a-f]{16})\.([A-Za-z0-9_-]{22})$/.exec(pass ?? ""); if (!m || Number(m[1]) <= now) return false; const message = `p1|${m[1]}|${m[2]}|${clientKey(ip)}|${userAgent}`; const sig = createHmac("sha256", passKey(secret)).update(message).digest("base64url").slice(0, 22); return timingSafeEqual(Buffer.from(sig), Buffer.from(m[3])); }
Правила
15 правил, у каждого свой режим
Жёсткие правила останавливают незащищённый адрес. Мягкие только показывают проверку. Правило, которое превысило 50 остановок в час, или сайт, превысивший 200, само возвращается в наблюдение, а вы получаете событие.
-
automationWebDriver, ChromeDriver, Selenium, PhantomJS, Nightmare, Playwright, Puppeteer, Cypress, TestCafe, HeadlessChrome.
-
stealthЗалатанная автоматизация: подменённый Function.toString, окно из отсоединённого iframe, переопределённый webdriver, Chromium под видом Chrome, worker, который называет себя HeadlessChrome.
-
antidetectПоддельный отпечаток: движок JS старше заявленного браузера, шум на canvas, экран не совпадает с CSS, часовой пояс, язык, нет системных шрифтов, worker или Client Hints противоречат.
-
fake-crawlerИмя робота, опровергнутое двумя независимыми источниками: официальным списком IP и обратным DNS.
-
robotsЗаявленный бот, который запрашивает пути, запрещённые его группе в robots.txt.
-
trapСкрытый путь-ловушка сайта, запрещённый в robots.txt.
Ещё 9 правил
-
challenge-ignoredСтраница проверки показана одному адресу 6 и более раз без ответа.
-
browser-softДва и более слабых признаков: нет плагинов в десктопном Chrome, нет window.chrome, пустые языки, программный WebGL, протокол DevTools.
-
no-proof12 и более страниц за 10 минут без отчёта сенсора и без cookie __shs.
-
rate60 и более страниц в минуту.
-
walk40 и более разных страниц за 10 минут.
-
stale-browserДесктопный Chrome на 8 и более версий старше, без пропуска и без __shs.
-
ua-claimChrome 101+ с полным номером сборки (настоящий Chrome пишет N.0.0.0) или без Sec-Fetch-Site в Chrome 80+.
-
client-hintsЗаголовки Sec-CH-UA противоречат User-Agent: мобильный, платформа, версия, или их нет в Chrome 90+.
-
datacenterБраузерный User-Agent из хостинговой или облачной сети (ASN), без пропуска.
- Никогда не оцениваются
- Проверенные роботы и ваш список разрешённых.
- Только проверка, никогда не остановка
- Выходы Tor, общие адреса (3 и более настоящих браузеров на одном адресе за 24 часа) и адреса, которым вы доверяете.
Конфиденциальность
ID, а не отпечатки
Shield видит ровно столько, сколько нужно, чтобы отличить браузер от программы. Ничего лишнего.
- Только ID проверок. Сенсор отправляет ID проверок, число взаимодействий (без координат и клавиш) и первый язык браузера. Никакого хеша отпечатка.
- Cookie только на вашем домене.
__shp, пропуск после проверки, и__shs, знак того, что браузер выполнил сенсор. Своих cookie Satelit не ставит. - Короткое хранение. Ключ клиента (адрес или его сеть /64), User-Agent, правило и его доказательство: 30 дней. Почасовые счётчики: 90 дней.
- Секрет остаётся на сервере. Ключ сайта публичный. Секрет вы видите один раз, а Satelit хранит только его хеш.
Цены
Вы платите за проверки, а не за трафик
Одна проверка: один отчёт сенсора или один вызов /assess. Строки в /ingest бесплатны, до 10 на каждую проверку.
-
Shield Start
Один сайт: магазин, блог, небольшая редакция.
19 € / мес.
381,72 лей
- Сайты
- 1
- Проверки в месяц
- 250 000
-
Shield Pro
РекомендуемНесколько сайтов с формами, голосованиями или аккаунтами.
79 € / мес.
1 587,15 лей
- Сайты
- 5
- Проверки в месяц
- 2 500 000
-
Shield Business
Сети сайтов и платформы с большим трафиком.
249 € / мес.
5 002,53 лей
- Сайты
- 25
- Проверки в месяц
- 15 000 000
-
Enterprise
Большие объёмы, условия и счета по договору.
от 990 € / мес.
от 19 889,59 лей
- Сайты
- по договору
- Проверки в месяц
- от 50 000 000
У каждого нового сайта 7 дней пробного периода и 100 000 проверок. Леи по курсу НБМ на 2 ноября 2026 г.: 1 евро = 20,0905 лея.
Вопросы о Shield
Не навредит ли Shield позициям в Google?
Нет. Проверенные роботы (Google, Bing, Apple, Yandex, DuckDuckGo, Baidu, OpenAI, Perplexity, Anthropic и другие) не получают никаких решений: их имя подтверждают официальный список IP и обратный DNS. Сенсор загружается async и не задерживает показ страницы.
Работает ли вместе с Cloudflare?
Да. Shield не заменяет правила Cloudflare, а добавляет слой, который видит браузер. Если сайт за Cloudflare, ваш прокси передаёт адрес из CF-Connecting-IP в X-Shield-Client-IP, чтобы Shield оценивал посетителя, а не Cloudflare.
Что будет с человеком, которого приняли за бота?
Слабые признаки только показывают проверку, которая проходит сама примерно за секунду. Выходы Tor, общие адреса и адреса, которым вы доверяете, не останавливаются никогда. Правило со слишком многими остановками за час само возвращается в наблюдение, а любое решение можно снять в панели.
Как начать без риска?
Новый сайт начинает со всеми правилами в наблюдении: Shield только отмечает, что остановил бы. Вы читаете события в панели и переводите в защиту правила, которым доверяете, по одному.
Замедлит ли это сайт?
Сенсор загружается async, после страницы. Middleware держит решения в памяти и читает их раз в 15–30 секунд, так что запрос не ждёт сеть. Только /assess, если вы его используете, вызывается на каждый запрос.
Какие данные собирает Shield?
ID проверок, число взаимодействий без координат и клавиш и первый язык браузера. Shield хранит ключ клиента, User-Agent, правило и его доказательство 30 дней, а почасовые счётчики 90 дней. Без хеша отпечатка и без cookie Satelit: это можно точно описать в вашей политике конфиденциальности.
Что делает Shield, если скрипт заблокирован?
Серверный слой работает и без него: клиент, который запрашивает много страниц без отчёта сенсора, получает проверку. Через first-party прокси скрипт идёт с вашего домена, и блокировщики рекламы его не видят.
Сколько длится остановка?
24 часа, затем 7 дней, затем 30 дней, если адрес повторяет в течение 90 дней. Действующий пропуск открывает проверку, но никогда не остановку.
Посмотрите, что Shield остановил бы на вашем сайте
Новый сайт начинает в наблюдении: Shield только делает заметки. Защиту вы включаете, когда уверены, правило за правилом.