Content Security Policy (CSP)
What is Content Security Policy (CSP)?
Content Security Policy (CSP) is a browser security mechanism that helps prevent cross-site scripting (XSS), data injection attacks, and other content execution vulnerabilities by defining and enforcing rules about what resources a web page can load and execute. CSP acts as an additional layer of security that works alongside other web security measures to mitigate the impact of potential vulnerabilities.
CSP is implemented through an HTTP response header or meta tag that specifies approved sources for various types of content, effectively creating a whitelist of trusted origins.
How CSP Works
- Policy Definition: Website administrator defines CSP rules in HTTP headers or meta tags
- Policy Delivery: Browser receives CSP directives with the web page response
- Resource Loading: Browser attempts to load resources (scripts, images, styles, etc.)
- Policy Enforcement: Browser checks each resource against CSP rules
- Action: Browser blocks resources that violate CSP directives
- Reporting: Browser can report violations to a specified endpoint (optional)
Key CSP Directives
Resource Control Directives
- default-src: Fallback for other directives
- script-src: Controls JavaScript sources
- style-src: Controls CSS sources
- img-src: Controls image sources
- font-src: Controls font sources
- connect-src: Controls connection sources (AJAX, WebSocket, etc.)
- media-src: Controls audio and video sources
- object-src: Controls plugins (Flash, Java, etc.)
- frame-src: Controls frame/iframe sources
- child-src: Controls web workers and nested browsing contexts
Document Directives
- base-uri: Restricts URLs for the document's base element
- form-action: Restricts URLs for form submissions
- frame-ancestors: Replaces X-Frame-Options for frame embedding control
Navigation Directives
- navigate-to: Restricts URLs to which a document can navigate
Reporting Directives
- report-uri: Specifies where violation reports should be sent
- report-to: Modern replacement for report-uri (uses Report-To header)
Other Directives
- sandbox: Applies sandbox restrictions to the page
- upgrade-insecure-requests: Upgrades HTTP requests to HTTPS
- block-all-mixed-content: Blocks mixed content (HTTP in HTTPS pages)
- require-sri-for: Requires Subresource Integrity for specified resource types
CSP Levels and Versions
| Version | Key Features | Status |
|---|---|---|
| CSP Level 1 | Basic directives, initial implementation | Obsolete |
| CSP Level 2 | Nonce support, hash support, frame-ancestors | Widely supported |
| CSP Level 3 | Strict-dynamic, report-to, navigate-to, webrtc | Current standard |
| CSP Next | Future enhancements, experimental features | In development |
Implementation Methods
HTTP Header
Content-Security-Policy: default-src 'self'; script-src 'self' https://trusted.cdn.com; img-src 'self' data:; report-uri https://example.com/csp-report-endpoint
Meta Tag
<meta http-equiv="Content-Security-Policy" content="default-src 'self'; script-src 'self' https://trusted.cdn.com">
Common CSP Use Cases
Preventing XSS Attacks
- Restrict inline scripts with
'unsafe-inline' - Require nonces or hashes for script execution
- Block eval() and similar functions with
'unsafe-eval'
Securing Third-Party Content
- Whitelist specific CDNs and external domains
- Implement Subresource Integrity (SRI) for external resources
- Restrict mixed content with
upgrade-insecure-requests
Controlling Frame Embedding
- Use
frame-ancestorsto prevent clickjacking - Restrict embedding to specific domains or block entirely
Monitoring Security Violations
- Implement
report-uriorreport-toto collect violation reports - Monitor for attempted attacks and misconfigurations
CSP Keywords and Values
| Keyword/Value | Description |
|---|---|
'none' | Blocks all resources of the specified type |
'self' | Allows resources from the same origin |
'unsafe-inline' | Allows inline scripts/styles (not recommended) |
'unsafe-eval' | Allows eval() and similar functions (not recommended) |
'strict-dynamic' | Allows scripts loaded by trusted scripts to execute |
'nonce-<value>' | Allows scripts/styles with matching nonce attribute |
'sha256-<hash>' | Allows scripts/styles with matching SHA-256 hash |
'sha384-<hash>' | Allows scripts/styles with matching SHA-384 hash |
'sha512-<hash>' | Allows scripts/styles with matching SHA-512 hash |
data: | Allows data URIs (use with caution) |
blob: | Allows blob URIs |
mediastream: | Allows mediastream URIs |
CSP vs. Other Security Headers
| Header | Purpose | Relationship to CSP |
|---|---|---|
| Content Security Policy (CSP) | Controls resource loading and execution | Primary security mechanism |
| X-Frame-Options | Controls frame embedding | Replaced by CSP's frame-ancestors |
| X-Content-Type-Options | Prevents MIME sniffing | Complements CSP |
| HTTP Strict Transport Security | Enforces HTTPS | Works alongside CSP |
| Referrer-Policy | Controls referrer information | Independent but complementary |
Real-World Examples
- Twitter: Implemented CSP to prevent XSS attacks and reduce security risks
- GitHub: Uses CSP with strict-dynamic and nonce-based script execution
- Google: Implements CSP across various services to enhance security
- Facebook: Uses CSP to control third-party content and prevent data exfiltration
- Financial Institutions: Banks use CSP to secure online banking platforms
- E-commerce Sites: Use CSP to protect payment processing and customer data
Implementation Challenges
Common Issues
- Inline Scripts/Styles: Legacy code often relies on inline scripts/styles
- Third-Party Dependencies: External libraries may violate CSP rules
- Dynamic Content: JavaScript frameworks that generate dynamic content
- Browser Compatibility: Different browsers support different CSP features
- Performance Impact: Additional checks may impact page load times
- Debugging Complexity: Violations can be difficult to diagnose
Best Practices for Implementation
- Start with Report-Only Mode: Use
Content-Security-Policy-Report-Onlyto monitor violations - Gradual Rollout: Implement CSP in stages, starting with permissive policies
- Use Nonces/Hashes: Replace
'unsafe-inline'with nonces or hashes - Monitor Violations: Set up reporting to collect and analyze CSP violations
- Test Thoroughly: Test across different browsers and devices
- Document Policies: Maintain documentation of CSP rules and exceptions
- Educate Developers: Train developers on CSP-compliant coding practices
- Automate Enforcement: Use build tools to generate and validate CSP headers
CSP Reporting
Report-Only Mode
Content-Security-Policy-Report-Only: default-src 'self'; report-uri https://example.com/csp-report-endpoint
Violation Report Format
{
"csp-report": {
"document-uri": "https://example.com/page.html",
"referrer": "https://example.com/",
"violated-directive": "script-src 'self'",
"effective-directive": "script-src",
"original-policy": "default-src 'self'; script-src 'self' https://trusted.cdn.com; report-uri https://example.com/csp-report-endpoint",
"disposition": "enforce",
"blocked-uri": "https://evil.com/malicious.js",
"line-number": 42,
"column-number": 12,
"source-file": "https://example.com/page.html",
"status-code": 200,
"script-sample": "alert('XSS')"
}
}
Advanced CSP Features
Strict CSP
Content-Security-Policy: script-src 'nonce-{random}' 'strict-dynamic'; object-src 'none'; base-uri 'none'
Trusted Types
Content-Security-Policy: require-trusted-types-for 'script'; trusted-types default
CSP with Service Workers
// In service worker
self.addEventListener('fetch', event => {
event.respondWith(
fetch(event.request).then(response => {
// Modify CSP headers for responses
const newHeaders = new Headers(response.headers);
newHeaders.set('Content-Security-Policy', "default-src 'self'");
return new Response(response.body, {
status: response.status,
statusText: response.statusText,
headers: newHeaders
});
})
);
});
Industry-Specific Considerations
| Industry | CSP Considerations | Potential Challenges |
|---|---|---|
| Finance | Strict policies for payment processing | Legacy banking systems |
| Healthcare | HIPAA compliance, patient data protection | Third-party health tools |
| E-commerce | Payment gateway security, customer data | Marketing trackers, analytics |
| Government | Classified information protection | Legacy government systems |
| Media | Content distribution, advertising | Third-party ad networks |
| Technology | API security, SaaS platforms | Dynamic content generation |
| Education | Student data protection | Learning management systems |
Legal and Compliance Aspects
- GDPR: CSP can help demonstrate security measures for data protection
- PCI DSS: CSP is recommended for securing payment card data
- HIPAA: CSP can support compliance with health data security requirements
- FISMA: CSP may be required for federal information systems
- Industry Standards: CSP aligns with various security best practices
Future of CSP
- More Granular Control: Additional directives for emerging web technologies
- Better Integration: Improved integration with web frameworks and build tools
- Enhanced Reporting: More detailed and actionable violation reports
- Automated Enforcement: AI-powered policy generation and enforcement
- Browser Improvements: Better developer tools for CSP debugging
- Standardization: Continued evolution of the CSP specification
Best Practices for CSP Implementation
- Start with report-only mode to monitor violations without breaking functionality
- Use nonces or hashes instead of
'unsafe-inline'for scripts and styles - Implement strict-dynamic for modern JavaScript applications
- Set up violation reporting to monitor and respond to security incidents
- Regularly review and update CSP policies as your application evolves
- Test across browsers to ensure consistent behavior
- Combine with other security headers for layered defense
- Educate developers about CSP-compliant coding practices
- Use build tools to automate CSP header generation
- Monitor performance impact and optimize policies as needed
Clickjacking
Clickjacking is a web security vulnerability that tricks users into clicking on malicious elements disguised as legitimate content, enabling attackers to perform unauthorized actions on behalf of the user.
Credential Stuffing
Cyberattack technique using stolen username and password pairs to gain unauthorized access to accounts.
