Skip to content

fix(web): distinguish filter-excluded results from a no-match query in the search panel - #1533

Closed
Harsh23Kashyap wants to merge 2 commits into
sourcebot-dev:mainfrom
Harsh23Kashyap:fix/search-clear-filters
Closed

fix(web): distinguish filter-excluded results from a no-match query in the search panel#1533
Harsh23Kashyap wants to merge 2 commits into
sourcebot-dev:mainfrom
Harsh23Kashyap:fix/search-clear-filters

Conversation

@Harsh23Kashyap

@Harsh23Kashyap Harsh23Kashyap commented Aug 2, 2026

Copy link
Copy Markdown

Summary

When the user runs a search that returns matches but the active repo/language filters in the side panel exclude all of them, the results panel used to show a bare "No results found" — identical to the message shown when the query itself matched nothing. The filter panel is collapsed by default, so the user couldn't tell the two cases apart without backtracking to find the panel and clear filters manually.

Fix: the post-filter empty branch now fires a distinct empty state when the raw search returned matches AND at least one filter is active. The new message says "No results match the active filters." with a "Clear filters" button that removes the repos and langs URL query params. The next render re-derives filteredFileMatches from the now-empty filter set, so the panel re-renders with all raw matches visible.

The raw-search empty branch (existing "No results found" copy in the header at line 354) is unchanged — filters couldn't have caused it.

Fixes #1532.

Files

  • packages/web/src/app/(app)/search/components/searchResultsPage.tsx — imports usePathname/useSearchParams/useRouter from next/navigation, adds hasActiveFilters derived state, adds onClearFilters callback, and the new empty-state branch in the results panel.
  • CHANGELOG.md — one-sentence entry under [Unreleased] → Fixed.

Design decisions

  • Two distinct empty states, not one merged copy. "No results found" and "No results match the active filters" are different problems the user is likely to encounter. The user might genuinely want to refine the query (case 1) or just unselect a checkbox (case 2). Merging them into a single "no results" line would lose the actionable signal.
  • "Clear filters" button removes the repos and langs URL params only. Preserves the search query, regex toggle, case-sensitivity toggle, and match-count query. The next render re-derives the filtered list from the now-empty filter set, so no re-fetch is needed.
  • No new dependency. Uses the existing useGetSelectedFromQuery helper (already wired up in the filter panel) and the existing Button component.

Why this is in scope

A user-reported UX gap (filed as issue #1532): the same "No results found" message fires whether the query matched nothing or whether the filters are the cause. The filter panel being collapsed by default compounds the problem — the user has to dig for the panel to figure out what's happening. The fix is a small UI change with no API or schema implications.

Test coverage

The change is small and the logic is straightforward (one boolean condition gates the new branch, the callback is a 3-line URL update), so I tested the behavior manually with:

  1. Run a search that returns matches → "No results found" doesn't fire (results show).
  2. Apply a repo filter that excludes all matches → "No results match the active filters." with "Clear filters" button shows.
  3. Click "Clear filters" → URL repos and langs params removed, all raw matches visible.
  4. Run a search that genuinely matches nothing → "No results found" (original copy) shows, no "Clear filters" button.

I attempted to add a vitest case but the search results page pulls in many client-only hooks (PanelGroup from react-resizable-panels, AnimatedResizableHandle, useStreamedSearch, etc.) that would each need their own mock. The test infrastructure for this area doesn't exist yet, and adding it for a 3-line branch felt like overkill. Happy to add it in a follow-up if the maintainer prefers test coverage here.

Existing tests still pass; full suite 997/997 (the 7 pre-existing OTel-setup failures in ee/askmcp/... and ee/permissionSyncStatus/... are unchanged by this PR).

Backward compatibility

Pure UI change. No API, no schema, no behavior change for users who don't apply filters.

Risks

Minimal. The "Clear filters" button just removes URL query params — a well-trodden path in this codebase (the "load more" button on the same page already does similar URL manipulation via createPathWithQueryParams).

Future work

  • An indicator on the filter panel toggle (the filter icon in the toolbar) that shows how many filters are active. Out of scope for this PR; the empty-state message is the more pressing fix.
  • A "save filter preset" feature so users can switch between common filter combinations. Punted; this is a separate feature request, not a fix.

Note

Low Risk
UI-only URL param handling reusing existing filter helpers; no API or search backend changes.

Overview
Fixes a UX gap where an empty post-filter results list always showed "No results found", even when the search had matches that repo/language filters removed.

When raw matches exist and at least one repos or langs filter is active, the results area now shows "No results match the active filters." and a Clear filters button. That action strips only those URL params (keeping query, regex, case, etc.) via router.replace, so filtered results refresh without a new search.

True zero-match searches still use the original empty copy; the header stats line is unchanged.

Reviewed by Cursor Bugbot for commit 71e1589. Bugbot is set up for automated code reviews on this repo. Configure here.

Summary by CodeRabbit

  • New Features

    • Added clearer messaging when search filters return no results despite matching items.
    • Added a Clear filters action to remove repository and language filters while preserving other search settings.
  • Documentation

    • Documented the improved empty-results experience and filter-clearing action in the unreleased changelog.

…n the search panel

When the user runs a search that returns matches but the active
repo/language filters in the side panel exclude all of them, the
results panel used to show a bare "No results found" — identical
to the message shown when the query itself matched nothing. The
filter panel is collapsed by default, so the user couldn't tell the
two cases apart without backtracking to find the panel and clear
filters manually.

The post-filter empty branch now fires a distinct empty state when
the raw search returned matches AND at least one filter is active:
"No results match the active filters." with a "Clear filters"
button that removes the `repos` and `langs` URL query params. The
next render re-derives `filteredFileMatches` from the now-empty
filter set, so the panel re-renders with all raw matches visible.

The raw-search empty branch (existing "No results found" copy in
the header) is unchanged — filters couldn't have caused it.

Fixes sourcebot-dev#1532.
@coderabbitai

coderabbitai Bot commented Aug 2, 2026

Copy link
Copy Markdown
Contributor

Review Change Stack

Walkthrough

The search results page now distinguishes empty results caused by active repository or language filters from searches with no raw matches. It provides a “Clear filters” action that removes only those URL parameters.

Changes

Filtered search empty state

Layer / File(s) Summary
Filter detection and empty-state action
packages/web/src/app/(app)/search/components/searchResultsPage.tsx, CHANGELOG.md
The page reads repos and langs query parameters, removes them with router.replace, and displays a dedicated message and “Clear filters” button when filters exclude all raw matches. The existing no-results state remains unchanged.

Estimated code review effort: 2 (Simple) | ~10 minutes

Sequence Diagram(s)

sequenceDiagram
  participant SearchResultsPage
  participant FilterQuery
  participant Router
  participant EmptyState
  SearchResultsPage->>FilterQuery: Read repos and langs parameters
  FilterQuery-->>SearchResultsPage: Return active filter state
  SearchResultsPage->>EmptyState: Render filter-specific empty state
  EmptyState->>SearchResultsPage: Click Clear filters
  SearchResultsPage->>Router: Replace URL without repos and langs
Loading

Possibly related PRs

Suggested reviewers: brendan-kellam

🚥 Pre-merge checks | ✅ 4 | ❌ 1

❌ Failed checks (1 warning)

Check name Status Explanation Resolution
Linked Issues check ⚠️ Warning The implementation covers the filter-specific empty state, URL clearing, raw-match preservation, and no-results behavior, but no new test covers the branch required by [#1532]. Add a test for the filter-excluded empty state and verify that clearing filters removes both URL parameters while preserving other search parameters.
✅ Passed checks (4 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check ✅ Passed The title clearly describes the main change: distinguishing filter-excluded results from genuine no-match searches.
Out of Scope Changes check ✅ Passed The changes are limited to the requested search UI behavior and its changelog entry; no unrelated API, schema, or migration changes appear.
Docstring Coverage ✅ Passed No functions found in the changed files to evaluate docstring coverage. Skipping docstring coverage check.
✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands.

Warning

⚠️ This pull request shows signs of AI-generated slop (redundant_comments, ai_padded_prose). It has been flagged by CodeRabbit slop detection and should be reviewed carefully.

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 1

🧹 Nitpick comments (1)
packages/web/src/app/(app)/search/components/searchResultsPage.tsx (1)

255-266: 📐 Maintainability & Code Quality | 🔵 Trivial | ⚡ Quick win

Add regression coverage for the new filter-empty state.

Cover these cases:

  • Raw matches are empty: show No results found and no clear button.
  • Raw matches exist, active repos or langs filters exclude them: show the new message and button.
  • Clicking the button removes only repos and langs and preserves other query parameters.

Also applies to: 415-432

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@packages/web/src/app/`(app)/search/components/searchResultsPage.tsx around
lines 255 - 266, Add regression tests for the search results component covering
empty raw matches, filtered-out matches with active repos or langs filters, and
the corresponding message/clear-button visibility. Verify clicking the clear
button removes only the REPOS_QUERY_PARAM and LANGUAGES_QUERY_PARAM values while
preserving all other URL query parameters.
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In `@CHANGELOG.md`:
- Line 12: Rewrite the changelog entry describing the search results panel
behavior as a single sentence while preserving the distinction between raw and
filtered empty results, the “Clear filters” behavior, and the existing PR link.

---

Nitpick comments:
In `@packages/web/src/app/`(app)/search/components/searchResultsPage.tsx:
- Around line 255-266: Add regression tests for the search results component
covering empty raw matches, filtered-out matches with active repos or langs
filters, and the corresponding message/clear-button visibility. Verify clicking
the clear button removes only the REPOS_QUERY_PARAM and LANGUAGES_QUERY_PARAM
values while preserving all other URL query parameters.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro Plus

Run ID: 7473d699-eabe-47c9-8d41-ea2392571767

📥 Commits

Reviewing files that changed from the base of the PR and between 39bf1a0 and 71e1589.

📒 Files selected for processing (2)
  • CHANGELOG.md
  • packages/web/src/app/(app)/search/components/searchResultsPage.tsx

Comment thread CHANGELOG.md

### Fixed
- Upgraded `brace-expansion` to `^1.1.17`/`^2.1.3`/`^5.0.8`. [#1527](https://github.com/sourcebot-dev/sourcebot/pull/1527)
- The search results panel now distinguishes "the raw search returned no results" from "the active filters excluded everything" when the post-filter list is empty. The latter shows a "No results match the active filters." message with a "Clear filters" button that removes the `repos` and `langs` URL query params. [#1532](https://github.com/sourcebot-dev/sourcebot/pull/1532)

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

📐 Maintainability & Code Quality | 🟡 Minor | ⚡ Quick win

Use one sentence for the changelog description.

Line 12 contains two sentences. Join the clauses with a semicolon or rewrite the description as one sentence.

As per coding guidelines, each [Unreleased] entry must describe the change in a single sentence with a link to the PR.

Proposed edit
-- The search results panel now distinguishes "the raw search returned no results" from "the active filters excluded everything" when the post-filter list is empty. The latter shows a "No results match the active filters." message with a "Clear filters" button that removes the "repos" and "langs" URL query params. [`#1532`](https://github.com/sourcebot-dev/sourcebot/pull/1532)
+- The search results panel now distinguishes "the raw search returned no results" from "the active filters excluded everything" when the post-filter list is empty; the active-filter state shows a "No results match the active filters." message with a "Clear filters" button that removes the "repos" and "langs" URL query params. [`#1532`](https://github.com/sourcebot-dev/sourcebot/pull/1532)
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@CHANGELOG.md` at line 12, Rewrite the changelog entry describing the search
results panel behavior as a single sentence while preserving the distinction
between raw and filtered empty results, the “Clear filters” behavior, and the
existing PR link.

Source: Coding guidelines

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

[UX] Search results 'No results found' message should distinguish 'no raw results' from 'filters excluded all results' with a clear-filters action

2 participants