كيفية استخدام Scrapy مع تطبيق Django

هناك بضعة مقالات حول كيفية دمج Scrapy في تطبيق Django (أو العكس؟). لكن معظمهم لا يغطي مثالًا كاملاً يشتمل على إطلاق العناكب من وجهات نظر جانغو. نظرًا لأن هذا تطبيق ويب ، يجب أن يكون هذا هو هدفنا الرئيسي.

ماذا نحتاج؟

قبل أن نبدأ ، من الأفضل تحديد ما نريد وكيف نريد ذلك. تحقق من هذا المخطط:

إنه يوضح كيفية عمل التطبيق لدينا:

  • يرسل العميل طلبًا بعنوان URL للزحف إليه. (1)
  • يقوم Django بتشغيل برنامج Scrapy لتشغيل عنكبوت للزحف إلى عنوان URL هذا. (2)
  • ترجع Django ردًا لإخبار العميل بأن عملية الزحف بدأت للتو. (3)
  • يكمل Scrapy الزحف ويحفظ البيانات المستخرجة في قاعدة بيانات. (4)
  • جلب Django تلك البيانات من قاعدة البيانات وإعادتها إلى العميل. (5)

تبدو رائعة وبسيطة حتى الآن.

ملاحظة على ذلك البيان الخامس

جلب Django تلك البيانات من قاعدة البيانات وإعادتها إلى العميل. (5)

لا يعرف Django ولا العميل متى يكمل Scrapy الزحف. هناك طريقة رد اتصال تسمى pipeline_closed ، لكنها تنتمي إلى مشروع Scrapy. لا يمكننا إرجاع استجابة من خطوط أنابيب Scrapy. نحن نستخدم هذه الطريقة فقط لحفظ البيانات المستخرجة في قاعدة البيانات.

حسنًا في نهاية المطاف ، في مكان ما ، علينا أن نقول للعميل:

مهلا! اكتمل الزحف وأرسل لك بيانات تم الزحف إليها هنا.

هناك طريقتان ممكنتان لذلك (يرجى التعليق إذا اكتشفت المزيد):

يمكننا إما استخدام مآخذ الويب لإبلاغ العميل عند اكتمال الزحف.

أو،

يمكننا بدء إرسال الطلبات كل ثانيتين (أكثر أو أقل؟) من العميل للتحقق من حالة الزحف بعد أن نحصل على استجابة "بدء الزحف".

يبدو حل Web Socket أكثر استقرارًا وقوة. لكنه يتطلب خدمة ثانية تعمل بشكل منفصل ويعني المزيد من التكوين. سوف أتخطى هذا الخيار في الوقت الحالي. لكنني سأختار مآخذ الويب لتطبيقات مستوى الإنتاج الخاصة بي.

دعنا نكتب بعض الرموز

لقد حان الوقت للقيام بعمل حقيقي. لنبدأ بإعداد بيئتنا.

تثبيت التبعيات

أنشئ بيئة افتراضية وقم بتنشيطها:

python3.5 $ venv venv
المصدر venv / بن / تفعيل

ثم تثبيت التبعيات المطلوبة مع:

$ pip تثبيت django scrapy scrapyd python-scrapyd-api

Scrapyd هي خدمة خفية لتشغيل العناكب Scrapy. يمكنك اكتشاف تفاصيلها من هنا.

python-scrapyd-api عبارة عن غلاف يسمح لنا بالتحدث عن scrapyd من برنامج Python الخاص بنا.

ملاحظة: سوف أستخدم Python 3.5 لهذا المشروع.

إنشاء مشروع جانغو

إنشاء مشروع Django مع تطبيق اسمه الرئيسي:

django-admin startproject iCrawler
cd $ iCrawler && python manager.py startapp الرئيسي

نحتاج أيضًا إلى نموذج لحفظ بياناتنا المحشورة. لنبقيه بسيطًا:

أضف التطبيق الرئيسي إلى INSTALLED_APPS في settings.py وكخطوة أخيرة ، الهجرات:

$ python manager.py makemigrations
ترحيل $ python manager.py

دعنا نضيف طريقة عرض وعنوان URL إلى تطبيقنا الرئيسي:

حاولت توثيق الكود قدر استطاعتي.

لكن الحيلة الرئيسية هي ، unique_id. عادةً ، نحفظ كائنًا في قاعدة البيانات ، ثم نحصل على هويته. في حالتنا ، نقوم بتحديد unique_id الخاص به قبل إنشائه. بمجرد اكتمال الزحف ويسأل العميل عن البيانات التي تم الزحف إليها ؛ يمكننا إنشاء استعلام بهذه النتائج الفريدة وإحضارها.

وعنوان URL لهذا العرض:

إنشاء مشروع Scrapy

من الأفضل أن ننشئ مشروع Scrapy ضمن (أو بجانب) مشروع Django الخاص بنا. هذا يجعل من السهل ربطها معا. فلنقم بإنشائه ضمن مجلد مشروع Django:

$ قرص iCrawler
$ scrapy startproject scrapy_app

نحتاج الآن إلى إنشاء أول عنكبوت من داخل مجلد scrapy_app:

$ cd scrapy_app
genspider $ scrapy -t الزحف إلى icrawler https://google.com

أنا اسم العنكبوت كما icrawler. يمكنك تسميته كأي شيء. انظر -t الزحف جزء. نقوم بتحديد قالب أساسي للعنكبوت الخاص بنا. يمكنك رؤية جميع القوالب المتاحة مع:

gscpider scrapy -l
القوالب المتاحة:
الأساسية
زحف
csvfeed
xmlfeed

الآن يجب أن يكون لدينا بنية مجلد مثل هذا:

ربط Scrapy بجانغو

من أجل الوصول إلى نماذج Django من Scrapy ، نحتاج إلى توصيلها معًا. انتقل إلى ملف settings.py تحت scrapy_app / scrapy_app / ثم ضع:

هذا هو. الآن لنبدأ scrapyd للتأكد من تثبيت كل شيء وتهيئته بشكل صحيح. داخل المدى scrapy_app / المجلد:

scrapyd $

سيبدأ هذا scrapyd ويولد بعض المخرجات. يحتوي Scrapyd أيضًا على وحدة تحكم ويب بسيطة للغاية. لا نحتاج إليه في الإنتاج ولكن يمكننا استخدامه لمشاهدة الوظائف النشطة أثناء التطوير. بمجرد بدء تشغيل scrapyd ، انتقل إلى http://127.0.0.1:6800 ومعرفة ما إذا كان يعمل.

تكوين مشروع Scrapy الخاص بنا

نظرًا لأن هذا المنشور لا يتعلق بأساسيات scrapy ، فسأتخطى الجزء المتعلق بتعديل العناكب. يمكنك إنشاء العنكبوت الخاص بك مع الوثائق الرسمية. سأضع مثال العنكبوت هنا ، على الرغم من:

أعلاه هو ملف icrawler.py من scrapy_app / scrapy_app / العناكب. الانتباه إلى طريقة __init__. انه مهم. إذا كنا نريد أن نجعل طريقة أو خاصية ديناميكية ، فنحن بحاجة إلى تعريفها ضمن طريقة __init__ ، حتى نتمكن من تمرير الوسائط من Django واستخدامها هنا.

نحتاج أيضًا إلى إنشاء "عنصر خط أنابيب" لمشروعنا scrapy. خط الأنابيب عبارة عن فصل لاتخاذ الإجراءات على العناصر المحشورة. من الوثائق:

الاستخدامات النموذجية لخطوط أنابيب البند هي:
  • تطهير بيانات HTML
  • التحقق من صحة البيانات المغطاة (التحقق من احتواء العناصر على حقول معينة)
  • التحقق من التكرارات (وإسقاطها)
  • تخزين العنصر كشط في قاعدة بيانات

ياي! تخزين العنصر كشط في قاعدة بيانات. الآن لنقم بإنشاء واحد. في الواقع ، يوجد بالفعل ملف باسم pipelines.py داخل مجلد scrapy_project. وكذلك يحتوي هذا الملف على خط أنابيب فارغ ولكن جاهز. نحتاج فقط إلى تعديله قليلاً:

وكخطوة أخيرة ، نحتاج إلى تمكين (uncomment) خط الأنابيب هذا في ملف scrapy settings.py:

# تكوين خطوط الأنابيب البند
# راجع http://scrapy.readthedocs.org/en/latest/topics/item-pipeline.html
ITEM_PIPELINES = {
    'scrapy_app.pipelines.ScrapyAppPipeline': 300 ،
}
لا تنس إعادة تشغيل scraypd إذا كان يعمل.

هذا المشروع scrapy أساسا ،

  • يزحف إلى موقع ويب (يأتي من عرض Django)
  • استخراج جميع عناوين المواقع من الموقع
  • وضعها في قائمة
  • احفظ القائمة في قاعدة البيانات عبر نماذج Django.

وهذا كل شيء بالنسبة للجزء الخلفي. كلا من Django و Scrapy متكاملان ويجب أن يعملا بشكل جيد.

ملاحظات على الجزء الأمامي

حسنا ، هذا الجزء هو شخصي جدا. لدينا الكثير من الخيارات. شخصيا ، لقد بنيت الواجهة الأمامية مع React. الجزء الوحيد الذي هو غير شخصي هو استخدام setInterval. نعم ، دعونا نتذكر خياراتنا: مآخذ الويب وإرسال الطلبات إلى الخادم كل X ثانية.

لتوضيح المنطق الأساسي ، هذا إصدار مبسط من مكون التفاعل الخاص بي:

يمكنك اكتشاف التفاصيل عن طريق التعليقات التي أضفتها. انها بسيطة جدا في الواقع.

أوه ، هذا كل شيء. استغرق وقتا أطول مما كنت أتوقع. يرجى ترك تعليق على أي نوع من ردود الفعل.

مشاريع عينة

يمكنك العثور أدناه على بعض أمثلة التطبيقات المستندة إلى هذه المقالة. إذا كان لديك واحدة ، يرجى ذكرها كتعليق. سأستمر في تحديث هذا القسم.

هذا تطبيق قالب جميل من Adrian Castellanos Zaragoza:

-

هذا من 심명훈 ويشمل أيضًا جزء الواجهة الأمامية مع Javascript عادي. تحقق من هذا!

-