Web Scraping war immer zwei zusammengeklebte Jobs: die Seite holen und dann die gewünschten Felder herausziehen. Der zweite Job ist, wo die meisten Scraper veralten. Man schreibt CSS-Selektoren oder XPath gegen ein Layout, die Site liefert ein Redesign, und die Extraktion gibt stillschweigend leere Strings zurück. Große Sprachmodelle verändern die Wirtschaftlichkeit. Statt zu beschreiben, wo ein Wert im DOM liegt, beschreibt man in einfachem Englisch, was man will, und lässt das Modell den Inhalt so lesen, wie es ein Mensch tun würde.
Diese Anleitung zeigt, wie man Gemini AI Web Scraping in Python auf zuverlässige Weise durchführt: die Crawling API nutzen, um die Zielseite in sauberes HTML oder Markdown zu laden und zu rendern, dann diesen Inhalt an Google Gemini zur Extraktion strukturierter JSON-Daten übergeben. Die Arbeitsteilung ist entscheidend und der Kerngedanke dieses Artikels. Crawlbase übernimmt das Laden und Rendern hinter einem echten Browser und einer vertrauenswürdigen IP; Gemini übernimmt das Lesen und Strukturieren. Jedes Werkzeug erledigt den Teil, für den es wirklich geeignet ist.
Warum Gemini überhaupt mit einer Abrufschicht kombinieren
Gemini ist ein großes Sprachmodell von Google. Es versteht natürliche Sprache, liest chaotische Inhalte und gibt strukturierte Daten zurück, wenn man danach fragt. Was es nicht tut: Webseiten abrufen. Es hat keinen HTTP-Client, keinen Browser, keinen Proxy-Pool und keine Möglichkeit, die Anti-Bot-Abwehrmechanismen zu überwinden, die die meisten kommerziellen Sites schützen. Eine URL übergeben und es kann sie nicht öffnen; rohes HTML, das man selbst gescrapt hat, übergeben und es extrahiert gerne aus dem, was man abzurufen vermochte, einschließlich einer leeren Hülle.
Das ist die Lücke, die die Abrufschicht füllt. Moderne Sites rendern Inhalte clientseitig und fordern automatisierten Datenverkehr aggressiv heraus, sodass ein einfaches requests.get häufig einen 200-Status mit keinem der gesuchten Daten zurückgibt. Man benötigt einen Browser, der das JavaScript der Seite tatsächlich ausführt, und eine IP, die die Site wie einen echten Besucher liest. Man kann das selbst mit einem Headless-Browser und rotierenden Residential-Proxies zusammenstellen, aber diesen Stack gesund zu halten ist der größte Aufwand. Die Crawling API fasst beides in einem einzigen Aufruf zusammen: eine URL mit einem JavaScript-Token senden, sie rendert die Seite und gibt fertiges HTML für Gemini zurück.
Halten Sie die Grenze klar im Kopf. Crawlbase lädt und rendert die Seite in sauberes HTML oder Markdown. Gemini extrahiert strukturierte Felder aus diesem Inhalt. Gemini berührt in diesem Design nie das Netzwerk, und Crawlbase versucht nie, die Daten zu verstehen. Diese Verantwortlichkeiten zu vermischen ist der häufigste Grund, warum sich solche Pipelines instabil anfühlen.
Was Sie bauen werden
Ein kleines, lauffähiges Python-Skript, das eine Produkt-URL entgegennimmt, die gerenderte Seite als sauberes Markdown über die Crawling API abruft, dieses Markdown mit einem Extraktionsprompt an Gemini sendet und das strukturierte Ergebnis in eine JSON-Datei schreibt. Wir verwenden eine öffentliche Testseite, sodass Sie jedes Code-Schnipsel ausführen können, bevor Sie es auf ein echtes Ziel richten.
Umgebung einrichten
Sie benötigen Python 3.8 oder neuer. Prüfen Sie Ihre Version, erstellen Sie eine virtuelle Umgebung, damit Projektabhängigkeiten isoliert bleiben, und installieren Sie dann die Bibliotheken.
python --version python -m venv gemini_env source gemini_env/bin/activate pip install google-generativeai crawlbase python-dotenv
Unter Windows aktivieren Sie die Umgebung mit gemini_env\Scripts\activate statt der source-Zeile. Drei Abhängigkeiten erledigen die Arbeit: crawlbase ist der offizielle Client für die Crawling API, google-generativeai ist Googles Gemini-Client, und python-dotenv lädt Ihre Schlüssel aus einer lokalen Datei, damit sie nie fest im Skript kodiert werden.
Sie benötigen zwei Anmeldedaten. Holen Sie sich einen Gemini-API-Schlüssel von Google AI Studio und ein JavaScript-Token (JS-Token) von Ihrem Crawlbase-Dashboard nach der Registrierung. Speichern Sie beide in einer .env-Datei in Ihrem Projektordner.
GEMINI_API_KEY=your_gemini_key_here CRAWLBASE_JS_TOKEN=your_crawlbase_js_token_here
Crawlbase bietet zwei Token-Typen. Das normale Token ruft statisches HTML ab; das JavaScript-Token (JS-Token) rendert die Seite zunächst in einem echten Browser. Die meisten Seiten, die das Scrapen lohnen, laden ihren Inhalt clientseitig, daher ist das JS-Token hier die sichere Standardwahl. Das normale Token auf einer clientseitig gerenderten Seite gibt dieselbe leere Hülle wie eine einfache Anfrage zurück, und Gemini kann keine Daten extrahieren, die nie vorhanden waren.
Schritt 1: Die gerenderte Seite mit der Crawling API abrufen
Die Crawling API kann die Seite bereits in Markdown konvertiert zurückgeben, was genau das ist, was man vor der Übergabe an ein LLM möchte. Markdown filtert Navigationselemente, Skripte und Styling-Rauschen heraus und lässt den lesbaren Inhalt übrig. Das reduziert die Token-Anzahl, die an Gemini gesendet wird, was den Aufruf günstiger macht und die Extraktion genauer, da das Modell seine Aufmerksamkeit auf echten Inhalt statt auf Boilerplate richtet. Übergeben Sie format: 'markdown' und die API gibt sauberen Text statt rohem HTML zurück.
import os from dotenv import load_dotenv from crawlbase import CrawlingAPI load_dotenv() api = CrawlingAPI({"token": os.environ["CRAWLBASE_JS_TOKEN"]}) url = "https://books.toscrape.com/catalogue/a-light-in-the-attic_1000/index.html" def fetch_markdown(target_url): options = {"format": "markdown", "ajax_wait": "true", "page_wait": 3000} response = api.get(target_url, options) return response["body"].decode("utf-8") page_markdown = fetch_markdown(url) print(page_markdown[:500])
Die beiden Warteoptionen sind bei clientseitig gerenderten Zielen wichtig. ajax_wait weist die API an, auf das Laden asynchroner Inhalte zu warten, und page_wait hält nach dem Laden für eine feste Anzahl von Millisekunden inne, damit spät gerenderte Elemente erscheinen, bevor die Seite erfasst wird. Drei Sekunden sind ein vernünftiger Ausgangspunkt; erhöhen Sie den Wert, wenn Inhalt unvollständig zurückkommt. Für eine statische Seite wie das obige Testbuch könnte man sogar das normale Token verwenden, aber das JS-Token und diese Optionen beizubehalten bedeutet, dass derselbe Code funktioniert, wenn man ihn auf eine schwierigere, clientseitig gerenderte Site richtet.
Gemini liest Seiten, lädt sie aber nicht. Die Crawling API schließt diese Lücke in einem Aufruf: ein JS-Token übergeben, die Seite in einem echten Browser rendern, server-seitig durch Residential-IPs rotieren und sauberes HTML oder LLM-fähiges Markdown zurückgeben, sodass Sie weder eine Headless-Flotte noch einen Proxy-Pool selbst betreiben müssen. Testen Sie es zunächst mit einer öffentlichen Seite im kostenlosen Tarif.
Schritt 2: Den Inhalt an Gemini senden und JSON anfordern
Jetzt der interessante Teil. Mit sauberem Markdown beschreiben Sie die gewünschten Felder in einem Prompt und lassen Gemini die Extraktion übernehmen. Der Schlüssel für eine zuverlässige Pipeline ist das Erzwingen von JSON-Ausgabe. Geminis Client unterstützt einen MIME-Typ für die Antwort, also setzen Sie ihn auf application/json und das Modell gibt parsbares JSON statt Prosatext mit Code-Fences zurück. Diese eine Einstellung beseitigt den größten Teil der Instabilität, über die Menschen bei LLM-Extraktion klagen.
import google.generativeai as genai genai.configure(api_key=os.environ["GEMINI_API_KEY"]) model = genai.GenerativeModel("gemini-2.0-flash") def extract_fields(content): prompt = f"""You are a data extraction tool. From the page content below, extract the book title, price, availability, and star rating. Return only JSON with keys: title, price, availability, rating. CONTENT: {content} """ response = model.generate_content( prompt, generation_config={"response_mime_type": "application/json"}, ) return response.text raw_json = extract_fields(page_markdown) print(raw_json)
Einige Dinge lassen diesen Prompt funktionieren. Er gibt die Rolle an ("data extraction tool"), damit Gemini präzise bleibt, er nennt die genauen gewünschten Schlüssel, sodass das Schema über Läufe hinweg stabil ist, und er übergibt das Markdown statt rohem HTML, damit das Modell seine Aufmerksamkeit auf Inhalt statt Boilerplate richtet. Wenn Sie ein reichhaltigeres Schema benötigen, listen Sie weitere Schlüssel auf und beschreiben Sie mehrdeutige; das Modell verarbeitet verschachtelte Objekte und Arrays ohne zusätzlichen Aufwand.
Schritt 3: Das strukturierte Ergebnis parsen und speichern
Da Sie einen JSON-MIME-Typ angefordert haben, ist der Antworttext bereits gültiges JSON. Parsen Sie ihn in ein Python-Dict und schreiben Sie es auf die Festplatte. Kapseln Sie das Parsen in einem try/except, damit eine seltene fehlerhafte Antwort den rohen Text protokolliert statt den Lauf zum Absturz zu bringen.
import json def save_json(raw, path="book_data.json"): try: data = json.loads(raw) except json.JSONDecodeError: print("Gemini did not return valid JSON:") print(raw) return with open(path, "w") as f: json.dump(data, f, indent=2) print(f"Saved {path}") save_json(raw_json)
Das vollständige Skript
Hier ist alles zu einer lauffähigen Datei zusammengeführt. Tragen Sie Ihre zwei Anmeldedaten in .env ein, ändern Sie die URL und passen Sie die Prompt-Schlüssel für das Ziel an, aus dem Sie extrahieren möchten.
import os import json from dotenv import load_dotenv from crawlbase import CrawlingAPI import google.generativeai as genai load_dotenv() api = CrawlingAPI({"token": os.environ["CRAWLBASE_JS_TOKEN"]}) genai.configure(api_key=os.environ["GEMINI_API_KEY"]) model = genai.GenerativeModel("gemini-2.0-flash") url = "https://books.toscrape.com/catalogue/a-light-in-the-attic_1000/index.html" def fetch_markdown(target_url): options = {"format": "markdown", "ajax_wait": "true", "page_wait": 3000} response = api.get(target_url, options) return response["body"].decode("utf-8") def extract_fields(content): prompt = f"""You are a data extraction tool. From the page content below, extract the book title, price, availability, and star rating. Return only JSON with keys: title, price, availability, rating. CONTENT: {content} """ response = model.generate_content( prompt, generation_config={"response_mime_type": "application/json"}, ) return response.text def main(): markdown = fetch_markdown(url) raw = extract_fields(markdown) try: data = json.loads(raw) except json.JSONDecodeError: print("Gemini did not return valid JSON:", raw) return with open("book_data.json", "w") as f: json.dump(data, f, indent=2) print(json.dumps(data, indent=2)) if __name__ == "__main__": main()
Wie die Ausgabe aussieht
Führen Sie es mit python scraper.py aus und erhalten Sie saubere strukturierte Daten, die in book_data.json geschrieben und auf der Konsole ausgegeben werden.
{ "title": "A Light in the Attic", "price": "£51.77", "availability": "In stock (22 available)", "rating": "Three" }
Beachten Sie, was Sie nicht geschrieben haben: keine CSS-Selektoren, kein XPath, keine feldspezifische Parse-Logik. Sie haben die Felder beschrieben und das Modell hat sie gefunden. Richten Sie dasselbe Skript auf eine andere Buch-URL oder eine Produktseite auf einer anderen Site, und es passt sich ohne Code-Änderungen an, was der eigentliche Vorteil des KI-Datenextraktions-Ansatzes gegenüber handabgestimmten Selektoren ist.
Auf viele Seiten skalieren
Eine Seite ist eine Demo; ein echter Auftrag läuft über eine Liste von URLs. Die Form bleibt dieselbe: URLs durchlaufen, jede über die Crawling API abrufen, mit Gemini extrahieren und die Zeilen sammeln. Zwei Dinge beim Skalieren im Kopf behalten. Gemini berechnet pro Token, also reduziert das Senden von Markdown statt vollständigem HTML die Kosten bei jedem Aufruf, und die Crawling API hat ihren eigenen Durchsatz, sodass man weder Proxies noch Browser-Instanzen selbst verwalten muss.
urls = [ "https://books.toscrape.com/catalogue/a-light-in-the-attic_1000/index.html", "https://books.toscrape.com/catalogue/tipping-the-velvet_999/index.html", ] results = [] for u in urls: markdown = fetch_markdown(u) raw = extract_fields(markdown) try: results.append(json.loads(raw)) except json.JSONDecodeError: print(f"Skipped {u}: invalid JSON") with open("books.json", "w") as f: json.dump(results, f, indent=2)
Wenn Sie immer wieder dieselbe bekannte Site extrahieren (Amazon, einen großen Händler, eine Jobbörse), lohnt sich ein Vergleich mit der Crawling API, die für unterstützte Sites vorparsiertes JSON ohne LLM im Loop zurückgibt. Für ungewöhnliche oder einmalige Layouts, für die kein Parser existiert, ist der Gemini-Ansatz in dieser Anleitung der flexible Fallback. Für den Hintergrund, warum Markdown die richtige Eingabeform für ein LLM ist, lesen Sie LLM-fähiges Markdown für Web Scraping.
Einschränkungen, die man vor dem Produktionseinsatz kennen sollte
Die Gemini-plus-Crawlbase-Pipeline ist flexibel, aber nicht der richtige Hammer für jeden Nagel. Diese Punkte im Kopf behalten.
Token-Kosten summieren sich. Gemini berechnet pro gesendeten und empfangenen Token. Vollständiges HTML statt Markdown zu senden kann die Rechnung ohne Nutzen vervielfachen, also die Eingabe immer kürzen. Bei sehr großen Seiten nur den relevanten Abschnitt vor dem LLM-Aufruf extrahieren.
Es ist langsamer als regelbasiertes Parsing. Ein LLM-Round-Trip dauert länger als ein Cheerio- oder BeautifulSoup-Selektor-Durchlauf. Für hochfrequente, niedrig-latente Aufgaben wie sekundenweise Preisüberwachung gewinnt ein dedizierter Parser. Der LLM-Ansatz glänzt, wenn Layouts variieren oder sich häufig ändern.
Modelle können sich irren. Auf dichten oder sich wiederholenden Seiten kann ein Modell gelegentlich ein Feld falsch beschriften oder auslassen. Das Erzwingen von JSON-Ausgabe und das Benennen genauer Schlüssel reduziert das erheblich, aber für alles Geschäftskritische das geparste Dict gegen ein erwartetes Schema validieren, bevor man ihm vertraut.
Für das Entsperrt-Bleiben bei großem Volumen übernimmt die Crawling API IP-Rotation und Rendering für Sie. Wenn Sie Ihren eigenen Datenverkehr lieber über einen rotierenden Pool leiten, gibt Ihnen der Smart AI Proxy (auch als AI Proxy bezeichnet) dieselbe Residential-IP-Rotation als Drop-in-Proxy-Endpunkt. In jedem Fall findet sich das übergeordnete Playbook unter wie man Webseiten scrapt, ohne gesperrt zu werden.
Wichtigste Erkenntnisse
- Den Auftrag aufteilen. Crawlbase lädt und rendert die Seite; Gemini extrahiert die Felder. Keines der Werkzeuge erledigt den Job des anderen, und diese Trennung ist, was die Pipeline zuverlässig macht.
-
JS-Token und Markdown-Format verwenden. Das JS-Token rendert clientseitige Seiten;
format: 'markdown'gibt saubenen, token-armen Inhalt zurück, der ideale Eingabe für ein LLM ist. -
JSON-Ausgabe erzwingen. Geminis
response_mime_typeaufapplication/jsonsetzen und die genauen Schlüssel benennen, damit das Ergebnis bei jedem Lauf parsbar ist. - Keine Selektoren nötig. Die Felder in einfachem Englisch beschreiben, sodass sich dasselbe Skript ohne Neuschreiben der Extraktionscode über Layouts anpasst.
- Die Kompromisse kennen. LLM-Extraktion ist flexibel, aber langsamer und pro Token berechnet, also Eingabe kürzen, Ausgabe validieren und bei zeitkritischen Aufgaben zu einem dedizierten Parser greifen.
Häufig gestellte Fragen
Kann Gemini Web Scraping alleine durchführen?
Nicht den Abruf-Teil. Gemini liest und strukturiert Inhalte, die man ihm übergibt, hat aber weder HTTP-Client, Browser noch Proxy-Pool und kann daher keine URL öffnen oder Anti-Bot-Abwehrmechanismen überwinden. Man kombiniert es mit einer Abrufschicht wie der Crawling API, die die Seite rendert und sauberes HTML oder Markdown zurückgibt; Gemini extrahiert dann die strukturierten Felder aus diesem Inhalt.
Warum die Seite vor der Übergabe an Gemini in Markdown umwandeln?
Markdown filtert Navigation, Skripte und Styling-Rauschen heraus und lässt den lesbaren Inhalt übrig. Das senkt die Token-Anzahl, die an Gemini gesendet wird, was Kosten reduziert und die Genauigkeit verbessert, da das Modell seine Aufmerksamkeit auf echten Inhalt statt auf Boilerplate richtet. Die Crawling API kann Markdown direkt mit format: 'markdown' zurückgeben, sodass kein separater Konvertierungsschritt benötigt wird.
Benötige ich das normale Token oder das JS-Token von Crawlbase?
Das JS-Token für jede Seite, die Inhalt clientseitig rendert, was die meisten modernen Sites sind. Das normale Token ruft statisches HTML ab, das auf einer clientseitig gerenderten Seite eine leere Hülle ist und Gemini nichts zum Extrahieren lässt. Das JS-Token rendert die Seite zunächst in einem echten Browser, sodass der Inhalt vorhanden ist, wenn er das Modell erreicht.
Wie lässt sich Gemini zuverlässig JSON statt Prosatext zurückgeben?
Den response_mime_type der Generierungskonfiguration auf application/json setzen und die genauen gewünschten Schlüssel im Prompt benennen. Diese Kombination lässt Gemini parsbares JSON ohne Code-Fences oder Kommentare zurückgeben. Den json.loads-Aufruf trotzdem in ein try/except kapseln, damit eine seltene fehlerhafte Antwort den rohen Text protokolliert statt den Lauf zum Absturz zu bringen.
Ist der Gemini-Ansatz für alles besser als die Scraper API?
Nein, sie dienen unterschiedlichen Zwecken. Für bekannte Sites mit vorhandenen Parsern gibt die Scraper API vorparsiertes JSON schneller und ohne LLM-Token-Kosten zurück. Die Gemini-Pipeline ist der flexible Fallback für ungewöhnliche, einmalige oder sich häufig ändernde Layouts, für die kein dedizierter Parser existiert und man lieber Felder beschreiben als Selektoren pflegen möchte.
Werde ich damit gesperrt?
Die Crawling API rendert Seiten hinter rotierenden Residential-IPs server-seitig, was die meisten Sperren für Sie übernimmt. Wenn Sie Ihren eigenen Abruf-Stack aufbauen, ist diese Rotation der Teil, in den sich zu investieren lohnt, und Sie können den Smart AI Proxy als Drop-in-rotierenden Endpunkt verwenden. Anfragen dosieren, Ziele variieren und Status-Codes beobachten, damit Sie zurückziehen können, wenn eine Site beginnt, Datenverkehr herauszufordern.
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.
