WordPress:如何获取“ the_content”过滤器的所有注册功能

WordPress: How do I get all the registered functions for 'the_content' filter

我对WordPress有疑问,特别是3.0版及更高版本。

有谁知道如何获取将被应用或"注册"到the_content过滤器的所有函数的数组或列表?

这个想法是生成一个可能的功能的复选框列表,这些功能可以从过滤器中删除,例如wpautop。 我知道如何从带有硬编码标签的过滤器中删除功能,但我希望创建一个更动态的解决方案。

如果有人对这是否可行以及如何实现有任何想法,我将非常感兴趣。 谢谢。


从过滤器阵列打印的简单功能?

1
2
3
4
5
6
7
8
function print_filters_for( $hook = '' ) {
    global $wp_filter;
    if( empty( $hook ) || !isset( $wp_filter[$hook] ) )
        return;

    print '[cc]';
    print_r( $wp_filter[$hook] );
    print '

';
}

在需要的地方调用它。

1
print_filters_for( 'the_content' );


这是一个更高级的示例,除了$wp_filter数组中的数据外,还将显示钩子所在的文件的路径以及定义函数的代码行。

要获取挂接到特定动作(或过滤器)上的基本功能列表,从过滤器数组中获取项目就足够了,但是由于可以通过各种方式(作为类方法或闭包)附加功能,因此该列表将包含大量无关数据,其中包括以字符串形式显示的对象。本示例将仅按优先级显示相关数据:

  • 函数名称(取决于回调语法):

    • 函数回调:'function_name'
    • 对象方法:array( $object, 'function_name' )
    • 静态类方法:array( 'class_name', 'function_name' )'class_name::function_name'
    • 关闭:function() {}
    • 相对静态类方法:array( 'class_name', 'parent::function_name' )
  • 接受的参数
  • 文件名
  • 起跑线
  • ID
  • 优先
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
function list_hooks( $hook = '' ) {
    global $wp_filter;

    if ( isset( $wp_filter[$hook]->callbacks ) ) {      
        array_walk( $wp_filter[$hook]->callbacks, function( $callbacks, $priority ) use ( &$hooks ) {          
            foreach ( $callbacks as $id => $callback )
                $hooks[] = array_merge( [ 'id' => $id, 'priority' => $priority ], $callback );
        });        
    } else {
        return [];
    }

    foreach( $hooks as &$item ) {
        // skip if callback does not exist
        if ( !is_callable( $item['function'] ) ) continue;

        // function name as string or static class method eg. 'Foo::Bar'
        if ( is_string( $item['function'] ) ) {
            $ref = strpos( $item['function'], '::' ) ? new ReflectionClass( strstr( $item['function'], '::', true ) ) : new ReflectionFunction( $item['function'] );
            $item['file'] = $ref->getFileName();
            $item['line'] = get_class( $ref ) == 'ReflectionFunction'
                ? $ref->getStartLine()
                : $ref->getMethod( substr( $item['function'], strpos( $item['function'], '::' ) + 2 ) )->getStartLine();

        // array( object, method ), array( string object, method ), array( string object, string 'parent::method' )
        } elseif ( is_array( $item['function'] ) ) {

            $ref = new ReflectionClass( $item['function'][0] );

            // $item['function'][0] is a reference to existing object
            $item['function'] = array(
                is_object( $item['function'][0] ) ? get_class( $item['function'][0] ) : $item['function'][0],
                $item['function'][1]
            );
            $item['file'] = $ref->getFileName();
            $item['line'] = strpos( $item['function'][1], '::' )
                ? $ref->getParentClass()->getMethod( substr( $item['function'][1], strpos( $item['function'][1], '::' ) + 2 ) )->getStartLine()
                : $ref->getMethod( $item['function'][1] )->getStartLine();

        // closures
        } elseif ( is_callable( $item['function'] ) ) {    
            $ref = new ReflectionFunction( $item['function'] );        
            $item['function'] = get_class( $item['function'] );
            $item['file'] = $ref->getFileName();
            $item['line'] = $ref->getStartLine();

        }      
    }

    return $hooks;
}

由于可以在整个运行时期间添加和删除挂钩,因此输出取决于调用函数的时间点(wp_footer操作是获取完整列表的好地方)

the_content过滤器的print_r示例:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
Array
(
    [0] => Array
        (
            [id] => 000000004c8a4a660000000011808a14run_shortcode
            [priority] => 8
            [function] => Array
                (
                    [0] => WP_Embed
                    [1] => run_shortcode
                )

            [accepted_args] => 1
            [file] => C:\\xampp\\htdocs\\wordpress\\wp-includes\\class-wp-embed.php
            [line] => 58
        )

    [1] => Array
        (
            [id] => wptexturize
            [priority] => 10
            [function] => wptexturize
            [accepted_args] => 1
            [file] => C:\\xampp\\htdocs\\wordpress\\wp-includes\\formatting.php
            [line] => 41
        )

    [2] => Array
        (
            [id] => 0000000006c5dc6d0000000064b1bc8e
            [priority] => 10
            [function] => Closure
            [accepted_args] => 1
            [file] => C:\\xampp\\htdocs\\wordpress\\wp-content\\plugins\\plugin\\plugin.php
            [line] => 16
        )

    .....

编辑:2017-05-05

  • 适用于WP_Hook
  • 增加优先级
  • 修复:如果回调不存在,则会引发错误,尽管WordPress也会对此发出警告
  • 固定:具有相同ID但优先级不同的钩子将覆盖前一个钩子


基于print_filters_for的相同思想,为不仅需要打印而且还需要返回的用户提供了扩展功能:

1
2
3
4
5
6
7
8
9
10
11
12
function filters_for( $hook = '', $return = FALSE ) {
    global $wp_filter;
    if( empty( $hook ) || !isset( $wp_filter[$hook] ) )
        return;

    if( $return ) {
        ob_start();
    }

    print '[cc]';
    print_r( $wp_filter[$hook] );
    print '

';

if($ return){
返回ob_get_flush();
}
}

输出:

1
filters_for( 'the_content' );

获取并输出:

1
2
$output = filters_for( 'the_content', true );
echo $output;