blob: 705368a827b810173f39087f25df30bcef16f2cf [file] [log] [blame]
import React, { useEffect, useState } from 'react';
import axios from 'axios';
import { useParams } from 'wouter';
import Header from '../../../components/Header';
import './SeedDetail.css';
import { useUser } from '../../../context/UserContext';
import SeedRating from './SeedRating';
import AuthButton from '../../../components/AuthButton';
const SeedDetail = () => {
const params = useParams();
const seed_id = params.id;
const [seed, setSeed] = useState(null);
const [coverImage, setCoverImage] = useState(null);
const [error, setError] = useState(null);
const [comments, setComments] = useState([]);
const [newComment, setNewComment] = useState('');
const { user } = useUser();
const formatImageUrl = (url) => {
if (!url) return '';
const filename = url.split('/').pop();
return `http://localhost:5011/uploads/torrents/${filename}`;
};
useEffect(() => {
if (!seed_id) {
setError('无效的种子ID');
return;
}
const fetchSeedDetail = async () => {
try {
const res = await axios.post(`/seeds/info/${seed_id}`);
if (res.data.code === 0) {
const seedData = res.data.data;
let cover = seedData.imageUrl;
if (!cover && seedData.imgUrl) {
const imgs = seedData.imgUrl
.split(',')
.map((i) => i.trim())
.filter(Boolean);
cover = imgs.length > 0 ? formatImageUrl(imgs[0]) : null;
}
setCoverImage(cover);
setSeed(seedData);
setError(null);
} else {
setError('未能获取种子信息');
}
} catch (err) {
console.error('请求种子详情出错:', err);
setError('获取种子详情失败');
}
};
const fetchComments = async () => {
try {
const res = await axios.get(`/seeds/${seed_id}/comments`);
if (res.data.code === 0) {
setComments(res.data.data || []);
} else {
setComments([]);
}
} catch {
setComments([]);
}
};
fetchSeedDetail();
fetchComments();
}, [seed_id]);
const handleDownload = async (seedId) => {
if (!user || !user.userId) {
alert('请先登录再下载种子文件');
return;
}
try {
const response = await axios.get(`/seeds/${seedId}/download`, {
params: { passkey: user.userId },
responseType: 'blob',
});
const blob = new Blob([response.data], { type: 'application/x-bittorrent' });
const downloadUrl = URL.createObjectURL(blob);
const a = document.createElement('a');
a.href = downloadUrl;
a.download = `${seedId}.torrent`;
a.click();
URL.revokeObjectURL(downloadUrl);
} catch (error) {
console.error('下载失败:', error);
alert('下载失败,请稍后再试。');
}
};
const handleCollect = async () => {
if (!user || !user.userId) {
alert('请先登录再收藏');
return;
}
try {
const res = await axios.post(`/seeds/${seed.id}/favorite-toggle`, null, {
params: { user_id: user.userId },
});
if (res.data.code === 0) {
alert('操作成功');
} else {
alert(res.data.msg || '操作失败');
}
} catch (err) {
console.error('收藏失败:', err);
alert('收藏失败,请稍后再试。');
}
};
const handleAddComment = async () => {
if (!user || !user.userId) {
alert('请登录后发表评论');
return;
}
if (newComment.trim()) {
try {
const res = await axios.post(`/seeds/${seed_id}/comments`, {
user_id: user.userId,
content: newComment,
});
if (res.data.code === 0) {
setComments([...comments, { content: newComment, user: user.username || '匿名用户' }]);
setNewComment('');
} else {
alert(res.data.msg || '评论失败');
}
} catch (err) {
console.error('评论提交失败:', err);
alert('评论失败,请稍后重试');
}
}
};
if (error) {
return (
<div className="seed-detail-page">
<Header />
<div className="seed-detail">
<p className="error-text">{error}</p>
</div>
</div>
);
}
if (!seed) {
return (
<div className="seed-detail-page">
<Header />
<div className="seed-detail">
<p>加载中...</p>
</div>
</div>
);
}
const tags = Array.isArray(seed.tags)
? seed.tags
: typeof seed.tags === 'string'
? seed.tags.split(',').map((t) => t.trim())
: [];
const actors = Array.isArray(seed.actors)
? seed.actors
: typeof seed.actors === 'string'
? seed.actors.split(',').map((a) => a.trim())
: [];
return (
<div className="seed-detail-page">
<Header />
<div className="seed-detail">
<h1>{seed.title}</h1>
<div className="seed-header-container">
<div className="seed-info">
<div className="seed-basic-info">
<p><strong>分类:</strong>{seed.category || '未知'}</p>
<p><strong>发布时间:</strong>{seed.upload_time ? new Date(seed.upload_time).toLocaleString() : '未知'}</p>
<p><strong>标签:</strong>{tags.join(' / ')}</p>
<p><strong>简介:</strong>{seed.description || ''}</p>
<p><strong>大小:</strong>{seed.size || '未知'}</p>
<p><strong>分辨率:</strong>{seed.resolution || '未知'}</p>
<p><strong>片长:</strong>{seed.duration || '未知'}</p>
<p><strong>地区:</strong>{seed.region || '未知'}</p>
<p><strong>下载次数:</strong>{seed.downloads ?? 0}</p>
</div>
{(seed.category === '电影' || seed.category === '电视剧') && (
<div className="seed-media-info">
<p><strong>导演:</strong>{seed.director || '未知'}</p>
<p><strong>编剧:</strong>{seed.writer || '未知'}</p>
<p><strong>主演:</strong>{actors.join(' / ')}</p>
</div>
)}
</div>
<img
src={coverImage || '/default-cover.png'}
alt={seed.title}
className="cover-image"
/>
</div>
<div className="action-buttons">
<AuthButton roles={["cookie", "chocolate", "ice-cream"]} onClick={() => handleDownload(seed.id)}>
下载
</AuthButton>
<AuthButton roles={["cookie", "chocolate", "ice-cream"]} onClick={handleCollect}>
收藏
</AuthButton>
<SeedRating seedId={seed.id} />
</div>
<hr className="divider" />
<h3>评论区</h3>
<div className="comments-section">
<div className="comments-list">
{comments.length === 0 ? (
<p className="no-comments">暂无评论</p>
) : (
comments.map((comment, index) => (
<div key={index} className="comment">
<p className="comment-user">{comment.user}</p>
<p className="comment-content">{comment.content}</p>
</div>
))
)}
</div>
<div className="add-comment-form">
<textarea
placeholder="输入你的评论..."
value={newComment}
onChange={(e) => setNewComment(e.target.value)}
/>
<div className="comment-options">
<button className="btn" onClick={handleAddComment}>发布评论</button>
</div>
</div>
</div>
</div>
</div>
);
};
export default SeedDetail;