Special offer. See more information about Outbyte and uninstall instructions. Please review EULA and Privacy policy.

Use Selenium to load the page in a real browser, wait for the specific content to become ready, locate its smallest meaningful container, and read only that element’s text or attributes. This avoids copying navigation, cookie notices, sidebars, and footers into your result. The complete pattern is: driver.get(), an explicit wait, a stable CSS or XPath locator, targeted extraction, and driver.quit() in a finally block.

The reliable extraction workflow

  1. Start a WebDriver session and navigate with driver.get(url).
  2. Identify the narrowest container representing the content: usually article, main article, a result card, or a stable ID/data attribute.
  3. Wait for that container, or for meaningful text inside it, instead of assuming the onload event means JavaScript work is finished.
  4. Read element.text and only the attributes you need.
  5. Handle frames, scrolling, and page variants deliberately.
  6. Always close the browser with driver.quit().

driver.get() waits for the browser’s onload event, but AJAX and other scripts can continue changing the DOM afterward. An explicit wait ties extraction to the state your scraper actually needs.

Complete Python example

Install Selenium with pip install selenium. Recent Selenium versions can manage a compatible Chrome driver automatically; otherwise install and configure the driver for your browser.

from selenium import webdriver
from selenium.webdriver.common.by import By
from selenium.webdriver.support.ui import WebDriverWait
from selenium.webdriver.support import expected_conditions as EC
from selenium.common.exceptions import TimeoutException, NoSuchElementException

url = "https://example.com/article"
driver = webdriver.Chrome()
driver.set_page_load_timeout(45)
driver.set_script_timeout(30)

try:
    driver.get(url)
    wait = WebDriverWait(driver, 15)  # polls every 500 ms by default

    article = wait.until(
        EC.visibility_of_element_located((By.CSS_SELECTOR, "article"))
    )
    text = article.text
    canonical = article.get_attribute("data-canonical-url")
    print(text)
    print("Canonical:", canonical)
except TimeoutException as exc:
    print(f"Timed out waiting for content at {url}: {exc}")
except NoSuchElementException as exc:
    print(f"Selector did not match this page variant: {exc}")
finally:
    driver.quit()

Use presence_of_element_located when the node only needs to exist, visibility_of_element_located when a user must be able to see it, and element_to_be_clickable before clicking. text_to_be_present_in_element is useful when a framework inserts the node immediately but fills it later.

Special offer. See more information about Outbyte and uninstall instructions. Please review EULA and Privacy policy.
#1 Best Overall
Elebase USB to USB C Adapter for iPhone 18 Pro Max,USBC Car Charger Adapter
  • Read Before You Buy — No Video Output: These adapters support charging and USB 2.0 data transfer, but cannot transmit video signals. Except for standard USB webcams (which use USB data only), they are not compatible with HDMI/DisplayPort cables, video-capable USB-C hubs, or docking stations with video output.
  • Convert USB-A Ports to USB-C: Designed to connect USB-C earphones, cables, flash drives, card readers, and other USB-C accessories to standard USB-A ports. Plug-and-play with no drivers or software required.
  • Aluminum Alloy Housing: Built with a sturdy aluminum alloy shell that aids in heat dissipation and protects against daily wear and scratches. Designed to maintain a stable and secure connection.
  • Compact & Travel-Friendly: The ultra-compact design allows the adapter to stay plugged into your device without blocking adjacent ports or adding bulk, reducing wear and tear on your original USB ports.
  • 12-Month Warranty: Backed by a 12-month manufacturer warranty for peace of mind. Designed to meet strict quality control standards for reliable everyday performance.

Choosing a selector that survives redesigns

Prefer, in order, a stable ID, a semantic element, a meaningful data attribute, or a short class-based CSS selector. Avoid selectors that encode every wrapper or depend on “the third div.” A redesign can preserve the article while changing its nesting.

containers = driver.find_elements(
    By.CSS_SELECTOR, "article, main, [role='main']"
)
for container in containers:
    print(container.text)

find_element returns the first match and raises NoSuchElementException when none exists. find_elements returns a list, which is appropriate for cards or repeated records. Validate that the selected node contains expected text; do not silently publish an empty result.

Text, links, and metadata

WebElement.text returns visible rendered text. Use get_attribute() for href, aria-label, datetime, data-* values, and other DOM properties.

title = article.find_element(By.CSS_SELECTOR, "h1").text
links = [a.get_attribute("href")
         for a in article.find_elements(By.CSS_SELECTOR, "a")]
published = article.find_element(
    By.CSS_SELECTOR, "time"
).get_attribute("datetime")

Rendered DOM versus page source

Extracting the selected element is normally more precise than dumping the entire document. Use driver.page_source for diagnostics or when handing the current DOM to another parser. For live markup or a computed value, execute JavaScript against the element:

What’s actually slowing this PC down?

Pick the symptom - the matching free tool is one click away.

Special offer. See more information about Outbyte and uninstall instructions. Please review EULA and Privacy policy.
Rank #2
Anker USB-C Hub, 5-in-1 USB Hub for Laptops, 4K HDMI Multiport Adapter
  • 5-in-1 USB-C Hub: Experience comprehensive connectivity featuring a Power Delivery input, two USB-A 2.0 ports, a USB-A 3.0 port, and an HDMI port. (Note: The USB-C power delivery input port is only for connecting an external wall charger to power your laptop and cannot power peripheral devices.)
  • 90W Pass-Through Charging: Achieve optimal charging with 90W pass-through power to your laptop, supported by a total input of 100W, with the hub reserving 10W for operational efficiency. (Note: Wall charger not included.)
  • Quick Data Transfers: Accelerate your productivity with rapid data transfers using a high-speed 5Gbps USB 3.0 port and two 480Mbps USB 2.0 ports.
  • 4K HDMI Display: Enhance your visual experience with a hub capable of delivering 4K resolution at 30Hz in both mirror and extend modes. Please note that this hub is compatible with MacBook (macOS 12 and newer), Windows 10 and 11, ChromeOS, and laptops equipped with DP Alt Mode and Power Delivery. Note: This device is not compatible with Linux.
  • What You Get: Anker USB-C Hub (5-in-1, 4K HDMI), welcome guide, 18-month warranty, and our friendly customer service.
html = driver.execute_script(
    "return arguments[0].outerHTML;", article
)
canonical = driver.execute_script(
    "return arguments[0].querySelector('link[rel=canonical]')?.href;",
    article,
)

These operations inspect the browser’s current DOM, including changes made by JavaScript, rather than only the original HTTP response.

Waiting for JavaScript content

Do not use time.sleep() as your only synchronization method. A fixed delay is too short on a slow response and wasteful on a fast one. Use a bounded condition tied to the content:

wait.until(EC.presence_of_element_located(
    (By.CSS_SELECTOR, "main article")
))
wait.until(EC.text_to_be_present_in_element(
    (By.ID, "results"), "Published"
))

Keep waits explicit and local to the operation that needs them. A global implicit wait changes the behavior of every lookup and can make failures slow and difficult to diagnose. If a page has a loading indicator, wait for it to disappear or for a result count to increase.

iframes: switch context before locating content

Elements inside an iframe do not belong to the top-level document’s search context. Locate and enter the frame, extract the content, then return to the default document:

Special offer. See more information about Outbyte and uninstall instructions. Please review EULA and Privacy policy.
Rank #3
Sale
Anker USB C Hub, 7in1 Multi-Port USB Adapter, 4K@60Hz USBC to HDMI Splitter
  • Sleek 7-in-1 USB-C Hub: Features an HDMI port, two USB-A 3.0 ports, and a USB-C data port, each providing 5Gbps transfer speeds. It also includes a USB-C PD input port for charging up to 100W and dual SD and TF card slots, all in a compact design.
  • Flawless 4K@60Hz Video with HDMI: Delivers exceptional clarity and smoothness with its 4K@60Hz HDMI port, making it ideal for high-definition presentations and entertainment. (Note: Only the HDMI port supports video projection; the USB-C port is for data transfer only.)
  • Double Up on Efficiency: The two USB-A 3.0 ports and a USB-C port support a fast 5Gbps data rate, significantly boosting your transfer speeds and improving productivity.
  • Fast and Reliable 85W Charging: Offers high-capacity, speedy charging for laptops up to 85W, so you spend less time tethered to an outlet and more time being productive.
  • What You Get: Anker USB-C Hub (7-in-1), welcome guide, 18-month warranty, and our friendly customer service.
frame = wait.until(EC.presence_of_element_located(
    (By.CSS_SELECTOR, "iframe")
))
driver.switch_to.frame(frame)
try:
    body = wait.until(EC.visibility_of_element_located(
        (By.CSS_SELECTOR, "article")
    ))
    text = body.text
finally:
    driver.switch_to.default_content()

If the frame is replaced during loading, reacquire it and switch again. Cross-origin policy still applies to what page scripts can do, but WebDriver can interact with a frame through its browsing context when the browser permits it.

Infinite scroll and lazy-loaded records

One get() call does not guarantee that an infinite-scroll page has loaded every record. Scroll in bounded steps and wait for a measurable change, such as item count:

previous = 0
for _ in range(10):
    items = driver.find_elements(By.CSS_SELECTOR, "article.card")
    if len(items) == previous:
        break
    previous = len(items)
    driver.execute_script("window.scrollTo(0, document.body.scrollHeight);")
    wait.until(lambda d: len(d.find_elements(
        By.CSS_SELECTOR, "article.card"
    )) > previous or d.execute_script(
        "return document.querySelector('.loading') === null"
    ))

Set a maximum number of iterations or a time budget. Otherwise a page that continually appends content can keep your job running forever.

Common failures and fixes

Symptom Likely cause Fix
TimeoutException The selector is wrong, content is slow, or a bot check changed the page. Save the URL and selector, inspect the rendered page, choose a readiness condition, and adjust the bounded timeout.
NoSuchElementException Markup differs by locale, device, login state, or page type. Support known variants with stable selectors and fail loudly when none matches.
Text is empty The node exists but is hidden, still loading, or content is inside a frame. Wait for visibility or expected text, then check frame context.
Stale element error JavaScript replaced the node after you located it. Wait for the update to finish and locate the element again; do not reuse the old reference.
Only the first records appear Lazy loading or infinite scroll has not been triggered. Scroll in bounded steps and wait for item count or loading-state changes.
Browser process remains after failure quit() was not reached. Put cleanup in finally, including around frame switches and extraction code.

When Selenium is the right tool

Selenium is appropriate when the required content depends on JavaScript, clicks, login state, scrolling, a rendered layout, or another browser interaction. If the needed HTML is already present in the HTTP response, a direct HTTP client and parser are usually simpler and cheaper. Narrow semantic selectors improve precision, while extremely specific selectors are fragile. A local WebDriver suits occasional jobs; parallel or long-running workloads may need remote or hosted browsers.

Free tools Windows power users keep installed

One-click scans. No signup required.

Special offer. See more information about Outbyte and uninstall instructions. Please review EULA and Privacy policy.
Rank #4
Sale
UGREEN USB to USB C Adapter Combo 4-Pack, 10Gbps USB C Converter Space Gray
  • Dual Converters, Infinite Potential:Includes 2× USB C male to USB A female adapters and 2× USB A male to USB C female adapters. Perfect for a wide range of uses—tablets with Bluetooth keyboards, expand USB ports on macbook, and more. Two different converters for all your daily needs
  • Next-Level 10Gbps & 3A Charging: No more slow 480Mbps, this usb to usb c adapter has a transfer speed of up to 10Gbps, allowing you to do more transferring in less time. This usb adapter fits both USB A and USB C charger, supporting up to 3A fast charging
  • Upgraded Exquisite Craftsmanship: With an aluminum alloy housing and metal connector, the usbc to usb adapter is extremely durable and sturdy. Rigorously tested to withstand more than 10,000 times of plugging and unplugging, ensuring long-lasting performance
  • Broad Compatible: The usb c to usb adapter widely supports all USB C/ USB A devices like laptops, tablets, cellphones, car chargers, and phone chargers. Such as compatible with MacBook Pro/Air 2023/2022, Thunderbolt 4/3 Devices,Apple MagSafe Watch 9/8/7/SE/Ultra, iPad Pro 2022/2021, Samsung Galaxy S23/S20/S10, and iPhone 17/16/15 Pro. Plug and play
  • Please Note: To reach 10Gbps speed, keep the cable under 3.3 ft. For USB A Male to USB C adapters, try flipping the USB C connector. USB C Male to USB A adapters support bidirectional 10Gbps transfer within 3.3 ft
Independent reader supportYour contribution helps us test, update, and keep practical guides available for everyone.Support on Ko-Fi

Or skip the browser setup

ScreenshotNeo provides a website screenshot API and MCP server when you need a rendered page image or PDF rather than writing browser orchestration yourself. A single request returns PNG, JPEG, WebP, or PDF. Before capture it accepts cookie/consent banners and removes more than 60 known consent platforms, newsletter popups, and chat widgets; each cleanup step can be disabled. Bot checks, CAPTCHAs, blank pages, timeouts, failed loads, and cache hits are not billed, and response headers report the page verdict and billing status.

Use the API documentation at https://screenshotneo.com/docs/ for the full option set, including full-page lazy-image loading, CSS-selector element capture, dark mode, device presets and custom viewports, retina scale, PDF paper size/margins/landscape/page ranges, HTML/CSS rendering, custom JavaScript, clicks, selector hiding, selector/delay/network-idle waits, request blocking, headers/cookies/user agents/Authorization, timezone and geolocation, transparent backgrounds, resizing, chosen-TTL caching, signed image links, asynchronous jobs with signed webhooks, bulk capture of 100 URLs per call, usage reporting, and OpenAPI compatibility. Its parameter names also support migration from other screenshot APIs.

One-call examples

curl -G "https://api.screenshotneo.com/v1/shot" 
  -d access_key=YOUR_API_KEY 
  --data-urlencode url=https://stripe.com 
  -o shot.webp
import requests
r = requests.get(
    "https://api.screenshotneo.com/v1/shot",
    params={"access_key": "YOUR_API_KEY", "url": "https://stripe.com"},
    timeout=90,
)
r.raise_for_status()
open("shot.webp", "wb").write(r.content)
const q = new URLSearchParams({
  access_key: 'YOUR_API_KEY', url: 'https://stripe.com'
});
const res = await fetch(`https://api.screenshotneo.com/v1/shot?${q}`);

The Free plan includes 1,000 screenshots per month with no card. Paid plans start at $5 for 3,000 shots; every feature is available on every plan. ScreenshotNeo also offers an MCP server with take_screenshot, get_page_info, and capture_pdf for Claude, Cursor, and other MCP clients. Create a free ScreenshotNeo account to start.

FAQ

Should I extract page_source or element.text?

Use element.text for visible content and selected attributes for metadata. Reserve page_source for diagnostics or a downstream parser that genuinely needs the complete rendered DOM.

Special offer. See more information about Outbyte and uninstall instructions. Please review EULA and Privacy policy.

How long should an explicit wait be?

Choose a bounded timeout that fits the site’s normal response time, then wait for a meaningful condition. Increase it only after confirming the selector and page state are correct; a longer timeout cannot fix a wrong locator.

Best Value
Anker USB C Hub, 5-in-1 USBC to HDMI Splitter with 4K Display
  • 5-in-1 Connectivity: Equipped with a 4K HDMI port, a 5 Gbps USB-C data port, two 5 Gbps USB-A ports, and a USB C 100W PD-IN port. Note: The USB C 100W PD-IN port supports only charging and does not support data transfer devices such as headphones or speakers.
  • Powerful Pass-Through Charging: Supports up to 85W pass-through charging so you can power up your laptop while you use the hub. Note: Pass-through charging requires a charger (not included). Note: To achieve full power for iPad, we recommend using a 45W wall charger.
  • Transfer Files in Seconds: Move files to and from your laptop at speeds of up to 5 Gbps via the USB-C and USB-A data ports. Note: The USB C 5Gbps Data port does not support video output.
  • HD Display: Connect to the HDMI port to stream or mirror content to an external monitor in resolutions of up to 4K@30Hz. Note: The USB-C ports do not support video output.
  • What You Get: Anker 332 USB-C Hub (5-in-1), welcome guide, our worry-free 18-month warranty, and friendly customer service.

Why does a selector work manually but fail in automation?

Automation may receive a different locale, login state, viewport, bot-check page, or iframe context. Capture the rendered URL and inspect the DOM at failure before changing the selector.

Frequently Asked Questions

Can Selenium extract content loaded after scrolling?

Yes. Scroll in bounded steps and wait for an observable change such as a larger item count or a finished loading indicator, then collect the matching elements.

How do I avoid publishing an empty scrape?

Require the expected container and, where practical, a meaningful text condition; treat timeout and missing-element exceptions as failures rather than returning an empty string.

Special offer. See more information about Outbyte and uninstall instructions. Please review EULA and Privacy policy.

Product prices and availability are accurate as of the date/time indicated and are subject to change. Any price and availability information displayed on Amazon at the time of purchase will apply.