diff --git a/vehicle-data-platform/apps/web/src/pages/Quality.tsx b/vehicle-data-platform/apps/web/src/pages/Quality.tsx index f126e079..01994295 100644 --- a/vehicle-data-platform/apps/web/src/pages/Quality.tsx +++ b/vehicle-data-platform/apps/web/src/pages/Quality.tsx @@ -18,7 +18,8 @@ function formatLag(value?: number | null) { } function storageReadStatus(health: OpsHealth | null) { - return health?.tdengineWritable && health.mysqlWritable ? 'ok' : 'error'; + if (!health) return 'pending'; + return health.tdengineWritable && health.mysqlWritable ? 'ok' : 'error'; } function formatRequestTimeout(health: OpsHealth | null) { @@ -191,7 +192,9 @@ export function Quality({ {formatRequestTimeout(health)} - {storageReadStatus(health) === 'ok' ? '正常' : '异常'} + + {storageReadStatus(health) === 'pending' ? '检测中' : storageReadStatus(health) === 'ok' ? '正常' : '异常'} + diff --git a/vehicle-data-platform/apps/web/src/test/App.test.tsx b/vehicle-data-platform/apps/web/src/test/App.test.tsx index cee9190e..ba2078c8 100644 --- a/vehicle-data-platform/apps/web/src/test/App.test.tsx +++ b/vehicle-data-platform/apps/web/src/test/App.test.tsx @@ -4101,6 +4101,33 @@ test('opens quality governance from vehicle detail overview', async () => { expect(fetchMock).toHaveBeenCalledWith(expect.stringContaining('/api/quality/issues?keyword=VIN001&limit=20&offset=0'), undefined); }); +test('quality health storage card stays pending before ops health loads', async () => { + window.history.replaceState(null, '', '/#/quality'); + vi.spyOn(globalThis, 'fetch').mockImplementation(async (input) => { + const path = String(input); + if (path.includes('/api/ops/health')) { + return new Promise(() => undefined); + } + return { + ok: true, + json: async () => ({ + data: path.includes('/api/quality/summary') + ? { issueVehicleCount: 0, issueRecordCount: 0, errorCount: 0, warningCount: 0, protocols: [], issueTypes: [] } + : { items: [], total: 0, limit: 20, offset: 0 }, + traceId: 'trace-test', + timestamp: 1783094400000 + }) + } as Response; + }); + + render(); + + expect(await screen.findByRole('heading', { name: '质量治理' })).toBeInTheDocument(); + expect(screen.getByText('存储读取')).toBeInTheDocument(); + expect(screen.getByText('检测中')).toBeInTheDocument(); + expect(screen.queryByText('异常')).not.toBeInTheDocument(); +}); + test('shows vehicle service evidence chain before source details', async () => { window.history.replaceState(null, '', '/#/detail?keyword=VIN001'); vi.spyOn(globalThis, 'fetch').mockImplementation(async (input) => {