diff --git a/FIX_PROPOSAL.md b/FIX_PROPOSAL.md new file mode 100644 index 0000000..67662ed --- /dev/null +++ b/FIX_PROPOSAL.md @@ -0,0 +1,195 @@ +To address the issue of modularizing the BountiesPage component, we will break down the main bounty listing page into smaller, reusable atomic components. Here's a step-by-step solution: + +### Step 1: Refactor Main Page + +Modify `app/bounty/page.tsx` to focus on data fetching, state management, and composition of child components. + +```tsx +// app/bounty/page.tsx +import React, { useState, useEffect } from 'react'; +import FiltersSidebar from '../components/bounty/filters-sidebar'; +import BountyGrid from '../components/bounty/bounty-grid'; +import SearchHeader from '../components/bounty/search-header'; + +const BountiesPage = () => { + const [bounties, setBounties] = useState([]); + const [filters, setFilters] = useState({}); + const [searchQuery, setSearchQuery] = useState(''); + const [sortOrder, setSortOrder] = useState(''); + + useEffect(() => { + // Fetch bounties data + const fetchBounties = async () => { + const response = await fetch('https://api.github.com/repos/boundlessfi/bounties'); + const data = await response.json(); + setBounties(data); + }; + fetchBounties(); + }, []); + + const handleFilterChange = (filters) => { + setFilters(filters); + }; + + const handleSearchQueryChange = (searchQuery) => { + setSearchQuery(searchQuery); + }; + + const handleSortOrderChange = (sortOrder) => { + setSortOrder(sortOrder); + }; + + return ( +
+ + + +
+ ); +}; + +export default BountiesPage; +``` + +### Step 2: Create Atomic Components + +#### `components/bounty/filters-sidebar.tsx` + +```tsx +// components/bounty/filters-sidebar.tsx +import React from 'react'; + +interface FiltersSidebarProps { + filters: any; + onFilterChange: (filters: any) => void; + searchQuery: string; + onSearchQueryChange: (searchQuery: string) => void; +} + +const FiltersSidebar: React.FC = ({ + filters, + onFilterChange, + searchQuery, + onSearchQueryChange, +}) => { + const handleFilterChange = (filter: any) => { + onFilterChange({ ...filters, ...filter }); + }; + + const handleSearchQueryChange = (event: React.ChangeEvent) => { + onSearchQueryChange(event.target.value); + }; + + return ( +
+

Filters

+ + {/* Filter accordion UI */} +
+

Filter by

+ + +
+
+ ); +}; + +export default FiltersSidebar; +``` + +#### `components/bounty/bounty-grid.tsx` + +```tsx +// components/bounty/bounty-grid.tsx +import React from 'react'; + +interface BountyGridProps { + bounties: any[]; + filters: any; + searchQuery: string; + sortOrder: string; +} + +const BountyGrid: React.FC = ({ bounties, filters, searchQuery, sortOrder }) => { + const filteredBounties = bounties.filter((bounty) => { + // Apply filters and search query + return bounty.title.includes(searchQuery) && bounty.status === filters.status; + }); + + const sortedBounties = filteredBounties.sort((a, b) => { + // Apply sort order + if (sortOrder === 'asc') { + return a.title.localeCompare(b.title); + } else { + return b.title.localeCompare(a.title); + } + }); + + return ( +
+

Bounties

+
    + {sortedBounties.map((bounty) => ( +
  • +

    {bounty.title}

    +

    {bounty.description}

    +
  • + ))} +
+
+ ); +}; + +export default BountyGrid; +``` + +#### `components/bounty/search-header.tsx` + +```tsx +// components/bounty/search-header.tsx +import React from 'react'; + +interface SearchHeaderProps { + count: number; + sortOrder: string; + onSortOrderChange: (sortOrder: string) => void; +} + +const SearchHeader: React.FC = ({ count, sortOrder, onSortOrderChange }) => { + const handleSortOrderChange = (event: React.ChangeEvent) => { + onSortOrderChange(event.target.value); + }; + + return ( +
+

Search Results ({count})

+ +
+ ); +}; + +export default SearchHeader; +``` + +### Step 3: Verify UI and Functionality + +Verify that the UI renders correctly after the refactor and ensure that filters, sorting, and search still function as expected. Confirm data flows correctly between parent and child components and check for any regressions in responsiveness or layout. + +By following these steps, we have successfully modularized the BountiesPage component into smaller, reusable atomic components, improving readability, maintainability, and scalability. \ No newline at end of file