E-commerce

Extract a JavaScript-Rendered Product Page

This real-world example shows how to extract product content from a JavaScript-rendered e-commerce page using the Scraper API.

We will use the ScrapingCourse JavaScript Rendering page and compare the same extraction with JavaScript rendering disabled and enabled.

Use Case

Modern websites often use JavaScript to render or load content after the initial page response.

For this example, we use:

https://www.scrapingcourse.com/javascript-rendering

The page contains multiple products with their names, prices, and product links.

The extracted content includes products such as:

  • Chaz Kangeroo Hoodie — $52
  • Teton Pullover Hoodie — $70
  • Bruno Compete Hoodie — $63
  • Frankie Sweatshirt — $60
  • Hollister Backyard Sweatshirt — $52
  • Stark Fundamental Hoodie — $42
  • Hero Hoodie — $54
  • Oslo Trek Hoodie — $42
  • Abominable Hoodie — $69
  • Mach Street Sweatshirt — $62
  • Grayson Crewneck Sweatshirt — $64
  • Ajax Full-Zip Sweatshirt — $69

Before You Start

You need:

  • A Geonode API key
  • Python 3.9 or later
  • The requests package

Store your API key in an environment variable:

export GEONODE_SCRAPER_API_KEY="YOUR_API_KEY"

On Windows PowerShell:

$env:GEONODE_SCRAPER_API_KEY="YOUR_API_KEY"

Keep Your API Key Private

Never put your Geonode API key directly in your source code or commit it to your repository. Store it in an environment variable or .env file instead.

Install the Dependency

Install the requests package:

pip install requests

Case 1: Extract Without JavaScript Rendering

First, send the request with JavaScript rendering disabled.

import os
import requests

api_key = os.environ["GEONODE_SCRAPER_API_KEY"]

response = requests.post(
    "https://scraper.geonode.io/v1/extract",
    headers={
        "X-Api-Key": api_key,
        "Content-Type": "application/json",
    },
    json={
        "url": "https://www.scrapingcourse.com/javascript-rendering",
        "formats": ["markdown"],
        "render_js": False,
        "processing_mode": "sync",
    },
)

response.raise_for_status()

result = response.json()

print(result["data"]["markdown"])

Case 1 Result

The actual extraction returned the following Markdown:

---
meta-viewport: width=device-width, initial-scale=1.0
title: JS Rendering Challenge to Learn Web Scraping - ScrapingCourse.com
---


# JS Rendering

![](https://www.scrapingcourse.com/assets/images/challenge.svg)

## Challenge

Enable JavaScript to see products

[Chaz Kangeroo Hoodie Chaz Kangeroo Hoodie $52](https://scrapingcourse.com/ecommerce/product/chaz-kangeroo-hoodie)

[Teton Pullover Hoodie Teton Pullover Hoodie $70](https://scrapingcourse.com/ecommerce/product/teton-pullover-hoodie)

[Bruno Compete Hoodie Bruno Compete Hoodie $63](https://scrapingcourse.com/ecommerce/product/bruno-compete-hoodie)

[Frankie Sweatshirt Frankie Sweatshirt $60](https://scrapingcourse.com/ecommerce/product/frankie-sweatshirt)

[Hollister Backyard Sweatshirt Hollister Backyard Sweatshirt $52](https://scrapingcourse.com/ecommerce/product/hollister-backyard-sweatshirt)

[Stark Fundamental Hoodie Stark Fundamental Hoodie $42](https://scrapingcourse.com/ecommerce/product/stark-fundamental-hoodie)

[Hero Hoodie Hero Hoodie $54](https://scrapingcourse.com/ecommerce/product/hero-hoodie)

[Oslo Trek Hoodie Oslo Trek Hoodie $42](https://scrapingcourse.com/ecommerce/product/oslo-trek-hoodie)

[Abominable Hoodie Abominable Hoodie $69](https://scrapingcourse.com/ecommerce/product/abominable-hoodie)

[Mach Street Sweatshirt Mach Street Sweatshirt $62](https://scrapingcourse.com/ecommerce/product/mach-street-sweatshirt)

[Grayson Crewneck Sweatshirt Grayson Crewneck Sweatshirt $64](https://scrapingcourse.com/ecommerce/product/grayson-crewneck-sweatshirt)

[Ajax Full-Zip Sweatshirt Ajax Full-Zip Sweatshirt $69](https://scrapingcourse.com/ecommerce/product/ajax-full-zip-sweatshirt)

Case 2: Extract With JavaScript Rendering

Now run the same extraction with JavaScript rendering enabled.

The only change is:

"render_js": true
import os
import requests

api_key = os.environ["GEONODE_SCRAPER_API_KEY"]

response = requests.post(
    "https://scraper.geonode.io/v1/extract",
    headers={
        "X-Api-Key": api_key,
        "Content-Type": "application/json",
    },
    json={
        "url": "https://www.scrapingcourse.com/javascript-rendering",
        "formats": ["markdown"],
        "render_js": True,
        "processing_mode": "sync",
    },
)

response.raise_for_status()

result = response.json()

print(result["data"]["markdown"])

Case 2 Result

The actual extraction returned the following Markdown:

---
meta-viewport: width=device-width, initial-scale=1.0
title: JS Rendering Challenge to Learn Web Scraping - ScrapingCourse.com
---


# JS Rendering

![](https://www.scrapingcourse.com/assets/images/challenge.svg)

## Challenge

Enable JavaScript to see products

[Chaz Kangeroo Hoodie Chaz Kangeroo Hoodie $52](https://scrapingcourse.com/ecommerce/product/chaz-kangeroo-hoodie)

[Teton Pullover Hoodie Teton Pullover Hoodie $70](https://scrapingcourse.com/ecommerce/product/teton-pullover-hoodie)

[Bruno Compete Hoodie Bruno Compete Hoodie $63](https://scrapingcourse.com/ecommerce/product/bruno-compete-hoodie)

[Frankie Sweatshirt Frankie Sweatshirt $60](https://scrapingcourse.com/ecommerce/product/frankie-sweatshirt)

[Hollister Backyard Sweatshirt Hollister Backyard Sweatshirt $52](https://scrapingcourse.com/ecommerce/product/hollister-backyard-sweatshirt)

[Stark Fundamental Hoodie Stark Fundamental Hoodie $42](https://scrapingcourse.com/ecommerce/product/stark-fundamental-hoodie)

[Hero Hoodie Hero Hoodie $54](https://scrapingcourse.com/ecommerce/product/hero-hoodie)

[Oslo Trek Hoodie Oslo Trek Hoodie $42](https://scrapingcourse.com/ecommerce/product/oslo-trek-hoodie)

[Abominable Hoodie Abominable Hoodie $69](https://scrapingcourse.com/ecommerce/product/abominable-hoodie)

[Mach Street Sweatshirt Mach Street Sweatshirt $62](https://scrapingcourse.com/ecommerce/product/mach-street-sweatshirt)

[Grayson Crewneck Sweatshirt Grayson Crewneck Sweatshirt $64](https://scrapingcourse.com/ecommerce/product/grayson-crewneck-sweatshirt)

[Ajax Full-Zip Sweatshirt Ajax Full-Zip Sweatshirt $69](https://scrapingcourse.com/ecommerce/product/ajax-full-zip-sweatshirt)

Compare the Results

You can compare both requests directly:

Request

{
  "url": "https://www.scrapingcourse.com/javascript-rendering",
  "formats": ["markdown"],
  "render_js": false,
  "processing_mode": "sync"
}

Result

The captured result contains the page heading, the JavaScript challenge message, and the 12 product links with their prices.

Request

{
  "url": "https://www.scrapingcourse.com/javascript-rendering",
  "formats": ["markdown"],
  "render_js": true,
  "processing_mode": "sync"
}

Result

The captured result also contains the page heading, the JavaScript challenge message, and the 12 product links with their prices.

Observed Result

For this particular target and the captured runs, both cases returned the same Markdown content. The example therefore demonstrates how to enable JavaScript rendering, but the captured result does not establish that render_js is required for this page.

Extracted Products

The returned Markdown contains 12 product entries.

ProductPrice
Chaz Kangeroo Hoodie$52
Teton Pullover Hoodie$70
Bruno Compete Hoodie$63
Frankie Sweatshirt$60
Hollister Backyard Sweatshirt$52
Stark Fundamental Hoodie$42
Hero Hoodie$54
Oslo Trek Hoodie$42
Abominable Hoodie$69
Mach Street Sweatshirt$62
Grayson Crewneck Sweatshirt$64
Ajax Full-Zip Sweatshirt$69

Understanding the Response

The extracted page content is available under:

data.markdown

You can use the returned Markdown directly or process it further in your application.

For example:

markdown = result["data"]["markdown"]

print(markdown)

The Scraper API returns page content rather than automatically converting the page into structured product fields.

If your application needs fields such as:

name
price
url
sku
availability

you can parse the returned Markdown or HTML in your own application.

Structured Product Data

The Scraper API returns extracted page content as Markdown or HTML. It does not automatically return e-commerce fields such as product name, price, or SKU as structured fields.

When to Use JavaScript Rendering

Use:

"render_js": true

when the content you need depends on JavaScript execution.

Common examples include:

  • Product information loaded after the page opens
  • Client-side rendered product listings
  • Content populated dynamically by JavaScript
  • Pages where the initial HTML does not contain the content you need

For pages where the required content is already available without browser rendering, you can use:

"render_js": false

This avoids browser rendering when it is not needed.

What About wait_config?

This example does not include wait_config.

The focused Case 2 probe successfully completed with:

{
  "render_js": true,
  "processing_mode": "sync",
  "wait_config": null
}

It reported 12 product links and 12 prices in the returned Markdown.

Using wait_config

If a JavaScript-rendered page requires an explicit browser wait condition, you can use wait_config to control when the browser should consider the page ready for extraction.

Complete Example

Once you understand the difference between the two requests, the JavaScript-rendered version can be reduced to this:

import os
import requests

API_KEY = os.environ["GEONODE_SCRAPER_API_KEY"]
URL = "https://www.scrapingcourse.com/javascript-rendering"

response = requests.post(
    "https://scraper.geonode.io/v1/extract",
    headers={
        "X-Api-Key": API_KEY,
        "Content-Type": "application/json",
    },
    json={
        "url": URL,
        "formats": ["markdown"],
        "render_js": True,
        "processing_mode": "sync",
    },
)

response.raise_for_status()

result = response.json()

print(result["data"]["markdown"])

Request Parameters

ParameterValuePurpose
urlhttps://www.scrapingcourse.com/javascript-renderingTarget page to extract
formats["markdown"]Returns the extracted content as Markdown
render_jstrueEnables JavaScript rendering
processing_modesyncWaits for the extraction to complete

Next Steps

Now that you can extract a page with JavaScript rendering, continue to Compare a Product Page Across Locations to extract the same product page from different countries with proxy geo-targeting.

You can also explore:

  • Extract multiple product URLs with Batch
  • Discover product URLs with Map and extract them with Batch
  • Crawl a product or content section
  • Run longer extractions asynchronously

On this page