Marketplace Page

The MarketplacePage serves as the dedicated e-commerce hub for Socon-MKT. Unlike the Main Feed, which blends social content with commerce, this page is strictly focused on product discovery, categorization, and browsing.

The layout is constrained to a maximum width of 1100px for optimal viewing across devices and is divided into three distinct vertical sections.


Component Architecture

The page aggregates three modular components, each responsible for fetching and rendering a specific slice of the marketplace data.

1. MarketCategories

Located at the top of the page, this component renders a responsive grid of available product categories (e.g., Electronics, Fashion).

  • Visuals: Displays a category icon/image with a fallback emoji (🛍️) if no image is provided.
  • Routing: Clicking a category routes the user to a filtered view (/category/:id).
  • UX: Implements a localized pulse skeleton loading state while fetching data.

2. RecentFeaturedMarket

A horizontal, snap-scroll carousel highlighting newly added or featured products.

  • Data Fetching: Fetches a hard-limited list of the 10 most recent products by applying the -created_at ordering parameter.
  • Fail-Safe: If this request fails, the component silently fails (returns null) rather than breaking the page, ensuring the user can still browse the main market.

3. MainMarketList

The primary product grid featuring infinite scrolling.

  • Product Cards: Renders responsive square cards for each item. If a product has a price, it overlays a custom, rotated "Soko Price Tag" styling.
  • Infinite Scroll: Utilizes a bottom sentinel div to automatically fetch the next cursor-based page of products as the user scrolls down.
  • Empty States: Provides a styled empty state UI if no products exist in the marketplace yet.

State Management & Infinite Scrolling

Data fetching is handled exclusively through @tanstack/react-query to ensure fast navigation and cached responses.

  • Standard Queries: The Categories and Featured sections use standard useQuery hooks.
  • Infinite Queries: The Main Market uses useInfiniteQuery. It intercepts the next URL string returned by the Django backend, extracts the c= (cursor) parameter, and passes it to the next API call.
  • Scroll Detection: The react-intersection-observer package monitors the loadMoreRef sentinel. When it enters the viewport (inView === true), it triggers the fetchNextPage() function.

API Endpoints & Data Structures

The Marketplace interacts with two primary API endpoints via the globally configured Axios authApi instance.

1. Market Categories

Retrieves the full list of active product categories.

  • Endpoint: GET /posts/market_category/
  • Authorization: Required (Bearer Token)
  • Response Structure (MarketCategoryType[]):
    [
      {
        id: "string",
        image: "string_url | null",
        title: "string",
      },
    ];
    

Retrieves the 10 most recently added products for the top carousel.

  • Endpoint: GET /posts/marketplace/
  • Query Parameters:
  • page_size: 10
  • o: "-created_at"
  • Authorization: Required (Bearer Token)
  • Response Structure (PaginatedMarketplaceResponse): (See structure below)

3. Main Market List (Infinite)

Retrieves the paginated list of all marketplace products.

  • Endpoint: GET /posts/marketplace/
  • Query Parameters: c (Cursor string for pagination)
  • Authorization: Required (Bearer Token)
  • Response Structure (PaginatedMarketplaceResponse):
    {
      "next": "url_string | null",
      "previous": "url_string | null",
      "results": [
        {
          "id": "string",
          "author": {
            "profile": {
              "seller_profile": "string | null"
            }
          },
          "title": "string",
          "price": "string | null",
          "unit": "string | null",
          "media": [
            {
              "file": "string_url",
              "media_type": "image | video",
              "thumbnail": "string_url | null"
            }
          ]
        }
      ]
    }