So you've just bought an addon for your latest project. Slight problem - it doesn't *quite* do what you want you need and open the module or extension to see if you can put in a hack to fullfil your requirements.

Just stop a moment and think - would it be better for you to put a hook instead?

We all work with various add-ons and at Hippo we're no different. However, quite a few of our requests are "We've bought X add-on but need it to do Y. Can you help?".

As a results, we started hacking around with the likes of Solspace Calendar, Zoo Visitor, BrilliantRetail, Matrix, Detour (Pro) and many others - however, once you start hacking the core of an add-on, maintaining an upgradable code base becomes more and more difficult.

So, we have started adding custom hooks into existing addons and points in the code that we need to inject our functionality. Not only does this abstract the custom logic away from the core add-on, but it means you're looking at 2-3 lines of code when it comes to upgrading the add-on for future releases.

Lets have a quick look at a piece of hook code:


Here's a simple hook from BrilliantRetail which allows a developer to take the resulting data from the system after an order has been created, do something with it and then pass it back to BrilliantRetail for onward processing.

Creating a custom hook

For my example, I'm going to use the BrilliantRetail module example I needed to do for a recent project. The client needed the ability for users from a specific email address to be put into their own member group. As is currently the case, the system by default puts customers into a single member group as defined in the store settings - so I needed to manipulate and override this functionality.

First thing to do is to the find the appropriate function in the add-on that you want to insert the hook. For those that don't know, although not *always* the case, a general rule of thumb, a {exp:addon_name:function} format is observed. So for our case, we wanted to do some custom processing to the {exp:brilliant_retail:register_form} tag. First thing to do is to find the register_form function in the module.

We can see in this function that the form action (i.e. where the form is posted to) is called 'customer_register' - so, we can now go look for this function.

Once I've found this function, I look through the code and see where the group and member information is processed. In this particular case, the data is stored nicely in an array - which is perfect for what we need.


So now all we need to do is to add our hook in directly after this array so that we can write an extension to process our custom logic by simply adding the following code:

if($this->EE->extensions->active_hook('hippo_custom_member_tweak') === TRUE) {
$new = $this->EE->extensions->call('hippo_custom_member_tweak', $new);

That's essentially it! You've now created a hook in the add-on to facilitate What this now means is that we've essentially created a hook called 'hippo_custom_member_tweak', are passing in the $new array. Since we've also assigning $new to the result of the hook call, we're expecting it to return the same array, but manipulated in some way to meet our requirements. If you don't need your hook to actually return any manipulated data to the add-on (for example just may just want to do some additional processing or update another part of the site) and don't need to send anything back, you can just call the extension hook function.

You can call this hook anything you want, but I would certainly recommend keeping it applicable to what you're trying to do with the custom functionality so that it's easier to understand in 12 months time when something isn't working or your need to update something.

To write your custom extension, I recommend the great package builder for ExpressionEngine at by Pascal Kriete and Greg Aker. At the end of this article is a link to a custom extension hook that I've created based on a pkg installation - feel free to download and use it til your hearts content.

Obviously, the usual caveats apply when you start putting your own custom code and logic into add-ons. Support is going to be limited in most cases, however, I have certainly found that if you explain to the add-on developer(s) why you've added this hook in, liklihood is that it may feature in future releases as part of the core functionality.