I’m using playwright to test my chrome extension. Currently I’m using page.evaluate to ensure chrome is defined. The problem with this approach is that I have to serialize my functions to run them in the scope of page.evaluate (the browser). Is there a better approach to where I don’t have to serialize my functions but still have access to the chrome api?
fixtures.ts
export const test = base.extend<{
context: BrowserContext
serviceWorker: Worker
extensionId: string
}>({
context: async ({}, use) => {
const pathToExtension = path.join(__dirname, "../build")
const context = await chromium.launchPersistentContext("", {
headless: false,
args: [
`--disable-extensions-except=${pathToExtension}`,
`--load-extension=${pathToExtension}`,
],
})
await use(context)
await context.close()
},
serviceWorker: async ({ context }, use) => {
let [serviceWorker] = context.serviceWorkers()
if (!serviceWorker) serviceWorker = await context.waitForEvent("serviceworker")
await use(serviceWorker)
},
extensionId: async ({ serviceWorker }, use) => {
const extensionId = serviceWorker.url().split("/")[2]
await use(extensionId)
},
})
export const expect = test.expect
example test case
test("move single tab in current window", async ({ page }) => {
const newTab = await page.evaluate(
async (data) => {
const { windows, moveTabFunc, getTabFunc } = data
const moveTab = new Function("return " + moveTabFunc)()
const getTab = new Function("return " + getTabFunc)()
const tab = windows![0].tabs![3]
await moveTab(tab.id, { index: 4 })
const newTab = await getTab(tab.id)
return newTab
},
{ windows, moveTabFunc: moveTab.toString(), getTabFunc: getTab.toString() }
)
expect(newTab.index).toBe(4)
expect(newTab.windowId).toBe(windows![0].id)
})