Chýba Content-Security-Policy

Čo to je

Vaše stránky neposielajú hlavičku Content-Security-Policy. Táto hlavička prehliadaču hovorí, z akých zdrojov smie načítať skripty, obrázky, fonty a iframy.

Bez nej prehliadač spustí akýkoľvek kód, ktorý sa v HTML objaví — či už ho tam dal váš tím, alebo útočník cez XSS.

Prečo je to problém

CSP je jediná účinná obrana proti cross-site scripting (XSS). Keď útočník niekde v aplikácii objaví dieru, cez ktorú pretlačí <script>, bez CSP mu prehliadač ten script s radosťou spustí. S CSP mu prehliadač povie „tento zdroj nemám v allowliste“ a script padne.

Druhá rovina — ochrana pred injektovanými drainermi a SEO spamom. Ak máte správne nastavený script-src, útočník cez hacknutý plugin nemôže ľahko pridať externý script.

Ako to opraviť

CSP je politika, ktorá môže rozbiť stránku. Nasaďte ju najskôr v report-only režime.

Fáza 1 — report-only

Content-Security-Policy-Report-Only: default-src 'self'; img-src 'self' data: https:; script-src 'self' 'unsafe-inline'; style-src 'self' 'unsafe-inline'; report-uri /csp-report

Táto politika nič neblokuje — len pošle JSON na /csp-report pri každom porušení. Sledujte logy niekoľko dní, aby ste vedeli, aké skripty/obrázky/fonty stránka skutočne používa.

Fáza 2 — vyladiť allowlist

Z reportov zostavte konkrétny allowlist. Príklad pre WordPress s Google Fonts a analytikou Umami:

Content-Security-Policy:
  default-src 'self';
  script-src 'self' https://i.xhs.cz;
  style-src 'self' 'unsafe-inline' https://fonts.googleapis.com;
  font-src 'self' https://fonts.gstatic.com;
  img-src 'self' data: https://*.gravatar.com;
  connect-src 'self' https://i.xhs.cz;
  frame-ancestors 'none';
  base-uri 'self';
  form-action 'self';

Fáza 3 — prepnúť na enforce

Keď report-only nehlási žiadne legitímne porušenie, zmeňte hlavičku z Content-Security-Policy-Report-Only na Content-Security-Policy.

Pozor na 'unsafe-inline'

Inline skripty (<script>...</script>) aj inline event handlery (onclick="...") vyžadujú 'unsafe-inline'. Tým ale CSP príde o väčšinu hodnoty proti XSS. Lepšie je použiť nonce alebo hash a inline skripty postupne vyhodiť. WordPress má pre nonce vstavanú podporu.

Konkrétne implementácie

Referencie