Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 2 additions & 1 deletion .github/workflows/ci.yml
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,7 @@ jobs:

steps:
- name: Check out repository
uses: actions/checkout@fbc6f3992d24b796d5a048ff273f7fcc4a7b6c09 # v5
uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7.0.1
with:
persist-credentials: false

Expand Down Expand Up @@ -61,6 +61,7 @@ jobs:
run: |
npm install --prefix "$RUNNER_TEMP/acp-browser" --no-save --ignore-scripts playwright@1.63.0 jquery@3.7.1
"$RUNNER_TEMP/acp-browser/node_modules/.bin/playwright" install --with-deps chromium
ACP_BROWSER_MODULES="$RUNNER_TEMP/acp-browser/node_modules" node tests/browser_fixture_test.cjs
ACP_BROWSER_MODULES="$RUNNER_TEMP/acp-browser/node_modules" node tests/theme_ui.cjs
ACP_BROWSER_MODULES="$RUNNER_TEMP/acp-browser/node_modules" node tests/maintenance_ui.cjs

Expand Down
2 changes: 1 addition & 1 deletion .github/workflows/codeql.yml
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,7 @@ jobs:

steps:
- name: Check out repository
uses: actions/checkout@fbc6f3992d24b796d5a048ff273f7fcc4a7b6c09 # v5
uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7.0.1
with:
persist-credentials: false

Expand Down
2 changes: 1 addition & 1 deletion .github/workflows/pr-test-package.yml
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,7 @@ jobs:
if: github.event.label.name == 'test-build'
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@fbc6f3992d24b796d5a048ff273f7fcc4a7b6c09 # v5
- uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7.0.1
with:
ref: ${{ github.event.pull_request.head.sha }}
persist-credentials: false
Expand Down
2 changes: 1 addition & 1 deletion .github/workflows/validate-workflows.yml
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,7 @@ jobs:
actionlint:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@fbc6f3992d24b796d5a048ff273f7fcc4a7b6c09 # v5
- uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7.0.1
with:
persist-credentials: false
- name: Install verified actionlint
Expand Down
12 changes: 12 additions & 0 deletions tests/browser_fixture.cjs
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
// Prepare trusted repository fixtures, not arbitrary/untrusted HTML. Preserve
// inline configuration while loading external scripts and styles explicitly.
async function setFixtureContent(page, html) {
const documentHtml = await page.evaluate(markup => {
const doc = new DOMParser().parseFromString(markup, 'text/html');
doc.querySelectorAll('script[src], link').forEach(element => element.remove());
return '<!DOCTYPE html>' + doc.documentElement.outerHTML;
}, html);
await page.setContent(documentHtml);
}

module.exports = {setFixtureContent};
26 changes: 26 additions & 0 deletions tests/browser_fixture_test.cjs
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
const assert = require('node:assert/strict');
const path = require('node:path');
const dependency = name => process.env.ACP_BROWSER_MODULES ? path.join(process.env.ACP_BROWSER_MODULES, name) : name;
const {chromium} = require(dependency('playwright'));
const {setFixtureContent} = require('./browser_fixture.cjs');

(async () => {
const browser = await chromium.launch({headless:true});
try {
const page = await browser.newPage();
const requests = [];
await page.route('**/*', route => { requests.push(route.request().url()); return route.abort(); });
await setFixtureContent(page, `<!doctype html><html lang="en"><head>
<SCRIPT defer SRC='https://fixture.invalid/one.js'></SCRIPT >
<script src=https://fixture.invalid/two.js></script\n>
<LiNk rel=stylesheet href='https://fixture.invalid/style.css'>
<script>window.fixtureConfig = {value: 'inline configuration retained'};</script>
</head><body><main id="fixture">Fixture content</main></body></html>`);
assert.equal(await page.locator('script[src], link').count(), 0);
assert.equal(await page.evaluate(() => window.fixtureConfig.value), 'inline configuration retained');
assert.equal(await page.locator('#fixture').textContent(), 'Fixture content');
assert.equal(await page.evaluate(() => document.compatMode), 'CSS1Compat');
assert.deepEqual(requests, [], 'Fixture assets must not be requested before explicit injection');
console.log('browser_fixture: DOM preparation handles alternate tag syntax and preserves inline configuration.');
} finally { await browser.close(); }
})().catch(error => { console.error(error); process.exitCode = 1; });
6 changes: 3 additions & 3 deletions tests/i18n_layout.cjs
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@
const path = require('node:path');
const fs = require('node:fs');
const {execFileSync} = require('node:child_process');
const {setFixtureContent} = require('./browser_fixture.cjs');
const assert = require('node:assert/strict');
const modules = process.env.ACP_BROWSER_MODULES;
const dependency = name => modules ? path.join(modules, name) : name;
Expand All @@ -15,13 +16,12 @@ const locales = JSON.parse(fs.readFileSync(path.join(plugin, 'locales/locales.js
const browser = await chromium.launch({headless:true});
try {
for (const [locale, definition] of Object.entries(locales)) {
const html = execFileSync('php', [path.join(__dirname, 'render_i18n_page.php'), locale], {encoding:'utf8', maxBuffer:4e6})
.replace(/<script src="[^"]*"><\/script>/g, '').replace(/<link[^>]+>/g, '');
const html = execFileSync('php', [path.join(__dirname, 'render_i18n_page.php'), locale], {encoding:'utf8', maxBuffer:4e6});
for (const width of [1280, 390]) {
const page = await browser.newPage({viewport:{width, height:900}});
const errors = [];
page.on('pageerror', error => errors.push(error.message));
await page.setContent(html);
await setFixtureContent(page, html);
await page.addStyleTag({path:path.join(plugin, 'styles/appdata.cleanup.plus.css')});
await page.addScriptTag({path:jquery});
for (const name of ['appdata.cleanup.plus.shared.js', 'appdata.cleanup.plus.panels.js']) {
Expand Down
5 changes: 3 additions & 2 deletions tests/maintenance_ui.cjs
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@ const fs = require('node:fs');
const path = require('node:path');
const assert = require('node:assert/strict');
const {execFileSync} = require('node:child_process');
const {setFixtureContent} = require('./browser_fixture.cjs');
const modules = process.env.ACP_BROWSER_MODULES;
const dependency = name => modules ? path.join(modules, name) : name;
const {chromium} = require(dependency('playwright'));
Expand All @@ -13,8 +14,8 @@ const plugin = path.resolve(__dirname, '../source/appdata.cleanup.plus/usr/local
const page = await browser.newPage({viewport:{width:1440,height:1000}});
const errors = [];
page.on('pageerror', e=>errors.push(e.message));
const html = execFileSync('php', [path.join(__dirname,'render_i18n_page.php'),'en_US'], {encoding:'utf8',maxBuffer:4e6}).replace(/<script src="[^"]*"><\/script>/g,'').replace(/<link[^>]+>/g,'');
await page.setContent(html);
const html = execFileSync('php', [path.join(__dirname,'render_i18n_page.php'),'en_US'], {encoding:'utf8',maxBuffer:4e6});
await setFixtureContent(page, html);
await page.addStyleTag({path:path.join(plugin,'styles/appdata.cleanup.plus.css')});
await page.addScriptTag({path:require.resolve(dependency('jquery/dist/jquery.js'))});
await page.evaluate(() => {
Expand Down
5 changes: 3 additions & 2 deletions tests/theme_ui.cjs
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@ const fs = require('node:fs');
const path = require('node:path');
const assert = require('node:assert/strict');
const {execFileSync} = require('node:child_process');
const {setFixtureContent} = require('./browser_fixture.cjs');
const dependency = name => process.env.ACP_BROWSER_MODULES ? path.join(process.env.ACP_BROWSER_MODULES, name) : name;
const {chromium} = require(dependency('playwright'));
const plugin = path.resolve(__dirname, '../source/appdata.cleanup.plus/usr/local/emhttp/plugins/appdata.cleanup.plus');
Expand Down Expand Up @@ -32,8 +33,8 @@ async function nativeCss(version, theme) {
const page = await browser.newPage({viewport:{width,height:1000}});
const errors = [];
page.on('pageerror',error=>errors.push(error.message));
const html = execFileSync('php',[path.join(__dirname,'render_i18n_page.php'),'en_US',theme],{encoding:'utf8',maxBuffer:4e6}).replace(/<script src="[^"]*"><\/script>/g,'').replace(/<link[^>]+>/g,'');
await page.setContent(html);
const html = execFileSync('php',[path.join(__dirname,'render_i18n_page.php'),'en_US',theme],{encoding:'utf8',maxBuffer:4e6});
await setFixtureContent(page, html);
const hostStyle = await page.addStyleTag({content:await nativeCss(version,theme)});
await hostStyle.evaluate(el=>el.id='native-theme');
await page.addStyleTag({path:path.join(plugin,'styles/appdata.cleanup.plus.css')});
Expand Down
Loading