CAPSOLVER
Blog
Cách giải Captcha trong Crawlee với tích hợp CapSolver

Cách giải Captcha trong Crawlee với tích hợp CapSolver

Logo of CapSolver

Anh Tuan

Data Science Expert

24-Dec-2025

TL;DR: Các crawler của Crawlee thường gặp rào cản CAPTCHA. Việc tích hợp CapSolver cho phép bạn giải các CAPTCHA như reCAPTCHA, Turnstile và nhiều loại khác, giúp quy trình quét dữ liệu ổn định và tự động hóa.

Khi xây dựng các crawler với Crawlee, việc gặp CAPTCHA là gần như không thể tránh khỏi—đặc biệt là trên các trang web hiện đại có bảo vệ bot mạnh mẽ. Ngay cả các crawler Playwright hoặc HTTP được cấu hình tốt cũng có thể bị chặn khi xuất hiện các bài kiểm tra reCAPTCHA, Turnstile hoặc tương tự.

Hướng dẫn này tập trung vào cách tiếp cận thực tế: sử dụng CapSolver để xử lý các bài kiểm tra CAPTCHA trực tiếp trong quy trình Crawlee. Thay vì phải chiến đấu với các dấu vân tay trình duyệt liên tục, bạn sẽ thấy cách phát hiện các loại CAPTCHA phổ biến, giải chúng một cách tự động hóa, và duy trì hoạt động ổn định của crawler trong các tình huống quét dữ liệu thực tế.

Crawlee là gì?

Crawlee là thư viện quét web và tự động hóa trình duyệt cho Node.js, được thiết kế để xây dựng các crawler đáng tin cậy, tạo cảm giác như người dùng thật và tránh bị phát hiện bởi các hệ thống bảo vệ bot hiện đại. Được xây dựng bằng TypeScript, nó cung cấp cả giao diện cấp cao đơn giản và tùy chỉnh cấp thấp.

Tính năng chính của Crawlee

  • Giao diện thống nhất: API duy nhất cho cả quét HTTP và trình duyệt không cần giao diện
  • Tự động hóa chống bot: Tạo vân tay trình duyệt tự động, sao chép vân tay TLS và hành vi giống người dùng thật
  • Quản lý hàng đợi thông minh: Hàng đợi URL bền vững với các tùy chọn quét theo chiều rộng và chiều sâu
  • Tự động mở rộng: Mở rộng tài nguyên tự động dựa trên tải hệ thống
  • Luân chuyển proxy: Luân chuyển proxy và quản lý phiên bản tích hợp
  • Hỗ trợ trình duyệt đa dạng: Hoạt động với Playwright và Puppeteer trên Chrome, Firefox và WebKit

Các loại crawler

Crawlee cung cấp nhiều loại crawler cho các trường hợp sử dụng khác nhau:

Loại Crawler Mô tả
CheerioCrawler Crawler HTTP siêu nhanh sử dụng Cheerio để phân tích HTML
PlaywrightCrawler Tự động hóa trình duyệt đầy đủ với Playwright cho các trang web nặng JavaScript
PuppeteerCrawler Tự động hóa trình duyệt đầy đủ với Puppeteer cho việc render JavaScript
JSDOMCrawler Crawler HTTP với JSDOM để thực thi JavaScript mà không cần trình duyệt

CapSolver là gì?

CapSolver là dịch vụ giải CAPTCHA hàng đầu cung cấp các giải pháp dựa trên trí tuệ nhân tạo để vượt qua các bài kiểm tra CAPTCHA khác nhau. Với khả năng hỗ trợ nhiều loại CAPTCHA và thời gian phản hồi nhanh như chớp, CapSolver tích hợp liền mạch vào các quy trình tự động hóa.

Các loại CAPTCHA được hỗ trợ

  • reCAPTCHA v2 (Hình ảnh & Không hiển thị)
  • reCAPTCHA v3
  • Cloudflare Turnstile
  • AWS WAF
  • Và nhiều loại khác...

Tại sao nên tích hợp CapSolver với Crawlee?

Khi xây dựng các crawler Crawlee tương tác với các trang web được bảo vệ, các bài kiểm tra CAPTCHA có thể làm dừng toàn bộ quy trình quét dữ liệu của bạn. Dưới đây là lý do tại sao tích hợp này quan trọng:

  1. Quá trình quét không bị gián đoạn: Crawler tiếp tục trích xuất dữ liệu mà không cần can thiệp thủ công
  2. Thao tác có thể mở rộng: Xử lý nhiều bài kiểm tra CAPTCHA trong các phiên quét song song
  3. Hiệu quả về chi phí: Chỉ trả phí cho các CAPTCHA được giải thành công
  4. Tỷ lệ thành công cao: Độ chính xác hàng đầu trong ngành cho tất cả các loại CAPTCHA được hỗ trợ

Cài đặt

Đầu tiên, cài đặt các gói cần thiết:

bash Copy
npm install crawlee playwright axios

Hoặc với yarn:

bash Copy
yarn add crawlee playwright axios

Tạo tiện ích CapSolver cho Crawlee

Dưới đây là lớp tiện ích CapSolver có thể tái sử dụng có thể được sử dụng trong các dự án Crawlee của bạn:

Dịch vụ CapSolver cơ bản

typescript Copy
import axios from 'axios';

const CAPSOLVER_API_KEY = 'YOUR_CAPSOLVER_API_KEY';

interface TaskResult {
    status: string;
    solution?: {
        gRecaptchaResponse?: string;
        token?: string;
    };
    errorDescription?: string;
}

class CapSolverService {
    private apiKey: string;
    private baseUrl = 'https://api.capsolver.com';

    constructor(apiKey: string = CAPSOLVER_API_KEY) {
        this.apiKey = apiKey;
    }

    async createTask(taskData: object): Promise<string> {
        const response = await axios.post(`${this.baseUrl}/createTask`, {
            clientKey: this.apiKey,
            task: taskData
        });

        if (response.data.errorId !== 0) {
            throw new Error(`Lỗi CapSolver: ${response.data.errorDescription}`);
        }

        return response.data.taskId;
    }

    async getTaskResult(taskId: string, maxAttempts = 60): Promise<TaskResult> {
        for (let i = 0; i < maxAttempts; i++) {
            await this.sleep(2000);

            const response = await axios.post(`${this.baseUrl}/getTaskResult`, {
                clientKey: this.apiKey,
                taskId
            });

            if (response.data.status === 'ready') {
                return response.data;
            }

            if (response.data.status === 'failed') {
                throw new Error(`Bài toán thất bại: ${response.data.errorDescription}`);
            }
        }

        throw new Error('Hết thời gian chờ đợi giải CAPTCHA');
    }

    private sleep(ms: number): Promise<void> {
        return new Promise(resolve => setTimeout(resolve, ms));
    }

    async solveReCaptchaV2(websiteUrl: string, websiteKey: string): Promise<string> {
        const taskId = await this.createTask({
            type: 'ReCaptchaV2TaskProxyLess',
            websiteURL: websiteUrl,
            websiteKey
        });

        const result = await this.getTaskResult(taskId);
        return result.solution?.gRecaptchaResponse || '';
    }

    async solveReCaptchaV3(
        websiteUrl: string,
        websiteKey: string,
        pageAction = 'submit'
    ): Promise<string> {
        const taskId = await this.createTask({
            type: 'ReCaptchaV3TaskProxyLess',
            websiteURL: websiteUrl,
            websiteKey,
            pageAction
        });

        const result = await this.getTaskResult(taskId);
        return result.solution?.gRecaptchaResponse || '';
    }

    async solveTurnstile(websiteUrl: string, websiteKey: string): Promise<string> {
        const taskId = await this.createTask({
            type: 'AntiTurnstileTaskProxyLess',
            websiteURL: websiteUrl,
            websiteKey
        });

        const result = await this.getTaskResult(taskId);
        return result.solution?.token || '';
    }
}

export const capSolver = new CapSolverService();

Giải các loại CAPTCHA khác nhau với Crawlee

reCAPTCHA v2 với PlaywrightCrawler

typescript Copy
import { PlaywrightCrawler, Dataset } from 'crawlee';
import { capSolver } from './capsolver-service';

const RECAPTCHA_SITE_KEY = 'YOUR_SITE_KEY';

const crawler = new PlaywrightCrawler({
    async requestHandler({ page, request, log }) {
        log.info(`Đang xử lý ${request.url}`);

        // Kiểm tra xem trang có reCAPTCHA không
        const hasRecaptcha = await page.$('.g-recaptcha');

        if (hasRecaptcha) {
            log.info('Phát hiện reCAPTCHA, đang giải...');

            // Lấy khóa trang từ trang
            const siteKey = await page.$eval(
                '.g-recaptcha',
                (el) => el.getAttribute('data-sitekey')
            ) || RECAPTCHA_SITE_KEY;

            // Giải CAPTCHA
            const token = await capSolver.solveReCaptchaV2(request.url, siteKey);

            // Chèn token - textarea bị ẩn, sử dụng JavaScript
            await page.$eval('#g-recaptcha-response', (el: HTMLTextAreaElement, token: string) => {
                el.style.display = 'block';
                el.value = token;
            }, token);

            // Gửi biểu mẫu
            await page.click('button[type="submit"]');
            await page.waitForLoadState('networkidle');

            log.info('reCAPTCHA được giải thành công!');
        }

        // Trích xuất dữ liệu sau khi CAPTCHA được giải
        const title = await page.title();
        const content = await page.locator('body').innerText();

        await Dataset.pushData({
            title,
            content: content.slice(0, 1000)
        });
    },

    maxRequestsPerCrawl: 50,
    headless: true
});

await crawler.run(['https://example.com/protected-page']);

reCAPTCHA v3 với PlaywrightCrawler

typescript Copy
import { PlaywrightCrawler, Dataset } from 'crawlee';
import { capSolver } from './capsolver-service';

const crawler = new PlaywrightCrawler({
    async requestHandler({ page, request, log }) {
        log.info(`Đang xử lý ${request.url}`);

        // reCAPTCHA v3 là ẩn, phát hiện bằng script
        const recaptchaScript = await page.$('script[src*="recaptcha/api.js?render="]');

        if (recaptchaScript) {
            log.info('Phát hiện reCAPTCHA v3, đang giải...');

            // Trích xuất khóa trang từ src script
            const scriptSrc = await recaptchaScript.getAttribute('src') || '';
            const siteKeyMatch = scriptSrc.match(/render=([^&]+)/);
            const siteKey = siteKeyMatch ? siteKeyMatch[1] : '';

            if (siteKey) {
                // Giải reCAPTCHA v3
                const token = await capSolver.solveReCaptchaV3(
                    request.url,
                    siteKey,
                    'submit'
                );

                // Chèn token vào trường ẩn bằng JavaScript
                await page.$eval('input[name="g-recaptcha-response"]', (el: HTMLInputElement, token: string) => {
                    el.value = token;
                }, token);

                log.info('Token reCAPTCHA v3 đã được chèn!');
            }
        }

        // Tiếp tục gửi biểu mẫu hoặc trích xuất dữ liệu
        const title = await page.title();
        const url = page.url();

        await Dataset.pushData({ title, url });
    }
});

await crawler.run(['https://example.com/v3-protected']);

Cloudflare Turnstile với PlaywrightCrawler

typescript Copy
import { PlaywrightCrawler, Dataset } from 'crawlee';
import { capSolver } from './capsolver-service';

const crawler = new PlaywrightCrawler({
    async requestHandler({ page, request, log }) {
        log.info(`Đang xử lý ${request.url}`);

        // Kiểm tra xem có widget Turnstile không
        const hasTurnstile = await page.$('.cf-turnstile');

        if (hasTurnstile) {
            log.info('Phát hiện Cloudflare Turnstile, đang giải...');

            // Lấy khóa trang
            const siteKey = await page.$eval(
                '.cf-turnstile',
                (el) => el.getAttribute('data-sitekey')
            );

            if (siteKey) {
                // Giải Turnstile
                const token = await capSolver.solveTurnstile(request.url, siteKey);

                // Chèn token bằng JavaScript (trường ẩn)
                await page.$eval('input[name="cf-turnstile-response"]', (el: HTMLInputElement, token: string) => {
                    el.value = token;
                }, token);

                // Gửi biểu mẫu
                await page.click('button[type="submit"]');
                await page.waitForLoadState('networkidle');

                log.info('Turnstile được giải thành công!');
            }
        }

        // Trích xuất dữ liệu
        const title = await page.title();
        const content = await page.locator('body').innerText();

        await Dataset.pushData({
            title,
            content: content.slice(0, 500)
        });
    }
});

await crawler.run(['https://example.com/turnstile-protected']);

Tích hợp nâng cao: Phát hiện tự động loại CAPTCHA

Dưới đây là một crawler nâng cao tự động phát hiện và giải các loại CAPTCHA khác nhau:

typescript Copy
import { PlaywrightCrawler, Dataset } from 'crawlee';
import { capSolver } from './capsolver-service';

interface CaptchaInfo {
    type: 'recaptcha-v2' | 'recaptcha-v3' | 'turnstile' | 'none';
    siteKey: string | null;
}

async function detectCaptcha(page: any): Promise<CaptchaInfo> {
    // Kiểm tra reCAPTCHA v2
    const recaptchaV2 = await page.$('.g-recaptcha');
    if (recaptchaV2) {
        const siteKey = await page.$eval('.g-recaptcha', (el: Element) =>
            el.getAttribute('data-sitekey')
        );
        return { type: 'recaptcha-v2', siteKey };
    }

    // Kiểm tra reCAPTCHA v3
    const recaptchaV3Script = await page.$('script[src*="recaptcha/api.js?render="]');
    if (recaptchaV3Script) {
        const scriptSrc = await recaptchaV3Script.getAttribute('src') || '';
        const match = scriptSrc.match(/render=([^&]+)/);
        const siteKey = match ? match[1] : null;
        return { type: 'recaptcha-v3', siteKey };
    }

    // Kiểm tra Turnstile
    const turnstile = await page.$('.cf-turnstile');
    if (turnstile) {
        const siteKey = await page.$eval('.cf-turnstile', (el: Element) =>
            el.getAttribute('data-sitekey')
        );
        return { type: 'turnstile', siteKey };
    }

    return { type: 'none', siteKey: null };
}

async function solveCaptcha(
    page: any,
    url: string,
    captchaInfo: CaptchaInfo
): Promise<void> {
    if (!captchaInfo.siteKey || captchaInfo.type === 'none') return;

    let token: string;

    switch (captchaInfo.type) {
        case 'recaptcha-v2':
            token = await capSolver.solveReCaptchaV2(url, captchaInfo.siteKey);
            // Trường textarea ẩn - sử dụng JavaScript để đặt giá trị
            await page.$eval('#g-recaptcha-response', (el: HTMLTextAreaElement, t: string) => {
                el.style.display = 'block';
                el.value = t;
            }, token);
            break;

        case 'recaptcha-v3':
            token = await capSolver.solveReCaptchaV3(url, captchaInfo.siteKey);
            // Trường ẩn - sử dụng JavaScript để đặt giá trị
            await page.$eval('input[name="g-recaptcha-response"]', (el: HTMLInputElement, t: string) => {
                el.value = t;
            }, token);
            break;

        case 'turnstile':
            token = await capSolver.solveTurnstile(url, captchaInfo.siteKey);
            // Trường ẩn - sử dụng JavaScript để đặt giá trị
            await page.$eval('input[name="cf-turnstile-response"]', (el: HTMLInputElement, t: string) => {
                el.value = t;
            }, token);
            break;
    }
}

const crawler = new PlaywrightCrawler({
    async requestHandler({ page, request, log, enqueueLinks }) {
        log.info(`Đang xử lý ${request.url}`);

        // Tự động phát hiện CAPTCHA
        const captchaInfo = await detectCaptcha(page);

        if (captchaInfo.type !== 'none') {
            log.info(`Phát hiện ${captchaInfo.type}, đang giải...`);
            await solveCaptcha(page, request.url, captchaInfo);

            // Gửi biểu mẫu nếu tồn tại
            const submitBtn = await page.$('button[type="submit"], input[type="submit"]');
            if (submitBtn) {
await submitBtn.click();
                await page.waitForLoadState('networkidle');
            }

            log.info('CAPTCHA đã được giải thành công!');
        }

        // Trích xuất dữ liệu
        const title = await page.title();
        const url = page.url();
        const text = await page.locator('body').innerText();

        await Dataset.pushData({
            title,
            url,
            text: text.slice(0, 1000)
        });

        // Tiếp tục quét
        await enqueueLinks();
    },

    maxRequestsPerCrawl: 100
});

await crawler.run(['https://example.com']);

Cách Gửi Token CAPTCHA

Mỗi loại CAPTCHA yêu cầu phương pháp gửi khác nhau trong ngữ cảnh trình duyệt:

reCAPTCHA v2/v3 - Chèn Token

typescript Copy
async function submitRecaptchaToken(page: any, token: string): Promise<void> {
    // Ô nhập phản hồi bị ẩn - sử dụng JavaScript để đặt giá trị
    await page.$eval('#g-recaptcha-response', (el: HTMLTextAreaElement, token: string) => {
        el.style.display = 'block';
        el.value = token;
    }, token);

    // Đặt giá trị cho trường ẩn nếu tồn tại (thường gặp trong các triển khai tùy chỉnh)
    try {
        await page.$eval('input[name="g-recaptcha-response"]', (el: HTMLInputElement, token: string) => {
            el.value = token;
        }, token);
    } catch (e) {
        // Trường có thể không tồn tại
    }

    // Gửi biểu mẫu
    await page.click('form button[type="submit"]');
}

Turnstile - Chèn Token

typescript Copy
async function submitTurnstileToken(page: any, token: string): Promise<void> {
    // Đặt token vào trường ẩn bằng JavaScript
    await page.$eval('input[name="cf-turnstile-response"]', (el: HTMLInputElement, token: string) => {
        el.value = token;
    }, token);

    // Gửi biểu mẫu
    await page.click('form button[type="submit"]');
}

Sử Dụng Mở Rộng CapSolver Với Crawlee

Đối với các tình huống bạn muốn giải CAPTCHA tự động, bạn có thể tải mở rộng CapSolver:

typescript Copy
import { PlaywrightCrawler } from 'crawlee';
import path from 'path';

const crawler = new PlaywrightCrawler({
    launchContext: {
        launchOptions: {
            // Tải mở rộng CapSolver
            args: [
                `--disable-extensions-except=${path.resolve('./capsolver-extension')}`,
                `--load-extension=${path.resolve('./capsolver-extension')}`
            ],
            headless: false // Mở rộng yêu cầu chế độ có giao diện
        }
    },

    async requestHandler({ page, request, log }) {
        log.info(`Đang xử lý ${request.url}`);

        // Mở rộng sẽ tự động giải CAPTCHA
        // Chờ CAPTCHA được giải
        await page.waitForTimeout(5000);

        // Tiếp tục quét
        const title = await page.title();
        const content = await page.locator('body').innerText();

        console.log({ title, content });
    }
});

await crawler.run(['https://example.com/captcha-page']);

Các Nguyên Tắc Tốt

1. Xử Lý Lỗi Với Tái Thử

typescript Copy
async function solveWithRetry(
    solverFn: () => Promise<string>,
    maxRetries = 3
): Promise<string> {
    for (let attempt = 0; attempt < maxRetries; attempt++) {
        try {
            return await solverFn();
        } catch (error) {
            if (attempt === maxRetries - 1) throw error;

            const delay = Math.pow(2, attempt) * 1000; // Chờ tăng dần
            await new Promise(resolve => setTimeout(resolve, delay));
        }
    }
    throw new Error('Đã vượt quá số lần thử');
}

// Sử dụng
const token = await solveWithRetry(() =>
    capSolver.solveReCaptchaV2(url, siteKey)
);

2. Quản Lý Số Dư

typescript Copy
import axios from 'axios';

async function checkBalance(apiKey: string): Promise<number> {
    const response = await axios.post('https://api.capsolver.com/getBalance', {
        clientKey: apiKey
    });

    return response.data.balance || 0;
}

// Kiểm tra trước khi bắt đầu crawler
const balance = await checkBalance(CAPSOLVER_API_KEY);
if (balance < 1) {
    console.warn('Số dư CapSolver thấp! Vui lòng nạp thêm.');
}

3. Quản Lý Phiên Cho Nhiều Trang

typescript Copy
import { PlaywrightCrawler, Dataset } from 'crawlee';
import { capSolver } from './capsolver-service';

// Lưu trữ token đã giải cho cùng một miền và khóa
const tokenCache = new Map<string, { token: string; timestamp: number }>();
const TOKEN_TTL = 90000; // 90 giây

async function getCachedToken(
    url: string,
    siteKey: string,
    solverFn: () => Promise<string>
): Promise<string> {
    const cacheKey = `${new URL(url).hostname}:${siteKey}`;
    const cached = tokenCache.get(cacheKey);

    if (cached && Date.now() - cached.timestamp < TOKEN_TTL) {
        return cached.token;
    }

    const token = await solverFn();
    tokenCache.set(cacheKey, { token, timestamp: Date.now() });
    return token;
}

4. Tích Hợp Proxy

typescript Copy
import { PlaywrightCrawler, ProxyConfiguration } from 'crawlee';

const proxyConfiguration = new ProxyConfiguration({
    proxyUrls: [
        'http://user:[email protected]:8080',
        'http://user:[email protected]:8080',
        'http://user:[email protected]:8080'
    ]
});

const crawler = new PlaywrightCrawler({
    proxyConfiguration,

    async requestHandler({ page, request, log, proxyInfo }) {
        log.info(`Đang sử dụng proxy: ${proxyInfo?.url}`);

        // Logic giải CAPTCHA và quét dữ liệu ở đây
    }
});

Ví Dụ Hoàn Chỉnh: Máy Quét Sản Phẩm Thương Mại Điện Tử Với Xử Lý CAPTCHA

typescript Copy
import { PlaywrightCrawler, Dataset, ProxyConfiguration } from 'crawlee';
import { capSolver } from './capsolver-service';

interface Product {
    name: string;
    price: string;
    url: string;
    image: string;
}

const proxyConfiguration = new ProxyConfiguration({
    proxyUrls: ['http://user:[email protected]:8080']
});

const crawler = new PlaywrightCrawler({
    proxyConfiguration,
    maxRequestsPerCrawl: 200,
    maxConcurrency: 5,

    async requestHandler({ page, request, log, enqueueLinks }) {
        log.info(`Đang quét: ${request.url}`);

        // Kiểm tra CAPTCHA
        const hasRecaptcha = await page.$('.g-recaptcha');
        const hasTurnstile = await page.$('.cf-turnstile');

        if (hasRecaptcha) {
            const siteKey = await page.$eval(
                '.g-recaptcha',
                (el) => el.getAttribute('data-sitekey')
            );

            if (siteKey) {
                log.info('Đang giải reCAPTCHA...');
                const token = await capSolver.solveReCaptchaV2(request.url, siteKey);

                // Chèn token bằng JavaScript (phần tử ẩn)
                await page.$eval('#g-recaptcha-response', (el: HTMLTextAreaElement, t: string) => {
                    el.style.display = 'block';
                    el.value = t;
                }, token);
                await page.click('button[type="submit"]');
                await page.waitForLoadState('networkidle');
            }
        }

        if (hasTurnstile) {
            const siteKey = await page.$eval(
                '.cf-turnstile',
                (el) => el.getAttribute('data-sitekey')
            );

            if (siteKey) {
                log.info('Đang giải Turnstile...');
                const token = await capSolver.solveTurnstile(request.url, siteKey);

                // Chèn token bằng JavaScript (phần tử ẩn)
                await page.$eval('input[name="cf-turnstile-response"]', (el: HTMLInputElement, t: string) => {
                    el.value = t;
                }, token);
                await page.click('button[type="submit"]');
                await page.waitForLoadState('networkidle');
            }
        }

        // Trích xuất dữ liệu sản phẩm bằng Playwright locators
        const productCards = await page.locator('.product-card').all();
        const products: Product[] = [];

        for (const card of productCards) {
            products.push({
                name: await card.locator('.product-name').innerText().catch(() => ''),
                price: await card.locator('.product-price').innerText().catch(() => ''),
                url: await card.locator('a').getAttribute('href') || '',
                image: await card.locator('img').getAttribute('src') || ''
            });
        }

        if (products.length > 0) {
            await Dataset.pushData(products);
            log.info(`Đã trích xuất ${products.length} sản phẩm`);
        }

        // Gửi các liên kết phân trang và danh mục
        await enqueueLinks({
            globs: ['**/products/**', '**/page/**', '**/category/**']
        });
    },

    failedRequestHandler({ request, log }) {
        log.error(`Yêu cầu thất bại: ${request.url}`);
    }
});

// Bắt đầu quét
await crawler.run(['https://example-store.com/products']);

// Xuất kết quả
const dataset = await Dataset.open();
await dataset.exportToCSV('products.csv');

console.log('Quét hoàn tất! Kết quả được lưu vào products.csv');

Kết Luận

Việc tích hợp CapSolver với Crawlee mở ra tiềm năng đầy đủ của việc quét web cho các nhà phát triển Node.js. Bằng cách kết hợp cơ sở hạ tầng quét mạnh mẽ của Crawlee với khả năng giải CAPTCHA hàng đầu của CapSolver, bạn có thể xây dựng các công cụ quét đáng tin cậy có thể xử lý các cơ chế bảo vệ bot khó khăn nhất.

Dù bạn đang xây dựng các pipeline trích xuất dữ liệu, hệ thống theo dõi giá cả hay các công cụ tổng hợp nội dung, sự kết hợp giữa Crawlee và CapSolver cung cấp độ tin cậy và khả năng mở rộng cần thiết cho các môi trường sản xuất.


Sẵn sàng bắt đầu chưa? Đăng ký CapSolver và sử dụng mã khuyến mãi CRAWLEE để nhận thêm 6% khuyến mãi cho mỗi lần nạp tiền!


Câu Hỏi Thường Gặp

Crawlee là gì?

Crawlee là thư viện quét web và tự động hóa trình duyệt cho Node.js được thiết kế để xây dựng các công cụ quét đáng tin cậy. Nó hỗ trợ cả quét dựa trên HTTP (với Cheerio/JSDOM) và tự động hóa trình duyệt đầy đủ (với Playwright/Puppeteer), bao gồm các tính năng tích hợp như xoay proxy, quản lý phiên và chống bot.

CapSolver tích hợp với Crawlee như thế nào?

CapSolver tích hợp với Crawlee thông qua một lớp dịch vụ bao bọc API của CapSolver. Trong hàm xử lý yêu cầu của crawler, bạn có thể phát hiện các thách thức CAPTCHA và sử dụng CapSolver để giải chúng, sau đó chèn các token trở lại trang.

CapSolver có thể giải được những loại CAPTCHA nào?

CapSolver hỗ trợ nhiều loại CAPTCHA bao gồm reCAPTCHA v2, reCAPTCHA v3, Cloudflare Turnstile, AWS WAF, GeeTest và nhiều loại khác.

Chi phí của CapSolver là bao nhiêu?

CapSolver cung cấp giá cả cạnh tranh dựa trên loại và khối lượng CAPTCHA được giải. Truy cập capsolver.com để xem thông tin giá cả hiện tại. Sử dụng mã CRAWLEE để nhận 6% khuyến mãi cho lần nạp đầu tiên.

Tôi có thể sử dụng CapSolver với các khung công tác Node.js khác không?

Có! CapSolver cung cấp API REST có thể tích hợp với bất kỳ khung công tác Node.js nào, bao gồm Express, Puppeteer standalone, Selenium và nhiều hơn nữa.

Crawlee có miễn phí không?

Có, Crawlee là mã nguồn mở và được phát hành dưới giấy phép Apache 2.0. Khung công tác này miễn phí để sử dụng, dù bạn có thể phải chịu chi phí cho các dịch vụ proxy và dịch vụ giải CAPTCHA như CapSolver.

Làm thế nào để tìm khóa site CAPTCHA?

Khóa site thường được tìm thấy trong mã nguồn trang. Tìm kiếm:

  • reCAPTCHA: thuộc tính data-sitekey trên phần tử .g-recaptcha
  • Turnstile: thuộc tính data-sitekey trên phần tử .cf-turnstile
  • Hoặc kiểm tra các yêu cầu mạng để tìm khóa trong các cuộc gọi API

Loại crawler nào của Crawlee nên sử dụng?

  • CheerioCrawler: Tốt nhất cho quét HTML nhanh và đơn giản mà không cần JavaScript
  • PlaywrightCrawler: Tốt nhất cho các trang nặng JavaScript và giải CAPTCHA (được khuyến khích cho tích hợp CapSolver)
  • PuppeteerCrawler: Lựa chọn thay thế cho Playwright với khả năng tương tự
  • JSDOMCrawler: Tốt hơn trung bình với hỗ trợ JavaScript cơ bản

Tuyên bố Tuân thủ: Thông tin được cung cấp trên blog này chỉ mang tính chất tham khảo. CapSolver cam kết tuân thủ tất cả các luật và quy định hiện hành. Việc sử dụng mạng lưới CapSolver cho các hoạt động bất hợp pháp, gian lận hoặc lạm dụng là hoàn toàn bị cấm và sẽ bị điều tra. Các giải pháp giải captcha của chúng tôi nâng cao trải nghiệm người dùng trong khi đảm bảo tuân thủ 100% trong việc giúp giải quyết các khó khăn về captcha trong quá trình thu thập dữ liệu công khai. Chúng tôi khuyến khích việc sử dụng dịch vụ của chúng tôi một cách có trách nhiệm. Để biết thêm thông tin, vui lòng truy cập Điều khoản Dịch vụ và Chính sách Quyền riêng tư.

Thêm

Dịch vụ Công ty Proxy Tốt nhất - Capsolver
Những Dịch Vụ Công Ty Proxy Tốt Nhất Bạn Nên Biết

Bài viết này cung cấp cái nhìn chi tiết về năm nhà cung cấp dịch vụ proxy nổi bật: ProxyScrape.com, Proxies.gg, Asocks.com, MetaProxies, RushProxy và Ake.net. Mỗi phần của bài viết phân tích chi tiết các đặc điểm nổi bật, tính năng, giá cả và lợi ích của từng dịch vụ, nhấn mạnh những ưu điểm và chuyên môn của chúng. Từ proxy nhà ở và proxy di động đến các tùy chọn trung tâm dữ liệu, bài viết cung cấp tổng quan toàn diện về thị trường proxy đa dạng. Dù bạn là doanh nghiệp tìm kiếm công cụ phân tích thị trường, cá nhân cần quyền riêng tư trực tuyến hay nhà phát triển cần giải pháp quét web, bài viết này là hướng dẫn giá trị để hiểu và chọn dịch vụ proxy phù hợp với nhu cầu của bạn.

web scraping
Logo of CapSolver

Aloísio Vítor

24-Dec-2025

Giải Captcha trong Crawlee bằng CapSolver
Cách giải Captcha trong Crawlee với tích hợp CapSolver

Một hướng dẫn thực tế để giải quyết reCAPTCHA và Turnstile trong Crawlee bằng CapSolver cho việc quét dữ liệu Node.js ổn định.

web scraping
Logo of CapSolver

Anh Tuan

24-Dec-2025

Công cụ trích xuất dữ liệu từ web - Giải thích
Công cụ khảo sát web – Giải thích

Khám phá các công cụ quét web hàng đầu dành cho trích xuất dữ liệu hiệu quả từ các trang web, phù hợp với cả người lập trình và người không lập trình trong hướng dẫn toàn diện của chúng tôi

web scraping
Logo of CapSolver

Sora Fujimoto

23-Dec-2025

Giải Captcha trong CrewAI bằng CapSolver
Làm thế nào để giải quyết Captcha trong CrewAI với tích hợp CapSolver

Tích hợp CrewAI với CapSolver cho phép xử lý CAPTCHA một cách liền mạch cho reCAPTCHA, Cloudflare Turnstile, AWS WAF và nhiều hơn nữa, cải thiện các nhiệm vụ web tự động.

web scraping
Logo of CapSolver

Anh Tuan

23-Dec-2025

MCP
Master MCP: Tăng cường khả năng AI vào năm 2026

Giao thức Bối cảnh Mô hình (MCP) là tương lai của tích hợp AI. Học cách MCP chuẩn hóa giao tiếp giữa AI và công cụ, thúc đẩy tự động hóa doanh nghiệp và tăng cường trí thông minh AI vào năm 2026.

web scraping
Logo of CapSolver

Adélia Cruz

22-Dec-2025

Top 7 Nhà cung cấp dữ liệu B2B vào năm 2026
Top 7 Nhà cung cấp dữ liệu B2B năm 2026: Hướng dẫn so sánh thực tế

So sánh 7 nhà cung cấp dữ liệu B2B hàng đầu năm 2026 dựa trên độ chính xác, tuân thủ và chuyên môn. Tìm nhà cung cấp dữ liệu tốt nhất cho nhu cầu bán hàng và tiếp thị của bạn.

web scraping
Logo of CapSolver

Anh Tuan

18-Dec-2025