PHPSymfony - Blog par un programmeur pour les programmeurs

To content | To menu | To search

Wednesday, April 7 2010

[MAGENTO] Les problèmes d'arrondi avec Magento 1.3

Dans Magento 1.3, il y a quelques problèmes d'arrondi.

J'ai eu le problème suivant :
Mon site doit avoir des codes de promotion qui rendent la commande gratuite, frais de ports compris. (Non, je ne donnerai pas ces codes :))
Ensuite, dans le tunnel de commande, l'idée était de n'afficher que la méthode "free" si celle-ci était trouvée. (D'ailleurs, il ne faut pas oublier d'activer l'option adéquate en backend).
Malheureusement, avec les problèmes d'arrondi, sur certaines commandes, j'obtenais un total non pas à 0.00 mais 0.000...x.
Ce qui, bien évidemment, empêche l'affichage de la méthode "free".

Le problème se situe dans la classe : Mage_Payment_Model_Method_Free et plus précisément dans la méthode isAvailable.

   public function isAvailable($quote=null)
    {
        if (is_null($quote)) {
           return false;
        }

        if (Mage::app()->getStore()->roundPrice($quote->getGrandTotal()) == 0) {
            return true;
        }

        return false;
    }


La méthode roundPrice peut renvoyer une valeur erronée à cause de l'utilisation de la fonction round() avec une précision de 2.

Une solution est d'ajouter le code suivant :

        if (number_format($quote->getGrandTotal(), 2) == '0.00')
        {
          return true;
        }

Cela devrait permettre d'avoir la méthode "free" disponible.

Si vous avez également des problèmes d'arrondi dans le total sur le panier, je vous conseille de modifier la précision de la méthode roundPrice().


Thursday, March 18 2010

[MAGENTO] Liste des évènements

Dernièrement, j'ai été amené à travailler sur MAGENTO chez Sensio Labs pour le compte d'un gros client.
Ne connaissant rien à cette plate-forme, j'ai du tout apprendre sur le tas !

Personnellement, je trouve Magento intéressant dans la mesure où l'on peut déployer très rapidement un site de e-commerce. Le backend de l'application est très fourni et fourmille de fonctionnalités permettant de paramétrer son site.
Cependant, d'un point de vue développement, la courbe d'apprentissage est très élevée et il faut un peu de patience pour comprendre le fonctionnement du système. D'autant plus que les articles/tutoriaux ne sont pas légions sur Internet, ce qui est bien dommage.

J'écrirais donc dans ce blog quelques articles spécialement consacrés à Magento.

La toute première tâche que j'ai eu à réaliser était de déclencher une action lors de la sauvegarde d'un compte utilisateur.
Pour cela, il faut se tourner vers les évènements.

Voici la liste des évènements que l'on peut "hooker" (version 1.3).

Pour utiliser cet évènement, on va devoir surcharger le module customer de Magento.

Dans les bonnes pratiques, il est (fortement) conseillé de ne pas modifier le code de base de Magento. Il est en effet possible de surcharger les différents modules de base (que l'on peut voir dans app/code/core/Mage) et bien évidemment d'en créer des nouveaux.

Après avoir choisi un namespace (le nom de l'entreprise par exemple), il faut créer le répertoire dans app/code/

mkdir app/code/[NAMESPACE]

C'est dans ce répertoire que l'on mettra tout notre code perso, on NE touchera JAMAIS à app/code/core.

Maintenant que l'on a définit un nouveau namespace, il faut que Magento puisse le détecter.
On va donc créer un fichier [NAMESPACE]_All.xml

touch /app/etc/modules/[NAMESPACE]_All.xml

On va placer dans ce fichier tous les modules de notre namespace. Exemple de contenu :

<?xml version="1.0"?>
<config>
    <modules>
        <[NAMESPACE]_Customer>
        <active>true</active>
            <codePool>local</codePool>
        </[NAMESPACE]_Customer>
    </modules>
</config>



Le code précédent permet d'activer le module [NAMESPACE]_Customer. Attention, vous devez configurer le namespace dans le backend de l'application.

Ensuite :

mkdir app/code/[NAMESPACE]/Customer
mkdir app/code/[NAMESPACE]/Customer/etc
touch app/code/[NAMESPACE]/Customer/etc/config.xml


Le fichier etc/config.xml contient toute la configuration du module. C'est notamment dans ce fichier que l'on pourra déclarer les installers, les règles de réécriture, ...

En ce qui nous concerne, on doit juste préciser la version du module et l'évènement à utiliser.

<?xml version="1.0"?>
<config>
    <modules>
        <[Namespace]_Customer>
            <version>0.1.0</version>
        </[Namespace]_Customer>
    </modules>
    <global>
     <events>
       <customer_save_after>
          <observers>
            <evian_customer>
              <type>singleton</type>
              <class>customer/observer</class>
              <method>afterCustomerSave</method>
            </evian_customer>
          </observers>
        </customer_save_after>
      </events>
    <models>
      <customer>
        <rewrite>
          <observer>[NAMESPACE]_Customer_Model_Observer</observer>
        </rewrite>
      </customer>
    </models>
    </global>
</config>


Le code précèdent signifie que lors de l'évènement customer_save_after, la méthode afterCustomerSave de la classe Observer doit être exécutée.
Le code a exécuter doit se trouver dans app/code/local/[NAMESPACE]/Customer/Model/Observer.php.
Or le fichier Observer.php existe déjà dans app/code/core/Customer/Model, il faut donc le réécrire (noeud rewrite).

Il nous faut donc créer un répertoire Model avec un fichier Observer.php

mkdir app/code/[NAMESPACE]/Customer/Model
touch app/code/[NAMESPACE]/Customer/Model/Observer.php


Le fichier Observer.php contiendra le code suivant :

class [NAMESPACE]_Customer_Model_Observer extends Mage_Customer_Model_Observer
{
  public function afterCustomerSave(Varien_Event_Observer $observer)
  {
    //execute code here
  }
}


Maintenant, après la sauvegarde d'un client, votre code perso sera exécuté.

Attention : ne pas oublier de nettoyer le cache après chaque modification de fichiers XML (de même que certains templates).

Je proposerais par la suite d'autres articles sur Magento et son utilisation.