diff options
Diffstat (limited to 'inc/3rdparty/htmlpurifier/HTMLPurifier/Injector')
7 files changed, 0 insertions, 832 deletions
diff --git a/inc/3rdparty/htmlpurifier/HTMLPurifier/Injector/AutoParagraph.php b/inc/3rdparty/htmlpurifier/HTMLPurifier/Injector/AutoParagraph.php deleted file mode 100644 index d3ec44f1..00000000 --- a/inc/3rdparty/htmlpurifier/HTMLPurifier/Injector/AutoParagraph.php +++ /dev/null | |||
@@ -1,356 +0,0 @@ | |||
1 | <?php | ||
2 | |||
3 | /** | ||
4 | * Injector that auto paragraphs text in the root node based on | ||
5 | * double-spacing. | ||
6 | * @todo Ensure all states are unit tested, including variations as well. | ||
7 | * @todo Make a graph of the flow control for this Injector. | ||
8 | */ | ||
9 | class HTMLPurifier_Injector_AutoParagraph extends HTMLPurifier_Injector | ||
10 | { | ||
11 | /** | ||
12 | * @type string | ||
13 | */ | ||
14 | public $name = 'AutoParagraph'; | ||
15 | |||
16 | /** | ||
17 | * @type array | ||
18 | */ | ||
19 | public $needed = array('p'); | ||
20 | |||
21 | /** | ||
22 | * @return HTMLPurifier_Token_Start | ||
23 | */ | ||
24 | private function _pStart() | ||
25 | { | ||
26 | $par = new HTMLPurifier_Token_Start('p'); | ||
27 | $par->armor['MakeWellFormed_TagClosedError'] = true; | ||
28 | return $par; | ||
29 | } | ||
30 | |||
31 | /** | ||
32 | * @param HTMLPurifier_Token_Text $token | ||
33 | */ | ||
34 | public function handleText(&$token) | ||
35 | { | ||
36 | $text = $token->data; | ||
37 | // Does the current parent allow <p> tags? | ||
38 | if ($this->allowsElement('p')) { | ||
39 | if (empty($this->currentNesting) || strpos($text, "\n\n") !== false) { | ||
40 | // Note that we have differing behavior when dealing with text | ||
41 | // in the anonymous root node, or a node inside the document. | ||
42 | // If the text as a double-newline, the treatment is the same; | ||
43 | // if it doesn't, see the next if-block if you're in the document. | ||
44 | |||
45 | $i = $nesting = null; | ||
46 | if (!$this->forwardUntilEndToken($i, $current, $nesting) && $token->is_whitespace) { | ||
47 | // State 1.1: ... ^ (whitespace, then document end) | ||
48 | // ---- | ||
49 | // This is a degenerate case | ||
50 | } else { | ||
51 | if (!$token->is_whitespace || $this->_isInline($current)) { | ||
52 | // State 1.2: PAR1 | ||
53 | // ---- | ||
54 | |||
55 | // State 1.3: PAR1\n\nPAR2 | ||
56 | // ------------ | ||
57 | |||
58 | // State 1.4: <div>PAR1\n\nPAR2 (see State 2) | ||
59 | // ------------ | ||
60 | $token = array($this->_pStart()); | ||
61 | $this->_splitText($text, $token); | ||
62 | } else { | ||
63 | // State 1.5: \n<hr /> | ||
64 | // -- | ||
65 | } | ||
66 | } | ||
67 | } else { | ||
68 | // State 2: <div>PAR1... (similar to 1.4) | ||
69 | // ---- | ||
70 | |||
71 | // We're in an element that allows paragraph tags, but we're not | ||
72 | // sure if we're going to need them. | ||
73 | if ($this->_pLookAhead()) { | ||
74 | // State 2.1: <div>PAR1<b>PAR1\n\nPAR2 | ||
75 | // ---- | ||
76 | // Note: This will always be the first child, since any | ||
77 | // previous inline element would have triggered this very | ||
78 | // same routine, and found the double newline. One possible | ||
79 | // exception would be a comment. | ||
80 | $token = array($this->_pStart(), $token); | ||
81 | } else { | ||
82 | // State 2.2.1: <div>PAR1<div> | ||
83 | // ---- | ||
84 | |||
85 | // State 2.2.2: <div>PAR1<b>PAR1</b></div> | ||
86 | // ---- | ||
87 | } | ||
88 | } | ||
89 | // Is the current parent a <p> tag? | ||
90 | } elseif (!empty($this->currentNesting) && | ||
91 | $this->currentNesting[count($this->currentNesting) - 1]->name == 'p') { | ||
92 | // State 3.1: ...<p>PAR1 | ||
93 | // ---- | ||
94 | |||
95 | // State 3.2: ...<p>PAR1\n\nPAR2 | ||
96 | // ------------ | ||
97 | $token = array(); | ||
98 | $this->_splitText($text, $token); | ||
99 | // Abort! | ||
100 | } else { | ||
101 | // State 4.1: ...<b>PAR1 | ||
102 | // ---- | ||
103 | |||
104 | // State 4.2: ...<b>PAR1\n\nPAR2 | ||
105 | // ------------ | ||
106 | } | ||
107 | } | ||
108 | |||
109 | /** | ||
110 | * @param HTMLPurifier_Token $token | ||
111 | */ | ||
112 | public function handleElement(&$token) | ||
113 | { | ||
114 | // We don't have to check if we're already in a <p> tag for block | ||
115 | // tokens, because the tag would have been autoclosed by MakeWellFormed. | ||
116 | if ($this->allowsElement('p')) { | ||
117 | if (!empty($this->currentNesting)) { | ||
118 | if ($this->_isInline($token)) { | ||
119 | // State 1: <div>...<b> | ||
120 | // --- | ||
121 | // Check if this token is adjacent to the parent token | ||
122 | // (seek backwards until token isn't whitespace) | ||
123 | $i = null; | ||
124 | $this->backward($i, $prev); | ||
125 | |||
126 | if (!$prev instanceof HTMLPurifier_Token_Start) { | ||
127 | // Token wasn't adjacent | ||
128 | if ($prev instanceof HTMLPurifier_Token_Text && | ||
129 | substr($prev->data, -2) === "\n\n" | ||
130 | ) { | ||
131 | // State 1.1.4: <div><p>PAR1</p>\n\n<b> | ||
132 | // --- | ||
133 | // Quite frankly, this should be handled by splitText | ||
134 | $token = array($this->_pStart(), $token); | ||
135 | } else { | ||
136 | // State 1.1.1: <div><p>PAR1</p><b> | ||
137 | // --- | ||
138 | // State 1.1.2: <div><br /><b> | ||
139 | // --- | ||
140 | // State 1.1.3: <div>PAR<b> | ||
141 | // --- | ||
142 | } | ||
143 | } else { | ||
144 | // State 1.2.1: <div><b> | ||
145 | // --- | ||
146 | // Lookahead to see if <p> is needed. | ||
147 | if ($this->_pLookAhead()) { | ||
148 | // State 1.3.1: <div><b>PAR1\n\nPAR2 | ||
149 | // --- | ||
150 | $token = array($this->_pStart(), $token); | ||
151 | } else { | ||
152 | // State 1.3.2: <div><b>PAR1</b></div> | ||
153 | // --- | ||
154 | |||
155 | // State 1.3.3: <div><b>PAR1</b><div></div>\n\n</div> | ||
156 | // --- | ||
157 | } | ||
158 | } | ||
159 | } else { | ||
160 | // State 2.3: ...<div> | ||
161 | // ----- | ||
162 | } | ||
163 | } else { | ||
164 | if ($this->_isInline($token)) { | ||
165 | // State 3.1: <b> | ||
166 | // --- | ||
167 | // This is where the {p} tag is inserted, not reflected in | ||
168 | // inputTokens yet, however. | ||
169 | $token = array($this->_pStart(), $token); | ||
170 | } else { | ||
171 | // State 3.2: <div> | ||
172 | // ----- | ||
173 | } | ||
174 | |||
175 | $i = null; | ||
176 | if ($this->backward($i, $prev)) { | ||
177 | if (!$prev instanceof HTMLPurifier_Token_Text) { | ||
178 | // State 3.1.1: ...</p>{p}<b> | ||
179 | // --- | ||
180 | // State 3.2.1: ...</p><div> | ||
181 | // ----- | ||
182 | if (!is_array($token)) { | ||
183 | $token = array($token); | ||
184 | } | ||
185 | array_unshift($token, new HTMLPurifier_Token_Text("\n\n")); | ||
186 | } else { | ||
187 | // State 3.1.2: ...</p>\n\n{p}<b> | ||
188 | // --- | ||
189 | // State 3.2.2: ...</p>\n\n<div> | ||
190 | // ----- | ||
191 | // Note: PAR<ELEM> cannot occur because PAR would have been | ||
192 | // wrapped in <p> tags. | ||
193 | } | ||
194 | } | ||
195 | } | ||
196 | } else { | ||
197 | // State 2.2: <ul><li> | ||
198 | // ---- | ||
199 | // State 2.4: <p><b> | ||
200 | // --- | ||
201 | } | ||
202 | } | ||
203 | |||
204 | /** | ||
205 | * Splits up a text in paragraph tokens and appends them | ||
206 | * to the result stream that will replace the original | ||
207 | * @param string $data String text data that will be processed | ||
208 | * into paragraphs | ||
209 | * @param HTMLPurifier_Token[] $result Reference to array of tokens that the | ||
210 | * tags will be appended onto | ||
211 | */ | ||
212 | private function _splitText($data, &$result) | ||
213 | { | ||
214 | $raw_paragraphs = explode("\n\n", $data); | ||
215 | $paragraphs = array(); // without empty paragraphs | ||
216 | $needs_start = false; | ||
217 | $needs_end = false; | ||
218 | |||
219 | $c = count($raw_paragraphs); | ||
220 | if ($c == 1) { | ||
221 | // There were no double-newlines, abort quickly. In theory this | ||
222 | // should never happen. | ||
223 | $result[] = new HTMLPurifier_Token_Text($data); | ||
224 | return; | ||
225 | } | ||
226 | for ($i = 0; $i < $c; $i++) { | ||
227 | $par = $raw_paragraphs[$i]; | ||
228 | if (trim($par) !== '') { | ||
229 | $paragraphs[] = $par; | ||
230 | } else { | ||
231 | if ($i == 0) { | ||
232 | // Double newline at the front | ||
233 | if (empty($result)) { | ||
234 | // The empty result indicates that the AutoParagraph | ||
235 | // injector did not add any start paragraph tokens. | ||
236 | // This means that we have been in a paragraph for | ||
237 | // a while, and the newline means we should start a new one. | ||
238 | $result[] = new HTMLPurifier_Token_End('p'); | ||
239 | $result[] = new HTMLPurifier_Token_Text("\n\n"); | ||
240 | // However, the start token should only be added if | ||
241 | // there is more processing to be done (i.e. there are | ||
242 | // real paragraphs in here). If there are none, the | ||
243 | // next start paragraph tag will be handled by the | ||
244 | // next call to the injector | ||
245 | $needs_start = true; | ||
246 | } else { | ||
247 | // We just started a new paragraph! | ||
248 | // Reinstate a double-newline for presentation's sake, since | ||
249 | // it was in the source code. | ||
250 | array_unshift($result, new HTMLPurifier_Token_Text("\n\n")); | ||
251 | } | ||
252 | } elseif ($i + 1 == $c) { | ||
253 | // Double newline at the end | ||
254 | // There should be a trailing </p> when we're finally done. | ||
255 | $needs_end = true; | ||
256 | } | ||
257 | } | ||
258 | } | ||
259 | |||
260 | // Check if this was just a giant blob of whitespace. Move this earlier, | ||
261 | // perhaps? | ||
262 | if (empty($paragraphs)) { | ||
263 | return; | ||
264 | } | ||
265 | |||
266 | // Add the start tag indicated by \n\n at the beginning of $data | ||
267 | if ($needs_start) { | ||
268 | $result[] = $this->_pStart(); | ||
269 | } | ||
270 | |||
271 | // Append the paragraphs onto the result | ||
272 | foreach ($paragraphs as $par) { | ||
273 | $result[] = new HTMLPurifier_Token_Text($par); | ||
274 | $result[] = new HTMLPurifier_Token_End('p'); | ||
275 | $result[] = new HTMLPurifier_Token_Text("\n\n"); | ||
276 | $result[] = $this->_pStart(); | ||
277 | } | ||
278 | |||
279 | // Remove trailing start token; Injector will handle this later if | ||
280 | // it was indeed needed. This prevents from needing to do a lookahead, | ||
281 | // at the cost of a lookbehind later. | ||
282 | array_pop($result); | ||
283 | |||
284 | // If there is no need for an end tag, remove all of it and let | ||
285 | // MakeWellFormed close it later. | ||
286 | if (!$needs_end) { | ||
287 | array_pop($result); // removes \n\n | ||
288 | array_pop($result); // removes </p> | ||
289 | } | ||
290 | } | ||
291 | |||
292 | /** | ||
293 | * Returns true if passed token is inline (and, ergo, allowed in | ||
294 | * paragraph tags) | ||
295 | * @param HTMLPurifier_Token $token | ||
296 | * @return bool | ||
297 | */ | ||
298 | private function _isInline($token) | ||
299 | { | ||
300 | return isset($this->htmlDefinition->info['p']->child->elements[$token->name]); | ||
301 | } | ||
302 | |||
303 | /** | ||
304 | * Looks ahead in the token list and determines whether or not we need | ||
305 | * to insert a <p> tag. | ||
306 | * @return bool | ||
307 | */ | ||
308 | private function _pLookAhead() | ||
309 | { | ||
310 | if ($this->currentToken instanceof HTMLPurifier_Token_Start) { | ||
311 | $nesting = 1; | ||
312 | } else { | ||
313 | $nesting = 0; | ||
314 | } | ||
315 | $ok = false; | ||
316 | $i = null; | ||
317 | while ($this->forwardUntilEndToken($i, $current, $nesting)) { | ||
318 | $result = $this->_checkNeedsP($current); | ||
319 | if ($result !== null) { | ||
320 | $ok = $result; | ||
321 | break; | ||
322 | } | ||
323 | } | ||
324 | return $ok; | ||
325 | } | ||
326 | |||
327 | /** | ||
328 | * Determines if a particular token requires an earlier inline token | ||
329 | * to get a paragraph. This should be used with _forwardUntilEndToken | ||
330 | * @param HTMLPurifier_Token $current | ||
331 | * @return bool | ||
332 | */ | ||
333 | private function _checkNeedsP($current) | ||
334 | { | ||
335 | if ($current instanceof HTMLPurifier_Token_Start) { | ||
336 | if (!$this->_isInline($current)) { | ||
337 | // <div>PAR1<div> | ||
338 | // ---- | ||
339 | // Terminate early, since we hit a block element | ||
340 | return false; | ||
341 | } | ||
342 | } elseif ($current instanceof HTMLPurifier_Token_Text) { | ||
343 | if (strpos($current->data, "\n\n") !== false) { | ||
344 | // <div>PAR1<b>PAR1\n\nPAR2 | ||
345 | // ---- | ||
346 | return true; | ||
347 | } else { | ||
348 | // <div>PAR1<b>PAR1... | ||
349 | // ---- | ||
350 | } | ||
351 | } | ||
352 | return null; | ||
353 | } | ||
354 | } | ||
355 | |||
356 | // vim: et sw=4 sts=4 | ||
diff --git a/inc/3rdparty/htmlpurifier/HTMLPurifier/Injector/DisplayLinkURI.php b/inc/3rdparty/htmlpurifier/HTMLPurifier/Injector/DisplayLinkURI.php deleted file mode 100644 index 9f904482..00000000 --- a/inc/3rdparty/htmlpurifier/HTMLPurifier/Injector/DisplayLinkURI.php +++ /dev/null | |||
@@ -1,40 +0,0 @@ | |||
1 | <?php | ||
2 | |||
3 | /** | ||
4 | * Injector that displays the URL of an anchor instead of linking to it, in addition to showing the text of the link. | ||
5 | */ | ||
6 | class HTMLPurifier_Injector_DisplayLinkURI extends HTMLPurifier_Injector | ||
7 | { | ||
8 | /** | ||
9 | * @type string | ||
10 | */ | ||
11 | public $name = 'DisplayLinkURI'; | ||
12 | |||
13 | /** | ||
14 | * @type array | ||
15 | */ | ||
16 | public $needed = array('a'); | ||
17 | |||
18 | /** | ||
19 | * @param $token | ||
20 | */ | ||
21 | public function handleElement(&$token) | ||
22 | { | ||
23 | } | ||
24 | |||
25 | /** | ||
26 | * @param HTMLPurifier_Token $token | ||
27 | */ | ||
28 | public function handleEnd(&$token) | ||
29 | { | ||
30 | if (isset($token->start->attr['href'])) { | ||
31 | $url = $token->start->attr['href']; | ||
32 | unset($token->start->attr['href']); | ||
33 | $token = array($token, new HTMLPurifier_Token_Text(" ($url)")); | ||
34 | } else { | ||
35 | // nothing to display | ||
36 | } | ||
37 | } | ||
38 | } | ||
39 | |||
40 | // vim: et sw=4 sts=4 | ||
diff --git a/inc/3rdparty/htmlpurifier/HTMLPurifier/Injector/Linkify.php b/inc/3rdparty/htmlpurifier/HTMLPurifier/Injector/Linkify.php deleted file mode 100644 index 5eed3c12..00000000 --- a/inc/3rdparty/htmlpurifier/HTMLPurifier/Injector/Linkify.php +++ /dev/null | |||
@@ -1,59 +0,0 @@ | |||
1 | <?php | ||
2 | |||
3 | /** | ||
4 | * Injector that converts http, https and ftp text URLs to actual links. | ||
5 | */ | ||
6 | class HTMLPurifier_Injector_Linkify extends HTMLPurifier_Injector | ||
7 | { | ||
8 | /** | ||
9 | * @type string | ||
10 | */ | ||
11 | public $name = 'Linkify'; | ||
12 | |||
13 | /** | ||
14 | * @type array | ||
15 | */ | ||
16 | public $needed = array('a' => array('href')); | ||
17 | |||
18 | /** | ||
19 | * @param HTMLPurifier_Token $token | ||
20 | */ | ||
21 | public function handleText(&$token) | ||
22 | { | ||
23 | if (!$this->allowsElement('a')) { | ||
24 | return; | ||
25 | } | ||
26 | |||
27 | if (strpos($token->data, '://') === false) { | ||
28 | // our really quick heuristic failed, abort | ||
29 | // this may not work so well if we want to match things like | ||
30 | // "google.com", but then again, most people don't | ||
31 | return; | ||
32 | } | ||
33 | |||
34 | // there is/are URL(s). Let's split the string: | ||
35 | // Note: this regex is extremely permissive | ||
36 | $bits = preg_split('#((?:https?|ftp)://[^\s\'",<>()]+)#Su', $token->data, -1, PREG_SPLIT_DELIM_CAPTURE); | ||
37 | |||
38 | |||
39 | $token = array(); | ||
40 | |||
41 | // $i = index | ||
42 | // $c = count | ||
43 | // $l = is link | ||
44 | for ($i = 0, $c = count($bits), $l = false; $i < $c; $i++, $l = !$l) { | ||
45 | if (!$l) { | ||
46 | if ($bits[$i] === '') { | ||
47 | continue; | ||
48 | } | ||
49 | $token[] = new HTMLPurifier_Token_Text($bits[$i]); | ||
50 | } else { | ||
51 | $token[] = new HTMLPurifier_Token_Start('a', array('href' => $bits[$i])); | ||
52 | $token[] = new HTMLPurifier_Token_Text($bits[$i]); | ||
53 | $token[] = new HTMLPurifier_Token_End('a'); | ||
54 | } | ||
55 | } | ||
56 | } | ||
57 | } | ||
58 | |||
59 | // vim: et sw=4 sts=4 | ||
diff --git a/inc/3rdparty/htmlpurifier/HTMLPurifier/Injector/PurifierLinkify.php b/inc/3rdparty/htmlpurifier/HTMLPurifier/Injector/PurifierLinkify.php deleted file mode 100644 index d7dd7d97..00000000 --- a/inc/3rdparty/htmlpurifier/HTMLPurifier/Injector/PurifierLinkify.php +++ /dev/null | |||
@@ -1,71 +0,0 @@ | |||
1 | <?php | ||
2 | |||
3 | /** | ||
4 | * Injector that converts configuration directive syntax %Namespace.Directive | ||
5 | * to links | ||
6 | */ | ||
7 | class HTMLPurifier_Injector_PurifierLinkify extends HTMLPurifier_Injector | ||
8 | { | ||
9 | /** | ||
10 | * @type string | ||
11 | */ | ||
12 | public $name = 'PurifierLinkify'; | ||
13 | |||
14 | /** | ||
15 | * @type string | ||
16 | */ | ||
17 | public $docURL; | ||
18 | |||
19 | /** | ||
20 | * @type array | ||
21 | */ | ||
22 | public $needed = array('a' => array('href')); | ||
23 | |||
24 | /** | ||
25 | * @param HTMLPurifier_Config $config | ||
26 | * @param HTMLPurifier_Context $context | ||
27 | * @return string | ||
28 | */ | ||
29 | public function prepare($config, $context) | ||
30 | { | ||
31 | $this->docURL = $config->get('AutoFormat.PurifierLinkify.DocURL'); | ||
32 | return parent::prepare($config, $context); | ||
33 | } | ||
34 | |||
35 | /** | ||
36 | * @param HTMLPurifier_Token $token | ||
37 | */ | ||
38 | public function handleText(&$token) | ||
39 | { | ||
40 | if (!$this->allowsElement('a')) { | ||
41 | return; | ||
42 | } | ||
43 | if (strpos($token->data, '%') === false) { | ||
44 | return; | ||
45 | } | ||
46 | |||
47 | $bits = preg_split('#%([a-z0-9]+\.[a-z0-9]+)#Si', $token->data, -1, PREG_SPLIT_DELIM_CAPTURE); | ||
48 | $token = array(); | ||
49 | |||
50 | // $i = index | ||
51 | // $c = count | ||
52 | // $l = is link | ||
53 | for ($i = 0, $c = count($bits), $l = false; $i < $c; $i++, $l = !$l) { | ||
54 | if (!$l) { | ||
55 | if ($bits[$i] === '') { | ||
56 | continue; | ||
57 | } | ||
58 | $token[] = new HTMLPurifier_Token_Text($bits[$i]); | ||
59 | } else { | ||
60 | $token[] = new HTMLPurifier_Token_Start( | ||
61 | 'a', | ||
62 | array('href' => str_replace('%s', $bits[$i], $this->docURL)) | ||
63 | ); | ||
64 | $token[] = new HTMLPurifier_Token_Text('%' . $bits[$i]); | ||
65 | $token[] = new HTMLPurifier_Token_End('a'); | ||
66 | } | ||
67 | } | ||
68 | } | ||
69 | } | ||
70 | |||
71 | // vim: et sw=4 sts=4 | ||
diff --git a/inc/3rdparty/htmlpurifier/HTMLPurifier/Injector/RemoveEmpty.php b/inc/3rdparty/htmlpurifier/HTMLPurifier/Injector/RemoveEmpty.php deleted file mode 100644 index 55669d1c..00000000 --- a/inc/3rdparty/htmlpurifier/HTMLPurifier/Injector/RemoveEmpty.php +++ /dev/null | |||
@@ -1,101 +0,0 @@ | |||
1 | <?php | ||
2 | |||
3 | class HTMLPurifier_Injector_RemoveEmpty extends HTMLPurifier_Injector | ||
4 | { | ||
5 | /** | ||
6 | * @type HTMLPurifier_Context | ||
7 | */ | ||
8 | private $context; | ||
9 | |||
10 | /** | ||
11 | * @type HTMLPurifier_Config | ||
12 | */ | ||
13 | private $config; | ||
14 | |||
15 | /** | ||
16 | * @type HTMLPurifier_AttrValidator | ||
17 | */ | ||
18 | private $attrValidator; | ||
19 | |||
20 | /** | ||
21 | * @type bool | ||
22 | */ | ||
23 | private $removeNbsp; | ||
24 | |||
25 | /** | ||
26 | * @type bool | ||
27 | */ | ||
28 | private $removeNbspExceptions; | ||
29 | |||
30 | /** | ||
31 | * @type array | ||
32 | * TODO: make me configurable | ||
33 | */ | ||
34 | private $_exclude = array('colgroup' => 1, 'th' => 1, 'td' => 1, 'iframe' => 1); | ||
35 | |||
36 | /** | ||
37 | * @param HTMLPurifier_Config $config | ||
38 | * @param HTMLPurifier_Context $context | ||
39 | * @return void | ||
40 | */ | ||
41 | public function prepare($config, $context) | ||
42 | { | ||
43 | parent::prepare($config, $context); | ||
44 | $this->config = $config; | ||
45 | $this->context = $context; | ||
46 | $this->removeNbsp = $config->get('AutoFormat.RemoveEmpty.RemoveNbsp'); | ||
47 | $this->removeNbspExceptions = $config->get('AutoFormat.RemoveEmpty.RemoveNbsp.Exceptions'); | ||
48 | $this->attrValidator = new HTMLPurifier_AttrValidator(); | ||
49 | } | ||
50 | |||
51 | /** | ||
52 | * @param HTMLPurifier_Token $token | ||
53 | */ | ||
54 | public function handleElement(&$token) | ||
55 | { | ||
56 | if (!$token instanceof HTMLPurifier_Token_Start) { | ||
57 | return; | ||
58 | } | ||
59 | $next = false; | ||
60 | $deleted = 1; // the current tag | ||
61 | for ($i = count($this->inputZipper->back) - 1; $i >= 0; $i--, $deleted++) { | ||
62 | $next = $this->inputZipper->back[$i]; | ||
63 | if ($next instanceof HTMLPurifier_Token_Text) { | ||
64 | if ($next->is_whitespace) { | ||
65 | continue; | ||
66 | } | ||
67 | if ($this->removeNbsp && !isset($this->removeNbspExceptions[$token->name])) { | ||
68 | $plain = str_replace("\xC2\xA0", "", $next->data); | ||
69 | $isWsOrNbsp = $plain === '' || ctype_space($plain); | ||
70 | if ($isWsOrNbsp) { | ||
71 | continue; | ||
72 | } | ||
73 | } | ||
74 | } | ||
75 | break; | ||
76 | } | ||
77 | if (!$next || ($next instanceof HTMLPurifier_Token_End && $next->name == $token->name)) { | ||
78 | if (isset($this->_exclude[$token->name])) { | ||
79 | return; | ||
80 | } | ||
81 | $this->attrValidator->validateToken($token, $this->config, $this->context); | ||
82 | $token->armor['ValidateAttributes'] = true; | ||
83 | if (isset($token->attr['id']) || isset($token->attr['name'])) { | ||
84 | return; | ||
85 | } | ||
86 | $token = $deleted + 1; | ||
87 | for ($b = 0, $c = count($this->inputZipper->front); $b < $c; $b++) { | ||
88 | $prev = $this->inputZipper->front[$b]; | ||
89 | if ($prev instanceof HTMLPurifier_Token_Text && $prev->is_whitespace) { | ||
90 | continue; | ||
91 | } | ||
92 | break; | ||
93 | } | ||
94 | // This is safe because we removed the token that triggered this. | ||
95 | $this->rewindOffset($b+$deleted); | ||
96 | return; | ||
97 | } | ||
98 | } | ||
99 | } | ||
100 | |||
101 | // vim: et sw=4 sts=4 | ||
diff --git a/inc/3rdparty/htmlpurifier/HTMLPurifier/Injector/RemoveSpansWithoutAttributes.php b/inc/3rdparty/htmlpurifier/HTMLPurifier/Injector/RemoveSpansWithoutAttributes.php deleted file mode 100644 index 270b7f82..00000000 --- a/inc/3rdparty/htmlpurifier/HTMLPurifier/Injector/RemoveSpansWithoutAttributes.php +++ /dev/null | |||
@@ -1,84 +0,0 @@ | |||
1 | <?php | ||
2 | |||
3 | /** | ||
4 | * Injector that removes spans with no attributes | ||
5 | */ | ||
6 | class HTMLPurifier_Injector_RemoveSpansWithoutAttributes extends HTMLPurifier_Injector | ||
7 | { | ||
8 | /** | ||
9 | * @type string | ||
10 | */ | ||
11 | public $name = 'RemoveSpansWithoutAttributes'; | ||
12 | |||
13 | /** | ||
14 | * @type array | ||
15 | */ | ||
16 | public $needed = array('span'); | ||
17 | |||
18 | /** | ||
19 | * @type HTMLPurifier_AttrValidator | ||
20 | */ | ||
21 | private $attrValidator; | ||
22 | |||
23 | /** | ||
24 | * Used by AttrValidator. | ||
25 | * @type HTMLPurifier_Config | ||
26 | */ | ||
27 | private $config; | ||
28 | |||
29 | /** | ||
30 | * @type HTMLPurifier_Context | ||
31 | */ | ||
32 | private $context; | ||
33 | |||
34 | public function prepare($config, $context) | ||
35 | { | ||
36 | $this->attrValidator = new HTMLPurifier_AttrValidator(); | ||
37 | $this->config = $config; | ||
38 | $this->context = $context; | ||
39 | return parent::prepare($config, $context); | ||
40 | } | ||
41 | |||
42 | /** | ||
43 | * @param HTMLPurifier_Token $token | ||
44 | */ | ||
45 | public function handleElement(&$token) | ||
46 | { | ||
47 | if ($token->name !== 'span' || !$token instanceof HTMLPurifier_Token_Start) { | ||
48 | return; | ||
49 | } | ||
50 | |||
51 | // We need to validate the attributes now since this doesn't normally | ||
52 | // happen until after MakeWellFormed. If all the attributes are removed | ||
53 | // the span needs to be removed too. | ||
54 | $this->attrValidator->validateToken($token, $this->config, $this->context); | ||
55 | $token->armor['ValidateAttributes'] = true; | ||
56 | |||
57 | if (!empty($token->attr)) { | ||
58 | return; | ||
59 | } | ||
60 | |||
61 | $nesting = 0; | ||
62 | while ($this->forwardUntilEndToken($i, $current, $nesting)) { | ||
63 | } | ||
64 | |||
65 | if ($current instanceof HTMLPurifier_Token_End && $current->name === 'span') { | ||
66 | // Mark closing span tag for deletion | ||
67 | $current->markForDeletion = true; | ||
68 | // Delete open span tag | ||
69 | $token = false; | ||
70 | } | ||
71 | } | ||
72 | |||
73 | /** | ||
74 | * @param HTMLPurifier_Token $token | ||
75 | */ | ||
76 | public function handleEnd(&$token) | ||
77 | { | ||
78 | if ($token->markForDeletion) { | ||
79 | $token = false; | ||
80 | } | ||
81 | } | ||
82 | } | ||
83 | |||
84 | // vim: et sw=4 sts=4 | ||
diff --git a/inc/3rdparty/htmlpurifier/HTMLPurifier/Injector/SafeObject.php b/inc/3rdparty/htmlpurifier/HTMLPurifier/Injector/SafeObject.php deleted file mode 100644 index 8450948c..00000000 --- a/inc/3rdparty/htmlpurifier/HTMLPurifier/Injector/SafeObject.php +++ /dev/null | |||
@@ -1,121 +0,0 @@ | |||
1 | <?php | ||
2 | |||
3 | /** | ||
4 | * Adds important param elements to inside of object in order to make | ||
5 | * things safe. | ||
6 | */ | ||
7 | class HTMLPurifier_Injector_SafeObject extends HTMLPurifier_Injector | ||
8 | { | ||
9 | /** | ||
10 | * @type string | ||
11 | */ | ||
12 | public $name = 'SafeObject'; | ||
13 | |||
14 | /** | ||
15 | * @type array | ||
16 | */ | ||
17 | public $needed = array('object', 'param'); | ||
18 | |||
19 | /** | ||
20 | * @type array | ||
21 | */ | ||
22 | protected $objectStack = array(); | ||
23 | |||
24 | /** | ||
25 | * @type array | ||
26 | */ | ||
27 | protected $paramStack = array(); | ||
28 | |||
29 | /** | ||
30 | * Keep this synchronized with AttrTransform/SafeParam.php. | ||
31 | * @type array | ||
32 | */ | ||
33 | protected $addParam = array( | ||
34 | 'allowScriptAccess' => 'never', | ||
35 | 'allowNetworking' => 'internal', | ||
36 | ); | ||
37 | |||
38 | /** | ||
39 | * @type array | ||
40 | */ | ||
41 | protected $allowedParam = array( | ||
42 | 'wmode' => true, | ||
43 | 'movie' => true, | ||
44 | 'flashvars' => true, | ||
45 | 'src' => true, | ||
46 | 'allowFullScreen' => true, // if omitted, assume to be 'false' | ||
47 | ); | ||
48 | |||
49 | /** | ||
50 | * @param HTMLPurifier_Config $config | ||
51 | * @param HTMLPurifier_Context $context | ||
52 | * @return void | ||
53 | */ | ||
54 | public function prepare($config, $context) | ||
55 | { | ||
56 | parent::prepare($config, $context); | ||
57 | } | ||
58 | |||
59 | /** | ||
60 | * @param HTMLPurifier_Token $token | ||
61 | */ | ||
62 | public function handleElement(&$token) | ||
63 | { | ||
64 | if ($token->name == 'object') { | ||
65 | $this->objectStack[] = $token; | ||
66 | $this->paramStack[] = array(); | ||
67 | $new = array($token); | ||
68 | foreach ($this->addParam as $name => $value) { | ||
69 | $new[] = new HTMLPurifier_Token_Empty('param', array('name' => $name, 'value' => $value)); | ||
70 | } | ||
71 | $token = $new; | ||
72 | } elseif ($token->name == 'param') { | ||
73 | $nest = count($this->currentNesting) - 1; | ||
74 | if ($nest >= 0 && $this->currentNesting[$nest]->name === 'object') { | ||
75 | $i = count($this->objectStack) - 1; | ||
76 | if (!isset($token->attr['name'])) { | ||
77 | $token = false; | ||
78 | return; | ||
79 | } | ||
80 | $n = $token->attr['name']; | ||
81 | // We need this fix because YouTube doesn't supply a data | ||
82 | // attribute, which we need if a type is specified. This is | ||
83 | // *very* Flash specific. | ||
84 | if (!isset($this->objectStack[$i]->attr['data']) && | ||
85 | ($token->attr['name'] == 'movie' || $token->attr['name'] == 'src') | ||
86 | ) { | ||
87 | $this->objectStack[$i]->attr['data'] = $token->attr['value']; | ||
88 | } | ||
89 | // Check if the parameter is the correct value but has not | ||
90 | // already been added | ||
91 | if (!isset($this->paramStack[$i][$n]) && | ||
92 | isset($this->addParam[$n]) && | ||
93 | $token->attr['name'] === $this->addParam[$n]) { | ||
94 | // keep token, and add to param stack | ||
95 | $this->paramStack[$i][$n] = true; | ||
96 | } elseif (isset($this->allowedParam[$n])) { | ||
97 | // keep token, don't do anything to it | ||
98 | // (could possibly check for duplicates here) | ||
99 | } else { | ||
100 | $token = false; | ||
101 | } | ||
102 | } else { | ||
103 | // not directly inside an object, DENY! | ||
104 | $token = false; | ||
105 | } | ||
106 | } | ||
107 | } | ||
108 | |||
109 | public function handleEnd(&$token) | ||
110 | { | ||
111 | // This is the WRONG way of handling the object and param stacks; | ||
112 | // we should be inserting them directly on the relevant object tokens | ||
113 | // so that the global stack handling handles it. | ||
114 | if ($token->name == 'object') { | ||
115 | array_pop($this->objectStack); | ||
116 | array_pop($this->paramStack); | ||
117 | } | ||
118 | } | ||
119 | } | ||
120 | |||
121 | // vim: et sw=4 sts=4 | ||