Page 1 sur 1

Panier, tableaux, etc....

Posté : 29 août 2019, 11:11
par gdepre
Bonjour à tous !

J'ai un projet de création de site de vente en ligne.
J'en suis au panier, qui, on peut le dire, me pose quelques soucis.

Tout se passe bien pour sa création, le premier produit est ajouté correctement, les infos sont bonnes.

Dans ce panier, j'ai besoin d'avoir un champ spécifique communiqué par le client, dans un form de la page précédente, avant ajout au panier, récupérée par un $_POST['champ_specifique'].

Voici le code de ce qui fonctionne et qui n'est exécuté que si il n'existe pas de panier (donc ajout du premier produit dans le panier)

Code : Tout sélectionner

$_SESSION['cart'] = array($product_id => array('qty' => $quantity, 'champ_specifique' => $_POST['champ_specifique']));
Lorsque je vais dans le panier, tout est ok. Je peux retirer le produit, vider le panier, ….

Ca se corse lorsque je veux ajouter un second produit, qui n'est pas le même que le premier, mais qui comportera aussi un champ spécifique.

Je précise que l'ajout du second produit est ok, les montants et les totaux sont ok, la seule chose, c'est que mon champ spécifique est le même (le dernier entré) pour tous les produits du panier.

Voici le code que j'ai intégré et qui lui est exécuté après qu'on ait vérifié qu'un panier existe déjà :

Code : Tout sélectionner

$_SESSION['cart'][$product_id] = array('qty' => $quantity, 'champ_specifique' => $_POST['champ_specifique']);
Je ne suis pas super à l'aise avec les array. J'ai fait un print_r sur une variable que je récupère et qui correspond à mon champ spécifique, il sont affichés correctement, tous.

Code : Tout sélectionner

foreach ($_SESSION['cart'] as $product){ print_r($champ_specifique = $product['champ_specifique']); }
Comment faire pour ajouter un nouveau produit au panier lorsqu'un panier existe déjà en prenant en compte le champ specifique de ce produit ?

Merci d'avance de vos réponses.

Gaëtan

Re: Panier, tableaux, etc....

Posté : 29 août 2019, 11:51
par Ryle
Hello !

Dans ton 2nd code tu n'a pas d'index "champ_specifique" mais un champ "domain" ce sont les mêmes ? c'est peut être normal de ne pas le retrouver là où tu l'attends s'ils n'ont pas le même nom :)

Mais commençons par le commencement : les tableaux en php, c'est simple à comprendre, ce sont des cases qui contiennent soit des valeurs, soit d'autres cases. Les indexes que tu définis correspondent aux noms de ces cases et te permettent (en les combinant au besoin) d'accéder à chacune des valeurs de ton tableau.
Comme rien ne vaut un dessin, voici ce que ton code "engendre" :
$_SESSION['cart'] = array($product_id => array('qty' => $quantity, 'champ_specifique' => $_POST['champ_specifique']));

| cart                                                  |
| <idProduitX>           | <idProduitY>           | ... |
| qty | champ_specifique | qty | domain           | ... |
| 1   | ta_valeur        | 66  | ta_valeur        | ... |
Tu peux ainsi accéder à la quantité du produit n°2 pour la lire ou la mettre à jour en parcourant ce tableau ainsi : $_SESSION['cart'][<idProduitY>]['qty']. Idem pour la valeur du champ spécifique du produit 1 : $_SESSION['cart'][<idProduitX>]['champ_specifique'].

Que le panier existe ou non, que l'article soit déjà dedans ou pas, tu peux ainsi gérer les différents cas de figure :
if (!isSet($_SESSION['cart'][$product_id]) // ajout d'un nouveau produit au panier
  $_SESSION['cart'][$product_id] = array('qty' => $quantity, 'champ_specifique' => $_POST['champ_specifique']));
else // mise à jour d'un produit existant dans le panier
  ...
Reste à s'assurer que champ_specifique est bien envoyé en post :) (et que $product_id et $quantity sont bien définis avant)

Re: Panier, tableaux, etc....

Posté : 29 août 2019, 12:36
par gdepre
Merci pour ta réponse rapide.

Oui pardon ce sont les mêmes. J'ai créé ce topic en anonyme avant d'activer mon compte, je ne peux pas éditer.

Il fallait donc lire :

Code : Tout sélectionner

//$_SESSION['cart'][$product_id] = array('qty' => $quantity, 'champ_specifique' => $_POST['champ_specifique']);
SI un modérateur peut corriger directement dans le premier post… :)

Je viens d'essayer ce code:

Code : Tout sélectionner

if (!isSet($_SESSION['cart'][$product_id]) // ajout d'un nouveau produit au panier $_SESSION['cart'][$product_id] = array('qty' => $quantity, 'champ_specifique' => $_POST['champ_specifique'])); else // mise à jour d'un produit existant dans le panier ...
Lors d'une vérification de l'existance d'un panier, j'ai ajouté un

Code : Tout sélectionner

foreach ($_SESSION['cart'] as $product){ print_r($champ = $product['champ_specifique']); }
Il m'affiche bien en haut de page mes deux entrées. Par contre, dans le panier, c'est toujours le dernier champ spécifique entré qui est affiché, sur tous les produits.

EDIT: c'est affiché de façon linéaire : champ_specifique1champspeicifique2champ_specifique3.

Re: Panier, tableaux, etc....

Posté : 29 août 2019, 14:20
par Ryle
Pour ne pas avoir l'affichage des éléments collés les uns aux autres, au lieu de la boucle pour contrôler le contenu de ton tableau, utilise le code suivant :
echo '<pre>';
print_r($_SESSION['cart']);
echo '</pre>';
ça sera plus facile à lire et à contrôler :)

Quant au fait que ce soit la même valeur qui soit stockée dans chacune des entrées de ton caddie, ce n'est pas normal. Tu dois avoir une boucle ou un autre appel aux enregistrements précédent qui vient les écraser avec ton $_POST...

Est-ce que tu ajoutes les éléments un par un dans ton panier ? ou est-ce plusieurs à la fois dans un seul formulaire envoyé en post ? Montre nous le code, ce sera sans doute plus facile de voir ce qui cloche :)

Re: Panier, tableaux, etc....

Posté : 29 août 2019, 14:36
par gdepre
Déjà merci pour cette astuce, ça me permet de voir l'ensemble de mon array et de constater qu'il n'y a pas d'erreur dedans, enfin, selon ce que j'ai compris.
Un exemple de deux produits ajoutés, avec dans le champ spécifique 'abc' pour le premier et 'def' pour le second.

Code : Tout sélectionner

Array ( [2] => Array ( [qty] => 1 [champ_specifique] => abc ) [3] => Array ( [qty] => 1 [champ_specifique] => def ) )
.

Mon array et le panier semblent ok, selon ce que j'ai demandé. Maintenant je viens de voir une chose, dans mon array, il devrait sans doute y avoir qq chose pour les différencier (ref du produit par exemple)… alors je m'y atèle ^^

EDIT : je fais les questions/réponses… :PCe que j'appelle ma ref produit, est-ce que c'est [2] ou [3] au début de chaque array ? Dans ce cas, je ne comprends pas pourquoi je ne parviens pas à afficher chaque champ_specifique pour chaque produit.

Re: Panier, tableaux, etc....

Posté : 29 août 2019, 15:41
par gdepre
Voilà, un peu de réflexion et de jugeotte, des gens pour vous mettre sur la bonne voie, et le tour est joué !

Dans ma boucle qui affiche le tableau de mise en page du panier, je fais un remplissage des variables du produit en fonctions de données MySQL récupérées dans un select, pour avoir des infos de chaque produit. Mon champ subsidiaire champ_specifique n'en faisant bien entendu pas partie !


J'ai donc, dans cette boucle, créé une variable de l'ID produit (MySQL)

Code : Tout sélectionner

$product_id = $product['id'];
(où $product['id'] est l'id récupéré via MySQL, tout le monde suit ?)
et ainsi, j'ai pu renseigner mon panier dans cette même boucle foreach en appelant

Code : Tout sélectionner

<?=$_SESSION['cart'][$product_id]['champ_specifique']?>
.

Un grand merci à toi Ryle pour le petit coup de main, ainsi qu'à ce forum qui m'a l'air bien vivant et actif, je saurai où trouver mes sources la prochaine fois !

Re: [RESOLU] Panier, tableaux, etc....

Posté : 30 août 2019, 11:32
par Ryle
Content que tu sois arrivé à résoudre ton problème :)

Deux p'tites remarques néanmoins :

- Evite les "short open tags", c'est à dire l'utilisation de " <? " et " <?= " et préfère leurs " <?php " et "<?php echo " respectivement. La directive permettant de gérer les tags d'ouverture courts est désactivée par défaut sur la majorité des serveurs et il y a potentiellement des risques de conflit avec d'autres langages comme le xml.

- J'ai un petit doute sur ta façon d'afficher le panier, du coup au cas où, une petite suggestion d'optimisation (et si c'est déjà le cas, n'y prête pas attention ;)).
Si j'ai bien compris, pour afficher le contenu de ton panier, tu commences par faire une requête SQL pour aller chercher les articles en base et tu boucles ensuite dessus pour voir s'il y en a un qui correspond à ceux du caddie ? Si cela fonctionne bien, ça n'est pas très performant. Tu vas en effet potentiellement charger des milliers d'enregistrements (en tout cas je te souhaite d'avoir plein d'articles à vendre ;)) alors que ton client n'en voudra qu'un ou deux.
Pour éviter cela, tu pourrais boucler sur le panier et faire une requête par article, mais là encore, pour peu que tu ais des clients acharnés, tu ne maîtriseras pas le nombre de requête envoyées au serveur.
Donc si ce n'est pas déjà le cas, je te recommande de limiter les enregistrements retournés par ta requête à ceux présents dans ton panier. La fonction array_keys() de php te permet de récupérer facilement les id_produit qui servent de clés dans ton tableau. Tu peux ainsi les utiliser facilement dans ta requête pour qu'elle ne retourne que les enregistrement qui te servent réellement :
$sql = " SELECT ... WHERE id_produit IN (" . implode(',', array_keys($_SESSION['cart'])) . ") ... ";