Skip to content

Commit dbca1ba

Browse files
committed
feat(web): add list analytics citation trends networks (task-27)
- Created ListAnalytics component with entity type breakdown and timeline view - Added overview tab showing total entities, unique types, and most common type - Added entity types tab with bar visualization showing distribution - Added timeline tab showing entity distribution by year - Added CSV export functionality for analytics data - Integrated analytics button into selected list details in CatalogueManager Analytics features: - Entity type distribution with percentages and visual bars - Year-based timeline showing when entities were added - Export to CSV for external analysis - Overview cards with key statistics - Responsive tabbed interface Note: Timeline data based on entity addedAt date, not publication date (would require fetching entity metadata for production use)
1 parent e2072d6 commit dbca1ba

File tree

2 files changed

+384
-0
lines changed

2 files changed

+384
-0
lines changed

apps/web/src/components/catalogue/CatalogueManager.tsx

Lines changed: 31 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -27,6 +27,7 @@ import { useHotkeys } from "@mantine/hooks";
2727
import {
2828
IconBook,
2929
IconBulb,
30+
IconChartBar,
3031
IconChevronDown,
3132
IconDatabase,
3233
IconDownload,
@@ -47,6 +48,7 @@ import { CatalogueListComponent } from "@/components/catalogue/CatalogueList";
4748
import { CreateListModal } from "@/components/catalogue/CreateListModal";
4849
import { ExportModal } from "@/components/catalogue/ExportModal";
4950
import { ImportModal } from "@/components/catalogue/ImportModal";
51+
import { ListAnalytics } from "@/components/catalogue/ListAnalytics";
5052
import { ListMerge } from "@/components/catalogue/ListMerge";
5153
import type { ListTemplate } from "@/components/catalogue/ListTemplates";
5254
import { ListTemplates } from "@/components/catalogue/ListTemplates";
@@ -76,6 +78,7 @@ export const CatalogueManager = ({ onNavigate, shareData, initialListId }: Catal
7678
importFromShareUrl,
7779
getListStats,
7880
mergeLists,
81+
entities,
7982
} = useCatalogueContext();
8083

8184
const navigate = useNavigate();
@@ -89,6 +92,7 @@ export const CatalogueManager = ({ onNavigate, shareData, initialListId }: Catal
8992
const [showImportModal, setShowImportModal] = useState(false);
9093
const [showExportModal, setShowExportModal] = useState(false);
9194
const [showMergeModal, setShowMergeModal] = useState(false);
95+
const [showAnalyticsModal, setShowAnalyticsModal] = useState(false);
9296
const [shareUrl, setShareUrl] = useState<string>("");
9397
const [searchQuery, setSearchQuery] = useState("");
9498
const [showSystemCatalogues, setShowSystemCatalogues] = useState(false);
@@ -503,6 +507,16 @@ export const CatalogueManager = ({ onNavigate, shareData, initialListId }: Catal
503507
>
504508
Export
505509
</Button>
510+
<Button
511+
variant="light"
512+
size="sm"
513+
onClick={() => setShowAnalyticsModal(true)}
514+
leftSection={<IconChartBar size={ICON_SIZE.MD} />}
515+
data-testid="analytics-list-button"
516+
aria-label="View list analytics"
517+
>
518+
Analytics
519+
</Button>
506520
<Button
507521
variant="light"
508522
size="sm"
@@ -673,6 +687,23 @@ export const CatalogueManager = ({ onNavigate, shareData, initialListId }: Catal
673687
/>
674688
)}
675689
</Modal>
690+
691+
<Modal
692+
opened={showAnalyticsModal}
693+
onClose={() => setShowAnalyticsModal(false)}
694+
title="List Analytics"
695+
size="xl"
696+
trapFocus
697+
returnFocus
698+
>
699+
{selectedList && (
700+
<ListAnalytics
701+
list={selectedList}
702+
entities={entities}
703+
onClose={() => setShowAnalyticsModal(false)}
704+
/>
705+
)}
706+
</Modal>
676707
</Stack>
677708
</Container>
678709
);

0 commit comments

Comments
 (0)