00001 <?php
00031 function wfRunHooks($event, $args = array()) {
00032
00033 global $wgHooks;
00034
00035
00036 if ( !isset( $wgHooks[$event] ) ) {
00037 return true;
00038 }
00039
00040 if (!is_array($wgHooks)) {
00041 throw new MWException("Global hooks array is not an array!\n");
00042 return false;
00043 }
00044
00045 if (!is_array($wgHooks[$event])) {
00046 throw new MWException("Hooks array for event '$event' is not an array!\n");
00047 return false;
00048 }
00049
00050 foreach ($wgHooks[$event] as $index => $hook) {
00051
00052 $object = null;
00053 $method = null;
00054 $func = null;
00055 $data = null;
00056 $have_data = false;
00057 $closure = false;
00058
00059
00060
00061
00062
00063
00064 if ( is_array( $hook ) ) {
00065 if ( count( $hook ) < 1 ) {
00066 throw new MWException("Empty array in hooks for " . $event . "\n");
00067 } else if ( is_object( $hook[0] ) ) {
00068 $object = $wgHooks[$event][$index][0];
00069 if ( $object instanceof Closure ) {
00070 $closure = true;
00071 if ( count( $hook ) > 1 ) {
00072 $data = $hook[1];
00073 $have_data = true;
00074 }
00075 } else {
00076 if ( count( $hook ) < 2 ) {
00077 $method = "on" . $event;
00078 } else {
00079 $method = $hook[1];
00080 if ( count( $hook ) > 2 ) {
00081 $data = $hook[2];
00082 $have_data = true;
00083 }
00084 }
00085 }
00086 } else if ( is_string( $hook[0] ) ) {
00087 $func = $hook[0];
00088 if ( count( $hook ) > 1) {
00089 $data = $hook[1];
00090 $have_data = true;
00091 }
00092 } else {
00093 throw new MWException( "Unknown datatype in hooks for " . $event . "\n" );
00094 }
00095 } else if ( is_string( $hook ) ) { # functions look like strings, too
00096 $func = $hook;
00097 } else if ( is_object( $hook ) ) {
00098 $object = $wgHooks[$event][$index];
00099 if ( $object instanceof Closure ) {
00100 $closure = true;
00101 } else {
00102 $method = "on" . $event;
00103 }
00104 } else {
00105 throw new MWException( "Unknown datatype in hooks for " . $event . "\n" );
00106 }
00107
00108
00109
00110 if ( $have_data ) {
00111 $hook_args = array_merge(array($data), $args);
00112 } else {
00113 $hook_args = $args;
00114 }
00115
00116 if ( $closure ) {
00117 $callback = $object;
00118 $func = "hook-$event-closure";
00119 } elseif ( isset( $object ) ) {
00120 $func = get_class( $object ) . '::' . $method;
00121 $callback = array( $object, $method );
00122 } elseif ( false !== ( $pos = strpos( $func, '::' ) ) ) {
00123 $callback = array( substr( $func, 0, $pos ), substr( $func, $pos + 2 ) );
00124 } else {
00125 $callback = $func;
00126 }
00127
00128
00129 is_callable( $callback );
00130
00131
00132 wfProfileIn( $func );
00133 $retval = call_user_func_array( $callback, $hook_args );
00134 wfProfileOut( $func );
00135
00136
00137
00138 if ( is_string( $retval ) ) {
00139 global $wgOut;
00140 $wgOut->showFatalError( $retval );
00141 return false;
00142 } elseif( $retval === null ) {
00143 if ( $closure ) {
00144 $prettyFunc = "$event closure";
00145 } elseif( is_array( $callback ) ) {
00146 if( is_object( $callback[0] ) ) {
00147 $prettyClass = get_class( $callback[0] );
00148 } else {
00149 $prettyClass = strval( $callback[0] );
00150 }
00151 $prettyFunc = $prettyClass . '::' . strval( $callback[1] );
00152 } else {
00153 $prettyFunc = strval( $callback );
00154 }
00155 throw new MWException( "Detected bug in an extension! " .
00156 "Hook $prettyFunc failed to return a value; " .
00157 "should return true to continue hook processing or false to abort." );
00158 } else if ( !$retval ) {
00159 return false;
00160 }
00161 }
00162
00163 return true;
00164 }