+17
-5
frontend/src/components/StatisticsModal.tsx
+17
-5
frontend/src/components/StatisticsModal.tsx
···
10
} from "recharts";
11
import { Card, CardContent, CardHeader, CardTitle } from "@/components/ui/card";
12
import { toast } from "@/hooks/use-toast";
13
-
import { useState, useEffect } from "react";
14
15
import { getLinkClickStats, getLinkSourceStats } from "../api/client";
16
import { ClickStats, SourceStats } from "../types/api";
···
97
}
98
}, [isOpen, linkId]);
99
100
return (
101
<Dialog open={isOpen} onOpenChange={onClose}>
102
<DialogContent className="max-w-3xl">
···
138
</CardHeader>
139
<CardContent>
140
<ul className="space-y-2">
141
-
{sourcesData.map((source, index) => (
142
<li
143
key={source.source}
144
className="flex items-center justify-between py-2 border-b last:border-0"
···
149
</span>
150
{source.source}
151
</span>
152
-
<span className="text-sm font-medium">
153
-
{source.count} clicks
154
-
</span>
155
</li>
156
))}
157
</ul>
···
10
} from "recharts";
11
import { Card, CardContent, CardHeader, CardTitle } from "@/components/ui/card";
12
import { toast } from "@/hooks/use-toast";
13
+
import { useState, useEffect, useMemo } from "react";
14
15
import { getLinkClickStats, getLinkSourceStats } from "../api/client";
16
import { ClickStats, SourceStats } from "../types/api";
···
97
}
98
}, [isOpen, linkId]);
99
100
+
const aggregatedSources = useMemo(() => {
101
+
const sourceMap = sourcesData.reduce<Record<string, number>>(
102
+
(acc, { source, count }) => ({
103
+
...acc,
104
+
[source]: (acc[source] || 0) + count
105
+
}),
106
+
{}
107
+
);
108
+
109
+
return Object.entries(sourceMap)
110
+
.map(([source, count]) => ({ source, count }))
111
+
.sort((a, b) => b.count - a.count);
112
+
}, [sourcesData]);
113
+
114
return (
115
<Dialog open={isOpen} onOpenChange={onClose}>
116
<DialogContent className="max-w-3xl">
···
152
</CardHeader>
153
<CardContent>
154
<ul className="space-y-2">
155
+
{aggregatedSources.map((source, index) => (
156
<li
157
key={source.source}
158
className="flex items-center justify-between py-2 border-b last:border-0"
···
163
</span>
164
{source.source}
165
</span>
166
+
<span className="text-sm font-medium">{source.count} clicks</span>
167
</li>
168
))}
169
</ul>