What is a Content Security Policy (CSP)?

A Content Security Policy is an HTTP header that tells browsers which resources a page may load. Learn how CSP blocks XSS attacks and how to deploy one safely.

Published

A Content Security Policy (CSP) is an HTTP response header that tells the browser which sources a page may load content from: scripts, styles, images, frames, fonts. Anything that violates the policy gets blocked, and the browser can send you a report about it.

Why CSP matters

Cross-site scripting (XSS) remains one of the most common web vulnerabilities, and no amount of careful input handling makes it disappear entirely. One injection flaw is enough for an attacker to run arbitrary JavaScript in your users’ browsers. A well-built CSP gives you a second line of defense. The injected code may well land in the page, but the browser refuses to execute it because its source is not allowed by the policy.

A minimal example

Content-Security-Policy: default-src 'self'; script-src 'self' https://js.example.com; object-src 'none'; base-uri 'self'

Broken down:

  • everything loads from the page’s own origin by default (default-src 'self').
  • scripts are allowed only from the origin and https://js.example.com.
  • plugins are forbidden outright (object-src 'none').
  • base-uri 'self' prevents <base> tag hijacking, an attack most people forget exists.

Report-only first, enforce later

Ship a strict policy straight to production and something will break. Usually an inline script you forgot about, a third-party widget, or a browser extension doing something odd. The safe path:

  1. Ship the policy with the Content-Security-Policy-Report-Only header. Nothing is blocked yet.
  2. Point report-uri / report-to at a violation collection endpoint.
  3. Review the reports. Fix the legitimate violations, filter out the extension noise.
  4. Switch the header to Content-Security-Policy to enforce it.

The reports are the painful part: high volume, mostly noise. That is why teams use a dedicated platform such as CentralCSP to aggregate reports, separate real issues from browser-extension junk, and track policy changes over time.

Key directives at a glance

DirectiveControls
default-srcFallback for all resource types
script-srcJavaScript sources, inline scripts, eval
style-srcStylesheets and inline styles
img-srcImages and favicons
connect-srcfetch, XHR, WebSocket targets
frame-ancestorsWho may embed this page (clickjacking protection)
report-to / report-uriWhere violation reports are sent

Where to go next

Start in report-only mode, collect a week of real traffic, then iterate. The next decision waiting for you is nonces or hashes, and it turns on your caching setup more than on your threat model. If what you are protecting is a logged-in product rather than a marketing site, CSP for SaaS platforms picks the story up there. And if nobody on the team has security in their job title, running a solid CSP without a dedicated security engineer is the version we wrote for you.

Frequently asked questions

Does a CSP replace input sanitization?

No. CSP is a defense-in-depth layer. You should still sanitize and escape user input. CSP limits the damage when a cross-site scripting vulnerability slips through anyway.

Will enabling CSP break my site?

It can if deployed carelessly. Start with Content-Security-Policy-Report-Only mode, collect violation reports with a tool like CentralCSP, then enforce the policy once the reports come back clean.

What is the difference between report-only and enforced CSP?

Report-only mode sends violation reports without blocking anything, which makes it safe for testing. Enforced mode blocks disallowed resources and sends reports as well.