98 votes

Les services web JSON sont-ils vulnérables aux attaques CSRF ?

Je suis en train de créer un service Web qui utilise exclusivement JSON pour le contenu de ses requêtes et de ses réponses (c'est-à-dire qu'il n'y a pas de charges utiles codées par formulaire).

Un service web est-il vulnérable à une attaque CSRF si les conditions suivantes sont réunies ?

  1. Tout POST sans objet JSON de premier niveau, par exemple, {"foo":"bar"} sera rejeté avec un 400. Par exemple, un POST avec le contenu 42 serait ainsi rejetée.

  2. Tout POST avec un type de contenu autre que application/json sera rejeté avec un 400. Par exemple, un POST demande avec content-type application/x-www-form-urlencoded serait ainsi rejetée.

  3. Toutes les demandes GET seront Sécurité et ne modifie donc aucune donnée côté serveur.

  4. Les clients sont authentifiés via un cookie de session, que le service web leur donne après qu'ils aient fourni un couple nom d'utilisateur/mot de passe correct via un POST avec des données JSON, par ex. {"username":"user@example.com", "password":"my password"} .

Question annexe : Est-ce que PUT y DELETE ne sont-elles jamais vulnérables au CSRF ? Je pose la question parce qu'il semble que la plupart (tous ?) des navigateurs interdisent ces méthodes dans les formulaires HTML.

EDIT : Ajouté le point #4.

EDIT : Beaucoup de bons commentaires et de bonnes réponses jusqu'à présent, mais personne n'a proposé une attaque CSRF spécifique à laquelle ce service web est vulnérable.

85voto

Gumbo Points 279147

Forger des requêtes CSRF arbitraires avec des types de médias arbitraires n'est effectivement possible qu'avec XHR, parce qu'un fichier de type La méthode du formulaire est limitée à GET et POST. et un Le corps du message POST du formulaire est également limité aux trois formats suivants application/x-www-form-urlencoded , multipart/form-data y text/plain . Cependant, avec l'encodage des données du formulaire text/plain il est toujours possible de falsifier des requêtes contenant des données JSON valides. .

La seule menace vient donc des attaques CSRF basées sur XHR. Et celles-ci ne seront fructueuses que si elles proviennent de la même origine, c'est-à-dire de votre propre site d'une manière ou d'une autre (par exemple XSS). Veillez à ne pas confondre la désactivation de CORS (c'est-à-dire le fait de ne pas définir Access-Control-Allow-Origin : *) avec une protection. CORS empêche simplement les clients de lire la réponse. L'ensemble de la demande est toujours envoyé et traité par le serveur.

3voto

Timothy Leung Points 619

Oui, c'est possible. Vous pouvez mettre en place un serveur attaquant qui renverra une redirection 307 vers le serveur cible sur la machine de la victime. Vous devez utiliser Flash pour envoyer le POST au lieu d'utiliser le formulaire.

Référence : https://bugzilla.mozilla.org/show_bug.cgi?id=1436241

Il fonctionne également sur Chrome.

0voto

Filip Waeytens Points 21

Il est possible de faire du CSRF sur des services Restful basés sur JSON en utilisant Ajax. J'ai testé cela sur une application (en utilisant à la fois Chrome et Firefox). Vous devez changer le contentType en text/plain et le dataType en JSON afin d'éviter une requête preflight. Ensuite, vous pouvez envoyer la demande, mais pour envoyer des données de session, vous devez activer le drapeau withCredentials dans votre demande ajax. J'en parle plus en détail ici (les références sont incluses) :

http://wsecblog.blogspot.be/2016/03/csrf-with-json-post-via-ajax.html

-1voto

Cheekysoft Points 16532

Toutes vos validations actuelles sont parfaitement sensées et limitent votre surface d'attaque, mais elles ne traitent pas réellement de ce qu'est la vulnérabilité CSRF.

On parle de "vulnérabilité CSRF" lorsque vous laissez votre application accepter et traiter une requête HTTP, sans confirmer au préalable que cette requête fait partie d'une conversation déjà en cours avec votre site. Toutes les requêtes HTTP (indépendamment de leur contenu) peuvent provenir d'une autre source que votre propre page Web.

N'importe qui peut créer une requête directe vers votre site contenant {"foo" : "bar"} et indiquant le mimetype application/json.

Vous devez expliquer comment vous prévoyez de vérifier que les demandes ne proviennent pas directement d'un client personnalisé, d'une session telnet ou en réponse à un contenu servi par le site de quelqu'un d'autre - ce n'est qu'alors que nous saurons si vous êtes vulnérable ou non. Si vous n'avez pas mis en place cette vérification, vous ÊTES vulnérable à TOUTES les requêtes HTTP.

Mise à jour

OK, toutes les demandes sont protégées par un login, donc nous ne devons pas trop nous inquiéter des demandes directes des clients personnalisés, à moins que les informations de login ne soient divulguées. Le principal vecteur d'attaque dont il faut se préoccuper ici est la duplication d'un utilisateur déjà connecté pour qu'il exécute une demande de changement d'état.

Vous devrez certainement protéger vos requêtes POST. À mon avis, vous pouvez tout aussi bien garder votre API cohérente et mettre la même protection sur PUT et DELETE - tout fonctionne de la même manière. Fournissez une bibliothèque client à tous les développeurs de clients afin de leur faciliter (ou, espérons-le, de les rendre transparents) la réalisation d'appels simples qui transmettront automatiquement toutes les informations requises à votre serveur.

Oui, les navigateurs ne sont pas conçus pour permettre le PUT ou le DELETE à partir de formulaires, et il se peut que vous ne connaissiez pas de moyen intersite pour le faire à l'heure actuelle, mais cela ne veut pas dire qu'il n'y a pas de moyen du tout. La semaine prochaine, le mois prochain ou l'année prochaine, quelqu'un pourrait trouver un exploit ou un bogue permettant de le faire. Le plus grand risque d'exploitation de PUT et DELETE provient d'attaques XSS, donc assurez-vous que vous ne souffrez d'aucune vulnérabilité XSS. Étant donné qu'une attaque XSS peut lire n'importe quel jeton CSRF, une vulnérabilité XSS permet également de contourner complètement les attaques de type tout La protection CSRF que vous avez mise en place, donc soyez particulièrement prudent à ce sujet.

Cependant, vous parlez également de "milliers de développeurs" qui "construisent des clients personnalisés". Si ces clients personnalisés ne sont pas implémentés en Javascript côté client, alors vous devez élargir votre compréhension aux restrictions que chacun de ces clients personnalisés impose à l'utilisateur et à l'environnement. Il peut être tout à fait facile de faire une demande PUT intersite dans le client personnalisé X.

-1voto

panteo Points 121

J'ai quelques doutes concernant le point 3. Bien que l'on puisse considérer qu'il s'agit d'une solution sûre puisqu'elle ne modifie pas les données du côté du serveur, les données peuvent toujours être lues, et le risque est qu'elles puissent être volées.

http://haacked.com/archive/2008/11/20/anatomy-of-a-subtle-json-vulnerability.aspx/

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X