'use client'; import { useState, useEffect } from 'react'; import { Box, Typography, Divider, Paper } from '@mui/material'; import { toast } from 'sonner'; import StarRating from '@/components/datasets/StarRating'; import TagSelector from '@/components/datasets/TagSelector'; import NoteInput from '@/components/datasets/NoteInput'; import { useTranslation } from 'react-i18next'; export default function MetadataEditor({ dataset, projectId, onUpdate }) { const { t } = useTranslation(); const [availableTags, setAvailableTags] = useState([]); const [loading, setLoading] = useState(false); // 解析数据集中的标签 const parseDatasetTags = tagsString => { try { return JSON.parse(tagsString || '[]'); } catch (e) { return []; } }; // 本地状态管理,从 props 初始化 const [localScore, setLocalScore] = useState(dataset?.score || 0); const [localTags, setLocalTags] = useState(() => { const tags = parseDatasetTags(dataset?.tags); // 确保 localTags 始终是数组 return Array.isArray(tags) ? tags : []; }); const [localNote, setLocalNote] = useState(dataset?.note || ''); // 获取项目中已使用的标签 useEffect(() => { const fetchAvailableTags = async () => { try { const response = await fetch(`/api/projects/${projectId}/image-datasets/tags`); if (response.ok) { const data = await response.json(); setAvailableTags(data.tags || []); } } catch (error) { console.error('获取可用标签失败:', error); } }; if (projectId) { fetchAvailableTags(); } }, [projectId]); // 同步props中的dataset到本地状态 useEffect(() => { if (dataset) { setLocalScore(dataset.score || 0); const tags = parseDatasetTags(dataset.tags); setLocalTags(Array.isArray(tags) ? tags : []); setLocalNote(dataset.note || ''); } }, [dataset]); // 更新数据集元数据 const updateMetadata = async updates => { if (loading) return; // 立即更新本地状态,提升响应速度 if (updates.score !== undefined) { setLocalScore(updates.score); } // 注意:tags 已经在 handleTagsChange 中更新过了,这里不需要再更新 if (updates.note !== undefined) { setLocalNote(updates.note); } setLoading(true); try { // 调用父组件的更新方法 if (onUpdate) { await onUpdate(updates); } toast.success(t('imageDatasets.updateSuccess', '更新成功')); } catch (error) { console.error('更新数据集元数据失败:', error); toast.error(t('imageDatasets.updateFailed', '更新失败')); // 出错时恢复本地状态 if (updates.score !== undefined) { setLocalScore(dataset?.score || 0); } if (updates.tags !== undefined) { // 恢复为原始的标签数组 const tags = parseDatasetTags(dataset?.tags); setLocalTags(Array.isArray(tags) ? tags : []); } if (updates.note !== undefined) { setLocalNote(dataset?.note || ''); } } finally { setLoading(false); } }; // 处理评分变更 const handleScoreChange = newScore => { updateMetadata({ score: newScore }); }; // 处理标签变更 const handleTagsChange = newTags => { // 立即更新本地状态(保持为数组) setLocalTags(newTags); // 发送给父组件时转换为 JSON 字符串 updateMetadata({ tags: JSON.stringify(newTags) }); }; // 处理备注变更 const handleNoteChange = newNote => { updateMetadata({ note: newNote }); }; return ( {/* 评分区域 */} {t('datasets.rating', '评分')} {/* 标签区域 */} {t('datasets.customTags', '自定义标签')} {/* 备注区域 */} ); }