Skip to content

fix(tui): paginate media search results#1097

Merged
wizzomafizzo merged 3 commits into
mainfrom
fix/tui-media-search-pagination-1023
Jul 13, 2026
Merged

fix(tui): paginate media search results#1097
wizzomafizzo merged 3 commits into
mainfrom
fix/tui-media-search-pagination-1023

Conversation

@wizzomafizzo

@wizzomafizzo wizzomafizzo commented Jul 13, 2026

Copy link
Copy Markdown
Member

Summary

  • follow media.search cursors instead of stopping after first 100 results
  • prefetch and append next page near end of TUI result list without moving selection
  • preserve active search filters across pages and surface loading or retry status in help text
  • cover automatic pagination and transient failure recovery

Closes #1023

Summary by CodeRabbit

  • New Features

    • Search results now automatically load additional pages as you near the end of the list.
    • Existing results remain visible while more items are fetched.
    • Result counts and status update during incremental loading.
  • Bug Fixes

    • Improved “load more” failure handling with clear messaging and a subsequent retry that preserves prior results.
    • Fresh searches and Clear/reset actions now properly reset pagination to prevent reuse of stale cursors.
  • Tests

    • Added integration coverage for incremental autoloading, autoload error/retry behavior, and pagination reset after a fresh search.

@coderabbitai

coderabbitai Bot commented Jul 13, 2026

Copy link
Copy Markdown

Review Change Stack

No actionable comments were generated in the recent review. 🎉

ℹ️ Recent review info
⚙️ Run configuration

Configuration used: defaults

Review profile: CHILL

Plan: Pro Plus

Run ID: d4786466-433f-4321-b264-0672723d2835

📥 Commits

Reviewing files that changed from the base of the PR and between 0e36bc7 and c8c88af.

📒 Files selected for processing (1)
  • pkg/ui/tui/searchmedia_test.go
🚧 Files skipped from review as they are similar to previous changes (1)
  • pkg/ui/tui/searchmedia_test.go

📝 Walkthrough

Walkthrough

Incremental media search pagination now prefetches additional results near the list boundary, preserves prior pages, tracks search identity and cursors, resets state for fresh searches, and supports retryable loading errors with integration coverage.

Changes

Media search pagination

Layer / File(s) Summary
Cursor-based pagination flow
pkg/ui/tui/searchmedia.go
BuildSearchMedia prefetches additional pages near the end of loaded results, passes query cursors to SearchMedia, appends results, updates pagination state, and resets that state when clearing the search.
Pagination integration validation
pkg/ui/tui/searchmedia_test.go
Integration tests cover autoloading, query changes, retained results, loading errors, retry behavior, fresh-search cursor clearing, and updated result-count messaging.

Estimated code review effort: 3 (Moderate) | ~25 minutes

Sequence Diagram(s)

sequenceDiagram
  participant ResultsList
  participant BuildSearchMedia
  participant executeSearch
  participant SearchMedia
  ResultsList->>BuildSearchMedia: selection approaches loaded results
  BuildSearchMedia->>executeSearch: loadNextPage with cursor
  executeSearch->>SearchMedia: query and cursor
  SearchMedia-->>executeSearch: page results and next cursor
  executeSearch-->>BuildSearchMedia: append results and update UI state
  BuildSearchMedia-->>ResultsList: preserve and extend visible results
Loading
🚥 Pre-merge checks | ✅ 5
✅ Passed checks (5 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check ✅ Passed The title clearly summarizes the main change: paginating TUI media search results.
Linked Issues check ✅ Passed The PR adds cursor-based pagination so users can reach results beyond the first 100 items, matching issue #1023.
Out of Scope Changes check ✅ Passed The code changes and tests stay focused on media search pagination and retry behavior, with no clear unrelated additions.
Docstring Coverage ✅ Passed Docstring coverage is 100.00% which is sufficient. The required threshold is 80.00%.
✨ Finishing Touches
📝 Generate docstrings
  • Create stacked PR
  • Commit on current branch
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch fix/tui-media-search-pagination-1023

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

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

Actionable comments posted: 2

🤖 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 `@pkg/ui/tui/searchmedia.go`:
- Around line 105-107: Make the prefetch triggered by SetChangedFunc
asynchronous so loadNextPage does not block the main tview UI goroutine during
scrolling. Run the blocking executeSearch/Svc.SearchMedia path in a goroutine,
marshal result and UI state updates through app.QueueUpdateDraw, and synchronize
access to resultPaths, nextCursor, activeSearchName, activeSearchSystem, and
searching to prevent races and duplicate requests.
- Around line 219-310: Reset fresh-search state before returning on a
SearchMedia error: when appendPage is false, clear nextCursor and reset
activeSearchName and activeSearchSystem so loadNextPage cannot continue the
previous query. Keep append-page failures’ existing pagination state unchanged,
and preserve the current error help text behavior.
🪄 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: defaults

Review profile: CHILL

Plan: Pro Plus

Run ID: 32e785ff-113a-441d-ac98-9972de54c1da

📥 Commits

Reviewing files that changed from the base of the PR and between 163139a and 409a7ab.

📒 Files selected for processing (2)
  • pkg/ui/tui/searchmedia.go
  • pkg/ui/tui/searchmedia_test.go

Comment thread pkg/ui/tui/searchmedia.go
Comment thread pkg/ui/tui/searchmedia.go
@codecov

codecov Bot commented Jul 13, 2026

Copy link
Copy Markdown

Codecov Report

❌ Patch coverage is 84.52381% with 13 lines in your changes missing coverage. Please review.

Files with missing lines Patch % Lines
pkg/ui/tui/searchmedia.go 84.52% 8 Missing and 5 partials ⚠️

📢 Thoughts on this report? Let us know!

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

🧹 Nitpick comments (1)
pkg/ui/tui/searchmedia_test.go (1)

249-273: 📐 Maintainability & Code Quality | 🔵 Trivial | ⚡ Quick win

Extract the repeated PlayStation fixture into a shared helper.

The "Game One"/"Game Two" SearchResults + PaginationInfo payload is duplicated near-verbatim across all three new tests, differing only in the cursor string ("next-page" vs "stale-cursor"). A small helper (e.g. psxFirstPageResult(cursor string) *models.SearchResults) would remove the copy/paste and keep the fixture consistent if the pagination contract shape changes later.

♻️ Suggested helper
func psxFirstPageResult(nextCursor string) *models.SearchResults {
	return &models.SearchResults{
		Results: []models.SearchResultMedia{
			{Name: "Game One", Path: "game-one.chd", ZapScript: "`@PlayStation/Game` One", System: models.System{ID: "psx", Name: "PlayStation"}},
			{Name: "Game Two", Path: "game-two.chd", ZapScript: "`@PlayStation/Game` Two", System: models.System{ID: "psx", Name: "PlayStation"}},
		},
		Total: 2,
		Pagination: &models.PaginationInfo{
			NextCursor:  &nextCursor,
			HasNextPage: true,
			PageSize:    2,
		},
	}
}

Also applies to: 347-371, 430-454

🤖 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 `@pkg/ui/tui/searchmedia_test.go` around lines 249 - 273, Extract the
duplicated PlayStation first-page fixture from the three affected tests into a
shared psxFirstPageResult(nextCursor string) helper. Have it construct the
existing Game One/Game Two SearchResults and PaginationInfo payload while
accepting the cursor value, then replace each inline fixture with calls using
the appropriate cursor string.
🤖 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.

Nitpick comments:
In `@pkg/ui/tui/searchmedia_test.go`:
- Around line 249-273: Extract the duplicated PlayStation first-page fixture
from the three affected tests into a shared psxFirstPageResult(nextCursor
string) helper. Have it construct the existing Game One/Game Two SearchResults
and PaginationInfo payload while accepting the cursor value, then replace each
inline fixture with calls using the appropriate cursor string.

ℹ️ Review info
⚙️ Run configuration

Configuration used: defaults

Review profile: CHILL

Plan: Pro Plus

Run ID: d8cdabd0-f269-41cf-830a-fbcedf824fe9

📥 Commits

Reviewing files that changed from the base of the PR and between 409a7ab and 0e36bc7.

📒 Files selected for processing (2)
  • pkg/ui/tui/searchmedia.go
  • pkg/ui/tui/searchmedia_test.go
🚧 Files skipped from review as they are similar to previous changes (1)
  • pkg/ui/tui/searchmedia.go

@wizzomafizzo wizzomafizzo merged commit 4d30a3b into main Jul 13, 2026
15 checks passed
@wizzomafizzo wizzomafizzo deleted the fix/tui-media-search-pagination-1023 branch July 13, 2026 23:43
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.

Zaparoo script UI only displays the first 100 PlayStation games in the list.

1 participant