القاعدة العملية مختصرة: إن كنت تحل أقل من 500 اختبار CAPTCHA يوميًا فالمعالجة المتسلسلة تكفيك تمامًا، وحين يتجاوز حجمك ذلك يصبح الحل المتوازي هو الفارق بين دقائق طويلة وثوانٍ معدودة. المقايضة الحقيقية ليست في السعر — فتكلفة الـ API لكل حل واحدة في الحالتين — بل في مقدار التعقيد الذي تقبل تحمّله مقابل الإنتاجية التي تكسبها. يقارن هذا الدليل النهجين عمليًا مع CaptchaAI بأمثلة قابلة للتشغيل، ويمنحك معيارًا واضحًا لاختيار الاستراتيجية المناسبة لحجمك وبنيتك التحتية.
أيّهما يناسبك: نظرة سريعة
الجدول التالي يلخّص الفروق التي تهمّ فعليًا عند اتخاذ القرار. ابدأ منه ثم انزل إلى التفاصيل والأمثلة.
| العامل | الحل المتسلسل | الحل المتوازي |
|---|---|---|
| الإنتاجية (reCAPTCHA v2، وسيط 15 ثانية) | ~240 حل/ساعة | ~10,000+ حل/ساعة |
| تعقيد الكود | بسيط | متوسط إلى مرتفع |
| معالجة الأخطاء | مباشرة | تتطلب عزل الأخطاء المتزامنة |
| استهلاك الذاكرة | ضئيل (~30 ميجابايت) | يتصاعد مع التزامن (~100–500 ميجابايت) |
| تكلفة الـ API لكل حل | ثابتة | ثابتة |
| صعوبة التصحيح | سهلة | أصعب (ظروف السباق والتوقيت) |
| ترتيب النتائج | محفوظ تلقائيًا | يتطلب تتبعًا صريحًا |
| الأنسب لـ | أقل من 500 حل/يوم | أكثر من 500 حل/يوم |
الخلاصة المبكرة في سطرين:
- التسلسل يشتري لك البساطة ووضوح تتبّع كل خطوة.
- التوازي يشتري لك الإنتاجية على حساب تعقيد إضافي في الكود والتشخيص.
الحل المتسلسل: البساطة قبل كل شيء
كيف يعمل
اختبار CAPTCHA واحد في كل مرة، وفق تسلسل ثابت:
- إرسال الطلب.
- الانتظار حتى يجهز الحل.
- الاستطلاع الدوري للنتيجة.
- الحصول على الرمز ثم الانتقال إلى المهمة التالية.
لا تزامن ولا حالة مشتركة هنا، ما يجعل تتبّع كل خطوة أمرًا يسيرًا.
# sequential_solver.py
import os
import time
import requests
API_KEY = os.environ.get("CAPTCHAAI_KEY", "YOUR_API_KEY")
def solve_sequential(tasks):
"""Solve CAPTCHAs one by one."""
results = []
session = requests.Session()
for task in tasks:
# Submit
resp = session.get("https://ocr.captchaai.com/in.php", params={
"key": API_KEY,
"method": "userrecaptcha",
"googlekey": task["sitekey"],
"pageurl": task["pageurl"],
"json": "1",
})
result = resp.json()
if result.get("status") != 1:
results.append({"error": result.get("request")})
continue
task_id = result["request"]
time.sleep(15)
# Poll
token = None
for _ in range(25):
poll = session.get("https://ocr.captchaai.com/res.php", params={
"key": API_KEY, "action": "get",
"id": task_id, "json": "1",
})
poll_result = poll.json()
if poll_result.get("status") == 1:
token = poll_result["request"]
break
if poll_result.get("request") != "CAPCHA_NOT_READY":
break
time.sleep(5)
results.append({"token": token} if token else {"error": "timeout"})
return results
# 10 tasks sequentially → ~150 seconds total
tasks = [{"sitekey": "SITEKEY", "pageurl": "https://example.com"}] * 10
start = time.time()
results = solve_sequential(tasks)
print(f"Completed in {time.time() - start:.0f}s")
كما يوضّح التعليق في نهاية الكود، عشر مهام متسلسلة تستغرق نحو 150 ثانية، لأن كل حل ينتظر انتهاء سابقه.
متى يكون التسلسل هو الخيار الصحيح
- سير عمل ذو صفحة واحدة — تعبئة نموذج واحد في كل مرة دون حاجة لتوازٍ.
- مرحلة التطوير والتصحيح — تدفق تنفيذ واضح يسهّل تتبّع كل طلب واستجابة.
- الأحجام المنخفضة — أقل من 500 حل/يوم لا يبرّر تكلفة التعقيد المتوازي.
- المهام المرتبطة بالترتيب — حين يجب استخدام كل نتيجة قبل الانتقال إلى التالية.
الحل المتوازي: أقصى إنتاجية
كيف يعمل
أرسل مجموعة اختبارات CAPTCHA دفعة واحدة، واستطلع نتائجها في الوقت نفسه بدل انتظار كل حل على حدة. المفتاح هنا هو التحكم في مستوى التزامن عبر Semaphore كي لا تتجاوز حدود خطتك.
# parallel_solver.py
import os
import asyncio
import aiohttp
API_KEY = os.environ.get("CAPTCHAAI_KEY", "YOUR_API_KEY")
async def solve_one(session, sitekey, pageurl, semaphore):
"""Solve a single CAPTCHA within concurrency limits."""
async with semaphore:
# Submit
async with session.get("https://ocr.captchaai.com/in.php", params={
"key": API_KEY, "method": "userrecaptcha",
"googlekey": sitekey, "pageurl": pageurl, "json": "1",
}) as resp:
result = await resp.json(content_type=None)
if result.get("status") != 1:
return {"error": result.get("request")}
task_id = result["request"]
await asyncio.sleep(15)
# Poll
for _ in range(25):
async with session.get("https://ocr.captchaai.com/res.php", params={
"key": API_KEY, "action": "get",
"id": task_id, "json": "1",
}) as resp:
poll_result = await resp.json(content_type=None)
if poll_result.get("status") == 1:
return {"token": poll_result["request"]}
if poll_result.get("request") != "CAPCHA_NOT_READY":
return {"error": poll_result.get("request")}
await asyncio.sleep(5)
return {"error": "timeout"}
async def solve_parallel(tasks, max_concurrent=50):
"""Solve CAPTCHAs in parallel with concurrency control."""
semaphore = asyncio.Semaphore(max_concurrent)
connector = aiohttp.TCPConnector(limit=max_concurrent)
async with aiohttp.ClientSession(connector=connector) as session:
coros = [
solve_one(session, t["sitekey"], t["pageurl"], semaphore)
for t in tasks
]
return await asyncio.gather(*coros)
# 10 tasks in parallel → ~20 seconds total
import time
tasks = [{"sitekey": "SITEKEY", "pageurl": "https://example.com"}] * 10
start = time.time()
results = asyncio.run(solve_parallel(tasks))
print(f"Completed in {time.time() - start:.0f}s")
النتيجة: العشر مهام نفسها تنتهي في نحو 20 ثانية بدل 150، لأن الانتظار يحدث للجميع في الوقت ذاته لا بالتتابع.
المثال نفسه بلغة JavaScript
إن كانت أدواتك في Node.js فالمنطق واحد؛ استبدل asyncio.gather بـ Promise.all واضبط عدد الاتصالات المتزامنة عبر maxSockets.
// parallel_solver.js
const axios = require('axios');
const https = require('https');
const API_KEY = process.env.CAPTCHAAI_KEY || 'YOUR_API_KEY';
const agent = new https.Agent({ keepAlive: true, maxSockets: 50 });
const api = axios.create({ baseURL: 'https://ocr.captchaai.com', httpsAgent: agent });
async function solveOne(sitekey, pageurl) {
const submit = await api.get('/in.php', {
params: { key: API_KEY, method: 'userrecaptcha', googlekey: sitekey, pageurl, json: '1' },
});
if (submit.data.status !== 1) return { error: submit.data.request };
await new Promise(r => setTimeout(r, 15000));
for (let i = 0; i < 25; i++) {
const poll = await api.get('/res.php', {
params: { key: API_KEY, action: 'get', id: submit.data.request, json: '1' },
});
if (poll.data.status === 1) return { token: poll.data.request };
if (poll.data.request !== 'CAPCHA_NOT_READY') return { error: poll.data.request };
await new Promise(r => setTimeout(r, 5000));
}
return { error: 'timeout' };
}
(async () => {
const tasks = Array.from({ length: 10 }, () => ({
sitekey: 'SITEKEY', pageurl: 'https://example.com',
}));
const start = Date.now();
const results = await Promise.all(tasks.map(t => solveOne(t.sitekey, t.pageurl)));
console.log(`Completed in ${((Date.now() - start) / 1000).toFixed(0)}s`);
console.log(`Solved: ${results.filter(r => r.token).length}/${tasks.length}`);
agent.destroy();
})();
كيف تتوسّع الإنتاجية مع مستوى التزامن
كلما رفعت عدد الحلول المتزامنة ارتفعت الإنتاجية، لكن مع زيادة في استهلاك الذاكرة وصعوبة الإدارة. الجدول التالي يوضّح هذا التصاعد استنادًا إلى reCAPTCHA v2 بوسيط حل 15 ثانية:
| الحلول المتزامنة | الإنتاجية المقدّرة/ساعة | الذاكرة (Python) | التعقيد |
|---|---|---|---|
| 1 (متسلسل) | 240 | 30 ميجابايت | منخفض |
| 10 | 2,400 | 50 ميجابايت | منخفض |
| 25 | 6,000 | 80 ميجابايت | متوسط |
| 50 | 10,000+ | 120 ميجابايت | متوسط |
| 100 | 18,000+ | 200 ميجابايت | مرتفع |
الأرقام تقديرية وتعتمد على reCAPTCHA v2 بوسيط حل يبلغ 15 ثانية؛ قد تختلف بحسب بيئة التشغيل والحجم والتوقيت.
هنا تدخل خطة CaptchaAI مباشرة في المعادلة. فالتسعير قائم على عدد الـ Threads المتزامنة لا على عدد الحلول، وكل خطة تشمل حلولًا غير محدودة لكل Thread خلال الشهر. عمليًا يعني ذلك أن أقصى تزامن مفيد لديك محكوم بعدد Threads خطتك:
- خطة ADVANCE — $90 شهريًا و50 Thread: حتى 50 حلًا متزامنًا دون أي رسوم إضافية لكل حل.
- خطة PREMIUM — $170 شهريًا و100 Thread: حتى مئة مسار متزامن حين يكبر حجمك.
اضبط max_concurrent ليطابق عدد Threads خطتك بالضبط: قيمة أعلى تصطدم بحدّ الخدمة، وقيمة أقل تترك سعة مدفوعة دون استخدام.
مثال عملي: منصة حجوزات خلال موسم الذروة
تخيّل فريق أتمتة في منصة حجوزات إلكترونية بالخليج يشغّل فحوصات جودة (QA) موثوقة على آلاف الصفحات قبل إطلاق عرض موسمي. القرار عنده يتبدّل بحسب اليوم:
- خارج الذروة: المسار المتسلسل يكفيه؛ بضع مئات من الفحوصات اليومية تمرّ بهدوء وتُسجَّل بترتيب واضح.
- يوم الإطلاق: يقفز الحجم إلى عشرات الآلاف خلال ساعات قليلة، فيتحوّل الفريق إلى
solve_parallelبحدّ تزامن 50 على خطة ADVANCE.
النتيجة: نافذة الاختبار تنكمش من ساعات إلى دقائق، وتظل تكلفة الـ API لكل حل كما هي لأن الفوترة على الـ Threads لا على عدد الحلول. القاعدة الحاكمة نفسها: التسلسل لليوم العادي، والتوازي لموجة الذروة.
النهج الهجين: الأفضل من العالمين
في كثير من خطوط الأتمتة لا تحتاج إلى توازٍ كامل. اجعل سير العمل متسلسلًا حيث يهمّ الترتيب، واحجز التوازي لخطوة حل CAPTCHA وحدها — وهي الخطوة البطيئة فعلًا:
# Process 10 URLs sequentially, but solve their CAPTCHAs in a parallel batch
urls = get_next_batch() # 10 URLs
captcha_params = [extract_sitekey(url) for url in urls] # Sequential extraction
tokens = asyncio.run(solve_parallel(captcha_params, max_concurrent=10)) # Parallel solving
for url, result in zip(urls, tokens):
submit_form(url, result.get("token")) # Sequential submission
بهذا تكسب سرعة التوازي في العنق الحقيقي للأداء، وتحتفظ ببساطة التسلسل ووضوح الترتيب في بقية الخطوات.
استكشاف الأخطاء وإصلاحها
| المشكلة | السبب المحتمل | الحل |
|---|---|---|
| الحل المتوازي أبطأ من المتوقع | قيمة max_concurrent مقيّدة أكثر من اللازم |
ارفع حدّ التزامن تدريجيًا حتى يبلغ عدد Threads خطتك |
| فشل عشوائي في الوضع المتوازي | تلف في الحالة المشتركة بين المهام | اعزل الحالة داخل كل coroutine أو promise على حدة |
| النتائج تصل بترتيب مختلف | الاعتماد على توقيت الاكتمال بدل الفهرسة | اعتمد على asyncio.gather الذي يحفظ الترتيب أو استخدم فهرسة صريحة |
ظهور الخطأ ERROR_NO_SLOT_AVAILABLE |
عدد الطلبات المتزامنة تجاوز الـ Threads المتاحة | خفّض التزامن ليطابق خطتك أو أضف فاصلًا بسيطًا بين الطلبات |
الأسئلة الشائعة
ما الحجم اليومي الذي يبرّر الانتقال من المتسلسل إلى المتوازي؟
القاعدة العملية هي حاجز 500 حل/يوم تقريبًا. تحته يظل المسار المتسلسل أبسط وأسهل في التصحيح دون أن تشعر بالبطء؛ فوقه يبدأ الانتظار المتسلسل بالتراكم إلى دقائق طويلة، وعندها يوفّر التوازي وقتًا حقيقيًا يستحق تعقيده الإضافي.
كيف يحدّد عدد الـ Threads في خطتي أقصى تزامن ممكن؟
أقصى تزامن مفيد يساوي عدد الـ Threads في خطتك، لأن كل Thread يعالج اختبارًا واحدًا في اللحظة. مع خطة ADVANCE ($90 شهريًا، 50 Thread) اضبط max_concurrent=50؛ فتجاوز هذا الحدّ يؤدي إلى الخطأ ERROR_NO_SLOT_AVAILABLE بدل زيادة السرعة.
هل تزيد المعالجة المتوازية من فاتورتي في CaptchaAI؟
لا. الفوترة قائمة على عدد الـ Threads المتزامنة مع حلول غير محدودة لكل Thread، لا على عدد الطلبات. لذلك تكلفة الـ API لكل حل واحدة سواء عالجت بالتسلسل أو بالتوازي؛ التوازي فقط يجعلك تبلغ الإجمالي نفسه أسرع.
هل يخفض التوازي معدل نجاح الحل؟
معدل الحل يعتمد على نوع اختبار CAPTCHA وجودة معلماتك، لا على مستوى التزامن بحد ذاته. تشغيل خمسين حلًا في آنٍ واحد لا يقلّل دقة أي حل مفرد ما دمت تبقى ضمن حدود Threads خطتك وتضبط معالجة الأخطاء لكل مهمة على حدة.
الخطوات التالية
- البدء السريع مع CaptchaAI: حلّ أول كابتشا في 5 دقائق
- حلّ reCAPTCHA v2 عبر الـ API خطوة بخطوة
- حل Cloudflare Turnstile عبر واجهة الـ API
- حل GeeTest v3 باستخدام الـ API