Việc xác minh quảng cáo yêu cầu truy cập hàng nghìn trang web để kiểm tra vị trí đặt quảng cáo, mức độ an toàn thương hiệu và tính tuân thủ. Nhiều trang web của nhà xuất bản sử dụng CAPTCHA để chặn việc kiểm tra tự động. CaptchaAI giúp hệ thống xác minh của bạn luôn hoạt động.
Kiểm tra xác minh quảng cáo nào
| Kiểm tra | Mô tả | Tại sao CAPTCHA chặn nó |
|---|---|---|
| Vị trí đặt quảng cáo | Quảng cáo có được hiển thị trong màn hình đầu tiên không? | Truy cập trang tự động kích hoạt phát hiện bot |
| An toàn thương hiệu | Không có quảng cáo bên cạnh nội dung có hại | Việc kiểm tra URL hàng loạt giống như việc thu thập dữ liệu |
| Khả năng xem | Quảng cáo có thực sự hiển thị không? | Trình duyệt headless được Cloudflare gắn cờ |
| Nhắm mục tiêu theo địa lý | Đúng quảng cáo ở đúng khu vực | Lưu lượng truy cập proxy kích hoạt CAPTCHA |
| Giám sát đối thủ cạnh tranh | Đối thủ cạnh tranh hiển thị những quảng cáo gì? | Tra cứu quảng cáo số lượng lớn |
Thực hiện
import requests
import time
import re
import json
import os
from datetime import datetime
API_KEY = os.environ["CAPTCHAAI_API_KEY"]
def solve_captcha(method, params):
params["key"] = API_KEY
params["method"] = method
resp = requests.get("https://ocr.captchaai.com/in.php", params=params)
if not resp.text.startswith("OK|"):
raise Exception(resp.text)
task_id = resp.text.split("|")[1]
for _ in range(60):
time.sleep(5)
result = requests.get("https://ocr.captchaai.com/res.php", params={
"key": API_KEY, "action": "get", "id": task_id,
})
if result.text == "CAPCHA_NOT_READY":
continue
if result.text.startswith("OK|"):
return result.text.split("|", 1)[1]
raise Exception(result.text)
raise TimeoutError()
def verify_ad_placement(url, session):
"""Verify ad placement on a publisher page."""
resp = session.get(url)
# Solve CAPTCHA if present
match = re.search(r'data-sitekey=["\']([A-Za-z0-9_-]+)["\']', resp.text)
if match:
token = solve_captcha("userrecaptcha", {
"googlekey": match.group(1),
"pageurl": url,
})
resp = session.post(url, data={"g-recaptcha-response": token})
html = resp.text
# Check for ad elements
result = {
"url": url,
"timestamp": datetime.utcnow().isoformat(),
"ads_found": [],
"brand_safety": True,
"captcha_solved": match is not None,
}
# Detect ad tags
ad_patterns = [
(r'googletag\.pubads', "Google Ad Manager"),
(r'doubleclick\.net', "DFP/DoubleClick"),
(r'ad\.doubleclick', "DoubleClick"),
(r'amazon-adsystem', "Amazon Ads"),
(r'criteo\.com/.*\.js', "Criteo"),
]
for pattern, name in ad_patterns:
if re.search(pattern, html):
result["ads_found"].append(name)
# Brand safety check — flag problematic content
safety_keywords = [
"violence", "hate speech", "explicit",
"gambling", "illegal",
]
page_text = re.sub(r'<[^>]+>', '', html).lower()
for keyword in safety_keywords:
if keyword in page_text:
result["brand_safety"] = False
break
return result
def run_verification(urls, output_file="verification_report.json"):
"""Run ad verification across multiple publisher URLs."""
session = requests.Session()
session.headers["User-Agent"] = (
"Mozilla/5.0 (Windows NT 10.0; Win64; x64) "
"AppleWebKit/537.36 Chrome/120.0.0.0"
)
results = []
for i, url in enumerate(urls):
try:
result = verify_ad_placement(url, session)
results.append(result)
ads = ", ".join(result["ads_found"]) or "None"
safe = "SAFE" if result["brand_safety"] else "UNSAFE"
print(f" [{i+1}/{len(urls)}] {url}: {ads} [{safe}]")
except Exception as e:
results.append({
"url": url,
"error": str(e),
"timestamp": datetime.utcnow().isoformat(),
})
print(f" [{i+1}/{len(urls)}] {url}: ERROR - {e}")
time.sleep(2)
with open(output_file, "w") as f:
json.dump(results, f, indent=2)
# Summary
total = len(results)
safe = sum(1 for r in results if r.get("brand_safety"))
captchas = sum(1 for r in results if r.get("captcha_solved"))
errors = sum(1 for r in results if "error" in r)
print(f"\n Total: {total} | Safe: {safe} | CAPTCHAs solved: {captchas} | Errors: {errors}")
return results
# Publisher URLs to verify
publisher_urls = [
"https://publisher1.com/article/tech-news",
"https://publisher2.com/sports/latest",
"https://publisher3.com/finance/markets",
]
run_verification(publisher_urls)
Mở rộng quy mô với các nhà xuất bản được bảo vệ bởi Cloudflare
Nhiều nhà xuất bản cao cấp sử dụng Cloudflare. Xử lý cả thử thách Turnstile và đầy đủ:
def handle_cloudflare(url, session):
"""Handle Cloudflare-protected publisher pages."""
resp = session.get(url)
if "cf-turnstile" in resp.text:
match = re.search(r'data-sitekey=["\']([^"\']+)', resp.text)
if match:
token = solve_captcha("turnstile", {
"sitekey": match.group(1),
"pageurl": url,
})
return session.post(url, data={
"cf-turnstile-response": token,
})
if resp.status_code == 403 and "cf-browser-verification" in resp.text:
data = solve_captcha("cloudflare_challenge", {
"pageurl": url,
"proxy": "user:pass@proxy:port",
"proxytype": "HTTP",
})
# Parse <staging-session-cookie> and use same proxy
return data
return resp
Câu hỏi thường gặp
Tôi có thể xác minh bao nhiêu trang mỗi giờ?
Với CaptchaAI, bạn có thể xác minh 200-500 trang mỗi giờ tùy thuộc vào tần suất CAPTCHA và thời gian giải quyết.
Điều này có áp dụng được cho việc xác minh quảng cáo video không?
Cách tiếp cận này hoạt động cho quảng cáo hiển thị và quảng cáo gốc. Việc xác minh quảng cáo video thường yêu cầu kết xuất trình duyệt bằng Selenium hoặc Playwright.
Làm cách nào để xử lý các khu vực khác nhau?
Sử dụng proxy từ các khu vực địa lý mục tiêu. CaptchaAI hỗ trợ các tham số proxy để bối cảnh giải quyết phù hợp với nhắm mục tiêu theo địa lý của bạn.
Hướng dẫn liên quan
- Quét các trang web được bảo vệ
- Các phương pháp hay nhất về thiết lập proxy
- Các vấn đề về CAPTCHA của trình duyệt headless