Skip to content

Commit dd58370

Browse files
committed
e2e(FR-2472): fix model-card-v2 flag persistence and serving submit resilience
1 parent ebdada1 commit dd58370

6 files changed

Lines changed: 246 additions & 68 deletions

File tree

e2e/E2E_COVERAGE_REPORT.md

Lines changed: 13 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -22,9 +22,9 @@
2222
| Dashboard | `/dashboard` | 9 | 7 | 🔶 78% |
2323
| Session List | `/session` | 22 | 14 | 🔶 64% |
2424
| Session Launcher | `/session/start` | 14 | 3 | 🔶 21% |
25-
| Serving | `/serving` | 7 | 0 | ❌ 0% |
25+
| Serving | `/serving` | 7 | 2 | 🔶 29% |
2626
| Endpoint Detail | `/serving/:serviceId` | 20 | 9 | 🔶 45% |
27-
| Service Launcher | `/service/start` | 5 | 0 | ❌ 0% |
27+
| Service Launcher | `/service/start` | 5 | 1 | 🔶 20% |
2828
| VFolder / Data | `/data` | 45 | 32 | 🔶 71% |
2929
| Model Store | `/model-store` | 6 | 6 | ✅ 100% |
3030
| Admin Model Store | `/admin-model-store` | 22 | 22 | ✅ 100% |
@@ -46,7 +46,11 @@
4646
| App Launcher | (modal) | 18 | 10 | 🔶 56% |
4747
| Chat | `/chat/:id?` | 6 | 6 | ✅ 100% |
4848
| Plugin System | (config-based) | 12 | 12 | ✅ 100% |
49+
<<<<<<< HEAD
4950
| **Total** | | **357** | **204** | **57%** |
51+
=======
52+
| **Total** | | **372** | **228** | **61%** |
53+
>>>>>>> a3f2e0fba (e2e(FR-2472): align route table test with current BAIRouteNodes columns)
5054
5155
---
5256

@@ -223,7 +227,7 @@
223227

224228
### 6. Serving / Model Service (`/serving`)
225229

226-
**Test files:** None (visual regression only: [`e2e/visual_regression/serving/serving_page.test.ts`](visual_regression/serving/serving_page.test.ts))
230+
**Test files:** [`e2e/serving/serving-deploy-lifecycle.spec.ts`](serving/serving-deploy-lifecycle.spec.ts) (integration, `@integration @serving`)
227231

228232
**Filter:** Active | Destroyed (radio)
229233
**Primary action:** "Start Service" → navigates to `/service/start`
@@ -232,15 +236,15 @@
232236

233237
| Feature | Status | Test |
234238
| --------------------------------------------------------- | ------ | ---- |
235-
| Endpoint list rendering | | - |
239+
| Endpoint list rendering | | `Admin can deploy a model service via ServiceLauncher UI` (verifies row visible in serving list) |
236240
| "Start Service" → navigate to `/service/start` || - |
237241
| Endpoint name click → EndpointDetailPage || - |
238242
| Status filtering (Active/Destroyed) || - |
239243
| Property filtering || - |
240244
| Edit endpoint → navigate to `/service/update/:endpointId` || - |
241-
| Delete endpoint → confirm dialog | | - |
245+
| Delete endpoint → confirm dialog | | `Admin can terminate a deployed service` |
242246

243-
**Coverage: ❌ 0/7 features**
247+
**Coverage: 🔶 2/7 features**
244248

245249
---
246250

@@ -281,17 +285,17 @@
281285

282286
### 8. Service Launcher (`/service/start`, `/service/update/:endpointId`)
283287

284-
**Test files:** None
288+
**Test files:** [`e2e/serving/serving-deploy-lifecycle.spec.ts`](serving/serving-deploy-lifecycle.spec.ts) (integration, `@integration @serving`)
285289

286290
| Feature | Status | Test |
287291
| ----------------------- | ------ | ---- |
288-
| Create model service | | - |
292+
| Create model service | | `Admin can deploy a model service via ServiceLauncher UI` |
289293
| Update existing service || - |
290294
| Resource configuration || - |
291295
| Model folder selection || - |
292296
| Form validation || - |
293297

294-
**Coverage: ❌ 0/5 features**
298+
**Coverage: 🔶 1/5 features**
295299

296300
---
297301

e2e/serving/endpoint-route-table.spec.ts

Lines changed: 36 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -137,11 +137,11 @@ test.describe(
137137
await expect(
138138
card.getByRole('columnheader', { name: 'Status', exact: true }),
139139
).toBeVisible();
140+
// TODO(needs-backend): Re-enable when BAIRouteNodes exposes the Traffic
141+
// Status column. It is currently commented out in BAIRouteNodes.tsx
142+
// pending backend support for per-route traffic status (FR-2591).
140143
await expect(
141-
card.getByRole('columnheader', { name: 'Traffic Status' }),
142-
).toBeVisible();
143-
await expect(
144-
card.getByRole('columnheader', { name: 'Traffic Ratio' }),
144+
card.getByRole('columnheader', { name: 'Created At' }),
145145
).toBeVisible();
146146
});
147147

@@ -305,7 +305,11 @@ test.describe(
305305
// 3. Property Filter
306306
// ─────────────────────────────────────────────────────────────────────────
307307

308-
test('3.1 Admin can see the Traffic Status filter property in the property filter selector', async ({
308+
// TODO(needs-backend): Re-enable when the EndpointDetailPage route property
309+
// filter exposes a "Traffic Status" option. The filter is currently only
310+
// populated with Health Status, pending backend support for per-route
311+
// traffic status (FR-2591).
312+
test.fixme('3.1 Admin can see the Traffic Status filter property in the property filter selector', async ({
309313
page,
310314
request,
311315
}) => {
@@ -325,7 +329,9 @@ test.describe(
325329
await page.keyboard.press('Escape');
326330
});
327331

328-
test('3.2 Admin can filter routes by trafficStatus ACTIVE using the property filter', async ({
332+
// TODO(needs-backend): Re-enable when the route property filter exposes a
333+
// "Traffic Status" option (FR-2591).
334+
test.fixme('3.2 Admin can filter routes by trafficStatus ACTIVE using the property filter', async ({
329335
page,
330336
request,
331337
}) => {
@@ -358,7 +364,9 @@ test.describe(
358364
await expect(filterTag.first()).toBeVisible();
359365
});
360366

361-
test('3.3 Admin can filter routes by trafficStatus INACTIVE using the property filter', async ({
367+
// TODO(needs-backend): Re-enable when the route property filter exposes a
368+
// "Traffic Status" option (FR-2591).
369+
test.fixme('3.3 Admin can filter routes by trafficStatus INACTIVE using the property filter', async ({
362370
page,
363371
request,
364372
}) => {
@@ -391,7 +399,11 @@ test.describe(
391399
await expect(filterTag.first()).toBeVisible();
392400
});
393401

394-
test('3.4 Admin can remove an applied filter to restore the full route list', async ({
402+
// TODO(needs-backend): Re-enable when the route property filter exposes a
403+
// "Traffic Status" option (FR-2591). The underlying remove-filter behavior
404+
// is covered indirectly via the Health Status filter once BAIRouteNodes
405+
// supports a secondary filter.
406+
test.fixme('3.4 Admin can remove an applied filter to restore the full route list', async ({
395407
page,
396408
request,
397409
}) => {
@@ -451,11 +463,10 @@ test.describe(
451463
await expect(
452464
card.getByRole('columnheader', { name: 'Status', exact: true }),
453465
).toBeVisible();
466+
// TODO(needs-backend): Re-enable when BAIRouteNodes exposes the Traffic
467+
// Status column (FR-2591).
454468
await expect(
455-
card.getByRole('columnheader', { name: 'Traffic Status' }),
456-
).toBeVisible();
457-
await expect(
458-
card.getByRole('columnheader', { name: 'Traffic Ratio' }),
469+
card.getByRole('columnheader', { name: 'Created At' }),
459470
).toBeVisible();
460471
});
461472

@@ -474,9 +485,8 @@ test.describe(
474485
.first();
475486
await expect(healthyTag).toBeVisible();
476487

477-
// Verify ACTIVE traffic status tag
478-
const activeTag = card.locator('.ant-tag').filter({ hasText: 'ACTIVE' });
479-
await expect(activeTag.first()).toBeVisible();
488+
// TODO(needs-backend): Re-enable ACTIVE traffic-status tag assertion
489+
// once BAIRouteNodes exposes the Traffic Status column (FR-2591).
480490
});
481491

482492
test('4.3 Admin sees a PROVISIONING route with a processing-colored status tag', async ({
@@ -507,7 +517,9 @@ test.describe(
507517
await expect(unhealthyTag).toBeVisible();
508518
});
509519

510-
test('4.5 Admin sees INACTIVE traffic status tags displayed', async ({
520+
// TODO(needs-backend): Re-enable when BAIRouteNodes exposes the Traffic
521+
// Status column. INACTIVE tags render inside that column (FR-2591).
522+
test.fixme('4.5 Admin sees INACTIVE traffic status tags displayed', async ({
511523
page,
512524
request,
513525
}) => {
@@ -522,7 +534,10 @@ test.describe(
522534
await expect(inactiveTags.first()).toBeVisible();
523535
});
524536

525-
test('4.6 Admin sees the traffic ratio value in the Traffic Ratio column', async ({
537+
// TODO(needs-backend): Re-enable when BAIRouteNodes exposes the Traffic Ratio
538+
// column. It is currently commented out in BAIRouteNodes.tsx pending backend
539+
// support for per-route traffic ratio.
540+
test.fixme('4.6 Admin sees the traffic ratio value in the Traffic Ratio column', async ({
526541
page,
527542
request,
528543
}) => {
@@ -720,21 +735,22 @@ test.describe(
720735
).toBeVisible();
721736
});
722737

723-
test('7.2 Admin can sort routes by Traffic Ratio column', async ({
738+
// TODO(needs-backend): Re-enable when BAIRouteNodes exposes the Traffic Ratio
739+
// column. It is currently commented out in BAIRouteNodes.tsx pending backend
740+
// support for per-route traffic ratio.
741+
test.fixme('7.2 Admin can sort routes by Traffic Ratio column', async ({
724742
page,
725743
request,
726744
}) => {
727745
await setupAndNavigateToDetail(page, request);
728746

729747
const card = getRoutesInfoCard(page);
730748

731-
// Click the "Traffic Ratio" column header to sort
732749
const trafficRatioHeader = card.getByRole('columnheader', {
733750
name: 'Traffic Ratio',
734751
});
735752
await trafficRatioHeader.click();
736753

737-
// Verify a sort indicator is shown
738754
await expect(
739755
trafficRatioHeader.locator('.ant-table-column-sorter'),
740756
).toBeVisible();

e2e/serving/fixtures/model-definition.yaml

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -8,5 +8,4 @@ models:
88
port: 8000
99
health_check:
1010
path: /health
11-
initial_delay: 5.0
1211
max_retries: 10

e2e/serving/mocking/model-store-mock.ts

Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -288,6 +288,20 @@ const EMPTY_TOKEN_LIST = {
288288
items: [],
289289
};
290290

291+
/**
292+
* Shared minimal `modelDeployment` node used by EndpointDetailPage mocks. The
293+
* page reads `modelDeployment.metadata.status` as the single source of truth
294+
* for `isDeploymentDeploying` / `hasAnyHealthyRoute` when the `model-card-v2`
295+
* feature flag is injected by the tests.
296+
*/
297+
const buildModelDeployment = (
298+
status: 'DEPLOYING' | 'READY' | 'TERMINATED',
299+
) => ({
300+
metadata: { status },
301+
currentRevision: null,
302+
revisionHistory: { edges: [] },
303+
});
304+
291305
/**
292306
* Mock for EndpointDetailPageQuery — "Preparing your service" state.
293307
* replicas=1, deploymentScopedSchedulingHistories.count=0 → hasReachedReady=false.
@@ -305,6 +319,7 @@ export function endpointDetailPreparingMockResponse() {
305319
routes: { edges: [], count: 0 },
306320
healthyRoutes: { count: 0 },
307321
deploymentScopedSchedulingHistories: { count: 0 },
322+
modelDeployment: buildModelDeployment('DEPLOYING'),
308323
});
309324
}
310325

@@ -324,6 +339,7 @@ export function endpointDetailZeroReplicasMockResponse() {
324339
routes: { edges: [], count: 0 },
325340
healthyRoutes: { count: 0 },
326341
deploymentScopedSchedulingHistories: { count: 0 },
342+
modelDeployment: buildModelDeployment('DEPLOYING'),
327343
});
328344
}
329345

@@ -343,6 +359,7 @@ export function endpointDetailTerminatedMockResponse() {
343359
routes: { edges: [], count: 0 },
344360
healthyRoutes: { count: 0 },
345361
deploymentScopedSchedulingHistories: { count: 0 },
362+
modelDeployment: buildModelDeployment('TERMINATED'),
346363
});
347364
}
348365

@@ -363,6 +380,7 @@ export function endpointDetailServiceReadyMockResponse() {
363380
routes: { edges: [], count: 0 },
364381
healthyRoutes: { count: 1 },
365382
deploymentScopedSchedulingHistories: { count: 1 },
383+
modelDeployment: buildModelDeployment('READY'),
366384
});
367385
}
368386

@@ -383,6 +401,7 @@ export function endpointDetailHealthyButNoSchedulingHistoryMockResponse() {
383401
routes: { edges: [], count: 0 },
384402
healthyRoutes: { count: 1 },
385403
deploymentScopedSchedulingHistories: { count: 0 },
404+
modelDeployment: buildModelDeployment('READY'),
386405
});
387406
}
388407

@@ -402,5 +421,8 @@ export function endpointDetailReadyButNoHealthyRoutesMockResponse() {
402421
routes: { edges: [], count: 0 },
403422
healthyRoutes: { count: 0 },
404423
deploymentScopedSchedulingHistories: { count: 1 },
424+
// No healthy routes → hasAnyHealthyRoute=false; use non-READY status so
425+
// the "Service Ready" alert is suppressed.
426+
modelDeployment: buildModelDeployment('DEPLOYING'),
405427
});
406428
}

0 commit comments

Comments
 (0)