> ## Documentation Index > Fetch the complete documentation index at: https://bunny.net/docs/llms.txt > Use this file to discover all available pages before exploring further. # Full-Text Search > Use the FTS5, FTS4, and FTS3 full-text search modules in Bunny Database, with BM25 ranking, highlighting, and snippets. Bunny Database includes SQLite's full-text search modules. See the SQLite documentation for [FTS5](https://www.sqlite.org/fts5.html) and [FTS3 and FTS4](https://www.sqlite.org/fts3.html). ## Modules | Module | What it does | | - | - | | `fts5` | Current-generation full-text index with tokenizers, BM25 ranking, prefix queries, and highlighting. Prefer this. | | `fts5vocab` | Read-only view of an FTS5 index's vocabulary: terms, document counts, and occurrence counts. | | `fts4`, `fts4aux` | Previous-generation index and its term statistics, kept for compatibility. | | `fts3`, `fts3tokenize` | Original module and a table that shows how a tokenizer splits text. | ```sql theme={null} CREATE VIRTUAL TABLE articles USING fts5(title, body); INSERT INTO articles (title, body) VALUES ('Edge caching', 'How a CDN keeps content close to users.'); SELECT title, bm25(articles) AS score FROM articles WHERE articles MATCH 'cdn' ORDER BY score; ``` ## Tokenizers and table options The `unicode61` (default), `ascii`, `porter`, and `trigram` tokenizers are available. The `icu` tokenizer is not. Contentless and external-content tables, `detail=`, `columnsize=`, `prefix=`, and `UNINDEXED` columns all work as documented upstream. ## Match expressions `MATCH` expressions support terms, `"phrases"`, `prefix*`, `column:term`, `NEAR`, `AND`, `OR`, and `NOT`. `NOT` is a binary operator in both FTS5 and FTS3/4, so write `a NOT b` rather than `a AND NOT b`. The `AND NOT` form is a syntax error. The `fts4aux` table accepts only the one-argument form `fts4aux(table)`. ## Auxiliary functions See the SQLite documentation for the [FTS5 auxiliary functions](https://www.sqlite.org/fts5.html#_auxiliary_functions_) and the [FTS3/4 snippet, offsets, and matchinfo functions](https://www.sqlite.org/fts3.html#snippet). | Function | What it does | | - | - | | `bm25(table [, weight1, weight2, ...])` | FTS5 relevance score inside a `MATCH` query. Scores are negative and lower is better. Optional per-column weights. | | `highlight(table, column, open, close)` | FTS5. Wraps each match in a column's text with the `open` and `close` markers. | | `snippet(table, column, open, close, ellipsis, tokens)` | FTS5. A short excerpt around a match. Pass `-1` as the column to pick the best one. | | `offsets(table)` | FTS3/4. Space-separated match offsets. | | `snippet(table, ...)` | FTS3/4. Snippet with its own argument order. | | `matchinfo(table [, format])` | FTS3/4. Binary match statistics. | | `optimize(table)` | FTS3/4. Merges index segments. | | `fts5_source_id()` | The source identifier of the FTS5 module. | | `fts3_tokenizer(name [, pointer])` | FTS3/4. Legacy tokenizer registration and lookup. Not needed in normal use. | The `bm25()` score is also exposed as the hidden `rank` column, and its weights can be configured with `INSERT INTO t(t, rank) VALUES ('rank', 'bm25(10.0, 1.0)')`. When a term appears in half or more of the rows, its score is `-0.0`. That is correct BM25 behavior, not a fault. ## Special commands FTS5 special commands are written as `INSERT INTO t(t) VALUES ('command')`. The `optimize`, `rebuild`, `integrity-check`, `merge`, `automerge`, `usermerge`, `crisismerge`, `pgsz`, `secure-delete`, and `flush` commands are accepted on every FTS5 table. The `delete` and `delete-all` commands work only on contentless and external-content tables. FTS3/4 tables accept `optimize`, `rebuild`, `integrity-check`, `merge=n,m`, and `automerge=n`. This documentation is built and hosted on [Mintlify](https://mintlify.com), a developer documentation platform.