Salta al contenuto

Come eseguire il web scraping su Yelp.com: la guida definitiva di 3000 parole per estrarre elenchi di attività commerciali, recensioni e altri dati

Yelp è una delle più grandi piattaforme di recensioni di crowdsourcing sul web. Con oltre 200 milioni di recensioni di ristoranti, bar, saloni, negozi e altre attività commerciali in oltre 30 paesi, contiene una miniera d'oro di dati per analisti, ricercatori, imprenditori e altro ancora.

Ma è possibile estrarre questi dati tramite web scraping? Assolutamente!

In questa guida completa di oltre 3000 parole, condividerò tutto ciò di cui hai bisogno per creare un web scraper in grado di estrarre enormi set di dati da Yelp utilizzando Python.

Ecco una breve descrizione di ciò che tratteremo:

  • Configurazione del nostro ambiente di web scraping Python
  • Trovare ed estrarre tutte le attività commerciali che corrispondono a una query di ricerca
  • Eliminazione di dettagli chiave come nome, indirizzo, numeri di telefono dalle pagine del profilo aziendale
  • Estrazione di tutte le recensioni per un'azienda, comprese valutazioni, dettagli utente, ecc.
  • Evitare il rilevamento dei bot tramite proxy, ritardi e altri trucchi

Quindi allacciatevi le cinture e cominciamo a raschiare!

Configurazione di un ambiente di web scraping Python

Prima di poter scaricare Yelp, dobbiamo configurare un ambiente Python con le dipendenze richieste.

Ci sono alcuni pacchetti chiave che dobbiamo installare:

Richieste – per inviare richieste HTTP ai server di Yelp

bellazuppa – per analizzare ed estrarre dati dalle pagine HTML di Yelp

Scrapy – (opzionale) una struttura per la costruzione di raschiatori

Consiglierei di creare un ambiente virtuale prima di installare questi:

python -m venv scraping-env
source scraping-env/bin/activate

Ora possiamo installare i pacchetti:

pip install requests beautifulsoup4 scrapy

Questo è tutto per le dipendenze. Abbiamo anche bisogno di intestazioni valide in modo che i server di Yelp pensino che le nostre richieste provengano da un browser reale:

headers = {
    "User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/70.0.3538.77 Safari/537.36"
}

La chiave è convincere User-Agent intestazione. Consiglierei di ruotare più user agent del browser per imitare ulteriormente il traffico reale.

E siamo pronti per iniziare a raschiare!

Trovare attività commerciali su Yelp

La nostra prima sfida è scoprire gli URL dei profili aziendali di Yelp da recuperare. Yelp non fornisce un'API pubblica o una mappa del sito su cui possiamo eseguire query a questo scopo.

Quindi dovremo decodificare la loro funzionalità di ricerca per trovare attività commerciali che corrispondono a un termine di ricerca o a una posizione.

Analizziamo una tipica query di ricerca:

https://www.yelp.com/search?find_desc=restaurants&find_loc=San+Francisco

Ciò restituisce un insieme impaginato di attività commerciali che corrispondono ai nostri criteri di ricerca. Ogni pagina contiene 10 elenchi di attività commerciali.

Per estrarre TUTTE le attività commerciali corrispondenti, dobbiamo:

  1. Recupera la prima pagina per ottenere il conteggio totale delle attività
  2. Scorrere tutte le pagine incrementando il file start parametro

Ecco come possiamo implementare questa logica di impaginazione in Python:

import requests
from urllib.parse import urlencode
from bs4 import BeautifulSoup

search_url = "https://www.yelp.com/search?"

params = {
  "find_desc": "restaurants",
  "find_loc": "San Francisco"  
}

search_url += urlencode(params)

print("Fetching first page")
first_page = requests.get(search_url, headers=headers)
soup = BeautifulSoup(first_page.content, "html.parser")

businesses = soup.select(".businessName") 
total = int(soup.select_one(".pagination-results-window").text.split()[0].replace(‘,‘, ‘‘))
print(f"Found {total} businesses")

# Calculate pages needed to cover all businesses
num_pages = math.ceil(total / 10)

print(f"Scraping {num_pages} pages...")

for page in range(0, num_pages):

  # Update start param 
  params["start"] = page * 10
  page_url = search_url + "&" + urlencode(params)

  # Fetch page
  print(f"Page {page+1}/{num_pages}")
  page = requests.get(page_url, headers=headers)

  # Extract businesses
  page_soup = BeautifulSoup(page.content, "html.parser")
  businesses.extend(page_soup.select(".businessName"))

print(f"Found {len(businesses)} businesses!")

Analizziamolo:

  • Iniziamo con l'URL di ricerca di base e i parametri di ricerca
  • Recupera la prima pagina per ottenere il conteggio totale delle attività
  • Calcola il numero di pagine necessarie per coprire tutte le attività
  • Scorri le pagine aggiornando il file start param
  • In ogni pagina, estrai elenchi di attività commerciali e aggiungili all'elenco principale

Nel mio test questo è stato estratto 6,000 elenchi di ristoranti a San Francisco – non male per 30 righe di Python!

Con alcune modifiche extra potresti trasformarlo in un business scraper di Yelp per un'intera città o paese.

Raschiare le pagine del profilo aziendale

Ora che possiamo scoprire gli URL dei profili aziendali, il nostro prossimo passo è visitare ciascuno di essi ed estrarre dettagli chiave come:

  • Nome
  • Indirizzo
  • Numero di telefono
  • Orari di apertura
  • Descrizione
  • Foto
  • E altre ancora...

Le pagine aziendali di Yelp vengono visualizzate in modo dinamico, ma l'HTML sottostante è abbastanza semplice da essere analizzato con BeautifulSoup.

Diamo un'occhiata a uno snippet di esempio:



<p>
  <strong>Phone:</strong> 
  415-387-2147
</p>

<p>
  <strong>Address:</strong>
  1345 9th Ave, San Francisco, CA 94122
</p>

<!-- And so on... -->

Possiamo estrarre ogni bit di informazione con alcuni selettori CSS ben posizionati:

from bs4 import BeautifulSoup
import requests

business_url = "https://www.yelp.com/biz/burma-superstar-san-francisco"

page = requests.get(business_url, headers=headers)
soup = BeautifulSoup(page.content, "html.parser")

name = soup.select_one("h1").text
phone = soup.find("strong", string="Phone:").next_sibling.strip() 
address = soup.find("strong", string="Address:").next_sibling.strip()

hours = {}
for day in soup.select(".day-hours"):
   day_name = day.select_one(".day-name").text
   hours[day_name] = day.select_one(".hours").text

print(name)
print(phone) 
print(address)
print(hours)

# Burma Superstar
# 415-387-2147
# 1345 9th Ave, San Francisco, CA 94122
# {‘Mon‘: ‘11:30am–3pm, 5–9:30pm‘, ‘Tue‘: ‘11:30am–3pm, 5–9:30pm‘...}

I punti chiave sono:

  • Usa il select_one per estrarre elementi singolari come nome, telefono ecc.
  • Per i dati nidificati come le ore, esegui il loop e crea un dizionario
  • Prefisso i selettori CSS con tag e classi per unicità

Con questi elementi costitutivi di scraping, possiamo estrarre dozzine di campi da ciascuna pagina del profilo in un dizionario Python strutturato o un oggetto JSON.

Alcuni altri campi che potresti prendere in considerazione per lo scraping includono:

  • Tag di categoria come "Messicano", "Brunch" ecc.
  • Tag di cucina come "Burger", "Sushi", "Caffè" ecc.
  • Misure di sicurezza COVID
  • Prezzo
  • quartiere
  • latitudine Longitudine
  • E altre ancora...

Essere creativi qui ti consente di creare ampi set di dati Yelp con centinaia di campi da analizzare se necessario.

Rimozione di recensioni dalle pagine aziendali di Yelp

Le recensioni sono il fiore all'occhiello dei dati di Yelp. Forniscono informazioni incredibili sul sentiment dei consumatori, sulle tendenze, sui dati demografici e altro ancora.

Sfortunatamente, le recensioni non vengono caricate direttamente nell'HTML. Vengono recuperati dinamicamente tramite chiamate JavaScript.

Dovremo intercettare e imitare queste richieste per estrarre i dati delle recensioni.

Apriamo una pagina aziendale e monitoriamo le richieste di rete negli strumenti del browser:

Yelp esamina la richiesta di rete

Aha – possiamo vedere che le recensioni vengono caricate da un URL come:

https://www.yelp.com/biz/{business_id}/reviews

Dove {business_id} è unico per ogni azienda. Possiamo estrarlo dall'HTML della pagina aziendale.

Le recensioni vengono impaginate tramite il file start parametro. Quindi seguiremo la stessa strategia di impaginazione:

  1. Recupera la prima pagina per ottenere il conteggio totale delle recensioni
  2. Scorrere tutte le pagine incrementando start

Ecco uno script per estrarre tutte le recensioni per un'azienda:

import json
import requests 

business_id = "WavvLdfdP6g8aZTtbBQHTw" # Extract this from HTML

review_url = f"https://www.yelp.com/biz/{business_id}/review_feed?rl=en&q=&sort_by=relevance_desc"

print("Fetching first page")
first_page = requests.get(review_url, headers=headers)
data = json.loads(first_page.text)

total = data["pagination"]["totalResults"]
print(f"Found {total} reviews")

reviews = data["reviews"]

for page in range(total//20 + 1): # 20 reviews per page

  print(f"Fetching page {page+1}/{math.ceil(total/20)}")
  next_page = f"{review_url}&start={page*20}"
  page_data = requests.get(next_page, headers=headers).json()

  reviews.extend(page_data["reviews"])

print(f"Scraped {len(reviews)} reviews!")

Boom! Ora disponiamo del corpus completo delle recensioni di un'azienda con dati quali:

{
   "id": "xAG4O7l-t1ubiIsO4cXMYg",
   "rating": 5,
   "user": {
      "id": "rpOyqD_893cqmDAtJLbdog",
      "profile_url": "https://www.yelp.com/user_details?userid=rpOyqD_893cqmDAtJLbdog",
      "name": "Sarah K.",
      "location": "Los Angeles, CA", 
      //...
   },
   "text": "This place is incredible! The sushi melts in your mouth and the...",
    //...
}

L'analisi di questi dati può fornire segnali forti sul sentiment dei clienti in base a località, dati demografici, tipi di cucina e altro ancora.

Evitare il rilevamento dei bot

Ora che abbiamo creato scraper per aziende e recensioni, è il momento di mettere tutto insieme.

Un problema: se iniziamo a intasare i server di Yelp con migliaia di richieste, verremo rapidamente bloccati.

Yelp utilizza sistemi avanzati di rilevamento dei bot per prevenire gli abusi, tra cui:

  • Limiti di utilizzo: limita la velocità con cui puoi richiedere le pagine
  • CAPTCHA: sfidano gli utenti a verificare che siano umani
  • Divieti IP: blocca gli indirizzi IP offensivi

Ecco alcuni suggerimenti per evitare blocchi durante lo scraping di Yelp su larga scala:

Usa i proxy

Instradando il traffico attraverso un ampio pool di IP residenziali, possiamo mascherare gli scraper ed evitare facili ban degli IP.

Ecco come utilizzare i proxy con il modulo Richieste:

from proxy_list import proxies 

# Rotate proxy per request
proxy = random.choice(proxies)

requests.get(url, headers=headers, proxies={"http": proxy, "https": proxy}) 

Consiglierei di avere una piscina almeno 10,000 proxy provenienti da diversi intervalli IP per essere sicuri.

Aggiungi ritardi casuali

L'aggiunta di vari ritardi tra le richieste aiuta a imitare il comportamento umano organico:

from random import randint

# Add random delay between 2s and 6s
time.sleep(randint(2, 6))

Punta a una media di secondi 3-5 tra le pagine. Qualsiasi velocità più veloce farà alzare le bandiere rosse.

Utilizza un browser senza testa

Per un maggiore anonimato, puoi utilizzare un browser headless come Selenium per eseguire il rendering di JavaScript e aggirare le protezioni.

Assicurati solo di modificare l'impronta digitale del browser e il proxy per sessione.

Risolvi i CAPTCHA con 2Captcha

Se colpisci un CAPTCHA, servizi come 2Captcha possono risolverli automaticamente per continuare lo scraping.

La maggior parte dei servizi addebita circa $ 2 per 1000 CAPTCHA risolti, il che vale la pena scalare grandi scraper.

Rispettare le limitazioni dell'account

Tieni d'occhio la pagina di stato del tuo account. Se il tuo tasso di scraping è troppo aggressivo, Yelp potrebbe imporre limiti di utilizzo temporanei.

Riduci le tue richieste e fai marcia indietro se gli errori indicano che ti stai avvicinando a una soglia di utilizzo.

Scraping Yelp: passaggi successivi

E questo copre le tecniche di base per lo scraping degli elenchi di attività commerciali, dei profili e delle recensioni di Yelp!

I dati che puoi estrarre aprono tantissime possibilità:

  • Analizzare il sentiment dei consumatori in base ai dati demografici
  • Tieni traccia delle tendenze e dei tipi di cucina emergenti
  • Costruisci modelli predittivi per i fattori di successo aziendale
  • Ottimizza il tuo SEO e la tua reputazione
  • Condurre ampie ricerche di mercato
  • Identificare le opportunità pubblicitarie

Ricorda solo di rispettare i Termini di servizio di Yelp, limitare il volume delle richieste ed evitare di estrarre dati privati ​​degli utenti.

Spero che questa guida ti sia stata utile! Sentiti libero di contattarci se hai altre domande.

Buona raschiatura!

Tag:

Partecipa alla conversazione

L'indirizzo email non verrà pubblicato. I campi obbligatori sono contrassegnati con *