1
0

feat: 完成前端重构,采用 Ant Design 5 和完整测试体系

- 采用 Ant Design 5 作为 UI 组件库,替换自定义组件
- 集成 React Router v7 提供路由导航
- 使用 TanStack Query v5 管理数据获取和缓存
- 建立 Vitest + React Testing Library 测试体系
- 添加 Playwright E2E 测试覆盖
- 使用 MSW mock API 响应
- 配置 TypeScript strict 模式
- 采用 SCSS Modules 组织样式
- 更新 OpenSpec 规格以反映前端架构变更
- 归档 frontend-refactor 变更记录
This commit is contained in:
2026-04-16 11:21:48 +08:00
parent c17903dcbc
commit 9359ca7f62
61 changed files with 4588 additions and 1095 deletions

View File

@@ -0,0 +1,94 @@
import { useEffect } from 'react';
import { Modal, Form, Input, Select, Switch } from 'antd';
import type { Provider, Model } from '@/types';
interface ModelFormValues {
id: string;
providerId: string;
modelName: string;
enabled: boolean;
}
interface ModelFormProps {
open: boolean;
model?: Model;
providerId: string;
providers: Provider[];
onSave: (values: ModelFormValues) => void;
onCancel: () => void;
loading: boolean;
}
export function ModelForm({
open,
model,
providerId,
providers,
onSave,
onCancel,
loading,
}: ModelFormProps) {
const [form] = Form.useForm<ModelFormValues>();
const isEdit = !!model;
useEffect(() => {
if (open) {
if (model) {
form.setFieldsValue({
id: model.id,
providerId: model.providerId,
modelName: model.modelName,
enabled: model.enabled,
});
} else {
form.resetFields();
form.setFieldsValue({ providerId });
}
}
}, [open, model, providerId, form]);
return (
<Modal
title={isEdit ? '编辑模型' : '添加模型'}
open={open}
onOk={() => form.submit()}
onCancel={onCancel}
confirmLoading={loading}
okText="保存"
cancelText="取消"
destroyOnClose
>
<Form form={form} layout="vertical" onFinish={onSave} initialValues={{ enabled: true }}>
<Form.Item label="ID" name="id" rules={[{ required: true, message: '请输入模型 ID' }]}>
<Input disabled={isEdit} placeholder="例如: gpt-4o" />
</Form.Item>
<Form.Item
label="供应商"
name="providerId"
rules={[{ required: true, message: '请选择供应商' }]}
>
<Select>
{providers.map((p) => (
<Select.Option key={p.id} value={p.id}>
{p.name}
</Select.Option>
))}
</Select>
</Form.Item>
<Form.Item
label="模型名称"
name="modelName"
rules={[{ required: true, message: '请输入模型名称' }]}
>
<Input placeholder="例如: gpt-4o" />
</Form.Item>
<Form.Item label="启用" name="enabled" valuePropName="checked">
<Switch />
</Form.Item>
</Form>
</Modal>
);
}