[SUPERSEDED] Lovable sync 1779811626#463
Conversation
X-Lovable-Edit-ID: edt-65367ce7-14f5-4395-a51d-c85d05a6f978 Co-authored-by: adm01-debug <231131902+adm01-debug@users.noreply.github.com>
X-Lovable-Edit-ID: edt-611c7804-1473-40a2-a367-4d923e4500fd Co-authored-by: adm01-debug <231131902+adm01-debug@users.noreply.github.com>
|
The latest updates on your projects. Learn more about Vercel for GitHub.
|
|
You have reached your Codex usage limits for code reviews. You can see your limits in the Codex usage dashboard. |
|
Warning Review limit reached
More reviews will be available in 35 minutes and 40 seconds. Learn how PR review limits work. Your organization has run out of usage credits. Purchase more in the billing tab. ⌛ How to resolve this issue?After more reviews become available, a review can be triggered using the We recommend that you space out your commits to avoid hitting the rate limit. 🚦 How do rate limits work?CodeRabbit enforces hourly rate limits for each developer per organization. Our paid plans include higher PR review limits than trial, open-source, and free plans. In all cases, reviews become available again over time. During sustained high-volume PR review activity, CodeRabbit may temporarily slow when the next review becomes available. Please see our Fair Usage Limits Policy for further information. ℹ️ Review info⚙️ Run configurationConfiguration used: Path: .coderabbit.yaml Review profile: CHILL Plan: Pro Run ID: 📒 Files selected for processing (11)
✨ Finishing Touches🧪 Generate unit tests (beta)
Comment |
|
This pull request has been ignored for the connected project Preview Branches by Supabase. |
There was a problem hiding this comment.
Pull request overview
This PR centralizes product grid column configuration and persistence so multiple pages share the same column-density behavior, while updating the column selector UI (always showing 3/4/5/6/8) and adding unit coverage.
Changes:
- Exported shared constants (
STORAGE_KEY,COLUMN_CLASSES) fromColumnSelectorand reused them across grids/utilities. - Unified grid column persistence to a single localStorage key across multiple pages/components.
- Added accessibility improvements to
ColumnSelector(radiogroup/radio roles) and introduced unit tests.
Reviewed changes
Copilot reviewed 11 out of 11 changed files in this pull request and generated 10 comments.
Show a summary per file
| File | Description |
|---|---|
| src/pages/products/FavoritesPage.tsx | Switches to shared grid columns storage key import. |
| src/pages/filters/useFiltersPageState.ts | Adds persistence wrapper for grid columns and updates responsive clamp logic. |
| src/pages/collections/useCollectionsPageState.ts | Adds persistence wrapper for grid columns using shared storage key. |
| src/hooks/products/useCatalogState.ts | Updates responsive clamp logic for grid columns and persists columns under shared key. |
| src/components/replenishments/ReplenishmentProductGrid.tsx | Adds persistence wrapper for grid columns using shared storage key. |
| src/components/replenishments/grid-layout.ts | Replaces local cols→class mapping with shared COLUMN_CLASSES. |
| src/components/products/ProductGrid.tsx | Reuses shared COLUMN_CLASSES instead of a local mapping. |
| src/components/products/LayoutPopover.tsx | Slight width adjustment for the popover content. |
| src/components/products/ColumnSelector.tsx | Exports shared constants, always shows all options, adds ARIA roles and keyboard handling, persists selection. |
| src/components/products/ColumnSelector.test.tsx | Adds unit tests for options visibility, persistence, ARIA, and keyboard interaction. |
| src/components/novelties/NoveltyProductGrid.tsx | Reuses shared COLUMN_CLASSES and adds persistence wrapper for grid columns. |
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
| import { COLUMN_CLASSES, type ColumnCount } from "./ColumnSelector"; | ||
| import { ProductCardSkeleton } from "./ProductCardSkeleton"; |
| // Responsive clamp: garante que o número de colunas não ultrapasse o disponível | ||
| // para a largura atual da tela, mantendo a consistência visual. | ||
| useEffect(() => { | ||
| const handleResize = () => { | ||
| const w = window.innerWidth; | ||
| if (w < 640 && gridColumns > 1) { | ||
| setGridColumnsState(3 as ColumnCount); | ||
| } else if (w >= 640 && w < 768 && gridColumns > 2) { | ||
| setGridColumnsState(3 as ColumnCount); | ||
| let maxCols: ColumnCount = 3; | ||
| if (w >= 1536) maxCols = 8; | ||
| else if (w >= 1280) maxCols = 6; | ||
| else if (w >= 1024) maxCols = 5; | ||
| else if (w >= 768) maxCols = 4; | ||
|
|
||
| if (gridColumns > maxCols) { | ||
| setGridColumns(maxCols); | ||
| } |
| const [gridColumns, setGridColumnsState] = useState<ColumnCount>(getDefaultColumns); | ||
| const setGridColumns = useCallback((cols: ColumnCount) => { | ||
| setGridColumnsState(cols); | ||
| try { | ||
| localStorage.setItem(GRID_COLS_KEY, String(cols)); | ||
| } catch { /* empty */ } | ||
| }, []); | ||
|
|
||
| // Responsive clamp: force appropriate columns on small screens | ||
| useEffect(() => { | ||
| const handleResize = () => { | ||
| const w = window.innerWidth; | ||
| if (w < 768 && gridColumns > 3) { | ||
| setGridColumns(3); | ||
| let maxCols: ColumnCount = 3; | ||
| if (w >= 1536) maxCols = 8; | ||
| else if (w >= 1280) maxCols = 6; | ||
| else if (w >= 1024) maxCols = 5; | ||
| else if (w >= 768) maxCols = 4; | ||
|
|
||
| if (gridColumns > maxCols) { | ||
| setGridColumns(maxCols); | ||
| } |
| @@ -97,9 +101,6 @@ export function ColumnSelector({ value, onChange, className }: ColumnSelectorPro | |||
|
|
|||
| const available = getAvailableOptions(screenWidth); | |||
|
|
|||
| const options = [3, 4, 5, 6, 8]; | ||
| options.forEach(cols => { | ||
| expect(screen.getByRole("radio", { name: `${cols} colunas` })).toBeInTheDocument(); | ||
| }); |
| [3, 4, 5, 6, 8].forEach(cols => { | ||
| expect(screen.getByRole("radio", { name: `${cols} colunas` })).toBeInTheDocument(); | ||
| }); |
| [3, 4, 5, 6, 8].forEach(cols => { | ||
| expect(screen.getByRole("radio", { name: `${cols} colunas` })).toBeInTheDocument(); | ||
| }); |
| @@ -0,0 +1,103 @@ | |||
| import { render, screen, fireEvent, waitFor, act } from "@testing-library/react"; | |||
| export function NoveltyProductGrid() { | ||
| const navigate = useNavigate(); | ||
| const [viewMode, setViewMode] = useState<ViewMode>('grid'); | ||
| const [gridColumns, setGridColumns] = useState<ColumnCount>(getDefaultColumns); | ||
| const [gridColumns, setGridColumnsState] = useState<ColumnCount>(getDefaultColumns); | ||
| const setGridColumns = useCallback((cols: ColumnCount) => { | ||
| setGridColumnsState(cols); | ||
| try { | ||
| localStorage.setItem(GRID_COLS_KEY, String(cols)); | ||
| } catch { /* empty */ } | ||
| }, []); |
| export function ReplenishmentProductGrid() { | ||
| const navigate = useNavigate(); | ||
| const [viewMode, setViewMode] = useState<ViewMode>('grid'); | ||
| const [gridColumns, setGridColumns] = useState<ColumnCount>(getDefaultColumns); | ||
| const [gridColumns, setGridColumnsState] = useState<ColumnCount>(getDefaultColumns); | ||
| const setGridColumns = useCallback((cols: ColumnCount) => { | ||
| setGridColumnsState(cols); | ||
| try { | ||
| localStorage.setItem(GRID_COLS_KEY, String(cols)); | ||
| } catch { /* empty */ } | ||
| }, []); |
Fechado: supersedido pelo PR #465 (lovable-sync-1779811798) que contém o mesmo conteúdo + COLUMN_CLASSES centralizado + data-testid + E2E tests. Conflito com main — conteúdo incorporado via #465.