bugfix
This commit is contained in:
@@ -1567,6 +1567,123 @@ def count_linkedin_contacts(company_name, website, position_query, crm_kurzform)
|
||||
debug_print(f"Fehler bei der SerpAPI-Suche (Count): {e}")
|
||||
return 0
|
||||
|
||||
def search_linkedin_contact(company_name, website, position_query, crm_kurzform):
|
||||
"""
|
||||
Sucht über SERPAPI einen einzelnen LinkedIn-Kontakt basierend auf der Positionsbezeichnung und der CRM-Kurzform des Unternehmens.
|
||||
Es wird nur ein Treffer zurückgegeben, wenn der Titel auch die CRM-Kurzform (als Teilstring) enthält.
|
||||
|
||||
Args:
|
||||
company_name (str): Der Firmenname.
|
||||
website (str): Die Website des Unternehmens.
|
||||
position_query (str): Die zu suchende Positionsbezeichnung (z. B. "Serviceleiter").
|
||||
crm_kurzform (str): Die manuell gepflegte Kurzform des Firmennamens.
|
||||
|
||||
Returns:
|
||||
dict oder None: Ein Dictionary mit den Kontaktdaten (Vorname, Nachname, Position, LinkedInURL) oder None, falls kein passender Kontakt gefunden wurde.
|
||||
"""
|
||||
try:
|
||||
with open("serpApiKey.txt", "r") as f:
|
||||
serp_key = f.read().strip()
|
||||
except Exception as e:
|
||||
debug_print("Fehler beim Lesen des SerpAPI-Schlüssels: " + str(e))
|
||||
return None
|
||||
|
||||
query = f'site:linkedin.com/in "{position_query}" "{company_name}"'
|
||||
params = {
|
||||
"engine": "google",
|
||||
"q": query,
|
||||
"api_key": serp_key,
|
||||
"hl": "de"
|
||||
}
|
||||
try:
|
||||
response = requests.get("https://serpapi.com/search", params=params, timeout=10)
|
||||
data = response.json()
|
||||
if "organic_results" in data and len(data["organic_results"]) > 0:
|
||||
# Gehe die Ergebnisse durch und prüfe, ob der Titel den crm_kurzform-String enthält
|
||||
for result in data["organic_results"]:
|
||||
title = result.get("title", "")
|
||||
if crm_kurzform.lower() in title.lower():
|
||||
# Aufteilen des Titels in Namens- und Positionsbestandteile
|
||||
if "–" in title:
|
||||
parts = title.split("–")
|
||||
elif "-" in title:
|
||||
parts = title.split("-")
|
||||
else:
|
||||
parts = [title]
|
||||
if len(parts) >= 2:
|
||||
name_part = parts[0].strip()
|
||||
pos_part = parts[1].split("|")[0].strip()
|
||||
name_parts = name_part.split(" ", 1)
|
||||
if len(name_parts) == 2:
|
||||
firstname, lastname = name_parts
|
||||
else:
|
||||
firstname = name_part
|
||||
lastname = ""
|
||||
linkedin_url = result.get("link", "") # LinkedIn-Profil-Link aus dem Ergebnis
|
||||
debug_print(f"Gefundener Kontakt: {firstname} {lastname}, Position: {pos_part}")
|
||||
return {
|
||||
"Firmenname": company_name,
|
||||
"Website": website,
|
||||
"Vorname": firstname,
|
||||
"Nachname": lastname,
|
||||
"Position": pos_part,
|
||||
"LinkedInURL": linkedin_url
|
||||
}
|
||||
debug_print("Kein Treffer mit CRM-Kurzform in Titel gefunden.")
|
||||
return None
|
||||
else:
|
||||
debug_print("Keine organic_results für Query gefunden.")
|
||||
return None
|
||||
except Exception as e:
|
||||
debug_print(f"Fehler bei der SerpAPI-Suche: {e}")
|
||||
return None
|
||||
|
||||
def count_linkedin_contacts(company_name, website, position_query, crm_kurzform):
|
||||
"""
|
||||
Zählt über SERPAPI, wieviele LinkedIn-Kontakte für einen bestimmten Positionsbegriff existieren,
|
||||
wobei als Filter zusätzlich geprüft wird, ob der Titel Teile der CRM-Kurzform enthält.
|
||||
|
||||
Args:
|
||||
company_name (str): Firmenname.
|
||||
website (str): Website des Unternehmens.
|
||||
position_query (str): Gewünschte Position (z. B. "Serviceleiter").
|
||||
crm_kurzform (str): Kurzform des Firmennamens.
|
||||
|
||||
Returns:
|
||||
int: Anzahl der Treffer, die den Filter erfüllen.
|
||||
"""
|
||||
try:
|
||||
with open("serpApiKey.txt", "r") as f:
|
||||
serp_key = f.read().strip()
|
||||
except Exception as e:
|
||||
debug_print("Fehler beim Lesen des SerpAPI-Schlüssels: " + str(e))
|
||||
return 0
|
||||
|
||||
query = f'site:linkedin.com/in "{position_query}" "{company_name}"'
|
||||
params = {
|
||||
"engine": "google",
|
||||
"q": query,
|
||||
"api_key": serp_key,
|
||||
"hl": "de"
|
||||
}
|
||||
try:
|
||||
response = requests.get("https://serpapi.com/search", params=params, timeout=10)
|
||||
data = response.json()
|
||||
count = 0
|
||||
if "organic_results" in data:
|
||||
for result in data["organic_results"]:
|
||||
title = result.get("title", "")
|
||||
if crm_kurzform.lower() in title.lower():
|
||||
count += 1
|
||||
debug_print(f"Anzahl Kontakte für Query '{query}' mit CRM-Kurzform-Filter: {count}")
|
||||
return count
|
||||
else:
|
||||
debug_print(f"Keine Ergebnisse für Query: {query}")
|
||||
return 0
|
||||
except Exception as e:
|
||||
debug_print(f"Fehler bei der SerpAPI-Suche (Count): {e}")
|
||||
return 0
|
||||
|
||||
def process_contact_research():
|
||||
"""
|
||||
Sucht mithilfe der SerpAPI Kontakte für bestimmte Positionen für jedes Unternehmen.
|
||||
@@ -1598,14 +1715,15 @@ def process_contact_research():
|
||||
debug_print("Keine neuen Zeilen zu verarbeiten, da Timestamp in Spalte AM bereits bis zum Ende vorhanden ist.")
|
||||
return
|
||||
|
||||
# Versuche, das Kontakte-Tabellenblatt zu öffnen; falls nicht vorhanden, erstelle es
|
||||
# Versuche, das Kontakte-Blatt zu öffnen; falls nicht vorhanden, erstelle es
|
||||
try:
|
||||
contacts_sheet = sh.worksheet("Contacts")
|
||||
except gspread.exceptions.WorksheetNotFound:
|
||||
contacts_sheet = sh.add_worksheet(title="Contacts", rows="1000", cols="10")
|
||||
# Header um eine zusätzliche Spalte für Suchbegriffskategorie erweitert
|
||||
header = ["Firmenname", "CRM Kurzform", "Website", "Vorname", "Nachname", "Position", "Suchbegriffskategorie", "Timestamp"]
|
||||
contacts_sheet.update(values=[header], range_name="A1:H1")
|
||||
# Header um eine zusätzliche Spalte für Suchbegriffskategorie, LinkedIn-Link und Timestamp angepasst
|
||||
header = ["Firmenname", "CRM Kurzform", "Website", "Vorname", "Nachname", "Position",
|
||||
"Suchbegriffskategorie", "LinkedIn-Link", "Timestamp"]
|
||||
contacts_sheet.update(values=[header], range_name="A1:I1")
|
||||
debug_print("Neues Blatt 'Contacts' erstellt und Header eingetragen.")
|
||||
|
||||
# Verarbeite jede Zeile im Hauptblatt ab der festgelegten Startzeile
|
||||
@@ -1627,7 +1745,8 @@ def process_contact_research():
|
||||
# Suche und speichere den ersten passenden Kontakt
|
||||
contact = search_linkedin_contact(crm_kurzform, website, pos, crm_kurzform)
|
||||
if contact:
|
||||
# Hänge den Kontakt im Kontakte-Blatt an; hier wird in Spalte G der Suchbegriff und in Spalte H der Timestamp eingetragen
|
||||
# In Spalte G wird der Suchbegriff (Kategorie) eingetragen,
|
||||
# in Spalte H der LinkedIn-Link und in Spalte I der Timestamp.
|
||||
timestamp = datetime.now().strftime("%Y-%m-%d %H:%M:%S")
|
||||
contact_row = [
|
||||
company_name,
|
||||
@@ -1636,8 +1755,9 @@ def process_contact_research():
|
||||
contact.get("Vorname", ""),
|
||||
contact.get("Nachname", ""),
|
||||
contact.get("Position", ""),
|
||||
pos, # Suchbegriffskategorie
|
||||
timestamp # Timestamp
|
||||
pos, # Suchbegriffskategorie in Spalte G
|
||||
contact.get("LinkedInURL", ""), # LinkedIn-Link in Spalte H
|
||||
timestamp # Timestamp in Spalte I
|
||||
]
|
||||
try:
|
||||
contacts_sheet.append_row(contact_row)
|
||||
|
||||
Reference in New Issue
Block a user