Skip to content

Web RAG, after the fetch

Context retrieval for RAG over web pages, from fetch to footnote

Context retrieval picks the passages your model answers from. With web pages, quality is set after the fetch: what you keep, how you chunk, rank and cite, and when you re-read the source.

Only Business, Enterprise and Custom sign-ups are reviewed before checkout. Failed fetches cost 0 credits.

Fetch a page, keep its metadata
import os, datetime, requests

r = requests.post(
    "https://livewebdata.com/api/v1/contents",
    headers={"Authorization": f"Bearer {os.environ['LIVE_WEB_DATA_API_KEY']}"},
    json={"urls": ["https://example.com/docs/setup"],
          "text": {"maxCharacters": 100000}},  # the default; raise it for longer pages
    timeout=60,
).json()

pages = {p["id"]: p for p in r["results"]}  # id = the requested URL
status = r["statuses"][0]
if status["status"] == "success":
    page = pages[status["id"]]
    record = {
        "url": page["url"],          # final URL: cite this one
        "title": page["title"],
        "retrieved_at": status["fetchedAt"],  # read live during this request
        "truncated": page["textTruncated"],
        "markdown": page["markdown"],
    }
else:
    print(status["error"]["tag"])    # record the failure, do not skip it

The problem

Why RAG over web pages goes wrong after the fetch

None of these are model problems. All of them are decided in the pipeline, usually by what it threw away or never wrote down.

  • Chunks lose the page they came from

    A chunk that says "set the timeout to 30 seconds" is useless without the product, version and section it belongs to. Fixed-size windows cut that context away.

  • Citations point at pages that changed

    The answer cites a URL, but the page was edited last week. The quoted sentence is gone, and the reader who clicks through finds something else.

  • Removed pages keep answering

    A page now returns 404, but its vectors are still in the index. Without a deletion step, retired docs and withdrawn policies keep being retrieved.

  • Failed fetches vanish without a trace

    Timeouts and empty pages drop out of the batch unrecorded, so the index looks complete while parts of the source list are missing.

How it works

How context retrieval for RAG works on web pages

Four steps from a list of URLs to answers with sources. Only the first is about fetching; the other three decide what the model sees.

  1. Step 1: Fetch clean Markdown with metadata

    Start from a reviewed list of public URLs. Keep the main content as Markdown plus the final URL, title, published date when present and retrieval time.

  2. Step 2: Chunk by headings, keep the path

    Split on headings first, cap long sections, keep tables and code blocks whole, and store the page title and heading path on every chunk.

  3. Step 3: Retrieve, rerank, measure

    Combine keyword and vector search, rerank the top candidates and check recall on a small set of real questions before you tune anything else.

  4. Step 4: Cite the passage, refresh the source

    Cite the final URL and the section the answer came from. Re-fetch each source on its own schedule, re-embed what changed and delete what is gone.

Use cases

Web pages as RAG context: where the details matter

Five common builds, and the guide that covers the step each one depends on most.

  • Research over a curated source list

    A few hundred pages from named publishers, with a record of what was fetched, when, and which pages failed and why.

    Read the guide
  • Assistant over your public docs

    Answers from your product documentation, where headings, code blocks and version numbers decide whether retrieval finds the right section.

    Read the guide
  • Lookups by error code and name

    Users paste exact error codes and product names. Hybrid keyword and vector search finds these where embeddings alone can miss them.

    Read the guide
  • Policy and standards Q&A

    Answers that a reviewer checks line by line need quote-level citations to the exact page and section, with the date it was read.

    Read the guide
  • Support bot that drops retired pages

    When a help article is removed or rewritten, the bot must stop citing the old version at the next refresh, not months later.

    Read the guide

Code

Fetch web pages for RAG and keep their metadata

Fetch a URL list, split each page on its headings and attach the final URL, title, heading and fetch time to every chunk. Splitting runs in your code.

import os, requests
from langchain_text_splitters import MarkdownHeaderTextSplitter

urls = ["https://example.com/docs/a", "https://example.com/docs/b"]
r = requests.post("https://livewebdata.com/api/v1/contents", timeout=90,
    headers={"Authorization": f"Bearer {os.environ['LIVE_WEB_DATA_API_KEY']}"},
    json={"urls": urls,
          "text": {"maxCharacters": 100000}}).json()

splitter = MarkdownHeaderTextSplitter([("#", "h1"), ("##", "h2"), ("###", "h3")])
pages = {p["id"]: p for p in r["results"]}  # id = the requested URL
chunks, failed = [], []
for st in r["statuses"]:  # one status per requested URL
    if st["status"] != "success":
        failed.append((st["id"], st["error"]["tag"]))
        continue
    page = pages[st["id"]]
    for i, doc in enumerate(splitter.split_text(page["markdown"])):
        chunks.append({
            "id": f"{page['url']}#{i}", "text": doc.page_content,
            "heading_path": list(doc.metadata.values()),
            "url": page["url"], "title": page["title"],
            "retrieved_at": st["fetchedAt"],
        })

Markdown is cut at text.maxCharacters, 100,000 characters by default. The splitter is LangChain's; any heading-aware one works. Chunking and storage stay yours.

Approaches

Structure-first vs raw HTML vs crawl once: web RAG compared

Three common ways to build retrieval augmented generation on web sources, compared on what they keep and what they lose over time.

Structure-first pipeline

What a chunk knows
Page title, heading path and final URL
What a citation points to
Final URL and section, with the date it was read
Pages that were removed
Deleted on 404 or 410 at the next refresh
Freshness signal per chunk
Fetch time per page (fetchedAt)
Failed or empty pages
Logged with an error tag, then retried or replaced
Effort to set up
A metadata schema and a refresh job

Raw HTML, fixed windows

What a chunk knows
Its own text, menus and banners included
What a citation points to
A URL, rarely the right section
Pages that were removed
Stay until someone notices
Freshness signal per chunk
None
Failed or empty pages
Embedded as empty or menu-only chunks
Effort to set up
Lowest: one loader and one splitter

Crawl once, never refresh

What a chunk knows
Title and URL as of the first crawl
What a citation points to
A URL whose content may have changed since
Pages that were removed
Keep answering questions
Freshness signal per chunk
One crawl date for the whole index
Failed or empty pages
Missing, with no record
Effort to set up
Low, until the first stale answer

An editorial comparison of pipeline approaches, not of products. Context Retrieval is published by Teneo Labs, which builds Live Web Data API, the fetch step in the code above.

Guides

Five guides to context retrieval, in pipeline order

Each guide covers one step end to end, with starting values to copy, what we have not tested, and the sources behind every claim.

All guides

FAQ

Context retrieval questions, answered plainly

What is context retrieval in RAG?
It is the step that finds the passages a language model answers from: the query is matched against an index of chunks, the best candidates are ranked, and the top few go into the prompt with their sources. The model can only be as right as the passages it is given, so most RAG quality problems are retrieval or ingestion problems.
Is context retrieval the same as Anthropic's contextual retrieval?
No. Contextual retrieval is one technique, published by Anthropic in 2024, in which a model writes a short note that places each chunk in its page before indexing. Context retrieval is the whole step of finding the passages a model answers from; the retrieval guide covers the technique and when web pages need it.
Can RAG use websites as a source?
Yes. A web page goes through the same pipeline as a PDF: load, clean, chunk, embed, retrieve. The differences are noise (navigation, cookie banners), metadata worth keeping (final URL, title, dates) and change: pages get edited, moved and removed, so a web index needs a refresh and deletion step. Use public pages and respect each site's terms of use and robots.txt. This is not legal advice; check the terms that apply to your use and the product's acceptable use policy.
How is context retrieval different from a bigger context window?
A larger window lets you pass more text; it does not choose which text. Passing whole sites is slow and costly, and the "Lost in the Middle" study (Liu et al., 2023) found that models use information in the middle of a long context less reliably than at its edges. Retrieval passes a few relevant passages with their sources, which also makes precise citations possible.
What should I store with every web page before chunking it?
At least the final URL after redirects, the page title, the time your pipeline read it, whether the copy was read live or reused from your own store, and a hash of the cleaned content. Add the published date only when the page states one. The ingestion guide has a full schema you can copy.
Which step of web RAG should I fix first?
Measure before you change anything: write about 30 real questions, note the page and section that answers each, and check what retrieval returns. If the right chunk does not exist, fix ingestion or chunking. If it exists but ranks low, fix retrieval. If it was retrieved and the answer is still wrong, look at the prompt and the citation check.
Does Live Web Data API chunk, embed or crawl?
No. It covers the fetch: you send one or more public URLs per request (see the API reference for the current limit) and get the main content as Markdown, text or HTML, cut at text.maxCharacters (100,000 characters by default), with the final URL, title, fetch time and per-URL errors, which cost 0 credits. Every request reads the page live; there is no cache. Chunking, embeddings, storage, search and crawling stay in your stack. Pages behind logins are out of scope; pages that need JavaScript can be read with the render option. Sign-up is for businesses only.

Notes

New notes on chunking, retrieval and citations

Short, sourced posts on one question each, grouped by pipeline step. The newest appear here first.

All posts

Start with the fetch, keep the rest yours

Businesses can request API access; only Business, Enterprise and Custom sign-ups are reviewed before checkout. Chunking, retrieval and your index stay in your own stack.