From 56fca0d21acb174689388cbd789aa67c699c6e91 Mon Sep 17 00:00:00 2001 From: Brad Slayter Date: Mon, 15 Jan 2024 12:41:57 -0600 Subject: [PATCH] Add AMP loop protection --- index.html | 1 + .../amp-loop-protection/amp-only.html | 58 +++++++ .../amp-loop-protection/index.html | 28 ++++ .../amp-loop-protection/main.js | 142 ++++++++++++++++++ .../amp-loop-protection/style.css | 7 + privacy-protections/index.html | 1 + 6 files changed, 237 insertions(+) create mode 100644 privacy-protections/amp-loop-protection/amp-only.html create mode 100644 privacy-protections/amp-loop-protection/index.html create mode 100644 privacy-protections/amp-loop-protection/main.js create mode 100644 privacy-protections/amp-loop-protection/style.css diff --git a/index.html b/index.html index 13d5ba0..46c5e53 100644 --- a/index.html +++ b/index.html @@ -76,6 +76,7 @@

Privacy Protections Tests

  • Surrogates
  • Global Privacy Control
  • AMP Links
  • +
  • AMP Loop Protection
  • Query Parameters
  • Runtime checks
  • diff --git a/privacy-protections/amp-loop-protection/amp-only.html b/privacy-protections/amp-loop-protection/amp-only.html new file mode 100644 index 0000000..c54447a --- /dev/null +++ b/privacy-protections/amp-loop-protection/amp-only.html @@ -0,0 +1,58 @@ + + + + + + + AMP loop protection + + +

    + + + \ No newline at end of file diff --git a/privacy-protections/amp-loop-protection/index.html b/privacy-protections/amp-loop-protection/index.html new file mode 100644 index 0000000..6b190bd --- /dev/null +++ b/privacy-protections/amp-loop-protection/index.html @@ -0,0 +1,28 @@ + + + + + + AMP loop protection + + + + + +

    [Home][Privacy Protections Tests][AMP Upgrade Loop Protection]

    + +

    This test will navigate to a non-AMP page that immediately redirects to its AMP version. This will cause a non-AMP↔AMP loop (client trying to get real page, page redirecting). Clients should detect this scenario and allow the AMP page to load.

    +

    If the loop protection works the reported url will have the amp=1 parameter.

    + +

    + + + +

    + + + \ No newline at end of file diff --git a/privacy-protections/amp-loop-protection/main.js b/privacy-protections/amp-loop-protection/main.js new file mode 100644 index 0000000..e6bc79e --- /dev/null +++ b/privacy-protections/amp-loop-protection/main.js @@ -0,0 +1,142 @@ +const startButton = document.querySelector('#start'); +const downloadButton = document.querySelector('#download'); + +const testsDiv = document.querySelector('#tests'); +const testsSummaryDiv = document.querySelector('#tests-summary'); +const testsDetailsDiv = document.querySelector('#tests-details'); + +const TEST_DOMAIN = 'good.third-party.site'; + +const tests = [ + { + id: 'rewrite-amp', + run: () => { + let res; + const promise = new Promise((resolve, reject) => { res = resolve; }); + const otherWindow = window.open(`http://${TEST_DOMAIN}/privacy-protections/amp-loop-protection/amp-only.html?amp=1&start`); + + const interval = setInterval(() => { + otherWindow.postMessage({ action: 'url', type: 'navigation' }, `http://${TEST_DOMAIN}/`); + }, 500); + + function onMessage (m) { + if (m.data && m.data.type === 'navigation') { + clearInterval(interval); + otherWindow.close(); + window.removeEventListener('message', onMessage); + console.log('navigation', m.data.url); + res(m.data.url); + } + } + + window.addEventListener('message', onMessage); + + return promise; + } + } +]; + +// object that contains results of all tests +const results = { + page: 'amp-loop-protection', + date: null, + results: [] +}; + +function resultToHTML (data) { + if (Array.isArray(data)) { + return ``; + } else if (data) { + return JSON.stringify(data, null, 2); + } + + return null; +} + +/** + * Test runner + */ +function runTests () { + startButton.setAttribute('disabled', 'disabled'); + downloadButton.removeAttribute('disabled'); + testsDiv.removeAttribute('hidden'); + + results.results.length = 0; + results.date = (new Date()).toUTCString(); + let all = 0; + let failed = 0; + + testsDetailsDiv.innerHTML = ''; + + function updateSummary () { + testsSummaryDiv.innerText = `Performed ${all} tests${failed > 0 ? ` (${failed} failed)` : ''}. Click for details.`; + } + + for (const test of tests) { + const resultObj = { + id: test.id, + value: null + }; + results.results.push(resultObj); + + const li = document.createElement('li'); + li.id = `test-${test.id.replace(' ', '-')}`; + li.innerHTML = `${test.id} - `; + const valueSpan = li.querySelector('.value'); + + testsDetailsDiv.appendChild(li); + + try { + const result = test.run(); + + if (result instanceof Promise) { + result + .then(data => { + valueSpan.textContent = resultToHTML(data); + resultObj.value = data || null; + }) + .catch(e => { + failed++; + valueSpan.innerHTML = `❌ error thrown ("${e.message ? e.message : e}")`; + updateSummary(); + }); + } else { + valueSpan.innerHTML = resultToHTML(result); + resultObj.value = result || null; + } + } catch (e) { + failed++; + valueSpan.innerHTML = `❌ error thrown ("${e.message ? e.message : e}")`; + } + + all++; + } + + updateSummary(); + + startButton.removeAttribute('disabled'); +} + +function downloadTheResults () { + const data = JSON.stringify(results, null, 2); + const a = document.createElement('a'); + const url = window.URL.createObjectURL(new Blob([data], { type: 'application/json' })); + a.href = url; + a.download = 'amp-loop-protection-results.json'; + + document.body.appendChild(a); + a.click(); + + window.URL.revokeObjectURL(url); + a.remove(); +} + +downloadButton.addEventListener('click', () => downloadTheResults()); + +// run tests if button was clicked or… +startButton.addEventListener('click', () => runTests()); + +// if url query is '?run' start tests imadiatelly +if (document.location.search === '?run') { + runTests(); +} diff --git a/privacy-protections/amp-loop-protection/style.css b/privacy-protections/amp-loop-protection/style.css new file mode 100644 index 0000000..060125f --- /dev/null +++ b/privacy-protections/amp-loop-protection/style.css @@ -0,0 +1,7 @@ +* { + box-sizing: border-box; +} + +.value { + color: gray; +} \ No newline at end of file diff --git a/privacy-protections/index.html b/privacy-protections/index.html index 1585244..2d904d7 100644 --- a/privacy-protections/index.html +++ b/privacy-protections/index.html @@ -24,6 +24,7 @@

    Privacy Protections Tests

  • Surrogates
  • Global Privacy Control
  • AMP Links
  • +
  • AMP Loop Protection
  • Query Parameters