RediSearch: Full-Text Search and Secondary Indexes on Redis Data
AI generated
SET
TTL
Redis Stack / RediSearch
RediSearch: Full-Text Search Directly on Redis Data
Secondary indexes without an external search index

Out of the box, Redis only knows direct key access, no queries across multiple fields and no full-text search. RediSearch closes this gap by building secondary indexes directly over hashes or JSON documents, enabling filter, sort, and full-text queries without duplicating the data into a separate search system.

13 min read RediSearch FT.SEARCH Full-Text Search Secondary Index Redis Stack

1. Why Redis Has No Secondary Indexes Out of the Box

At its core, Redis is a key-value store: without the exact key there is no direct way to find a record. Anyone searching for all products in a given category or all orders above a minimum value would, without additional structure, have to scan every key, which is neither practical nor performant as data volume grows.

Many teams work around this with manually maintained sets or sorted sets as an index, such as one set per category holding the associated product IDs. That works for simple cases but quickly becomes unmanageable once multiple filter criteria need to be combined or free-text search over product names is required. This is exactly where RediSearch comes in.

2. Defining an Index over Redis Hashes

RediSearch does not build an index through explicit commands per record but through a schema definition that specifies which key prefix is indexed and which hash fields are treated as text, numeric, tag, or geo coordinates. Once the index exists, new or changed hashes with a matching prefix are automatically indexed in the background, without the application ever having to manage index maintenance itself.

This automatic indexing is a key difference from classic search systems: there is no separate ingestion process that exports data from Redis and loads it into an index. A simple HSET on a key with the right prefix is enough for the record to be findable on the next FT.SEARCH.


redis-cli FT.CREATE idx_products ON HASH PREFIX 1 product: \
  SCHEMA name TEXT WEIGHT 2.0 \
         category TAG \
         price NUMERIC SORTABLE \
         stock NUMERIC

redis-cli HSET product:4711 name "Basic Shirt Blue" category "shirts" price 29.90 stock 140

3. Indexing JSON Documents with RediSearch

Since RediSearch also supports JSON documents, the same mechanism can be combined with RedisJSON. Instead of hash fields, JSONPath expressions are specified in the schema, so nested values within a document can also be indexed, such as the price of a specific variant inside a larger product document.

This approach is particularly suited for applications that already use RedisJSON for data storage and do not want to maintain an additional, redundant hash per record. The index definition remains conceptually identical to the hash variant, only field addressing happens through paths instead of simple field names.


redis-cli FT.CREATE idx_products_json ON JSON PREFIX 1 product: \
  SCHEMA $.name AS name TEXT \
         $.price AS price NUMERIC SORTABLE \
         $.category AS category TAG

4. Query Syntax: Full Text, Filters, and Combinations

FT.SEARCH combines full-text search and structured filters in a single query. A simple text search on the name field finds all products whose name contains the searched term, including stemming, so terms like shirt and shirts are recognized as related. Numeric filters can be appended directly in square brackets, for example to find only products within a specific price range.

Tag fields are suited for exact categorization such as category slugs or status values and are referenced with curly braces. All filter types can be freely combined with logical AND and OR, so complex queries such as a text search within a category with minimum stock can be formulated in a single command, without the application having to merge multiple Redis calls afterward.


redis-cli FT.SEARCH idx_products "shirt @category:{shirts} @price:[20 40]" SORTBY price ASC LIMIT 0 10

5. The Difference from a Dedicated Search Engine like Elasticsearch

Elasticsearch and OpenSearch are built with search as their primary task: a distributed sharding architecture, mature BM25-based relevance scoring with fine-grained boosting options, extensive aggregation pipelines, and a rich ecosystem of analyzers for different languages. RediSearch offers a solid subset of these features but is conceptually an add-on module on an in-memory database, not a distributed system optimized for search.

The practical difference shows up mainly with very large data volumes and complex relevance requirements: an Elasticsearch cluster scales horizontally across many shards and nodes and offers sophisticated language analysis for multilingual full-text search. RediSearch, on the other hand, runs in the same memory space as the rest of the Redis data and tends to hit available memory limits before running out of query functionality at very large index sizes.

6. Aggregations with FT.AGGREGATE

Beyond plain search, RediSearch offers FT.AGGREGATE, a pipeline for grouping, sums, averages, and sorting over the indexed data, similar to a simplified SQL GROUP BY query. This makes it possible to compute, for example, the average price per category or the number of available items per warehouse location directly from the index, without loading the raw data into the application.

This aggregation capability is noticeably more limited than what Elasticsearch offers, but it is often already sufficient for typical dashboard and reporting needs at small to medium data volumes. Anyone who regularly needs complex, multi-stage aggregations with nested buckets will hit conceptual limits with FT.AGGREGATE sooner than with a dedicated analytics engine.


redis-cli FT.AGGREGATE idx_products "*" \
  GROUPBY 1 @category \
  REDUCE AVG 1 @price AS avg_price \
  SORTBY 2 @avg_price DESC

7. Sensible Limits: When RediSearch Is Enough

RediSearch is particularly well suited when search data already lives in Redis and simply needs to be complemented with simple filter or free-text search, such as an autocomplete feature, an internal admin search tool, or a product catalog with a manageable number of attributes. In these cases, RediSearch entirely avoids running an additional search system with its own indexing pipeline.

For very latency-critical use cases, where search results need to be available within a few milliseconds and the data volume fits into memory, RediSearch fully leverages its in-memory nature. For a shop backend with a few tens of thousands of items and a small number of filter dimensions, this is often completely sufficient, without an additional search infrastructure being justified.

8. When a Dedicated Search Engine Remains the Better Choice

As soon as relevance ranking becomes central, for example in a public product search with thousands of items, multiple languages, and the requirement to reliably show the most relevant hits first, RediSearch reaches its limits. Fine-grained boosting, sophisticated synonym handling, and multilingual analyzers are considerably more mature in Elasticsearch.

At very large data volumes in the high double-digit or triple-digit gigabyte range, the in-memory nature of RediSearch also becomes a limiting factor, because the entire index has to fit into memory. Thanks to its segment-based architecture and disk persistence, Elasticsearch can run considerably larger indexes economically. For a Magento shop with an extensive catalog and high demands on search relevance, a dedicated search engine therefore often remains the more robust foundation.

9. Practical Example: Internal Product Search with RediSearch

A realistic use case is an internal tool or admin interface where staff need to quickly search for items, for example in customer service when handling order inquiries. The product data already lives in Redis as a hash or JSON document, and an additional search index via Elasticsearch would mean disproportionately high operational overhead for this internal, manageable use case.

With a RediSearch index over product name, SKU, and category, such an internal search can be set up within minutes, directly on the same data that already sits in the cache. Consistency between the search index and the actual data is guaranteed automatically, because RediSearch independently updates index entries on every change to the underlying hash or document.

Criterion RediSearch Elasticsearch/OpenSearch
Data storage Directly on Redis hashes or JSON documents Separate, dedicated data store with an ingestion pipeline
Relevance ranking Simple TF-based scoring Mature BM25 scoring with boosting
Scaling Limited by available memory Horizontal scaling across shards and nodes
Multilingual analysis Basic stemming for a few languages Extensive analyzer library for many languages
Operational overhead No additional system needed Its own cluster with its own operational model
Aggregations FT.AGGREGATE, functionally limited Extensive, multi-stage aggregation pipelines

Mironsoft

Cache layer setup and Magento Redis integration

Magento cache that isn't quite working or is misconfigured?

We set up Redis as a cache and session backend for Magento cleanly, tune memory usage and eviction strategies, and make sure full page cache and session storage work together reliably.

Redis Setup

Configure the cache, session, and FPC backend production-ready for Magento.

Memory Tuning

Match memory usage and eviction policies to the shop's actual load.

High Availability Setup

Set up Redis Sentinel or Cluster for resilient Magento environments.

10. Summary

RediSearch: The Essentials at a Glance

Core Idea

Secondary indexes and full-text search directly on existing Redis data

Core Commands

FT.CREATE, FT.SEARCH, FT.AGGREGATE with a schema on hash or JSON

Typical Use

Internal searches, autocomplete, and filters on manageable data volumes

Limits

In-memory nature and simpler relevance scoring than dedicated search engines

11. FAQ: RediSearch: The Essentials at a Glance

1Does RediSearch have to copy data from Redis into a separate index?
No, RediSearch indexes the existing hashes or JSON documents directly in place. There is no separate data store, every change to the underlying key automatically updates the index.
2Can RediSearch fully replace Elasticsearch?
For small to medium data volumes with simple relevance requirements, often yes. For extensive multilingual full-text search with high demands on ranking quality, a dedicated search engine usually remains the more robust choice.
3How are new fields added after an index has already been created?
FT.ALTER SCHEMA ADD lets you add additional fields to an existing index, but already existing records are not automatically reindexed retroactively and have to be written once again.
4Does RediSearch support stemming for German text?
Yes, RediSearch offers stemming support for numerous languages including German, which can be set via the LANGUAGE parameter on the index or per document.
5What happens to the index when a hash is deleted?
RediSearch automatically removes the associated entry from the index as soon as the key disappears from Redis via DEL or through TTL expiry, with no manual intervention needed.
6Can RediSearch be combined with Redis Cluster?
Yes, newer versions of RediSearch also support cluster operation, with the index distributed across the shards. For very large indexes, careful planning of the sharding strategy is important.
7How exactly does numeric filtering with square brackets work?
The expression @price:[20 40] filters for values between 20 and 40 inclusive. For open intervals, inf and -inf can be used as boundary values.
8Is RediSearch part of the standard Redis server?
No, like RedisJSON, RediSearch is a separate module that must be provided through Redis Stack, Redis Enterprise, or a manually loaded library.
9How performant is FT.SEARCH with several million documents?
As long as the index fits entirely into memory, queries typically stay in the low millisecond range. With several million documents and many full-text fields, memory needs should be realistically measured beforehand.
10Can multiple indexes run in parallel on the same data?
Yes, several FT.CREATE calls with different names and possibly different prefixes or schemas can exist in parallel on the same or overlapping data, though this means additional memory and indexing overhead.