Django・PythonでAIクローラーをブロックする方法
PythonフレームワークでAIボットをブロックする必要性
Next.jsやNginxの事例は多く紹介されていますが、DjangoやFastAPIなどPythonで構築されたWebサービスへの対応はあまり解説されていません。このガイドではPythonフレームワーク向けの具体的な実装方法を紹介します。
Django:Middlewareでブロック
Djangoの場合、カスタムMiddlewareを作成するのが最もクリーンな方法です。
ai_block/middleware.py を作成
import re
from django.http import HttpResponseForbidden
AI_BOT_PATTERN = re.compile(
r"GPTBot|OAI-SearchBot|ClaudeBot|anthropic-ai|"
r"PerplexityBot|Google-Extended|Amazonbot|Bytespider|"
r"CCBot|cohere-ai|MistralBot|Diffbot",
re.IGNORECASE
)
class AIBotBlockerMiddleware:
def __init__(self, get_response):
self.get_response = get_response
def __call__(self, request):
ua = request.META.get("HTTP_USER_AGENT", "")
if AI_BOT_PATTERN.search(ua):
return HttpResponseForbidden("Access denied")
return self.get_response(request)
settings.pyに登録
MIDDLEWARE = [
"django.middleware.security.SecurityMiddleware",
"ai_block.middleware.AIBotBlockerMiddleware", # ← 追加(上部に配置)
"django.contrib.sessions.middleware.SessionMiddleware",
# ... 以下省略
]
Django:robots.txtビューの実装
Djangoではrobots.txtも動的に生成できます:
# urls.py
from django.urls import path
from .views import robots_txt
urlpatterns = [
path("robots.txt", robots_txt),
# ...
]
# views.py
from django.http import HttpResponse
def robots_txt(request):
lines = [
"User-agent: GPTBot",
"Disallow: /",
"",
"User-agent: ClaudeBot",
"Disallow: /",
"",
"User-agent: PerplexityBot",
"Disallow: /",
"",
"User-agent: Google-Extended",
"Disallow: /",
"",
"User-agent: Amazonbot",
"Disallow: /",
"",
"User-agent: Bytespider",
"Disallow: /",
"",
"User-agent: *",
"Allow: /",
"Sitemap: https://yourdomain.com/sitemap.xml",
]
return HttpResponse(
"\n".join(lines),
content_type="text/plain"
)
FastAPI:Middlewareでブロック
FastAPIではStarlette Middlewareを活用します:
import re
from fastapi import FastAPI
from starlette.middleware.base import BaseHTTPMiddleware
from starlette.requests import Request
from starlette.responses import Response
AI_BOT_PATTERN = re.compile(
r"GPTBot|OAI-SearchBot|ClaudeBot|anthropic-ai|"
r"PerplexityBot|Google-Extended|Amazonbot|Bytespider|"
r"CCBot|cohere-ai|MistralBot|Diffbot",
re.IGNORECASE
)
class AIBotBlockerMiddleware(BaseHTTPMiddleware):
async def dispatch(self, request: Request, call_next):
ua = request.headers.get("user-agent", "")
if AI_BOT_PATTERN.search(ua):
return Response("Access denied", status_code=403)
return await call_next(request)
app = FastAPI()
app.add_middleware(AIBotBlockerMiddleware)
FastAPI:依存性注入でエンドポイント単位にブロック
全体ではなく特定のエンドポイントだけブロックしたい場合:
from fastapi import Depends, HTTPException, Request
def block_ai_bots(request: Request):
ua = request.headers.get("user-agent", "")
if AI_BOT_PATTERN.search(ua):
raise HTTPException(status_code=403, detail="AI crawlers not allowed")
@app.get("/articles/{article_id}", dependencies=[Depends(block_ai_bots)])
async def get_article(article_id: int):
# ...
pass
Flask:before_requestフック
import re
from flask import Flask, request, abort
AI_BOT_PATTERN = re.compile(
r"GPTBot|ClaudeBot|PerplexityBot|Google-Extended|Amazonbot",
re.IGNORECASE
)
app = Flask(__name__)
@app.before_request
def block_ai_bots():
ua = request.headers.get("User-Agent", "")
if AI_BOT_PATTERN.search(ua):
abort(403)
レート制限と組み合わせる
完全ブロックではなくレート制限でコスト増を狙うアプローチも有効です(slowapi使用):
from slowapi import Limiter
from slowapi.util import get_remote_address
limiter = Limiter(key_func=get_remote_address)
@app.get("/content")
@limiter.limit("10/hour") # AIボット向けに厳しく制限
async def get_content():
pass
アクセス状況の可視化
どのAIボットがどの頻度でアクセスしているかを把握するには、AI Access Monitorが便利です。1行のJavaScript、またはAPIエンドポイント経由でPythonバックエンドからも利用できます。
import httpx
async def log_to_monitor(ua: str, url: str, site_id: str):
"""AI Access MonitorにアクセスをPOSTする例"""
async with httpx.AsyncClient() as client:
await client.post(
"https://monitor-api.microforge.works/collect",
json={"site_id": site_id, "ua": ua, "url": url},
timeout=2.0 # fire-and-forget
)
まとめ
PythonフレームワークでのAIボットブロックは、Middlewareを使えばわずか20行程度で実装できます。robots.txtと組み合わせた多層防御で、コンテンツを守りましょう。