44 lines
1.4 KiB
Python
44 lines
1.4 KiB
Python
from typing import Optional
|
|
|
|
import httpx
|
|
|
|
from ..runtime import get_runtime_settings
|
|
|
|
|
|
async def verify_captcha(token: Optional[str], remote_ip: Optional[str] = None) -> bool:
|
|
runtime = get_runtime_settings()
|
|
provider = (runtime.captcha_provider or "none").strip().lower()
|
|
if provider in {"", "none", "off", "disabled"}:
|
|
return True
|
|
if not token:
|
|
return False
|
|
|
|
if provider == "hcaptcha":
|
|
secret = runtime.hcaptcha_secret_key
|
|
url = "https://hcaptcha.com/siteverify"
|
|
payload = {"secret": secret, "response": token}
|
|
elif provider == "recaptcha":
|
|
secret = runtime.recaptcha_secret_key
|
|
url = "https://www.google.com/recaptcha/api/siteverify"
|
|
payload = {"secret": secret, "response": token}
|
|
elif provider == "turnstile":
|
|
secret = runtime.turnstile_secret_key
|
|
url = "https://challenges.cloudflare.com/turnstile/v0/siteverify"
|
|
payload = {"secret": secret, "response": token}
|
|
else:
|
|
return False
|
|
|
|
if not secret:
|
|
return False
|
|
if remote_ip:
|
|
payload["remoteip"] = remote_ip
|
|
|
|
try:
|
|
async with httpx.AsyncClient(timeout=10.0) as client:
|
|
response = await client.post(url, data=payload)
|
|
response.raise_for_status()
|
|
data = response.json()
|
|
return bool(data.get("success"))
|
|
except httpx.HTTPError:
|
|
return False
|