You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 
 
 

80 lines
3.9 KiB

  1. import type { Page, Route } from '@playwright/test'
  2. import { captureScreenshot, expect, test } from './fixtures'
  3. const json = (route: Route, data: unknown) => route.fulfill({
  4. status: 200,
  5. contentType: 'application/json',
  6. body: JSON.stringify({ code: 0, message: '成功', data, timestamp: Date.now(), requestId: 'zentao-user-regression' }),
  7. })
  8. const roles = [
  9. { id: '1', code: 'admin', name: '管理员', shortName: '管', enabled: true, builtIn: true, superAdmin: true, dataScope: 'ALL', dataVersion: 1 },
  10. { id: '2', code: 'teacher', name: '教员', shortName: '教', enabled: true, builtIn: true, superAdmin: false, dataScope: 'SYSTEM', dataVersion: 1 },
  11. ]
  12. async function mockUsers(page: Page) {
  13. let userRequests = 0
  14. let statsRequests = 0
  15. await page.route(/\/api\/(?:auth\/v1|v1)\//, async (route) => {
  16. const path = new URL(route.request().url()).pathname
  17. if (path.endsWith('/auth/me')) return json(route, {
  18. userId: '1', username: 'admin', displayName: '系统管理员', departmentId: '100', departmentName: '数字人平台',
  19. activeRoleId: '1', roles, authorizationMode: 'SINGLE_ACTIVE', mustChangePassword: false,
  20. permissions: ['system.users', 'system.users.update', 'system.users.reset-password'],
  21. })
  22. if (path.endsWith('/departments/tree')) return json(route, [{
  23. id: '100', code: 'ORG-100', name: '数字人平台', parentId: null, enabled: true, isRoot: true,
  24. sortOrder: 10, directUserCount: 1, directChildCount: 0, dataVersion: 1, children: [],
  25. }])
  26. if (path.endsWith('/roles/all')) return json(route, roles)
  27. if (path.endsWith('/users/stats')) {
  28. statsRequests += 1
  29. const pending = statsRequests === 1 ? 2 : 1
  30. return json(route, { total: 12, enabled: 12, disabled: 0, passwordPending: pending, mustChangePasswordCount: pending })
  31. }
  32. if (path.endsWith('/users')) {
  33. userRequests += 1
  34. return json(route, {
  35. records: [{
  36. id: '9', username: 'teacher09', displayName: '测试教员', departmentId: '100', departmentName: '数字人平台',
  37. roleIds: ['2', '1'], defaultRoleId: '1', enabled: true, isProtected: false,
  38. credentialConfigured: true, mustChangePassword: userRequests === 1, lastLoginAt: null, dataVersion: 1,
  39. }],
  40. total: 1, page: 1, size: 20,
  41. })
  42. }
  43. if (path.endsWith('/menus/navigation')) return json(route, [])
  44. if (path.endsWith('/system-config/public')) return json(route, { systemName: '数字人平台' })
  45. return json(route, {})
  46. })
  47. await page.addInitScript(() => {
  48. window.sessionStorage.setItem('ai-person:web:access-token:v1', 'zentao-user-regression-token')
  49. })
  50. return {
  51. statsRequests: () => statsRequests,
  52. }
  53. }
  54. test('Bug 860、862:默认角色置顶且搜索同步刷新全局待改密统计', async ({ page }, testInfo) => {
  55. const requests = await mockUsers(page)
  56. await page.goto('/organization/users')
  57. const row = page.locator('.users-table .el-table__row').filter({ hasText: '测试教员' })
  58. const roleTags = row.locator('.role-tags .el-tag')
  59. await expect(roleTags).toHaveCount(2)
  60. await expect(roleTags.first()).toContainText('管理员')
  61. await expect(roleTags.first()).toContainText('默认')
  62. await expect(page.getByTestId('user-inline-statistics')).toContainText('全局待改密 2')
  63. const searchInput = page.getByPlaceholder('请输入姓名、账号、部门或角色')
  64. await searchInput.fill('teacher09')
  65. await searchInput.press('Enter')
  66. await expect.poll(requests.statsRequests).toBe(2)
  67. await expect(page.getByTestId('user-inline-statistics')).toContainText('全局待改密 1')
  68. await expect(row.getByText('待修改密码', { exact: true })).toHaveCount(0)
  69. await expect(page).toHaveURL(/\/organization\/users(?:[?#].*)?$/)
  70. await captureScreenshot(page, testInfo, 'bugs-860-862-user-role-and-pending-statistics')
  71. await expect(page).toHaveURL(/\/organization\/users(?:[?#].*)?$/)
  72. })