Meteen naar de inhoud

Hoe XPath-selectors te gebruiken voor webscraping in Python

  • by
  • Blog
  • 8 min gelezen

Als u gegevens uit webpagina's wilt extraheren met Python, is XPath een essentiële tool die u in uw webscraping-toolkit moet hebben. XPath biedt een manier om door de HTML-structuur van een pagina te navigeren en de exacte elementen en gegevens te lokaliseren die u nodig heeft.

In deze handleiding lopen we door de basisprincipes van XPath en laten we zien hoe u de kracht ervan kunt benutten voor webscrapen met Python. Tegen het einde ben je klaar om een ​​breed scala aan scraptaken uit te voeren met behulp van XPath om de gegevens die je zoekt operatief te extraheren.

Wat is XPath?

XPath staat voor XML Path Language. Het is een querytaal voor het selecteren van knooppunten uit een XML- of HTML-document. Met XPath specificeert u een patroon dat overeenkomt met de documentstructuur, en het retourneert alle elementen die met dat patroon overeenkomen.

Hoewel oorspronkelijk ontworpen voor XML, werkt XPath net zo goed met HTML, waardoor het ideaal is voor webscraping. Het biedt een krachtiger en flexibeler alternatief voor CSS-selectors of reguliere expressies.

Basisprincipes van XPath-syntaxis

Om XPath te kunnen gebruiken, moet u de bouwstenen van de XPath-syntaxis begrijpen. Dit zijn de belangrijkste concepten:

Knooppunten selecteren op tagnaam

De meest elementaire XPath-expressie is het eenvoudigweg opgeven van een tagnaam. Bijvoorbeeld:

  • //h1 selecteert alle <h1> kopelementen op de pagina
  • //p selecteert alle <p> alinea-elementen
  • //img selecteert alle <img> beeldelementen

Knooppunten selecteren op attribuut

U kunt elementen selecteren die een specifiek attribuut of attribuutwaarde hebben met behulp van @ syntaxis:

  • //*[@class="highlighted"] selecteert alle elementen die de klasse "gemarkeerd" hebben
  • //a[@href] selecteert alles <a> ankerelementen die een href-attribuut hebben
  • //img[@alt="Logo"] selecteert <img> elementen met een alt-tekst van "Logo"

Knopen selecteren op positie

U kunt knooppunten selecteren op basis van hun positie met behulp van vierkante haken [] en een numerieke index:

  • //ul/li[1] selecteert de eerste <li> item binnen elk <ul> ongeordende lijst
  • //table/tr[last()] selecteert de laatste <tr> rij in elk <table>
  • //ol/li[position() <= 3] selecteert de eerste drie <li> artikelen in elk <ol> bestelde lijst

Knooppunten selecteren op relatie

Met XPath kunt u op en neer door de documentboom navigeren om elementen te selecteren op basis van hun voorouders, nakomelingen, broers en zussen, enz.:

  • //div[@class="content"]/* selecteert alle onderliggende elementen van <div> elementen met klasse "inhoud"
  • //p/.. selecteert de bovenliggende elementen van allemaal <p> paragrafen
  • //h1/following-sibling::p selecteert alles <p> elementen die broers en zussen zijn na een <h1> rubriek
  • //section//img selecteert alles <img> elementen die afstammen van a <section> op elk niveau

Predikaten en functies

XPath ondersteunt een breed scala aan predicaten en functies om uw selecties verder te verfijnen:

  • //p[contains(text(),"scrapy")] selecteert <p> elementen die de tekst "scrapy" bevatten
  • //a[starts-with(@href,"https")] selecteert <a> elementen waarbij de href begint met "https"
  • //ul[count(li) > 10] selecteert <ul> elementen die meer dan 10 bevatten <li> artikelen
  • //img[string-length(@alt) > 0] selecteert <img> elementen met een niet-leeg alt-attribuut

XPath gebruiken met lxml en BeautifulSoup

Nu u de basisbeginselen van de XPath-syntaxis begrijpt, gaan we kijken hoe u deze in Python kunt gebruiken met de populaire lxml- en BeautifulSoup-bibliotheken. We zullen een voorbeeld bekijken van het schrapen van de hoofdkoptekst van de ScrapingBee-startpagina.

HTML parseren met lxml en BeautifulSoup

Eerst moeten we de HTML van de webpagina ophalen met behulp van de verzoekenbibliotheek en deze parseren in een boomstructuur die we kunnen opvragen met XPath. We zullen BeautifulSoup gebruiken om de HTML en lxml te parseren om onze XPath-expressies te evalueren:

import requests
from bs4 import BeautifulSoup
from lxml import etree

html = requests.get("https://scrapingbee.com") 
soup = BeautifulSoup(html.text, "html.parser")
dom = etree.HTML(str(soup))

Hier Wij:

  1. Haal de HTML op met requests.get()
  2. Parseer de HTML-tekenreeks in een BeautifulSoup-object met behulp van html.parser
  3. Converteer het BeautifulSoup-object naar een string, zodat we het kunnen parseren met lxml's etree.HTML() functie
  4. Parseer de tekenreeks in een lxml Element object dat we kunnen opvragen met XPath

XPath-expressies construeren en evalueren

Nu we een geparseerde HTML-boom hebben, kunnen we een XPath-expressie construeren om de hoofdstructuur te selecteren <h1> kop op de pagina:

heading_xpath = ‘//h1‘

Om dit XPath te evalueren aan de hand van ons geparseerde HTML-document, gebruiken we de xpath() methode:

heading_elements = dom.xpath(heading_xpath)

De dom.xpath() call retourneert een lijst met alle elementen die overeenkomen met onze XPath-selector. In dit geval zou er slechts één matching moeten zijn <h1> element.

Tekst en attributen extraheren

Zodra we een verwijzing naar het element hebben, kunnen we eenvoudig de tekst en eventuele attributen extraheren met behulp van de eigenschappen van lxml:

heading_text = heading_elements[0].text
print(heading_text)
# Tired of getting blocked while scraping the web?  

We hebben de koptekst met succes geëxtraheerd met slechts één regel XPath! We kunnen ook toegang krijgen tot attribuutwaarden van het element met behulp van get():

heading_id = heading_elements[0].get(‘id‘)  

XPath gebruiken met Selenium

Een alternatieve benadering is om Selenium te gebruiken voor het automatiseren en schrapen van dynamische websites die JavaScript vereisen. Selenium biedt zijn eigen methoden voor het selecteren van elementen met behulp van XPath-reeksen.

Selenium WebDriver configureren

Om aan de slag te gaan met Selenium moet je eerst het Selenium-pakket en een webdriver installeren voor de browser die je wilt gebruiken. Zo kunt u een Chrome-stuurprogramma configureren:

from selenium import webdriver
from selenium.webdriver.common.by import By

driver_path = "/path/to/chromedriver"  
driver = webdriver.Chrome(driver_path)

Zorg ervoor dat u de juiste ChromeDriver-versie voor uw Chrome-installatie downloadt en het pad naar het uitvoerbare bestand opgeeft.

Elementen zoeken met XPath

Als het stuurprogramma is geconfigureerd, kunnen we naar een webpagina navigeren en elementen gaan zoeken. Selenium's WebDriver biedt een find_element methode die een XPath-locator accepteert:

driver.get("https://scrapingbee.com")

heading_xpath = "//h1"
heading_element = driver.find_element(By.XPATH, heading_xpath)

Vergelijkbaar met het lxml-voorbeeld, zal dit de eerste vinden <h1> element op de pagina. Als u alle elementen wilt vinden die overeenkomen met een XPath, gebruikt u find_elements in plaats daarvan:

paragraph_xpath = "//p"
paragraph_elements = driver.find_elements(By.XPATH, paragraph_xpath)  

Tekst en attributen extraheren

Zodra u een verwijzing naar een webelement heeft, heeft u toegang tot de eigenschappen ervan, zoals tekstinhoud en attributen:

heading_text = heading_element.text
print(heading_text)  
# Tired of getting blocked while scraping the web?

paragraph_id = paragraph_elements[0].get_attribute("id")

Gegevens extraheren met Selenium en XPath is vrij eenvoudig, maar houd er rekening mee dat Selenium over het algemeen langzamer is dan het gebruik van een gewone HTTP-verzoekbibliotheek, omdat er een echte browser op draait.

Tips en best practices

Als u XPath gaat gebruiken voor webscrapen, volgen hier enkele tips en trucs waarmee u rekening moet houden:

Gebruik Chrome DevTools om XPath-expressies te testen

Bij het bouwen van XPath-selectors is het erg handig om ze interactief uit te testen om er zeker van te zijn dat ze overeenkomen met wat u verwacht. De Chrome DevTools bieden een eenvoudige manier om dit te doen:

  1. Klik met de rechtermuisknop op een element en selecteer "Inspecteren" om het paneel DevTools Elements te openen
  2. Druk op Ctrl+F om het zoekvak te openen
  3. Voer uw XPath-expressie in om overeenkomende elementen op de pagina te markeren

Omgaan met inconsistente markeringen

Websites in het wild hebben vaak inconsistente of kapotte HTML-opmaak waardoor uw XPath-selectors kunnen struikelen. Het is een goed idee om een ​​bibliotheek zoals BeautifulSoup te gebruiken om de HTML op te schonen en te normaliseren voordat deze met lxml wordt geparseerd.

Schrijf robuuste en onderhoudbare XPath

Om de kans te verkleinen dat uw scraper kapot gaat als gevolg van wijzigingen in de lay-out op de doelsite, probeert u XPath-expressies te schrijven die zo specifiek mogelijk zijn, maar niet specifieker dan nodig. Geef de voorkeur aan selecteren op semantische eigenschappen, zoals tagnamen, ID's en gegevensattributen, in plaats van te vertrouwen op de specifieke structuur van de markup.

Het is ook een goed idee om complexe XPath-expressies op te splitsen in variabelen met beschrijvende namen om de leesbaarheid en onderhoudbaarheid te verbeteren.

Cacheresultaten om de prestaties te verbeteren

Als u grote hoeveelheden gegevens verzamelt of meerdere keren dezelfde pagina's bezoekt, kunt u overwegen de geparseerde HTML- en XPath-resultaten in de cache op te slaan om onnodige netwerkverzoeken en parseringsoverhead te voorkomen. U kunt een eenvoudig woordenboek of een robuustere oplossing zoals MongoDB of Redis gebruiken voor caching.

Conclusie

XPath is een ongelooflijk krachtig hulpmiddel voor het nauwkeurig extraheren van gegevens uit HTML-pagina's. Met een basiskennis van de syntaxis en de mogelijkheid om CSS-selectors te vertalen naar hun XPath-equivalenten, kunt u een breed scala aan webscraping-taken aan.

Python-bibliotheken zoals lxml, BeautifulSoup en Selenium bieden eenvoudige manieren om XPath te integreren in uw scraping-workflows. Afhankelijk van uw specifieke behoeften en de kenmerken van de doelsite, kunt u de aanpak kiezen die het beste werkt.

Terwijl u uw webscraping-reis voortzet met Python en XPath, moet u er altijd voor zorgen dat u de servicevoorwaarden van de website en de robots.txt-beperkingen respecteert. En vergeet niet om de basisprincipes van XPath-functies en -operatoren op te frissen. U zult versteld staan ​​hoeveel u kunt bereiken met slechts een paar regels slimme XPath!

Doe mee aan het gesprek

Uw e-mailadres wordt niet gepubliceerd. Verplichte velden zijn gemarkeerd *