876529e668
- 删除 ProjectSupervisorView、SupervisorChatOnlyView、ProjectWorkspaceChatPane、AgentConversationOverlay、DeveloperProjectPanels、DeveloperRuntimePanels 与 features/agent-runtime/panels.tsx - 删除 Supervisor 独立调试窗口:windows.rs 的 supervisor_chat_window_url / open_project_supervisor_chat_window、main.rs 的 invoke 注册、?supervisor-chat 与 ?agent-chat 前端入口、developer.json capability 和对应 Rust 用例 - 删除工作台壳的开发者 Agent 面板:DeveloperAgentPanel、useDeveloperAgentPanel、useDeveloperAgentState、developerAgentControls - App.tsx 删除只服务退役面板的 state/ref/effect/handler(agentConversation*、文件/记忆/资产/画板/预览面板处理、commandLog、llmConfigStatus、editorBaseUrl、回放历史与 trace 面板状态、selectedAgent 等)以及由此产生的空分支,并把 requestRuntimeConfigOpen 接回本地 RuntimeConfigDialog - 立项策划独立成模块:Design Agent 与 Planning V2 的容器和表现移到 view/project-development/planning/(PlanningChatView、PlanningUserInputCard、GddApprovalCard、DesignAgentSurface、PlanningLaneRuntimeStrip、planningLane、planningSessionV2、planningSessionContract) - 改名到中性概念:ProjectSupervisorComponentProps→ProjectChatComponentProps、WorkspaceLauncherShellProps.ProjectSupervisor→ProjectChat、ProjectDevelopmentView.supervisor→chat、orchestrationMode→agentDockVisible、initialSupervisorMessageClaims→initialTurnClaims、ProjectManifestSnapshotSource 'supervisor'→'chat'、CSS project-supervisor-*/project-planning-*→project-chat-* - 删除 PROJECT_SUPERVISOR_AGENT_ID 与 PROJECT_SUPERVISOR_PLAN_SOURCE 常量 - 工作台壳自己订阅 game-creator-manifest-invalidated,用 revision→清单→revision 配对读(source: asset-event)并入 currentProjectContext,且不重新检查项目目录;测试夹具改为按监听器集合广播该事件 - 删除只钉住退役界面的 appSurface 用例(旧调试窗口、开发者面板、Agent 对话浮层、运行历史面板) - 同步文档:ADR、DirectProject 聊天模块抽离实施计划与里程碑、Provider 推理里程碑、策划会话 RuntimeV2、AI 游戏创作实施计划,并在 decision-log 新增 2026-09-19 条 - 删除随退役面板失去调用方的模块与导出:projectSummaryCommands.ts(1054 行旧 Supervisor 斜杠命令处理器)、AGENT_RUN_HISTORY_* 常量、agent-runtime/model.ts 与 project-summary/agentPresentation.ts 里的死导出,以及 agentRunTrace / memoryCommands / projectCommandPolicy 中无调用方的校验与解析函数 - 更新 scripts/check-config.mjs 与 scripts/check-native-shells.mjs 的窗口与命令守卫
108 lines
3.6 KiB
TypeScript
108 lines
3.6 KiB
TypeScript
// @vitest-environment jsdom
|
|
|
|
import { readFileSync } from 'node:fs';
|
|
import { resolve } from 'node:path';
|
|
|
|
import { render } from '@testing-library/react';
|
|
import { describe, expect, it } from 'vitest';
|
|
|
|
import { AgentMessageContent } from '../../../packages/shared/src/components/AgentMessageContent';
|
|
import { ChatMarkdownMessage } from '../src/components/ChatMarkdownMessage';
|
|
import {
|
|
declaration,
|
|
parseStyleSheet,
|
|
resolveDeclarations,
|
|
} from './styleCascade';
|
|
|
|
const sharedCss = readFileSync(
|
|
resolve(
|
|
process.cwd(),
|
|
'packages/shared/src/components/AgentMessageContent.css',
|
|
),
|
|
'utf8',
|
|
);
|
|
const appCss = readFileSync(
|
|
resolve(process.cwd(), 'apps/ai-game-creator-shell/src/styles.css'),
|
|
'utf8',
|
|
);
|
|
const base = '.agent-message-content[data-agent-content]';
|
|
const processTone = ".agent-message-content[data-agent-content='process']";
|
|
|
|
describe('AgentMessageContent', () => {
|
|
it('正文与过程复用表现组件,保留折叠语义和宿主属性', () => {
|
|
const { container } = render(
|
|
<>
|
|
<AgentMessageContent>最终回复</AgentMessageContent>
|
|
<AgentMessageContent as="details" tone="process" aria-label="思考过程">
|
|
<summary>思考过程</summary>
|
|
<pre>先分析需求</pre>
|
|
</AgentMessageContent>
|
|
</>,
|
|
);
|
|
expect(
|
|
container.querySelector('[data-agent-content="body"]')?.textContent,
|
|
).toBe('最终回复');
|
|
const details = container.querySelector('details')!;
|
|
expect(details.getAttribute('data-agent-content')).toBe('process');
|
|
expect(details.getAttribute('aria-label')).toBe('思考过程');
|
|
expect(details.open).toBe(false);
|
|
});
|
|
|
|
it('过程的标题和表格继承层级变量,不用强制字号压回正文大小', () => {
|
|
const { container } = render(
|
|
<AgentMessageContent tone="process">
|
|
<ChatMarkdownMessage
|
|
role="assistant"
|
|
text={
|
|
'# 分析\n\n| 项目 |\n| --- |\n| 内容 |\n\n```js\nconst value = 1;\n```'
|
|
}
|
|
/>
|
|
</AgentMessageContent>,
|
|
);
|
|
expect(container.querySelector('h1')).not.toBeNull();
|
|
expect(container.querySelector('table')).not.toBeNull();
|
|
expect(container.querySelector('pre code .hljs-keyword')).not.toBeNull();
|
|
});
|
|
|
|
it.each([sharedCss + appCss, appCss + sharedCss])(
|
|
'共享层级不受宿主 CSS 加载顺序影响',
|
|
(css) => {
|
|
const rules = parseStyleSheet(css);
|
|
const body = resolveDeclarations(rules, [base], 1024);
|
|
expect(declaration(body, 'font-size')).toBe('14px');
|
|
expect(declaration(body, 'color')).toContain('--platform-text-strong');
|
|
for (const host of [
|
|
['.design-agent-reasoning'],
|
|
['.agent-tool-call-group'],
|
|
[
|
|
'.project-chat-process-card',
|
|
'.game-workbench-chat .project-chat-process-card',
|
|
'.game-workbench-chat .project-chat-surface.is-direct-codex .project-chat-conversation > .project-chat-process-card',
|
|
],
|
|
]) {
|
|
const process = resolveDeclarations(
|
|
rules,
|
|
[base, processTone, ...host],
|
|
1024,
|
|
);
|
|
expect(declaration(process, 'font-size')).toBe('12px');
|
|
expect(declaration(process, 'color')).toContain('--platform-text-soft');
|
|
expect(declaration(process, '--agent-message-heading-size')).toBe(
|
|
'1em',
|
|
);
|
|
}
|
|
const failure = resolveDeclarations(
|
|
rules,
|
|
[
|
|
'.agent-tool-call-row-status',
|
|
".agent-tool-call-group-row[data-status='failed'] .agent-tool-call-row-status",
|
|
],
|
|
1024,
|
|
);
|
|
expect(declaration(failure, 'color')).toBe(
|
|
'var(--platform-button-danger-text)',
|
|
);
|
|
},
|
|
);
|
|
});
|