Files
photo-live/apps/viewer/e2e/dbg-outside.spec.ts
T

107 lines
4.5 KiB
TypeScript
Raw Normal View History

// 临时窗外释放调试(验证后删除)
import { createServer, type Server } from 'node:http';
import { expect, test, type Page } from '@playwright/test';
import {
cleanupSeededAlbums, createEmbedSlot, flushOutbox, flushSync,
seedAlbum, seedPhoto, updateEmbedSlot,
} from './helpers';
const HOST_PORT = 3976;
const MINUTE = 60_000;
let slotToken = '';
test.beforeAll(async () => {
const album = await seedAlbum({
alias: 'outsidedbg', defaultLocale: 'zh-CN',
translations: [{ locale: 'zh-CN', title: '窗外释放调试' }],
});
for (let i = 1; i <= 6; i++) {
await seedPhoto(album.id, `outsidedbg-p${i}`, { publishedAt: new Date(Date.now() - (7 - i) * MINUTE) });
}
await flushSync(album.id);
const slot = await createEmbedSlot('outside-dbg');
await updateEmbedSlot(slot.id, {
albumId: album.id,
settings: {
position: 'right', size: 'md', intervalMs: 5000, lang: 'auto', collapsedDefault: false,
imageFit: 'contain', offsetX: 16, offsetBottom: 24, zIndex: 1000,
displayMode: 'vertical-stream', scrollSpeed: 16, reactionsEnabled: true,
},
});
await flushOutbox();
slotToken = slot.token;
});
const server: Server = createServer((_q, res) => {
res.setHeader('content-type', 'text/html; charset=utf-8');
res.end(`<!doctype html><html><body style="min-height:900px">
<script>window.addEventListener('message',(e)=>console.log('[host-msg]',e.data&&e.data.type));</script>
<script src="http://127.0.0.1:5175/embed/v2/loader.js" data-slot="${slotToken}" defer></script></body></html>`);
});
test.afterAll(async () => { await cleanupSeededAlbums(); server.close(); });
test('outside release debug', async ({ page }: { page: Page }) => {
page.on('console', (m) => {
const txt = m.text();
if (txt.includes('stream-frame-error') || txt.includes('host-msg') || txt.includes('[ev]')) {
console.log(txt.slice(0, 200));
}
});
await new Promise<void>((r) => server.listen(HOST_PORT, '127.0.0.1', r));
await page.setViewportSize({ width: 1440, height: 900 });
await page.goto(`http://127.0.0.1:${HOST_PORT}`);
const frame = page.locator('iframe[src*="/embed/"][src*="v=2"]');
await frame.waitFor({ timeout: 20000 });
await page.waitForTimeout(3000);
const f = page.frames().find((fr) => fr.url().includes('v=2'));
expect(f).toBeDefined();
const offset = async () => {
const t = await f!.locator('.stream-track').evaluate((el) => el.style.transform);
return Number.parseFloat((/translateY\((-?[\d.]+)px\)/.exec(t) ?? ['0', '0'])[1]);
};
const box = await frame.boundingBox();
const cx = (box ? box.x : 0) + 90;
const cy = (box ? box.y : 0) + 150;
const b1 = await offset();
await page.waitForTimeout(1000);
console.log('[1 baseline]', b1 !== (await offset()));
await f!.evaluate(() => {
const log = (name: string) => (e: PointerEvent) =>
console.log(`[ev] ${name} type=${e.type} x=${e.clientX} y=${e.clientY}`);
const vp = document.querySelector('.stream-viewport');
vp?.addEventListener('pointerdown', log('vp'), true);
window.addEventListener('pointerup', log('win'), true);
window.addEventListener('pointercancel', log('win'), true);
window.addEventListener('pointerleave', log('win'), true);
window.addEventListener('pointerout', log('win'), true);
vp?.addEventListener('pointerleave', log('vp'), true);
});
await page.mouse.move(cx, cy);
await page.mouse.down();
await page.mouse.move(cx + 120, cy + 200, { steps: 4 });
await page.mouse.up();
await page.waitForTimeout(3500);
const w1 = await offset();
await page.waitForTimeout(1000);
console.log('[2 after outside]', w1 !== (await offset()), 'offset =', w1);
console.log('[2 state]', await f!.evaluate(() => {
const d = (window as unknown as { __embedDebug?: { reasons: Set<string>; userPaused: { value: boolean } } }).__embedDebug;
return `reasons=[${d ? [...d.reasons].join(',') : '?'}] userPaused=${d?.userPaused.value}`;
}));
// 手动在 iframe window 派发 pointerup——验证组件监听是否注册生效
await f!.evaluate(() => {
window.dispatchEvent(new PointerEvent('pointerup', { bubbles: true, clientX: 0, clientY: 0, pointerId: 1 }));
});
await page.waitForTimeout(1500);
console.log('[2b after manual pointerup]', await f!.evaluate(() => {
const d = (window as unknown as { __embedDebug?: { reasons: Set<string> } }).__embedDebug;
return `reasons=[${d ? [...d.reasons].join(',') : '?'}]`;
}));
const s1 = await offset();
await page.waitForTimeout(15000);
console.log('[3 15s moved]', Math.abs((await offset()) - s1).toFixed(0), 'px');
});