L'injection JavaScript est-elle pertinente?

Autrefois, lorsque le développement Web était basé sur le fait que les applications serveur envoyaient des requêtes aux bases de données relationnelles et émettaient une sortie HTML, ce code était souvent trouvé:

// :  ! function popup(msg: string): string { return "<p class=\"popup\">" + msg + "</p>"; } 

ou tel:

 // :  ! function getName(login: string): string { return "SELECT name FROM users WHERE login = \"" + login + "\""; } 

Depuis lors, nous avons appris à utiliser des approches plus sûres.

Les outils tels que les moteurs de modèles et la liaison de paramètres sont largement utilisés. Aujourd'hui, il est rare de trouver une concaténation de chaîne dangereuse.

Dans cet article, je voudrais partager mes réflexions sur les attaques en injectant du code. Apparemment, ils constituent toujours une menace en JavaScript.



Pour comprendre pourquoi, nous divisons l'un des exemples infructueux en fragments plus simples. Comme ça:

 function f(userInput: A): A { const firstCommand: A = ...; const secondCommand: A = ...; return firstCommand.concat(userInput.concat(secondCommand)); } 

De toute évidence, la cause première des attaques en introduisant le code est qu'il n'y a pas de différence entre une commande et une entrée utilisateur pour un ordinateur! Par conséquent, un attaquant peut entrer des données qui seront ensuite traitées sous forme de code.

Naturellement, comme je l'ai dit, il existe des défenses bien connues contre de telles attaques. Au lieu de cela:

 "SELECT name FROM users WHERE login = \"" + login + "\"" 

mieux écrire quelque chose comme ça:

 query("SELECT name FROM users WHERE login = :login", {login}) 

Ainsi, la commande SELECT name FROM users WHERE login =:login est clairement séparée des données {login} . Dans le même temps, les mécanismes internes garantissent que les données sont préparées pour être utilisées dans une requête SQL. Échapper aux citations et injecter du code malveillant échouera.

Cependant, le développement d'applications Web est en plein essor. Non seulement cela se retrouve de plus en plus:

 { paramA: "the value of the A parameter", paramB: "the value of the A parameter", } 

mais aussi ceci:

 { paramA: "the value of the A parameter", paramB: {$in: [ "the value of the B parameter", "the value of the C parameter", ]}, } 

Une différence significative entre les deux options est que la valeur du paramètre est un objet qui inclut une commande!

Disons que les valeurs sont lues à partir de userInput :

 { paramA: userInput.paramA, paramB: {$in: [ userInput.paramB[0], userInput.paramB[1], ]}, } 

Il n'est pas nécessaire de s'inquiéter que l'utilisateur fournisse une chaîne malveillante. Tout sera traité en toute sécurité.

Le problème est que les valeurs des paramètres peuvent être non seulement des valeurs simples comme the value of the A parameter , mais aussi des commandes, par exemple {$in: ["B", "C"]} . L'utilisateur peut envoyer une requête de différentes manières, après décryptage dont un objet est obtenu (formulaire, JSON ou XML), et donc le code peut être attaqué par injection.

Supposons que userInput.paramA est {$empty: false} . Ensuite, la requête est la suivante:

 { paramA: {$empty: false}, paramB: {$in: [ userInput.paramB[0], userInput.paramB[1], ]}, } 

Encore une fois, il s'avère que pour un ordinateur, les commandes fiables ne se distinguent pas des entrées utilisateur non fiables. Ce n'est que maintenant qu'il ne s'agit pas de chaînes fiables et non fiables, mais d'objets fiables et non fiables.

Pour éviter ce problème, vous devez toujours écrire des commandes afin qu'elles ne puissent pas être reçues de l'utilisateur. Cela peut être réalisé, entre autres, en utilisant l'approche utilisée dans React et Snabbdom-Signature (il s'agit d'une petite bibliothèque de protection contre l'injection dans le DOM virtuel), à savoir, le marquage de chaque objet de commande Symbol afin qu'il ne puisse pas être envoyé sur le réseau.

J'avoue, j'ai moi-même souvent pensé que puisqu'il n'y a pas de base de données SQL ou si j'utilise le DOM virtuel, les attaques par injection de code ne me menacent pas. Comme j'avais tort!


LOOKING.HOUSE - le projet a collecté plus de 150 points de miroir dans 40 pays. Vous pouvez exécuter rapidement les commandes host, ping, traceroute et mtr.


Source: https://habr.com/ru/post/fr422077/


All Articles