17.02.2012

Einstellen einer Standard Versandart in Magento

In Magento gibt es bis dato keinen vernünftigen Weg eine standardmässige Versandart zu definieren.  Bietet man als Shopbetreiber ohnehin nur eine Versandart an, muss der Kunde unnötigerweise trotzdem noch den kognitiven Aufwand leisten, diese im Checkout auszuwählen.  Im ersten Schritt dieses 2-teiligen Tutorials zeige ich, wie man diesen Konversionshemmer elegant beseitigen und der Kunde die Versandkosten im Warenkorb angezeigt bekommt, ohne dass von ihm dafür extra eine Aktion erforderlich ist.

Für dieses Tutorial nehmen wir an, dass der Shopbetreiber nur in ein einziges Land versendet, wie es bei vielen Onlineshops ja der Fall ist.

Damit wir das Ganze in all unseren Magento-Projekten leicht wiederverwenden können, bauen wir uns eine Magento-Extension. Die komplette Extension kann übrigens hier kostenlos heruntergeladen werden.
Ausserdem wollen wir nicht, dass der Kunde uns jedes Mal anruft, wenn die Versandart geändert werden soll :-) Deshalb entwickeln wir auch gleich noch ein Administrationsbackend, in dem er die Versandmethode selbst einstellen kann, ohne im Code herumfriemeln zu müssen.

Schritt 1 - Erstellen des Grundgerüsts unseres Moduls

Für unser Magento-Modul benötigen wir folgende Verzeichnisse (Der Einfacheit halber benutze ich für dieses Tutorial die Namen, wie ich sie in meinem Modul verwendet habe):

app/code/community/Bozoo/DefaultShipping/Helper

app/code/community/Bozoo/DefaultShipping/Model

app/code/community/Bozoo/DefaultShipping/etc

Unter app/etc/modules erstellen wir eine Datei mit dem Namen Bozoo_DefaultShipping.xml und folgendem Inhalt:

<?xml version="1.0"?>
<config>
    <modules>
        <Bozoo_DefaultShipping>
            <active>true</active>
            <codePool>community</codePool>
        </Bozoo_DefaultShipping>
    </modules>
</config>

Jetzt haben wir soweit alles beisammen, um mit der Entwicklung des eigentlichen Moduls beginnen zu können.

Schritt 2 - Die Konfiguration unseres Moduls

In dem soeben angelegten Verzeichnis app/code/community/Bozoo/DefaultShipping/etc erstellen wir eine Datei mit Namen config.xml und folgendem Inhalt:

<config>
    <modules>
      <Bozoo_DefaultShipping>
          <version>1.0.0</version>
      </Bozoo_DefaultShipping>
    </modules>
    <global>
        <helpers>
            <defaultshipping>
                <class>Bozoo_DefaultShipping_Helper</class>
            </defaultshipping>
        </helpers>
        <models>
            <defaultshipping>
                <class>Bozoo_DefaultShipping_Model</class>
            </defaultshipping>
        </models>
        <events>
            <checkout_cart_save_before>
                <observers>
                  <bozoo_defaultshipping_model_observer>
                    <type>singleton</type>
                    <class>Bozoo_DefaultShipping_Model_Observer</class>
                    <method>apply_default_shipping</method>
                  </bozoo_defaultshipping_model_observer>
                </observers>
            </checkout_cart_save_before>
        </events>
    </global>
    <frontend>
        <layout>
            <updates>
                <defaultshipping>
                    <file>bozoo_defaultshipping.xml</file>
                </defaultshipping>
            </updates>
        </layout>
    </frontend>
    <admin>
        <routers>
            <adminhtml>
                <args>
                    <modules>
                        <defaultshipping before="Mage_Adminhtml">Bozoo_DefaultShipping_Adminhtml</defaultshipping>
                    </modules>
                </args>
            </adminhtml>
        </routers>
    </admin>
</config>

Hiermit teilen wir Magento mit, wo die Codebestandteile unseres Moduls zu finden sind und vor allem, dass wir bei Auftreten des Ereignisses 'checkout_cart_save_before' eigenen Code ausführen wollen. Dies ist sozusagen der eigentliche Kern unseres Moduls, der das standardmässige Verhalten Magentos an dieser Stelle leicht abändert. Weiter zu Schritt 3.

Schritt 3 - Erstellen des Observers

In der config.xml haben wir Magento mitgeteilt, bei Auftreten des Events 'checkout_cart_save_before' die Methode 'apply_default_shipping' in unserem Observer aufzurufen. D.h., dass jedes Mal, wenn der Kunde seinen Warenkorb aufruft, der Code ausgeführt wird, den wir jetzt schreiben:

Wir erstellen eine Datei mit Namen 'Observer.php' unter app/code/community/Bozoo/DefaultShipping/Model und zwar mit folgendem Inhalt:

class Bozoo_DefaultShipping_Model_Observer {

    public function apply_default_shipping() {

        try {
            $default_country = Mage::getStoreConfig('defaultshipping/general/default_country');
            $default_shipping_method = Mage::getStoreConfig('defaultshipping/general/default_shipping_method');


            if (Mage::getSingleton('checkout/cart')->getQuote()->getShippingAddress()->getCountryId() != $default_country ||
                    Mage::getSingleton('checkout/cart')->getQuote()->getShippingAddress()->getShippingMethod() != $default_shipping_method) {

                Mage::getSingleton('checkout/cart')->getQuote()->getShippingAddress()->setCountryId($default_country);

                if (Mage::getSingleton('checkout/cart')->getQuote()->getShippingAddress()->getShippingMethod() != $default_shipping_method) {
                    Mage::getSingleton('checkout/cart')->getQuote()->getShippingAddress()->setShippingMethod($default_shipping_method)->save();
                }
            }
        } catch (Mage_Core_Exception $e) {
            Mage::getSingleton('checkout/session')->addError($e->getMessage());
        } catch (Exception $e) {
            Mage::getSingleton('checkout/session')->addException($e, Mage::helper('checkout')->__('An error occured when trying to apply default shipping'));
        }
    }

Hier wird im Prinzip nur geprüft, ob die vorhandene Versandart und das Land, in das versendet werden soll, den gewünschten Werten entspricht. Falls nicht, werden diese gesetzt. Die gewünschten Werte stammen dabei aus dem Konfigurationsbackend Magentos:

$default_country = Mage::getStoreConfig('defaultshipping/general/default_country');
$default_shipping_method = Mage::getStoreConfig('defaultshipping/general/default_shipping_method');

Damit der Observer die Werte dort auch findet, bauen wir uns in Schritt 4 eine Administrationskonsole für unser Modul.

Schritt 4 - Erstellen der Administrationsoberfläche

Unsere Admin-Oberfläche können wir komplett in XML beschreiben. Dazu legen wir unter app/code/community/Bozoo/DefaultShipping/etc eine Datei mit Namen system.xml an, die folgenden Inhalt hat:

<?xml version="1.0"?>

<config>
    <tabs>
        <bozoo translate="label" module="defaultshipping">
            <label>Bozoo</label>
            <sort_order>110</sort_order>
        </bozoo>
    </tabs>
    <sections>
        <defaultshipping translate="label" module="defaultshipping">
            <class>separator-top</class>
            <label>Default Shipping</label>
            <tab>bozoo</tab>
            <sort_order>10</sort_order>
            <show_in_default>1</show_in_default>
            <show_in_website>1</show_in_website>
            <show_in_store>1</show_in_store>
            <groups>
                <general translate="label">
                    <label>General</label>
                    <frontend_type>text</frontend_type>
                    <sort_order>1</sort_order>
                    <show_in_default>1</show_in_default>
                    <show_in_website>1</show_in_website>
                    <show_in_store>1</show_in_store>
                    <fields>
                        
                        <default_country translate="label comment">
                            <label>Default Country</label>
                            <frontend_type>select</frontend_type>
                            <source_model>adminhtml/system_config_source_country</source_model>
                            <comment>Please select a country to which the shipping method can applied to</comment>
                            <sort_order>1</sort_order>
                            <show_in_default>1</show_in_default>
                            <show_in_website>1</show_in_website>
                            <show_in_store>1</show_in_store>
                        </default_country>
                        
                        <default_shipping_method translate="label comment">
                            <label>Default Shipping Method</label>
                            <frontend_type>select</frontend_type>
                            <source_model>defaultshipping/ActiveShippingMethods</source_model>
                            <comment>Note: If the desired shipping method doesn't appear in this field, make sure it's activated</comment>
                            <sort_order>0</sort_order>
                            <show_in_default>1</show_in_default>
                            <show_in_website>1</show_in_website>
                            <show_in_store>1</show_in_store>
                        </default_shipping_method>
                        
                        <remove_shipping_block_from_cart translate="label comment">
                            <label>Remove Shipping Block from Cart</label>
                            <frontend_type>select</frontend_type>
                            <source_model>adminhtml/system_config_source_yesno</source_model>
                            <comment>E.g. if you provide only one shipping method, displaying the block is obsolete</comment>
                            <sort_order>2</sort_order>
                            <show_in_default>1</show_in_default>
                            <show_in_website>1</show_in_website>
                            <show_in_store>1</show_in_store>
                        </remove_shipping_block_from_cart>
                        
                    </fields>
                </general>
            </groups>
        </defaultshipping>
    </sections>
</config>

Hier sind besonders die 3 Knoten unter <fields> interessant. Für 'default_country' und 'remove_shipping_block_from_cart' kann auf vorhandene sog. "Source-Models" zurückgegriffebn werden. Diese sind:

<source_model>adminhtml/system_config_source_country</source_model>

<source_model>adminhtml/system_config_source_yesno</source_model>

Zwar könnten wir für die Select-Box der Versandarten auch auf das in Magento vorhandene Source-Model zurückgreifen, aber dann würden dort alle möglichen Versandarten erscheinen, also auch jene, die vom Shopbetreiber gar nicht aktiviert wurden. Um diese mögliche Fehlerquelle zu vermeiden und es so einfach wie möglich zu machen, erstellen wir ein eigenes Model, das das vorhandene erweitert. Dazu erstellen wir unter app/code/community/Bozoo/DefaultShipping/Model eine Datei mit Namen 'ActiveShippingMethods.php' und füllen diese mit folgendem Inhalt:

class Bozoo_DefaultShipping_Model_ActiveShippingMethods extends Mage_Adminhtml_Model_System_Config_Source_Shipping_Allmethods{
    
    public function toOptionArray($isActiveOnlyFlag = true){
        
        return parent::toOptionArray(true);
        
    }
}

Das Source-Model wird in der system.xml dann wie folgt angegeben:

<source_model>defaultshipping/ActiveShippingMethods</source_model>

 

Schritt 5 - Ändern des Layouts des Warenkorbs

Innerhalb unserer soeben erstellten Admin-Oberfläche haben wir ein Feld aufgenommen, über das der Shopbetreiber auswählen kann, ob der den Versand-Block im Warenkorb anzeigen will, oder nicht. Dies macht z.B. Sinn, wenn er ohnehin nur eine mögliche Versandart anbieten möchte. Die Anzeige des Blocks zur Auswahl der Versandart und Schätzung der Versandkosten wäre damit obsolet. Daher erstellen wir noch ein Layout-Update, indem wir unter app/design/frontend/default/default/layout noch eine Datei 'bozoo_defaultshipping.xml' mit folgendem Inhalt erstellen:

<layout version="0.1.0">

    <checkout_cart_index>
        <reference name="checkout.cart">
            <action ifconfig="defaultshipping/general/remove_shipping_block_from_cart" method="unsetChild"><name>shipping</name></action>
        </reference>
    </checkout_cart_index>

    <bozoo_defaultshipping_checkout_cart_index>
        <update handle="checkout_cart_index"/>
    </bozoo_defaultshipping_checkout_cart_index>

</layout>

Den konfigurierten Wert lesen wir innerhalb des Attributes ifconfig' können so die Anzeige des Blocks konditional steuern.

Für diejenigen, die nur eine Versandart in ihrem Shop anbieten wollen, zeige ich im 2. Teil des Tutorials (ich hoffe ich komme kommende Woche noch dazu), wie die Auswahl der Versandart komplett aus dem Checkout-Prozess verbannt werden kann. Hierzu müssen auch ein paar JavaScripte angepasst werden.

 

 

 

 

 

 

«Einstellen einer Standard Versandart in Magento» kommentieren

 
 

Suche

Werbung

© 2012 bozoo.com