Skip to content

[8.6] MOD-13884: Fix FT.HYBRID VSIM RANGE + FILTER returning zero results#8259

Merged
nafraf merged 1 commit into8.6from
backport-8205-to-8.6
Feb 4, 2026
Merged

[8.6] MOD-13884: Fix FT.HYBRID VSIM RANGE + FILTER returning zero results#8259
nafraf merged 1 commit into8.6from
backport-8205-to-8.6

Conversation

@redisearch-backport-pull-request
Copy link
Copy Markdown
Contributor

@redisearch-backport-pull-request redisearch-backport-pull-request Bot commented Feb 3, 2026

Description

Backport of #8205 to 8.6.

Describe the changes in the pull request

A clear and concise description of what the PR is solving, including:

  1. Current:
    When the document insertion order doesn't match the score order returned by the vector RANGE query, the query returns no results instead of the expected matches.

Root Cause

  • RANGE queries in FT.HYBRID are always combined with a filter (either explicit like @description:blue or implicit "*") via a PHRASE node in the AST.
  • The PHRASE node creates an intersection iterator that uses SkipTo operations to efficiently find documents existing in all child iterators.
  • SkipTo requires child iterators to be sorted by document ID.
  • The bug: RANGE queries were returning results sorted BY_SCORE (by vector distance). When the score order differs from the document ID order (which is determined by insertion order), the SkipTo operations fail to find matching documents because they assume sorted-by-ID iteration.
  1. Change:
    We implemented a conditional approach based on whether an explicit FILTER clause is provided:
  • RANGE + explicit FILTER → Use BY_ID ordering (required for intersection iterator compatibility)
  • RANGE without explicit FILTER → Use BY_SCORE ordering and skip filter integration so the vector node becomes the root directly
  1. Outcome:
  • FT.HYBRID VSIM RANGE + FILTER returns right results independent of docs ingestion order.
  • test_hybrid_vector_range_with_filter was failing if the docs were ingested in different order of the vector results, now it works independent of ingestion order.

Which additional issues this PR fixes

  1. MOD-13884

Main objects this PR modified

  1. ...

Mark if applicable

  • This PR introduces API changes
  • This PR introduces serialization changes

Release Notes

  • This PR requires release notes
  • This PR does not require release notes

If a release note is required (bug fix / new feature / enhancement), describe the user impact of this PR in the title.


Note

Medium Risk
Changes AST construction and iterator ordering for hybrid VSIM RANGE queries, which can affect result ordering/selection when filters are present; coverage is improved with new C++/Python tests but behavior changes are query-critical.

Overview
Fixes FT.HYBRID VSIM RANGE queries returning empty/incorrect results when combined with FILTER by ensuring RANGE+FILTER runs the vector iterator in BY_ID order (required for intersection/SkipTo).

For RANGE queries without an explicit FILTER, the vector node is now left as the AST root (via new ParsedVectorData.skipFilterIntegration) to preserve BY_SCORE ordering, and AREQ_ApplyContext skips parsing the implicit "*" wildcard since it would be immediately replaced.

Updates and expands tests to cover RANGE behavior with/without FILTER and to validate correctness independent of document insertion order.

Written by Cursor Bugbot for commit 671fc60. This will update automatically on new commits. Configure here.

…8205)

* Fix FT.HYBRID RANGE + FILTER

* FT.HYBRID RANGE sort by ID only when filter is used.

* Add test for RANGE query with FILTER clause in hybrid parsing

* Avoids allocating and immediately freeing a wildcard node for RANGE queries without explicit FILTER

(cherry picked from commit 7348b08)
@nafraf nafraf changed the title [8.6] MOD-12370: Fix FT.HYBRID VSIM RANGE + FILTER returning zero results [8.6] MOD-13884: Fix FT.HYBRID VSIM RANGE + FILTER returning zero results Feb 3, 2026
@codecov
Copy link
Copy Markdown

codecov Bot commented Feb 3, 2026

Codecov Report

✅ All modified and coverable lines are covered by tests.
✅ Project coverage is 83.77%. Comparing base (9c2a723) to head (671fc60).
⚠️ Report is 4 commits behind head on 8.6.

Additional details and impacted files
@@            Coverage Diff             @@
##              8.6    #8259      +/-   ##
==========================================
- Coverage   83.78%   83.77%   -0.02%     
==========================================
  Files         365      365              
  Lines       55291    55299       +8     
  Branches    14296    14296              
==========================================
+ Hits        46323    46324       +1     
- Misses       8807     8814       +7     
  Partials      161      161              
Flag Coverage Δ
flow 84.56% <100.00%> (-0.12%) ⬇️
unit 50.71% <92.30%> (+<0.01%) ⬆️

Flags with carried forward coverage won't be shown. Click here to find out more.

☔ View full report in Codecov by Sentry.
📢 Have feedback on the report? Share it here.

🚀 New features to boost your workflow:
  • ❄️ Test Analytics: Detect flaky tests, report on failures, and find test suite problems.

@redisearch-backport-pull-request redisearch-backport-pull-request Bot added this pull request to the merge queue Feb 3, 2026
@github-merge-queue github-merge-queue Bot removed this pull request from the merge queue due to failed status checks Feb 3, 2026
@nafraf nafraf added this pull request to the merge queue Feb 4, 2026
Merged via the queue into 8.6 with commit c67021c Feb 4, 2026
52 checks passed
@nafraf nafraf deleted the backport-8205-to-8.6 branch February 4, 2026 12:51
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant