Web Security

How Does SRI Relate to Content Security Policy (CSP)?

Understand the relationship between SRI and CSP, how they complement each other, and best practices for implementing both for comprehensive web security.

By Inventive HQ Team

SRI and CSP: Complementary Security Controls

Subresource Integrity (SRI) and Content Security Policy (CSP) are complementary, not competing, security controls: SRI verifies that a specific resource is byte-for-byte the file you expect, while CSP controls which sources a page is allowed to load from at all. SRI pins a cryptographic hash to a <script> or <link> and the browser refuses to run it if the downloaded content does not match; CSP defines an origin allowlist and blocks anything from an unapproved source. They protect against different attacks — a compromised-but-approved CDN versus a script injected from an unapproved origin — so a hardened site deploys both as defense in depth.

That is the summary an AI Overview will give you. What it cannot give you is the diagram, the side-by-side table, and the attack-by-attack breakdown below that show exactly where each control catches something the other misses — and the deprecated directive most CSP guides still get wrong.

Need to build a CSP header to pair with your SRI hashes? Try our free CSP Generator to create a Content Security Policy instantly.

How CSP and SRI complement each other A resource request passes through CSP, which checks whether the source origin is on the allowlist, then through SRI, which checks whether the file content matches its pinned hash. Both must pass before the browser runs the resource. Two questions, two controls Both must pass before the browser runs the resource request CSP WHICH source is allowed to load? origin allowlist script-src 'self' cdn.example checks the SOURCE SRI Is THIS file the one I expect? hash match integrity="sha384-…" checks the CONTENT

CSP blocks an unapproved origin · SRI blocks a tampered file from an approved origin Neither control catches the other's attack — that is why you run both

What SRI and CSP Do

SRI verifies content integrity - It ensures that a resource you load hasn't been modified. When you add an integrity attribute to a script tag, the browser verifies that the downloaded content matches the hash you specified. If it doesn't match, the script is rejected.

CSP controls what can be loaded - It specifies where resources can come from and what they're allowed to do. CSP prevents loading resources from unauthorized sources and can prevent execution of inline scripts entirely.

These are distinct security mechanisms addressing different attack vectors.

SRI vs CSP at a glance

Subresource Integrity (SRI)Content Security Policy (CSP)
Core questionIs this file exactly what I expect?Where is the browser allowed to load from?
What it protectsContent integrity of a known resourceWhich sources/origins may load, and what runs
How it worksPinned cryptographic hash on <script>/<link>Response header / meta with an origin allowlist
Applies toExternal resources with src/hrefScripts, styles, images, fonts, frames, connects — everything
Inline scriptsNot covered (no URL to hash)Covered via nonce-… or sha256-… hashes
Stops a compromised but approved CDNYes — hash no longer matchesNo — the source is still allowed
Stops a script from an unapproved originNo — SRI ignores where it came fromYes — origin not on allowlist is blocked
Stops inline <script> injectionNoYes — inline blocked unless nonce/hash matches
Where the overlap isBoth use cryptographic hashes and both fail closed (block on failure)
Enforced byPer-tag integrity attribute (per resource)One policy for the whole page

The overlap row is where people get confused: both mechanisms use hashes, but for different jobs. A CSP hash authorizes an inline script to run; an SRI hash verifies a downloaded external file is unchanged. Same primitive, opposite direction.

The Attack Scenarios They Protect Against

Consider these scenarios to understand the differences:

Scenario 1: CDN Compromise

An attacker gains access to a CDN hosting your JavaScript libraries. They modify the hosted library to include malicious code.

  • SRI prevents this: The browser verifies the library's hash, detects the modification, and rejects the malicious script.
  • CSP doesn't prevent this: CSP allows scripts from that CDN, so the malicious script would be accepted.

SRI is the primary defense here.

Scenario 2: Attacker Injects Script From Unapproved Origin

An attacker exploits a vulnerability to inject a script tag that loads JavaScript from their own malicious server.

  • SRI can't prevent this: SRI only validates content integrity, not where it comes from. If the attacker controls the injected tag, they also control the integrity hash.
  • CSP prevents this: CSP specifies allowed script sources. If the attacker's domain isn't on the allowlist, the browser rejects the script regardless of its integrity attribute.

CSP is the primary defense here.

Scenario 3: Inline Script Injection

An attacker injects inline JavaScript directly into your HTML.

  • SRI can't prevent this: SRI applies to external resources with src attributes, not inline scripts.
  • CSP prevents this: CSP can restrict or prevent inline scripts entirely, requiring scripts to be external and from approved sources.

CSP is the primary defense here.

Scenario 4: Website Forwarded Through Proxy

Your website is served through an intercepting proxy (common in some corporate networks), and the proxy modifies your scripts while forwarding them.

  • SRI prevents this: The modified content fails integrity verification, protecting against proxy-based attacks.
  • CSP doesn't prevent this: CSP allows scripts from your own origin, so even modified content would be allowed.

SRI is the primary defense here.

Advertisement

How They Work Together: The Layers of Security

A comprehensive approach uses both SRI and CSP:

<!-- CSP prevents loading scripts from unauthorized sources -->
<meta http-equiv="Content-Security-Policy" content="script-src 'self' https://cdn.example.com">

<!-- SRI verifies that the allowed script hasn't been modified -->
<script src="https://cdn.example.com/library.js" integrity="sha256-abc123..."></script>

The CSP header ensures scripts only load from your domain or a specific trusted CDN. The SRI integrity attribute verifies that the script from that trusted source hasn't been modified. Together, they address different attack vectors:

  • CSP: "Only load scripts from sources we trust"
  • SRI: "Even if we load from a trusted source, verify it hasn't been modified"

This defense-in-depth approach means an attacker would need to compromise multiple layers to successfully inject malicious code.

CSP Restrictions on Script Attributes

CSP can actually affect how you use SRI. Modern CSP implementations interact with script attributes:

With script-src 'self', you can load scripts from your own origin:

<script src="https://example.com/my-script.js" integrity="sha256-..."></script>

With script-src 'self' https://trusted-cdn.com, you can load from your origin and a trusted CDN:

<script src="https://trusted-cdn.com/lib.js" integrity="sha256-..."></script>

CSP's allowlist acts as a gatekeeper—only sources on the list are even attempted. SRI then verifies the content from those approved sources.

Can CSP force every resource to use SRI?

Not reliably today. CSP once proposed a require-sri-for directive that would reject any script or style lacking an integrity attribute — effectively making SRI mandatory. require-sri-for is deprecated and never reached stable, cross-browser support, so do not depend on it. Its successor is an Integrity-Policy mechanism (also discussed as integrity-required) being standardized to enforce mandatory SRI, but until browser support is broad, the practical way to guarantee integrity attributes exist is your build or review pipeline: fail the build when an external resource ships without a hash. In other words, CSP defines where resources may come from; enforcing that they carry SRI is currently a tooling problem, not a header you can rely on.

Integrity Hashes and CSP Nonces: Different Approaches to Inline Scripts

CSP and SRI take different approaches to securing inline scripts:

CSP with nonces - Allows specific inline scripts identified by a nonce:

<meta http-equiv="Content-Security-Policy" content="script-src 'nonce-abc123'">
<script nonce="abc123">
  console.log('This inline script is allowed');
</script>

CSP with hashes - Allows inline scripts matching a specific hash:

<meta http-equiv="Content-Security-Policy" content="script-src 'sha256-abc123'">
<script>
  const staticCode = 'never changes';
</script>

SRI applies to external resources and doesn't directly protect inline scripts. This is a key distinction: CSP has mechanisms for inline scripts (nonces and hashes), while SRI focuses on external resources.

Practical Implementation: Combining Both

Step 1: Implement CSP — you can build this policy with our CSP Generator rather than writing it by hand.

<meta http-equiv="Content-Security-Policy"
      content="script-src 'self' https://cdn.jsdelivr.net; style-src 'self' https://fonts.googleapis.com">

This CSP allows scripts from your own origin and a specific CDN, and styles from your origin and Google Fonts.

Step 2: Add SRI to External Resources

<link rel="stylesheet" href="https://fonts.googleapis.com/css2?family=Roboto" integrity="sha256-...">
<script src="https://cdn.jsdelivr.net/npm/axios@0.21.1/dist/axios.min.js" integrity="sha256-..."></script>

Each external resource has an integrity attribute verifying its content. Generate the correct sha384 hash for any external script or stylesheet right here:

Loading interactive tool...

Step 3: Secure Inline Scripts With Nonces

<script nonce="random-value-123">
  const apiUrl = 'https://api.example.com';
</script>

The nonce prevents injection of unauthorized inline scripts.

Reporting and Monitoring

Both SRI and CSP can report violations:

CSP Reporting - You can configure CSP to report violations to a logging endpoint:

Content-Security-Policy: script-src 'self' https://cdn.example.com; report-uri /csp-violations

Violations might indicate:

  • Attempted injection of scripts from unauthorized sources
  • Inline script injection attempts
  • Misconfigured CSP that's too restrictive

SRI Violations - When SRI verification fails, the browser doesn't load the resource and often logs an error (though not all browsers report to CSP report-uri). You can detect this through:

  • Browser console errors
  • Service worker logs
  • Application monitoring

Together, these reporting mechanisms provide visibility into both potential attacks and configuration problems.

Performance Implications

CSP Performance Impact - CSP has minimal performance impact. The browser just checks URLs against the allowlist.

SRI Performance Impact - SRI requires computing a hash of the downloaded content, which has a tiny performance cost. Modern browsers do this efficiently, but it's not completely free.

Combined Impact - Using both SRI and CSP together has minimal performance impact. The security benefits far outweigh any minor performance cost.

Common Mistakes in Using Both

CSP Too Permissive, Relying Only on SRI -

<!-- CSP allows scripts from anywhere -->
<meta http-equiv="Content-Security-Policy" content="script-src *">
<script src="https://example.com/script.js" integrity="sha256-..."></script>

This defeats the purpose of CSP. CSP should restrict the sources; SRI verifies the content. Using both relaxes into using neither.

SRI on Dynamic Content

<script src="https://example.com/dynamic-config.js" integrity="sha256-..."></script>

If the script changes on each request (based on user, timestamp, etc.), the integrity hash becomes invalid. SRI should only be used on truly static resources.

Not Updating SRI When Updating Libraries -

<!-- Old library -->
<script src="https://example.com/lib-1.0.js" integrity="sha256-old123"></script>

If you update the library without updating the integrity hash, the script fails to load.

Forgetting CSP Applies to Images and Fonts Too -

Content-Security-Policy: script-src 'self'

This CSP only restricts scripts. Images can come from anywhere. A more comprehensive CSP restricts all resources:

Content-Security-Policy: default-src 'self'; script-src 'self' cdn.example.com; img-src 'self' data: *.example.com

Modern Framework Support

Modern frameworks often support SRI and CSP automatically:

Create React App - Generates SRI hashes for bundled assets automatically.

Next.js - Has built-in CSP support and can generate integrity attributes.

Django - Provides CSP middleware (django-csp) and can include SRI in templates.

Express.js - Helmet middleware provides CSP; SRI requires manual attribute addition.

Using framework built-in support reduces manual configuration errors.

Real-World Example: Comprehensive Security

<!DOCTYPE html>
<html>
<head>
  <!-- CSP: Strict policy for scripts, styles, fonts -->
  <meta http-equiv="Content-Security-Policy"
        content="default-src 'self';
                 script-src 'self' https://cdn.jsdelivr.net 'nonce-abc123';
                 style-src 'self' https://fonts.googleapis.com;
                 font-src https://fonts.gstatic.com;
                 report-uri /csp-violations">

  <!-- External library with SRI: Verified from trusted CDN -->
  <script src="https://cdn.jsdelivr.net/npm/axios@0.21.1/dist/axios.min.js"
          integrity="sha256-WZKhc00l73eJIGJ+FXbb4YvI8rKeXe7y3+3p5sznTw="></script>

  <!-- Local script: From same origin, no integrity needed -->
  <script src="https://example.com/app.js"></script>

  <!-- Inline script: Secured with nonce -->
  <script nonce="abc123">
    window.API_KEY = 'development-key';
  </script>
</head>
<body>
  <!-- Content -->
</body>
</html>

This example shows:

  • CSP allowing scripts from same origin and a specific CDN, with a nonce for inline scripts
  • SRI on the external library to verify it hasn't been modified
  • Local scripts without SRI (they're from same origin, already protected by CSP)
  • Inline script protected by nonce

Conclusion: Use Both for Maximum Security

SRI and CSP are complementary security mechanisms that address different attack vectors. CSP restricts where resources can come from; SRI verifies that approved resources haven't been modified. Together, they create a defense-in-depth approach that significantly improves security against script injection attacks. Modern web applications should implement both as part of their security strategy, using framework tools and build processes to manage SRI hashes and CSP policies automatically rather than manually maintaining them.

Frequently Asked Questions

What is the difference between SRI and CSP?

SRI (Subresource Integrity) and CSP (Content Security Policy) answer two different questions. SRI answers "is THIS specific resource exactly the file I expect?" — the browser hashes the downloaded script or stylesheet and refuses to run it if the hash does not match the integrity attribute you pinned. CSP answers "WHERE is the browser even allowed to load resources from?" — it defines an allowlist of origins and blocks anything from an unapproved source. SRI checks content; CSP checks source. Neither replaces the other, which is why security teams deploy both.

Does CSP replace the need for SRI?

No. CSP restricts which origins a page can load from, but it does not inspect the content that comes back from an approved origin. If you allow a CDN in your CSP and that CDN is compromised, CSP happily loads the tampered file — it came from an allowed source. SRI is the layer that catches that: the modified file no longer matches its pinned hash, so the browser rejects it. You need SRI precisely for the attack CSP cannot see: a trusted source serving untrusted content.

Can SRI protect inline scripts?

No. SRI only applies to external resources loaded with a src or href attribute (script and link elements). It has no mechanism for inline scripts, which have no URL to fetch and hash. Inline scripts are CSP's job: CSP can block inline JavaScript entirely, or allow specific inline blocks using a nonce (a random per-request token) or a hash of the script's exact contents. So for inline code, CSP's nonce/hash approach is the only control — SRI does not participate.

Is the require-sri-for CSP directive still supported?

The require-sri-for directive — which was meant to force every script or style to carry an integrity attribute — is deprecated and never shipped as a stable cross-browser feature. Do not rely on it. The successor is the Integrity-Policy mechanism (an Integrity-Policy / integrity-required approach) being standardized to enforce mandatory SRI, but until it has broad support the practical way to enforce integrity is your build pipeline: fail the build or the review if an external resource lacks an integrity hash.

What happens if an SRI hash does not match?

The browser blocks the resource entirely — the script does not execute and the stylesheet does not apply, exactly as if the network request had failed. This is fail-closed behavior and it is the whole point: a mismatch means the file changed, whether from a CDN compromise, a proxy rewriting content, or simply a library update you forgot to re-hash. The failure surfaces as a console error. The most common innocent cause is updating a library version without regenerating the hash, so any integrity failure is worth investigating rather than ignoring.

Do CSP nonces and SRI hashes do the same thing?

No — they look similar because both involve hashes, but they guard different things. A CSP hash or nonce authorizes an inline script to run (it proves the inline block is one you intended). An SRI hash verifies that an external file fetched over the network matches the exact bytes you pinned. One is about permitting inline code; the other is about validating downloaded content. A hardened page uses CSP nonces/hashes for its inline scripts and SRI hashes for its external scripts at the same time.

Should I use SRI on scripts from my own domain?

It is usually unnecessary. SRI's main value is protecting resources you do not control — third-party CDNs and shared libraries. Scripts served from your own origin are already governed by CSP's 'self' source and by your own server security, so a first-party file changing implies your server is already compromised. SRI shines on cross-origin resources; for same-origin bundles most teams skip it, though adding it does no harm on truly static assets.

Does CSP or SRI slow down my website?

Both have negligible impact. CSP is essentially a string match of each resource URL against an allowlist, which is effectively free. SRI adds one cryptographic hash computation per protected file after it downloads, which modern browsers do in a fraction of a millisecond. There is no extra network round trip for either. The security gain from defense in depth far outweighs the microscopic CPU cost.

sricspweb-securitysecurity-headersdefense-in-depth