How Content Security Policy Prevents Injection Attacks
Content Security Policy (CSP) is a critical HTTP response header that restricts the resources a browser is allowed to load and execute on a web page. By establishing strict rules for fetching scripts, stylesheets, and data, CSP acts as a robust defense layer designed specifically to prevent code injection attacks, primarily Cross-Site Scripting (XSS). This article breaks down the operational mechanics of CSP, detailing how directive enforcement, script execution restrictions, and reporting mechanisms eliminate malicious payloads.
Restricting Trusted Resource Sources
The primary mechanism of CSP is resource whitelisting through
explicit directives. By defining directives like
default-src, script-src, and
style-src, a web developer can tell the browser exactly
which origins are permitted to serve executable code and assets.
When an attacker successfully injects an external script tag—such as
<script src="https://attacker.com/malicious.js"></script>—the
browser evaluates the source domain against the active
script-src directive. If attacker.com is not
explicitly permitted in the policy, the browser blocks the network
request immediately, preventing the hostile code from loading.
Disabling Inline Execution and Dynamic Code Evaluation
Most injection attacks rely on executing arbitrary inline scripts or abusing dynamic JavaScript execution functions. CSP mitigates this behavior through two default behaviors:
- Blocking Inline Scripts: By default, CSP disallows
the execution of inline
<script>elements, inline event handlers (such asonclick="..."), andjavascript:URIs. Even if an attacker injects<script>stealData()</script>into a vulnerable comment field, the browser identifies it as an inline script and refuses to run it. - Restricting
eval(): CSP bans the use ofeval(),new Function(),setTimeout(string), and related dynamic string-to-code execution primitives unless the risky'unsafe-eval'keyword is explicitly permitted. This stops attackers from passing injected strings into dynamic execution sinks.
Implementing Cryptographic Nonces and Hashes
Modern applications often require legitimate inline scripts to function. CSP solves this without weakening security by implementing cryptographic nonces (numbers used once) and SHA hashes:
- Nonces: A server generates a cryptographically
random, single-use token on every HTTP request and includes it in the
header:
Content-Security-Policy: script-src 'nonce-EDNnf03nceI1nnq'. The developer includes this matching nonce in authorized inline scripts:<script nonce="EDNnf03nceI1nnq">...</script>. Injected scripts lacking this unpredictable value are rejected. - Hashes: Developers can calculate the SHA-256 (or higher) hash of a static inline script and specify it in the policy. The browser hashes the script before execution; if the generated hash does not match the policy, execution is blocked.
Preventing Data Exfiltration
A successful injection attack often attempts to transmit sensitive user data—such as session tokens, credentials, or personal information—to a remote server controlled by the attacker. CSP limits this phase of an attack using directives that govern outbound connections:
connect-srclimits destinations forfetch(),XMLHttpRequest, WebSockets, andEventSource.form-actioncontrols which targets can receive<form>submissions, preventing attackers from injecting actions that submit user inputs to external URLs.
By locking down outbound communications, CSP ensures that even if an attacker manages to execute code in the browser context, they cannot easily exfiltrate captured data.
Monitoring Violations with Reporting Directives
CSP provides a controlled path for deployment through violation
reporting. Using the report-to or report-uri
directive, the browser sends JSON-formatted reports to a specified
endpoint whenever a policy violation occurs.
Developers can also deploy policies using the
Content-Security-Policy-Report-Only header. In this mode,
the browser logs violations and alerts security teams to potential
injection attempts or policy misconfigurations without interrupting page
rendering. Once the policy is validated, moving it to standard
enforcement blocks all non-compliant scripts automatically.