WordPress.org

Make WordPress Core

Ticket #21883: class-wp-plugin.patch

File class-wp-plugin.patch, 44.2 KB (added by johnjamesjacoby, 6 years ago)
  • wp-includes/class-wp-plugin.php

     
     1<?php
     2
     3/**
     4 * The plugin API is located in this file, which allows for creating actions
     5 * and filters and hooking functions, and methods. The functions or methods will
     6 * then be run when the action or filter is called.
     7 *
     8 * The API callback examples reference functions, but can be methods of classes.
     9 * To hook methods, you'll need to pass an array one of two ways.
     10 *
     11 * Any of the syntaxes explained in the PHP documentation for the
     12 * {@link http://us2.php.net/manual/en/language.pseudo-types.php#language.types.callback 'callback'}
     13 * type are valid.
     14 *
     15 * Also see the {@link http://codex.wordpress.org/Plugin_API Plugin API} for
     16 * more information and examples on how to use a lot of these functions.
     17 *
     18 * @package WordPress
     19 * @subpackage Plugin
     20 * @since 1.5
     21 */
     22class WP_Plugin {
     23
     24        /**
     25         * Array of actions and filters for this plugin
     26         *
     27         * @since 3.6
     28         * @var array
     29         */
     30        public $_filters = array();
     31
     32        /**
     33         * Array of actions and filters for this plugin
     34         *
     35         * @since 3.6
     36         * @var array
     37         */
     38        public $_merged_filters = array();
     39
     40        /**
     41         * The current filter(s) being run
     42         *
     43         * @since 3.6
     44         * @var array
     45         */
     46        public $_current_filter = array();
     47
     48        /**
     49         * A count of the number of times an action has fired
     50         *
     51         * @since 3.6
     52         * @var array
     53         */
     54        public $_action_calls = array();
     55
     56        /** Filters ***************************************************************/
     57
     58        /**
     59         * Hooks a function or method to a specific filter action.
     60         *
     61         * Filters are the hooks that WordPress launches to modify text of various types
     62         * before adding it to the database or sending it to the browser screen. Plugins
     63         * can specify that one or more of its PHP functions is executed to
     64         * modify specific types of text at these times, using the Filter API.
     65         *
     66         * To use the API, the following code should be used to bind a callback to the
     67         * filter.
     68         *
     69         * <code>
     70         * function example_hook($example) { echo $example; }
     71         * $plugin->add_filter('example_filter', 'example_hook');
     72         * </code>
     73         *
     74         * In WordPress 1.5.1+, hooked functions can take extra arguments that are set
     75         * when the matching do_action() or apply_filters() call is run. The
     76         * $accepted_args allow for calling functions only when the number of args
     77         * match. Hooked functions can take extra arguments that are set when the
     78         * matching do_action() or apply_filters() call is run. For example, the action
     79         * comment_id_not_found will pass any functions that hook onto it the ID of the
     80         * requested comment.
     81         *
     82         * <strong>Note:</strong> the function will return true no matter if the
     83         * function was hooked fails or not. There are no checks for whether the
     84         * function exists beforehand and no checks to whether the <tt>$function_to_add
     85         * is even a string. It is up to you to take care and this is done for
     86         * optimization purposes, so everything is as quick as possible.
     87         *
     88         * @package WordPress
     89         * @subpackage Plugin
     90         * @since 0.71
     91         *
     92         * @param string $tag The name of the filter to hook the $function_to_add to.
     93         * @param callback $function_to_add The name of the function to be called when the filter is applied.
     94         * @param int $priority optional. Used to specify the order in which the functions associated with a particular action are executed (default: 10). Lower numbers correspond with earlier execution, and functions with the same priority are executed in the order in which they were added to the action.
     95         * @param int $accepted_args optional. The number of arguments the function accept (default 1).
     96         * @return boolean true
     97         */
     98        public function add_filter( $tag, $function_to_add, $priority = 10, $accepted_args = 1 ) {
     99                $idx = $this->build_unique_id( $tag, $function_to_add, $priority );
     100
     101                $this->_filters[$tag][$priority][$idx] = array( 'function' => $function_to_add, 'accepted_args' => $accepted_args );
     102
     103                unset( $this->_merged_filters[$tag] );
     104
     105                return true;
     106        }
     107
     108        /**
     109         * Check if any filter has been registered for a hook.
     110         *
     111         * @package WordPress
     112         * @subpackage Plugin
     113         * @since 2.5
     114         * @global array $this->_filters Stores all of the filters
     115         *
     116         * @param string $tag The name of the filter hook.
     117         * @param callback $function_to_check optional.
     118         * @return mixed If $function_to_check is omitted, returns boolean for whether the hook has anything registered.
     119         *      When checking a specific function, the priority of that hook is returned, or false if the function is not attached.
     120         *      When using the $function_to_check argument, this function may return a non-boolean value that evaluates to false
     121         *      (e.g.) 0, so use the === operator for testing the return value.
     122         */
     123        public function has_filter( $tag, $function_to_check = false ) {
     124
     125                $has = !empty( $this->_filters[$tag] );
     126                if ( false === $function_to_check || false == $has )
     127                        return $has;
     128
     129                $idx = $this->build_unique_id( $tag, $function_to_check, false );
     130                if ( empty( $idx ) )
     131                        return false;
     132
     133                foreach ( (array) array_keys( $this->_filters[$tag] ) as $priority ) {
     134                        if ( isset( $this->_filters[$tag][$priority][$idx] ) ) {
     135                                return $priority;
     136                        }
     137                }
     138
     139                return false;
     140        }
     141
     142        /**
     143         * Call the functions added to a filter hook.
     144         *
     145         * The callback functions attached to filter hook $tag are invoked by calling
     146         * this function. This function can be used to create a new filter hook by
     147         * simply calling this function with the name of the new hook specified using
     148         * the $tag parameter.
     149         *
     150         * The function allows for additional arguments to be added and passed to hooks.
     151         * <code>
     152         * function example_hook($string, $arg1, $arg2)
     153         * {
     154         *              //Do stuff
     155         *              return $string;
     156         * }
     157         * $value = apply_filters('example_filter', 'filter me', 'arg1', 'arg2');
     158         * </code>
     159         *
     160         * @package WordPress
     161         * @subpackage Plugin
     162         * @since 0.71
     163         *
     164         * @param string $tag The name of the filter hook.
     165         * @param mixed $value The value on which the filters hooked to <tt>$tag</tt> are applied on.
     166         * @param mixed $var,... Additional variables passed to the functions hooked to <tt>$tag</tt>.
     167         * @return mixed The filtered value after all hooked functions are applied to it.
     168         */
     169        public function apply_filters( $tag, $value ) {
     170
     171                $args = array();
     172
     173                // Do 'all' actions first
     174                if ( isset( $this->_filters['all'] ) ) {
     175                        $this->_current_filter[] = $tag;
     176                        $args                   = func_get_args();
     177                        $this->call_all( $args );
     178                }
     179
     180                if ( !isset( $this->_filters[$tag] ) ) {
     181                        if ( isset( $this->_filters['all'] ) ) {
     182                                array_pop( $this->_current_filter );
     183                        }
     184
     185                        return $value;
     186                }
     187
     188                if ( !isset( $this->_filters['all'] ) )
     189                        $this->_current_filter[] = $tag;
     190
     191                // Sort
     192                if ( !isset( $this->_merged_filters[$tag] ) ) {
     193                        ksort( $this->_filters[$tag] );
     194                        $this->_merged_filters[$tag] = true;
     195                }
     196
     197                reset( $this->_filters[$tag] );
     198
     199                if ( empty( $args ) )
     200                        $args = func_get_args();
     201
     202                do {
     203                        foreach ( (array) current( $this->_filters[$tag] ) as $the_ ) {
     204                                if ( !is_null( $the_['function'] ) ) {
     205                                        $args[1] = $value;
     206                                        $value   = call_user_func_array( $the_['function'], array_slice( $args, 1, (int) $the_['accepted_args'] ) );
     207                                }
     208                        }
     209                } while ( next( $this->_filters[$tag] ) !== false );
     210
     211                array_pop( $this->_current_filter );
     212
     213                return $value;
     214        }
     215
     216        /**
     217         * Execute functions hooked on a specific filter hook, specifying arguments in an array.
     218         *
     219         * @see apply_filters() This function is identical, but the arguments passed to the
     220         * functions hooked to <tt>$tag</tt> are supplied using an array.
     221         *
     222         * @package WordPress
     223         * @subpackage Plugin
     224         * @since 3.0.0
     225         *
     226         * @param string $tag The name of the filter hook.
     227         * @param array $args The arguments supplied to the functions hooked to <tt>$tag</tt>
     228         * @return mixed The filtered value after all hooked functions are applied to it.
     229         */
     230        public function apply_filters_ref_array( $tag, $args ) {
     231
     232                // Do 'all' actions first
     233                if ( isset( $this->_filters['all'] ) ) {
     234                        $this->_current_filter[] = $tag;
     235                        $all_args               = func_get_args();
     236                        $this->call_all( $all_args );
     237                }
     238
     239                if ( !isset( $this->_filters[$tag] ) ) {
     240                        if ( isset( $this->_filters['all'] ) ) {
     241                                array_pop( $this->_current_filter );
     242                        }
     243
     244                        return $args[0];
     245                }
     246
     247                if ( !isset( $this->_filters['all'] ) ) {
     248                        $this->_current_filter[] = $tag;
     249                }
     250
     251                // Sort
     252                if ( !isset( $this->_merged_filters[$tag] ) ) {
     253                        ksort( $this->_filters[$tag] );
     254                        $this->_merged_filters[$tag] = true;
     255                }
     256
     257                reset( $this->_filters[$tag] );
     258
     259                do {
     260                        foreach ( (array) current( $this->_filters[$tag] ) as $the_ ) {
     261                                if ( !is_null( $the_['function'] ) ) {
     262                                        $args[0] = call_user_func_array( $the_['function'], array_slice( $args, 0, (int) $the_['accepted_args'] ) );
     263                                }
     264                        }
     265                } while ( next( $this->_filters[$tag] ) !== false );
     266
     267                array_pop( $this->_current_filter );
     268
     269                return $args[0];
     270        }
     271
     272        /**
     273         * Removes a function from a specified filter hook.
     274         *
     275         * This function removes a function attached to a specified filter hook. This
     276         * method can be used to remove default functions attached to a specific filter
     277         * hook and possibly replace them with a substitute.
     278         *
     279         * To remove a hook, the $function_to_remove and $priority arguments must match
     280         * when the hook was added. This goes for both filters and actions. No warning
     281         * will be given on removal failure.
     282         *
     283         * @package WordPress
     284         * @subpackage Plugin
     285         * @since 1.2
     286         *
     287         * @param string $tag The filter hook to which the function to be removed is hooked.
     288         * @param callback $function_to_remove The name of the function which should be removed.
     289         * @param int $priority optional. The priority of the function (default: 10).
     290         * @param int $accepted_args optional. The number of arguments the function accepts (default: 1).
     291         * @return boolean Whether the function existed before it was removed.
     292         */
     293        public function remove_filter( $tag, $function_to_remove, $priority = 10 ) {
     294                $function_to_remove = $this->build_unique_id( $tag, $function_to_remove, $priority );
     295
     296                $r = isset( $this->_filters[$tag][$priority][$function_to_remove] );
     297
     298                if ( true === $r ) {
     299                        unset( $this->_filters[$tag][$priority][$function_to_remove] );
     300
     301                        if ( empty( $this->_filters[$tag][$priority] ) ) {
     302                                unset( $this->_filters[$tag][$priority] );
     303                        }
     304
     305                        unset( $this->_merged_filters[$tag] );
     306                }
     307
     308                return $r;
     309        }
     310
     311        /**
     312         * Remove all of the hooks from a filter.
     313         *
     314         * @since 2.7
     315         *
     316         * @param string $tag The filter to remove hooks from.
     317         * @param int $priority The priority number to remove.
     318         * @return bool True when finished.
     319         */
     320        public function remove_all_filters( $tag, $priority = false ) {
     321
     322                if ( isset( $this->_filters[$tag] ) ) {
     323                        if ( false !== $priority && isset( $this->_filters[$tag][$priority] ) ) {
     324                                unset( $this->_filters[$tag][$priority] );
     325                        } else {
     326                                unset( $this->_filters[$tag] );
     327                        }
     328                }
     329
     330                if ( isset( $this->_merged_filters[$tag] ) ) {
     331                        unset( $this->_merged_filters[$tag] );
     332                }
     333
     334                return true;
     335        }
     336
     337        /**
     338         * Retrieve the name of the current filter or action.
     339         *
     340         * @package WordPress
     341         * @subpackage Plugin
     342         * @since 2.5
     343         *
     344         * @return string Hook name of the current filter or action.
     345         */
     346        public function current_filter() {
     347                return end( $this->_current_filter );
     348        }
     349
     350        /**
     351         * Hooks a function on to a specific action.
     352         *
     353         * Actions are the hooks that the WordPress core launches at specific points
     354         * during execution, or when specific events occur. Plugins can specify that
     355         * one or more of its PHP functions are executed at these points, using the
     356         * Action API.
     357         *
     358         * @uses WP_Plugin::add_filter() Adds an action. Parameter list and functionality are the same.
     359         *
     360         * @package WordPress
     361         * @subpackage Plugin
     362         * @since 1.2
     363         *
     364         * @param string $tag The name of the action to which the $function_to_add is hooked.
     365         * @param callback $function_to_add The name of the function you wish to be called.
     366         * @param int $priority optional. Used to specify the order in which the functions associated with a particular action are executed (default: 10). Lower numbers correspond with earlier execution, and functions with the same priority are executed in the order in which they were added to the action.
     367         * @param int $accepted_args optional. The number of arguments the function accept (default 1).
     368         */
     369        public function add_action( $tag, $function_to_add, $priority = 10, $accepted_args = 1 ) {
     370                return $this->add_filter( $tag, $function_to_add, $priority, $accepted_args );
     371        }
     372
     373        /**
     374         * Execute functions hooked on a specific action hook.
     375         *
     376         * This function invokes all functions attached to action hook $tag. It is
     377         * possible to create new action hooks by simply calling this function,
     378         * specifying the name of the new hook using the <tt>$tag</tt> parameter.
     379         *
     380         * You can pass extra arguments to the hooks, much like you can with
     381         * apply_filters().
     382         *
     383         * @see apply_filters() This function works similar with the exception that
     384         * nothing is returned and only the functions or methods are called.
     385         *
     386         * @package WordPress
     387         * @subpackage Plugin
     388         * @since 1.2
     389         *
     390         * @param string $tag The name of the action to be executed.
     391         * @param mixed $arg,... Optional additional arguments which are passed on to the functions hooked to the action.
     392         * @return null Will return null if $tag does not exist in $this->_filters array
     393         */
     394        public function do_action( $tag, $arg = '' ) {
     395
     396                if ( !isset( $this->_action_calls ) )
     397                        $this->_action_calls = array();
     398
     399                if ( !isset( $this->_action_calls[$tag] ) )
     400                        $this->_action_calls[$tag] = 1;
     401                else
     402                        ++$this->_action_calls[$tag];
     403
     404                // Do 'all' actions first
     405                if ( isset( $this->_filters['all'] ) ) {
     406                        $this->_current_filter[] = $tag;
     407                        $all_args               = func_get_args();
     408                        $this->call_all( $all_args );
     409                }
     410
     411                if ( !isset( $this->_filters[$tag] ) ) {
     412                        if ( isset( $this->_filters['all'] ) ) {
     413                                array_pop( $this->_current_filter );
     414                        }
     415
     416                        return;
     417                }
     418
     419                if ( !isset( $this->_filters['all'] ) )
     420                        $this->_current_filter[] = $tag;
     421
     422                $args = array();
     423               
     424                if ( is_array( $arg ) && 1 == count( $arg ) && isset( $arg[0] ) && is_object( $arg[0] ) )
     425                        $args[]  = & $arg[0];
     426                else
     427                        $args[]  = $arg;
     428
     429                for ( $a = 2; $a < func_num_args(); $a++ )
     430                        $args[]  = func_get_arg( $a );
     431
     432                // Sort
     433                if ( !isset( $this->_merged_filters[$tag] ) ) {
     434                        ksort( $this->_filters[$tag] );
     435                        $this->_merged_filters[$tag] = true;
     436                }
     437
     438                reset( $this->_filters[$tag] );
     439
     440                do {
     441                        foreach ( (array) current( $this->_filters[$tag] ) as $the_ ) {
     442                                if ( !is_null( $the_['function'] ) ) {
     443                                        call_user_func_array( $the_['function'], array_slice( $args, 0, (int) $the_['accepted_args'] ) );
     444                                }
     445                        }
     446                } while ( next( $this->_filters[$tag] ) !== false );
     447
     448                array_pop( $this->_current_filter );
     449        }
     450
     451        /**
     452         * Retrieve the number of times an action is fired.
     453         *
     454         * @package WordPress
     455         * @subpackage Plugin
     456         * @since 2.1
     457         * @global array $this->_action_calls Increments the amount of times action was triggered.
     458         *
     459         * @param string $tag The name of the action hook.
     460         * @return int The number of times action hook <tt>$tag</tt> is fired
     461         */
     462        public function did_action( $tag ) {
     463
     464                if ( !isset( $this->_action_calls ) || !isset( $this->_action_calls[$tag] ) )
     465                        return 0;
     466
     467                return $this->_action_calls[$tag];
     468        }
     469
     470        /**
     471         * Execute functions hooked on a specific action hook, specifying arguments in an array.
     472         *
     473         * @see do_action() This function is identical, but the arguments passed to the
     474         * functions hooked to <tt>$tag</tt> are supplied using an array.
     475         *
     476         * @package WordPress
     477         * @subpackage Plugin
     478         * @since 2.1
     479         * @global array $this->_filters Stores all of the filters
     480         * @global array $this->_action_calls Increments the amount of times action was triggered.
     481         *
     482         * @param string $tag The name of the action to be executed.
     483         * @param array $args The arguments supplied to the functions hooked to <tt>$tag</tt>
     484         * @return null Will return null if $tag does not exist in $this->_filters array
     485         */
     486        public function do_action_ref_array( $tag, $args ) {
     487
     488                if ( !isset( $this->_action_calls ) )
     489                        $this->_action_calls = array( );
     490
     491                if ( !isset( $this->_action_calls[$tag] ) )
     492                        $this->_action_calls[$tag] = 1;
     493                else
     494                        ++$this->_action_calls[$tag];
     495
     496                // Do 'all' actions first
     497                if ( isset( $this->_filters['all'] ) ) {
     498                        $this->_current_filter[] = $tag;
     499                        $all_args               = func_get_args();
     500                        $this->call_all( $all_args );
     501                }
     502
     503                if ( !isset( $this->_filters[$tag] ) ) {
     504                        if ( isset( $this->_filters['all'] ) ) {
     505                                array_pop( $this->_current_filter );
     506                        }
     507                        return;
     508                }
     509
     510                if ( !isset( $this->_filters['all'] ) )
     511                        $this->_current_filter[] = $tag;
     512
     513                // Sort
     514                if ( !isset( $this->_merged_filters[$tag] ) ) {
     515                        ksort( $this->_filters[$tag] );
     516                        $this->_merged_filters[$tag] = true;
     517                }
     518
     519                reset( $this->_filters[$tag] );
     520
     521                do {
     522                        foreach ( (array) current( $this->_filters[$tag] ) as $the_ ) {
     523                                if ( !is_null( $the_['function'] ) ) {
     524                                        call_user_func_array( $the_['function'], array_slice( $args, 0, (int) $the_['accepted_args'] ) );
     525                                }
     526                        }
     527                } while ( next( $this->_filters[$tag] ) !== false );
     528
     529                array_pop( $this->_current_filter );
     530        }
     531
     532        /**
     533         * Check if any action has been registered for a hook.
     534         *
     535         * @package WordPress
     536         * @subpackage Plugin
     537         * @since 2.5
     538         * @see has_filter() has_action() is an alias of has_filter().
     539         *
     540         * @param string $tag The name of the action hook.
     541         * @param callback $function_to_check optional.
     542         * @return mixed If $function_to_check is omitted, returns boolean for whether the hook has anything registered.
     543         *      When checking a specific function, the priority of that hook is returned, or false if the function is not attached.
     544         *      When using the $function_to_check argument, this function may return a non-boolean value that evaluates to false
     545         *      (e.g.) 0, so use the === operator for testing the return value.
     546         */
     547        public function has_action( $tag, $function_to_check = false ) {
     548                return $this->has_filter( $tag, $function_to_check );
     549        }
     550
     551        /**
     552         * Removes a function from a specified action hook.
     553         *
     554         * This function removes a function attached to a specified action hook. This
     555         * method can be used to remove default functions attached to a specific filter
     556         * hook and possibly replace them with a substitute.
     557         *
     558         * @package WordPress
     559         * @subpackage Plugin
     560         * @since 1.2
     561         *
     562         * @param string $tag The action hook to which the function to be removed is hooked.
     563         * @param callback $function_to_remove The name of the function which should be removed.
     564         * @param int $priority optional The priority of the function (default: 10).
     565         * @return boolean Whether the function is removed.
     566         */
     567        public function remove_action( $tag, $function_to_remove, $priority = 10 ) {
     568                return $this->remove_filter( $tag, $function_to_remove, $priority );
     569        }
     570
     571        /**
     572         * Remove all of the hooks from an action.
     573         *
     574         * @since 2.7
     575         *
     576         * @param string $tag The action to remove hooks from.
     577         * @param int $priority The priority number to remove them from.
     578         * @return bool True when finished.
     579         */
     580        public function remove_all_actions( $tag, $priority = false ) {
     581                return $this->remove_all_filters( $tag, $priority );
     582        }
     583
     584        /**
     585         * Set the activation hook for a plugin.
     586         *
     587         * When a plugin is activated, the action 'activate_PLUGINNAME' hook is
     588         * activated. In the name of this hook, PLUGINNAME is replaced with the name of
     589         * the plugin, including the optional subdirectory. For example, when the plugin
     590         * is located in wp-content/plugin/sampleplugin/sample.php, then the name of
     591         * this hook will become 'activate_sampleplugin/sample.php'. When the plugin
     592         * consists of only one file and is (as by default) located at
     593         * wp-content/plugin/sample.php the name of this hook will be
     594         * 'activate_sample.php'.
     595         *
     596         * @package WordPress
     597         * @subpackage Plugin
     598         * @since 2.0
     599         *
     600         * @param string $file The filename of the plugin including the path.
     601         * @param callback $function the function hooked to the 'activate_PLUGIN' action.
     602         */
     603        public function register_activation_hook( $file, $function ) {
     604                $file = plugin_basename( $file );
     605                $this->add_action( 'activate_' . $file, $function );
     606        }
     607
     608        /**
     609         * Set the deactivation hook for a plugin.
     610         *
     611         * When a plugin is deactivated, the action 'deactivate_PLUGINNAME' hook is
     612         * deactivated. In the name of this hook, PLUGINNAME is replaced with the name
     613         * of the plugin, including the optional subdirectory. For example, when the
     614         * plugin is located in wp-content/plugin/sampleplugin/sample.php, then
     615         * the name of this hook will become 'activate_sampleplugin/sample.php'.
     616         *
     617         * When the plugin consists of only one file and is (as by default) located at
     618         * wp-content/plugin/sample.php the name of this hook will be
     619         * 'activate_sample.php'.
     620         *
     621         * @package WordPress
     622         * @subpackage Plugin
     623         * @since 2.0
     624         *
     625         * @param string $file The filename of the plugin including the path.
     626         * @param callback $function the function hooked to the 'activate_PLUGIN' action.
     627         */
     628        public function register_deactivation_hook( $file, $function ) {
     629                $file = plugin_basename( $file );
     630                $this->add_action( 'deactivate_' . $file, $function );
     631        }
     632
     633        /**
     634         * Set the uninstallation hook for a plugin.
     635         *
     636         * Registers the uninstall hook that will be called when the user clicks on the
     637         * uninstall link that calls for the plugin to uninstall itself. The link won't
     638         * be active unless the plugin hooks into the action.
     639         *
     640         * The plugin should not run arbitrary code outside of functions, when
     641         * registering the uninstall hook. In order to run using the hook, the plugin
     642         * will have to be included, which means that any code laying outside of a
     643         * function will be run during the uninstall process. The plugin should not
     644         * hinder the uninstall process.
     645         *
     646         * If the plugin can not be written without running code within the plugin, then
     647         * the plugin should create a file named 'uninstall.php' in the base plugin
     648         * folder. This file will be called, if it exists, during the uninstall process
     649         * bypassing the uninstall hook. The plugin, when using the 'uninstall.php'
     650         * should always check for the 'WP_UNINSTALL_PLUGIN' constant, before
     651         * executing.
     652         *
     653         * @since 2.7
     654         *
     655         * @param string $file
     656         * @param callback $callback The callback to run when the hook is called. Must be a static method or function.
     657         */
     658        public function register_uninstall_hook( $file, $callback ) {
     659                if ( is_array( $callback ) && is_object( $callback[0] ) ) {
     660                        _doing_it_wrong( __FUNCTION__, __( 'Only a static class method or function can be used in an uninstall hook.' ), '3.1' );
     661                        return;
     662                }
     663
     664                // The option should not be autoloaded, because it is not needed in most
     665                // cases. Emphasis should be put on using the 'uninstall.php' way of
     666                // uninstalling the plugin.
     667                $file                         = plugin_basename( $file );
     668                $uninstallable_plugins        = (array) get_option( 'uninstall_plugins' );
     669                $uninstallable_plugins[$file] = $callback;
     670                update_option( 'uninstall_plugins', $uninstallable_plugins );
     671        }
     672
     673        /**
     674         * Calls the 'all' hook, which will process the functions hooked into it.
     675         *
     676         * The 'all' hook passes all of the arguments or parameters that were used for
     677         * the hook, which this function was called for.
     678         *
     679         * This function is used internally for apply_filters(), do_action(), and
     680         * do_action_ref_array() and is not meant to be used from outside those
     681         * functions. This function does not check for the existence of the all hook, so
     682         * it will fail unless the all hook exists prior to this function call.
     683         *
     684         * @package WordPress
     685         * @subpackage Plugin
     686         * @since 2.5
     687         * @access private
     688         *
     689         * @uses $this->_filters Used to process all of the functions in the 'all' hook
     690         *
     691         * @param array $args The collected parameters from the hook that was called.
     692         * @param string $hook Optional. The hook name that was used to call the 'all' hook.
     693         */
     694        private function call_all( $args ) {
     695                reset( $this->_filters['all'] );
     696                do {
     697                        foreach ( (array) current( $this->_filters['all'] ) as $the_ ) {
     698                                if ( !is_null( $the_['function'] ) ) {
     699                                        call_user_func_array( $the_['function'], $args );
     700                                }
     701                        }
     702                } while ( next( $this->_filters['all'] ) !== false );
     703        }
     704
     705        /**
     706         * Build Unique ID for storage and retrieval.
     707         *
     708         * The old way to serialize the callback caused issues and this function is the
     709         * solution. It works by checking for objects and creating an a new property in
     710         * the class to keep track of the object and new objects of the same class that
     711         * need to be added.
     712         *
     713         * It also allows for the removal of actions and filters for objects after they
     714         * change class properties. It is possible to include the property $this->_filters_id
     715         * in your class and set it to "null" or a number to bypass the workaround.
     716         * However this will prevent you from adding new classes and any new classes
     717         * will overwrite the previous hook by the same class.
     718         *
     719         * Functions and static method callbacks are just returned as strings and
     720         * shouldn't have any speed penalty.
     721         *
     722         * @package WordPress
     723         * @subpackage Plugin
     724         * @access private
     725         * @since 2.2.3
     726         * @link http://trac.wordpress.org/ticket/3875
     727         *
     728         * @global array $this->_filters Storage for all of the filters and actions
     729         * @param string $tag Used in counting how many hooks were applied
     730         * @param callback $function Used for creating unique id
     731         * @param int|bool $priority Used in counting how many hooks were applied. If === false and $function is an object reference, we return the unique id only if it already has one, false otherwise.
     732         * @return string|bool Unique ID for usage as array key or false if $priority === false and $function is an object reference, and it does not already have a unique id.
     733         */
     734        private function build_unique_id( $tag, $function, $priority ) {
     735                static $filter_id_count = 0;
     736
     737                if ( is_string( $function ) )
     738                        return $function;
     739
     740                // Closures are currently implemented as objects
     741                if ( is_object( $function ) ) {
     742                        $function = array( $function, '' );
     743                } else {
     744                        $function = (array) $function;
     745                }
     746
     747                // Object Class Calling
     748                if ( is_object( $function[0] ) ) {
     749                        if ( function_exists( 'spl_object_hash' ) ) {
     750                                return spl_object_hash( $function[0] ) . $function[1];
     751                        } else {
     752                                $obj_idx = get_class( $function[0] ) . $function[1];
     753                                if ( !isset( $function[0]->wp_filter_id ) ) {
     754                                        if ( false === $priority ) {
     755                                                return false;
     756                                        }
     757
     758                                        if ( isset( $this->_filters[$tag][$priority] ) ) {
     759                                                $obj_idx = count( (array) $this->_filters[$tag][$priority] );
     760                                        } else {
     761                                                $obj_idx = $filter_id_count;
     762                                        }
     763
     764                                        $function[0]->wp_filter_id = $filter_id_count;
     765
     766                                        ++$filter_id_count;
     767                                } else {
     768                                        $obj_idx .= $function[0]->wp_filter_id;
     769                                }
     770
     771                                return $obj_idx;
     772                        }
     773
     774                // Static Calling
     775                } elseif ( is_string( $function[0] ) ) {
     776                        return $function[0] . $function[1];
     777                }
     778        }
     779}
  • wp-includes/plugin.php

     
    1919 * @since 1.5
    2020 */
    2121
     22function wp_global_hooks() {
     23
     24        if ( ! isset( $GLOBALS['wp_global_hooks'] ) ) {
     25                $GLOBALS['wp_global_hooks']   = new WP_Plugin();
     26                $GLOBALS['wp_actions']        = &$GLOBALS['wp_global_hooks']->_action_calls;
     27                $GLOBALS['wp_filter']         = &$GLOBALS['wp_global_hooks']->_filters;
     28                $GLOBALS['merged_filters']    = &$GLOBALS['wp_global_hooks']->_merged_filters;
     29                $GLOBALS['wp_current_filter'] = &$GLOBALS['wp_global_hooks']->_current_filter;
     30        }
     31
     32        return $GLOBALS['wp_global_hooks'];
     33}
     34
    2235/**
    2336 * Hooks a function or method to a specific filter action.
    2437 *
     
    5265 * @package WordPress
    5366 * @subpackage Plugin
    5467 * @since 0.71
    55  * @global array $wp_filter Stores all of the filters added in the form of
    56  *      wp_filter['tag']['array of priorities']['array of functions serialized']['array of ['array (functions, accepted_args)']']
    57  * @global array $merged_filters Tracks the tags that need to be merged for later. If the hook is added, it doesn't need to run through that process.
    5868 *
    5969 * @param string $tag The name of the filter to hook the $function_to_add to.
    6070 * @param callback $function_to_add The name of the function to be called when the filter is applied.
     
    6272 * @param int $accepted_args optional. The number of arguments the function accept (default 1).
    6373 * @return boolean true
    6474 */
    65 function add_filter($tag, $function_to_add, $priority = 10, $accepted_args = 1) {
    66         global $wp_filter, $merged_filters;
    67 
    68         $idx = _wp_filter_build_unique_id($tag, $function_to_add, $priority);
    69         $wp_filter[$tag][$priority][$idx] = array('function' => $function_to_add, 'accepted_args' => $accepted_args);
    70         unset( $merged_filters[ $tag ] );
    71         return true;
     75function add_filter( $tag, $function_to_add, $priority = 10, $accepted_args = 1 ) {
     76        return wp_global_hooks()->add_filter( $tag, $function_to_add, $priority, $accepted_args );
    7277}
    7378
    7479/**
     
    7782 * @package WordPress
    7883 * @subpackage Plugin
    7984 * @since 2.5
    80  * @global array $wp_filter Stores all of the filters
    8185 *
    8286 * @param string $tag The name of the filter hook.
    8387 * @param callback $function_to_check optional.
     
    8690 *      When using the $function_to_check argument, this function may return a non-boolean value that evaluates to false
    8791 *      (e.g.) 0, so use the === operator for testing the return value.
    8892 */
    89 function has_filter($tag, $function_to_check = false) {
    90         global $wp_filter;
    91 
    92         $has = !empty($wp_filter[$tag]);
    93         if ( false === $function_to_check || false == $has )
    94                 return $has;
    95 
    96         if ( !$idx = _wp_filter_build_unique_id($tag, $function_to_check, false) )
    97                 return false;
    98 
    99         foreach ( (array) array_keys($wp_filter[$tag]) as $priority ) {
    100                 if ( isset($wp_filter[$tag][$priority][$idx]) )
    101                         return $priority;
    102         }
    103 
    104         return false;
     93function has_filter( $tag, $function_to_check = false ) {
     94        return wp_global_hooks()->has_filter( $tag, $function_to_check );
    10595}
    10696
    10797/**
     
    125115 * @package WordPress
    126116 * @subpackage Plugin
    127117 * @since 0.71
    128  * @global array $wp_filter Stores all of the filters
    129  * @global array $merged_filters Merges the filter hooks using this function.
    130  * @global array $wp_current_filter stores the list of current filters with the current one last
    131118 *
    132119 * @param string $tag The name of the filter hook.
    133120 * @param mixed $value The value on which the filters hooked to <tt>$tag</tt> are applied on.
    134121 * @param mixed $var,... Additional variables passed to the functions hooked to <tt>$tag</tt>.
    135122 * @return mixed The filtered value after all hooked functions are applied to it.
    136123 */
    137 function apply_filters($tag, $value) {
    138         global $wp_filter, $merged_filters, $wp_current_filter;
     124function apply_filters( $tag, $value ) {
    139125
    140126        $args = array();
    141127
    142128        // Do 'all' actions first
    143         if ( isset($wp_filter['all']) ) {
    144                 $wp_current_filter[] = $tag;
    145                 $args = func_get_args();
    146                 _wp_call_all_hook($args);
     129        if ( isset( wp_global_hooks()->_filters['all'] ) ) {
     130                wp_global_hooks()->_current_filter[] = $tag;
     131                $args                   = func_get_args();
     132                wp_global_hooks()->call_all( $args );
    147133        }
    148134
    149         if ( !isset($wp_filter[$tag]) ) {
    150                 if ( isset($wp_filter['all']) )
    151                         array_pop($wp_current_filter);
     135        if ( !isset( wp_global_hooks()->_filters[$tag] ) ) {
     136                if ( isset( wp_global_hooks()->_filters['all'] ) ) {
     137                        array_pop( wp_global_hooks()->_current_filter );
     138                }
     139
    152140                return $value;
    153141        }
    154142
    155         if ( !isset($wp_filter['all']) )
    156                 $wp_current_filter[] = $tag;
     143        if ( !isset( wp_global_hooks()->_filters['all'] ) )
     144                wp_global_hooks()->_current_filter[] = $tag;
    157145
    158146        // Sort
    159         if ( !isset( $merged_filters[ $tag ] ) ) {
    160                 ksort($wp_filter[$tag]);
    161                 $merged_filters[ $tag ] = true;
     147        if ( !isset( wp_global_hooks()->_merged_filters[$tag] ) ) {
     148                ksort( wp_global_hooks()->_filters[$tag] );
     149                wp_global_hooks()->_merged_filters[$tag] = true;
    162150        }
    163151
    164         reset( $wp_filter[ $tag ] );
     152        reset( wp_global_hooks()->_filters[$tag] );
    165153
    166         if ( empty($args) )
     154        if ( empty( $args ) )
    167155                $args = func_get_args();
    168156
    169157        do {
    170                 foreach( (array) current($wp_filter[$tag]) as $the_ )
    171                         if ( !is_null($the_['function']) ){
     158                foreach ( (array) current( wp_global_hooks()->_filters[$tag] ) as $the_ ) {
     159                        if ( !is_null( $the_['function'] ) ) {
    172160                                $args[1] = $value;
    173                                 $value = call_user_func_array($the_['function'], array_slice($args, 1, (int) $the_['accepted_args']));
     161                                $value   = call_user_func_array( $the_['function'], array_slice( $args, 1, (int) $the_['accepted_args'] ) );
    174162                        }
     163                }
     164        } while ( next( wp_global_hooks()->_filters[$tag] ) !== false );
    175165
    176         } while ( next($wp_filter[$tag]) !== false );
     166        array_pop( wp_global_hooks()->_current_filter );
    177167
    178         array_pop( $wp_current_filter );
    179 
    180168        return $value;
    181169}
    182170
     
    189177 * @package WordPress
    190178 * @subpackage Plugin
    191179 * @since 3.0.0
    192  * @global array $wp_filter Stores all of the filters
    193  * @global array $merged_filters Merges the filter hooks using this function.
    194  * @global array $wp_current_filter stores the list of current filters with the current one last
    195180 *
    196181 * @param string $tag The name of the filter hook.
    197182 * @param array $args The arguments supplied to the functions hooked to <tt>$tag</tt>
    198183 * @return mixed The filtered value after all hooked functions are applied to it.
    199184 */
    200 function apply_filters_ref_array($tag, $args) {
    201         global $wp_filter, $merged_filters, $wp_current_filter;
    202 
    203         // Do 'all' actions first
    204         if ( isset($wp_filter['all']) ) {
    205                 $wp_current_filter[] = $tag;
    206                 $all_args = func_get_args();
    207                 _wp_call_all_hook($all_args);
    208         }
    209 
    210         if ( !isset($wp_filter[$tag]) ) {
    211                 if ( isset($wp_filter['all']) )
    212                         array_pop($wp_current_filter);
    213                 return $args[0];
    214         }
    215 
    216         if ( !isset($wp_filter['all']) )
    217                 $wp_current_filter[] = $tag;
    218 
    219         // Sort
    220         if ( !isset( $merged_filters[ $tag ] ) ) {
    221                 ksort($wp_filter[$tag]);
    222                 $merged_filters[ $tag ] = true;
    223         }
    224 
    225         reset( $wp_filter[ $tag ] );
    226 
    227         do {
    228                 foreach( (array) current($wp_filter[$tag]) as $the_ )
    229                         if ( !is_null($the_['function']) )
    230                                 $args[0] = call_user_func_array($the_['function'], array_slice($args, 0, (int) $the_['accepted_args']));
    231 
    232         } while ( next($wp_filter[$tag]) !== false );
    233 
    234         array_pop( $wp_current_filter );
    235 
    236         return $args[0];
     185function apply_filters_ref_array( $tag, $args ) {
     186        return wp_global_hooks()->apply_filters_ref_array( $tag, $args );
    237187}
    238188
    239189/**
     
    258208 * @return boolean Whether the function existed before it was removed.
    259209 */
    260210function remove_filter( $tag, $function_to_remove, $priority = 10 ) {
    261         $function_to_remove = _wp_filter_build_unique_id($tag, $function_to_remove, $priority);
    262 
    263         $r = isset($GLOBALS['wp_filter'][$tag][$priority][$function_to_remove]);
    264 
    265         if ( true === $r) {
    266                 unset($GLOBALS['wp_filter'][$tag][$priority][$function_to_remove]);
    267                 if ( empty($GLOBALS['wp_filter'][$tag][$priority]) )
    268                         unset($GLOBALS['wp_filter'][$tag][$priority]);
    269                 unset($GLOBALS['merged_filters'][$tag]);
    270         }
    271 
    272         return $r;
     211        return wp_global_hooks()->remove_filter( $tag, $function_to_remove, $priority );
    273212}
    274213
    275214/**
     
    282221 * @return bool True when finished.
    283222 */
    284223function remove_all_filters($tag, $priority = false) {
    285         global $wp_filter, $merged_filters;
    286 
    287         if( isset($wp_filter[$tag]) ) {
    288                 if( false !== $priority && isset($wp_filter[$tag][$priority]) )
    289                         unset($wp_filter[$tag][$priority]);
    290                 else
    291                         unset($wp_filter[$tag]);
    292         }
    293 
    294         if( isset($merged_filters[$tag]) )
    295                 unset($merged_filters[$tag]);
    296 
    297         return true;
     224        return wp_global_hooks()->remove_all_filters( $tag, $priority );
    298225}
    299226
    300227/**
     
    307234 * @return string Hook name of the current filter or action.
    308235 */
    309236function current_filter() {
    310         global $wp_current_filter;
    311         return end( $wp_current_filter );
     237        return wp_global_hooks()->current_filter();
    312238}
    313239
    314240/**
     
    331257 * @param int $accepted_args optional. The number of arguments the function accept (default 1).
    332258 */
    333259function add_action($tag, $function_to_add, $priority = 10, $accepted_args = 1) {
    334         return add_filter($tag, $function_to_add, $priority, $accepted_args);
     260        return wp_global_hooks()->add_action($tag, $function_to_add, $priority, $accepted_args );
    335261}
    336262
    337263/**
     
    350276 * @package WordPress
    351277 * @subpackage Plugin
    352278 * @since 1.2
    353  * @global array $wp_filter Stores all of the filters
    354  * @global array $wp_actions Increments the amount of times action was triggered.
    355279 *
    356280 * @param string $tag The name of the action to be executed.
    357281 * @param mixed $arg,... Optional additional arguments which are passed on to the functions hooked to the action.
    358282 * @return null Will return null if $tag does not exist in $wp_filter array
    359283 */
    360284function do_action($tag, $arg = '') {
    361         global $wp_filter, $wp_actions, $merged_filters, $wp_current_filter;
     285        if ( !isset( wp_global_hooks()->_action_calls ) )
     286                wp_global_hooks()->_action_calls = array();
    362287
    363         if ( ! isset($wp_actions) )
    364                 $wp_actions = array();
    365 
    366         if ( ! isset($wp_actions[$tag]) )
    367                 $wp_actions[$tag] = 1;
     288        if ( !isset( wp_global_hooks()->_action_calls[$tag] ) )
     289                wp_global_hooks()->_action_calls[$tag] = 1;
    368290        else
    369                 ++$wp_actions[$tag];
     291                ++wp_global_hooks()->_action_calls[$tag];
    370292
    371293        // Do 'all' actions first
    372         if ( isset($wp_filter['all']) ) {
    373                 $wp_current_filter[] = $tag;
    374                 $all_args = func_get_args();
    375                 _wp_call_all_hook($all_args);
     294        if ( isset( wp_global_hooks()->_filters['all'] ) ) {
     295                wp_global_hooks()->_current_filter[] = $tag;
     296                $all_args               = func_get_args();
     297                wp_global_hooks()->call_all( $all_args );
    376298        }
    377299
    378         if ( !isset($wp_filter[$tag]) ) {
    379                 if ( isset($wp_filter['all']) )
    380                         array_pop($wp_current_filter);
     300        if ( !isset( wp_global_hooks()->_filters[$tag] ) ) {
     301                if ( isset( wp_global_hooks()->_filters['all'] ) ) {
     302                        array_pop( wp_global_hooks()->_current_filter );
     303                }
     304
    381305                return;
    382306        }
    383307
    384         if ( !isset($wp_filter['all']) )
    385                 $wp_current_filter[] = $tag;
     308        if ( !isset( wp_global_hooks()->_filters['all'] ) )
     309                wp_global_hooks()->_current_filter[] = $tag;
    386310
    387311        $args = array();
    388         if ( is_array($arg) && 1 == count($arg) && isset($arg[0]) && is_object($arg[0]) ) // array(&$this)
    389                 $args[] =& $arg[0];
     312
     313        if ( is_array( $arg ) && 1 == count( $arg ) && isset( $arg[0] ) && is_object( $arg[0] ) )
     314                $args[]  = & $arg[0];
    390315        else
    391                 $args[] = $arg;
     316                $args[]  = $arg;
     317
    392318        for ( $a = 2; $a < func_num_args(); $a++ )
    393                 $args[] = func_get_arg($a);
     319                $args[]  = func_get_arg( $a );
    394320
    395321        // Sort
    396         if ( !isset( $merged_filters[ $tag ] ) ) {
    397                 ksort($wp_filter[$tag]);
    398                 $merged_filters[ $tag ] = true;
     322        if ( !isset( wp_global_hooks()->_merged_filters[$tag] ) ) {
     323                ksort( wp_global_hooks()->_filters[$tag] );
     324                wp_global_hooks()->_merged_filters[$tag] = true;
    399325        }
    400326
    401         reset( $wp_filter[ $tag ] );
     327        reset( wp_global_hooks()->_filters[$tag] );
    402328
    403329        do {
    404                 foreach ( (array) current($wp_filter[$tag]) as $the_ )
    405                         if ( !is_null($the_['function']) )
    406                                 call_user_func_array($the_['function'], array_slice($args, 0, (int) $the_['accepted_args']));
     330                foreach ( (array) current( wp_global_hooks()->_filters[$tag] ) as $the_ ) {
     331                        if ( !is_null( $the_['function'] ) ) {
     332                                call_user_func_array( $the_['function'], array_slice( $args, 0, (int) $the_['accepted_args'] ) );
     333                        }
     334                }
     335        } while ( next( wp_global_hooks()->_filters[$tag] ) !== false );
    407336
    408         } while ( next($wp_filter[$tag]) !== false );
    409 
    410         array_pop($wp_current_filter);
     337        array_pop( wp_global_hooks()->_current_filter );
    411338}
    412339
    413340/**
     
    422349 * @return int The number of times action hook <tt>$tag</tt> is fired
    423350 */
    424351function did_action($tag) {
    425         global $wp_actions;
    426 
    427         if ( ! isset( $wp_actions ) || ! isset( $wp_actions[$tag] ) )
    428                 return 0;
    429 
    430         return $wp_actions[$tag];
     352        return wp_global_hooks()->did_action( $tag );
    431353}
    432354
    433355/**
     
    447369 * @return null Will return null if $tag does not exist in $wp_filter array
    448370 */
    449371function do_action_ref_array($tag, $args) {
    450         global $wp_filter, $wp_actions, $merged_filters, $wp_current_filter;
    451 
    452         if ( ! isset($wp_actions) )
    453                 $wp_actions = array();
    454 
    455         if ( ! isset($wp_actions[$tag]) )
    456                 $wp_actions[$tag] = 1;
    457         else
    458                 ++$wp_actions[$tag];
    459 
    460         // Do 'all' actions first
    461         if ( isset($wp_filter['all']) ) {
    462                 $wp_current_filter[] = $tag;
    463                 $all_args = func_get_args();
    464                 _wp_call_all_hook($all_args);
    465         }
    466 
    467         if ( !isset($wp_filter[$tag]) ) {
    468                 if ( isset($wp_filter['all']) )
    469                         array_pop($wp_current_filter);
    470                 return;
    471         }
    472 
    473         if ( !isset($wp_filter['all']) )
    474                 $wp_current_filter[] = $tag;
    475 
    476         // Sort
    477         if ( !isset( $merged_filters[ $tag ] ) ) {
    478                 ksort($wp_filter[$tag]);
    479                 $merged_filters[ $tag ] = true;
    480         }
    481 
    482         reset( $wp_filter[ $tag ] );
    483 
    484         do {
    485                 foreach( (array) current($wp_filter[$tag]) as $the_ )
    486                         if ( !is_null($the_['function']) )
    487                                 call_user_func_array($the_['function'], array_slice($args, 0, (int) $the_['accepted_args']));
    488 
    489         } while ( next($wp_filter[$tag]) !== false );
    490 
    491         array_pop($wp_current_filter);
     372        wp_global_hooks()->do_action_ref_array( $tag, $args );
    492373}
    493374
    494375/**
     
    507388 *      (e.g.) 0, so use the === operator for testing the return value.
    508389 */
    509390function has_action($tag, $function_to_check = false) {
    510         return has_filter($tag, $function_to_check);
     391        return wp_global_hooks()->has_action( $tag, $function_to_check );
    511392}
    512393
    513394/**
     
    527408 * @return boolean Whether the function is removed.
    528409 */
    529410function remove_action( $tag, $function_to_remove, $priority = 10 ) {
    530         return remove_filter( $tag, $function_to_remove, $priority );
     411        return wp_global_hooks()->remove_filter( $tag, $function_to_remove, $priority );
    531412}
    532413
    533414/**
     
    540421 * @return bool True when finished.
    541422 */
    542423function remove_all_actions($tag, $priority = false) {
    543         return remove_all_filters($tag, $priority);
     424        return wp_global_hooks()->remove_all_filters( $tag, $priority );
    544425}
    545426
    546427//
     
    710591 * @param string $hook Optional. The hook name that was used to call the 'all' hook.
    711592 */
    712593function _wp_call_all_hook($args) {
    713         global $wp_filter;
    714 
    715         reset( $wp_filter['all'] );
    716         do {
    717                 foreach( (array) current($wp_filter['all']) as $the_ )
    718                         if ( !is_null($the_['function']) )
    719                                 call_user_func_array($the_['function'], $args);
    720 
    721         } while ( next($wp_filter['all']) !== false );
     594        return wp_global_hooks()->call_all( $args );
    722595}
    723596
    724597/**
     
    751624 * @return string|bool Unique ID for usage as array key or false if $priority === false and $function is an object reference, and it does not already have a unique id.
    752625 */
    753626function _wp_filter_build_unique_id($tag, $function, $priority) {
    754         global $wp_filter;
    755         static $filter_id_count = 0;
    756 
    757         if ( is_string($function) )
    758                 return $function;
    759 
    760         if ( is_object($function) ) {
    761                 // Closures are currently implemented as objects
    762                 $function = array( $function, '' );
    763         } else {
    764                 $function = (array) $function;
    765         }
    766 
    767         if (is_object($function[0]) ) {
    768                 // Object Class Calling
    769                 if ( function_exists('spl_object_hash') ) {
    770                         return spl_object_hash($function[0]) . $function[1];
    771                 } else {
    772                         $obj_idx = get_class($function[0]).$function[1];
    773                         if ( !isset($function[0]->wp_filter_id) ) {
    774                                 if ( false === $priority )
    775                                         return false;
    776                                 $obj_idx .= isset($wp_filter[$tag][$priority]) ? count((array)$wp_filter[$tag][$priority]) : $filter_id_count;
    777                                 $function[0]->wp_filter_id = $filter_id_count;
    778                                 ++$filter_id_count;
    779                         } else {
    780                                 $obj_idx .= $function[0]->wp_filter_id;
    781                         }
    782 
    783                         return $obj_idx;
    784                 }
    785         } else if ( is_string($function[0]) ) {
    786                 // Static Calling
    787                 return $function[0].$function[1];
    788         }
     627        return wp_global_hooks()->build_unique_id( $tag, $function, $priority );
    789628}
  • wp-settings.php

     
    6161wp_set_lang_dir();
    6262
    6363// Load early WordPress files.
    64 require( ABSPATH . WPINC . '/compat.php' );
    65 require( ABSPATH . WPINC . '/functions.php' );
    66 require( ABSPATH . WPINC . '/class-wp.php' );
    67 require( ABSPATH . WPINC . '/class-wp-error.php' );
    68 require( ABSPATH . WPINC . '/plugin.php' );
    69 require( ABSPATH . WPINC . '/pomo/mo.php' );
     64require( ABSPATH . WPINC . '/compat.php'          );
     65require( ABSPATH . WPINC . '/functions.php'       );
     66require( ABSPATH . WPINC . '/class-wp.php'        );
     67require( ABSPATH . WPINC . '/class-wp-error.php'  );
     68require( ABSPATH . WPINC . '/class-wp-plugin.php' );
     69require( ABSPATH . WPINC . '/plugin.php'          );
     70require( ABSPATH . WPINC . '/pomo/mo.php'         );
    7071
    7172// Include the wpdb class and, if present, a db.php database drop-in.
    7273require_wp_db();