RAG Pipeline Scraper — Website to Markdown & JSONL
Pricing
Pay per usage
RAG Pipeline Scraper — Website to Markdown & JSONL
Transform any website into clean Markdown and JSONL ready for RAG pipelines, vector databases (Pinecone, Weaviate, Chroma), and LLM training. Removes ads, navigation, and boilerplate automatically.
Pricing
Pay per usage
Rating
0.0
(0)
Developer
Niu Yuchiao
Maintained by CommunityActor stats
0
Bookmarked
1
Total users
0
Monthly active users
a day ago
Last modified
Categories
Share
Transform any website into clean Markdown and JSONL chunks, ready to drop into a RAG pipeline, vector database, or LLM fine-tuning workflow. The scraper automatically strips navigation menus, ads, footers, and boilerplate, leaving you only the content that matters.
Why use this Actor?
Building a RAG (Retrieval-Augmented Generation) system requires clean, chunked text from your source documents. This Actor does the heavy lifting:
- Crawls the entire site (or a single page) starting from a seed URL
- Cleans the HTML — removes scripts, ads, navbars, cookie banners, sidebars
- Converts to Markdown using a battle-tested HTML→MD library (Turndown + GFM)
- Chunks the text with a configurable word count and 10% overlap for better retrieval
- Outputs both individual Markdown files (Key-Value store) and a combined
output.jsonl(Dataset + Key-Value store)
Works with any public website: documentation sites, blogs, news portals, product pages, wikis.
Input
| Field | Type | Default | Description |
|---|---|---|---|
startUrl | string | (required) | The URL to start crawling from |
maxPages | number | 50 | Maximum number of pages to scrape |
chunkSize | number | 300 | Target word count per JSONL chunk |
outputMarkdown | boolean | true | Save per-page Markdown to Key-Value store |
outputJsonl | boolean | true | Save chunks to Dataset and output.jsonl |
includeMetadata | boolean | true | Add url, title, chunkIndex, scrapedAt to each chunk |
sameDomainOnly | boolean | true | Only follow links on the same domain as startUrl |
Example input
{"startUrl": "https://docs.example.com","maxPages": 100,"chunkSize": 400,"outputMarkdown": true,"outputJsonl": true,"includeMetadata": true,"sameDomainOnly": true}
Output
Dataset (JSONL chunks)
Each row in the Dataset is one text chunk, ready for embedding:
{"text": "Retrieval-Augmented Generation (RAG) combines a retrieval system with a language model...","metadata": {"url": "https://docs.example.com/intro","title": "Introduction to RAG","chunkIndex": 0,"scrapedAt": "2025-01-01T00:00:00.000Z"}}
The Dataset also contains one page_summary row per page:
{"_type": "page_summary","url": "https://docs.example.com/intro","title": "Introduction to RAG","wordCount": 1240,"chunkCount": 5}
Key-Value store
| Key | Content |
|---|---|
page-1-docs-example-com-intro | Full Markdown for that page |
output.jsonl | All chunks concatenated as JSONL (one JSON object per line) |
STATS | { pagesScraped, totalChunks, startUrl } |
Integrations
Pinecone
import json, openai, pineconewith open("output.jsonl") as f:chunks = [json.loads(line) for line in f]pc = pinecone.Pinecone(api_key="YOUR_KEY")index = pc.Index("my-index")for i, chunk in enumerate(chunks):embedding = openai.embeddings.create(input=chunk["text"], model="text-embedding-3-small").data[0].embeddingindex.upsert([(str(i), embedding, chunk["metadata"])])
Weaviate
import weaviate, jsonclient = weaviate.connect_to_local()collection = client.collections.get("Document")with open("output.jsonl") as f:for line in f:chunk = json.loads(line)collection.data.insert({"text": chunk["text"], **chunk["metadata"]})
LangChain
from langchain_community.document_loaders import JSONLoaderloader = JSONLoader(file_path="output.jsonl",jq_schema=".",content_key="text",metadata_func=lambda r, _: r.get("metadata", {}),json_lines=True,)docs = loader.load()
How it works
- Crawl — Uses
CheerioCrawler(fast, no-JavaScript HTML scraper) to fetch pages concurrently - Clean — Strips
<script>,<style>,<nav>,<header>,<footer>,<aside>, cookie banners, ad containers, sidebars - Extract — Prefers
<article>,<main>,[role="main"]elements; falls back to<body> - Convert — Runs the cleaned HTML through Turndown (with GitHub Flavored Markdown plugin) to produce clean Markdown
- Chunk — Splits by word count with 10% overlap so context is preserved across chunk boundaries
- Store — Saves Markdown files and JSONL chunks to Apify storage for easy download via API
FAQ
Does it handle JavaScript-rendered pages?
No — this Actor uses a fast HTML-only scraper. For JavaScript-heavy SPAs, pair it with Apify's apify/web-scraper to render pages first.
What languages does it support? Any language. The scraper is language-agnostic — it converts whatever HTML it receives.
Can I scrape a single page without following links?
Yes — set maxPages: 1 or sameDomainOnly: false with a specific URL.
How large can the site be?
The default cap is 50 pages. Raise maxPages up to any number — the Actor handles large sites gracefully with concurrent crawling.
Pricing
This Actor is billed per output chunk. A typical documentation site with 50 pages generates roughly 200–500 chunks.
Feedback & Issues
Found a bug or want a feature? Open an issue via the Issues tab in Apify Store, or contact the author directly through the Apify platform.