IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

PHP & Base de données Discussion :

bloquer les injections sur un array numéraire [MySQL]


Sujet :

PHP & Base de données

  1. #1
    Membre régulier
    Inscrit en
    Septembre 2004
    Messages
    387
    Détails du profil
    Informations forums :
    Inscription : Septembre 2004
    Messages : 387
    Points : 109
    Points
    109
    Par défaut bloquer les injections sur un array numéraire
    Bonjour à tous,

    Voilà je suis en train de modifier un script
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    ($id_category ? ' AND c.`id_category` = '.(int)$id_category : '').
    en
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    ($id_category ? (is_array($id_category) ? ' AND c.`id_category` IN ('.join(',', $id_category).')':' AND c.`id_category` = '.(int)$id_category) : '').
    Afin que faire un requete à partir d'un array(15,20,25)
    Mais je souhaiterais de prémunir contre tout attaque sql, mais je me demande quel test pourais je faire?

  2. #2
    Membre régulier
    Inscrit en
    Septembre 2004
    Messages
    387
    Détails du profil
    Informations forums :
    Inscription : Septembre 2004
    Messages : 387
    Points : 109
    Points
    109
    Par défaut
    J'ai pensé à celà.

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    if (is_array($id_category)){
    	foreach ($id_category as $element)
    	$t[] = (int)$element;
    	$id_category = $t;
    }
    [...]
    ($id_category ? (is_array($id_category) ? ' AND c.`id_category` IN ('.join(',', $id_category).')':' AND c.`id_category` = '.(int)$id_category) : '').
    Y a t il mieux?

  3. #3
    Expert éminent sénior
    Avatar de rawsrc
    Homme Profil pro
    Dev indep
    Inscrit en
    Mars 2004
    Messages
    6 142
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 47
    Localisation : France, Bouches du Rhône (Provence Alpes Côte d'Azur)

    Informations professionnelles :
    Activité : Dev indep

    Informations forums :
    Inscription : Mars 2004
    Messages : 6 142
    Points : 16 545
    Points
    16 545
    Billets dans le blog
    12
    Par défaut
    Salut,

    comme ça :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    if ( ! empty($id_category))
    {
        $ids  = array_filter(array_map('intval', (array)$id_category));
        if ( ! empty($ids))
        {
            $sql .= (count($ids) === 1)
                        ? ' AND c.`id_category` = '.current($ids)
                        : ' AND c.`id_category` IN ('.implode(', ', $ids).')';
        }
    }

  4. #4
    Membre régulier
    Inscrit en
    Septembre 2004
    Messages
    387
    Détails du profil
    Informations forums :
    Inscription : Septembre 2004
    Messages : 387
    Points : 109
    Points
    109
    Par défaut
    Merci beaucop pour ta réponse
    Cela m'as permis de découvrir
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    array_filter(array_map('intval', (array)
    En revanche je crois qu'il y avais une erreur:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
     
    $sql .= (count($ids) === 1)
                        ? ' AND c.`id_category` = '.current($ids)
                        : ' AND c.`id_category` IN ('.implode(', ', $ids).')';

    Du coup je l'ai modifié pour l'addapté à mon code:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    if ( ! empty($id_category)) $ids  = array_filter(array_map('intval', (array)$id_category));
    		$sql = 'SELECT p.*, product_shop.*, pl.* , m.`name` AS manufacturer_name, s.`name` AS supplier_name
    				FROM `'._DB_PREFIX_.'product` p
    				'.Shop::addSqlAssociation('product', 'p').'
    				LEFT JOIN `'._DB_PREFIX_.'product_lang` pl ON (p.`id_product` = pl.`id_product` '.Shop::addSqlRestrictionOnLang('pl').')
    				LEFT JOIN `'._DB_PREFIX_.'manufacturer` m ON (m.`id_manufacturer` = p.`id_manufacturer`)
    				LEFT JOIN `'._DB_PREFIX_.'supplier` s ON (s.`id_supplier` = p.`id_supplier`) 
    				LEFT JOIN `'._DB_PREFIX_.'category_product` c ON (c.`id_product` = p.`id_product`)
    				WHERE pl.`id_lang` = '.(int)$id_lang.
    					(( ! empty($ids))?((count($ids) === 1)? ' AND c.`id_category` = '.current($ids): ' AND c.`id_category` IN ('.implode(', ', $ids).')'):'').
    					($front ? ' AND product_shop.`visibility` IN ("both", "catalog")' : '').
    					($only_active ? ' AND product_shop.`active` = 1' : '').'
    				ORDER BY '.(isset($order_by_prefix) ? pSQL($order_by_prefix).'.' : '').($order_by!="rand"?'`'.pSQL($order_by).'` '.pSQL($order_way):"rand()").
    				($limit > 0 ? ' LIMIT '.(int)$start.','.(int)$limit : '');

    Dernière petit question sachant qu 99% du temps $id_category est (int) et non un array, penser vous que cela risque de ralentir les 99% des requetes?

  5. #5
    Expert éminent sénior
    Avatar de rawsrc
    Homme Profil pro
    Dev indep
    Inscrit en
    Mars 2004
    Messages
    6 142
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 47
    Localisation : France, Bouches du Rhône (Provence Alpes Côte d'Azur)

    Informations professionnelles :
    Activité : Dev indep

    Informations forums :
    Inscription : Mars 2004
    Messages : 6 142
    Points : 16 545
    Points
    16 545
    Billets dans le blog
    12
    Par défaut
    Le ralentissement c'est de l'ordre de quelques microsecondes, donc à moins d'avoir des dizaines de milliers de requêtes simultanées, tu ne devrais pas voir la différence.

    Un conseil, tu dois toujours privilégier la lisibilité du code, toujours ! Pour y parvenir il faut absolument éviter l'imbrication de plusieurs opérateurs ternaire.
    Pareil avec les longues chaînes : il est possible d'éviter les concaténations en pagailles, le bordel des guillemets : regarde du côté des notations heredoc et nowdoc.

    Un code bien écrit te facilite tellement la vie par la suite..., fais l'effort maintenant et après tu n'y penseras plus.
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    $sql_where = 'pl.`id_lang` = '.(int)$id_lang;
     
    if ( ! empty($id_category))
    {
        $ids  = array_filter(array_map('intval', (array)$id_category));
        if ( ! empty($ids))
            $sql_where .= (count($ids) === 1)
                              ? ' AND c.`id_category` = '.current($ids)
                              : ' AND c.`id_category` IN ('.implode(', ', $ids).')';
    }
     
    if ($front)
        $sql_where .= ' AND product_shop.`visibility` IN ("both", "catalog")';
     
    if ($only_active)
        $sql_where .= ' AND product_shop.`active` = 1';
     
     
    $prefix       = (isset($order_by_prefix)) ? pSQL($order_by_prefix).'.' : '';
    $sql_order_by = $prefix.(($order_by === 'rand') ? 'rand()' : '`'.pSQL($order_by).'` '.pSQL($order_way));
    $sql_limit    = ($limit) ? ' LIMIT '.(int)$start.','.(int)$limit : '';
     
    $dbp          = _DB_PREFIX_;
    $sql_assoc    = Shop::addSqlAssociation('product', 'p');
    $sql_lang     = Shop::addSqlRestrictionOnLang('pl');
     
    $sql = <<<sql
    SELECT
        p.*,
        product_shop.*,
        pl.*,
        m.`name` AS manufacturer_name,
        s.`name` AS supplier_name
    FROM
        `{$dbp}product` p
            {$sql_assoc}
            LEFT JOIN `{$dbp}product_lang` pl    ON (p.`id_product`      = pl.`id_product` {$sql_lang})
            LEFT JOIN `{$dbp}manufacturer` m     ON (m.`id_manufacturer` = p.`id_manufacturer`)
            LEFT JOIN `{$dbp}supplier` s         ON (s.`id_supplier`     = p.`id_supplier`)
            LEFT JOIN `{$dbp}category_product` c ON (c.`id_product`      = p.`id_product`)
    WHERE
        {$sql_where}
    ORDER BY
        {$sql_order_by}
    {$sql_limit}
    sql;
    Dans 100% des cas, les problèmes de performances ne sont pas liés à la mise en page du code...
    Et puis depuis quelques temps maintenant, avec les système de cache, le code PHP n'est parsé qu'une seule et unique fois donc une super mise en page n'est pas du tout pénalisante bien au contraire.

  6. #6
    Membre habitué
    Homme Profil pro
    Directeur technique
    Inscrit en
    Février 2011
    Messages
    146
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Hauts de Seine (Île de France)

    Informations professionnelles :
    Activité : Directeur technique
    Secteur : Transports

    Informations forums :
    Inscription : Février 2011
    Messages : 146
    Points : 172
    Points
    172
    Par défaut
    le delais va être au niveau du select et nul part ailleurs :p

  7. #7
    Membre régulier
    Inscrit en
    Septembre 2004
    Messages
    387
    Détails du profil
    Informations forums :
    Inscription : Septembre 2004
    Messages : 387
    Points : 109
    Points
    109
    Par défaut
    Citation Envoyé par rawsrc Voir le message
    Le ralentissement c'est de l'ordre de quelques microsecondes, donc à moins d'avoir des dizaines de milliers de requêtes simultanées, tu ne devrais pas voir la différence.

    Un conseil, tu dois toujours privilégier la lisibilité du code, toujours ! Pour y parvenir il faut absolument éviter l'imbrication de plusieurs opérateurs ternaire.
    Pareil avec les longues chaînes : il est possible d'éviter les concaténations en pagailles, le bordel des guillemets : regarde du côté des notations heredoc et nowdoc.

    Un code bien écrit te facilite tellement la vie par la suite..., fais l'effort maintenant et après tu n'y penseras plus.

    Un grand merci.
    Cependant c'est le code presta de base. J'apporte juste un amélioration personnelle, mais je récris pas tout.
    Bien que je sois entièrement d'accord.
    Un grand merci pour la démonstration!

+ Répondre à la discussion
Cette discussion est résolue.

Discussions similaires

  1. [XL-2010] Bloquer les onglets sur excel en vba
    Par Marc31 dans le forum Macros et VBA Excel
    Réponses: 14
    Dernier message: 29/06/2015, 20h25
  2. Bloquer les menus sur la face avant
    Par Kardej dans le forum LabVIEW
    Réponses: 3
    Dernier message: 30/08/2012, 19h03
  3. Bloquer les liens sur une page
    Par dré kam dans le forum Général JavaScript
    Réponses: 3
    Dernier message: 23/01/2012, 12h08
  4. Comment bloquer les photos sur mon site
    Par footeuse13 dans le forum Sécurité
    Réponses: 5
    Dernier message: 08/08/2007, 16h54
  5. Bloquer les clics sur une fenêtre
    Par Enzololo dans le forum Général JavaScript
    Réponses: 7
    Dernier message: 22/05/2006, 22h12

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo