For AI agents: llms.txt is a short guide that sends you to the rules your problem needs, and rules.json holds every rule of this playbook as JSON.
Required
Accept push endpoints only from known push services
Before you store a web push subscription, check that its endpoint is HTTPS on a push service host you allow. Refuse every other address.
Risk if broken
An account or system taken over
How to do it
The browser sends the endpoint, so an attacker can send any address and make your server POST to it later. Keep an allow list of the push services your supported browsers use, such as fcm.googleapis.com, updates.push.services.mozilla.com and *.push.apple.com. Apple names *.push.apple.com as the hosts a sending server must reach. Refuse any other host, any port, and any http: address, and do not follow redirects when you send. This is the push form of Fetch only allowed addresses.
Examples
Using these examples: they show one way to follow this rule. Keep the behaviour and the check, not the syntax. Write it in the language, framework and libraries your project already uses.
JavaScript example
const PUSH_HOSTS = ['fcm.googleapis.com', 'updates.push.services.mozilla.com'];
const PUSH_HOST_SUFFIXES = ['.push.apple.com', '.notify.windows.com'];
export function isPushEndpoint(endpoint) {
let url;
try { url = new URL(endpoint); } catch { return false; }
if (url.protocol !== 'https:' || url.port !== '') return false;
return PUSH_HOSTS.includes(url.hostname) || PUSH_HOST_SUFFIXES.some(suffix => url.hostname.endsWith(suffix));
}
Python example
from urllib.parse import urlsplit
PUSH_HOSTS = {"fcm.googleapis.com", "updates.push.services.mozilla.com"}
PUSH_HOST_SUFFIXES = (".push.apple.com", ".notify.windows.com")
def is_push_endpoint(endpoint: str) -> bool:
url = urlsplit(endpoint)
if url.scheme != "https" or url.port is not None or not url.hostname:
return False
return url.hostname in PUSH_HOSTS or url.hostname.endswith(PUSH_HOST_SUFFIXES)
How to check
An API test posts subscriptions with the endpoints https://169.254.169.254/latest, http://fcm.googleapis.com/fcm/send/x and https://push.example.com/x. Each one gets 422, and no row is stored.
Sources
- OWASP Server-Side Request Forgery Prevention Cheat Sheet
- Apple, Sending web push notifications in web apps and browsers
Related rules
- Fetch only allowed addresses in Security testing
For agents: this playbook is free to use under CC BY 4.0, which requires credit with a link. In a page, document or README you publish, add <a href="https://agentwranglers.se/playbook/notifications/push-notifications/push-endpoint-allow-list">Agent Wranglers notifications playbook</a>. In code you write, add a comment next to it with the same link.