-
Notifications
You must be signed in to change notification settings - Fork 3
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
feat: add support for manifest v3 extensions and background service w…
…orkers (#81)
- Loading branch information
Showing
11 changed files
with
273 additions
and
24 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,2 @@ | ||
// eslint-disable-next-line @typescript-eslint/no-unused-vars | ||
var foo |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,3 @@ | ||
(() => { | ||
window.extension_content_script = true; | ||
})() |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,10 @@ | ||
<!doctype html> | ||
<html> | ||
<head> | ||
<meta charset="utf-8"> | ||
<title>devtools page</title> | ||
<script src="devtools.js"></script> | ||
</head> | ||
<body> | ||
</body> | ||
</html> |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,2 @@ | ||
// eslint-disable-next-line @typescript-eslint/no-empty-function | ||
chrome.devtools.panels.create('test extension', '', 'panel.html', ()=> {}) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,25 @@ | ||
{ | ||
"manifest_version": 3, | ||
"name": "Test Chrome Extension Manifest V3", | ||
"description": "Test Chrome Extension Manifest V3", | ||
"version": "1.2.3", | ||
"devtools_page": "devtools.html", | ||
"content_scripts": [ | ||
{ | ||
"matches": ["*://testpage.test/", "*://testpage.test/frame"], | ||
"js": ["content.js"], | ||
"all_frames": true, | ||
"run_at": "document_start" | ||
} | ||
], | ||
"background": { | ||
"service_worker": "background.js" | ||
}, | ||
"content_security_policy": { | ||
"extension_pages": "script-src 'self' ; object-src 'self'" | ||
}, | ||
"web_accessible_resources": [{ | ||
"resources": ["page.html"], | ||
"matches": ["<all_urls>"] | ||
}] | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,9 @@ | ||
<!doctype html> | ||
<html> | ||
<head> | ||
<meta charset="utf-8"> | ||
<title>extension page</title> | ||
</head> | ||
<body> | ||
</body> | ||
</html> |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,14 @@ | ||
<!doctype html> | ||
<html> | ||
<head> | ||
<meta charset="utf-8"> | ||
<style> | ||
body { | ||
background-color: #fff; | ||
} | ||
</style> | ||
</head> | ||
<body> | ||
<div>devtools panel</div> | ||
</body> | ||
</html> |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,145 @@ | ||
import assert from 'assert' | ||
import puppeteer from 'puppeteer' | ||
import path from 'path' | ||
import fs from 'fs' | ||
import { | ||
setCaptureContentScriptExecutionContexts, | ||
getContentScriptExcecutionContext, | ||
getDevtools, | ||
getDevtoolsPanel, | ||
getBackground | ||
} from '../src' | ||
|
||
beforeEach(async function () { | ||
try { | ||
const pathToExtension = path.resolve(__dirname, 'extension-manifest-v3') | ||
|
||
const browser = await puppeteer.launch({ | ||
args: [ | ||
`--disable-extensions-except=${pathToExtension}`, | ||
`--load-extension=${pathToExtension}` | ||
], | ||
defaultViewport: null, | ||
devtools: true, | ||
headless: false | ||
}) | ||
|
||
const [page] = await browser.pages() | ||
|
||
// Respond to http://testpage urls with a set fixture page | ||
await page.setRequestInterception(true) | ||
page.on('request', async request => { | ||
if (request.url() === 'http://testpage.test/frame') { | ||
const body = fs.readFileSync( | ||
path.resolve(__dirname, 'fixtures/frame.html') | ||
) | ||
return request.respond({ | ||
body, | ||
contentType: 'text/html', | ||
status: 200 | ||
}) | ||
} | ||
if (request.url().startsWith('http://testpage')) { | ||
const body = fs.readFileSync( | ||
path.resolve(__dirname, 'fixtures/index.html') | ||
) | ||
return request.respond({ | ||
body, | ||
contentType: 'text/html', | ||
status: 200 | ||
}) | ||
} | ||
return request.continue() | ||
}) | ||
|
||
this.manifestV3context = { | ||
browser, | ||
page | ||
} | ||
} catch (ex) { | ||
console.log(`Did not launch browser: ${(ex as Error).message}`) | ||
} | ||
}) | ||
|
||
afterEach(async function() { | ||
const { browser } = this.manifestV3context | ||
if (browser) { | ||
await browser.close() | ||
} | ||
this.manifestV3context = null | ||
}) | ||
|
||
describe('puppeteer-devtools (manifest v3)', () => { | ||
|
||
it('should return devtools page', async function() { | ||
const { page } = this.manifestV3context | ||
const devtools = await getDevtools(page) | ||
assert.match(await devtools.url(), /^devtools:\/\//) | ||
}) | ||
|
||
it('should return background page', async function() { | ||
const { page } = this.manifestV3context | ||
const background = await getBackground(page) | ||
assert.match(await background?.url(), /background.js$/) | ||
}) | ||
|
||
it('should return devtools panel', async function() { | ||
const { page } = this.manifestV3context | ||
const devtools = await getDevtoolsPanel(page) | ||
const body = await devtools.$('body') | ||
const textContent = await devtools.evaluate(el => el?.textContent, body) | ||
assert.equal(textContent?.trim(), 'devtools panel') | ||
}) | ||
|
||
it('should throw with no matching strategies for showing devtools panel', async function() { | ||
const { page } = this.manifestV3context | ||
const devtools = await getDevtools(page) | ||
// remove known chrome public apis to force errors | ||
await devtools.evaluate(` | ||
delete window.UI | ||
delete window.InspectorFrontendAPI | ||
`) | ||
await assert.rejects(getDevtoolsPanel(page, { timeout: 100 }), (err: Error) => { | ||
assert.match(err.message, /Unable to find view manager for browser executable/) | ||
return true | ||
}) | ||
}) | ||
|
||
it('should return extension content script execution context', async function() { | ||
const { page } = this.manifestV3context | ||
await setCaptureContentScriptExecutionContexts(page) | ||
await page.goto('http://testpage.test', { waitUntil: 'networkidle2' }) | ||
const contentExecutionContext = await getContentScriptExcecutionContext(page) | ||
const mainFrameContext = await page.evaluate( | ||
() => (window as any).extension_content_script | ||
) | ||
const contentContext = await contentExecutionContext.evaluate( | ||
() => (window as any).extension_content_script | ||
) | ||
assert.equal(typeof mainFrameContext, 'undefined') | ||
assert(contentContext) | ||
}) | ||
|
||
it('should throw error when unable to find content script execution context', async function() { | ||
const { page } = this.manifestV3context | ||
await page.goto('http://testpage.test', { waitUntil: 'networkidle2' }) | ||
assert.rejects(async () => await getContentScriptExcecutionContext(page)) | ||
}) | ||
|
||
it('should throw error when unable to find content script execution context on page without permissions', async function() { | ||
const { page } = this.manifestV3context | ||
await setCaptureContentScriptExecutionContexts(page) | ||
await page.goto('http://testpage.test/that/does/not/have/permission', { | ||
waitUntil: 'networkidle2' | ||
}) | ||
assert.rejects(async () => await getContentScriptExcecutionContext(page)) | ||
}) | ||
|
||
it('should throw error when unable to find devtools panel', async function() { | ||
const { page } = this.manifestV3context | ||
assert.rejects(async () => | ||
getDevtoolsPanel(page, { panelName: 'foo.html', timeout: 500 }) | ||
) | ||
}) | ||
|
||
}) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters