Web-Crawling ist schon lange kein Scraping-Problem mehr, bevor es überhaupt zum Parsing-Problem wird. Der schwierige Teil ist nicht das Herunterladen von HTML oder das Extrahieren von Daten. Schwierig ist es, Millionen von Abrufen über Tausende von Domains zu koordinieren, ohne Arbeit zu verlieren, dieselbe Seite doppelt zu crawlen oder die eigene Zeit mit der Pflege von Proxy-Pools und Browser-Infrastruktur zu verbringen, statt die eigentliche Anwendung zu bauen.
An diesem Punkt ändert sich die Architektur. Ein Produktions-Crawler braucht Queues, Worker, Retries, Proxy-Rotation, JavaScript-Rendering, Anti-Bot-Handling und eine dauerhafte Crawl-Frontier, die sich kontinuierlich erweitern kann, ohne dieselben URLs erneut zu besuchen. Kurz gesagt: Sie lösen ein Problem verteilter Systeme.
Der bessere Ansatz besteht darin, die Crawl-Orchestrierung von der Crawl-Ausführung zu trennen. Ihre Anwendung entscheidet, was gecrawlt wird, wie tief gecrawlt wird und was extrahiert werden soll. Die Crawling-Infrastruktur übernimmt Queueing, Parallelität, Retries, Rendering und Netzwerkzuverlässigkeit, sodass sich Ihre Engine auf die Geschäftslogik statt auf Infrastruktur konzentriert.
In diesem Artikel bauen wir eine verteilte Crawling-Engine in Node.js, die genau diesem Design folgt. Die Engine besitzt Crawl-Richtlinie, URL-Deduplizierung, HTML-Parsing, Ergebnisspeicherung und rekursive Frontier-Erweiterung, während Crawlbase über den Crawlbase Enterprise Crawler und die Crawlbase Crawling API die verteilte Ausführungsschicht bereitstellt. Der Enterprise Crawler fungiert als verwaltete Queue mit Worker-Flotte, die Crawl-Ergebnisse asynchron an einen Webhook liefert, während die Crawling API einen Inline-Abrufpfad für latenzkritische Anfragen bietet. Das Ergebnis ist ein Crawler, der mit der Infrastruktur von Crawlbase skaliert und dabei klein genug bleibt, um ihn in wenigen hundert Zeilen Code zu verstehen.
Jede hier gezeigte Implementierung stammt aus dem begleitenden GitHub-Repository. Klonen Sie es, folgen Sie parallel zum Artikel jeder Implementierungsstufe, und am Ende haben Sie ein produktionsreifes Fundament, das Sie mit eigener Extraktionslogik, eigenem Storage-Backend und eigenen Crawl-Richtlinien erweitern können.
Einen verteilten Crawler entwerfen
Jeder verteilte Crawler löst kontinuierlich vier Probleme:
- Die Crawl-Frontier verwalten: entscheiden, was als Nächstes gecrawlt wird.
- Crawls ausführen: Seiten zuverlässig und in großem Maßstab abrufen.
- Ergebnisse verarbeiten: nützliche Daten extrahieren und speichern.
- Den Crawl erweitern: neu entdeckte Links in zukünftige Crawl-Jobs verwandeln.
Diese Aufgaben sind eng miteinander verbunden. Jeder abgeschlossene Crawl erzeugt sowohl Daten als auch neue URLs. Diese URLs durchlaufen die Crawl-Richtlinie, werden Teil der Frontier und werden irgendwann selbst abgerufen, wodurch eine kontinuierliche Feedback-Schleife entsteht.
Crawl-Frontier
Die Frontier ist das Gedächtnis des Crawlers für ausstehende Arbeit. Jede entdeckte URL wird normalisiert, gegen die Crawl-Richtlinie geprüft, dedupliziert und für das Crawling eingeplant. Ohne verwaltete Frontier besuchen rekursive Crawls schnell dieselben Seiten erneut oder verlassen ihren vorgesehenen Geltungsbereich.
Crawl-Ausführung
Seiten in großem Maßstab abzurufen ist in erster Linie ein Infrastrukturproblem. Es erfordert Worker-Koordination, Retries, Proxy-Rotation, Browser-Rendering und Anti-Bot-Handling, bevor Ihr Parser das HTML überhaupt zu sehen bekommt. Diese Infrastruktur zu bauen und zu betreiben ist oft komplexer als der Crawler selbst.
Ergebnisverarbeitung
Abgeschlossene Crawls müssen in eine unabhängige Verarbeitungspipeline fließen, in der Seiten geparst, strukturierte Daten extrahiert und Ergebnisse persistiert werden. Den Abruf von der Verarbeitung getrennt zu halten macht beide Systeme leichter wartbar und weiterentwickelbar.
Rekursive Erweiterung
Jede verarbeitete Seite erzeugt neue Links. Nachdem sie Tiefen-, Domain- und Deduplizierungsprüfungen bestanden haben, werden diese Links zu neuen Crawl-Jobs und gelangen zurück in die Frontier. Diese rekursive Feedback-Schleife läuft weiter, bis keine Seiten im Geltungsbereich mehr zu besuchen sind.
Die Engine, die wir bauen, besitzt Frontier, Crawl-Richtlinie, Parsing, Storage und rekursive Erweiterung. Crawlbase stellt die verteilte Queue, die Worker-Flotte, Retries, Browser-Rendering, Proxy-Rotation und Anti-Bot-Infrastruktur bereit. Diese Trennung hält die Engine auf Anwendungslogik statt auf Crawling-Infrastruktur fokussiert.
Was wir bauen
Ein kleiner Express-Service und eine Handvoll Skripte, die zusammen einen selbsterhaltenden Crawler bilden:
- Ein einmaliges Setup-Skript erstellt eine benannte Crawler-Queue, die an Ihren Webhook gebunden ist.
- Ein Seed-Skript schiebt Start-URLs in die Queue.
- Crawlbase crawlt jede URL und sendet das Ergebnis per POST an Ihren Webhook.
- Der Webhook parst die Seite, speichert einen Datensatz, entdeckt Links und schiebt die noch nicht gesehenen Links im Geltungsbereich zurück in die Queue.
Das Ergebnis ist ein Crawler, der mit der Parallelität von Crawlbase statt mit der Ihres Servers skaliert und den Sie in wenigen hundert Zeilen Code nachvollziehen können.
Architekturüberblick
Der Ablauf ist eine Schleife. Das Seed-Skript befüllt die Engine, die URLs in den Enterprise Crawler schiebt. Der Crawler ist der verteilte Teil: Er hält die Queue, führt die Crawls mit der konfigurierten Parallelität über das Proxy-Netzwerk von Crawlbase aus und übernimmt Retries und Anti-Bot-Auflösung gegenüber den Ziel-Websites. Sobald ein Crawl abgeschlossen ist, sendet Crawlbase die Seite per POST an den Webhook der Engine zurück. Der Parser der Engine erzeugt einen Datensatz für den Store und eine Liste ausgehender Links, die über Deduplizierungs- und Tiefenprüfungen in die nächste Runde von Pushes zurückfließen.
Crawlbase besitzt Abruf, Parallelität, Retries und Proxy-/Anti-Bot-Infrastruktur. Die Engine besitzt die Crawl-Richtlinie (was im Geltungsbereich liegt, wie tief gecrawlt wird) und entscheidet, was mit den Daten geschieht. Das Hero-Diagramm oben zeigt auch die gepunktete Kante: die Crawling API, synchron genutzt für einzelne On-Demand-Seitenabrufe, wenn Sie ein Ergebnis inline statt über die Queue benötigen.
Das Projekt vorbereiten
Nachdem die Architektur steht, bringen wir das Projekt lokal zum Laufen. Das begleitende Repository enthält die vollständige Implementierung, die in diesem Artikel verwendet wird. Wir arbeiten im Projekt final/ und verweisen beim Aufbau jeder Komponente auf die inkrementellen Checkpoints unter steps/.
Sie benötigen:
-
Node.js 18 oder neuer (das Setup-Skript nutzt das eingebaute
fetch). - Ein Crawlbase-Konto, um Ihre Request-Tokens zu erhalten.
- Einen öffentlich erreichbaren Webhook-Endpunkt. Für die lokale Entwicklung exponieren Sie Ihren Express-Server über Cloudflare Tunnel (
cloudflared) oder ngrok und richtenCALLBACK_URLaufhttps://<your-public-host>/webhook.
Klonen Sie das Repository und installieren Sie das Projekt aus dem Verzeichnis final/:
git clone https://github.com/ScraperHub/building-a-distributed-crawling-engine.git cd building-a-distributed-crawling-engine/final npm install cp .env.example .env
Tragen Sie anschließend Ihren Crawlbase-Token und Ihre öffentliche Callback-URL in .env ein. Im weiteren Verlauf des Artikels entspricht jeder Implementierungsschritt direkt einem Checkpoint unter steps/, während final/ stets das vollständige, lauffähige Projekt enthält. Die README des Repositorys enthält für jeden Abschnitt eine Artikel-zu-Code-Referenz.
Schritt 1: Konfiguration zentralisieren
Die Engine beginnt mit einer einzigen zentralen Quelle für ihre Konfiguration. Statt Secrets und Crawl-Richtlinienwerte über die Codebasis zu verstreuen, wird alles aus Umgebungsvariablen geladen und beim Start validiert. Fehlt ein erforderlicher Wert wie der Crawlbase-Token, schlägt die Engine sofort fehl, statt später während eines Crawls.
Die vollständige Implementierung liegt in final/src/config.js im begleitenden Repository.
const config = { crawlbaseToken: required('CRAWLBASE_TOKEN'), crawlerName: process.env.CRAWLER_NAME || 'distributed-engine', callbackUrl: process.env.CALLBACK_URL || '', port: Number(process.env.PORT || 3000), maxDepth: Number(process.env.MAX_DEPTH || 2), allowedDomains: (process.env.ALLOWED_DOMAINS || '') .split(',') .map((domain) => domain.trim().toLowerCase()) .filter(Boolean), };
Die meisten dieser Werte definieren die Crawl-Richtlinie der Engine, nicht ihre Infrastruktur. MAX_DEPTH begrenzt, wie weit der Crawler rekursiv expandieren kann, während ALLOWED_DOMAINS den Crawl auf die Websites beschränkt, die Sie ausdrücklich zulassen. Derselbe CRAWLBASE_TOKEN authentifiziert sowohl den Enterprise Crawler als auch die Crawling API, eine einzige Zugangsberechtigung genügt der Engine also für die Kommunikation mit Crawlbase.
Mit der Konfiguration an ihrem Platz besteht der nächste Schritt darin, den verteilten Crawler zu erstellen, der unsere Crawl-Jobs ausführen wird.
Schritt 2: Die verteilte Queue erstellen
In Crawlbase ist die verteilte Queue der Enterprise Crawler: eine verwaltete Queue mit Worker-Flotte, die URLs entgegennimmt, sie asynchron crawlt und die Ergebnisse entweder an einen Webhook oder an Cloud Storage liefert. Wir verwenden die Webhook-Zustellung, indem wir beim Erstellen des Crawlers eine callback_url angeben.
Die Setup-Logik ist in final/src/setup-crawler.js implementiert. Die Management API erwartet den Crawlbase-Token im URL-Pfad statt im Query-String, das Skript baut den Endpunkt daher entsprechend zusammen.
const endpoint = `https://api.crawlbase.com/crawler/${config.crawlbaseToken}`; const response = await fetch(endpoint, { method: 'POST', headers: { 'Content-Type': 'application/json' }, body: JSON.stringify({ name: config.crawlerName, callback_url: config.callbackUrl, }), });
Erstellen Sie den Crawler einmalig:
npm run setup
Sobald der Crawler an Ihren Webhook gebunden ist, wird das Hinzufügen von Arbeit zur Queue zu einer normalen Crawling-API-Anfrage mit zwei zusätzlichen Parametern. crawler identifiziert die Ziel-Queue, während callback=true Crawlbase anweist, die Anfrage asynchron zu verarbeiten, statt die Seite sofort zurückzugeben. Die Anfrage liefert eine Request-ID (rid), sobald die URL in die Queue aufgenommen wurde, sodass der eigentliche Crawl im Hintergrund stattfinden kann.
Die Push-Logik ist in final/src/crawlbase-client.js implementiert.
async function pushToCrawler(url, depth) { const response = await api.get(url, { crawler: config.crawlerName, callback: true, callbackHeaders: `X-Crawl-Depth|${depth}`, }); // Surface auth/quota errors instead of silently dropping the URL. if (response.statusCode !== 200) { throw new Error(`Crawler push failed (${response.statusCode}): ${response.body}`); } // The push response is the small JSON envelope { "rid": "..." }, but it is // not served with a JSON content-type, so parse the body ourselves. const parsed = response.json || parseRid(response.body); return parsed && parsed.rid; }
Zwei Implementierungsdetails sind erwähnenswert. Erstens: Obwohl die Push-Antwort eine JSON-Payload enthält, wird sie nicht mit einem JSON-Content-Type zurückgegeben, der Helper parst den Antwortkörper daher selbst, statt sich auf automatische Deserialisierung zu verlassen. Zweitens hält callbackHeaders die Engine zustandslos. Die aktuelle Crawl-Tiefe wird der Anfrage als X-Crawl-Depth mitgegeben, und Crawlbase liefert sie bei der Webhook-Zustellung zurück. So kann die Engine die Crawl-Tiefe wiederherstellen, ohne eigenen Request-Zustand zu verwalten.
Derselbe Helper wird vom Seed-Skript verwendet, implementiert in final/src/seed.js, um die initiale Menge an URLs einzureihen.
for (const url of SEED_URLS) { if (!shouldCrawl(url, 0)) { console.log(`Skipped (filtered or duplicate): ${url}`); continue; } const rid = await pushToCrawler(url, 0); console.log(`Queued ${url} -> rid ${rid}`); }
Der Befehl npm run seed gibt für jeden akzeptierten Seed eine Zeile Queued <url> -> rid <rid> aus. Ab diesem Punkt läuft der verteilte Crawler. Die URLs liegen jetzt in der Queue von Crawlbase, und die ersten Crawl-Ergebnisse treffen bald an dem Webhook ein, den wir als Nächstes implementieren.
Schritt 3: Crawl-Ergebnisse mit einem Webhook verarbeiten
Sobald der Crawler beginnt, URLs zu verarbeiten, braucht die Engine eine Möglichkeit, die Ergebnisse zu empfangen. Jeder abgeschlossene Crawl wird an die zuvor konfigurierte callback_url zugestellt. Die HTML-Seite kommt als Request-Body an, während Metadaten wie pc_status, original_status, rid, url und alle benutzerdefinierten Callback-Header als HTTP-Header gesendet werden.
setImmediate; die Health-Probes des Monitoring-Bots werden als No-Ops beantwortet.Die Webhook-Implementierung liegt in final/src/server.js. Zwei Details sind hier wichtig. Erstens liefert Crawlbase Antworten gzip-komprimiert aus, der Server nutzt daher express.raw(), um den Request-Body als Buffer zu empfangen, den Express transparent dekomprimiert. Zweitens sollten Webhook-Bestätigungen so schnell wie möglich erfolgen: sofort bestätigen, erst nach dem Senden der Antwort verarbeiten.
app.use(express.raw({ type: '*/*', limit: '10mb' })); app.post('/webhook', (req, res) => { // The monitoring bot probes this endpoint to detect outages. Acknowledge // it as a no-op - it carries no real crawl result to process. Crawlbase // expects a 2xx with an empty body, so end the response without content. if ((req.headers['user-agent'] || '').includes('Crawlbase Monitoring Bot')) { return res.status(200).end(); } const pcStatus = Number(req.headers['pc_status']); const rid = req.headers['rid']; const url = req.headers['url']; const depth = Number(req.headers['x-crawl-depth'] || 0); const html = req.body.toString('utf8'); res.status(200).end(); if (pcStatus !== 200 || !rid || !url) { return; } setImmediate(() => handleResult({ rid, url, depth, html })); });
Crawlbase validiert die Webhook-Gesundheit über eine leere 2xx-Antwort, die innerhalb von rund 200 Millisekunden eintrifft, und prüft den Endpunkt regelmäßig mit seinem Monitoring-Bot. Deshalb antwortet der Handler mit res.status(200).end() statt mit einem Antwortkörper, und deshalb werden die Probes des Bots als No-Ops bestätigt. Langsame oder nicht erreichbare Endpunkte lösen Zustellungs-Retries aus.
Der Handler verzweigt außerdem anhand von pc_status statt anhand des original_status der Ziel-Website. Ein pc_status von 200 zeigt an, dass Crawlbase den Crawl nach allen erforderlichen Retries oder Anti-Bot-Maßnahmen erfolgreich abgeschlossen hat, fehlgeschlagene Anfragen kann die Engine daher einfach ignorieren.
Beachten Sie, dass die eigentliche Verarbeitung innerhalb von setImmediate() stattfindet, nachdem die Antwort bereits bestätigt wurde. Das hält den Webhook reaktionsschnell, unabhängig davon, wie viel Parsing- oder Speicherarbeit als Nächstes anfällt, und erlaubt Crawlbase, weiter neue Crawl-Ergebnisse zuzustellen, ohne auf das Ende der nachgelagerten Verarbeitung zu warten.
In diesem Stadium empfängt die Engine Crawl-Ergebnisse, macht damit aber noch nichts Nützliches. Der nächste Schritt besteht darin, jede Seite zu parsen, strukturierte Daten zu extrahieren, neue Links zu entdecken und sie zurück in den Crawler zu speisen.
Schritt 4: Daten extrahieren und die Frontier erweitern
Hier wird der Crawler selbsterhaltend. Jede an den Webhook gelieferte Seite erzeugt zwei Ausgaben: einen strukturierten Datensatz, der gespeichert werden kann, und eine neue Menge von Links, die zu zukünftigen Crawl-Jobs werden können. Die Frontier sitzt zwischen diesen beiden Stufen und stellt sicher, dass der Crawl begrenzt, deterministisch und frei von doppelter Arbeit bleibt.
Die Frontier-Implementierung liegt in final/src/frontier.js.
function shouldCrawl(rawUrl, depth) { if (depth > config.maxDepth) { return false; } const url = normalize(rawUrl); if (!url || !isAllowed(url) || seen.has(url)) { return false; } seen.add(url); return true; }
Der Helper shouldCrawl fungiert als Torwächter der Engine. Jede entdeckte URL wird normalisiert, gegen die erlaubten Domains geprüft, an der maximalen Crawl-Tiefe gemessen und als gesehen vermerkt, bevor sie zurück in den Crawl aufgenommen wird. Diese eine Funktion erzwingt den Geltungsbereich des Crawlers, garantiert die Terminierung und verhindert doppelte Arbeit.
Sobald eine Seite den Webhook durchlaufen hat, extrahiert die Engine ihre Daten, persistiert das Ergebnis und bewertet jeden ausgehenden Link für die nächste Crawling-Runde. Die Extraktions- und Speicherlogik ist in final/src/extract.js implementiert, während die Orchestrierung im Webhook-Handler in final/src/server.js stattfindet.
async function handleResult({ rid, url, depth, html }) { const { record, links } = extract(html, url); save(rid, { rid, url, depth, crawledAt: new Date().toISOString(), ...record }); let queued = 0; for (const link of links) { if (shouldCrawl(link, depth + 1)) { try { await pushToCrawler(link, depth + 1); queued += 1; } catch (error) { console.error(`Failed to queue ${link}: ${error.message}`); } } } console.log(`[${rid}] depth=${depth} url=${url} queued=${queued} new links`); }
Jeder ausgehende Link durchläuft die Frontier, bevor er zu einem weiteren Crawl-Job werden kann. Gültige URLs werden sofort zurück in den Enterprise Crawler geschoben, während Duplikate, Domains außerhalb des Geltungsbereichs und Seiten jenseits der konfigurierten Tiefe verworfen werden. Die Engine wartet nie darauf, dass diese Seiten gecrawlt werden; sie reiht sie lediglich ein und verarbeitet das aktuelle Ergebnis weiter. Crawlbase übernimmt die verteilte Ausführung, und der Webhook erhält die nächste fertige Seite, sobald sie bereit ist.
Diese rekursive Feedback-Schleife ist der Kern der Architektur. Jeder abgeschlossene Crawl erzeugt weitere Arbeit, bis keine neuen URLs im Geltungsbereich mehr zu entdecken sind, sodass die Engine den Crawl kontinuierlich erweitern kann, ohne einen eigenen Worker-Pool oder eine eigene Crawl-Queue zu unterhalten.
Der vollständige Crawl-Lebenszyklus
An diesem Punkt ist jedes Teil der Engine an seinem Platz. Mit laufendem Tunnel und einer CALLBACK_URL, die darauf zeigt, startet der gesamte Crawl mit nur drei Befehlen:
npm run setup # once: create the crawler and bind it to your webhook npm start # start the webhook consumer npm run seed # enqueue the initial URLs
Von dort an läuft die Engine autonom. Seed-URLs werden eingereiht, Crawlbase verarbeitet sie asynchron, fertige Seiten werden an den Webhook geliefert, strukturierte Daten werden extrahiert und gespeichert, und jeder neu entdeckte Link wird bewertet, bevor er zurück in die Queue geschoben wird. Der Zyklus wiederholt sich, bis keine Seiten im Geltungsbereich mehr zu crawlen sind.
Da die Engine nur den Workflow orchestriert, wird der Durchsatz von der Worker-Parallelität von Crawlbase bestimmt, nicht von den Ressourcen Ihrer Anwendung. Den Crawl zu skalieren erfordert keine zusätzlichen Worker-Prozesse und keine Änderungen an der Engine selbst; es bedeutet, Crawlbase mehr Crawl-Jobs gleichzeitig verarbeiten zu lassen. Während der Crawl fortschreitet, können Sie die Aktivität über die Server-Logs und die wachsende Sammlung von JSON-Datensätzen im Verzeichnis results/ verfolgen.
Die Architektur unterstützt auch synchronen Seitenabruf, wenn ein eingereihter Crawl nicht passt. Der Helper fetchInline in final/src/crawlbase-client.js nutzt die Crawling API, um eine einzelne Seite sofort mit demselben Crawlbase-Token abzurufen. In der Praxis ist der Enterprise Crawler die richtige Wahl für asynchrone Crawls mit hohem Volumen, während sich die Crawling API besser für latenzkritische Anfragen eignet, etwa Benutzer-Lookups oder KI-Agenten, die Kontext auf Abruf beziehen.
Überlegungen für die Produktion
Die Implementierung, die wir gebaut haben, ist bewusst klein gehalten, damit die Architektur leicht verständlich bleibt. Vor dem Produktionseinsatz lohnt es sich, einige Bereiche zu stärken.
-
Verlagern Sie die Frontier in gemeinsamen Storage. Das Beispiel hält das
seen-Set im Speicher, wodurch die Deduplizierung auf einen einzelnen Prozess beschränkt ist und bei einem Neustart verloren geht. Für mehrere Engine-Instanzen oder langlaufende Crawls verlagern Sie die Frontier in Redis oder einen anderen gemeinsamen Datastore, der über normalisierte URLs indiziert ist. -
Verwalten Sie Secrets außerhalb der Anwendung. Das Beispiel lädt den Crawlbase-Token für die lokale Entwicklung aus
.env. In der Produktion injizieren Sie Zugangsdaten über den Secret-Manager Ihrer Plattform, statt sie in Konfigurationsdateien abzulegen. - Halten Sie den Webhook schnell und zuverlässig. Der Webhook sollte Anfragen sofort bestätigen und teure Verarbeitung aufschieben, bis die Antwort gesendet ist. Langsame oder nicht erreichbare Endpunkte lösen Zustellungs-Retries aus; den Endpunkt mit einem gemeinsamen Secret oder benutzerdefinierten Callback-Headern zu schützen verbessert daher sowohl Zuverlässigkeit als auch Sicherheit.
- Ziehen Sie Crawlbase Cloud Storage für asynchrone Verarbeitung in Betracht. Webhooks sind ideal, wenn Sie Crawl-Ergebnisse verarbeiten möchten, sobald sie verfügbar sind, aber sie sind nicht die einzige Zustelloption. Ist der Enterprise Crawler für Cloud Storage konfiguriert, wird jeder abgeschlossene Crawl automatisch persistiert, ohne dass ein Webhook nötig ist, und Ihre Anwendung ruft die Ergebnisse nach eigenem Zeitplan über die Storage API ab. Das eignet sich gut für Batch-Verarbeitung, Umgebungen, in denen das Exponieren eines HTTPS-Endpunkts unpraktisch ist, oder Workflows, die von einer permanenten URL für jede gecrawlte Seite profitieren. Details finden Sie in der Dokumentation zum Storage-Zustellmodus.
- Überwachen Sie das Queue-Wachstum. Enterprise Crawler erzwingen Limits für Parallelität, Queue-Kapazität und Push-Rate, um Crawls vorhersehbar zu halten. Wenn Ihre Producer Ihre Consumer überholen, überwachen Sie die Queue-Größe und pausieren oder leeren Sie außer Kontrolle geratene Crawls über die Management API, bevor sie unnötig Ressourcen verbrauchen. Wächst Ihr Workload, können Sie über das Crawlbase Support Dashboard höhere Parallelitäts- oder Push-Rate-Limits anfragen.
-
Wählen Sie den richtigen Rendering-Modus. Beginnen Sie wann immer möglich mit einem Normal-Token. Wenn ein Ziel stark auf clientseitiges Rendering setzt oder Challenge-Seiten zurückgibt, wechseln Sie zum JavaScript Crawler und nutzen Sie Rendering-Parameter wie
page_waitoderajax_wait, um vor der Extraktion auf dynamische Inhalte zu warten. -
Respektieren Sie Crawl-Grenzen. Halten Sie den Crawler innerhalb von Domains, die Ihnen gehören oder auf die Sie zugreifen dürfen, beachten Sie, wo anwendbar, die
robots.txtund die Nutzungsbedingungen jeder Website und konfigurieren Sie vernünftige Crawl-Limits, um unnötigen Traffic zu vermeiden.
Fazit
Wir haben eine verteilte Crawling-Engine gebaut, indem wir die Crawl-Orchestrierung von der Crawl-Ausführung getrennt haben. Die Engine besitzt Crawl-Richtlinie, URL-Deduplizierung, Parsing, Storage und rekursive Frontier-Erweiterung, während Crawlbase die verteilte Queue, die Worker-Flotte, Retries, Browser-Rendering und Proxy-Infrastruktur bereitstellt. Diese Trennung hält die Anwendung klein, leicht nachvollziehbar und auf die Logik fokussiert, die sie einzigartig macht.
Die Beispielimplementierung bevorzugt bewusst Einfachheit gegenüber Produktionsreife. Wenn Ihre Workloads wachsen, können Sie die In-Memory-Frontier durch Redis ersetzen, Crawl-Ergebnisse in einer Datenbank persistieren oder mehrere zustandslose Engine-Instanzen hinter derselben verteilten Queue betreiben, ohne die Gesamtarchitektur zu ändern.
Eine verwaltete Queue mit Worker-Flotte für asynchrones Crawling in großem Maßstab: Schieben Sie URLs hinein, und fertige Seiten treffen an Ihrem Webhook oder in Cloud Storage ein, mit bereits angewendeten Retries, JavaScript-Rendering, Proxy-Rotation und Anti-Bot-Handling. Ihre Engine behält die Richtlinie; Crawlbase führt die Abrufe aus. Erstellen Sie Ihr Konto und starten Sie im kostenlosen Tarif.
Häufig gestellte Fragen
Wann sollte ich den Enterprise Crawler statt der Crawling API verwenden?
Die beiden Dienste lösen unterschiedliche Probleme. Verwenden Sie den Enterprise Crawler für asynchrone, großangelegte Crawls, bei denen Sie Queueing, Retries, Parallelität und Zustellung per Webhook oder Cloud Storage benötigen. Verwenden Sie die Crawling API, wenn Sie eine Seite sofort brauchen, etwa für eine nutzerseitige Anfrage oder um einem KI-Agenten Echtzeit-Kontext zu liefern. Eine gute Faustregel: die Queue für Durchsatz, die Crawling API für latenzarme Anfragen.
Muss ich einen öffentlichen Webhook exponieren?
Nein. Dieser Artikel verwendet einen Webhook, weil das die reaktionsschnellste Art ist, Crawl-Ergebnisse zu verarbeiten, sobald sie verfügbar sind. Alternativ können Sie einen Enterprise Crawler so konfigurieren, dass er Ergebnisse an Crawlbase Cloud Storage liefert, und sie später über die Storage API abrufen. Das passt oft besser zu Batch-Verarbeitungs-Workflows oder Umgebungen, in denen das Exponieren eines öffentlichen HTTPS-Endpunkts unpraktisch ist.
Wann sollte ich einen JavaScript-Token statt eines Normal-Tokens verwenden?
Beginnen Sie wann immer möglich mit einem Normal-Token, weil er schneller und kosteneffizienter ist. Wenn die Ziel-Website Inhalte clientseitig rendert, eine leere HTML-Hülle zurückgibt oder Anti-Bot-Challenges stellt, die einen Browser erfordern, wechseln Sie zu einer JavaScript-Anfrage und nutzen Sie bei Bedarf Rendering-Parameter wie page_wait oder ajax_wait.
Wie bringe ich den Crawler dazu, URLs schneller zu verarbeiten?
Die Engine selbst ist bewusst leichtgewichtig; sie orchestriert lediglich den Crawl. Der Gesamtdurchsatz wird von der Parallelität des Enterprise Crawlers bestimmt, nicht von den Ressourcen Ihrer Anwendung. Benötigt Ihr Workload mehr Durchsatz, als Ihre aktuellen Limits erlauben, können Sie über das Support Dashboard eine Erhöhung anfragen.
Kann ich mehrere Instanzen dieser Engine betreiben?
Ja. Die Architektur ist auf horizontale Skalierung ausgelegt. Die einzige Komponente, die sich ändern muss, ist die In-Memory-Frontier. Ersetzen Sie das lokale seen-Set durch gemeinsamen Storage wie Redis, können mehrere Webhook-Consumer den Crawl-Zustand koordinieren und sich dieselbe Queue des Enterprise Crawlers teilen.
Crawlen Sie jede Website im großen Maßstab, ohne gegen die Infrastruktur zu kämpfen.
Crawlbase übernimmt Proxys, Fingerprints und CAPTCHAs, damit Ihr Team Datenpipelines ausliefert, statt Crawl-Infrastruktur zu pflegen. 1.000 Anfragen kostenlos, keine Karte erforderlich.

