16

How do you impliment a hook system in a PHP application to change the code before or after it executes. How would the basic architecture of a hookloader class be for a PHP CMS (or even a simple application). How then could this be extended into a full plugins/modules loader?

(Also, are there any books or tutorials on a CMS hook system?)

alecwhardy
  • 2,698
  • 6
  • 27
  • 33
  • possible duplicate of [How does plugin system work (wordpress, mybb ...)?](http://stackoverflow.com/questions/5127424/how-does-plugin-system-work-wordpress-mybb) – mario Dec 01 '11 at 03:49
  • 1
    This doesn't answer your question - but an alternative... Make template objects at the beginning of your script, load up the different objects throughout the execution by passing them around with the controller or initiating them with a template factory (i use it in the controller). Then, compile the templates into how you want them to look at the end. You can point to custom style sheets then too. – phpmeh Dec 01 '11 at 03:51
  • Can you provide your own insights for this question? It's been a while since you asked this question and I'm interested to know what are the most important aspects you learned from your own experience with writing a custom CMS – Adrian Moisa Jan 15 '16 at 13:59

3 Answers3

31

You can build an events system as simple or complex as you want it.

/**
 * Attach (or remove) multiple callbacks to an event and trigger those callbacks when that event is called.
 *
 * @param string $event name
 * @param mixed $value the optional value to pass to each callback
 * @param mixed $callback the method or function to call - FALSE to remove all callbacks for event
 */
function event($event, $value = NULL, $callback = NULL)
{
    static $events;

    // Adding or removing a callback?
    if($callback !== NULL)
    {
        if($callback)
        {
            $events[$event][] = $callback;
        }
        else
        {
            unset($events[$event]);
        }
    }
    elseif(isset($events[$event])) // Fire a callback
    {
        foreach($events[$event] as $function)
        {
            $value = call_user_func($function, $value);
        }
        return $value;
    }
}

Add an event

event('filter_text', NULL, function($text) { return htmlspecialchars($text); });
// add more as needed
event('filter_text', NULL, function($text) { return nl2br($text); });
// OR like this
//event('filter_text', NULL, 'nl2br');

Then call it like this

$text = event('filter_text', $_POST['text']);

Or remove all callbacks for that event like this

event('filter_text', null, false);
Xeoncross
  • 55,620
  • 80
  • 262
  • 364
2

Here's another solution:

Creating a hook

Run this wherever you want to create a hook:

x_do_action('header_scripts');


Attach a function to the hook

Then attach a function to the above by doing:

x_add_action('header_scripts','my_function_attach_header_scripts');

function my_function_attach_header_scripts($values) {

   /* add my scripts here */

}

Global variable to store all hooks/events

Add this to the top of your main PHP functions file, or equivalent

$x_events = array();
global $x_events;

Base functions

function x_do_action($hook, $value = NULL) {
    global $x_events;

    if (isset($x_events[$hook])) {

        foreach($x_events[$hook] as $function) {

            if (function_exists($function)) { call_user_func($function, $value); }

        }
    }

}

function x_add_action($hook, $func, $val = NULL) {
    global $x_events;
    $x_events[$hook][] = $func;

}
Nick Duncan
  • 829
  • 6
  • 17
0

this solutions has some problems that you can't set several function for one callable hook. you can fallow this code.



 $action = [];

 function apply($hook, $args){
    global $action;
    $action[$hook]['args'] = $args;
    return doa($hook, $args);
 }

 function add($hook, $func){
    global $action;
    $action[$hook]['funcs'][] = $func;
 }

 function doa($hook,$args){
    global $action;
    if(isset($action[$hook]['funcs'])){
        foreach($action[$hook]['funcs'] as $k => $func){
            call_user_func_array($func, $args);
       }
    }
    
 }

 add('this_is', 'addOne');
function addOne($user){
    echo "this is test add one $user <br>";
}
add('this_is', function(){
    echo 'this is test add two <br>';
});


add('this_is_2', 'addTwo');
function addTwo($user, $name){
    echo $user . '   ' . $name . '<br>';
}


function test(){
    echo 'hello one <br>';
    apply('this_is', ['user'=> 123]);
}


function test2(){
    echo 'hello two <br>';
    apply('this_is_2', ['user'=> 123, 'name' => 'mohammad']);
}
test();
test2();



mohammad13
  • 453
  • 3
  • 17