Sécuriser les entrées utilisateurs avec du raw sql ?

un peu comme avec PDO et php

Le problème exposé dans ce sujet a été résolu.

Après mon précédent post sur ajax ou @artragis me disait à juste titre que mon code, en l'état, était vulnérable aux injections de sql :x

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
        [HttpPost]
        public ActionResult CheckReturn(TitreWrapper titreWrap)
        {
            string titre = titreWrap.titre;

            var contexte = new intranetEntities();
            var ajax = contexte.evenementiel.SqlQuery("SELECT * FROM evenementiel WHERE titrebri_evenementiel LIKE '%"+ titre +"%' ORDER BY datecreation_evenementiel DESC;");

            ViewBag.ajax = ajax;

            return PartialView();
        }

effectivement, il l'est, donc j'ai cherché et découvert les "Parameterized Queries" c'est à dire les requêtes paramètrées. Et pour l'implémentation, ça coince J'ai commencé par faire ça :

1
2
3
4
5
6
7
string titre = titreWrap.titre;

            SqlParameter[] param = new SqlParameter[1];
            param[0] = new SqlParameter("@titre", titre);

            var contexte = new intranetEntities();
            var ajax = contexte.evenementiel.SqlQuery("SELECT * FROM evenementiel WHERE titrebri_evenementiel LIKE '%@titre%' ORDER BY datecreation_evenementiel DESC;");

mais ça marchait pas, le "@titre" n'est pas reconnu comme une variable, alors j'ai aussi essayé ça :

1
2
3
4
5
6
7
string titre = titreWrap.titre;

            SqlParameter[] param = new SqlParameter[1];
            param[0] = new SqlParameter("@titre", titre);

            var contexte = new intranetEntities();
            var ajax = contexte.evenementiel.SqlQuery("SELECT * FROM evenementiel WHERE titrebri_evenementiel LIKE '%" + param[0] +"%' ORDER BY datecreation_evenementiel DESC;");

(ç'aurait été idiot si ça avait marché mais bon.....)

enfin, je sais qu'il existe des façons de faire avec LINQ, ou d'autres trucs mais ça me forcerait à réécrire tout ou partie de mon code (ce que je veux éviter)

Quelqu'un sait ce que je dois faire ?

EDIT : J'ai trouvé le LINQ, réussi à faire ça :

1
var ajax = contexte.evenementiel.Where(x => x.titrebri_evenementiel.Contains(titre)).OrderByDescending(x => x.datecreation_evenementiel);

qui… marche ? les injections semblent ne pas passer mais les résultats de cette requête ne sont pas les mêmes qu'avec SQL, du coup j'aime pas trop :/

+0 -0

qui… marche ? les injections semblent ne pas passer mais les résultats de cette requête ne sont pas les mêmes qu'avec SQL, du coup j'aime pas trop :/

Quels étaient les résultats précédents qui ne sont plus présents maintenant? Linq est une méthode standard et plutôt efficace pour faire des requêtes SQL, donc j'ai tendance à t'encourager à le faire.

contexte.evenementiel.SqlQuery("SELECT * FROM evenementiel WHERE titrebri_evenementiel LIKE '%@titre%' ORDER BY datecreation_evenementiel DESC;");

Si tu veux faire un paramètre, il ne faut pas qu'il soit précédé par autre chause que @.

Du coup si tu veux mettre des wildcards dans ton LIKE, il faut que tu fasses `contexte.evenementiel.SqlQuery("SELECT * FROM evenementiel WHERE titrebri_evenementiel LIKE '@titre' ORDER BY datecreation_evenementiel DESC;"); puis que tu passes comme valeur à ta requête "%" + param[0] + "%".

PPS : avec Linq la méthode la plus sûre est :

1
2
3
4
IEnumerable<evenementiel> events = from event in contexte.evenementiel
                                   where SqlMethods.Like(event.titrebri_evenementiel, "%" + titre + "%")
                                   select event
                                   order by event.date_evenementiel;
+1 -0

Quels étaient les résultats précédents qui ne sont plus présents maintenant?

les résultats étaient ceux de la requête, et la méthode Linq et SQL ne retournaient pas les mêmes choses EXACTEMENT

Du coup, je vais faire comme tu dis :) je pense aussi que linq (bien que **) est la meilleure solution (comme ça j'apprend un nouveau truc)

Il y a pas de tutos pour linq sur zds ?

Il y a pas de tutos pour linq sur zds ?

il y a un tuto sur l'entity framework qui se base sur link au sein du tuto asp.net.

Sinon pour ce qui est des résultats, tu cherchais quel mot exact pour avoir ces résultat? En effet, j'ai l'impression que tu cherchais "test" dans le cas "sql brut" et totalement autre chose dans le cas "linq".

merci :)

non, je cherche test dans les deux cas, je change seulement cette ligne :

1
var ajax = contexte.evenementiel.SqlQuery("SELECT * FROM evenementiel WHERE titrebri_evenementiel LIKE '%"+titre+"%' ORDER BY datecreation_evenementiel DESC;");

par celle-là :

1
var ajax = contexte.evenementiel.Where(x => x.titrebri_evenementiel.Contains(titre)).OrderByDescending(x => x.datecreation_evenementiel);

Je sais pas si tu es encore là, mais j'essaie encore un peu les requêtes parametrées et je sais pas pour quoi ça ne marche pas ici ?

1
var ajax = contexte.evenementiel.SqlQuery("SELECT * FROM evenementiel WHERE titrebri_evenementiel LIKE @titre_param ORDER BY datecreation_evenementiel DESC;", new SqlParameter("@titre_param", ("'%" + titre + "%'")));

en mettant un point d'arrêt, il me semble que le "@titre" n'est pas reconnu comme une variable.

j'ai mis une valeur fixe pour essayer, et c'est pas mieux

1
var ajax = contexte.evenementiel.SqlQuery("SELECT * FROM evenementiel WHERE titrebri_evenementiel LIKE @titre_param" + " ORDER BY datecreation_evenementiel DESC;", new SqlParameter("@titre_param", "'%ouverture%'"));

PS : cette ligne seule s'occupe de tout, il n'y a pas de déclaration de paramètres ailleurs

Bon y'a un gros problème déjà tu mixe l'utilisation de ADO.NET/Entity Framework avec l'utilisation de sql brut. Ce genre de requêtes c'est uniquement si tu veux faire des optimisations bien complexes, pas pour jouer avec des select simples.

Ensuite, les quotes autour de ton "%ouverture%" sont de trop.

bravo, c'était effectivement les quotes qui étaient de trop ._.

sinon oui, j'imagine que je mélange plein de choses, mais cette façon de faire est à mes yeux la plus "évidente" : je comprend tout ce que je fais.

Qu'est ce que je mélange exactement ? plusieurs façons de faire les appels ?

Connectez-vous pour pouvoir poster un message.
Connexion

Pas encore membre ?

Créez un compte en une minute pour profiter pleinement de toutes les fonctionnalités de Zeste de Savoir. Ici, tout est gratuit et sans publicité.
Créer un compte