Je tente de régler une bonne fois pour toute ces histoires de XSS (il serait temps
Dans les tutoriels, on voit souvent qu'il faut filtrer les entrées. Ok, mais c'est une méthode, qui est un peu pénible est contraignante.
Si un utilisateur veut s'appeller <script>alert('hello')</script>, c'est son problème et pas le mien.
Mon idée est de récupérer les données de l'utilisateur sans les filtrer. La sauvegarde dans la base de données se faisant avec des requêtes préparés pour éviter l'injection SQL, mais là n'est pas le débat.
Le problème va venir des affichages des pages HTML. Afin d'avoir quelque chose qui fonctionne dans tous les cas, je vois trois endroit où d'afficher le contenu d'une variable :
- dans une page HTML (dans le contenu d'une balise, dans la valeur d'un attribut)
- dans un paramètre d'URL pour affichage en HTML
- dans un paramètre d'URL pour une redirection via un header("Location: ...")
J'ai donc développé les trois fonctions suivantes :
<?php
//echo for HTML output
function hecho($texte){
echo htmlentities($texte,ENT_QUOTES,"UTF-8");
}
//echo for displaying URL
function uecho(array $param,$script = false){
if (! $script){
$script = $_SERVER['PHP_SELF'];
}
echo $script."?".http_build_query($param,'','&');
}
//redirecting
function redirect(array $param,$script){
header("Location: $script?".http_build_query($param));
exit;
}
Ainsi qu'un petit script pour tester tous ca :
<?php
$xss = "";
if (isset($_GET['xss'])){
$xss = $_GET['xss'];
}
if (isset($_GET['redirect'])){
unset($_GET['redirect']);
redirect($_GET,$_SERVER['PHP_SELF']);
}
$redirect_args = $_GET;
$redirect_args['redirect'] = true;
header("Content-type: text/html; charset=UTF-8");
?>
Contenu de xss : <?php hecho($xss); ?>
URL <a href='<?php uecho($_GET) ?>'>
<br/>
<?php uecho($_GET) ?></a>
<br/>
<img src='' alt='<?php hecho($xss); ?>' title='<?php hecho($xss); ?>'></img>
<br/>
<img src="" alt="<?php hecho($xss); ?>" title="<?php hecho($xss); ?>"></img>
<form>
<input name='xss' value='<?php hecho($xss)?>' />
<input type='submit'/>
</form>
<a href='<?php uecho($redirect_args) ?>'>redirect</a>
Si :- j'enlève complètement tous les opérateurs echo, print, printf de mon site
- je les remplace par une l'appel à une des trois fonctions
- je valide tous de même les adresse emails ainsi que les URL
Alors :
- je suis définitivement protégé contre les attaques XSS
- je n'ai pas oublié de cas tordus
Merci de vos réponses éclairées.