Comment fonctionne la Politique de sécurité du contenu?

je reçois un tas d'erreurs dans la console du développeur:

a Refusé d'évaluer une chaîne de caractères

a refusé d'exécuter le script en ligne parce qu'il viole la directive suivante de la Politique de sécurité du contenu

a refusé de charger le script

a refusé de charger la feuille de style

c'est Quoi? Comment fonctionne la Politique de sécurité du contenu? Comment utiliser L'en-tête HTTP Content-Security-Policy ?

spécifiquement, comment faire...

  1. ...autoriser plusieurs sources?
  2. ...utiliser des directives différentes?
  3. ...utiliser plusieurs directives?
  4. ...poignée de ports?
  5. ...gérer des protocoles différents?
  6. ...autoriser le protocole file:// ?
  7. ...utiliser les styles en ligne, scripts, et tags <style> et <script> ?
  8. ...permettre à eval() ?

et enfin:

  1. que signifie exactement 'self' ?
156
demandé sur Michał Perłakowski 2015-05-16 23:22:47

2 réponses

la méta-étiquette Content-Security-Policy vous permet de réduire le risque d'attaques XSS en vous permettant de définir d'où les ressources peuvent être chargées, empêchant les navigateurs de charger des données à partir d'autres endroits. Cela rend plus difficile pour un attaquant d'injecter du code malveillant dans votre site.

j'ai cogné ma tête contre un mur de briques en essayant de comprendre pourquoi je recevais des erreurs CSP l'un après l'autre, et il ne semble pas y avoir de concise, des instructions claires sur la façon dont ça marche. Donc voici ma tentative d'expliquer quelques points de CSP brièvement, se concentrant principalement sur les choses que j'ai trouvé difficile à résoudre.

par souci de brièveté, Je n'écrirai pas l'étiquette complète dans chaque échantillon. Au lieu de cela, je vais seulement montrer la propriété content , donc un échantillon qui dit content="default-src 'self'" signifie ceci:

<meta http-equiv="Content-Security-Policy" content="default-src 'self'">

1. Comment autoriser des sources multiples?

vous pouvez simplement lister vos sources après une directive comme une liste séparée par des espaces:

content="default-src 'self' https://example.com/js/"

notez qu'il n'y a pas de guillemets autour des paramètres autres que Spéciaux ceux, comme 'self' . De plus, il n'y a pas de deux points ( : ) après la directive. Juste la directive, puis une liste de paramètres séparés par des espaces.

Tout ce qui est en dessous des paramètres spécifiés est implicitement autorisé. Cela signifie que dans l'exemple ci-dessus, ce sont des sources valables:

https://example.com/js/file.js
https://example.com/js/subdir/anotherfile.js

ceux-ci, cependant, ne seraient pas valides:

http://example.com/js/file.js
^^^^ wrong protocol

https://example.com/file.js
                   ^^ above the specified path

2. Comment utiliser des directives différentes, que font-elles chacune?

les directives les plus courantes sont:

  • default-src la politique par défaut pour le chargement des javascript, les images, les CSS, les polices, les requêtes AJAX, etc
  • script-src définit les sources valides pour les fichiers javascript
  • style-src définit les sources valides pour les fichiers css
  • img-src définit des sources valables pour des images
  • connect-src définit des cibles valides pour to XMLHttpRequest (AJAX), WebSockets ou EventSource. Si une tentative de connexion est faite à un hôte qui n'est pas autorisé ici, le navigateur émule une 400 erreur

il en existe d'autres, mais ce sont ceux que vous êtes le plus susceptible d'avoir besoin.

3. Comment utiliser plusieurs directives?

vous définissez toutes vos directives à l'intérieur d'une méta-étiquette en les terminant par un point-virgule ( ; ):

content="default-src 'self' https://example.com/js/; style-src 'self'"

4. Comment gérer les ports?

tout sauf les ports par défaut doit être autorisé explicitement en ajoutant le port numéro ou astérisque après le domaine autorisé:

content="default-src 'self' https://ajax.googleapis.com http://example.com:123/free/stuff/"

le résultat ci-dessus serait:

https://ajax.googleapis.com:123
                           ^^^^ Not ok, wrong port

https://ajax.googleapis.com - OK

http://example.com/free/stuff/file.js
                 ^^ Not ok, only the port 123 is allowed

http://example.com:123/free/stuff/file.js - OK

comme je l'ai mentionné, vous pouvez aussi utiliser un astérisque pour autoriser explicitement tous les ports:

content="default-src example.com:*"

5. Comment gérer différents protocoles?

par défaut, seuls les protocoles standards sont autorisés. Par exemple, pour autoriser WebSockets ws:// vous devrez autoriser explicitement:

content="default-src 'self'; connect-src ws:; style-src 'self'"
                                         ^^^ web sockets are now allowed on all domains and ports

6. Comment autoriser le protocole de fichier file:// ?

si vous essayez de le Définir comme tel, ça ne marchera pas. À la place, vous l'autoriserez avec le paramètre filesystem :

content="default-src filesystem"

7. Comment utiliser les scripts en ligne et les définitions de style?

sauf autorisation explicite, vous ne pouvez pas utiliser les définitions de style inline, code dans les étiquettes <script> ou dans les propriétés des étiquettes comme onclick . Vous les autorisez ainsi:

content="script-src 'unsafe-inline'; style-src 'unsafe-inline'"

vous devrez aussi autoriser explicitement inline, base64 encoded images:

content="img-src data:"

8. Comment autoriser eval() ?

je suis sûr que beaucoup de gens diraient que vous ne le faites pas, puisque "eval est mauvais" et la cause la plus probable pour la fin imminente du monde. Ces personnes seraient mauvais. Bien sûr, vous pouvez certainement percer des trous majeurs dans la sécurité de votre site avec eval, mais il a des cas d'utilisation parfaitement valide. Tu dois juste être intelligent pour l'utiliser. Vous l'autorisez ainsi:

content="script-src 'unsafe-eval'"

9. Que signifie exactement 'self' ?

vous pourriez prendre 'self' pour signifier localhost, local filesystem, ou n'importe quoi sur le même hôte. Cela ne signifie pas que l'un quelconque de ceux-ci. Il signifie des sources qui ont le même scheme (protocol), même hôte, et même port que le fichier dans lequel la Politique de contenu est définie. Servir votre site sur HTTP? Pas de https pour vous alors, sauf si vous le définissez explicitement.

j'ai utilisé 'self' dans la plupart des exemples car il est généralement logique de l'inclure, mais il est nullement obligatoire. Laissez-si vous n'en avez pas besoin.

mais attendez une minute! est-ce que je ne peux pas juste utiliser content="default-src *" et en finir avec ça?

Pas de. En plus des vulnérabilités de sécurité évidentes, cela laisserait aussi cela ne fonctionnera pas comme vous vous y attendiez. Même si certains docs prétendent qu'il permet quoi que ce soit, ce n'est pas vrai. Il ne permet pas de lining ou evals, donc pour vraiment, vraiment rendre votre site très vulnérable, vous utiliseriez ceci:

content="default-src * 'unsafe-inline' 'unsafe-eval'"

... mais j'espère que non.

autre lecture:

http://content-security-policy.com

http://en.wikipedia.org/wiki/Content_Security_Policy

386
répondu Schlaus 2018-06-01 15:27:01

APACHE2 MOD_HEADERS

vous pouvez aussi activer Apache2 mod_headers, sur Fedora il est déjà activé par défaut, si vous utilisez Ubuntu / Debian le permet comme ceci:

# First enable headers module for Apache2, 
# then restart the Apache2 service   
a2enmod headers
apache2 -k graceful

sur Ubuntu / Debian vous pouvez configurer les en-têtes dans le fichier /etc/apache2/conf-enabled/security.conf

#
# Setting this header will prevent MSIE from interpreting files as something
# else than declared by the content type in the HTTP headers.
# Requires mod_headers to be enabled.
# 
#Header set X-Content-Type-Options: "nosniff"

#
# Setting this header will prevent other sites from embedding pages from this
# site as frames. This defends against clickjacking attacks.
# Requires mod_headers to be enabled.
#
Header always set X-Frame-Options: "sameorigin"
Header always set X-Content-Type-Options nosniff
Header always set X-XSS-Protection "1; mode=block"
Header always set X-Permitted-Cross-Domain-Policies "master-only"
Header always set Cache-Control "no-cache, no-store, must-revalidate"
Header always set Pragma "no-cache"
Header always set Expires "-1"
Header always set Content-Security-Policy: "default-src 'none';"
Header always set Content-Security-Policy: "script-src 'self' www.google-analytics.com adserver.example.com www.example.com;"
Header always set Content-Security-Policy: "style-src 'self' www.example.com;"

Note: C'est la partie inférieure du fichier, seules les 3 dernières entrées sont des paramètres CSP.

le premier le paramètre est la directive, le 2nd sont les sources à énumérer en blanc. J'ai ajouté Google analytics et un serveur publicitaire, que vous pourriez avoir. En outre, j'ai constaté que si vous avez des pseudonymes, E. g, www.example.com et example.com configurés dans Apache2, vous devriez les ajouter à la liste blanche.

code Inline est considéré comme nocif, vous devez l'éviter. Copiez tous les javascripts et css dans des fichiers séparés et ajoutez-les à la liste blanche.

pendant que vous êtes vous pouvez y jeter un oeil aux autres paramètres d'en-tête et installer mod_security

autre lecture:

https://developers.google.com/web/fundamentals/security/csp /

https://www.w3.org/TR/CSP /

10
répondu Erik Hendriks 2017-02-25 17:20:53