Files
Priceflow/frontend/src/App.jsx
T
Claude 684535ee85 feat: Add Amazon France search page with Crawl4AI anti-detection
- Created Amazon scraper service with advanced anti-bot techniques:
  * User-Agent rotation from realistic pool
  * Complete browser headers (Accept, Accept-Language, etc.)
  * Proxy rotation (10 residential proxies)
  * Random delays (1.5-4s) to mimic human behavior
  * Crawl4AI browser fingerprint randomization
  * NetworkIdle waiting for complete page load
  * Cookie acceptance automation

- Added Amazon search API endpoint with SSE streaming
  * Real-time progress updates
  * Proper error handling
  * Health check endpoint

- Created dedicated Amazon France frontend page:
  * Modern UI with product cards
  * Rating display (stars + review count)
  * Price formatting with discount badges
  * Prime badge support
  * Stock status indicators
  * Sponsored product labels
  * Direct Amazon links

- Removed store list (ENSEIGNES_DATA cleared)
  * Migration from discount stores to Amazon France
  * Catalog system kept for future use

- Updated navigation:
  * Added "Amazon France" menu item with ShoppingBag icon
  * Positioned between Search and Compare
  * Available on desktop and mobile

Technical stack:
- Backend: Crawl4AI + BeautifulSoup for scraping
- Frontend: React + Shadcn UI components
- API: FastAPI with SSE streaming
2025-11-30 00:36:39 +00:00

111 lines
3.5 KiB
React

import React from 'react'
import { BrowserRouter as Router, Routes, Route, Navigate } from 'react-router-dom'
import { Toaster } from 'sonner'
import Layout from '@/components/layout/Layout'
import Dashboard from '@/pages/Dashboard'
import Search from '@/pages/Search'
import MultiSearch from '@/pages/MultiSearch'
import AmazonSearch from '@/pages/AmazonSearch'
import Catalogues from '@/pages/Catalogues'
import Login from '@/pages/Login'
import Admin from '@/pages/Admin'
import { useTheme } from '@/hooks/use-theme'
import { AuthProvider, useAuth } from '@/hooks/use-auth'
// Protected route wrapper
function ProtectedRoute({ children, adminOnly = false }) {
const { isAuthenticated, isAdmin, loading } = useAuth();
if (loading) {
return (
<div className="min-h-screen flex items-center justify-center">
<div className="animate-spin rounded-full h-8 w-8 border-b-2 border-primary"></div>
</div>
);
}
if (!isAuthenticated) {
return <Navigate to="/login" replace />;
}
if (adminOnly && !isAdmin) {
return <Navigate to="/" replace />;
}
return children;
}
// Public route that redirects to home if already logged in
function PublicRoute({ children }) {
const { isAuthenticated, loading } = useAuth();
if (loading) {
return (
<div className="min-h-screen flex items-center justify-center">
<div className="animate-spin rounded-full h-8 w-8 border-b-2 border-primary"></div>
</div>
);
}
if (isAuthenticated) {
return <Navigate to="/" replace />;
}
return children;
}
function AppRoutes() {
const { theme, toggleTheme } = useTheme();
const { isAuthenticated } = useAuth();
return (
<>
<Toaster position="bottom-right" theme={theme} />
<Routes>
<Route
path="/login"
element={
<PublicRoute>
<Login />
</PublicRoute>
}
/>
<Route
path="/*"
element={
<ProtectedRoute>
<Layout theme={theme} toggleTheme={toggleTheme}>
<Routes>
<Route path="/" element={<Dashboard />} />
<Route path="/search" element={<Search />} />
<Route path="/compare" element={<MultiSearch />} />
<Route path="/amazon" element={<AmazonSearch />} />
<Route path="/catalogues" element={<Catalogues />} />
<Route
path="/admin"
element={
<ProtectedRoute adminOnly>
<Admin />
</ProtectedRoute>
}
/>
</Routes>
</Layout>
</ProtectedRoute>
}
/>
</Routes>
</>
);
}
export default function App() {
return (
<Router>
<AuthProvider>
<AppRoutes />
</AuthProvider>
</Router>
);
}