ساخت یک وب‌اسکرپر همزمان با Puppeteer، Node.js، Docker و Kubernetes

مقدمه

وب‌اسکرپینگ (Web Scraping) فرآیند استخراج خودکار داده‌ها از وب‌سایت‌ها است. این تکنیک برای جمع‌آوری اطلاعات، مانیتورینگ قیمت‌ها، تحلیل رقبا، استخراج محتوا و بسیاری از کاربردهای دیگر مورد استفاده قرار می‌گیرد.

اما زمانی که حجم داده‌ها افزایش پیدا می‌کند، اجرای اسکرپینگ به‌صورت ترتیبی (Sequential) دیگر کارآمد نیست. در چنین شرایطی استفاده از پردازش همزمان (Concurrent Processing) می‌تواند سرعت جمع‌آوری داده‌ها را به شکل چشمگیری افزایش دهد.

در این آموزش یاد می‌گیرید چگونه با استفاده از:

  • Puppeteer برای کنترل مرورگر Chrome
  • Node.js برای توسعه برنامه
  • Docker برای کانتینرسازی
  • Kubernetes برای مقیاس‌پذیری و مدیریت سرویس‌ها

یک وب‌اسکرپر همزمان و مقیاس‌پذیر بسازید.


وب‌اسکرپینگ همزمان چیست؟

در حالت عادی، اسکرپر هر صفحه را به‌ترتیب پردازش می‌کند:

  1. باز کردن صفحه اول
  2. استخراج اطلاعات
  3. بستن صفحه
  4. رفتن به صفحه بعدی

این روش برای تعداد زیاد صفحات بسیار کند است.

در مقابل، اسکرپینگ همزمان چندین صفحه را به‌صورت موازی پردازش می‌کند و باعث می‌شود:

  • سرعت جمع‌آوری اطلاعات افزایش یابد.
  • استفاده بهتری از منابع سیستم انجام شود.
  • زمان اجرای پروژه کاهش پیدا کند.

پیش‌نیازها

برای دنبال کردن این آموزش به موارد زیر نیاز دارید:

  • Node.js نسخه ۱۴ یا بالاتر
  • npm
  • Docker
  • Kubernetes Cluster
  • kubectl
  • آشنایی اولیه با JavaScript و Node.js

مرحله اول: ایجاد پروژه Node.js

یک پوشه جدید ایجاد کنید:

mkdir concurrent-scraper
cd concurrent-scraper

پروژه را مقداردهی اولیه کنید:

npm init -y

پکیج‌های موردنیاز را نصب کنید:

npm install puppeteer express

مرحله دوم: ساخت اسکرپر با Puppeteer

فایل scraper.js را ایجاد کنید:

const puppeteer = require('puppeteer');

async function scrape(url) {
  const browser = await puppeteer.launch({
    headless: true,
    args: ['--no-sandbox']
  });

  const page = await browser.newPage();

  await page.goto(url, {
    waitUntil: 'networkidle2'
  });

  const title = await page.title();

  await browser.close();

  return {
    url,
    title
  };
}

module.exports = scrape;

این تابع:

  • مرورگر Chrome را اجرا می‌کند.
  • صفحه موردنظر را باز می‌کند.
  • عنوان صفحه را استخراج می‌کند.
  • مرورگر را می‌بندد.

مرحله سوم: اجرای همزمان چند درخواست

فایل index.js را ایجاد کنید:

const scrape = require('./scraper');

const urls = [
  'https://example.com',
  'https://github.com',
  'https://nodejs.org'
];

async function run() {
  const results = await Promise.all(
    urls.map(url => scrape(url))
  );

  console.log(results);
}

run();

در اینجا از Promise.all() استفاده شده است تا تمام صفحات به‌صورت همزمان پردازش شوند.


مزایای Promise.all

استفاده از Promise.all() باعث می‌شود:

  • همه درخواست‌ها به‌طور موازی اجرا شوند.
  • زمان کلی پردازش کاهش پیدا کند.
  • بهره‌وری سیستم افزایش یابد.

مرحله چهارم: ایجاد API برای اسکرپر

فایل server.js را بسازید:

const express = require('express');
const scrape = require('./scraper');

const app = express();

app.use(express.json());

app.post('/scrape', async (req, res) => {
  try {
    const urls = req.body.urls;

    const results = await Promise.all(
      urls.map(url => scrape(url))
    );

    res.json(results);

  } catch (error) {
    res.status(500).json({
      error: error.message
    });
  }
});

app.listen(3000, () => {
  console.log('Server started');
});

اکنون می‌توانید لیستی از URLها را ارسال کنید و نتایج را به‌صورت JSON دریافت نمایید.


مرحله پنجم: ساخت Docker Image

فایل Dockerfile را ایجاد کنید:

FROM node:18-slim

RUN apt-get update && apt-get install -y \
    chromium \
    fonts-liberation

WORKDIR /app

COPY package*.json ./

RUN npm install

COPY . .

ENV PUPPETEER_EXECUTABLE_PATH=/usr/bin/chromium

EXPOSE 3000

CMD ["node", "server.js"]

سپس ایمیج را بسازید:

docker build -t concurrent-scraper .

اجرای کانتینر:

docker run -p 3000:3000 concurrent-scraper

مرحله ششم: آماده‌سازی برای Kubernetes

فایل deployment.yaml را ایجاد کنید:

apiVersion: apps/v1
kind: Deployment
metadata:
  name: scraper
spec:
  replicas: 3
  selector:
    matchLabels:
      app: scraper
  template:
    metadata:
      labels:
        app: scraper
    spec:
      containers:
      - name: scraper
        image: concurrent-scraper:latest
        ports:
        - containerPort: 3000

در اینجا سه نمونه (Replica) از اسکرپر اجرا می‌شود.


مرحله هفتم: ایجاد Service

فایل service.yaml را بسازید:

apiVersion: v1
kind: Service
metadata:
  name: scraper-service
spec:
  selector:
    app: scraper
  ports:
  - port: 80
    targetPort: 3000
  type: LoadBalancer

استقرار در Kubernetes

منابع را اعمال کنید:

kubectl apply -f deployment.yaml
kubectl apply -f service.yaml

بررسی وضعیت:

kubectl get pods

نمایش سرویس:

kubectl get services

مزایای Kubernetes برای Web Scraping

استفاده از Kubernetes مزایای زیادی دارد:

مقیاس‌پذیری خودکار

در صورت افزایش حجم درخواست‌ها می‌توانید تعداد Podها را افزایش دهید:

kubectl scale deployment scraper --replicas=10

تحمل خطا (Fault Tolerance)

اگر یکی از Podها از کار بیفتد، Kubernetes به‌طور خودکار نمونه جدیدی ایجاد می‌کند.

توزیع بار

درخواست‌ها بین Podهای مختلف توزیع می‌شوند و فشار روی یک نمونه کاهش پیدا می‌کند.


نکات مهم برای اسکرپینگ در مقیاس بالا

برای جلوگیری از مسدود شدن توسط وب‌سایت‌ها:

  • بین درخواست‌ها تأخیر ایجاد کنید.
  • از Proxy استفاده کنید.
  • User-Agent را تغییر دهید.
  • محدودیت نرخ درخواست (Rate Limiting) را رعایت کنید.
  • فایل robots.txt سایت‌ها را بررسی کنید.

جمع‌بندی

در این آموزش یاد گرفتید چگونه با استفاده از Puppeteer، Node.js، Docker و Kubernetes یک وب‌اسکرپر همزمان و مقیاس‌پذیر ایجاد کنید. با کمک Promise.all توانستید چندین صفحه را به‌صورت موازی پردازش کنید، برنامه را در Docker کانتینرسازی نمایید و در نهایت با Kubernetes آن را برای اجرای در مقیاس بالا آماده کنید.

این معماری برای پروژه‌های جمع‌آوری داده، مانیتورینگ وب‌سایت‌ها، تحلیل رقبا و استخراج اطلاعات در حجم بالا بسیار کاربردی است.

از همراهی شما با پارمین کلود متشکریم.

Click to rate this post!
[Total: 0 Average: 0]

نظرات کاربران

دیدگاهی بنویسید

نشانی ایمیل شما منتشر نخواهد شد. بخش‌های موردنیاز علامت‌گذاری شده‌اند *