Files
Brancheneinstufung2/readme.md

24 KiB

Projekt: Automatisierte Unternehmensbewertung & Lead-Generierung v2.2.1

1. Projektübersicht

Dieses Repository enthält eine Suite von Python-Skripten zur automatisierten Anreicherung und Analyse von Unternehmensdaten. Das System ist modular aufgebaut und für den Betrieb in einem Docker-Container ausgelegt.

  • brancheneinstufung.py: Das Kernmodul zur Datenanreicherung (Web, Wikipedia, KI-Analyse).
  • duplicate_checker.py: Ein Modul zur intelligenten Duplikatsprüfung.
  • generate_marketing_text.py: Eine Engine zur Erstellung personalisierter Marketing-Texte.
  • app.py & Docker: Eine fernsteuerbare Schnittstelle via Google Sheets.

2. Aktueller Status: KRITISCHER FEHLER (BLOCKER)

Das gesamte System ist derzeit nicht lauffähig. Ein Inkompatibilitätsproblem zwischen dem bestehenden Code und der installierten Version der openai-Python-Bibliothek führt zu einem ModuleNotFoundError bei jedem Versuch, eine KI-Funktion aufzurufen. Dies verhindert jegliche Weiterentwicklung und Nutzung.

3. Nächster Schritt

Priorität 1: Behebung des openai-Abhängigkeitskonflikts. Die gewählte Strategie ist ein gezieltes Downgrade der openai-Bibliothek auf eine mit dem Code kompatible Version, um die Funktionalität schnellstmöglich wiederherzustellen. planning.md (v2.2.1) code Markdown

Projektplanung v2.2.1

1. Aktueller Stand

  • [X] Architektur & Module: Alle Kernmodule sind konzipiert und implementiert.
  • [!] System-Blocker: Ein Versionskonflikt der openai-Bibliothek legt das gesamte System lahm. Alle Funktionen, die auf die KI zugreifen, stürzen mit einem ModuleNotFoundError ab.

2. Strategischer Plan

Phase 1: Stabilität wiederherstellen (Hotfix)

  • [ ] Schritt 1.1 (Analyse): Überprüfung aller Code-Stellen, die openai-Fehlerklassen importieren oder verwenden, um den Umfang des Problems zu bestätigen.
  • [ ] Schritt 1.2 (Downgrade): Modifikation der requirements.txt, um die openai-Bibliothek auf eine stabile, kompatible Version (z.B. 0.28.0) festzuschreiben.
  • [ ] Schritt 1.3 (Anwendung): Neubau des Docker-Images (docker build), um die Installation der korrekten Bibliotheksversion zu erzwingen.
  • [ ] Schritt 1.4 (Validierung): Durchführung eines Testlaufs (z.B. reclassify_branches), um zu bestätigen, dass der ModuleNotFoundError behoben ist und die KI-Aufrufe wieder funktionieren.

Phase 2: Geplante Weiterentwicklung (nach Hotfix)

  • [ ] Finalisierung des Duplikats-Checks.
  • [ ] Vervollständigung der Wissensbasis und Generierung aller Marketing-Texte.
  • [ ] (Zukünftig) Planung des Code-Refactorings, um die neue openai v1.x API zu unterstützen.

Automatisierte Unternehmensbewertung & Lead-Generierung

Version: 2.1.0 (nach Implementierung des Sync-Moduls)

Projektbeschreibung

Dieses Projekt automatisiert die Anreicherung von Unternehmensdaten aus einem D365-CRM-System. Es nutzt externe APIs (Google, Wikipedia, OpenAI) und Web-Scraping, um Stammdaten zu validieren, zu ergänzen und neue, marketing-relevante Informationen (z.B. FSM-Pitches) zu generieren. Die Verarbeitung und Speicherung der angereicherten Daten erfolgt in einem Google Sheet.

Aktueller Status (August 2025)

  • Systemstabilität: Das System ist nach der Behebung von Inkompatibilitäten mit der OpenAI-Bibliothek stabil und voll lauffähig.
  • Daten-Import: Ein robuster, intelligenter Synchronisations-Mechanismus (sync_manager.py) wurde implementiert. Er gleicht einen vollständigen D365-Excel-Export mit dem Google Sheet ab, aktualisiert Stammdaten nach definierten Fachregeln und markiert Datätze für die Neu-Anreicherung.
  • Kernfunktionen: Datenanreicherung (Wikipedia, Website-Scraping) und KI-basierte Analysen (Brancheneinstufung, Text-Zusammenfassungen) sind operational.
  • Nächster Schritt: Implementierung des Daten-Exports aus dem Google Sheet zur Aktualisierung des D365-Systems.

Duplicate Checker (duplicate_checker_old.py)

Hauptfunktion

Das Skript duplicate_checker_old.py (Version 2.15) ist ein spezialisiertes Werkzeug zur Identifizierung von potenziellen Duplikaten zwischen zwei Unternehmenslisten in Google Sheets: einer Matching-Liste (Matching_Accounts) und einer Referenz-CRM-Liste (CRM_Accounts). Es verwendet einen gewichteten, heuristischen Algorithmus, um für jeden Eintrag in der Matching-Liste den wahrscheinlichsten Treffer im CRM-Bestand zu finden und bewertet diesen mit einem numerischen Score.

Abhängigkeiten

  • pandas: Zur Datenmanipulation und -analyse.
  • thefuzz: Für Fuzzy-String-Vergleiche zur Bewertung der Namensähnlichkeit.
  • gspread, oauth2client: Für die Interaktion mit der Google Sheets API.
  • Lokale Module:
    • helpers.py: Stellt Normalisierungsfunktionen (normalize_company_name, simple_normalize_url) und eine optionale Web-Suche (serp_website_lookup) bereit.
    • config.py: Zentralisiert Konfigurationswerte und API-Schlüssel.
    • google_sheet_handler.py: Kapselt die Logik für den Zugriff auf Google Sheets.

Konfiguration

Die Logik des Skripts wird durch mehrere Konstanten am Anfang der Datei gesteuert:

  • Sheet-Namen: CRM_SHEET_NAME und MATCHING_SHEET_NAME.
  • Score-Schwellenwerte: SCORE_THRESHOLD (Standard: 80) und SCORE_THRESHOLD_WEAK (95), ein strengerer Wert für Treffer ohne starke Indikatoren wie Domain- oder Standortübereinstimmung.
  • Penalties: CITY_MISMATCH_PENALTY (30) und COUNTRY_MISMATCH_PENALTY (40) werden vom Score abgezogen, wenn Standorte voneinander abweichen.
  • Prefiltering: PREFILTER_MIN_PARTIAL (70) und PREFILTER_LIMIT (30) zur Vorauswahl potenzieller Kandidaten, um die Performance zu verbessern.
  • Stop-Wörter: STOP_TOKENS_BASE und CITY_TOKENS (dynamisch generiert) enthalten Begriffe, die bei Namensvergleichen ignoriert werden, um die Signalqualität zu erhöhen.

Ablauf-Logik

  1. Initialisierung: Das Skript richtet das Logging ein, lädt API-Schlüssel (optional für SerpAPI) und initialisiert den GoogleSheetHandler.
  2. Daten laden: Die Daten aus den beiden Google Sheets (CRM_Accounts und Matching_Accounts) werden in Pandas DataFrames geladen.
  3. SerpAPI-Fallback (Optional): Für Einträge in der Matching-Liste ohne Website wird versucht, über die SerpAPI eine URL zu finden. Das Vertrauen in die gefundene URL wird bewertet (hoch, mittel, niedrig).
  4. Normalisierung: Unternehmensnamen, Domains, Orte und Länder in beiden DataFrames werden standardisiert (z.B. Kleinschreibung, Entfernung von Rechtsformzusätzen).
  5. Index-Erstellung: Zur Optimierung der Suche werden mehrere "Blocking"-Indizes aus den CRM-Daten erstellt:
    • Ein domain_index für schnelle Suchen über die Website-Domain.
    • Ein token_index für die Suche nach einzelnen Namensbestandteilen.
    • Eine token_freq Zählung, um seltene und damit aussagekräftige Namensbestandteile zu identifizieren.
  6. Iteratives Matching: Das Skript durchläuft jeden Datensatz der Matching-Liste: a. Kandidatenauswahl: Anstatt jeden Eintrag mit der gesamten CRM-Liste zu vergleichen, wird eine kleine, relevante Untergruppe von Kandidaten ausgewählt. Die Auswahl erfolgt priorisiert: zuerst über Domain-Übereinstimmung, dann über den seltensten Namens-Token und zuletzt über einen allgemeinen Prefilter. b. Scoring: Jeder Kandidat wird mit dem aktuellen Matching-Datensatz verglichen. Die Funktion calculate_similarity berechnet einen Score basierend auf einer gewichteten Formel, die Namensähnlichkeit, Domain-Match, Standortübereinstimmung, Boni und Strafen berücksichtigt. c. Bester Treffer: Der Kandidat mit dem höchsten Score wird als potenzielles Duplikat ausgewählt.
  7. Ergebnis-Aggregation: Die Ergebnisse (bester Treffer, Score, Begründung der Bewertung) werden gesammelt.
  8. Daten zurückschreiben: Die Matching-Liste wird um die Ergebnisspalten (Match, Score, Match_Grund) erweitert und vollständig in das Google Sheet Matching_Accounts zurückgeschrieben. Ein lokales CSV-Backup wird ebenfalls erstellt.

brancheneinstufung2.py

Hauptfunktion

Das Skript brancheneinstufung2.py ist der zentrale Einstiegspunkt und Orchestrator für die Datenanreicherungs-Pipeline. Es dient nicht der direkten Implementierung der Verarbeitungslogik, sondern dem Parsen von Kommandozeilen-Argumenten, der Initialisierung von Handler-Klassen (GoogleSheetHandler, WikipediaScraper, DataProcessor, SyncManager) und dem Starten des vom Benutzer ausgewählten Verarbeitungsmodus. Das Skript ist hochgradig modular und delegiert die eigentliche Arbeit an die DataProcessor-Klasse.

Abhängigkeiten

  • Standardbibliotheken: logging, os, argparse, time, datetime.
  • Lokale Module:
    • config.py: Stellt globale Konfigurationsparameter und die Projektversion bereit.
    • helpers.py: Bietet Hilfsfunktionen, z.B. für das Erstellen von Log-Dateinamen und das Initialisieren des Branchenschemas.
    • google_sheet_handler.py: Kapselt die gesamte Kommunikation mit der Google Sheets API.
    • wikipedia_scraper.py: Stellt Methoden zum Suchen und Parsen von Wikipedia-Artikeln bereit.
    • data_processor.py: Enthält die Kernlogik für alle Datenverarbeitungsschritte.
    • sync_manager.py: Implementiert die Logik zum Abgleich von CRM-Exporten mit dem Google Sheet.

Wichtige Funktionen/Methoden

Die Logik des Skripts ist primär in der main()-Funktion enthalten und lässt sich in folgende Schritte unterteilen:

  1. Argumenten-Parsing: Mittels argparse wird die Kommandozeile ausgewertet. Der wichtigste Parameter ist --mode, der den auszuführenden Prozess festlegt (z.B. sync, full_run, reeval, predict_technicians). Weitere Parameter wie --limit oder --start_sheet_row erlauben eine feingranulare Steuerung der zu verarbeitenden Datenmenge.
  2. Interaktiver Modus: Wird kein --mode übergeben, startet ein interaktiver Modus, in dem der Benutzer aus einer Liste aller verfügbaren Modi auswählen kann.
  3. Initialisierung: Basierend auf dem gewählten Modus werden die notwendigen Klassen instanziiert. Für die meisten Anreicherungs-Modi wird ein DataProcessor-Objekt erstellt, das wiederum Instanzen des GoogleSheetHandler und WikipediaScraper erhält. Für den sync-Modus wird der SyncManager verwendet.
  4. Modus-Dispatching: Eine if/elif/else-Struktur leitet die Ausführung an die passende Methode weiter.
    • sync / simulate_sync: Ruft den SyncManager auf, um einen D365-Excel-Export mit dem Google Sheet abzugleichen.
    • full_run: Startet einen sequentiellen Anreicherungsprozess für Zeilen, die noch nicht verarbeitet wurden.
    • reeval: Verarbeitet Zeilen, die explizit für eine Neubewertung markiert wurden.
    • reclassify_branches: Führt eine Neubewertung der Branchenzuordnung für alle oder eine Teilmenge der Zeilen durch.
    • train_technician_model / predict_technicians: Steuert das Training und die Anwendung eines Machine-Learning-Modells zur Vorhersage von Techniker-Anzahlen.
    • Dynamische Aufrufe: Viele Modi (z.B. wiki_verify, website_scraping) werden dynamisch aufgerufen, indem Methoden des DataProcessor-Objekts ausgeführt werden, deren Namen dem Modus entsprechen (z.B. process_wiki_verify).
  5. Fehlerbehandlung und Logging: Das gesamte Skript ist von einem try...except...finally-Block umschlossen, der Fehler abfängt, protokolliert und sicherstellt, dass das Logging am Ende sauber beendet wird.

Kernlogik (data_processor.py)

Die Klasse DataProcessor ist das Herzstück der Anreicherungslogik und enthält alle Methoden zur schrittweisen Verarbeitung von Unternehmensdaten.

setup()

  • Zweck: Initialisiert den DataProcessor, indem das Ziel-Branchenschema geladen und das trainierte Machine-Learning-Modell für die Technikerschätzung in den Speicher geladen wird.
  • Input: Keine direkten Argumente, greift aber auf die Konfigurationsdateien (ziel_Branchenschema.csv, technician_decision_tree_model.pkl etc.) zu.
  • Output: Gibt True bei Erfolg zurück und setzt das interne Flag is_setup_complete. Bei Fehlern wird False zurückgegeben und das Skript beendet.

process_rows_sequentially(...)

  • Zweck: Führt den vollständigen, schrittweisen Anreicherungsprozess für einen definierten Bereich von Zeilen im Google Sheet aus. Dies ist der Hauptmodus für die initiale Verarbeitung neuer Daten.
  • Input: start_sheet_row (Startzeile), num_to_process (Anzahl der Zeilen), sowie boolesche Flags (process_wiki_steps, process_chatgpt_steps, etc.) zur Steuerung der auszuführenden Anreicherungsschritte.
  • Output: Die Methode hat keinen direkten Rückgabewert, aber ihr Seiteneffekt ist die Aktualisierung der verarbeiteten Zeilen im Google Sheet mit den angereicherten Daten.

process_reevaluation_rows(...)

  • Zweck: Führt den vollständigen Anreicherungsprozess gezielt für Zeilen aus, die im Google Sheet manuell mit einem 'x' in der "ReEval Flag"-Spalte markiert wurden. Vor der Neubewertung werden alle zuvor abgeleiteten Daten in der Zeile gelöscht.
  • Input: row_limit (maximale Anzahl zu verarbeitender Zeilen), clear_flag (ob das 'x'-Flag nach der Verarbeitung entfernt werden soll) und die booleschen Flags zur Schritt-Steuerung.
  • Output: Aktualisiert die markierten Zeilen im Google Sheet mit neu angereicherten Daten.

process_website_scraping(...)

  • Zweck: Führt einen Batch-Prozess ausschließlich für das Scrapen von Websites durch. Die Methode identifiziert Zeilen, in denen der "Website Scrape Timestamp" fehlt, und extrahiert parallel den Rohtext und die Meta-Details der jeweiligen Unternehmens-Websites.
  • Input: start_sheet_row, end_sheet_row, limit zur Eingrenzung des Verarbeitungsbereichs.
  • Output: Schreibt den extrahierten Rohtext, Meta-Details, einen Status zur URL-Prüfung und einen Zeitstempel in die entsprechenden Spalten im Google Sheet.

process_summarize_website(...)

  • Zweck: Führt einen Batch-Prozess zur Zusammenfassung von bereits extrahierten Website-Rohtexten mittels KI durch.
  • Input: start_sheet_row, end_sheet_row, limit. Die Methode verarbeitet Zeilen, bei denen der Rohtext vorhanden, aber die Zusammenfassung noch leer ist.
  • Output: Schreibt die KI-generierte Zusammenfassung in die Spalte "Website Zusammenfassung" im Google Sheet.

process_branch_batch(...) / reclassify_all_branches(...)

  • Zweck: Führt eine (Neu-)Bewertung der Branchenzugehörigkeit für einen Zeilenbereich im Batch-Verfahren durch. Die Methode sammelt relevante Informationen (CRM-Daten, Website-Zusammenfassung, Wikipedia-Inhalte) und sendet sie gebündelt an die KI, um eine effiziente und konsistente Brancheneinstufung zu erhalten.
  • Input: start_sheet_row, end_sheet_row, limit.
  • Output: Aktualisiert die Spalten zur KI-basierten Brancheneinstufung ("Chat Vorschlag Branche", Konfidenz, Begründung etc.) im Google Sheet.

process_wiki_verify(...)

  • Zweck: Verifiziert in einem Batch-Prozess, ob der in einer Zeile hinterlegte Wikipedia-Artikel thematisch zum Unternehmen passt. Nutzt KI, um die Konsistenz zu prüfen und ggf. einen passenderen Artikel vorzuschlagen.
  • Input: start_sheet_row, end_sheet_row, limit. Verarbeitet Zeilen, die eine Wiki-URL, aber noch keinen Verifizierungs-Timestamp haben.
  • Output: Schreibt das Ergebnis der KI-Prüfung (OK, X), eine Begründung und ggf. einen Alternativvorschlag in die entsprechenden Spalten im Google Sheet.

process_find_wiki_serp(...)

  • Zweck: Sucht für große Unternehmen (definiert über Mindestumsatz/-mitarbeiter), bei denen noch keine Wikipedia-URL bekannt ist, über eine Google-Suche (SerpAPI) nach einem passenden Wikipedia-Artikel.
  • Input: start_sheet_row, end_sheet_row, limit, min_employees, min_umsatz.
  • Output: Wenn eine passende URL gefunden wird, wird diese in die "Wiki URL"-Spalte eingetragen und die Zeile für eine Neubewertung (ReEval Flag) markiert.
  • Zweck: Führt eine Suche nach LinkedIn-Kontakten für bestimmte Positionen (z.B. Serviceleiter, IT-Leiter) bei den Unternehmen im Sheet durch.
  • Input: start_sheet_row, end_sheet_row, limit. Verarbeitet Zeilen, die noch keinen "Contact Search Timestamp" haben.
  • Output: Schreibt die Anzahl der gefundenen Kontakte pro Kategorie in die "Linked... gefunden"-Spalten und speichert detaillierte Kontaktinformationen in einem separaten "Contacts"-Tabellenblatt.

train_technician_model()

  • Zweck: Bereitet die vorhandenen Daten auf, trainiert ein Machine-Learning-Modell (RandomForest) zur Vorhersage von Servicetechniker-Anzahlen, führt ein Hyperparameter-Tuning durch und speichert das trainierte Modell sowie den zugehörigen Imputer als .pkl-Dateien.
  • Input: Keine direkten Argumente. Die Methode liest die Trainingsdaten aus dem konfigurierten Google Sheet.
  • Output: Erstellt und speichert die technician_decision_tree_model.pkl- und median_imputer.pkl-Dateien sowie eine JSON-Datei mit den verwendeten Features.

process_predict_technicians(...)

  • Zweck: Wendet das trainierte ML-Modell auf Zeilen an, für die noch keine Techniker-Schätzung vorliegt, aber die notwendigen Input-Features (Umsatz, Mitarbeiter, Branche) vorhanden sind.
  • Input: start_sheet_row, end_sheet_row, limit.
  • Output: Schreibt den vorhergesagten Techniker-Bucket (z.B. "Techniker_Klein (0-49)") in die Spalte "Geschaetzter Techniker Bucket".

Hilfsfunktionen (helpers.py)

Diese Datei enthält eine Sammlung von globalen, wiederverwendbaren Hilfsfunktionen, die in verschiedenen Modulen des Projekts verwendet werden.

Decorators

retry_on_failure(func)

  • Zweck: Ein Decorator, der eine Funktion bei bestimmten, temporären Fehlern (z.B. Netzwerkprobleme, API-Rate-Limits) automatisch mehrmals ausführt. Er verwendet eine exponentielle Backoff-Strategie, um die Wartezeit zwischen den Versuchen zu erhöhen.
  • Input: Eine Funktion, die dekoriert werden soll.
  • Output: Das Ergebnis der dekorierten Funktion oder löst eine Ausnahme aus, wenn alle Wiederholungsversuche fehlschlagen.

Logging & Token Counting

token_count(text, model=None)

  • Zweck: Zählt die Anzahl der Tokens in einem gegebenen Text. Verwendet die tiktoken-Bibliothek für eine genaue Zählung, falls verfügbar, andernfalls schätzt sie die Anzahl basierend auf Leerzeichen.
  • Input: text (der zu analysierende String), model (optional, das zu verwendende KI-Modell).
  • Output: Eine Ganzzahl, die die Anzahl der Tokens darstellt.

create_log_filename(mode)

  • Zweck: Erstellt einen standardisierten, zeitgestempelten Dateinamen für Log-Dateien.
  • Input: mode (ein String, der den aktuellen Ausführungsmodus beschreibt, z.B. 'full_run').
  • Output: Ein String, der den vollständigen Pfad zur Log-Datei enthält (z.B. Log/2025-11-07_10-30_v221_Modus-full_run.txt).

Text-, String- & URL-Utilities

simple_normalize_url(url)

  • Zweck: Bereinigt und normalisiert eine URL auf ihre Kern-Domain (z.B. https://www.beispiel.de/path -> beispiel.de).
  • Input: url (ein String mit einer URL).
  • Output: Ein normalisierter Domain-String oder "k.A." bei ungültiger Eingabe.

normalize_string(s)

  • Zweck: Standardisiert einen String, indem Umlaute (ä -> ae) und gängige Sonderzeichen ersetzt werden.
  • Input: s (ein beliebiger String).
  • Output: Der normalisierte String.

clean_text(text)

  • Zweck: Bereinigt einen Text von unerwünschten Artefakten, die typischerweise beim Scrapen von Websites oder Wikipedia auftreten (z.B. [1], [Bearbeiten], überflüssige Leerzeichen).
  • Input: text (ein String).
  • Output: Der bereinigte Text.

normalize_company_name(name)

  • Zweck: Normalisiert einen Firmennamen, indem gängige Rechtsformzusätze (GmbH, AG, etc.) und andere generische Begriffe entfernt werden, um Vergleiche zu erleichtern.
  • Input: name (ein Firmenname als String).
  • Output: Der normalisierte Firmenname in Kleinbuchstaben.

extract_numeric_value(raw_value, is_umsatz=False)

  • Zweck: Extrahiert und normalisiert einen numerischen Wert aus einem unstrukturierten String. Kann Einheiten wie "Mio.", "Mrd." oder "Tsd." interpretieren und in einen Basiswert umrechnen.
  • Input: raw_value (ein String, z.B. "ca. 250 Mio. EUR"), is_umsatz (ein Flag, das die Umrechnung für Umsätze steuert, z.B. Rückgabe in Millionen).
  • Output: Ein String mit der normalisierten Zahl (z.B. "250") oder "k.A.".

API Wrappers & Externe Dienste

call_openai_chat(...)

  • Zweck: Eine zentrale Wrapper-Funktion für Aufrufe an die OpenAI Chat-API. Kapselt die Authentifizierung, die Fehlerbehandlung und den eigentlichen API-Aufruf.
  • Input: prompt (der an die KI gesendete Text), temperature (steuert die Kreativität der Antwort), model (das zu verwendende KI-Modell).
  • Output: Der von der KI generierte Antwort-Text als String.

summarize_website_content(raw_text, company_name)

  • Zweck: Nutzt die KI, um den Rohtext einer Website zu analysieren und eine strukturierte Zusammenfassung des Geschäftsmodells und des Potenzials für Field Service Management (FSM) zu erstellen.
  • Input: raw_text (der Inhalt der Website), company_name (Name des Unternehmens).
  • Output: Ein formatierter String, der das Geschäftsmodell, das FSM-Potenzial und Belegsätze enthält.

evaluate_branche_chatgpt(...)

  • Zweck: Führt eine KI-basierte Brancheneinstufung für ein einzelnes Unternehmen durch. Sendet ein Unternehmensprofil und ein vordefiniertes Branchenschema an die KI.
  • Input: company_name, website_summary, wiki_absatz.
  • Output: Ein Dictionary mit der vorgeschlagenen "Branche", "Konfidenz" und "Begruendung".

evaluate_branches_batch(companies_data)

  • Zweck: Führt die Brancheneinstufung für eine Liste von Unternehmen in einem einzigen API-Aufruf durch, um die Effizienz zu steigern.
  • Input: companies_data (eine Liste von Dictionaries, die Unternehmensprofile enthalten).
  • Output: Eine Liste von Dictionaries mit den Ergebnissen für jedes Unternehmen.

generate_fsm_pitch(...)

  • Zweck: Generiert einen hochpersonalisierten, einleitenden Satz für eine Marketing-E-Mail (FSM-Pitch), basierend auf den gesammelten Unternehmensdaten.
  • Input: Diverse Unternehmensdaten wie Name, Branche, Zusammenfassungen und Mitarbeiter-/Technikerzahlen.
  • Output: Ein einzelner, prägnanter Satz als String.

serp_website_lookup(company_name)

  • Zweck: Verwendet die SerpAPI (Google-Suche), um die offizielle Website eines Unternehmens zu finden. Filtert dabei unzuverlässige Quellen wie soziale Medien oder Nachrichtenportale heraus.
  • Input: company_name.
  • Output: Die normalisierte URL der gefundenen Website oder "k.A.".

search_linkedin_contacts(...)

  • Zweck: Führt eine gezielte Google-Suche über die SerpAPI durch, um LinkedIn-Profile von Mitarbeitern in bestimmten Positionen (z.B. "Serviceleiter") bei einem Unternehmen zu finden.
  • Input: company_name, website, position_query (z.B. "Leiter Kundendienst"), crm_kurzform.
  • Output: Eine Liste von Dictionaries, die die gefundenen Kontakte mit Namen, Position und LinkedIn-URL enthalten.

Website Scraping & Validierung

get_website_raw(url, ...)

  • Zweck: Lädt den reinen Textinhalt von einer Webseite. Die Funktion ist gehärtet, um mit verschiedenen Fehlern (SSL, Timeout, Connection Errors) umzugehen und versucht, Cookie-Banner intelligent zu entfernen.
  • Input: url (die zu scrapende URL).
  • Output: Der extrahierte Text der Website als String oder ein Fehlerhinweis (z.B. "k.A. (Timeout)").

is_valid_wikipedia_article_url(url)

  • Zweck: Überprüft, ob eine gegebene URL tatsächlich auf einen existierenden Wikipedia-Artikel verweist und nicht auf eine "Seite existiert nicht"-Seite.
  • Input: url (die zu prüfende Wikipedia-URL).
  • Output: True, wenn der Artikel existiert, andernfalls False.