Files
gym-manage/docs/superpowers/specs/2026-04-05-role-based-tests-migration-design.md

8.3 KiB
Raw Permalink Blame History

角色测试框架迁移设计文档

日期: 2026-04-05 作者: 张翔 状态: 已批准

1. 背景

问题描述

运行完整E2E测试套件时遇到错误:

TypeError: Cannot redefine property: Symbol($$jest-matchers-object)

根本原因

  • e2e/role-based-tests/目录下存在vitest单元测试文件(.test.ts
  • Playwright运行时会加载这些文件,导致与Playwright的expect冲突
  • 单元测试文件位置不当,不符合项目结构最佳实践

受影响的文件

单元测试文件6个):

  • e2e/role-based-tests/shared/__tests__/permission-helper.test.ts
  • e2e/role-based-tests/shared/__tests__/role-auth-manager.test.ts
  • e2e/role-based-tests/shared/__tests__/test-data-manager.test.ts
  • e2e/role-based-tests/roles/__tests__/admin.role.test.ts
  • e2e/role-based-tests/roles/__tests__/base.role.test.ts
  • e2e/role-based-tests/roles/__tests__/role-factory.test.ts

工具类文件8个):

  • e2e/role-based-tests/shared/auth-helper.ts
  • e2e/role-based-tests/shared/permission-helper.ts
  • e2e/role-based-tests/shared/role-auth-manager.ts
  • e2e/role-based-tests/shared/test-data-manager.ts
  • e2e/role-based-tests/roles/admin.role.ts
  • e2e/role-based-tests/roles/base.role.ts
  • e2e/role-based-tests/roles/role-factory.ts
  • e2e/role-based-tests/roles/user.role.ts

E2E测试文件4个,需要更新导入路径):

  • e2e/role-based-tests/scenarios/authentication/login-flow.spec.ts
  • e2e/role-based-tests/scenarios/authentication/logout-flow.spec.ts
  • e2e/role-based-tests/scenarios/user-management/admin-creates-user.spec.ts
  • e2e/role-based-tests/scenarios/user-management/permission-boundary.spec.ts

2. 解决方案

设计原则

  1. 职责分离:单元测试和E2E测试应该分开存放
  2. 符合最佳实践:单元测试放在src/目录,E2E测试放在e2e/目录
  3. 便于维护:工具类和单元测试在同一目录,便于查找和修改
  4. 避免冲突:彻底解决Playwright与Vitest的冲突问题

文件结构变更

迁移前

e2e/role-based-tests/
├── shared/
│   ├── __tests__/
│   │   ├── permission-helper.test.ts
│   │   ├── role-auth-manager.test.ts
│   │   └── test-data-manager.test.ts
│   ├── auth-helper.ts
│   ├── permission-helper.ts
│   ├── role-auth-manager.ts
│   └── test-data-manager.ts
├── roles/
│   ├── __tests__/
│   │   ├── admin.role.test.ts
│   │   ├── base.role.test.ts
│   │   └── role-factory.test.ts
│   ├── admin.role.ts
│   ├── base.role.ts
│   ├── role-factory.ts
│   └── user.role.ts
└── scenarios/
    ├── authentication/
    │   ├── login-flow.spec.ts
    │   └── logout-flow.spec.ts
    └── user-management/
        ├── admin-creates-user.spec.ts
        └── permission-boundary.spec.ts

迁移后

src/role-based-tests/
├── shared/
│   ├── __tests__/
│   │   ├── permission-helper.test.ts
│   │   ├── role-auth-manager.test.ts
│   │   └── test-data-manager.test.ts
│   ├── auth-helper.ts
│   ├── permission-helper.ts
│   ├── role-auth-manager.ts
│   └── test-data-manager.ts
└── roles/
    ├── __tests__/
    │   ├── admin.role.test.ts
    │   ├── base.role.test.ts
    │   └── role-factory.test.ts
    ├── admin.role.ts
    ├── base.role.ts
    ├── role-factory.ts
    └── user.role.ts

e2e/role-based-tests/
└── scenarios/
    ├── authentication/
    │   ├── login-flow.spec.ts
    │   └── logout-flow.spec.ts
    └── user-management/
        ├── admin-creates-user.spec.ts
        └── permission-boundary.spec.ts

3. 实施步骤

步骤1:创建目标目录结构

mkdir -p src/role-based-tests/shared/__tests__
mkdir -p src/role-based-tests/roles/__tests__

步骤2:迁移shared目录

# 迁移工具类
mv e2e/role-based-tests/shared/*.ts src/role-based-tests/shared/
# 迁移单元测试
mv e2e/role-based-tests/shared/__tests__/*.test.ts src/role-based-tests/shared/__tests__/

步骤3:迁移roles目录

# 迁移角色定义
mv e2e/role-based-tests/roles/*.ts src/role-based-tests/roles/
# 迁移单元测试
mv e2e/role-based-tests/roles/__tests__/*.test.ts src/role-based-tests/roles/__tests__/

步骤4:删除空目录

rm -rf e2e/role-based-tests/shared
rm -rf e2e/role-based-tests/roles

步骤5:更新vitest配置

文件: vitest.config.ts

变更前

include: [
  'src/test/**/*.{test,spec}.{js,ts,jsx,tsx}',
  'e2e/role-based-tests/**/__tests__/*.{test,spec}.{js,ts,jsx,tsx}'
]

变更后

include: [
  'src/test/**/*.{test,spec}.{js,ts,jsx,tsx}',
  'src/__tests__/**/*.{test,spec}.{js,ts,jsx,tsx}'
]

完整配置更新

export default defineConfig({
  plugins: [vue()],
  test: {
    globals: true,
    environment: 'jsdom',
    setupFiles: ['./src/test/setup.ts'],
    include: [
      'src/test/**/*.{test,spec}.{js,ts,jsx,tsx}',
      'src/__tests__/**/*.{test,spec}.{js,ts,jsx,tsx}'
    ],
    exclude: [
      'node_modules/',
      'dist/',
      'e2e/**/*.spec.ts',
      '**/*.d.ts',
      '**/*.config.*',
      '**/mockData',
    ],
    coverage: {
      provider: 'v8',
      reporter: ['text', 'json', 'html', 'lcov'],
      exclude: [
        'node_modules/',
        'src/test/',
        'src/__tests__/',
        '**/*.d.ts',
        '**/*.config.*',
        '**/mockData',
        'e2e/',
      ],
      lines: 80,
      functions: 80,
      branches: 80,
      statements: 80,
    },
  },
  resolve: {
    alias: {
      '@': fileURLToPath(new URL('./src', import.meta.url)),
    },
  },
})

步骤6:更新E2E测试导入路径

文件: e2e/role-based-tests/scenarios/authentication/login-flow.spec.ts

变更前

import { RoleFactory } from '../../roles/role-factory';
import { createAuthenticatedPage } from '../../shared/auth-helper';

变更后

import { RoleFactory } from '@/role-based-tests/roles/role-factory';
import { createAuthenticatedPage } from '@/role-based-tests/shared/auth-helper';

需要更新的文件

  1. e2e/role-based-tests/scenarios/authentication/login-flow.spec.ts
  2. e2e/role-based-tests/scenarios/authentication/logout-flow.spec.ts
  3. e2e/role-based-tests/scenarios/user-management/admin-creates-user.spec.ts
  4. e2e/role-based-tests/scenarios/user-management/permission-boundary.spec.ts

4. 验证步骤

4.1 验证单元测试

npm run test:unit

预期结果

  • 所有单元测试通过
  • vitest能够正确找到src/role-based-tests/下的测试文件

4.2 验证E2E测试

npx playwright test e2e/role-based-tests --project=chromium

预期结果

  • 无TypeError错误
  • 所有E2E测试正常运行

4.3 验证导入路径

npm run type-check

预期结果

  • 无类型错误
  • TypeScript能够正确解析@/别名

5. 风险与缓解措施

风险1:导入路径遗漏

描述:可能有其他文件引用了迁移的文件 缓解措施

  • 使用grep搜索所有引用
  • 运行类型检查确保无遗漏

风险2Playwright配置冲突

描述Playwright可能无法正确解析@/别名 缓解措施

  • Playwright使用自己的配置,不依赖tsconfig.json
  • 如果出现问题,可以使用相对路径作为备选方案

风险3:单元测试依赖问题

描述:单元测试可能依赖E2E测试的某些资源 缓解措施

  • 单元测试使用相对路径导入,不依赖别名
  • 迁移后立即运行测试验证

6. 后续优化建议

  1. 清理诊断代码:移除PasswordDiagnosticHandler.java(生产环境不需要)
  2. 完善测试文档:更新README,说明单元测试和E2E测试的运行方式
  3. CI/CD集成:确保CI流水线正确运行单元测试和E2E测试

7. 参考资料