TRACIOのボット検知システムは、クライアントサイドでのシグナル収集とサーバーサイドでの分析という二層アーキテクチャを用いて、自動化ブラウザ、ヘッドレスツール、スクリプト化された攻撃を識別します。主要な自動化フレームワーク、ヘッドレスブラウザ、AIブラウジングエージェント、アンチディテクトブラウザをほぼゼロの誤検知で検知し、同時に正規の検索エンジンクローラーを自動的に許可リストへ登録します。
ブラウザエージェントは、サーバーサイドの判断に用いるさまざまなボット固有シグナルおよびクロス検証シグナルを収集します。以下のシグナルIDは説明用であり、内部IDは安定した公開契約ではありません。
| シグナル | 説明 |
|---|---|
s300 (webdriver) | navigator.webdriver フラグ — 自動化フレームワークによって true に設定される |
s301 (eval length) | eval.toString().length — Chrome/Edge: 33、Firefox: 37。それ以外の値はインストルメンテーションを示します。 |
s305 (bot composite) | window/documentをスキャンし、14種類の自動化フレームワークのアーティファクトを検出 |
s97 (headless markers) | CDPアーティファクト、通知許可、プラグイン数、外側の寸法 |
s157 (automation scan) | Selenium、Puppeteer、PhantomJS、Playwrightほか10種類を対象とした網羅的スキャン |
s158 (iframe webdriver) | 隠しiframeを作成し、その中で navigator.webdriver を読み取ります。メインフレームにはパッチを当てるがiframeを見落とすツールを捕捉します。 |
s159 (native function) | Function と Object を削除し、getterが本当にネイティブかどうかをテストします。Proxyベースのインストルメンテーションを検知します。 |
s155 (window CRC32) | 各 window プロパティのCRC32ハッシュスキャンで、注入された自動化グローバルを検出 |
s163 (devtools trap) | コンソールgetterトラップ — DevToolsが現在開いているかどうかを検知 |
サーバーは一連の検知器を実行し、その重み付けされた出力を組み合わせてボットスコアを算出します。スコアはしきい値によって判定にマッピングされます —bot は0.70以上のとき、suspicious は0.30以上のとき、それ以外は human です — そしてハードフェイルシグナル(navigator.webdriver など)は無条件で bot 判定を強制します。ボット判定には自由形式の bot_type ラベルが付随します。
代表的な検知器とその効果:
| 検知器 | 効果 |
|---|---|
| Webdriverフラグ | ハードフェイル → bot(タイプ webdriver) |
| 複合的な自動化 / フレームワークスキャン | 高い重み → bot(タイプ {framework}) |
| ヘッドレスマーカー | 重み付け → bot(タイプ headless) |
| eval-lengthの異常 | 重み付け → bot(タイプ unknown) |
| 悪質ボットのUAパターン | 重み付け → bot(タイプ {label}) |
| 検証済みの良性ボット(逆引きDNS) | 許可リスト → human |
| 挙動(レート / エントロピー / インタラクション) | 重み付け → bot(タイプ rateBot) |
| VM(Enterprise)・エミュレータ・DevTools(Business+) | 重み付けされたデバイス/改ざんシグナル |
プランと提供状況。 DevTools検知はBusinessおよびEnterpriseで動作します。 VM検知はEnterprise、エミュレータ検知はすべてのプランで動作します。これらはいずれも Webエージェントで動作します。root、jailbreak、クローン/デュアルアプリ、Frida、工場出荷時リセットの 検知はネイティブモバイルシグナルに依存しており、Web専用の デプロイ(開発中)では有効ではありません。Web上で完全に有効な、自動化、ヘッドレス、 AIエージェント、アンチディテクト、VM/エミュレータ、挙動に基づく判定を ご利用ください。
ボット検知は、すべてのイベントに bot_result フィールドを書き込みます(webhookのペイロードでは bot.result)。
bot_result は3つの正規の値のいずれかです:
| 結果 | 説明 |
|---|---|
human | 自動化の兆候は見つかりませんでした。検証済みの検索エンジンクローラーも human として解決されます。 |
bot | 自動化またはスクリプト化されたアクセスが検知されました。自由形式の bot_type ラベルが付随します。 |
uncertain | 混在または弱いシグナル — 明確に人間とも明確に自動化とも言えません。 |
これはダッシュボード全体で使用されるビジネス上の decision フィールド(real、fake、suspicious)にマッピングされ、またwebhookペイロードの bot.result にも対応します。
"bot" の場合)bot_type は自由形式の文字列です。以下の値は検知器が出力する内容の説明用の例であり、網羅的なenumではありません:
| タイプ | 検知方法 |
|---|---|
webdriver | navigator.webdriver が true |
selenium | Selenium固有のwindow/documentプロパティを検出 |
puppeteer | Puppeteer/Chromiumのヘッドレス指標に一致 |
playwright | Playwright固有のマーカーまたはUA文字列を検出 |
headless | 11種類中2つ以上のヘッドレスマーカーが発火 |
phantomjs | PhantomJSのグローバルを検出(callPhantom、_phantom) |
nightmare | NightmareJSのグローバルを検出 |
unknown | eval lengthの異常、またはその他の非特異的な自動化指標 |
rateBot | 挙動に基づくレート分析がしきい値を超過 |
最も直接的な検知です。主要な自動化フレームワークはすべて、WebDriver仕様に従って navigator.webdriver = true を設定します。これは、メインフレームのみにパッチを当てるツールを捕捉するために、メインフレーム(s300)と隠しiframe(s158)の両方でチェックされます。
window および document のプロパティに対して、フレームワーク固有のアーティファクトを網羅的にスキャンします:
| フレームワーク | 検出されるプロパティ |
|---|---|
| Selenium | _Selenium_IDE_Recorder、_selenium、calledSelenium、__selenium_evaluate、$cdc_*(ChromeDriver) |
| Puppeteer | domAutomation、domAutomationController、HeadlessChromeのUA |
| Playwright | __playwright、automation-controlledフラグ |
| PhantomJS | callPhantom、_phantom |
| NightmareJS | __nightmare、nightmare |
| CefSharp | CefSharp |
| Awesomium | awesomium |
| WebDriverIO | wdioElectron |
| Cypress | __cypress windowプロパティ |
このスキャンでは、Seleniumが注入する補助グローバルを検出するために、正規表現パターン /^([a-z]){3}_.*_(Array|Promise|Symbol)$/ も使用します。
11個のマーカーを評価し、分類のしきい値は2個以上です:
| マーカー | シグナル | 条件 |
|---|---|---|
| webdriver | s300 | = "true" |
| ベンダー派生の欠落 | s28 | window に chrome/safari オブジェクトがない |
| CDPヘッドレスchrome | s305 | headlessChrome = true |
| 通知が拒否 | s88 | 初回訪問時に Notification.permission = "denied" |
| chromeにruntimeなし | s89 | window.chrome は存在するが chrome.runtime が欠落 |
| 単一言語 | s90 | navigator.languages.length <= 1 |
| デフォルト画面800x600 | s5 | ヘッドレスChromeのデフォルト解像度 |
| HeadlessChromeのUA | UA | User-Agentに "HeadlessChrome" を含む |
| 外側の寸法がゼロ | s97 | outerWidth = 0 かつ outerHeight = 0 |
| WebGL SwiftShader | s70 | レンダラーに "swiftshader" を含む(ソフトウェアGPU) |
| WebGL llvmpipe | s70 | レンダラーに "llvmpipe" を含む(ソフトウェアGPU) |
既知の良性ボットはUser-Agentのパターンで認識されます。それぞれ偽装を防ぐために逆引きDNSで検証されます:
.googlebot.com)と照合| ボット | 許可ドメイン |
|---|---|
.googlebot.com、.google.com | |
| Bing | .search.msn.com |
| Apple | .applebot.apple.com |
| Yahoo | .crawl.yahoo.net |
| Yandex | .yandex.com、.yandex.net、.yandex.ru |
| DuckDuckGo | .duckduckgo.com |
あるリクエストがGooglebotを名乗っていても、そのIPの逆引きDNSが無関係なドメインに解決される場合(単なる欠落やタイムアウトではなく、確認されたPTR不一致)、bot(タイプ spoofed:google)として分類されます。
エントロピースコアリングを伴うレートベースの検知:
| レート(req/分) | エントロピーしきい値 | アクション |
|---|---|---|
| 120+ | < 0.1 | bot(タイプ: rateBot) |
| 60-120 | < 0.3 | bot(タイプ: rateBot) |
| 45-60 | < 0.1 | bot(タイプ: rateBot) |
| < 45 | 任意 | 正常 |
追加ルール: セッション経過30秒以上でマウス/キーボードのイベントがない場合、その訪問はタイプ noInteraction の bot として分類されます。
eval.toString().length はエンジンごとに一貫した値を生成します:
それ以外の値は eval 関数が自動化フレームワークによってフックされていることを示し、その訪問はタイプ unknown の bot として分類されます。
クライアントSDKは便利な真偽値 result.bot.detected を公開します:
const result = await tracio.getResult()
if (result.bot.detected) { // Log and block console.warn(`Bot detected (confidence ${result.bot.confidence})`) showCaptcha() return}
// Proceed with loginawait login(credentials)サーバー側では、webhookの配信に基づいて処理します。ボット検知は bot オブジェクト内にあります — bot.result と bot.type:
// `event` is the webhook delivery body (/docs/webhooks)app.post("/webhook/tracio", async (req, res) => { const event = req.body
if (event.bot.result === "bot") { await db.blockedRequests.insert({ visitorId: event.visitorId, botType: event.bot.type, ip: event.ip, timestamp: new Date(), }) }
res.status(200).send("OK")})TRACIOのボット検知は、ほぼゼロの誤検知を目指して設計されています。ただし、エッジケースは起こり得ます:
| シナリオ | リスク | 緩和策 |
|---|---|---|
navigator を変更するブラウザ拡張機能 | 低 | 複数シグナルのクロス検証により、単一シグナルでの発火を防止 |
| 企業向けセキュリティソフトウェア | 非常に低 | ヘッドレス検知には2つ以上のマーカーが必要 |
| アクセシビリティツール | なし | アクセシビリティAPIはいかなる検知シグナルも発火させません |
| VPN/プロキシユーザー | なし | VPNの使用はボット検知とは別に追跡されます |
誤検知が発生した場合は、bot.type フィールドを確認してどの検知器が発火したかを把握し、それに応じてポリシーを調整してください。