]> scripts.mit.edu Git - autoinstallsdev/mediawiki.git/blob - vendor/wikimedia/remex-html/RemexHtml/TreeBuilder/DispatchTracer.php
MediaWiki 1.30.2
[autoinstallsdev/mediawiki.git] / vendor / wikimedia / remex-html / RemexHtml / TreeBuilder / DispatchTracer.php
1 <?php
2
3 namespace RemexHtml\TreeBuilder;
4 use RemexHtml\Tokenizer\TokenHandler;
5 use RemexHtml\Tokenizer\Tokenizer;
6 use RemexHtml\Tokenizer\Attributes;
7
8 /**
9  * This is a debugging helper class which calls a callback function with a
10  * descriptive message each time a token event comes from the Tokenizer. The
11  * messages include information about the current state and transitions of the
12  * Dispatcher which is the next stage in the pipeline.
13  */
14 class DispatchTracer implements TokenHandler {
15         private $input;
16         private $dispatcher;
17         private $callback;
18
19         function __construct( $input, Dispatcher $dispatcher, callable $callback ) {
20                 $this->input = $input;
21                 $this->dispatcher = $dispatcher;
22                 $this->callback = $callback;
23         }
24
25         private function trace( $msg ) {
26                 call_user_func( $this->callback, "[Dispatch] $msg" );
27         }
28
29         private function excerpt( $text ) {
30                 if ( strlen( $text ) > 20 ) {
31                         $text = substr( $text, 0, 20 ) . '...';
32                 }
33                 return str_replace( "\n", "\\n", $text );
34         }
35
36         private function wrap( $funcName, $sourceStart, $sourceLength, $args ) {
37                 $prevHandler = $this->getHandlerName();
38                 $excerpt = $this->excerpt( substr( $this->input, $sourceStart, $sourceLength ) );
39                 $msg = "$funcName $prevHandler \"$excerpt\"";
40                 $this->trace( $msg );
41                 call_user_func_array( [ $this->dispatcher, $funcName ], $args );
42                 $handler = $this->getHandlerName();
43                 if ( $prevHandler !== $handler ) {
44                         $this->trace( "$prevHandler -> $handler" );
45                 }
46         }
47
48         private function getHandlerName() {
49                 $handler = $this->dispatcher->getHandler();
50                 $name = $handler ? get_class( $handler ) : 'NULL';
51                 $slashPos = strrpos( $name, '\\' );
52                 if ( $slashPos === false ) {
53                         return $name;
54                 } else {
55                         return substr( $name, $slashPos + 1 );
56                 }
57         }
58
59         public function startDocument( Tokenizer $tokenizer, $ns, $name ) {
60                 $prevHandler = $this->getHandlerName();
61                 $nsMsg = $ns === null ? 'NULL' : $ns;
62                 $nameMsg = $name === null ? 'NULL' : $name;
63                 $this->trace( "startDocument $prevHandler $nsMsg $nameMsg" );
64                 $this->dispatcher->startDocument( $tokenizer, $ns, $name );
65                 $handler = $this->getHandlerName();
66                 if ( $prevHandler !== $handler ) {
67                         $this->trace( "$prevHandler -> $handler" );
68                 }
69         }
70
71         public function endDocument( $pos ) {
72                 $this->wrap( __FUNCTION__, $pos, 0, func_get_args() );
73         }
74
75         public function error( $text, $pos ) {
76                 $handler = $this->getHandlerName();
77                 $this->trace( "error $handler \"$text\"" );
78                 $this->dispatcher->error( $text, $pos );
79         }
80
81         public function characters( $text, $start, $length, $sourceStart, $sourceLength ) {
82                 $this->wrap( __FUNCTION__, $sourceStart, $sourceLength, func_get_args() );
83         }
84
85         public function startTag( $name, Attributes $attrs, $selfClose, $sourceStart, $sourceLength ) {
86                 $this->wrap( __FUNCTION__, $sourceStart, $sourceLength, func_get_args() );
87         }
88
89         public function endTag( $name, $sourceStart, $sourceLength ) {
90                 $this->wrap( __FUNCTION__, $sourceStart, $sourceLength, func_get_args() );
91         }
92
93         public function doctype( $name, $public, $system, $quirks, $sourceStart, $sourceLength ) {
94                 $this->wrap( __FUNCTION__, $sourceStart, $sourceLength, func_get_args() );
95         }
96
97         public function comment( $text, $sourceStart, $sourceLength ) {
98                 $this->wrap( __FUNCTION__, $sourceStart, $sourceLength, func_get_args() );
99         }
100 }