Lovable prompt to build a data table with sorting
Client-side sorting quietly lies once data spans multiple pages, reordering the loaded rows instead of the full set. This prompt keeps Lovable honest by pushing sort and pagination into the Supabase query, syncing state to the URL, and defining the empty, loading, and error rows, leaving you a table fit for real datasets.
Last updated
Build a data table screen for {{resource}} rows backed by Supabase.
Columns: name, status as a colored badge, owner, created_at shown as relative time with the absolute date in a tooltip, and a numeric amount column right-aligned.
Sorting: clicking a header cycles ascending, descending, then cleared, with a direction arrow in the header. Sorting runs server-side through the Supabase query so it holds past the first page, and the sorted column plus direction sync into the URL so a shared link reproduces the view.
Pagination: server-side, 25 rows per page, a footer showing the visible range against the total from a count query, and previous and next buttons disabled at the edges.
Extras: a column visibility dropdown persisted to localStorage, a checkbox column with select-all scoped to the current page, and bulk delete on selection behind a confirmation dialog naming the exact count.
States: a loading skeleton with the same row height so nothing jumps, an empty state with a create button when no rows exist, and an inline error row with a retry action when the query fails.
Styling: a sticky header row inside a scrollable container, compact density with comfortable line height, and badge colors that keep readable contrast in dark mode.
Acceptance: sorting by amount descending across pages surfaces the true top values, not the loaded page reordered, the URL restores sort and page on reload, select-all touches only the visible page, and deleting the last row of a page steps back one page instead of stranding an empty screen.Customize it
Runs in your browser. Nothing you type here is sent anywhere.
Build a data table screen for users rows backed by Supabase. Columns: name, status as a colored badge, owner, created_at shown as relative time with the absolute date in a tooltip, and a numeric amount column right-aligned. Sorting: clicking a header cycles ascending, descending, then cleared, with a direction arrow in the header. Sorting runs server-side through the Supabase query so it holds past the first page, and the sorted column plus direction sync into the URL so a shared link reproduces the view. Pagination: server-side, 25 rows per page, a footer showing the visible range against the total from a count query, and previous and next buttons disabled at the edges. Extras: a column visibility dropdown persisted to localStorage, a checkbox column with select-all scoped to the current page, and bulk delete on selection behind a confirmation dialog naming the exact count. States: a loading skeleton with the same row height so nothing jumps, an empty state with a create button when no rows exist, and an inline error row with a retry action when the query fails. Styling: a sticky header row inside a scrollable container, compact density with comfortable line height, and badge colors that keep readable contrast in dark mode. Acceptance: sorting by amount descending across pages surfaces the true top values, not the loaded page reordered, the URL restores sort and page on reload, select-all touches only the visible page, and deleting the last row of a page steps back one page instead of stranding an empty screen.
Same task in other tools
Questions about this prompt
Why insist on server-side sorting when the table looks fine locally?
With 25 rows per page, client sorting only reorders what is loaded, so sorting by amount descending shows the wrong top values. The Supabase order clause sorts the whole set before pagination slices it.
How do I add filtering on top of this?
Ask for filter chips that add where clauses to the same query, with their state joining sort and page in the URL. Keeping every input in one query builder stops the count query drifting from the rows.
The footer count stops matching after deletes. What happened?
The delete is updating rows without refetching the count. Have Lovable invalidate both together, the range display and the rows must come from the same filtered query or the footer lies.