import { useState, useEffect } from 'react'; import PageMeta from '../../components/common/PageMeta'; import { useToast } from '../../components/ui/toast/ToastContainer'; import { fetchIndustries, Industry, fetchSeedKeywords, SeedKeyword } from '../../services/api'; import { Card } from '../../components/ui/card'; import Badge from '../../components/ui/badge/Badge'; import PageHeader from '../../components/common/PageHeader'; import { PieChartIcon } from '../../icons'; import { Tooltip } from '../../components/ui/tooltip/Tooltip'; interface IndustryWithData extends Industry { keywordsCount: number; topKeywords: SeedKeyword[]; totalVolume: number; } // Format volume with k for thousands and m for millions const formatVolume = (volume: number): string => { if (volume >= 1000000) { return `${(volume / 1000000).toFixed(1)}m`; } else if (volume >= 1000) { return `${(volume / 1000).toFixed(1)}k`; } return volume.toString(); }; export default function Industries() { const toast = useToast(); const [industries, setIndustries] = useState([]); const [loading, setLoading] = useState(true); useEffect(() => { loadIndustries(); }, []); const loadIndustries = async () => { try { setLoading(true); const response = await fetchIndustries(); const industriesList = response.industries || []; // First, fetch all seed keywords once (more efficient than per-industry) // We'll fetch a larger sample to get accurate counts and top keywords let allKeywords: SeedKeyword[] = []; try { const keywordsResponse = await fetchSeedKeywords({ page_size: 1000, // Get a large sample for accurate counts }); allKeywords = keywordsResponse.results || []; } catch (error) { console.warn('Failed to fetch keywords, will show without keyword data:', error); } // Process each industry with its keywords data const industriesWithData = industriesList.map((industry) => { // Filter keywords by industry name (matching industry.name) const industryKeywords = allKeywords.filter( (kw: SeedKeyword) => kw.industry_name === industry.name ); // Sort by volume and get top 5 const topKeywords = [...industryKeywords] .sort((a, b) => (b.volume || 0) - (a.volume || 0)) .slice(0, 5); // Calculate total volume of all keywords const totalVolume = industryKeywords.reduce( (sum, kw) => sum + (kw.volume || 0), 0 ); return { ...industry, keywordsCount: industryKeywords.length, topKeywords, totalVolume, }; }); // Filter to only show industries that have keywords associated const industriesWithKeywords = industriesWithData.filter( (industry) => industry.keywordsCount > 0 ); setIndustries(industriesWithKeywords); } catch (error: any) { toast.error(`Failed to load industries: ${error.message}`); } finally { setLoading(false); } }; return ( <> , color: 'blue' }} hideSiteSector={true} />

Explore our comprehensive global database of industries, sectors, and high-volume keywords

{loading ? (
Loading industries...
) : (
{industries.map((industry) => ( {/* Header */}

{industry.name}

{industry.totalVolume > 0 && ( {formatVolume(industry.totalVolume)} )}
{/* Description - Compact */} {industry.description && (

{industry.description}

)} {/* Stats Row - Compact */}
{industry.sectors?.length || industry.sectors_count || 0} sectors
{industry.keywordsCount || 0} keywords
{/* Top Keywords Section */} {industry.topKeywords && industry.topKeywords.length > 0 && (

Top Keywords

{industry.topKeywords.slice(0, 5).map((keyword, idx) => (
{keyword.keyword} {keyword.volume ? (keyword.volume >= 1000 ? `${(keyword.volume / 1000).toFixed(1)}k` : keyword.volume.toString()) : '-'}
))}
)}
))}
)}
); }