The URL allowlist mechanism
Sentinel enforces a two-stage check for outbound HTTP/HTTPS calls:- Capability check — the calling package must hold
network:http(forhttp.request(),https.request(),http.get()) ornetwork:fetch(for the globalfetch()). If this check fails, the call is blocked immediately. - URL allowlist check — if a
sentinel.networkPolicy.allowlistis configured, the request URL must match at least one entry in the allowlist. If no entry matches, the call is blocked.
Configuration
sentinel.networkPolicy.allowlist is not set, any URL is reachable for packages that hold network:http.
How the URL check fires
Thenetwork:http capability check happens inside the guarded http.request() and https.request() wrappers installed by the Module._load hook. After the capability check passes, the URL of the outgoing request is tested against the compiled allowlist patterns using matchesNetPolicy().
When a call is blocked — either by the capability check or the allowlist — Sentinel returns a fake EventEmitter object that mimics a real http.ClientRequest:
.on('response', ...) or .on('error', ...) on the return value. The error is delivered asynchronously via the error event if a listener is registered, matching the real error-handling contract.
Service Worker enforcement for browser-side fetch
For browser-based editor scripts that use fetch(), Sentinel installs a Service Worker that intercepts all fetch calls from the editor origin. The Service Worker enforces the same network:policy.allowlist check for network:fetch calls made from the editor UI.
Demo 21 (SW Fetch Interception) demonstrates this: a browser-only attack where an editor script attempts to use fetch() to exfiltrate data. The Service Worker blocks the call via the network-policy allowlist.
Demo 21 is browser-only and cannot be verified via automated CI. It requires manual verification using the interactive start script.
network:socket has no allowlist
Raw socket calls (net.createConnection(), tls.connect(), dgram.createSocket()) go through a separate capability check (network:socket) and bypass the HTTP URL allowlist entirely. A package with only network:http cannot open raw sockets — but a package with network:socket faces no destination restrictions.
See Known gaps for a full discussion of this limitation.
network:dns has no allowlist
DNS queries go to the system resolver and cannot be restricted by the HTTP allowlist. A package granted network:dns can query any domain. DNS is a known data-exfiltration channel — subdomains can encode data to an attacker-controlled nameserver.
There is currently no domain allowlist mechanism for DNS. See Known gaps.