Skip to content

Overriding a Magento Controller

Magento uses an MVC design pattern, and provides facilities to override functionality of each part without overwriting the core code-leaving you in a position to make changes to the site code that won’t be overwritten by upgrades. Since we have moved to Magento Enterprise Edition for a new project (and are now contractually obligated to upgrade to the newest software version immediately), this functionality is more important than ever.

Recently, I needed to change the Customer Account Controller, to keep new customers from being automatically signed in when they signed up for the site. I’ve made changes to Magento Core Models and Views before; for those, all you have to do is copy the file structure under /app/code/Mage to /app/code/local/. For example, if you want to override the Catalog/Product model, put your new file at /app/code/local/Catalog/Model/Product/Product.php. Magento will look first for files in the local folder, so it will use your new Product.php in place of the default. I tried to use the same method to override the Account Controller-recreating the file structure and making the necessary changes to my new file with no luck. To override a controller, I found out, you need to create a new module.

There are two ways to do this. One method uses regular expressions to rewrite the path to the controller file from the default to your file, described here. I chose a slightly cleaner second method, in which you use the ‘before’ attribute to give higher priority to one module over another in a frontname space, described here.

After some futzing with the xml (and creating a nice ‘hello world’ module based on Alan Storm’s excellent tutorial), I ran into a problem that I had a hard time solving. The script kept crashing…but I’d done everything right!

Debugging revealed that my include statement was crashing the script. I wanted to include_once() the default Account controller, because I only wanted to override one function in it, and didn’t want to reproduce the rest of the code unnecessarily. Was my php include path misconfigured? No, it looks ok. Say, I wonder what the Magento include path might be? Oh…er, oh.

I never cleaned up my mess from my earlier attempt to solve the problem-I still had AccountController.php sitting in /app/code/local. And since /app/code/local is higher in the Magento include path than /app/code/core, my local AccountController.php is the one that’s getting included in my new module. And that one still doesn’t have the right configuration information. Once I deleted that file, my new overrided controller worked perfectly.

Lessons:
1) Computers always do what you tell them to do, no more and no less (I like to think of this as “The Grand Lesson”).
2) Be sure that your current problem isn’t a symptom of your earlier “solution”.

Post a Comment

Your email is never published nor shared. Required fields are marked *
*
*