- 上下文清单、任务列表与详情、恢复控制、运行观察、创作对话与消息流、正式变更决策面板、正文写作与候选审阅、资料研究等页面同步本轮后端能力。 - 事件标签表补齐后端事件类型;查询键与生成客户端随 HTTP 契约重新生成。 - 依赖调整后 lockfile 同步;交互用例与浏览器旅程 spec 一并更新。 - 证据:make 前端检查(lint + typecheck + Pi 工具桥 tsc)exit 0;make 前端测试 37 文件 / 120 用例通过。
52 lines
1.8 KiB
TypeScript
52 lines
1.8 KiB
TypeScript
/** 生成过程的消息流:正文段落、材料读取与检查事件按序呈现。 */
|
||
import type { 任务事件 } from "../任务运行/数据";
|
||
import { 事件名 } from "../任务运行/数据";
|
||
import { 事件名补充 } from "./数据";
|
||
|
||
/** 把任务事件流折叠为可读消息;正文段落按写作顺序累积成稿。 */
|
||
export function 折叠消息(事件: 任务事件[]): {
|
||
正文段落: { key: string; text: string }[];
|
||
动作: { key: string; 文案: string }[];
|
||
} {
|
||
const 正文段落: { key: string; text: string }[] = [];
|
||
const 动作: { key: string; 文案: string }[] = [];
|
||
for (const 条 of 事件) {
|
||
const 载荷 = 条.payload;
|
||
if (条.event_type === "text.delta" && typeof 载荷?.文本 === "string") {
|
||
正文段落.push({ key: 条.event_id, text: 载荷.文本 });
|
||
continue;
|
||
}
|
||
const 名 = 事件名补充[条.event_type] ?? 事件名[条.event_type];
|
||
if (名) 动作.push({ key: 条.event_id, 文案: 名 });
|
||
}
|
||
return { 正文段落, 动作 };
|
||
}
|
||
|
||
export function Ui消息流({ 事件 }: { 事件: 任务事件[] }) {
|
||
const { 正文段落, 动作 } = 折叠消息(事件);
|
||
if (!正文段落.length && !动作.length)
|
||
return (
|
||
<p className="muted">
|
||
生成过程的事件会在这里按顺序出现;页面重开后仍可找回。
|
||
</p>
|
||
);
|
||
return (
|
||
<div className="event-panel" aria-live="polite">
|
||
{动作.length > 0 && (
|
||
<ol className="event-list">
|
||
{动作.map((条) => (
|
||
<li key={条.key}>{条.文案}</li>
|
||
))}
|
||
</ol>
|
||
)}
|
||
{正文段落.length > 0 && (
|
||
<article className="draft-stream">
|
||
{正文段落.map((段) => (
|
||
<p key={段.key}>{段.text}</p>
|
||
))}
|
||
</article>
|
||
)}
|
||
</div>
|
||
);
|
||
}
|