This commit is contained in:
fengxiangdebaozi committed 2026-06-24 19:48:15 +08:00
commit 3ea8e73389
61 files changed
+734 -429

No files matched your search

+1 -1
View File
@@ -186,7 +186,7 @@ export default function AgentChatPage({
const lastHuman = [...msgs].reverse().find((m) => (m as { type?: string }).type === "human");
writeYLog({
optType: OptType.other,
optDetail: "B1-CM助手-专家代理问答",
optDetail: "CM助手-全量-专家代理问答",
url: `/api/threads/${threadId ?? ""}/runs/stream`,
reqParam: { agent_id, question: lastHuman ? textOfMessage(lastHuman) : "" },
returnParam: { data: lastAi ? textOfMessage(lastAi) : "" },
+1 -1
View File
@@ -195,7 +195,7 @@ export default function ChatPage() {
const lastHuman = [...msgs].reverse().find((m) => (m as { type?: string }).type === "human");
writeYLog({
optType: OptType.other,
optDetail: "B1-CM助手-专家代理问答",
optDetail: "CM助手-全量-专家代理问答",
url: `/api/threads/${threadId ?? ""}/runs/stream`,
reqParam: { agent_id: selectedAgentId, question: lastHuman ? textOfMessage(lastHuman) : "" },
returnParam: { data: lastAi ? textOfMessage(lastAi) : "" },
+1 -1
View File
@@ -200,7 +200,7 @@ export default function LoginPage() {
void fetchYLogConfig();
writeYLog({
optType: OptType.login,
optDetail: 'B1-CM助手-登录',
optDetail: 'CM助手-全量-登录',
url: '/api/v1/auth/login/token',
reqParam: { username: loginUserName || auth.user_id },
returnParam: { user_id: auth.user_id },
@@ -154,6 +154,7 @@ function SourcesDialog({
isLoadingSources,
selectedSourceIds,
pendingSources,
pendingImportTitles,
onToggle,
onDelete,
}: {
@@ -164,6 +165,7 @@ function SourcesDialog({
isLoadingSources: boolean;
selectedSourceIds: number[];
pendingSources: Map<string, { id?: number; title: string }>;
pendingImportTitles: string[];
onToggle: (id: number) => void;
onDelete: (id: number) => void;
}) {
@@ -216,6 +218,14 @@ function SourcesDialog({
.map(([taskId, s]) => (
<PendingSourceCard key={taskId} title={s.title} />
))}
{pendingImportTitles
.filter((t) => !sources.some((src) => {
const srcTitle = src.title ?? (src.document as { title?: string } | undefined)?.title ?? "";
return srcTitle === t;
}))
.map((t) => (
<PendingSourceCard key={`import-${t}`} title={t} />
))}
{sources.map((src) => (
<SourceCard
key={src.id}
@@ -269,6 +279,8 @@ export default function StudioNotebookDetailPage({
// 轮询任务管理:task_id -> 来源信息
const [pendingSources, setPendingSources] = useState<Map<string, { id?: number; title: string }>>(new Map());
const pollingIntervalRef = useRef<ReturnType<typeof setInterval> | null>(null);
// 同步导入(搜索导入)的占位标题列表,sources 刷新后按标题匹配移除
const [pendingImportTitles, setPendingImportTitles] = useState<string[]>([]);
useEffect(() => {
if (!selectedModel && models.length > 0) {
@@ -287,20 +299,25 @@ export default function StudioNotebookDetailPage({
}
}, [sources, notebook?.id, initializedForNotebook]);
// sources 刷新后,将轮询成功的来源(按标题匹配)自动选中
// sources 刷新后,将轮询成功/同步导入的来源(按标题匹配)自动选中,并移除占位卡
useEffect(() => {
if (pendingSelectTitlesRef.current.size === 0) return;
const matched = sources.filter((s) => {
const title = s.title ?? (s.document as { title?: string } | undefined)?.title ?? "";
return pendingSelectTitlesRef.current.has(title);
});
if (matched.length > 0) {
setSelectedSourceIds((prev) => [...new Set([...prev, ...matched.map((s) => s.id)])]);
matched.forEach((s) => {
const title = s.title ?? (s.document as { title?: string } | undefined)?.title ?? "";
pendingSelectTitlesRef.current.delete(title);
});
const getTitle = (s: SourceItem) =>
s.title ?? (s.document as { title?: string } | undefined)?.title ?? "";
if (pendingSelectTitlesRef.current.size > 0) {
const matched = sources.filter((s) => pendingSelectTitlesRef.current.has(getTitle(s)));
if (matched.length > 0) {
setSelectedSourceIds((prev) => [...new Set([...prev, ...matched.map((s) => s.id)])]);
matched.forEach((s) => pendingSelectTitlesRef.current.delete(getTitle(s)));
}
}
setPendingImportTitles((prev) => {
if (prev.length === 0) return prev;
const sourceTitles = new Set(sources.map(getTitle));
const remaining = prev.filter((t) => !sourceTitles.has(t));
return remaining.length === prev.length ? prev : remaining;
});
}, [sources]);
const citationRehypePlugins = useMemo(() => {
const mapped = sources.map((s) => ({
@@ -392,6 +409,12 @@ export default function StudioNotebookDetailPage({
return newMap;
});
}
// 同步导入(status=success,无 task_id):立刻显示占位卡 + 等 sources 刷新后自动选中
const syncTitles = uploadedSources.filter(s => s.status === 'success' && s.title).map(s => s.title);
if (syncTitles.length > 0) {
syncTitles.forEach(t => pendingSelectTitlesRef.current.add(t));
setPendingImportTitles(prev => [...new Set([...prev, ...syncTitles])]);
}
// 刷新来源列表
void queryClient.invalidateQueries({ queryKey: ["studio", "sources", notebook.id] });
// 刷新 notebooks 数据以更新 source_count
@@ -854,6 +877,7 @@ export default function StudioNotebookDetailPage({
isLoadingSources={isLoadingSources}
selectedSourceIds={selectedSourceIds}
pendingSources={pendingSources}
pendingImportTitles={pendingImportTitles}
onToggle={handleToggleSource}
onDelete={handleDeleteSource}
/>