يأتي Cloudflare Turnstile مزودًا بثلاثة أوضاع لعناصر واجهة المستخدم التي تتحكم في كيفية تقديم التحديات: مُدار (يقرر Cloudflare)، غير تفاعلي (إثبات العمل فقط، لا يُظهر واجهة المستخدم مطلقًا)، وغير مرئي (لا توجد حاوية لعناصر واجهة المستخدم، ويعمل بصمت). يحدد الوضع ما يراه المستخدم، والمدة التي يستغرقها التحدي، وما إذا كانت الأداة ستصبح مرئية أم لا. بالنسبة للتشغيل الآلي، تنتج الأوضاع الثلاثة نفس الإخراج - رمز cf-turnstile-response - ولكن اكتشافها وحلها يتطلب فهم الاختلافات.
مقارنة الوضع
| ميزة | تمكنت | غير تفاعلية | غير مرئية |
|---|---|---|---|
| ** القطعة مرئية؟ ** | في بعض الأحيان | أبدًا (الدوار فقط) | أبدا |
| عنصر الحاوية مطلوب؟ | نعم | نعم | نعم (مخفي) |
| ** مطلوب تفاعل المستخدم؟ ** | في بعض الأحيان (مربع الاختيار) | لا | لا |
| تحدي إثبات العمل؟ | نعم (قد تتصاعد) | نعم (دائماً) | نعم (دائماً) |
| مربع الاختيار التفاعلي الاحتياطي؟ | نعم | لا (فشل بدلاً من ذلك) | لا (فشل بدلاً من ذلك) |
| إخراج الرمز | cf-turnstile-response |
cf-turnstile-response |
cf-turnstile-response |
| طريقة CaptchaAI | turnstile |
turnstile |
turnstile |
| ** الموصى بها ل ** | تسجيل الدخول، الاشتراك | أشكال منخفضة الاحتكاك | التحقق من الخلفية |
الوضع المُدار (الافتراضي)
يتيح الوضع المُدار لـ Cloudflare تحديد مستوى التحدي لكل زائر. يمر معظم المستخدمين بشكل غير مرئي. ترى حركة المرور المشبوهة مربع اختيار. قد تواجه حركة المرور المشبوهة للغاية تحديًا أكثر تعقيدًا.
التنفيذ
<!-- Managed mode (default) -->
<div class="cf-turnstile"
data-sitekey="0x4AAAAAAAC3DHQhMMQ_Rxrg"
data-theme="light">
</div>
<script src="https://challenges.cloudflare.com/turnstile/v0/api.js" async defer></script>
ما ترى الأتمتة
يتكيف الوضع المُدار بناءً على إشارات الطالب:
| السمعة | القطعة تجعل كما |
|---|---|
| ثقة عالية | تمريرة غير مرئية (لا توجد واجهة مستخدم مرئية) |
| ثقة متوسطة | أداة مربع الاختيار (انقر للتحقق) |
| ثقة منخفضة | التحدي التفاعلي أو الكتلة |
بالنسبة للأتمتة، يعد الوضع المُدار هو الأكثر شيوعًا والأكثر تغيرًا. قد تكون الأداة مرئية أو لا تكون مرئية وفقًا لإشارات المتصفح.
الكشف في HTML
def is_managed_mode(html):
"""Check if Turnstile is using managed mode (default)."""
# Managed mode is the default — no explicit mode attribute
has_turnstile = "cf-turnstile" in html
has_explicit_mode = 'data-appearance="interaction-only"' in html or \
'data-appearance="always"' in html or \
'appearance: "interaction-only"' in html
return has_turnstile and not has_explicit_mode
الوضع غير التفاعلي
لا يعرض الوضع غير التفاعلي أبدًا مربع اختيار أو عنصرًا تفاعليًا. يتم تشغيل تحدي إثبات العمل في الخلفية ويظهر فقط أداة التحميل الدوارة. إذا لم يكن من الممكن إكمال التحدي بشكل غير تفاعلي، فإنه يفشل بدلاً من تصعيده.
التنفيذ
<!-- Non-interactive mode -->
<div class="cf-turnstile"
data-sitekey="0x4AAAAAAAC3DHQhMMQ_Rxrg"
data-appearance="interaction-only">
</div>
أو عبر JavaScript API:
turnstile.render('#turnstile-container', {
sitekey: '0x4AAAAAAAC3DHQhMMQ_Rxrg',
appearance: 'interaction-only',
callback: function(token) {
document.getElementById('cf-turnstile-response').value = token;
},
});
السلوك
Page loads → Widget initializes
↓
Background proof-of-work runs
↓
Success → Token generated (no visible UI)
OR
Failure → Widget reports error (no fallback to checkbox)
عندما تستخدم المواقع غير التفاعلية
- نماذج التعليق وعناصر واجهة المستخدم للتعليقات
- الاشتراكات في النشرة الإخبارية
- الإجراءات ذات القيمة المنخفضة حيث يجب أن يكون الاحتكاك في حده الأدنى
- نقاط نهاية API مع حماية من جانب المتصفح
وضع غير مرئي
الوضع غير المرئي غير مرئي حقًا، ولا يظهر أي عنصر حاوية في إطار العرض. يتم تشغيل الأداة عند تحميل الصفحة (أو المشغل البرمجي) وتنتج رمزًا مميزًا دون أي إشارة مرئية.
التنفيذ
<!-- Invisible mode — container is hidden -->
<div id="turnstile-invisible"
class="cf-turnstile"
data-sitekey="0x4AAAAAAAC3DHQhMMQ_Rxrg"
data-size="invisible">
</div>
أو بالكامل عبر JavaScript:
// Programmatic invisible Turnstile
turnstile.render('#hidden-container', {
sitekey: '0x4AAAAAAAC3DHQhMMQ_Rxrg',
size: 'invisible',
callback: function(token) {
// Token ready — submit form automatically
submitForm(token);
},
'error-callback': function() {
// Challenge failed
console.error('Invisible Turnstile failed');
},
});
تحدي الكشف
من الصعب اكتشاف Turnstile غير المرئي لأن الحاوية ليس لها أبعاد مرئية:
import re
def detect_invisible_turnstile(html):
"""Detect invisible Turnstile on a page."""
indicators = {
"script_loaded": "challenges.cloudflare.com/turnstile" in html,
"size_invisible": 'data-size="invisible"' in html or
"size: 'invisible'" in html or
'size: "invisible"' in html,
"api_render_call": "turnstile.render" in html,
"response_field": "cf-turnstile-response" in html,
}
if indicators["script_loaded"] and indicators["size_invisible"]:
return {"mode": "invisible", "confidence": "high"}
elif indicators["script_loaded"] and indicators["api_render_call"]:
return {"mode": "invisible_or_programmatic", "confidence": "medium"}
elif indicators["response_field"]:
return {"mode": "turnstile_present", "confidence": "low"}
return {"mode": "none", "confidence": "high"}
استخراج مفتاح الموقع عبر جميع الأوضاع
بغض النظر عن الوضع، فإن مفتاح الموقع مطلوب للحل. استخراجه من أي وضع:
import re
def extract_turnstile_sitekey(html):
"""Extract Turnstile sitekey from page HTML (works for all modes)."""
# Pattern 1: data-sitekey attribute in HTML
match = re.search(r'data-sitekey=["\']([0-9x][A-Za-z0-9_-]+)["\']', html)
if match:
return match.group(1)
# Pattern 2: JavaScript render call
match = re.search(r"sitekey:\s*['\"]([0-9x][A-Za-z0-9_-]+)['\"]", html)
if match:
return match.group(1)
# Pattern 3: Turnstile config object
match = re.search(r"siteKey['\"]?\s*[:=]\s*['\"]([0-9x][A-Za-z0-9_-]+)['\"]", html)
if match:
return match.group(1)
return None
حل جميع الأوضاع الثلاثة باستخدام CaptchaAI
يتم حل جميع أوضاع Turnstile الثلاثة بشكل متطابق مع CaptchaAI. لا يؤثر الوضع على استدعاء API:
بايثون
import requests
import time
API_KEY = "YOUR_API_KEY"
def solve_turnstile(sitekey, page_url):
"""Solve any Turnstile mode — managed, non-interactive, or invisible."""
submit = requests.post("https://ocr.captchaai.com/in.php", data={
"key": API_KEY,
"method": "turnstile",
"sitekey": sitekey,
"pageurl": page_url,
"json": 1,
})
task_id = submit.json()["request"]
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,
"json": 1,
}).json()
if result.get("status") == 1:
return result["request"]
raise TimeoutError("Turnstile solve timed out")
# Use with any mode
token = solve_turnstile("0x4AAAAAAAC3DHQhMMQ_Rxrg", "https://example.com/login")
print(f"Token: {token[:50]}...")
Node.js
const axios = require("axios");
const API_KEY = "YOUR_API_KEY";
async function solveTurnstile(sitekey, pageUrl) {
const submit = await axios.post("https://ocr.captchaai.com/in.php", null, {
params: {
key: API_KEY,
method: "turnstile",
sitekey,
pageurl: pageUrl,
json: 1,
},
});
const taskId = submit.data.request;
for (let i = 0; i < 60; i++) {
await new Promise((r) => setTimeout(r, 5000));
const result = await axios.get("https://ocr.captchaai.com/res.php", {
params: { key: API_KEY, action: "get", id: taskId, json: 1 },
});
if (result.data.status === 1) {
return result.data.request;
}
}
throw new Error("Turnstile solve timed out");
}
// Same function works for all Turnstile modes
solveTurnstile("0x4AAAAAAAC3DHQhMMQ_Rxrg", "https://example.com/login")
.then((token) => console.log("Token:", token.substring(0, 50)));
استكشاف الأخطاء وإصلاحها
| أعراض | السبب | إصلاح |
|---|---|---|
| الرمز صالح لكن النموذج يرفضه | مفتاح الموقع غير صحيح (يختلف عن الأداة المرئية) | تحقق من وجود مفتاح الموقع الذي تم عرضه بواسطة JavaScript |
| القطعة غير موجودة في HTML | تم تحميل الوضع غير المرئي بعد العرض الأولي | انتظر تحميل الصفحة بالكامل، وتحقق من استجابات XHR |
| أدوات متعددة للباب الدوار على الصفحة | مفاتيح مواقع مختلفة لأشكال مختلفة | مطابقة مفتاح الموقع بالنموذج المحدد |
data-size="compact" يخلط بين الكشف |
المضغوط هو متغير الحجم، وليس الوضع | يستخدم الضغط الوضع المُدار بشكل افتراضي |
سمة data-action موجودة |
علامة الإجراء للتحليلات، وليس الوضع | قم بتضمين الإجراء في الحل إذا لزم الأمر للتحقق من الصحة |
| تنتهي صلاحية الرمز المميز قبل الإرسال | تنتهي صلاحية رموز Turnstile خلال 300 ثانية | حل قبل التقديم مباشرة |
الأسئلة المتداولة
هل يؤثر وضع Turnstile على حل CaptchaAI؟
لا، يستخدم CaptchaAI نفس أسلوب turnstile لجميع الأوضاع الثلاثة. يعد مفتاح الموقع وعنوان URL للصفحة المعلمتين الوحيدتين المطلوبتين. لا يغير الوضع تنسيق الرمز المميز أو تدفق التحقق من الصحة.
كيف أعرف الوضع الذي يستخدمه الموقع؟
تحقق من HTML لسمات data-appearance أو data-size. إذا كان data-size="invisible" موجودًا، فهو وضع غير مرئي. إذا كان data-appearance="interaction-only" موجودًا، فهو غير تفاعلي. إذا لم يتم تعيين أي منهما، فهذا هو الوضع المُدار (الافتراضي).
هل يمكن للموقع تبديل الأوضاع ديناميكيًا؟
نعم. تستخدم بعض المواقع الوضع المُدار افتراضيًا وتتحول إلى الوضع غير التفاعلي لصفحات أو شرائح معينة من المستخدمين. عادةً ما يظل مفتاح الموقع كما هو. قم دائمًا بإعادة اكتشاف الوضع أثناء التنقل.
ما هو الفرق في معدل النجاح بين الأوضاع؟
يحقق CaptchaAI معدل نجاح بمعدل نجاح عالٍ في جميع أوضاع Turnstile. يؤثر الوضع فقط على السلوك الذي يواجه المستخدم - التحدي على مستوى واجهة برمجة التطبيقات متطابق.
ملخص
تتحكم أوضاع عناصر واجهة المستخدم الثلاثة في Cloudflare Turnstile - مُدارة وغير تفاعلية وغير مرئية - في تجربة المستخدم ولكنها تنتج نفس رمز cf-turnstile-response. بالنسبة للأتمتة، يتم حل جميع الأوضاع بشكل مماثل باستخدام حل Turnstile من CaptchaAIوبنسبة نجاح عالٍ. يتمثل الاختلاف الرئيسي للمطورين في الاكتشاف: يعرض الوضع المُدار HTML مرئيًا، بينما يتطلب الوضع غير المرئي تحليلًا أعمق للصفحة للعثور على مفتاح الموقع.
مقالات ذات صلة
- Cloudflare Challenge مقابل اكتشاف Turnstile
- مقارنة Geetest وCloudflare Turnstile
- Cloudflare Turnstile 403 بعد إصلاح الرمز المميز