Skip to content
AI Dev Toolkit.
Esc
  • AI Token CounterCount tokens for GPT, Claude, Gemini, DeepSeek, Qwen and more.Tool
  • LLM API Cost CalculatorEstimate per-request, daily and monthly API costs.Tool
  • AI Model ComparisonCompare prices, context windows and features across models.Tool
  • AI Model Pricing PagesSpecs, real costs and cheaper alternatives for popular models.Tool
  • Context Window CheckerSee whether your text fits each model’s context window.Tool
  • Subscription vs API CalculatorFind out whether a chat plan or the API is cheaper for you.Tool
  • GPU / VRAM CalculatorCheck how much VRAM a local model needs and which GPUs fit.Tool
  • Prompt Caching CalculatorEstimate savings from prompt caching.Tool

Utilities

Text chunker for RAG: chunk size and overlap

Paste a document, pick a chunk size and overlap, and see exactly how LangChain’s text splitters will cut it for RAG: every chunk, the overlap highlighted, and sizes in characters and tokens. This free text chunker runs in your browser, and nothing you paste is uploaded.

1,320 characters · 0 words

Split in your browser. Nothing you paste is uploaded or stored.

Library
Size counts

Used for the token stats.

Chunks0
Avg characters0
Avg tokens0
Tokens to embed0
Python: RecursiveCharacterTextSplitter
# pip install langchain-text-splitters
from langchain_text_splitters import RecursiveCharacterTextSplitter

splitter = RecursiveCharacterTextSplitter(
    chunk_size=500,
    chunk_overlap=100,
)
chunks = splitter.split_text(text)
print(len(chunks))

Chunks

Reproduces langchain-text-splitters 1.1.3; checked against the library’s own output.

Steps

How to use the text chunker

  1. Paste your text, open a file, or keep the sample help page.
  2. Choose the library you use, Python or LangChain.js, and the splitter.
  3. Set the chunk size and overlap, and whether the size counts characters or tokens.
  4. Read the chunks: the shaded start of each one is text repeated from the chunk before, and the bar shows how full it is.
  5. Copy the matching code into your project, or download the chunks as JSON.

Method

How it works

Retrieval-augmented generation (RAG) works on chunks: each piece of a document is embedded on its own and pasted into the prompt when it matches a question. So the way text is cut decides what a search can find. Most tutorials set chunk_size and chunk_overlap on a LangChain splitter and move on, but the result is hard to picture, and many online chunkers only approximate it. This tool runs a line-by-line port of LangChain’s splitters (langchain-text-splitters 1.1.3 for Python and @langchain/textsplitters 1.0.2 for JavaScript). On 2026-10-12 we ran both libraries on 840 combinations of text and settings, and the tests check that every chunk here matches their output character for character.

How the recursive splitter cuts

RecursiveCharacterTextSplitter tries the separators "\n\n", "\n", " " and "" in order. It splits on the first one the text contains, keeps every piece shorter than chunk_size (strictly shorter), and splits any longer piece again with the next separator. It then glues neighbouring short pieces back together until the next one would push the chunk past the limit, and trims the whitespace from both ends.

Overlap works on those pieces. When a chunk is full, the splitter keeps its last few pieces, as many as fit within chunk_overlap, as the start of the next chunk. Pieces are never cut to fit, so the real overlap is often smaller than the setting, and zero when the final paragraph alone is longer. Pieces that had to be split again are merged on their own, so chunks either side of them never share text. With the tool’s starting settings (500 characters, 100 overlap), the sample help page splits into 4 chunks, and 3 of them start with repeated text.

Characters or tokens

By default chunk_size counts characters. Python’s len() counts Unicode code points, while JavaScript’s .length counts UTF-16 units, so an emoji is 1 character in Python and 2 in LangChain.js, and LangChain.js can cut an emoji in half when it falls back to single characters. Embedding models limit and bill in tokens, so token counting is usually what you want: in Python, build the splitter with from_tiktoken_encoder and name the encoding, because the default is the old gpt2 one. This tool offers cl100k_base, which OpenAI says to use for its text-embedding-3 models, and o200k_base. In token mode, LangChain adds up the token counts of the pieces it joins, so a chunk can come out a token or two over the limit.

Fixed token windows

TokenTextSplitter ignores structure. It encodes the whole text and takes windows of chunk_size token ids, each starting chunk_size − chunk_overlap ids after the last. Sizes are predictable, but a window can end in the middle of a word or of a character that takes several bytes, which decodes to the replacement character �, just as tiktoken does.

Markdown

The Markdown mode tries headings, code fences and horizontal rules before paragraphs. The libraries differ here: Python’s from_language(Language.MARKDOWN) uses regular expressions for headings 1 to 6, LangChain.js uses plain strings for headings 2 to 6, and Python’s MarkdownTextSplitter() class matches its patterns as literal text, so it never splits on a heading. On the sample, Python’s Markdown mode gives 4 chunks and LangChain.js’s 4, with different boundaries.

Python and LangChain.js defaults

Python defaults to 4,000 characters with 200 overlap, LangChain.js to 1,000 with 200. Python accepts an overlap equal to the chunk size; LangChain.js throws an error. Only Python can keep separators at the end of a piece instead of the start.

What it doesn’t show

Embedding cost isn’t shown, because our daily price data covers chat models, not embedding models. “Tokens to embed” is the number to multiply by your embedding model’s price; the RAG chunk size guide lists dated prices and works through the sums. If your text contains special-token markers such as <|endoftext|>, LangChain’s tiktoken helpers raise an error by default; this tool counts them as plain text. To see how many retrieved chunks fit a model, use the context window checker.

Examples

Worked examples

One help page, eight ways to split it

SplitterSize / overlapChunksSharing textCharactersTokens embedded
Python, charactersRecursiveCharacterTextSplitter500 / 100 chars4356–482328 (+8.6%)
Python, no overlapRecursiveCharacterTextSplitter500 / 0 chars30409–482301 (−0.3%)
Python, library defaultsRecursiveCharacterTextSplitter4,000 / 200 chars101,320–1,320302 (+0.0%)
Python, MarkdownRecursiveCharacterTextSplitter.from_language(Language.MARKDOWN)500 / 100 chars41183–470320 (+6.0%)
Python, MarkdownTextSplitter()MarkdownTextSplitter500 / 100 chars42188–482327 (+8.3%)
LangChain.js, MarkdownMarkdownTextSplitter500 / 100 chars40183–470302 (+0.0%)
Python, tokensRecursiveCharacterTextSplitter128 / 16 tokens31421–482305 (+1.0%)
Token windowsTokenTextSplitter128 / 16 tokens32352–569334 (+10.6%)

The “Markdown help page” sample in the tool: 1,320 characters, 302 tokens in cl100k_base. “Sharing text” counts chunks that start with text repeated from the chunk before. Tokens embedded is the sum over all chunks; it can fall below the document’s count because splitters drop the whitespace at chunk edges. Computed with the tool’s own code when this page was built.

FAQ

Frequently asked questions

What chunk size should I use for RAG?

For mixed documentation, about 512 tokens with 10% overlap is a reasonable first setting. Research by Bhat et al. (2025) found 64 to 128 tokens best for short factual answers and 512 to 1,024 for questions that need wider context. Split a few real documents here, then test two or three sizes on real questions before you index everything.

Is LangChain’s chunk_size in characters or tokens?

Characters, by default: LangChain measures with Python’s len() or JavaScript’s .length. Build the Python splitter with from_tiktoken_encoder to count tokens, or pass a lengthFunction in LangChain.js. Note that from_tiktoken_encoder defaults to the old gpt2 encoding, so name the one your embedding model uses, such as cl100k_base for OpenAI’s text-embedding-3 models.

Why do my chunks overlap less than chunk_overlap?

RecursiveCharacterTextSplitter carries whole pieces (paragraphs, lines or words) into the next chunk, never part of one, and only up to chunk_overlap. If the last paragraph is longer than the overlap, nothing is carried. Pieces that had to be split again are merged separately, so chunks on either side of that boundary never overlap. Token windows always repeat exactly chunk_overlap tokens.

Why is a chunk longer than chunk_size?

Two reasons, both in token mode. If a piece can’t be split further, such as a single emoji that takes more tokens than the limit, LangChain keeps it whole. And LangChain adds up the token counts of the pieces it joins, but the joined text can tokenize into a token or two more. The tool marks any chunk over the limit in red.

What’s the difference between RecursiveCharacterTextSplitter and TokenTextSplitter?

The recursive splitter cuts at paragraphs, then lines, then spaces, so chunks end at natural breaks and vary in size. TokenTextSplitter encodes the whole text and cuts fixed windows of token ids, so every chunk except the last is exactly chunk_size tokens, but cuts land mid-word or even mid-character, which decodes to a replacement character (�).

Does LangChain’s MarkdownTextSplitter split on headings?

Not in Python 1.1.3. MarkdownTextSplitter() uses the Markdown separator list, but those separators are regular expressions and the class doesn’t turn on is_separator_regex, so they are matched as literal text. RecursiveCharacterTextSplitter.from_language(Language.MARKDOWN) does split on headings 1 to 6. In LangChain.js, MarkdownTextSplitter splits on headings 2 to 6.

Is my text uploaded anywhere?

No. The text is split in your browser, in a background worker so big documents don’t freeze the page. The tokenizer tables load from this site, and nothing you paste is sent to a server, stored or logged. The JSON export is created in your browser too.