Créer un PDF Recommander Imprimer

Les injections SQL

(16 votes)
  • Document type
    Tutoriel PHP
  • Niveau
    Débutant
  • Version Joomla
    1.5.x
  • Dernière modification
    28.07.11
  • Créé par
    Adrien

pirateUne bonne partie des failles de sécurité des extensions Joomla concerne ce que l'on appelle une injection SQL.
Un utilisateur lambda va pouvoir, sans accès particulier, modifier la requête sql exécutée par le composant en introduisant dans le formulaire ou l'url soumise une chaîne de caractères, ceci afin de charger d'autres informations (le mot de passe de l'admin par exemple) ou d'exécuter une autre requête pour endommager votre site web.
Il est pourtant très simple de se protéger contre ces attaques en comprenant comment un hacker va pouvoir exploiter ce genre de failles.

 


Imaginons un composant chargeant et affichant une liste d'articles à partir d'une catégorie avec l'url:

1
 index.php?option=com_moncompo&view=categorie&catid=3

 

1
2
3
4
5
6
7
8
9
$category_id = $_GET['catid'];
$db =& JFactory::getDBO();
$db->setQuery('SELECT `title`,`introtext`,`fulltext` FROM `#__content` WHERE `catid` = '.$category_id);
$mesarticles = $db->loadObjectList();
 
foreach($mesarticles as $monarticle){
echo $monarticle->title;
echo $monarticle->introtext.$monarticle->fulltext;
}


L'identifiant de la catégorie n'est pas protégé et en changeant l'url, on peut provoquer une injection SQL.
L'accès à

1
index.php?option=com_moncompo&view=categorie&catid=3/**/UNION/**/SELECT/**/ id,username,password/**/FROM/**/ #__users

fera exécuter sans erreur la requête  

1
SELECT `title`,`introtext`,`fulltext` FROM `#__content` WHERE `catid` = 3 UNION SELECT id,username,password FROM #__users

et affichera finalement dans la page du composant l'identifiant, le nom d'utilisateur ainsi que le mot de passe (encrypté) de tous les utilisateurs en plus des articles de la catégorie.
Des outils sur internet permettent après de décrypter le mot de passe et ainsi d'obtenir un accès au back-end du site sans que vous ne vous rendiez compte que vous êtes attaqués.

Il est néanmoins très facile de se protéger contre ce genre d'attaque lors du développement en suivant deux règles simples:
1/ Toujours contrôler le type de variable provenant de l'extérieur
2/ Sécuriser les variables lors de l'exécution de requêtes



Au lieu d'exécuter

1
$category_id = $_GET['catid'];

utilisez les méthodes fournies par Joomla pour la récupération de variables.
La classe JRequest met à disposition un bon nombre de fonctions permettant cela et notamment

1
JRequest::getInt($nom_de_variable); 

qui s'assurera de vous retourner un entier.
Ceci est une première couche de protection qui aurait pu éviter le problème dans notre exemple.


La seconde - et indispensable - couche de protection est de sécuriser correctement chacune de vos requêtes.
Pensez à caster vos entiers avant l'insertion ou plus généralement, utilisez la fonction $db->Quote() de Joomla pour toute chaîne de caractères.

Notre code devient à présent:

1
2
3
4
5
6
7
8
9
$category_id = JRequest::getInt('catid');
$db =& JFactory::getDBO();
$db->setQuery('SELECT `title`,`introtext`,`fulltext` FROM `#__content` WHERE `catid` = '.(int)$category_id);
$mesarticles = $db->loadObjectList();
 
foreach($mesarticles as $monarticle){
echo $monarticle->title;
echo $monarticle->introtext.$monarticle->fulltext;
}

 

Dans cet exemple, la double couche de protection est visiblement inutile mais la plupart du temps vous récupérerez une variable à un endroit pour l'utiliser quelques fonctions plus tard... en prenant l'habitude de contrôler les données lors de la récupération et lors de l'exécution de la requête, vous supprimerez toute faille potentielle d'injection SQL.

 

Dans l'exemple nous utilisons (int) dans un simple but d'optimisation, mais le code

1
$db->setQuery('SELECT `title`,`introtext`,`fulltext` FROM `#__content` WHERE `catid` = '.$db->Quote( $category_id))

aurait très bien fait l'affaire.
C'est d'ailleurs la fonction à utiliser dans tous les autres cas (utilisation de chaînes de caractères) afin de protéger l'exécution de votre requête.

Attention néanmoins à l'utilisation de l'opérateur LIKE dans les requêtes SQL (notamment dans les recherches), pensez à utiliser directement la fonction getEscaped() en spécifiant le second argument à true, d'autre caractères (% et _) étant alors sensibles :

1
2
3
4
5
6
7
8
9
$category_id = JRequest::getInt('catid');
$recherche = JRequest::getString('recherche');
$db =& JFactory::getDBO();
$requete = 'SELECT `title`,`introtext`,`fulltext` FROM `#__content` WHERE `catid` = '.(int)$category_id;
if(!empty(
$recherche)) $requete .= " AND `title` LIKE '%".$db->getEscaped($recherche,true)."%' ";
$db
->setQuery(
$requete  );
$mesarticles = $db->loadObjectList();
 
foreach($mesarticles as $monarticle){
echo $monarticle->title;
echo $monarticle->introtext.$monarticle->fulltext;
}

 


En résumé:

  1. Vérifiez le type de vos variables lors de leur chargement
  2. Ne faites pas confiance à vos variables avant d'exécuter une requête et sécurisez votre requête comme s'il pouvait y avoir tout et n'importe quoi dans vos variables!

 

Cet article ne concerne que les injections SQL et ce ne sont pas les seules failles que l'on puisse créer lors du développement de composants Joomla... articles à suivre.

Commentaires  

 
#5 26-02-2012 02:50
Merci, de très bon conseils

A développer et et à améliorer pour 15,J&fam17,25

Le cryptage de la db bien que très hardu ne serait t'il pas une solution ? du moins pour les site à données sensible ? ce qui ce fait deja, mais une idée du style serait bien venu.
Citer
 
 
#4 02-01-2012 12:24
Bon article à lire
Citer
 
 
#3 22-08-2011 22:14
Très bon article, merci pour les différentes infos ! ;)
Citer
 
 
#2 08-05-2011 16:52
j ai besoin d'un guide pour comprendre comment developpé une interface sur joomla
Citer
 
 
#1 07-02-2011 15:46
Bonjour, pouriez vous m'envoier un email a mon adresse email pour que je puisse vous poser une question?
Merci,
Eric Gontier.
Citer
 

Ajouter un Commentaire


Code de sécurité
Rafraîchir

Recherche

Télécharger Joomla

telecharger joomla télécharger Joomla 1.5.26 télécharger Joomla 2.5.4 télécharger Joomla Platform 12.1

Connexion

Espace contributeurs