Question

I created a custom module to add an event to the Checkout Model saveBilling() function contained in Mage/Checkout/Model/Type/Onepage.php. Aside from the event firing properly every time it's called, the module now occasionally throws an error:

Notice: Undefined property: Fla_Checkout_Model_Type_Onepage::$_customerEmailExistsMessage
in /home/magento/public_html/app/code/local/Fla/Checkout/Model/Type/Onepage.php
on line 154

Pertinent bits of the module, the code in public function saveBilling() is exactly the same as Magento core aside from the dispatchEvent() line and its preceeding comment. The section throwing the error:

<?php
class Fla_Checkout_Model_Type_Onepage extends Mage_Checkout_Model_Type_Onepage {
    public function saveBilling($data, $customerAddressId) {

        /* much code removed here as not relevant to question */

        /* This section throws error because $this->_customerEmailExistsMessage not found */


        if (!$this->getQuote()->getCustomerId() && self::METHOD_REGISTER == $this->getQuote()->getCheckoutMethod()) {
            if ($this->_customerEmailExists($address->getEmail(), Mage::app()->getWebsite()->getId())) {
                return array('error' => 1, 'message' => $this->_customerEmailExistsMessage);
            }
        }


        /* much code removed here as not relevant to question, below code works as intended*/

        /* Fiascolabs added event for exporting billing data */
        Mage::dispatchEvent('fla_billing_export', array('quote'=>$this->getQuote()));

        return array();
    }
}

When I consult the Magento core code, at the top, I have several items declared that seem to not be accessed in the function overwrite.

  1. Are the constants and public function __construct() available to my module?

  2. Do I only have to duplicate the declared private items?

The code in question is below:

/**
 * Checkout types: Checkout as Guest, Register, Logged In Customer
 */
const METHOD_GUEST    = 'guest';
const METHOD_REGISTER = 'register';
const METHOD_CUSTOMER = 'customer';

/**
 * Error message of "customer already exists"
 *
 * @var string
 */
private $_customerEmailExistsMessage = '';

/**
 * Class constructor
 * Set customer already exists message
 */
public function __construct()
{
    $this->_helper = Mage::helper('checkout');
    $this->_customerEmailExistsMessage = $this->_helper->__('There is already a customer registered using this email address. Please login using this email address or enter a different email address to register your account.');
    $this->_checkoutSession = Mage::getSingleton('checkout/session');
    $this->_customerSession = Mage::getSingleton('customer/session');
}
Was it helpful?

Solution

It's easy to get tripped up and mystified by Magento's class rewrites, because they seem like voodoo at first. However, outside of the "instantiate this class instead of this other class" functionality, class rewrites are just standard PHP OOP, and all standard PHP OOP rules apply.

Specifically, if your class extends another class, it will not have access to private properties of the base class/object.

private $_customerEmailExistsMessage = '';

You will have access to protected and public properties and methods. You could redefine the __constructor method if you wanted

public function __construct()
{        
    //do the stuff in the parent consturctor
    parent::__construct();

    //do my new stuff
}    

You don't need to call parent::__construct(), but it's always a good idea to do this unless you have a reason not to. The parent::methodName() syntax will work with other methods as well

public function getCheckout()
{
    $parent_results = parent::getCheckout();

    //do my stuff

    return $parent_results;
}

Constants are a bit trickier. While constants don't have access rules like member functions and variables, depending on your version of PHP (5.2 vs. 5.3 and greater), PHP's "Late Static Bindings" behavior will change how its special 'self', 'parent', and 'static' keywords interact with constants. Generally speaking, the Magento codebase uses the full class name when referencing constants

echo Mage_Checkout_Model_Type_Onepage::METHOD_REGISTER

I've tended to, and recommend you, do the same.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top