Skip to content
This repository was archived by the owner on Jan 12, 2024. It is now read-only.

Commit bcbc1d8

Browse files
committed
fix(test-util-ipfs-example.servers): allow server stop from tests
remove waitForSelectors and ensure service worker response is done before checking for text debugging: query /view directly this removes the need for playwright navigating iframes and still utilizes the serviceWorker in the test
1 parent 8958d50 commit bcbc1d8

File tree

2 files changed

+123
-24
lines changed
  • examples/browser-service-worker/tests
  • lib/test-util-ipfs-example/playwright

2 files changed

+123
-24
lines changed
Lines changed: 101 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -1,43 +1,127 @@
1+
// @ts-check
12
import { test, expect } from '@playwright/test';
23
import { playwright } from 'test-util-ipfs-example';
34

45
// Setup
56
const play = test.extend({
6-
...playwright.servers(),
7+
...playwright.servers([], true),
78
});
89

9-
play.setTimeout(60 * 1000)
10+
/**
11+
* attempt to prevent net::ERR_ABORTED error
12+
*/
13+
play.setTimeout(120 * 1000)
1014

1115
play.describe('browser service worker:', () => {
1216
// DOM
1317
const linkDOM = "a"
1418
const textDOM = "body"
1519
const debugDOM = "#debug"
1620

17-
// play.beforeEach(async ({servers, page}) => {
18-
// await page.goto(`http://localhost:${servers[0].port}/`);
19-
// })
21+
play.beforeEach(async ({servers, page}) => {
22+
await page.goto(`http://localhost:${servers[0].port}/`);
23+
})
2024

21-
play('should properly load the content of an IPFS hash', async ({ servers, page }) => {
22-
const currentURL = `http://localhost:${servers[0].port}/`
23-
await page.goto(currentURL);
24-
await page.waitForSelector(textDOM)
25-
await page.waitForSelector(linkDOM)
25+
play('should properly load the content of an IPFS hash', async ({ servers, page, context }) => {
26+
page.on('console', msg => console.log('PAGE LOG:', msg.text()));
27+
page.on("pageerror", (err) => {
28+
console.trace(`pageerror: ${err.message}`)
29+
})
30+
// await page.waitForSelector(textDOM)
31+
// await page.waitForSelector(linkDOM)
2632

2733
expect(await page.textContent(textDOM)).toContain("Load content by adding IPFS path to the URL")
2834
expect(await page.textContent(linkDOM)).toContain("/ipfs/bafy")
2935

30-
await page.waitForSelector(`${debugDOM}:has-text("SW is ready")`, {
31-
state: 'attached'
36+
const ipfsRequestUrl = `http://localhost:${servers[0].port}/view/ipfs/Qmf412jQZiuVUtdgnB36FXFX7xg5V6KEbSJ4dpQuhkLyfD`
37+
38+
/**
39+
* Wait for the service worker to be ready
40+
* @see https://playwright.dev/docs/service-workers-experimental#accessing-service-workers-and-waiting-for-activation
41+
*/
42+
await page.evaluate(async () => {
43+
const registration = await window.navigator.serviceWorker.getRegistration();
44+
if (registration?.active?.state === 'activated') {
45+
console.log('Service worker is already activated')
46+
return;
47+
}
48+
await /** @type {Promise<void>} */(new Promise(res => {
49+
window.navigator.serviceWorker.addEventListener('controllerchange', () => {
50+
console.log('Service worker is activated')
51+
res()
52+
})
53+
}));
54+
});
55+
// await page.waitForSelector(`${debugDOM}:has-text("SW is ready")`, {
56+
// state: 'attached'
57+
// })
58+
59+
context.on('request', (request) => {
60+
console.log(`request.url(): ${request.url()}`)
61+
})
62+
context.on('requestfailed', (request) => {
63+
console.log(`context.requestfailed: ${request.url()}`)
64+
console.log(`context.requestfailed request?.failure()?.errorText: `, request?.failure()?.errorText);
65+
})
66+
page.on('requestfailed', (request) => {
67+
console.log(`page.requestfailed: ${request.url()}`)
68+
console.log(`page.requestfailed request?.failure()?.errorText: `, request?.failure()?.errorText);
69+
})
70+
const serviceWorkerResponsePromise = new Promise((resolve, reject) => {
71+
context.on('response', async (response) => {
72+
console.log(`context.response response.url(): ${response.url()}`)
73+
if (response.url() === ipfsRequestUrl && response.fromServiceWorker()) {
74+
resolve(response);
75+
}
76+
})
3277
})
3378

3479
// const currentURL = await page.url();
35-
await page.goto(`${currentURL}ipfs/Qmf412jQZiuVUtdgnB36FXFX7xg5V6KEbSJ4dpQuhkLyfD`);
36-
await page.waitForSelector(textDOM)
80+
await page.goto(ipfsRequestUrl, {waitUntil: 'commit'});
81+
const serviceWorkerResponse = await serviceWorkerResponsePromise
82+
page.on('request', async (request) => {
83+
try {
84+
console.log(`page.request request.url(): ${request.url()}`)
85+
console.log(`page.request (await request.response())?.status(): ${(await request.response())?.status()}`)
86+
console.log(`page.request await (await request.response())?.text(): ${await (await request.response())?.text()}`)
87+
console.log(`request.serviceWorker(): `, request.serviceWorker());
88+
} catch {}
89+
});
3790

38-
const elementFrame = await page.waitForSelector("iframe")
39-
const frame = await elementFrame.contentFrame()
91+
expect(await serviceWorkerResponse.status()).toBe(200)
92+
expect(await serviceWorkerResponse.text()).toContain("hello world")
93+
// await page.waitForSelector('#viewer', {state: 'visible'})
4094

41-
expect(await frame.textContent('pre')).toContain("hello world")
95+
// const frameText2 = page.frameLocator('#viewer').locator(textDOM)
96+
// // await frameText2.waitFor({state: 'visible'})
97+
98+
// // loop over all of the frames and log their content
99+
// const frames = await page.frames();
100+
// for (const frame of frames) {
101+
// console.log('page.frames textContent: ', await frame.textContent(textDOM));
102+
// console.log('page.frames innerText: ', await frame.innerText(textDOM));
103+
// }
104+
105+
// expect(await frameText2.textContent()).toContain("hello world")
106+
107+
// const elementFrame = await page.waitForSelector("iframe")
108+
// /**
109+
// * @type {import('playwright').Frame}
110+
// */
111+
// // @ts-ignore
112+
// const frame = await elementFrame.contentFrame()
113+
// if (frame == null) {
114+
// throw new Error('frame is null')
115+
// }
116+
// const frameText = await frame.textContent(textDOM)
117+
118+
// expect(frameText).toContain("hello world")
42119
});
120+
121+
play.afterAll(async ({servers}) => {
122+
// now stop all servers
123+
for (const server of servers) {
124+
await server.stop()
125+
}
126+
})
43127
});

lib/test-util-ipfs-example/playwright/servers.js

Lines changed: 22 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,14 @@ import sirv from 'sirv'
22
import polka from 'polka'
33
import stoppable from 'stoppable'
44

5-
const servers = (serverConfiguration = []) => {
5+
/**
6+
* @template T
7+
* @template W
8+
* @template PT
9+
* @template PW
10+
* @return {import('@playwright/test').Fixtures<T, W, PT, PW>}
11+
*/
12+
const servers = (serverConfiguration = [], explicitStop = false) => {
613
return {
714
// We pass a tuple to specify fixtures options.
815
// In this case, we mark this fixture as worker-scoped.
@@ -38,9 +45,15 @@ const servers = (serverConfiguration = []) => {
3845
.listen(port, err => {
3946
if (err) throw err;
4047

48+
const server = stoppable(app.server)
4149
servers.push({
42-
server: stoppable(app.server),
43-
port: port
50+
server,
51+
port: port,
52+
stop: async () => {
53+
console.log(`Stopping server on port ${port}...`)
54+
await new Promise(r => server.stop(r))
55+
console.log(`Server on port ${port} stopped`)
56+
}
4457
})
4558
console.log(`> Ready on localhost:${port}!`);
4659

@@ -54,11 +67,13 @@ const servers = (serverConfiguration = []) => {
5467
// Use the server in the tests.
5568
await use(servers)
5669

57-
// Cleanup.
58-
console.log('Stopping servers...');
70+
if (!explicitStop) {
71+
// Cleanup.
72+
console.log('Stopping servers...');
5973

60-
await Promise.all(servers.map(m => new Promise(f => m.server.stop(f))))
61-
console.log('Servers stopped');
74+
await Promise.all(servers.map(s => s.stop()))
75+
console.log('Servers stopped');
76+
}
6277
}, { scope: 'worker', auto: true } ],
6378
}
6479
}

0 commit comments

Comments
 (0)