Skip to content

Commit 655c3c5

Browse files
committed
feat: добавлены кнопки для открытия репозитория и улучшено управление совместным использованием ссылки с уведомлениями
1 parent 86c5fba commit 655c3c5

2 files changed

Lines changed: 100 additions & 29 deletions

File tree

frontend/src/app/explore/page.tsx

Lines changed: 34 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -32,6 +32,7 @@ import {
3232
FilterList,
3333
TrendingUp,
3434
Security,
35+
OpenInNew,
3536
} from "@mui/icons-material";
3637
import LibraryCardSkeleton from "@/components/skeletons/LibraryCardSkeleton";
3738
import LoginModal from "@/components/LoginModal";
@@ -573,22 +574,39 @@ function ExploreContent() {
573574
borderColor: "divider",
574575
}}
575576
>
576-
<Button
577-
fullWidth
578-
variant="outlined"
579-
size="small"
580-
sx={{ fontWeight: 600 }}
581-
onClick={(e) => {
582-
e.stopPropagation();
583-
if (isAuthenticated) {
584-
router.push(`/dashboard?libraryId=${lib.id}`);
585-
} else {
586-
setLoginModalOpen(true);
587-
}
588-
}}
589-
>
590-
Подробнее
591-
</Button>
577+
<Stack direction="row" spacing={1.5}>
578+
{lib.repositoryUrl && (
579+
<Button
580+
fullWidth
581+
variant="outlined"
582+
size="small"
583+
startIcon={<OpenInNew />}
584+
sx={{ fontWeight: 600 }}
585+
onClick={(e) => {
586+
e.stopPropagation();
587+
window.open(lib.repositoryUrl, "_blank", "noopener,noreferrer");
588+
}}
589+
>
590+
Репозиторий
591+
</Button>
592+
)}
593+
<Button
594+
fullWidth
595+
variant="outlined"
596+
size="small"
597+
sx={{ fontWeight: 600 }}
598+
onClick={(e) => {
599+
e.stopPropagation();
600+
if (isAuthenticated) {
601+
router.push(`/dashboard?libraryId=${lib.id}`);
602+
} else {
603+
setLoginModalOpen(true);
604+
}
605+
}}
606+
>
607+
Подробнее
608+
</Button>
609+
</Stack>
592610
</Box>
593611
</CardContent>
594612
</Card>

frontend/src/components/dashboard/LibraryDetailView.tsx

Lines changed: 66 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,7 @@ import {
1212
Paper,
1313
Divider,
1414
Alert,
15+
Snackbar,
1516
} from "@mui/material";
1617
import {
1718
ArrowBack,
@@ -36,6 +37,15 @@ export default function LibraryDetailView({ libraryId }: LibraryDetailViewProps)
3637
const [healthMetrics, setHealthMetrics] = useState<HealthMetrics | null>(null);
3738
const [loading, setLoading] = useState(true);
3839
const [error, setError] = useState<string | null>(null);
40+
const [shareToast, setShareToast] = useState<{
41+
open: boolean;
42+
message: string;
43+
severity: "success" | "error";
44+
}>({
45+
open: false,
46+
message: "",
47+
severity: "success",
48+
});
3949

4050
const libraryIdNum = parseInt(libraryId);
4151
const { status, fetchSubscriptionStatus } = useLibrarySubscription(libraryIdNum);
@@ -108,9 +118,38 @@ export default function LibraryDetailView({ libraryId }: LibraryDetailViewProps)
108118

109119
const handleShare = async () => {
110120
try {
111-
await navigator.clipboard.writeText(window.location.href);
121+
const shareData = {
122+
title: library?.name || "Библиотека",
123+
text: `Посмотри библиотеку ${library?.name || ""} в StackScout`,
124+
url: window.location.href,
125+
};
126+
127+
if (navigator.share) {
128+
await navigator.share(shareData);
129+
} else {
130+
await navigator.clipboard.writeText(window.location.href);
131+
}
132+
133+
setShareToast({
134+
open: true,
135+
message: "Ссылка готова к отправке",
136+
severity: "success",
137+
});
112138
} catch {
113-
// Handle copy error silently
139+
try {
140+
await navigator.clipboard.writeText(window.location.href);
141+
setShareToast({
142+
open: true,
143+
message: "Ссылка скопирована в буфер обмена",
144+
severity: "success",
145+
});
146+
} catch {
147+
setShareToast({
148+
open: true,
149+
message: "Не удалось поделиться ссылкой",
150+
severity: "error",
151+
});
152+
}
114153
}
115154
};
116155

@@ -127,9 +166,9 @@ export default function LibraryDetailView({ libraryId }: LibraryDetailViewProps)
127166
<Button
128167
variant="outlined"
129168
startIcon={<ArrowBack />}
130-
onClick={() => router.push("/dashboard")}
169+
onClick={() => router.push("/explore")}
131170
>
132-
Вернуться к дашборду
171+
Вернуться к исследованию
133172
</Button>
134173
</Container>
135174
);
@@ -150,12 +189,13 @@ export default function LibraryDetailView({ libraryId }: LibraryDetailViewProps)
150189
>
151190
<Container maxWidth="lg">
152191
<Button
153-
variant="text"
192+
variant="outlined"
193+
color="primary"
154194
startIcon={<ArrowBack />}
155-
onClick={() => router.push("/dashboard")}
156-
sx={{ mb: 2 }}
195+
onClick={() => router.push("/explore")}
196+
sx={{ mb: 2, borderWidth: 1.5 }}
157197
>
158-
Назад к обзору
198+
Назад к исследованию
159199
</Button>
160200

161201
<Box sx={{ mb: 3 }}>
@@ -167,9 +207,6 @@ export default function LibraryDetailView({ libraryId }: LibraryDetailViewProps)
167207
>
168208
{library.name}
169209
</Typography>
170-
<Typography variant="body1" color="text.secondary" paragraph>
171-
{library.description || "Описание отсутствует"}
172-
</Typography>
173210
</Box>
174211

175212
<Stack
@@ -275,8 +312,6 @@ export default function LibraryDetailView({ libraryId }: LibraryDetailViewProps)
275312
}}
276313
>
277314
<Stack spacing={3}>
278-
{healthMetrics && <HealthMetricsDisplay metrics={healthMetrics} />}
279-
280315
<Paper
281316
elevation={0}
282317
sx={{ p: 3, border: "1px solid", borderColor: "divider" }}
@@ -289,11 +324,29 @@ export default function LibraryDetailView({ libraryId }: LibraryDetailViewProps)
289324
{library.description || "Описание отсутствует"}
290325
</Typography>
291326
</Paper>
327+
328+
{healthMetrics && <HealthMetricsDisplay metrics={healthMetrics} />}
292329
</Stack>
293330

294331
<LibraryInfo library={library} />
295332
</Box>
296333
</Container>
334+
335+
<Snackbar
336+
open={shareToast.open}
337+
autoHideDuration={2500}
338+
onClose={() => setShareToast((prev) => ({ ...prev, open: false }))}
339+
anchorOrigin={{ vertical: "bottom", horizontal: "center" }}
340+
>
341+
<Alert
342+
onClose={() => setShareToast((prev) => ({ ...prev, open: false }))}
343+
severity={shareToast.severity}
344+
variant="filled"
345+
sx={{ width: "100%" }}
346+
>
347+
{shareToast.message}
348+
</Alert>
349+
</Snackbar>
297350
</Box>
298351
);
299352
}

0 commit comments

Comments
 (0)