1e1d9dcc8SAndreas Gohr<?php 242f12f7dSAndreas Gohr// phpcs:disable PSR1.Methods.CamelCapsMethodName.NotCamelCaps 3e1d9dcc8SAndreas Gohr 4e1d9dcc8SAndreas Gohrnamespace dokuwiki\Extension; 5e1d9dcc8SAndreas Gohr 6e1d9dcc8SAndreas Gohr/** 7e1d9dcc8SAndreas Gohr * Controls the registration and execution of all events, 8e1d9dcc8SAndreas Gohr */ 9e1d9dcc8SAndreas Gohrclass EventHandler 10e1d9dcc8SAndreas Gohr{ 11e1d9dcc8SAndreas Gohr 12e1d9dcc8SAndreas Gohr // public properties: none 13e1d9dcc8SAndreas Gohr 14e1d9dcc8SAndreas Gohr // private properties 1542f12f7dSAndreas Gohr protected $hooks = array(); // array of events and their registered handlers 16e1d9dcc8SAndreas Gohr 17e1d9dcc8SAndreas Gohr /** 18e1d9dcc8SAndreas Gohr * event_handler 19e1d9dcc8SAndreas Gohr * 20e1d9dcc8SAndreas Gohr * constructor, loads all action plugins and calls their register() method giving them 21e1d9dcc8SAndreas Gohr * an opportunity to register any hooks they require 22e1d9dcc8SAndreas Gohr */ 23e1d9dcc8SAndreas Gohr public function __construct() 24e1d9dcc8SAndreas Gohr { 25e1d9dcc8SAndreas Gohr 26e1d9dcc8SAndreas Gohr // load action plugins 27e1d9dcc8SAndreas Gohr /** @var ActionPlugin $plugin */ 28e1d9dcc8SAndreas Gohr $plugin = null; 29e1d9dcc8SAndreas Gohr $pluginlist = plugin_list('action'); 30e1d9dcc8SAndreas Gohr 31e1d9dcc8SAndreas Gohr foreach ($pluginlist as $plugin_name) { 32e1d9dcc8SAndreas Gohr $plugin = plugin_load('action', $plugin_name); 33e1d9dcc8SAndreas Gohr 34e1d9dcc8SAndreas Gohr if ($plugin !== null) $plugin->register($this); 35e1d9dcc8SAndreas Gohr } 36e1d9dcc8SAndreas Gohr } 37e1d9dcc8SAndreas Gohr 38e1d9dcc8SAndreas Gohr /** 39e1d9dcc8SAndreas Gohr * register_hook 40e1d9dcc8SAndreas Gohr * 41e1d9dcc8SAndreas Gohr * register a hook for an event 42e1d9dcc8SAndreas Gohr * 43e1d9dcc8SAndreas Gohr * @param string $event string name used by the event, (incl '_before' or '_after' for triggers) 44e1d9dcc8SAndreas Gohr * @param string $advise 45e1d9dcc8SAndreas Gohr * @param object $obj object in whose scope method is to be executed, 46e1d9dcc8SAndreas Gohr * if NULL, method is assumed to be a globally available function 47e1d9dcc8SAndreas Gohr * @param string $method event handler function 48e1d9dcc8SAndreas Gohr * @param mixed $param data passed to the event handler 49e1d9dcc8SAndreas Gohr * @param int $seq sequence number for ordering hook execution (ascending) 50e1d9dcc8SAndreas Gohr */ 51e1d9dcc8SAndreas Gohr public function register_hook($event, $advise, $obj, $method, $param = null, $seq = 0) 52e1d9dcc8SAndreas Gohr { 53e1d9dcc8SAndreas Gohr $seq = (int)$seq; 5442f12f7dSAndreas Gohr $doSort = !isset($this->hooks[$event . '_' . $advise][$seq]); 5542f12f7dSAndreas Gohr $this->hooks[$event . '_' . $advise][$seq][] = array($obj, $method, $param); 56e1d9dcc8SAndreas Gohr 57e1d9dcc8SAndreas Gohr if ($doSort) { 5842f12f7dSAndreas Gohr ksort($this->hooks[$event . '_' . $advise]); 59e1d9dcc8SAndreas Gohr } 60e1d9dcc8SAndreas Gohr } 61e1d9dcc8SAndreas Gohr 62e1d9dcc8SAndreas Gohr /** 63e1d9dcc8SAndreas Gohr * process the before/after event 64e1d9dcc8SAndreas Gohr * 65e1d9dcc8SAndreas Gohr * @param Event $event 66e1d9dcc8SAndreas Gohr * @param string $advise BEFORE or AFTER 67e1d9dcc8SAndreas Gohr */ 68e1d9dcc8SAndreas Gohr public function process_event($event, $advise = '') 69e1d9dcc8SAndreas Gohr { 70e1d9dcc8SAndreas Gohr 71e1d9dcc8SAndreas Gohr $evt_name = $event->name . ($advise ? '_' . $advise : '_BEFORE'); 72e1d9dcc8SAndreas Gohr 7342f12f7dSAndreas Gohr if (!empty($this->hooks[$evt_name])) { 7442f12f7dSAndreas Gohr foreach ($this->hooks[$evt_name] as $sequenced_hooks) { 75e1d9dcc8SAndreas Gohr foreach ($sequenced_hooks as $hook) { 76e1d9dcc8SAndreas Gohr list($obj, $method, $param) = $hook; 77e1d9dcc8SAndreas Gohr 78*7c9b63b7SAndreas Gohr if ($obj === null) { 79e1d9dcc8SAndreas Gohr $method($event, $param); 80e1d9dcc8SAndreas Gohr } else { 81e1d9dcc8SAndreas Gohr $obj->$method($event, $param); 82e1d9dcc8SAndreas Gohr } 83e1d9dcc8SAndreas Gohr 84e1d9dcc8SAndreas Gohr if (!$event->mayPropagate()) return; 85e1d9dcc8SAndreas Gohr } 86e1d9dcc8SAndreas Gohr } 87e1d9dcc8SAndreas Gohr } 88e1d9dcc8SAndreas Gohr } 89e1d9dcc8SAndreas Gohr 90e1d9dcc8SAndreas Gohr /** 91e1d9dcc8SAndreas Gohr * Check if an event has any registered handlers 92e1d9dcc8SAndreas Gohr * 93e1d9dcc8SAndreas Gohr * When $advise is empty, both BEFORE and AFTER events will be considered, 94e1d9dcc8SAndreas Gohr * otherwise only the given advisory is checked 95e1d9dcc8SAndreas Gohr * 96e1d9dcc8SAndreas Gohr * @param string $name Name of the event 97e1d9dcc8SAndreas Gohr * @param string $advise BEFORE, AFTER or empty 98e1d9dcc8SAndreas Gohr * @return bool 99e1d9dcc8SAndreas Gohr */ 100e1d9dcc8SAndreas Gohr public function hasHandlerForEvent($name, $advise = '') 101e1d9dcc8SAndreas Gohr { 102e1d9dcc8SAndreas Gohr if ($advise) { 10342f12f7dSAndreas Gohr return isset($this->hooks[$name . '_' . $advise]); 104e1d9dcc8SAndreas Gohr } 105*7c9b63b7SAndreas Gohr 106*7c9b63b7SAndreas Gohr return isset($this->hooks[$name . '_BEFORE']) || isset($this->hooks[$name . '_AFTER']); 107e1d9dcc8SAndreas Gohr } 108e1d9dcc8SAndreas Gohr} 109