'use client' import { useEffect, useState } from 'react' import { useStore } from '@/lib/store' import { api } from '@/lib/api' import { Header } from '@/components/Header' import { Footer } from '@/components/Footer' import { PremiumTable, Badge, PlatformBadge, StatCard } from '@/components/PremiumTable' import { Clock, ExternalLink, Search, Flame, Timer, Gavel, DollarSign, RefreshCw, Target, X, ArrowRight, Lock, Sparkles, } from 'lucide-react' import Link from 'next/link' import clsx from 'clsx' interface Auction { domain: string platform: string platform_url: string current_bid: number currency: string num_bids: number end_time: string time_remaining: string buy_now_price: number | null reserve_met: boolean | null traffic: number | null age_years: number | null tld: string affiliate_url: string } type TabType = 'all' | 'ending' | 'hot' type SortField = 'ending' | 'bid_asc' | 'bid_desc' | 'bids' const PLATFORMS = [ { id: 'All', name: 'All Sources' }, { id: 'GoDaddy', name: 'GoDaddy' }, { id: 'Sedo', name: 'Sedo' }, { id: 'NameJet', name: 'NameJet' }, { id: 'DropCatch', name: 'DropCatch' }, ] export default function AuctionsPage() { const { isAuthenticated, checkAuth } = useStore() const [allAuctions, setAllAuctions] = useState([]) const [endingSoon, setEndingSoon] = useState([]) const [hotAuctions, setHotAuctions] = useState([]) const [loading, setLoading] = useState(true) const [refreshing, setRefreshing] = useState(false) const [activeTab, setActiveTab] = useState('all') const [sortBy, setSortBy] = useState('ending') const [sortDirection, setSortDirection] = useState<'asc' | 'desc'>('asc') const [searchQuery, setSearchQuery] = useState('') const [selectedPlatform, setSelectedPlatform] = useState('All') const [maxBid, setMaxBid] = useState('') useEffect(() => { checkAuth() loadAuctions() }, [checkAuth]) const loadAuctions = async () => { setLoading(true) try { const [all, ending, hot] = await Promise.all([ api.getAuctions(undefined, undefined, undefined, undefined, undefined, false, 'ending', 100, 0), api.getEndingSoonAuctions(50), api.getHotAuctions(50), ]) setAllAuctions(all.auctions || []) setEndingSoon(ending || []) setHotAuctions(hot || []) } catch (error) { console.error('Failed to load auctions:', error) } finally { setLoading(false) } } const handleRefresh = async () => { setRefreshing(true) await loadAuctions() setRefreshing(false) } const getCurrentAuctions = (): Auction[] => { switch (activeTab) { case 'ending': return endingSoon case 'hot': return hotAuctions default: return allAuctions } } const filteredAuctions = getCurrentAuctions().filter(auction => { if (searchQuery && !auction.domain.toLowerCase().includes(searchQuery.toLowerCase())) { return false } if (selectedPlatform !== 'All' && auction.platform !== selectedPlatform) { return false } if (maxBid && auction.current_bid > parseFloat(maxBid)) { return false } return true }) const sortedAuctions = [...filteredAuctions].sort((a, b) => { switch (sortBy) { case 'bid_asc': return sortDirection === 'asc' ? a.current_bid - b.current_bid : b.current_bid - a.current_bid case 'bid_desc': return sortDirection === 'asc' ? b.current_bid - a.current_bid : a.current_bid - b.current_bid case 'bids': return sortDirection === 'asc' ? a.num_bids - b.num_bids : b.num_bids - a.num_bids default: return 0 } }) const handleSort = (field: SortField) => { if (sortBy === field) { setSortDirection(sortDirection === 'asc' ? 'desc' : 'asc') } else { setSortBy(field) setSortDirection('asc') } } const formatCurrency = (amount: number, currency = 'USD') => { return new Intl.NumberFormat('en-US', { style: 'currency', currency }).format(amount) } const getTimeColor = (timeRemaining: string) => { if (timeRemaining.includes('m') && !timeRemaining.includes('h')) return 'text-red-400' if (timeRemaining.includes('h') && parseInt(timeRemaining) < 12) return 'text-amber-400' return 'text-foreground-muted' } const getSubtitle = () => { if (loading) return 'Loading live auctions...' const total = allAuctions.length if (total === 0) return 'No active auctions found' return `${total.toLocaleString()} live auctions across 4 platforms` } return (
{/* Background Effects */}
{/* Header */}
Live Market

Domain Auctions

{getSubtitle()}

{/* Stats */}
{/* CTA Banner for non-authenticated users */} {!isAuthenticated && (

Unlock Smart Opportunities

Get AI-powered auction analysis and personalized recommendations

Sign In
)} {/* Tabs */}
{[ { id: 'all' as const, label: 'All', icon: Gavel, count: allAuctions.length }, { id: 'ending' as const, label: 'Ending Soon', icon: Timer, count: endingSoon.length, color: 'warning' }, { id: 'hot' as const, label: 'Hot', icon: Flame, count: hotAuctions.length }, ].map((tab) => ( ))}
{/* Filters */}
setSearchQuery(e.target.value)} className="w-full pl-11 pr-10 py-3 bg-background-secondary/50 border border-border/50 rounded-xl text-sm text-foreground placeholder:text-foreground-subtle focus:outline-none focus:border-accent/50 transition-all" /> {searchQuery && ( )}
setMaxBid(e.target.value)} className="w-32 pl-10 pr-4 py-3 bg-background-secondary/50 border border-border/50 rounded-xl text-sm text-foreground placeholder:text-foreground-subtle focus:outline-none focus:border-accent/50" />
{/* Auctions Table */}
`${a.domain}-${a.platform}`} loading={loading} sortBy={sortBy} sortDirection={sortDirection} onSort={(key) => handleSort(key as SortField)} emptyIcon={} emptyTitle={searchQuery ? `No auctions matching "${searchQuery}"` : "No auctions found"} emptyDescription="Try adjusting your filters or check back later" columns={[ { key: 'domain', header: 'Domain', sortable: true, render: (a) => (
{a.domain}
{a.age_years && {a.age_years}y}
), }, { key: 'platform', header: 'Platform', hideOnMobile: true, render: (a) => (
{a.age_years && ( {a.age_years}y )}
), }, { key: 'bid_asc', header: 'Bid', sortable: true, align: 'right', render: (a) => (
{formatCurrency(a.current_bid)} {a.buy_now_price && (

Buy: {formatCurrency(a.buy_now_price)}

)}
), }, { key: 'bids', header: 'Bids', sortable: true, align: 'right', hideOnMobile: true, render: (a) => ( = 20 ? "text-accent" : a.num_bids >= 10 ? "text-amber-400" : "text-foreground-muted" )}> {a.num_bids} {a.num_bids >= 20 && } ), }, { key: 'ending', header: 'Time Left', sortable: true, align: 'right', hideOnMobile: true, render: (a) => ( {a.time_remaining} ), }, { key: 'action', header: '', align: 'right', render: (a) => ( Bid ), }, ]} />
) }