web-dev-qa-db-fra.com

Qu'est-ce que cela signifie d'échapper à une chaîne?

Je lisais Est-ce que $ _SESSION ['nom d'utilisateur'] doit être échappé avant d'entrer dans une requête SQL? et il était écrit "Vous devez échapper chaque chaîne que vous transmettez à la requête SQL, quelle que soit son origine. ". Maintenant, je sais que quelque chose comme ceci est vraiment basique. Une recherche sur Google a donné plus de 20 000 résultats. Stackoverflow à lui seul contenait 20 pages de résultats, mais personne n’explique réellement ce qu’est le caractère qui échappe une chaîne et comment le faire. C'est juste supposé. Pouvez-vous m'aider? Je veux apprendre parce que, comme toujours, je crée une application Web en PHP.

J'ai examiné: Insertion de caractères d'échappement , Quels sont tous les caractères d'échappement Java? , Impossible d'échapper à une chaîne avec addcslashes () , - Caractère d'échappement , que fait vraiment mysql_real_escape_string ()? , comment puis-je échapper à des guillemets doubles dans une chaîne de caractères? , MySQL_real_escape_string ne pas ajouter de barres obliques? , supprimer les séquences d'échappement de la chaîne en php Je pourrais continuer, mais je suis sûr que vous obtenez le point. Ce n'est pas de la paresse.

70
Brett

Échapper à une chaîne signifie réduire l'ambiguïté des guillemets (et autres caractères) utilisés dans cette chaîne. Par exemple, lorsque vous définissez une chaîne, vous l'entourez généralement de guillemets ou de guillemets simples:

"Hello World."

Mais que se passe-t-il si ma chaîne contient des guillemets?

"Hello "World.""

Maintenant, j'ai une ambiguïté: l'interprète ne sait pas où se termine ma chaîne. Si je veux garder mes guillemets, j'ai deux options. Je pourrais utiliser des guillemets simples autour de ma chaîne:

'Hello "World."'

Ou je peux échapper à mes citations:

"Hello \"World.\""

Toute citation précédée d'une barre oblique est échappée et est comprise comme faisant partie de la valeur de la chaîne.

En ce qui concerne les requêtes, MySQL surveille certains mots clés que nous ne pouvons pas utiliser dans nos requêtes sans créer de la confusion. Supposons que nous ayons une table de valeurs où une colonne s'appelle "Select" et que nous voulions sélectionner:

SELECT select FROM myTable

Nous avons maintenant introduit une certaine ambiguïté dans notre requête. Dans notre requête, nous pouvons réduire cette ambiguïté en utilisant des back-ticks:

SELECT `select` FROM myTable

Cela élimine la confusion que nous avons introduite en faisant preuve d'un manque de discernement dans la sélection des noms de champs.

Une grande partie de ceci peut être gérée pour vous simplement en passant vos valeurs par mysql_real_escape_string() . Dans l'exemple ci-dessous, vous pouvez voir que nous transmettons les données soumises par l'utilisateur à travers cette fonction pour nous assurer que cela ne posera aucun problème pour notre requête:

// Query
$query = sprintf("SELECT * FROM users WHERE user='%s' AND password='%s'",
            mysql_real_escape_string($user),
            mysql_real_escape_string($password));

Il existe d’autres méthodes pour échapper des chaînes, telles que add_slashes, addcslashes, quotemeta, etc. et les grands développeurs préfèrent mysql_real_escape_string ou pg_escape_string (dans le contexte de PostgreSQL.

119
Sampson

Certains caractères ont une signification particulière pour la base de données SQL que vous utilisez. Lorsque ces caractères sont utilisés dans une requête, ils peuvent provoquer un comportement inattendu et/ou involontaire, notamment en permettant à un attaquant de compromettre votre base de données. Pour éviter que ces caractères n'affectent une requête de cette manière, vous devez les échapper, ou pour le dire autrement, vous devez indiquer à la base de données de ne pas les traiter comme des caractères spéciaux dans cette requête.

Dans le cas de mysql_real_escape_string(), il échappe à \x00, \n, \r, \, ', " et \x1a car ces derniers, lorsqu'ils ne sont pas protégés, peuvent entraîner les problèmes susmentionnés, qui incluent des injections SQL avec une base de données MySQL.

19
John Conde