feat(e2e): autologin patch (dev) + 登录态路由测试脚本

- util_web devAutologin: localStorage[_test_token]=user|pass -> 登录API写Hive+dispatch currentUser
- 延迟3s执行等 Flutter/Hive ready (否则 httpPost hang)
- main.dart 调用 devAutologin
- run_auth.js: 注入token遍历登录态路由
- 已验证: autologin API 200 OK
This commit is contained in:
2026-08-03 01:50:12 +08:00
parent 901e42a41b
commit 33b54fe454
10 changed files with 221 additions and 0 deletions

86
tools/e2e/run_auth.js Normal file
View File

@@ -0,0 +1,86 @@
// 登录态路由测试:注入 _test_tokenautologin 后遍历需登录路由
const { chromium } = require('playwright');
const BASE = 'http://127.0.0.1:8099';
const USER = '6477108200';
const PASS = '8818';
// 需登录路由(动态参数用合理默认)
const AUTH_ROUTES = [
'/me',
'/orders',
'/user-profile',
'/my-cards',
'/my-addresses/310',
'/coupons/310',
'/my-support/310',
'/new-ticket/310',
'/change-password',
'/checkout/310',
];
(async () => {
const browser = await chromium.launch({ headless: true });
const ctx = await browser.newContext({ viewport: { width: 1280, height: 900 } });
await ctx.addInitScript(([u, p]) => { localStorage['_test_token'] = u + '|' + p; }, [USER, PASS]);
// 先访问首页触发 autologin
const page = await ctx.newPage();
let autologinOk = false;
page.on('console', m => { if (m.text().includes('CK_AUTOLOGIN_OK')) autologinOk = true; });
console.log('触发 autologin...');
await page.goto(BASE + '/', { waitUntil: 'load', timeout: 60000 });
await page.waitForSelector('canvas', { timeout: 90000 });
await page.reload({ waitUntil: 'load' });
await page.waitForTimeout(8000);
console.log('autologin:', autologinOk ? '✓ 成功' : '✗ 未确认\n');
const results = [];
for (const route of AUTH_ROUTES) {
const errors = [];
const stacks = [];
const pageErrs = [];
page.removeAllListeners('console');
page.removeAllListeners('pageerror');
page.on('console', m => {
const t = m.text();
if (t.startsWith('CK_ERROR:')) errors.push(t.slice(0, 120));
if (t.startsWith('CK_STACK:')) {
const proj = t.match(/flutter_wisetronic\/[^\s]+:\d+/g);
if (proj) stacks.push([...new Set(proj)].slice(0, 2));
}
});
page.on('pageerror', e => pageErrs.push(e.message.slice(0, 120)));
try {
await page.goto(BASE + route, { waitUntil: 'load', timeout: 30000 });
await page.waitForTimeout(6000);
} catch (e) {
errors.push('GOTO: ' + e.message.slice(0, 80));
}
const allErr = [...errors, ...pageErrs];
const status = allErr.length === 0 ? '✓ OK' : `${allErr.length}`;
console.log(`${status.padEnd(10)} ${route}`);
if (allErr.length) {
console.log(` ${allErr[0].slice(0, 120)}`);
if (stacks.length) console.log(` 位置: ${JSON.stringify(stacks[0])}`);
}
results.push({ route, errors: allErr, stacks });
}
const failed = results.filter(r => r.errors.length > 0);
console.log(`\n========== 汇总 ==========`);
console.log(`${results.length} 个登录态路由,${failed.length} 个有错误`);
if (failed.length) {
const locMap = {};
for (const f of failed) {
const loc = f.stacks[0] ? f.stacks[0][0] : f.errors[0].slice(0, 40);
locMap[loc] = locMap[loc] || [];
locMap[loc].push(f.route);
}
for (const [loc, routes] of Object.entries(locMap)) {
console.log(` ${loc}\n${routes.join(', ')}`);
}
}
await browser.close();
})();

View File

@@ -0,0 +1,22 @@
const { chromium } = require('playwright');
(async () => {
const browser = await chromium.launch({ headless: true });
const ctx = await browser.newContext({ viewport: { width: 1280, height: 900 } });
// 注入 _test_tokenaddInitScript 在每个页面加载前执行)
await ctx.addInitScript(() => { localStorage['_test_token'] = '6477108200|8818'; });
const page = await ctx.newPage();
const logs = [];
page.on('console', m => logs.push(m.text()));
await page.goto('http://127.0.0.1:8099/', { waitUntil: 'load', timeout: 60000 });
await page.waitForTimeout(8000); // 等 autologin
const ok = logs.filter(l => l.includes('CK_AUTOLOGIN_OK'));
const fail = logs.filter(l => l.includes('CK_AUTOLOGIN_FAIL'));
console.log('autologin:', ok.length ? '✓ OK' : (fail.length ? '✗ FAIL '+fail[0].slice(0,100) : '? 未触发'));
// 访问 /me登录态
await page.goto('http://127.0.0.1:8099/me', { waitUntil: 'load' }).catch(()=>{});
await page.waitForTimeout(6000);
const errs = logs.filter(l => l.startsWith('CK_ERROR') || l.includes('PAGEERROR'));
console.log('/me 错误数:', errs.length);
if (errs.length) console.log(' ', errs[0].slice(0,150));
await browser.close();
})();

View File

@@ -0,0 +1,16 @@
const { chromium } = require('playwright');
(async () => {
const browser = await chromium.launch({ headless: true });
const ctx = await browser.newContext({ viewport: { width: 1280, height: 900 } });
await ctx.addInitScript(() => { localStorage['_test_token'] = '6477108200|8818'; });
const page = await ctx.newPage();
const logs = [];
page.on('console', m => logs.push(m.text()));
await page.goto('http://127.0.0.1:8099/', { waitUntil: 'load', timeout: 60000 });
await page.waitForTimeout(10000);
// 确认 localStorage 注入 + autologin 日志
const ls = await page.evaluate(() => localStorage['_test_token']);
console.log('localStorage 注入:', ls ? '✓' : '✗');
console.log('autologin 日志:', logs.filter(l=>l.includes('CK_AUTOLOGIN')).join(' | ') || '(无)');
await browser.close();
})();

View File

@@ -0,0 +1,20 @@
const { chromium } = require('playwright');
(async () => {
const browser = await chromium.launch({ headless: true });
const ctx = await browser.newContext({ viewport: { width: 1280, height: 900 } });
await ctx.addInitScript(() => { localStorage['_test_token'] = '6477108200|8818'; });
const page = await ctx.newPage();
const logs = [];
page.on('console', m => logs.push(m.text()));
// 第一次访问触发编译
await page.goto('http://127.0.0.1:8099/', { waitUntil: 'load', timeout: 60000 });
await page.waitForSelector('canvas', { timeout: 60000 });
await page.waitForTimeout(3000);
console.log('编译完成 canvas:', await page.locator('canvas').count());
// reload 让 main() 重跑devAutologin
logs.length = 0;
await page.reload({ waitUntil: 'load' });
await page.waitForTimeout(10000);
console.log('reload 后 autologin 日志:', logs.filter(l=>l.includes('CK_AUTOLOGIN')).join(' | ') || '(无)');
await browser.close();
})();

View File

@@ -0,0 +1,17 @@
const { chromium } = require('playwright');
(async () => {
const browser = await chromium.launch({ headless: true });
const ctx = await browser.newContext({ viewport: { width: 1280, height: 900 } });
await ctx.addInitScript(() => { localStorage['_test_token'] = '6477108200|8818'; });
const page = await ctx.newPage();
const logs = [];
page.on('console', m => logs.push(m.text()));
page.on('response', r => { if (r.url().includes('access_token')) console.log('登录API:', r.status()); });
await page.goto('http://127.0.0.1:8099/', { waitUntil: 'load', timeout: 60000 });
await page.waitForSelector('canvas', { timeout: 60000 });
await page.reload({ waitUntil: 'load' });
await page.waitForTimeout(18000);
console.log('所有 CK_AUTOLOGIN 日志:');
logs.filter(l=>l.includes('AUTOLOGIN')).forEach(l => console.log(' ', l.slice(0,120)));
await browser.close();
})();

View File

@@ -0,0 +1,16 @@
const { chromium } = require('playwright');
(async () => {
const browser = await chromium.launch({ headless: true });
const ctx = await browser.newContext({ viewport: { width: 1280, height: 900 } });
await ctx.addInitScript(() => { localStorage['_test_token'] = '6477108200|8818'; });
const page = await ctx.newPage();
const logs = [];
page.on('console', m => logs.push(m.text()));
page.on('response', r => { if (r.url().includes('access_token')) console.log(' 登录API:', r.status()); });
await page.goto('http://127.0.0.1:8099/', { waitUntil: 'load', timeout: 60000 });
await page.waitForSelector('canvas', { timeout: 60000 });
await page.reload({ waitUntil: 'load' });
await page.waitForTimeout(25000);
console.log('autologin 日志:', logs.filter(l=>l.includes('CK_AUTOLOGIN')).join(' | ') || '(无)');
await browser.close();
})();

View File

@@ -0,0 +1,18 @@
const { chromium } = require('playwright');
(async () => {
const browser = await chromium.launch({ headless: true });
const ctx = await browser.newContext({ viewport: { width: 1280, height: 900 } });
await ctx.addInitScript(() => { localStorage['_test_token'] = '6477108200|8818'; });
const page = await ctx.newPage();
const logs = [];
page.on('console', m => logs.push(m.text()));
page.on('request', r => { if (r.url().includes('access_token')) console.log(' →请求发出:', r.url().slice(-40)); });
page.on('response', r => { if (r.url().includes('access_token')) console.log(' ←响应:', r.status()); });
page.on('requestfailed', r => { if (r.url().includes('access_token') || r.url().includes('api.minipos')) console.log(' ✗请求失败:', r.url().slice(-50), r.failure()?.errorText); });
await page.goto('http://127.0.0.1:8099/', { waitUntil: 'load', timeout: 60000 });
await page.waitForSelector('canvas', { timeout: 90000 });
await page.reload({ waitUntil: 'load' });
await page.waitForTimeout(15000); // 等 3s 延迟 + autologin
console.log('autologin 日志:', logs.filter(l=>l.includes('CK_AUTOLOGIN')).join(' | ') || '(无)');
await browser.close();
})();