210 lines
7.7 KiB
TypeScript
210 lines
7.7 KiB
TypeScript
import { expect, test } from '@playwright/test';
|
|
|
|
test('first-run wizard tests MySQL, creates the administrator and stays responsive', async ({ page }) => {
|
|
let completed = false;
|
|
await page.route('**/api/v1/setup/**', async (route) => {
|
|
const request = route.request();
|
|
const pathname = new URL(request.url()).pathname;
|
|
if (pathname === '/api/v1/setup/status') {
|
|
await route.fulfill({
|
|
json: {
|
|
data: {
|
|
required: !completed,
|
|
locked: completed,
|
|
// Production status is locked after setup; readiness is not the
|
|
// completion signal used by the redirect flow.
|
|
ready: false,
|
|
supportedDatabaseTypes: ['MYSQL'],
|
|
message: completed ? '系统已完成安装' : '请完成安装',
|
|
},
|
|
},
|
|
});
|
|
return;
|
|
}
|
|
const body = request.postDataJSON() as Record<string, unknown>;
|
|
expect(body.databaseType).toBe('MYSQL');
|
|
expect(body.database).toBe('kaidi_finance');
|
|
expect(body.setupCode).toBe('fixture-setup-code');
|
|
if (pathname.endsWith('/test-connection')) {
|
|
await route.fulfill({
|
|
json: {
|
|
data: {
|
|
successful: true,
|
|
databaseType: 'MYSQL',
|
|
serverVersion: '8.4.6',
|
|
schemaReady: false,
|
|
message: 'MySQL 8.4 只读连接验证通过;尚未修改数据库,点击完成安装后才会执行迁移',
|
|
},
|
|
},
|
|
});
|
|
return;
|
|
}
|
|
expect(body.adminUsername).toBe('admin');
|
|
expect(body.adminDisplayName).toBe('系统管理员');
|
|
completed = true;
|
|
await route.fulfill({
|
|
json: {
|
|
data: {
|
|
completed: true,
|
|
username: 'admin',
|
|
message: '安装完成,系统正在切换到正式模式',
|
|
restartAfterSeconds: 10,
|
|
},
|
|
},
|
|
});
|
|
});
|
|
|
|
await page.setViewportSize({ width: 390, height: 844 });
|
|
await page.goto('/setup');
|
|
await expect(page.getByRole('heading', { name: '安装向导', exact: true })).toBeVisible();
|
|
|
|
await page.getByLabel('数据库密码').fill('fixture-db-password');
|
|
await page.getByLabel('安装码').fill('fixture-setup-code');
|
|
await page.getByRole('button', { name: '测试连接' }).click();
|
|
await expect(
|
|
page.locator('.t-alert__description').filter({
|
|
hasText: 'MySQL 8.4 只读连接验证通过;尚未修改数据库,点击完成安装后才会执行迁移',
|
|
}),
|
|
).toBeVisible();
|
|
await page.getByRole('button', { name: '下一步' }).click();
|
|
|
|
await page.getByLabel('管理员密码').fill('SetupAdmin@2026Strong');
|
|
await page.getByLabel('确认密码').fill('SetupAdmin@2026Strong');
|
|
await page.getByRole('button', { name: '完成安装' }).click();
|
|
await page.getByRole('button', { name: '确定', exact: true }).click();
|
|
await expect(page.getByText('安装完成', { exact: true })).toBeVisible();
|
|
await expect(page.getByText('安装完成,系统正在切换到正式模式')).toBeVisible();
|
|
|
|
await expect(page).toHaveURL(/\/login$/, { timeout: 15_000 });
|
|
|
|
const layout = await page.evaluate(() => ({
|
|
clientWidth: document.documentElement.clientWidth,
|
|
scrollWidth: document.documentElement.scrollWidth,
|
|
}));
|
|
expect(layout.scrollWidth).toBeLessThanOrEqual(layout.clientWidth);
|
|
});
|
|
|
|
test('confirms completion after the setup response is interrupted by a service restart', async ({ page }) => {
|
|
let completionStarted = false;
|
|
let recoveryChecks = 0;
|
|
await page.route('**/api/v1/setup/**', async (route) => {
|
|
const request = route.request();
|
|
const pathname = new URL(request.url()).pathname;
|
|
if (pathname === '/api/v1/setup/status') {
|
|
if (completionStarted) recoveryChecks += 1;
|
|
const ready = completionStarted && recoveryChecks >= 2;
|
|
await route.fulfill({
|
|
json: {
|
|
data: {
|
|
required: !completionStarted,
|
|
locked: completionStarted,
|
|
ready,
|
|
supportedDatabaseTypes: ['MYSQL'],
|
|
message: ready ? '系统已完成安装' : '请完成安装',
|
|
},
|
|
},
|
|
});
|
|
return;
|
|
}
|
|
const body = request.postDataJSON() as Record<string, unknown>;
|
|
if (pathname.endsWith('/test-connection')) {
|
|
await route.fulfill({
|
|
json: {
|
|
data: {
|
|
successful: true,
|
|
databaseType: 'MYSQL',
|
|
serverVersion: '8.4.6',
|
|
schemaReady: false,
|
|
message: 'MySQL 8.4 只读连接验证通过;尚未修改数据库,点击完成安装后才会执行迁移',
|
|
},
|
|
},
|
|
});
|
|
return;
|
|
}
|
|
expect(body.adminUsername).toBe('admin');
|
|
completionStarted = true;
|
|
await route.abort('connectionreset');
|
|
});
|
|
|
|
await page.goto('/setup');
|
|
await page.getByLabel('数据库密码').fill('fixture-db-password');
|
|
await page.getByLabel('安装码').fill('fixture-setup-code');
|
|
await page.getByRole('button', { name: '测试连接' }).click();
|
|
await page.getByRole('button', { name: '下一步' }).click();
|
|
await page.getByLabel('管理员密码').fill('SetupAdmin@2026Strong');
|
|
await page.getByLabel('确认密码').fill('SetupAdmin@2026Strong');
|
|
await page.getByRole('button', { name: '完成安装' }).click();
|
|
await page.getByRole('button', { name: '确定', exact: true }).click();
|
|
|
|
await expect(page.getByText('安装完成', { exact: true })).toBeVisible();
|
|
await expect(page.getByText('安装已完成,系统正在切换到正式模式')).toBeVisible();
|
|
await expect(page.getByText('网络请求失败')).toHaveCount(0);
|
|
await expect(page).toHaveURL(/\/login$/, { timeout: 15_000 });
|
|
});
|
|
|
|
test('leaves the completed wizard when post-completion status polling is unavailable', async ({ page }) => {
|
|
let completionStarted = false;
|
|
await page.route('**/api/v1/setup/**', async (route) => {
|
|
const request = route.request();
|
|
const pathname = new URL(request.url()).pathname;
|
|
if (pathname === '/api/v1/setup/status') {
|
|
if (completionStarted) {
|
|
await route.abort('connectionreset');
|
|
return;
|
|
}
|
|
await route.fulfill({
|
|
json: {
|
|
data: {
|
|
required: true,
|
|
locked: false,
|
|
ready: false,
|
|
supportedDatabaseTypes: ['MYSQL'],
|
|
message: '请完成安装',
|
|
},
|
|
},
|
|
});
|
|
return;
|
|
}
|
|
const body = request.postDataJSON() as Record<string, unknown>;
|
|
if (pathname.endsWith('/test-connection')) {
|
|
await route.fulfill({
|
|
json: {
|
|
data: {
|
|
successful: true,
|
|
databaseType: 'MYSQL',
|
|
serverVersion: '8.4.6',
|
|
schemaReady: false,
|
|
message: 'MySQL 8.4 只读连接验证通过;尚未修改数据库,点击完成安装后才会执行迁移',
|
|
},
|
|
},
|
|
});
|
|
return;
|
|
}
|
|
expect(body.adminUsername).toBe('admin');
|
|
completionStarted = true;
|
|
await route.fulfill({
|
|
json: {
|
|
data: {
|
|
completed: true,
|
|
username: 'admin',
|
|
message: '安装完成,系统正在切换到正式模式',
|
|
restartAfterSeconds: 1,
|
|
},
|
|
},
|
|
});
|
|
});
|
|
|
|
await page.goto('/setup');
|
|
await page.getByLabel('数据库密码').fill('fixture-db-password');
|
|
await page.getByLabel('安装码').fill('fixture-setup-code');
|
|
await page.getByRole('button', { name: '测试连接' }).click();
|
|
await page.getByRole('button', { name: '下一步' }).click();
|
|
await page.getByLabel('管理员密码').fill('SetupAdmin@2026Strong');
|
|
await page.getByLabel('确认密码').fill('SetupAdmin@2026Strong');
|
|
await page.getByRole('button', { name: '完成安装' }).click();
|
|
await page.getByRole('button', { name: '确定', exact: true }).click();
|
|
|
|
await expect(page.getByText('安装完成', { exact: true })).toBeVisible();
|
|
await expect(page).toHaveURL(/\/login$/, { timeout: 5_000 });
|
|
});
|