How to select elements by text in XPath?

You can select elements by text in XPath by using the contains(text(), "Text string") or text()="Text string" expression.

The first expression will match any element that contains the "Text string" sub-string. However, the second expression will match only those elements that contain this exact string.

Here is some sample code for using lxml, BeautifulSoup, and Requests for opening up the ScrapingBee homepage and extracting the text from h1 tag using the text-based XPath selector:

import requests
from lxml import etree
from bs4 import BeautifulSoup

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

# Here we are doing a `contains` match 
match_using_text = dom.xpath('//*[contains(text(), "Tired")]')[0].text
print(match_using_text)
# Output: Tired of getting blocked while scraping the web?

# Here we are doing an exact match so it will fail
match_using_exact_text = dom.xpath('//*[text()="Tired"]')
print(len(match_using_exact_text))
# Output: 0

Here is some sample code for doing the same with Selenium:

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

DRIVER_PATH = '/path/to/chromedriver'
driver = webdriver.Chrome(executable_path=DRIVER_PATH)

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

# Here we are doing a `contains` match 
match_using_text = driver.find_element(By.XPATH, "//*[contains(text(), 'Tired')]")
print(match_using_text.text)
# Output: Tired of getting blocked while scraping the web?

# Here we are doing an exact match so it will fail
match_using_exact_text = driver.find_element(By.XPATH, "//*[text()='Tired']")
# Will raise NoSuchElementException

Related XPath web scraping questions: