Tests how the web-app-installation Permissions Policy affects
navigator.install() and the <install> element
in various iframe configurations.
web-app-installation is allowed for self (the top-level document's origin).allow attribute on the <iframe> tag.Permissions-Policy HTTP header can restrict or grant the policy server-side, but GitHub Pages does not support custom headers, so we test the allow attribute approach here.These run directly in the top-level browsing context. Should always work.
await navigator.install();
<install></install>
allow attribute (default)Expected: Blocked — subframes do not inherit the permission by default.
<iframe src="iframe.html"></iframe>
allow="web-app-installation"Expected (with iframe support): Allowed — parent explicitly delegates the permission to same-origin child.
Expected (without iframe support): Blocked — delegation not supported.
<iframe src="iframe.html" allow="web-app-installation"></iframe>
allow="web-app-installation 'none'" (explicitly denied)Expected: Blocked — parent explicitly revokes the permission even for same-origin.
<iframe src="iframe.html" allow="web-app-installation 'none'"></iframe>
allow="web-app-installation 'self'"Expected (with iframe support): Allowed — explicitly grants to self (the iframe's own origin, which matches the parent).
Expected (without iframe support): Blocked — delegation not supported.
<iframe src="iframe.html" allow="web-app-installation 'self'"></iframe>
allow attributeExpected: Blocked — cross-origin without delegation.
<iframe src="https://liahiscock.github.io/PWA/WebInstall/index.html"></iframe>
allow="web-app-installation"Expected: Delegation attempted — behavior depends on whether cross-origin install delegation is supported.
<iframe src="https://liahiscock.github.io/PWA/WebInstall/index.html" allow="web-app-installation"></iframe>
allow="web-app-installation https://liahiscock.github.io"Expected: Delegation to specific origin — tests origin-scoped delegation.
<iframe src="https://liahiscock.github.io/PWA/WebInstall/index.html" allow="web-app-installation https://liahiscock.github.io"></iframe>
sandbox="allow-scripts", no allowExpected: Blocked — not supported.
<iframe src="iframe.html" sandbox="allow-scripts"></iframe>
sandbox="allow-scripts" + allow="web-app-installation"Expected: Blocked — not supported.
<iframe src="iframe.html" sandbox="allow-scripts" allow="web-app-installation"></iframe>
sandbox="allow-scripts allow-same-origin" + allow="web-app-installation"Expected: Blocked — not supported.
<iframe src="iframe.html" sandbox="allow-scripts allow-same-origin" allow="web-app-installation"></iframe>
The <install> element should obey the same permission policy as the API.
allowExpected: Blocked
allow="web-app-installation"Expected (with iframe support): Allowed
Expected (without iframe support): Blocked
<iframe src="iframe.html" allow="web-app-installation"></iframe>
allow="web-app-installation"Expected: Delegation attempted — depends on cross-origin support.
The Permissions-Policy HTTP response header can also control the policy at the server level. Examples:
// Disable for all contexts (including self):
Permissions-Policy: web-app-installation=()
// Allow for self only (default):
Permissions-Policy: web-app-installation=(self)
// Allow for self and a specific origin:
Permissions-Policy: web-app-installation=(self "https://liahiscock.github.io")
// Allow for all origins:
Permissions-Policy: web-app-installation=*
Note: GitHub Pages does not support custom HTTP response headers.
To test header-based policies, you would need a server you control (e.g., Express, Netlify with _headers,
Cloudflare Workers, or a local dev server).