[ALFMOB-339] Implement Search via BFF#23
Conversation
There was a problem hiding this comment.
Pull request overview
Migrates Search from the legacy autocomplete/suggestions flow to the BFF-backed searchProducts query by routing search results through the existing PLP (paging/sort/cursor), removing the old suggestions stack, and adding shared empty/error UI states plus a blank-search deeplink guard.
Changes:
- Removed legacy Search suggestions GraphQL op, domain/data plumbing, and Search overlay suggestion states; Search overlay now focuses on recent searches + submit → PLP.
- Added BFF
SearchProductsQueryand a sharedProductListResponseFragment, introducingProductListQuerySourceto switch between collection and search queries while reusing PLP paging. - Implemented reusable
StateMessageUI for PLP empty/no-results/error states and added deeplink handling for blank search queries viaDeeplinkResult.ShowErrorsurfaced as an error snackbar.
Reviewed changes
Copilot reviewed 63 out of 63 changed files in this pull request and generated 1 comment.
Show a summary per file
| File | Description |
|---|---|
| network/src/main/graphql/legacy/search-queries.graphql | Removes legacy SearchSuggestionsQuery operation. |
| network/src/main/graphql/bff/product-listing-queries.graphql | Adds SearchProductsQuery and reuses a shared response fragment for PLP/search. |
| network/src/main/graphql/bff/fragments/ProductListResponseFragment.graphql | Introduces a fragment capturing shared paging response shape. |
| feature/src/main/java/com/mindera/alfie/feature/webview/delegate/WebViewHandlerDelegate.kt | Handles/logs new DeeplinkResult.ShowError in webview deeplink flow. |
| feature/src/main/java/com/mindera/alfie/feature/webview/component/WebViewNavigator.kt | Treats ShowError as non-navigable from webview. |
| feature/search/src/test/java/com/mindera/alfie/feature/search/SearchViewModelTest.kt | Updates SearchViewModel tests to match submit-only behavior and blank guard. |
| feature/search/src/test/java/com/mindera/alfie/feature/search/SearchMockData.kt | Removes mock data for deleted suggestions UI/models. |
| feature/search/src/test/java/com/mindera/alfie/feature/search/factory/SearchUIFactoryTest.kt | Removes tests for deleted Search suggestions UI factory. |
| feature/search/src/main/res/values/strings.xml | Removes strings used by the deleted suggestions UI. |
| feature/search/src/main/java/com/mindera/alfie/feature/search/SearchViewModel.kt | Removes suggestion fetching/state; trims term before navigation/saving. |
| feature/search/src/main/java/com/mindera/alfie/feature/search/SearchOverlay.kt | Removes suggestions UI and related state wiring; keeps recent searches + submit. |
| feature/search/src/main/java/com/mindera/alfie/feature/search/model/SearchUIState.kt | Deletes now-unused Search overlay state model. |
| feature/search/src/main/java/com/mindera/alfie/feature/search/model/SearchUI.kt | Deletes now-unused Search suggestions UI model. |
| feature/search/src/main/java/com/mindera/alfie/feature/search/model/SearchEvent.kt | Removes events related to suggestions/autocomplete. |
| feature/search/src/main/java/com/mindera/alfie/feature/search/model/ProductSuggestionUI.kt | Deletes now-unused product suggestion UI model. |
| feature/search/src/main/java/com/mindera/alfie/feature/search/model/KeywordSuggestionUI.kt | Deletes now-unused keyword suggestion UI model. |
| feature/search/src/main/java/com/mindera/alfie/feature/search/model/BrandSuggestionUI.kt | Deletes now-unused brand suggestion UI model. |
| feature/search/src/main/java/com/mindera/alfie/feature/search/factory/SearchUIFactory.kt | Deletes now-unused suggestions UI factory. |
| feature/plp/src/test/java/com/mindera/alfie/feature/plp/ProductListViewModelTest.kt | Updates PLP tests to validate query-source branching and searchQuery exposure. |
| feature/plp/src/test/java/com/mindera/alfie/feature/plp/ProductListPreviewCountTest.kt | Updates preview-count tests for new query-source parameter. |
| feature/plp/src/main/res/values/strings.xml | Adds placeholder copy for search blank/no-results/empty/error states. |
| feature/plp/src/main/java/com/mindera/alfie/feature/plp/ProductListViewModel.kt | Switches to ProductListQuerySource and exposes searchQuery. |
| feature/plp/src/main/java/com/mindera/alfie/feature/plp/ProductListTypeMapper.kt | Adds mapping from nav type → query source + display title. |
| feature/plp/src/main/java/com/mindera/alfie/feature/plp/ProductListScreen.kt | Uses StateMessage to render error/empty/no-results states and enables retry. |
| feature/plp/src/main/java/com/mindera/alfie/feature/plp/ProductListDeeplinks.kt | Trims/validates search deeplink query and emits ShowError when blank. |
| feature/plp/src/androidTest/java/com/mindera/alfie/feature/plp/ProductListDeeplinksTest.kt | Adds instrumentation tests for blank-query error vs navigation. |
| domain/src/test/java/com/mindera/alfie/domain/usecase/search/GetSearchSuggestionsUseCaseTest.kt | Removes tests for deleted suggestions use case. |
| domain/src/test/java/com/mindera/alfie/domain/usecase/productlist/GetProductListUseCaseTest.kt | Updates tests for new query-source parameter. |
| domain/src/test/java/com/mindera/alfie/domain/usecase/productlist/GetPaginatedProductListUseCaseTest.kt | Updates tests for new query-source parameter. |
| domain/src/main/java/com/mindera/alfie/domain/usecase/search/GetSearchSuggestionsUseCase.kt | Deletes suggestions use case. |
| domain/src/main/java/com/mindera/alfie/domain/usecase/productlist/GetProductListUseCase.kt | Replaces collection handle param with query source param. |
| domain/src/main/java/com/mindera/alfie/domain/usecase/productlist/GetPaginatedProductListUseCase.kt | Replaces collection handle param with query source param in paging setup. |
| domain/repository/src/test/java/com/mindera/alfie/repository/search/model/SearchSuggestionsTest.kt | Removes tests for deleted suggestions model. |
| domain/repository/src/test/java/com/mindera/alfie/repository/productlist/paging/ProductListPagingSourceTest.kt | Updates paging source tests for new query-source parameter. |
| domain/repository/src/main/java/com/mindera/alfie/repository/search/SearchRepository.kt | Removes suggestions API from repository interface. |
| domain/repository/src/main/java/com/mindera/alfie/repository/search/model/SearchSuggestions.kt | Deletes suggestions model. |
| domain/repository/src/main/java/com/mindera/alfie/repository/search/model/SearchSuggestion.kt | Deletes suggestions model types. |
| domain/repository/src/main/java/com/mindera/alfie/repository/productlist/ProductListRepository.kt | Replaces collection handle with query source in repository API. |
| domain/repository/src/main/java/com/mindera/alfie/repository/productlist/paging/ProductListPagingSource.kt | Threads query source through paging source. |
| domain/repository/src/main/java/com/mindera/alfie/repository/productlist/model/ProductListQuerySource.kt | Adds sealed type to identify BFF list query source (collection vs search). |
| designsystem/src/main/java/com/mindera/alfie/designsystem/component/state/StateMessageAction.kt | Adds CTA model for state-message action button. |
| designsystem/src/main/java/com/mindera/alfie/designsystem/component/state/StateMessage.kt | Adds reusable centered empty/error/no-results component. |
| designsystem/src/main/java/com/mindera/alfie/designsystem/component/searchbar/SearchState.kt | Removes custom on-term-change listener support. |
| debug/operational/src/main/java/com/mindera/alfie/debug/operational/view/catalog/screen/SearchPullDownScreen.kt | Updates Search overlay usage to new signature. |
| data/src/test/java/com/mindera/alfie/data/search/service/SearchServiceImplTest.kt | Removes tests for deleted legacy suggestions service. |
| data/src/test/java/com/mindera/alfie/data/search/SearchMockData.kt | Removes legacy suggestions mock data. |
| data/src/test/java/com/mindera/alfie/data/search/repository/SearchRepositoryImplTest.kt | Removes suggestions repository tests and dependencies. |
| data/src/test/java/com/mindera/alfie/data/search/mapper/SearchSuggestionsMapperTest.kt | Removes tests for deleted suggestions mapper. |
| data/src/test/java/com/mindera/alfie/data/productlist/service/ProductListServiceImplTest.kt | Adds tests for new BFF searchProducts service call. |
| data/src/test/java/com/mindera/alfie/data/productlist/repository/ProductListRepositoryImplTest.kt | Adds tests for search-vs-collection branching and fragment mapping. |
| data/src/test/java/com/mindera/alfie/data/productlist/mapper/ProductListMapperTest.kt | Updates mapper tests to target shared response fragment. |
| data/src/main/java/com/mindera/alfie/data/search/service/SearchServiceImpl.kt | Deletes legacy search suggestions service implementation. |
| data/src/main/java/com/mindera/alfie/data/search/service/SearchService.kt | Deletes legacy search suggestions service interface. |
| data/src/main/java/com/mindera/alfie/data/search/repository/SearchRepositoryImpl.kt | Removes suggestions dependency/implementation, keeps recent searches persistence. |
| data/src/main/java/com/mindera/alfie/data/search/mapper/SearchSuggestionMapper.kt | Deletes legacy suggestions mapper. |
| data/src/main/java/com/mindera/alfie/data/search/di/SearchModule.kt | Removes binding for deleted search suggestions service. |
| data/src/main/java/com/mindera/alfie/data/productlist/service/ProductListServiceImpl.kt | Adds searchProducts query call via new BFF GraphQL operation. |
| data/src/main/java/com/mindera/alfie/data/productlist/service/ProductListService.kt | Adds searchProducts API to product list service. |
| data/src/main/java/com/mindera/alfie/data/productlist/repository/ProductListRepositoryImpl.kt | Branches between productList and searchProducts based on query source; maps via response fragment. |
| data/src/main/java/com/mindera/alfie/data/productlist/mapper/ProductListMapper.kt | Maps from shared ProductListResponseFragment to domain ProductList. |
| core/ui/src/main/java/com/mindera/alfie/core/ui/test/TestTagConstants.kt | Removes now-unused Search no-results test tag. |
| core/deeplink/src/main/java/com/mindera/alfie/core/deeplink/DeeplinkResult.kt | Adds ShowError(@StringRes messageRes) deeplink result type. |
| app/src/main/java/com/mindera/alfie/navigation/AppNavigation.kt | Surfaces DeeplinkResult.ShowError via error snackbar without navigation. |
There was a problem hiding this comment.
Pull request overview
Copilot reviewed 63 out of 63 changed files in this pull request and generated no new comments.
Comments suppressed due to low confidence (1)
feature/search/src/main/java/com/mindera/alfie/feature/search/SearchViewModel.kt:84
navigateToQueryassumes the passed term is already trimmed/non-blank. That’s true forOnSearchAction, but not for other call sites likeOnRecentSearchClick(which can surface older persisted recent searches that include whitespace). This can lead to navigating to a search PLP with a blank/space-only query and re-saving that invalid query. Centralize trimming/blank-guard insidenavigateToQueryso all entry points behave consistently.
amccall-mindera
left a comment
There was a problem hiding this comment.
Approving — all ALFMOB-339 acceptance criteria verified. The suggestion/autocomplete stack is fully removed (SearchSuggestionsQuery, Suggestion domain/UI types, GetSearchSuggestionsUseCase, SearchUIFactory) with zero leftover references, and search is rewired through PLP: SearchViewModel navigates ProductListType.Search(query) into ProductListQuerySource.Search, backed by searchProducts sharing the ProductListResponseFragment so pagination/sort/filters are source-agnostic. Recent searches and the search bar are retained, no-results is search-aware via the new StateMessage, and the search deeplink guards empty queries. Test coverage is solid (repository, service, PLP ViewModel, deeplink) and the prior Copilot KDoc comment is addressed.
ALFMOB-339 — Implement Search via BFF
Migrates Android Search off the legacy autocomplete (
SearchSuggestionsQuery) and onto the BFF'ssearchProductsquery, reusing the rewired PLP from ALFMOB-337/338 for results.What changed
SearchSuggestionsQueryGraphQL op, and the overlay'sLoading/Loaded/Errorstates. Kept the search bar, recent searches (Room), empty state, and submit→PLP.ProductListQuerySourcesealed type (Collection|Search) threaded through the repository → service → paging source → use cases. The repo callssearchProducts(searchTerm, …)in search mode andproductList(collectionHandle, …)otherwise — both share the newProductListResponseFragment, so pagination/sort/cursor plumbing is identical.StateMessagedesign-system component, now driving the search no-results state, a generic empty state, and an error state with a Try again (retry) button.qnow show an error snackbar (DeeplinkResult.ShowError) instead of navigating to an empty PLP; the search term is trimmed before it reaches the BFF/title/recent-searches.Figma ↔ Jira conflicts (Jira wins — see
Docs/ALFMOB-339-search-via-bff-plan.md)suggestionquery exists yet (tracked as a follow-up).Out of scope / follow-ups
plp_empty_*andplp_search_empty_query_errorcopy is placeholder — needs design/content sign-off."women"placeholder (BFF gap, shared with the PLP work) — search is unaffected since it threads the query string directly.Testing
data,domain,domain:repository,feature:search,feature:plp(search-source branching,searchProductsmapper/service, no-results gating, deeplink blank-query guard).compileDebugKotlin(incl. app), affectedtestDebugUnitTestsuites, anddetektall green.🤖 Generated with Claude Code