Bright Data - Fetch
One URL in, one page out, as markdown, HTML, or a screenshot. Nothing is parsed for you.
Every request is unblocked: IP rotation, browser fingerprints, cookies, CAPTCHA solving and automatic retries, from a country you choose. JavaScript rendering can be forced with the REST body's
parameter. The CLI has no flag for it, so a CLI fetch cannot force rendering (a
is still an image of the rendered page).
The call
CLI. The command is
, which runs Web Unlocker.
bdata scrape https://example.com/article
Markdown is the default. A first
tries to create
and, when no default is set, stores it as the zone default, so a fresh login on a normal account needs no
. It never overwrites a default you already set. A key from agent registration cannot create zones and its account has no
, so run
bdata config set default_zone_unlocker agent_unlocker
once. An account set up any other way carries its unlocker zone under another name (
from agent registration,
from the MCP server, any name at all when a person made it by hand): find it by the entry whose
is
in
, and pass that name. Override with
, or
, or
bdata config set default_zone_unlocker <name>
.
If
is not recognized, the CLI is not installed or npm's global directory is not on PATH; both fixes live in the
skill's Install section.
REST. The same request, for any machine with no CLI.
POST https://api.brightdata.com/request
Authorization: Bearer $BRIGHTDATA_API_KEY
Content-Type: application/json
{"zone":"cli_unlocker","url":"https://example.com/article",
"format":"raw","data_format":"markdown"}
is the name after
. On any other account use the name of your
zone, as above.
is the envelope and
is the page.
returns the body itself,
wraps it with status and headers.
For code the user keeps, the SDK wraps this same call in one line:
const html = await client.scrapeUrl('https://example.com/article')
. The
skill owns that surface. The
skill's
references/web-unlocker.md
covers the same one-POST shape and the KYC error codes. The full parameter list, including
,
and
, is in Bright Data's Web Unlocker API docs.
Formats
| Want | CLI | REST body | Note |
|---|
| Markdown (default) | | "format":"raw","data_format":"markdown"
| For a model, an index, or a human |
| Raw HTML | | , no | When the user's own code parses it |
| Screenshot | | "format":"raw","data_format":"screenshot"
| Binary PNG. The CLI writes unless says otherwise |
| Response metadata | | | Status and headers around the body |
One honest note on the markdown: links come back exactly as the page wrote them, so a relative link like
stays relative and points nowhere once the text leaves the site. That is fine when the output feeds a model, an index or a RAG store. For a standalone document a person will read and click, resolve the links against the page URL first, and say that you did.
The other flags that exist:
,
,
,
,
,
, and
, which has no effect in the current CLI release.
Example - one blocked article
The ask: "my script gets a 403 on this URL, I just need the article text"
- One URL, and the page itself is the answer. Stay in this skill.
- The 403 is the reason to be here, not a problem to route around. Unblocking is the product.
- Text for a human or a model, so markdown, which is already the default.
bdata scrape https://www.example-news.com/2026/08/some-article
Then state the choice in one line the user can override with one word:
Fetched the page with Web Unlocker as markdown. Say
if you want the data fields pulled out instead, and I will use a maintained scraper.
When a fetch is refused
Read the error first. A 403 from the target site is not on this list, because that is the ordinary case this skill exists to solve.
| The message contains | What it means |
|---|
No Web Unlocker zone specified.
| No zone resolved. Take the name of the entry in and pass it as , or save it once with bdata config set default_zone_unlocker <name>
. Do not log in again: it replaces the stored key. |
| The resolved zone does not exist on this account, often on an account made by agent registration. Take the entry from and save it with bdata config set default_zone_unlocker <name>
. |
Two other refusals are not this skill's to fix. A missing or dead key (
, or 401) means the machine is not logged in. A few targets need KYC on the account before Bright Data will serve them: sites that block themselves in robots.txt such as Reddit, government sites, sites on Bright Data's blocked list, and targets its compliance policy does not permit. Most sites need none of this. Both belong to the
skill, which carries the exact error codes. Send the user there, and never send anyone to KYC before a call has actually been refused.
Handoff boundaries
| The ask | Skill |
|---|
| Data fields, or many pages of one site | |
| The same site fetched twice with a parser in between | , because that is a scraper being written by hand |
| A query with no URL | |
| Their own browser code, pointed at an unblocked browser | |
A fetch whose real purpose is pulling data fields out of the page is a scrape ask. Hand it over.
Never promise JavaScript rendering on a CLI markdown or HTML fetch; when a page needs it, use the REST call with
. Never reach for a browser or a proxy because a page returned 403. That is what this one call already handles.