Test
10,000 pages
$3.75
$0.38/1K pages
- Try it on your real URLs
- Same API as the biggest pack
- Credits never expire
POST /crawl · up to 10,000 pages per job · robots.txt and Crawl-delay respected
Give a start URL and a page limit. The crawler follows the site's sitemap and links within the same domain, reads each page as Markdown and hands you the results page by page. One credit per page.
Quick answer
How can I crawl a whole website and get every page as Markdown?
Use a crawl API: you send a start URL and a limit, and it returns each page of the site as Markdown. WebReaderAPI crawls up to 10,000 pages per job within one domain, follows the sitemap, robots.txt and Crawl-delay, and charges one credit per page read, from $0.07/1K pages as of October 2026. Pages refused by robots.txt are free. No KYC; pay in crypto.
| Start a crawl | POST https://webreaderapi.com/api/v1/crawl with url, limit, max_depth, include_paths, exclude_paths |
|---|---|
| Get the results | GET https://webreaderapi.com/api/v1/jobs/{job_id}, paginated with a cursor |
| Scope | Crawl one website per job, up to 10,000 pages, following its sitemap, its robots.txt and its Crawl-delay |
| Many separate URLs | POST https://webreaderapi.com/api/v1/batch: Up to 100 URLs per batch job |
| Billing | 1 credit = 1 page read without a browser; 2 credits when the page needs a browser to render JavaScript. A request that fails, or that a site's robots.txt refuses, is not charged |
| Site owners | We respect robots.txt: our crawler identifies itself as WebReaderAPI, follows the rules written for it or for all robots, and does not read a page that a site disallows. Refused pages are not charged |
| Price | $14.25 for 50,000 pages, $50 for 500,000 pages |
A crawl is a background job, because reading hundreds of pages takes longer than one HTTP request should.
POST https://webreaderapi.com/api/v1/crawl with the start URL and your limits. You get a job_id at once.max_depth./read: Markdown, main content, rendering when needed.GET https://webreaderapi.com/api/v1/jobs/{job_id} and page through the results with the cursor while the job runs, or once it is done.The job stops at your limit, so you never pay for more pages than you asked for.
import os
import pathlib
import re
import time
import requests
API = "https://webreaderapi.com/api/v1"
HEADERS = {"Authorization": "Bearer " + os.environ["WEBREADER_API_KEY"]}
job = requests.post(
API + "/crawl",
headers=HEADERS,
json={"url": "https://docs.example.com/", "limit": 500, "max_depth": 4, "include_paths": ["/guide/*"]},
timeout=60,
).json()
out = pathlib.Path("docs_md")
out.mkdir(exist_ok=True)
cursor, delay = None, 5
while True:
params = {"cursor": cursor} if cursor else {}
page = requests.get(API + "/jobs/" + job["job_id"], headers=HEADERS, params=params, timeout=60).json()
for item in page.get("results", []):
if "markdown" in item:
name = re.sub(r"[^a-z0-9]+", "-", item["url"].lower()).strip("-")[:120]
(out / (name + ".md")).write_text(item["markdown"], encoding="utf-8")
cursor = page.get("next_cursor")
if page["status"] == "done" and not cursor:
break
if not cursor:
time.sleep(delay)
delay = min(delay * 2, 60)
print("credits used:", page.get("credits_used"))
It stays inside the domain of the start URL and skips anything the site asks robots to leave alone. In detail:
WebReaderAPI or for all robots are skipped and not charged.include_paths and exclude_paths take simple patterns such as /blog/*; use them to avoid tag pages, search pages and archives.Use a crawl when you know the site but not the pages; use a batch when you already have the list of URLs. A crawl discovers pages from the sitemap and links. A batch reads exactly the URLs you send, up to 100 per job, across any number of sites.
For a weekly refresh of a knowledge base, a common pattern is one crawl to build the index, then batches of the pages whose lastmod changed in the sitemap. That keeps the weekly cost to the pages that actually moved.
One credit per page read, two for pages that needed a browser. A documentation site of 1,500 pages that renders on the server costs 1,500 credits; the same site built as a single-page app may cost up to 3,000.
Three typical jobs, as of October 2026: a 300-page product manual fits in the 10,000 pages pack ($3.75); ten documentation sites of 2,000 pages each fit in 50,000 pages ($14.25); a 400,000-page archive fits in 500,000 pages ($50). Skipped and failed pages are free.
Size the pack on the number of pages, then add a margin for pages that need a browser. Credits never expire, so the rest serves the next crawl.
10,000 pages
$3.75
$0.38/1K pages
50,000 pages
$14.25
$0.28/1K pages
100,000 pages
$21.75
$0.22/1K pages
500,000 pages
$50
$0.10/1K pages
In every plan: Main-content extraction · JavaScript rendering when needed · Failed and refused pages not charged · Credits never expire
Up to 10,000 pages per job, within the domain of the start URL. For a larger site, split it into several jobs with include_paths, for example one per section.
Yes. It reads the sitemap listed in robots.txt or at the usual location, then follows links on the pages it reads. Pages that only the sitemap lists are still read if robots.txt allows them.
Not with WebReaderAPI. If robots.txt disallows our crawler or all robots, those pages are skipped and not charged. If the site declares Content-Signal: ai-input=no, we do not read it for you. We never try to get around such choices.
Yes. GET https://webreaderapi.com/api/v1/jobs/{job_id} returns the pages read so far with a cursor; keep paging until the job is done and no cursor is left.
No. Credits are counted page by page, and the job stops when it reaches the limit you set. Pages it skips because of robots.txt, and pages that fail, use no credit.
From $0.07/1K pages · no KYC
Get an API key