Jump to content

Comment obtenir les ID des produits de plusieurs catégories et les intégrer dans un tableau PHP ?


Recommended Posts

Bonjour,

Je travaille sur un module de paiement perso. qui ne doit s'afficher dans le tunnel d'achat qu'à certaines conditions, pour créer ce module je me suis basé sur le module de paiement par chèque.

Les conditions d'affichage du nouveau module dans le tunnel d'achat :

  1. Les produits du panier doivent faire partie de certaines catégories de produits spécifiques.
  2. Le prix HT de chaque produit du panier doit être supérieur à un certain montant.

 

Mon problème est le suivant :

Pour gérer la première condition (vérifier que les produits du paniers font partie de certaines catégories) j'ai modifié la fonction hookPayment de mon module comme ceci :

public function hookPayment($params)
	{
		// Tableau $allowed_products avec les ID des produits éligibles à cette méthode de paiement
		$allowed_products= array(6244,8871,5,10,12);
		
		// Je récupère les produits du panier
		$products = Context::getContext()->cart->getProducts();
		
		// je compare les produits du panier à ceux du tableau $allowed_products
		$allowed=false;
		foreach ($products as $product)
		{
			// Si il y a correspondance $allowed = true
		    if (in_array($product['id_product'], $allowed_products)){
					$allowed=true;
				}
		}
		
		if (!$allowed)
		    return;

		if (!$this->active)
			return;
		if (!$this->checkCurrency($params['cart']))
			return;

		$this->smarty->assign(array(
			'this_path' => $this->_path,
			'this_path_bw' => $this->_path,
			'this_path_ssl' => Tools::getShopDomainSsl(true, true).__PS_BASE_URI__.'modules/'.$this->name.'/'
		));
		return $this->display(__FILE__, 'payment.tpl');
	}

 

Cette méthode fonctionne mais j'ai beaucoup de produits éligibles pour cette méthode de paiement et pour éviter de taper à la main tous les ID produit dans le tableau $allowed_products, je souhaite savoir comment récupérer les ID des produits de certaines catégories et les intégrer dans le tableau $allowed_products, .

Jusqu'à présent je n'ai pas trouvé de solution je dois passer à côté de quelque chose ! -_-'

Quelqu'un peut m'aider ou me donner une piste ? Merci d'avance.

 

INFO : Version de PrestaShop 1.6.0.14.

 

Edited by Alain D. (see edit history)
Link to comment
Share on other sites

Bonjour,

pourquoi ne pas tester seulement la liste des catégories des produits avec Products::idIsOnCategoryId($id_product, $categories)

vous pouvez faire une fonction séparée qui fera un return true au premier produit dans une des catégories autorisée et éviter de scanner tout le panier inutilement.

Link to comment
Share on other sites

Bonjour Mediacome87,

Tout d'abord, merci pour votre réponse.

Je ne suis pas certain de comprendre la méthode que vous me suggérez. Pourriez-vous m'éclairer d'avantage ?
J'interprète votre réponse de la façon suivante :

Quote

pourquoi ne pas tester seulement la liste des catégories des produits avec Products::idIsOnCategoryId($id_product, $categories)

Cette approche me semble intéressante mais je ne suis pas sûr de comprendre le fonctionnement de : Products::idIsOnCategoryId($id_product, $categories).

Après recherches :

     

Les variables de cette méthode sraient dans mon cas :

  • $id_product = int (ID de chaque produit du panier à vérifier ?)
  • $categories = array()  (des ID des catégories éligibles ?).

Donc si je comprends bien, je crée un array() avec les ID des catégories de produits éligibles ($categories) puis je boucle la vérification des produits du panier avec votre méthode ? Une autre question me vient à l'esprit : $categories doivent être les catégories parents direct des produits ou est-ce qu'il peut y avoir plusieurs niveau de catégories ?

       
       
       
       
       
Quote

vous pouvez faire une fonction séparée qui fera un return true au premier produit dans une des catégories autorisée et éviter de scanner tout le panier inutilement.

J'utilise " Products::idIsOnCategoryId($id_product, $categories) " pour tester la catégorie de chaque produit du panier (par exemple dans une boucle) et lorsque je tombe sur un produit enfant d'une catégorie éligible je stop la boucle de vérification et j'affiche ma méthode de paiement ?

 

 

Link to comment
Share on other sites

Vous avez tout compris.

Pour les catégories vous devez préciser l'id de chaque catégorie autorisées. Après la fonction contrôl si l'id produit est associé à une des catégorie. Donc on se fiche des parents, enfants, il faut préciser clairement chaque catégorie.

Pour la fonction qui test le truc c'est assez simple.
 

if (Products::idIsOnCategoryId($id_product, $categories)) {
	//On affiche le module de paiement
}

 

Link to comment
Share on other sites

Merci pour cette précision !

Je reste dubitatif quand à l'appartenance des produits aux catégories.

Exemple de hiérarchie actuel de ma boutique :

  1. Bonbons
    1. Menthe
      1. produit-1
      2. produit-2
    2. Fraise
      1. produit-3
      2. produit-4

Si je teste l'id du produi-1 avec votre méthode, est-ce que la catégorie associée sera Menthe ou Bonbons ou les deux ?

 

Si j'ai bien compris ma vérification doit donc ressembler à ça ? :

public function hookPayment($params)
	{
		// 4 catégories dont tous les produits sont eligibles à la méthode de paiement
		$categories_eligibles = array(28, 5, 9, 22);

		// On récupère les produits du panier pour vérification
		$products = Context::getContext()->cart->getProducts();

		// On crée une variable d'état qui de base désactive la méthode de paiement
		$allowed = false;

		// On crée une boucle qui vérifie l'appartenance des produits du panier à nos $catégories éligibles
		foreach ($products as $product)
		{
		if (Products::idIsOnCategoryId($product['id_product'], $categories_eligibles)) {
			// Si un produit est éligible on change la variable d'état à TRUE
			$allowed = true;
		}
		else{
			$allowed = false;
		}
		}
		// Si notre variable d'état est à TRUE on active la méthode de paiement
		if (!$allowed)
		return;

		// Autres érifications de base du module
		if (!$this->active)
			return;
		if (!$this->checkCurrency($params['cart']))
			return;

		$this->smarty->assign(array(
			'this_path' => $this->_path,
			'this_path_bw' => $this->_path,
			'this_path_ssl' => Tools::getShopDomainSsl(true, true).__PS_BASE_URI__.'modules/'.$this->name.'/'
		));
		return $this->display(__FILE__, 'payment.tpl');
	}

 

Encore merci pour votre temps !

Edited by Alain D.
Correction de fautes de frappes dans le code PHP (see edit history)
Link to comment
Share on other sites

Le produit est associé à une ou plusieurs catégories, c’est vous qui choisissez les catégories associées.

Dans votre exemple, si le produit est associé à Menthe mais pas à Bonbon alors si vous faites un test sur Bonbon le produit ne sera pas dans cette catégorie, mais cela c’est juste votre choix, rien d'autre.

Dans votre exemple de code, le soucis c'est que vous scannez tous les produits du paniers avant de définir si vous affichez ou pas la solution de paiement. En gros si il y a 5 000 produits cela va prendre un temps fou (je sais c’est beaucoup, mais 'est jute pour faire comprendre le principe).

Donc, lorsque l'on trouve le premier produit éligible pour l'affichage de ce mode de paiement, hop on arrête de scanner les produits un par un.

    if (Products::idIsOnCategoryId($product['id_product'], $categories_eligibles)) {
      // Si un produit est éligible on change la variable d'état à TRUE
      $allowed = true;
      // on sort du foreach pour éviter de scanner tous les produits inutilement
      break;
    }

 

Link to comment
Share on other sites

Oui j'avais oublié le "break;" pour stopper la boucle.

En revanche mon code ne semble pas fonctionner car lorsque je souhaite accéder à l'étape 05 (paiement) j'obtiens le message d'erreur suivant :

Fatal error: Class 'Products' not found  ... in line 156

Le message fait référence à cette ligne de code :

			if (Products::idIsOnCategoryId($product['id_product'], $categories_eligibles)) {

Comment intégrer la classe Product ? Quelque chose m’échappe :o

 

Link to comment
Share on other sites

Bien vu merci !

Effectivement avec "Product::" je n'ai plus l'erreur en revanche ma méthode de paiement ne s'affiche pas :/

Voici mon code actuel :

public function hookPayment($params)
{
	// 4 catégories dont tous les produits sont eligibles à la méthode de paiement
	$categories_eligibles = array(283, 5, 9, 22);

	// On récupère les produits du panier pour vérification
	$products = Context::getContext()->cart->getProducts();

	// On crée une variable d'état qui de base désactive la méthode de paiement
	$allowed = false;

	// On crée une boucle qui vérifie l'appartenance des produits du panier à nos $catégories éligibles
	foreach ($products as $product)
		{
			if (Product::idIsOnCategoryId($product['id_product'], $categories_eligibles)) {
				// Si un produit est éligible on change la variable d'état à TRUE
				$allowed = true;
				// on sort du foreach pour éviter de scanner tous les produits inutilement
				break;
			}
		}
	// Si notre variable d'état est à TRUE on active la méthode de paiement
	if (!$allowed)
	return;

	// Autres érifications de base du module
	if (!$this->active)
	return;

	if (!$this->checkCurrency($params['cart']))
	return;

	$this->smarty->assign(array(
		'this_path' => $this->_path,
		'this_path_bw' => $this->_path,
		'this_path_ssl' => Tools::getShopDomainSsl(true, true).__PS_BASE_URI__.'modules/'.$this->name.'/'
	));
	return $this->display(__FILE__, 'payment.tpl');
}

Dans mon panier j'ai pourtant un seul produit, qui appartient à la catégorie dont l'ID est 283 (283 est dans le array $categories_eligibles).

Le code me semble pourtant bon et je n'ai aucune erreur.

 

Link to comment
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now
×
×
  • Create New...