feat: 改造云智能体桌面编辑与试用工作区
This commit is contained in:
@@ -63,11 +63,13 @@ it('returns to the last selected thread on remount and requires restoring an arc
|
||||
return base(operation, input);
|
||||
});
|
||||
const first = render(<CloudChat slug={slug} />);
|
||||
fireEvent.click(screen.getByRole('button', { name: '查看历史对话' }));
|
||||
await waitFor(() => expect(screen.getByLabelText('历史对话')).toHaveValue('older'));
|
||||
fireEvent.change(screen.getByLabelText('历史对话'), { target: { value: 'newest' } });
|
||||
await waitFor(() => expect(recent.thread_id).toBe('newest'));
|
||||
first.unmount();
|
||||
const second = render(<CloudChat slug={slug} />);
|
||||
fireEvent.click(screen.getByRole('button', { name: '查看历史对话' }));
|
||||
await waitFor(() => expect(screen.getByLabelText('历史对话')).toHaveValue('newest'));
|
||||
second.unmount();
|
||||
recent = { ...recent, thread_id: 'older' };
|
||||
@@ -241,6 +243,7 @@ it('returns to a newly created conversation from history without remounting the
|
||||
await waitFor(() => expect(screen.getByLabelText('消息')).not.toBeDisabled());
|
||||
fireEvent.change(screen.getByLabelText('消息'), { target: { value: '新对话主题' } });
|
||||
fireEvent.click(screen.getByRole('button', { name: '发送', exact: true }));
|
||||
fireEvent.click(screen.getByRole('button', { name: '查看历史对话' }));
|
||||
await waitFor(() => expect(screen.getByLabelText('历史对话')).toBeEnabled());
|
||||
expect(screen.getByRole('option', { name: '新对话主题 · 已完成' })).toBeInTheDocument();
|
||||
fireEvent.click(screen.getByRole('button', { name: '新对话' }));
|
||||
@@ -280,3 +283,69 @@ it('creates an attachment conversation only when the selected file is confirmed'
|
||||
expect(api.call.mock.calls.filter(call => call[0] === 'createThread')).toHaveLength(1);
|
||||
await waitFor(() => expect(screen.getByText('附件与产物 · 本条消息附带 1 个文件')).toBeVisible());
|
||||
});
|
||||
|
||||
|
||||
it('pins uncertain preview retries to the original request and revision after a draft save', async () => {
|
||||
const base = api.call.getMockImplementation()!;
|
||||
let attempts = 0;
|
||||
api.call.mockImplementation(async (operation, input) => {
|
||||
if (operation === 'preview') {
|
||||
if (++attempts === 1) throw new Error('响应丢失');
|
||||
return { request_id: input.request_id, thread_id: 'thread-1', run_id: 'run-1', status: 'completed', version: 'draft:1' };
|
||||
}
|
||||
if (operation === 'history') return { ...history, run: { ...run, status: 'completed', version: 'draft:1' }, messages: [{ id: 1, role: 'assistant', content: '第一版回答' }] };
|
||||
return base(operation, input);
|
||||
});
|
||||
const view = render(<CloudChat slug={slug} previewRevision={1} />);
|
||||
await waitFor(() => expect(screen.getByLabelText('消息')).toBeEnabled());
|
||||
fireEvent.change(screen.getByLabelText('消息'), { target: { value: '原来的问题' } });
|
||||
fireEvent.click(screen.getByRole('button', { name: '发送', exact: true }));
|
||||
await screen.findByRole('button', { name: '重试本次发送' });
|
||||
view.rerender(<CloudChat slug={slug} previewRevision={2} />);
|
||||
expect(screen.getByRole('button', { name: '用最新草稿试用' })).toBeDisabled();
|
||||
fireEvent.click(screen.getByRole('button', { name: '重试本次发送' }));
|
||||
await screen.findByText('第一版回答');
|
||||
const submissions = api.call.mock.calls.filter(call => call[0] === 'preview');
|
||||
expect(submissions).toHaveLength(2);
|
||||
expect(submissions[0][1]).toEqual(submissions[1][1]);
|
||||
expect(submissions[1][1]).toMatchObject({ expected_revision: 1, query: '原来的问题' });
|
||||
fireEvent.click(screen.getByRole('button', { name: '用最新草稿试用' }));
|
||||
expect(screen.queryByText('第一版回答')).not.toBeInTheDocument();
|
||||
fireEvent.click(screen.getByRole('button', { name: '查看历史对话' }));
|
||||
fireEvent.change(screen.getByLabelText('历史对话'), { target: { value: 'thread-1' } });
|
||||
await screen.findByText('第一版回答');
|
||||
expect(screen.getByText('草稿预览 · 修订 1')).toBeVisible();
|
||||
});
|
||||
|
||||
it('uses Enter to send while preserving Shift+Enter and Chinese IME composition', async () => {
|
||||
const base = api.call.getMockImplementation()!;
|
||||
api.call.mockImplementation(async (operation, input) => operation === 'preview'
|
||||
? { request_id: input.request_id, thread_id: 'thread-1', status: 'completed' } : base(operation, input));
|
||||
render(<CloudChat slug={slug} previewRevision={3} />);
|
||||
const input = screen.getByLabelText('消息');
|
||||
await waitFor(() => expect(input).toBeEnabled());
|
||||
fireEvent.change(input, { target: { value: '整理我的思路' } });
|
||||
fireEvent.keyDown(input, { key: 'Enter', shiftKey: true });
|
||||
fireEvent.keyDown(input, { key: 'Enter', isComposing: true });
|
||||
fireEvent.keyDown(input, { key: 'Enter', keyCode: 229 });
|
||||
expect(api.call.mock.calls.some(call => call[0] === 'preview')).toBe(false);
|
||||
fireEvent.keyDown(input, { key: 'Enter' });
|
||||
await waitFor(() => expect(api.call).toHaveBeenCalledWith('preview', expect.objectContaining({ expected_revision: 3, query: '整理我的思路' })));
|
||||
});
|
||||
|
||||
|
||||
it('does not mark a retained hidden conversation as read until it is shown', async () => {
|
||||
const base = api.call.getMockImplementation()!;
|
||||
api.call.mockImplementation(async (operation, input) => {
|
||||
if (operation === 'threads') return { threads: [{ thread_id: 'thread-1', mode: 'published' }], next_offset: null };
|
||||
if (operation === 'history') return { ...history, run: { ...run, status: 'completed' }, messages: [{ id: 1, role: 'assistant', content: '后台的新回答' }] };
|
||||
if (operation === 'viewed') return { viewed: true };
|
||||
return base(operation, input);
|
||||
});
|
||||
const view = render(<CloudChat slug={slug} activeView={false} />);
|
||||
await screen.findByText('后台的新回答');
|
||||
expect(api.call.mock.calls.some(call => call[0] === 'viewed')).toBe(false);
|
||||
expect(api.remember).not.toHaveBeenCalled();
|
||||
view.rerender(<CloudChat slug={slug} activeView />);
|
||||
await waitFor(() => expect(api.call).toHaveBeenCalledWith('viewed', { thread_id: 'thread-1', run_id: 'run-1' }));
|
||||
});
|
||||
|
||||
Reference in New Issue
Block a user