Procházet zdrojové kódy

✅ test(area-management-ui-mt): 完善4级区域测试覆盖并中文化测试名称

- 添加4个4级区域集成测试用例,覆盖乡镇层级功能
- 将集成测试和单元测试名称全部改为中文描述
- 验证4级区域(省→市→区→乡镇)的完整CRUD操作
- 确保测试覆盖乡镇创建、状态切换和删除功能

🤖 Generated with [Claude Code](https://claude.ai/code)
via [Happy](https://happy.engineering)

Co-Authored-By: Claude <noreply@anthropic.com>
Co-Authored-By: Happy <yesreply@happy.engineering>
yourname před 1 měsícem
rodič
revize
8e5066c927

+ 254 - 8
packages/area-management-ui-mt/tests/integration/area-management.integration.test.tsx

@@ -75,12 +75,12 @@ const TestWrapper: React.FC<{ children: React.ReactNode }> = ({ children }) => {
   );
 };
 
-describe('AreaManagement Integration Tests', () => {
+describe('区域管理集成测试', () => {
   beforeEach(() => {
     vi.clearAllMocks();
   });
 
-  it('should render area management component with title', async () => {
+  it('应该渲染区域管理组件并显示标题', async () => {
     // Mock successful API response for province data
     (areaClient.index.$get as any).mockResolvedValueOnce(createMockResponse(200, {
       data: [
@@ -112,7 +112,7 @@ describe('AreaManagement Integration Tests', () => {
     });
   });
 
-  it('should show loading state when fetching data', async () => {
+  it('应该在获取数据时显示加载状态', async () => {
     // Mock delayed API response
     (areaClient.index.$get as any).mockImplementationOnce(() =>
       new Promise(resolve => setTimeout(() => resolve(createMockResponse(200, { data: [] })), 100))
@@ -133,7 +133,7 @@ describe('AreaManagement Integration Tests', () => {
     });
   });
 
-  it('should show empty state when no data', async () => {
+  it('应该在无数据时显示空状态', async () => {
     // Mock empty API response
     (areaClient.index.$get as any).mockResolvedValueOnce(createMockResponse(200, { data: [] }));
 
@@ -149,7 +149,7 @@ describe('AreaManagement Integration Tests', () => {
     });
   });
 
-  it('should open create dialog when clicking add button', async () => {
+  it('应该在点击新增按钮时打开创建对话框', async () => {
     // Mock successful API response
     (areaClient.index.$get as any).mockResolvedValueOnce(createMockResponse(200, {
       data: [
@@ -187,7 +187,7 @@ describe('AreaManagement Integration Tests', () => {
     });
   });
 
-  it('should handle API errors gracefully', async () => {
+  it('应该优雅地处理API错误', async () => {
     // Mock API error
     (areaClient.index.$get as any).mockRejectedValueOnce(new Error('API Error'));
 
@@ -204,7 +204,7 @@ describe('AreaManagement Integration Tests', () => {
     });
   });
 
-  it('should complete create and delete workflow', async () => {
+  it('应该完成创建和删除工作流程', async () => {
     const { toast } = await import('sonner');
 
     // Mock initial areas data
@@ -298,7 +298,7 @@ describe('AreaManagement Integration Tests', () => {
     });
   });
 
-  it('should handle API errors in CRUD operations', async () => {
+  it('应该处理CRUD操作中的API错误', async () => {
     const { areaClient } = await import('../../src/api/areaClient');
     const { toast } = await import('sonner');
 
@@ -354,4 +354,250 @@ describe('AreaManagement Integration Tests', () => {
       expect(toast.error).toHaveBeenCalledWith('创建失败,请重试');
     });
   });
+
+  it('应该支持4级区域层级(省→市→区→乡镇)', async () => {
+    // Mock initial data with all levels
+    const mockAreas = {
+      data: [
+        {
+          id: 1,
+          tenantId: 1,
+          name: '北京市',
+          code: '110000',
+          level: 1,
+          parentId: null,
+          isDisabled: 0
+        },
+        {
+          id: 2,
+          tenantId: 1,
+          name: '北京市市辖区',
+          code: '110100',
+          level: 2,
+          parentId: 1,
+          isDisabled: 0
+        },
+        {
+          id: 3,
+          tenantId: 1,
+          name: '朝阳区',
+          code: '110105',
+          level: 3,
+          parentId: 2,
+          isDisabled: 0
+        },
+        {
+          id: 4,
+          tenantId: 1,
+          name: '建国门街道',
+          code: '110105001',
+          level: 4,
+          parentId: 3,
+          isDisabled: 0
+        }
+      ]
+    };
+
+    (areaClient.index.$get as any).mockResolvedValue(createMockResponse(200, mockAreas));
+
+    render(
+      <TestWrapper>
+        <AreaManagement />
+      </TestWrapper>
+    );
+
+    // Wait for all level data to load
+    await waitFor(() => {
+      expect(screen.getByText('北京市')).toBeInTheDocument();
+      expect(screen.getByText('北京市市辖区')).toBeInTheDocument();
+      expect(screen.getByText('朝阳区')).toBeInTheDocument();
+      expect(screen.getByText('建国门街道')).toBeInTheDocument();
+    });
+
+    // Verify all levels are displayed correctly
+    expect(screen.getByText('北京市')).toBeInTheDocument();
+    expect(screen.getByText('北京市市辖区')).toBeInTheDocument();
+    expect(screen.getByText('朝阳区')).toBeInTheDocument();
+    expect(screen.getByText('建国门街道')).toBeInTheDocument();
+  });
+
+  it('应该成功创建4级区域(乡镇)', async () => {
+    const { toast } = await import('sonner');
+
+    // Mock initial data with district
+    const mockAreas = {
+      data: [
+        {
+          id: 3,
+          tenantId: 1,
+          name: '朝阳区',
+          code: '110105',
+          level: 3,
+          parentId: 2,
+          isDisabled: 0
+        }
+      ]
+    };
+
+    (areaClient.index.$get as any).mockResolvedValue(createMockResponse(200, mockAreas));
+
+    render(
+      <TestWrapper>
+        <AreaManagement />
+      </TestWrapper>
+    );
+
+    // Wait for data to load
+    await waitFor(() => {
+      expect(screen.getByText('朝阳区')).toBeInTheDocument();
+    });
+
+    // Click add child button for district
+    const addChildButtons = screen.getAllByRole('button', { name: '新增乡镇' });
+    fireEvent.click(addChildButtons[0]);
+
+    // Check if town creation dialog opens
+    await waitFor(() => {
+      expect(screen.getByRole('heading', { name: '新增乡镇' })).toBeInTheDocument();
+      expect(screen.getByText('在区县 "朝阳区" 下新增街道/乡镇')).toBeInTheDocument();
+    });
+
+    // Fill town form
+    const nameInput = screen.getByPlaceholderText('输入区域名称');
+    const codeInput = screen.getByPlaceholderText('输入行政区划代码');
+
+    fireEvent.change(nameInput, { target: { value: '建国门街道' } });
+    fireEvent.change(codeInput, { target: { value: '110105001' } });
+
+    // Mock successful town creation
+    (areaClient.index.$post as any).mockResolvedValue(createMockResponse(201, { id: 4, name: '建国门街道' }));
+
+    const submitButton = screen.getByText('创建');
+    fireEvent.click(submitButton);
+
+    await waitFor(() => {
+      expect(areaClient.index.$post).toHaveBeenCalledWith({
+        json: {
+          tenantId: 1,
+          name: '建国门街道',
+          code: '110105001',
+          level: 4,
+          parentId: 3,
+          isDisabled: 0
+        }
+      });
+      expect(toast.success).toHaveBeenCalledWith('省市区创建成功');
+    });
+  });
+
+  it('应该处理4级区域状态切换', async () => {
+    const { toast } = await import('sonner');
+
+    // Mock initial data with town
+    const mockAreas = {
+      data: [
+        {
+          id: 4,
+          tenantId: 1,
+          name: '建国门街道',
+          code: '110105001',
+          level: 4,
+          parentId: 3,
+          isDisabled: 0
+        }
+      ]
+    };
+
+    (areaClient.index.$get as any).mockResolvedValue(createMockResponse(200, mockAreas));
+
+    render(
+      <TestWrapper>
+        <AreaManagement />
+      </TestWrapper>
+    );
+
+    // Wait for data to load
+    await waitFor(() => {
+      expect(screen.getByText('建国门街道')).toBeInTheDocument();
+    });
+
+    // Click toggle status button for town
+    const toggleButtons = screen.getAllByRole('button', { name: '禁用' });
+    fireEvent.click(toggleButtons[0]);
+
+    // Check if status toggle dialog opens
+    await waitFor(() => {
+      expect(screen.getByRole('heading', { name: '禁用确认' })).toBeInTheDocument();
+      expect(screen.getByText('确定要禁用省市区 "建国门街道" 吗?')).toBeInTheDocument();
+    });
+
+    // Mock successful status toggle
+    (areaClient[':id'].$put as any).mockResolvedValue(createMockResponse(200));
+
+    const confirmButton = screen.getByRole('button', { name: '确认' });
+    fireEvent.click(confirmButton);
+
+    await waitFor(() => {
+      expect(areaClient[':id'].$put).toHaveBeenCalledWith({
+        param: { id: 4 },
+        json: { isDisabled: 1 }
+      });
+      expect(toast.success).toHaveBeenCalledWith('省市区禁用成功');
+    });
+  });
+
+  it('应该成功删除4级区域(乡镇)', async () => {
+    const { toast } = await import('sonner');
+
+    // Mock initial data with town
+    const mockAreas = {
+      data: [
+        {
+          id: 4,
+          tenantId: 1,
+          name: '建国门街道',
+          code: '110105001',
+          level: 4,
+          parentId: 3,
+          isDisabled: 0
+        }
+      ]
+    };
+
+    (areaClient.index.$get as any).mockResolvedValue(createMockResponse(200, mockAreas));
+
+    render(
+      <TestWrapper>
+        <AreaManagement />
+      </TestWrapper>
+    );
+
+    // Wait for data to load
+    await waitFor(() => {
+      expect(screen.getByText('建国门街道')).toBeInTheDocument();
+    });
+
+    // Click delete button for town
+    const deleteButtons = screen.getAllByRole('button', { name: '删除' });
+    fireEvent.click(deleteButtons[0]);
+
+    // Check if delete confirmation dialog opens
+    await waitFor(() => {
+      expect(screen.getByRole('heading', { name: '确认删除' })).toBeInTheDocument();
+      expect(screen.getByText('确定要删除省市区 "建国门街道" 吗?此操作不可恢复。')).toBeInTheDocument();
+    });
+
+    // Mock successful deletion
+    (areaClient[':id'].$delete as any).mockResolvedValue(createMockResponse(204));
+
+    const confirmDeleteButton = screen.getByRole('button', { name: '确认删除' });
+    fireEvent.click(confirmDeleteButton);
+
+    await waitFor(() => {
+      expect(areaClient[':id'].$delete).toHaveBeenCalledWith({
+        param: { id: 4 }
+      });
+      expect(toast.success).toHaveBeenCalledWith('省市区删除成功');
+    });
+  });
 });

+ 7 - 7
packages/area-management-ui-mt/tests/unit/useAreas.test.tsx

@@ -72,12 +72,12 @@ const createWrapper = () => {
   );
 };
 
-describe('useAreas Hook', () => {
+describe('useAreas Hook测试', () => {
   beforeEach(() => {
     vi.clearAllMocks();
   });
 
-  it('should fetch areas successfully', async () => {
+  it('应该成功获取区域数据', async () => {
     const mockAreas = [
       {
         id: 1,
@@ -116,7 +116,7 @@ describe('useAreas Hook', () => {
     });
   });
 
-  it('should handle fetch areas error', async () => {
+  it('应该处理获取区域数据错误', async () => {
     (areaClient.index.$get as any).mockRejectedValueOnce(new Error('API Error'));
 
     const { result } = renderHook(() => useAreas(), {
@@ -131,7 +131,7 @@ describe('useAreas Hook', () => {
     expect(result.current.error).toBeDefined();
   });
 
-  it('should create area successfully', async () => {
+  it('应该成功创建区域', async () => {
     const mockAreaData = {
       tenantId: 1,
       name: '北京市',
@@ -154,7 +154,7 @@ describe('useAreas Hook', () => {
     });
   });
 
-  it('should update area successfully', async () => {
+  it('应该成功更新区域', async () => {
     const mockUpdateData = {
       tenantId: 1,
       name: '北京市更新',
@@ -181,7 +181,7 @@ describe('useAreas Hook', () => {
     });
   });
 
-  it('should delete area successfully', async () => {
+  it('应该成功删除区域', async () => {
     (areaClient[':id'].$delete as any).mockResolvedValueOnce(createMockResponse(204));
 
     const { result } = renderHook(() => useDeleteArea(), {
@@ -195,7 +195,7 @@ describe('useAreas Hook', () => {
     });
   });
 
-  it('should toggle area status successfully', async () => {
+  it('应该成功切换区域状态', async () => {
     (areaClient[':id'].$put as any).mockResolvedValueOnce(createMockResponse(200));
 
     const { result } = renderHook(() => useToggleAreaStatus(), {