تحدد قواعد validate الخاصة بـ request الخاص بك الآن كيفية تصنيف كل نتيجة. حدد الرمز 403 كمقبول، وستُحتسب استجابة 403 التي تم تسليمها كـ success، وتُفوتر كـ success، وتظهر في خلاصة النشاط (Activity feed) الخاصة بك إلى جانب استجابات 200.
قد يبدو هذا التغيير بسيطاً. لكنه يغير طريقة قياسك لدقة عملية الكشط (scraping) على نطاق واسع.
آلية العمل
يحصل كل request إلى FourA على واحدة من سبع نتائج تحدد الفوترة والتحليلات. نتيجة success فقط هي القابلة للفوترة. وتتوزع بقية النتائج بناءً على الطرف المسؤول عن الفشل:
application_failوapplication_errorعندما يرفض الموقع المستهدف الطلب أو يعيد جسم خطأ (error body)client_errorعندما يكون الـ request الذي أرسلته غير صالح (malformed)service_failوservice_errorوrate_limitعندما يقوم شيء ما من جانبنا بحظر الـ request
قبل هذا التغيير، كان النجاح يعني شيئاً واحداً فقط: HTTP 200. وكانت استجابة 403 تُصنف دائماً كـ application_fail، حتى لو كنت تعلم أن 403 هي الـ response التي تريدها. (تُرجع بعض واجهات برمجة تطبيقات البيانات الرياضية (sports data APIs) الرمز 403 للأسواق المحظورة جغرافياً، وهذه هي الإشارة التي ينتظرها الكود الخاص بك).
الآن، يقرر كتلة validate الخاصة بك ذلك. يقوم الـ request بتشغيل قواعدك أثناء التنفيذ. وإذا استوفت الـ response هذه القواعد، تكون النتيجة success.
curl -X POST "https://eu.api.foura.ai/v1/request" \
-H "Authorization: Bearer YOUR_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"url": "https://example.com/api/feed",
"unblocker": true,
"validate": {
"status": { "accept": [200, 403] },
"data": { "fail": ["captcha", "Access Denied"] }
}
}'
يعامل هذا الرمزين 200 و 403 كرموز حالة (status codes) صالحة. إذا كان الجسم (body) يحتوي على علامة CAPTCHA أو سلسلة نصية تفيد برفض الوصول (access-denied)، يفشل الـ request. وأي شيء آخر يُعتبر success.
قاعدتان يجب تذكرهما:
- بدون
validate، لا يتغير السلوك. الـ requests التي لا تحدد التحقق (validation) لا تزال تُفوتر على HTTP 200 فقط. الأمر اختياري بالنسبة لك. - تعمل
validateفي كلا الاتجاهين. قواعد القبول (accept) تمرر الطلب، وقواعد الفشل (fail) ترفضه. وهي تندمج معاً. لذا يمكنك قبول[200, 403]ومع ذلك يفشل الطلب عندما يحتوي الجسم (body) على محتوى خاطئ.
الأثر
هذا التحول يهم بشكل أساسي الفرق التي ترجع مواقعها المستهدفة responses غير 200 وهي تريدها بالفعل.
أمثلة من الـ requests التي نراها يومياً:
- واجهات برمجة تطبيقات البيانات الرياضية (sports data APIs) التي تُرجع 403 للأسواق المحظورة جغرافياً (لا تزال بيانات مفيدة، ولا يزال من المفيد تسجيلها كـ success)
- نقاط نهاية (endpoints) البحث في التجارة الإلكترونية التي تُرجع 404 عندما يكون المنتج (SKU) غير متوفر في المخزون (إشارة يقرأها الكود الخاص بك، وليست فشلاً)
- واجهات برمجة تطبيقات البث والمحتوى الجزئي (streaming and partial-content APIs) التي تُرجع 206
قبل هذا التغيير، كانت تلك الفرق تقوم بعمليات تتبع خاصة بها فوق سجلات النشاط (Activity logs) لدينا. لم يكن بإمكانهم الوثوق بعمود outcome لأن تعريفهم للنجاح لم يكن يتطابق مع تعريفنا. وكانوا يُفوترون بناءً على رقم لا يهمهم فعلياً.
الآن يعكس هذا العمود الواقع. تبويب النشاط (Activity) في لوحة التحكم (Dashboard) الخاصة بك يعرض ما حددته أنت كـ success، وليس ما خمنّاه نحن. وتتطابق إجماليات الفوترة الخاصة بك مع ما كنت ستحسبه بنفسك (النتائج الأولية: ينطبق التغيير على العمليات المستقبلية فقط، لذا تحتفظ صفوف النشاط القديمة بتصنيفها الأصلي).
الأثر العملي على مهمة الكشط (scraping): خطوات تسوية أقل بين الـ pipeline الخاص بك وفاتورتنا. إذا كنت تقوم بالفعل بإجراء تحقق (validation) على جسم الـ response (response body) بعد حدوثها، يمكنك نقل هذا العقد إلى الـ request نفسه والتوقف عن صيانة مجموعة موازية من قواعد النجاح/الفشل خارج الـ API الخاص بنا. تعريف واحد يحدد ما إذا كان الـ request قد استحق مكانه في مجموعة البيانات الخاصة بك، بدلاً من تعريفين متعارضين.
لكننا حافظنا على شبكة الأمان. إذا لم تقم بتمرير كتلة validate، فلن يتغير شيء. يعود المصنف تلقائياً إلى "200 تعني success" بحيث تعمل الـ requests التي كانت تعمل بالأمس بنفس الطريقة اليوم.
للمستخدمين المتقدمين
تقبل validate ثلاث مجموعات من القواعد التي تعمل بشكل مستقل: status و headers و data. وتأخذ كل منها قوائم accept و fail اختيارية.
curl -X POST "https://eu.api.foura.ai/v1/request" \
-H "Authorization: Bearer YOUR_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"url": "https://example.com/product/9876",
"followRedirects": 5,
"unblocker": true,
"validate": {
"status": { "accept": [200, 304] },
"headers": { "accept": { "content-type": "application/json" } },
"data": { "accept": ["\"price\":"], "fail": ["maintenance", "captcha"] }
}
}'
يتطلب هذا ما يلي:
- أن تكون الحالة (status) هي 200 أو 304
- أن تعلن الـ response عن نوع محتوى JSON
- أن يحتوي الجسم (body) على حقل السعر (price)
- ألا يحتوي الجسم (body) على إشعار صيانة أو فخ CAPTCHA
إذا فشلت أي قاعدة، تكون النتيجة application_fail. وإذا نجح كل شيء، تكون النتيجة success. يعمل المصنف داخل الـ request نفسه، مما يجنبك وقت رحلة الذهاب والإياب (round trip) الذي قد تتطلبه خطوة تحقق منفصلة.
بالدمج مع followRedirects: تتبع ما يصل إلى خمس قفزات (hops)، ثم تحقق من الـ response النهائية. إن عملية التمويه والتحويل (bait-and-switch) من URL نظيف إلى بوابة CAPTCHA ستفشل بشكل نظيف بدلاً من تلويث مجموعة البيانات الخاصة بك.
ونصيحة من واقع تشغيل أدوات الكشط (scrapers) الخاصة بنا: حدد أنماط data.fail بحزم. إن استجابة 200 OK التي تحتوي على CAPTCHA بداخلها هي أكثر أنماط الفشل الصامت شيوعاً على المواقع المحمية. تعامل مع الجسم (body) كمرجع أساسي، وليس رمز الحالة (status code).
للحصول على المخطط الكامل (schema)، تسرد مرجعية request كل حقل من حقول validate وكيفية تركيب كل منها.
الخطوات التالية
نحن نعمل على توفير أساسيات قواعد أكثر ثراءً: مطابقات التعبيرات النمطية (regex matchers) لـ data، ومسنَدات JSON-path الهيكلية، ومطابقة مرنة للـ headers. يبقى المبدأ كما هو. أنت تحدد شكل النجاح، ويلتزم الـ API به من البداية إلى النهاية، بدءاً من الـ request وحتى فاتورتك.
عندما يتعطل الـ scraper الخاص بك، يجب أن يكون ذلك واضحاً وصريحاً. وعندما يعمل وفقاً لقواعد كتبتها بنفسك، فهذا رقم يمكنك الوثوق به حقاً.