Debounce short search queries for longer - #6651
Draft
gpunto wants to merge 3 commits into
Draft
Conversation
Message search and the add-members user search have no minimum query length, so a one character query is sent as typed. Those queries match a large portion of the data set, which makes them the slowest ones to serve, while they are usually just a step towards the query the user is after. Debounce queries of 1-2 characters for at least 500ms instead of the configured 300ms, matching the iOS SDK. The thresholds live in SearchDebounce in ui-common, marked as internal API since they are not meant to be configured by integrators: the existing debounce still applies to regular queries, and wins for short ones too when it is longer than 500ms. Applied to the Compose message search in ChannelListViewModel, to the debounced input listener of the XML SearchInputView, and to the user search in AddMembersViewController. Channel search is left alone: it only queries from 3 characters on, so it never sends the short autocomplete queries this targets, and iOS likewise debounces only queries built around a text-search operator. Mention autocomplete is also left alone, as it queries the members of a single channel. SearchInputView.clear() now cancels a debounce still pending from the last keystroke, which would otherwise notify the listener with the query being cleared and re-run the search the user just dismissed. Debouncer gained internal submit/submitSuspendable overloads taking the debounce period for a single piece of work. The public API of every module is unchanged. AND-1409 Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Contributor
PR checklist ✅All required conditions are satisfied:
🎉 Great job! This PR is ready for review. |
Contributor
SDK Size Comparison 📏
|
The add-members search trims the query before building the request, so a padded short query was debounced as a regular one while firing a one character queryUsers. Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Every touched module already passes -opt-in=InternalStreamChatApi. Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
|
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.



Goal
Message search, the XML search input and the add-members user search send a query as typed, from the first character. Queries of 1-2 characters match a large portion of the data set, so they are the slowest ones to serve and some of them time out, while they are usually just a step towards the query the user is after. Debounce them for at least 500ms instead of the configured 300ms, matching iOS (stream-chat-swift#4198).
Closes AND-1409
Implementation
SearchDebouncein ui-common, marked@InternalStreamChatApisince the thresholds are not meant to be configured by integrators: 500ms up to 2 characters, the configured debounce from 3 on, and never shorter than the configured one. No public API changes, the API dumps are untouched.Debouncer: internalsubmit/submitSuspendableoverloads taking the debounce period for a single piece of work.ChannelListViewModel, the debounced input listener ofSearchInputView, and the user search inAddMembersViewController.SearchInputView.clear()now cancels a debounce still pending from the last keystroke, which notified the listener with the query being cleared and re-ran the search the user had just dismissed.Channel search is left alone: it only queries from 3 characters on, so it never sends the short autocomplete
queryChannelsthis targets. Mention autocomplete is left alone too, as it queries the members of a single channel.Testing
SearchDebounceTestcovers the thresholds, including a configured debounce longer than 500ms winning for short queries.ChannelListViewModelTest: a 2 character message search reachessearchMessagesonly after 500ms, a 3 character one after 300ms, and asearchDebounceMsabove 500ms is honoured for short queries.AddMembersViewControllerTest: a 2 character query starts no search before 500ms. Reverting the controller to the flat 300ms debounce fails this test.DebouncerTest: the new overloads debounce by the period passed per submission, and a later submission cancels pending work.SearchInputView.clear()fix has no test: ui-components has no Robolectric setup in its unit tests, so there is no harness to drive the view'sTextWatcher.