Files
crawler-plugin/admin-frontend-vue/e2e/list-time-columns.spec.ts
T
huangzd1997 5b8105ec2b feat(后台管理): 实体管理列表统一展示创建时间/更新时间
用户管理、菜单管理、不符合ASIN、数据去重总数据、查询ASIN、最低价ASIN、
商品类目、密钥管理共 8 个实体管理列表补齐两列。分组管理/店铺密钥/店铺管理
此前已带创建+修改时间,任务列表与统计报表(撞款监控、密钥用量、日志、
记录与版本)不含实体更新语义,均未改动。

关键点——时间列必须由数据库维护,否则新列是假的:
这些表的更新走 selectById → 改字段 → updateById,实体带着读出的旧
updated_at 一起写回。MySQL 规则是「UPDATE 显式给某列赋值时不触发该列的
ON UPDATE 自动更新」,不禁写就会把旧值写回去,更新时间永远冻结在首次写入
时刻。按 V125(biz_file_result)既有样板,给 7 个实体标注
@TableField(insertStrategy=NEVER, updateStrategy=NEVER)。

- V131:users / columns 补 updated_at(幂等 ADD COLUMN,仿 V125 写法)。
  存量行被回填为迁移执行时刻,非真实历史变更时间(历史上无记录,无法还原)
- 实体/VO:AdminUserEntity、PermissionMenuEntity、InvalidAsinDataEntity、
  DedupeTotalDataEntity、ProductCategoryEntity、QueryAsinEntity、
  SkipPriceAsinEntity 加/改写 updatedAt;AdminUserItemVo、PermissionMenuItemVo、
  InvalidAsinDataItemVo、DedupeTotalDataItemVo 补 updatedAt;
  AdminUserSecretRowVo 补 createdAt(行级首次配置时间 = 三模块最早)
- 查询ASIN/最低价ASIN 后端 VO 与前端 model 本就有两字段,仅补渲染
- 前端 8 页表格加列,同步修正空态/加载行的 colspan(手写表格,不同步会错位)
- 测试:align-query-asin / align-skip-price 原断言「不允许有更新时间列」
  (像素复刻旧版),按新需求改为断言两列存在;新增 e2e list-time-columns
  覆盖 8 页表头与真实时间值渲染
2026-09-19 15:53:01 +08:00

45 lines
2.2 KiB
TypeScript
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
import { expect, test, type Page } from '@playwright/test'
// 后台管理列表「创建时间 + 更新时间」两列验收(2026-09-19 需求):
// 8 个实体管理列表统一展示创建/更新时间,数据取自各列表 VO。
// mock 夹具统一给 createdAt=2026-03-01 09:15:00、updatedAt=2026-09-18 16:42:30
// 页面统一经 formatDateTime 归一为「YYYY-MM-DD HH:mm:ss」。
const CREATED = '2026-03-01 09:15:00'
const UPDATED = '2026-09-18 16:42:30'
const PAGES: Array<{ title: string; path: string; heading: string }> = [
{ title: '用户管理', path: '/admin-vue/account/users', heading: '用户列表' },
{ title: '菜单管理', path: '/admin-vue/account/menus', heading: '菜单' },
{ title: '密钥管理', path: '/admin-vue/account/user-secrets', heading: '用户密钥列表' },
{ title: '不符合ASIN数据', path: '/admin-vue/asin-center/invalid', heading: '品牌数据列表' },
{ title: '数据去重总数据', path: '/admin-vue/asin-center/registry', heading: '数据去重总数据' },
{ title: '查询ASIN', path: '/admin-vue/asin-center/query', heading: '查询' },
{ title: '最低价ASIN', path: '/admin-vue/asin-center/skip-price', heading: '最低价' },
{ title: '商品类目', path: '/admin-vue/asin-center/categories', heading: '商品类目' },
]
async function openPage(page: Page, path: string) {
await page.goto(path)
await expect(page.locator('.panel-box table tbody tr').first()).toBeVisible({ timeout: 15000 })
}
for (const spec of PAGES) {
test(`${spec.title}:表格展示创建时间与更新时间`, async ({ page }) => {
const errors: string[] = []
page.on('pageerror', (error) => errors.push(error.message))
await openPage(page, spec.path)
const table = page.locator('.panel-box table').first()
// 表头出现两列
await expect(table.locator('thead')).toContainText('创建时间')
await expect(table.locator('thead')).toContainText('更新时间')
// 数据行渲染出真实时间值(非空、非占位符)
await expect(table.locator('tbody')).toContainText(CREATED)
await expect(table.locator('tbody')).toContainText(UPDATED)
expect(errors).toEqual([])
})
}