DEV Community

Ubaid Ullah
Ubaid Ullah

Posted on Originally published at djangix.com

Content Security Policy Blocking Your Scripts? Fix "Refused to Execute Inline Script" Properly

Originally published on the Djangix blog. This is a condensed version — the full article is linked at the end.

You add a Content Security Policy, deploy, and the site looks fine but nothing responds. That is not the policy failing — it is the policy working. Your own inline code simply is not allowed yet.

What the policy is doing

CSP is a browser-enforced allowlist for scripts, styles, images and connections. Its main security value is against injected scripts, and injected code is usually inline — so a strict policy blocks inline code by default, including yours.

Five fixes, in the order to try them

  1. Move inline code to external files. This is the fix the policy is pushing you toward. A script file served from your own origin is already allowed by a self-only script rule, and it also gains caching and linting.
  2. Use a fresh nonce for code that must stay inline. Some per-page configuration has to be rendered inline. Generate a random value for every response, put the same value in the policy and the tag, and never reuse it.
  3. Hash a script that never changes. A fixed snippet can be allowed by its hash — but any edit, even formatting, changes the hash and blocks it again.
  4. Replace inline handlers with listeners. Attributes such as click handlers in markup are blocked, which is why pages can load while buttons do nothing. Move the behaviour into JavaScript and attach listeners there.
  5. Name third parties explicitly. Analytics, chat and embeds each need their own origins listed in the relevant directives. Do not use a wildcard — that also allows an attacker's origin.

The shortcut to avoid

Allowing inline scripts generally makes the errors disappear by disabling the protection CSP exists to provide. If that is the fix, the policy is mostly decoration.

Safer rollout

Start in report-only mode: the browser enforces nothing but reports violations, so you can find and fix real usage before enforcing the same policy for users.


Read the full article on Djangix: Content Security Policy Blocking Your Scripts? — including the Django nonce middleware example and the full ranked fixes.

Top comments (0)