Tests_Formatting_WPTexturize   F
last analyzed

Complexity

Total Complexity 91

Size/Duplication

Total Lines 2084
Duplicated Lines 37.38 %

Coupling/Cohesion

Components 0
Dependencies 1

Importance

Changes 0
Metric Value
dl 779
loc 2084
rs 0.6314
c 0
b 0
f 0
wmc 91
lcom 0
cbo 1

72 Methods

Rating   Name   Duplication   Size   Complexity  
A test_dashes() 0 4 1
A test_disable() 0 22 1
A test_bracketed_quotes_1418() 0 5 1
A test_bracketed_quotes_3810() 0 3 1
A test_full_sentences_with_unmatched_single_quotes() 0 6 1
A test_quotes() 0 15 1
A test_quotes_before_s() 0 7 1
B test_quotes_before_numbers() 0 25 1
A test_quotes_after_numbers() 0 3 1
A test_other_html() 0 5 1
A test_x() 0 3 1
A test_wptexturize_quotes_around_numbers() 0 6 1
A test_wptexturize_html_comments() 0 5 1
A test_entity_quote_cuddling() 0 4 1
A test_apostrophes_before_primes() 0 3 1
A test_spaces_around_hyphens() 0 19 1
A test_spaces_around_quotes_never() 0 8 1
A test_spaces_around_quotes() 0 3 1
B data_spaces_around_quotes() 0 43 1
A test_apos_before_digits() 0 3 1
A test_opening_single_quote() 0 3 1
B data_opening_single_quote() 0 116 1
A test_double_prime() 0 3 1
A test_single_prime() 0 3 1
A test_contractions() 0 3 1
A test_opening_quote() 0 3 1
A test_closing_quote() 0 3 1
A test_closing_single_quote() 0 3 1
A test_multiplication() 0 3 1
B data_multiplication() 0 37 1
A test_ampersand() 0 3 1
A test_cockney() 0 3 1
A test_smart_dashes() 0 3 1
B data_smart_dashes() 0 40 1
A test_misc_static_replacements() 0 3 1
B data_misc_static_replacements() 0 44 1
A test_quoted_numbers() 0 3 1
A test_quotes_and_dashes() 0 3 1
A test_tag_avoidance() 0 3 1
B data_tag_avoidance() 0 212 1
A test_year_abbr() 0 3 1
B data_translate() 0 180 1
A test_element_stack() 0 3 1
A test_unregistered_shortcodes() 0 8 1
A filter_shortcodes() 0 4 1
A test_primes_vs_quotes() 0 3 1
A data_primes_vs_quotes() 0 49 1
A data_primes_quotes_translation() 0 49 1
A test_pcre_performance() 0 14 1
A test_trailing_less_than() 0 3 1
A data_whole_posts() 0 4 1
A test_basic_quotes() 18 18 1
A test_minutes_seconds() 10 10 1
A test_hyphens_at_start_and_end() 9 9 1
B data_apos_before_digits() 28 28 1
A data_double_prime() 20 20 1
A data_single_prime() 20 20 1
B data_contractions() 28 28 1
A data_opening_quote() 64 64 1
B data_closing_quote() 76 76 1
B data_closing_single_quote() 76 76 1
A data_ampersand() 52 52 1
A data_cockney() 48 48 1
B data_quoted_numbers() 40 40 1
A data_quotes_and_dashes() 52 52 1
B data_year_abbr() 76 76 1
A test_translate() 10 10 1
B filter_translate() 20 20 11
B data_element_stack() 40 40 1
A data_unregistered_shortcodes() 64 64 1
A test_primes_quotes_translation() 10 10 1
B filter_translate2() 18 18 10

How to fix   Duplicated Code    Complexity   

Duplicated Code

Duplicate code is one of the most pungent code smells. A rule that is often used is to re-structure code once it is duplicated in three or more places.

Common duplication problems, and corresponding solutions are:

Complex Class

 Tip:   Before tackling complexity, make sure that you eliminate any duplication first. This often can reduce the size of classes significantly.

Complex classes like Tests_Formatting_WPTexturize often do a lot of different things. To break such a class down, we need to identify a cohesive component within that class. A common approach to find such a component is to look for fields/methods that share the same prefixes, or suffixes. You can also have a look at the cohesion graph to spot any un-connected, or weakly-connected components.

Once you have determined the fields that belong together, you can apply the Extract Class refactoring. If the component makes sense as a sub-class, Extract Subclass is also a candidate, and is often faster.

While breaking up the class, it is a good idea to analyze how other classes use Tests_Formatting_WPTexturize, and based on these observations, apply Extract Interface, too.

1
<?php
2
3
/**
4
 * @group formatting
5
 */
6
class Tests_Formatting_WPTexturize extends WP_UnitTestCase {
7
	function test_dashes() {
8
		$this->assertEquals('Hey &#8212; boo?', wptexturize('Hey -- boo?'));
9
		$this->assertEquals('<a href="http://xx--xx">Hey &#8212; boo?</a>', wptexturize('<a href="http://xx--xx">Hey -- boo?</a>'));
10
	}
11
12
	function test_disable() {
13
		$this->assertEquals('<pre>---&</pre>', wptexturize('<pre>---&</pre>'));
14
		$this->assertEquals('<pre><code></code>--&</pre>', wptexturize('<pre><code></code>--&</pre>'));
15
16
		$this->assertEquals( '<code>---&</code>',     wptexturize( '<code>---&</code>'     ) );
17
		$this->assertEquals( '<kbd>---&</kbd>',       wptexturize( '<kbd>---&</kbd>'       ) );
18
		$this->assertEquals( '<style>---&</style>',   wptexturize( '<style>---&</style>'   ) );
19
		$this->assertEquals( '<script>---&</script>', wptexturize( '<script>---&</script>' ) );
20
		$this->assertEquals( '<tt>---&</tt>',         wptexturize( '<tt>---&</tt>'         ) );
21
22
		$this->assertEquals('<code>href="baba"</code> &#8220;baba&#8221;', wptexturize('<code>href="baba"</code> "baba"'));
23
24
		$enabled_tags_inside_code = '<code>curl -s <a href="http://x/">baba</a> | grep sfive | cut -d "\"" -f 10 &gt; topmp3.txt</code>';
25
		$this->assertEquals($enabled_tags_inside_code, wptexturize($enabled_tags_inside_code));
26
27
		$double_nest = '<pre>"baba"<code>"baba"<pre></pre></code>"baba"</pre>';
28
		$this->assertEquals($double_nest, wptexturize($double_nest));
29
30
		$invalid_nest = '<pre></code>"baba"</pre>';
31
		$this->assertEquals($invalid_nest, wptexturize($invalid_nest));
32
33
	}
34
35
	//WP Ticket #1418
36
	function test_bracketed_quotes_1418() {
37
		$this->assertEquals('(&#8220;test&#8221;)', wptexturize('("test")'));
38
		$this->assertEquals('(&#8216;test&#8217;)', wptexturize("('test')"));
39
		$this->assertEquals('(&#8217;twas)', wptexturize("('twas)"));
40
	}
41
42
	//WP Ticket #3810
43
	function test_bracketed_quotes_3810() {
44
		$this->assertEquals('A dog (&#8220;Hubertus&#8221;) was sent out.', wptexturize('A dog ("Hubertus") was sent out.'));
45
	}
46
47
	//WP Ticket #4539
48 View Code Duplication
	function test_basic_quotes() {
49
		$this->assertEquals('test&#8217;s', wptexturize('test\'s'));
50
51
		$this->assertEquals('&#8216;quoted&#8217;', wptexturize('\'quoted\''));
52
		$this->assertEquals('&#8220;quoted&#8221;', wptexturize('"quoted"'));
53
54
		$this->assertEquals('space before &#8216;quoted&#8217; space after', wptexturize('space before \'quoted\' space after'));
55
		$this->assertEquals('space before &#8220;quoted&#8221; space after', wptexturize('space before "quoted" space after'));
56
57
		$this->assertEquals('(&#8216;quoted&#8217;)', wptexturize('(\'quoted\')'));
58
		$this->assertEquals('{&#8220;quoted&#8221;}', wptexturize('{"quoted"}'));
59
60
		$this->assertEquals('&#8216;qu(ot)ed&#8217;', wptexturize('\'qu(ot)ed\''));
61
		$this->assertEquals('&#8220;qu{ot}ed&#8221;', wptexturize('"qu{ot}ed"'));
62
63
		$this->assertEquals(' &#8216;test&#8217;s quoted&#8217; ', wptexturize(' \'test\'s quoted\' '));
64
		$this->assertEquals(' &#8220;test&#8217;s quoted&#8221; ', wptexturize(' "test\'s quoted" '));
65
	}
66
67
	/**
68
	 * @ticket 4539
69
	 * @ticket 15241
70
	 */
71
	function test_full_sentences_with_unmatched_single_quotes() {
72
		$this->assertEquals(
73
			'That means every moment you&#8217;re working on something without it being in the public it&#8217;s actually dying.',
74
			wptexturize("That means every moment you're working on something without it being in the public it's actually dying.")
75
		);
76
	}
77
78
	/**
79
	 * @ticket 4539
80
	 */
81
	function test_quotes() {
82
		$this->assertEquals('&#8220;Quoted String&#8221;', wptexturize('"Quoted String"'));
83
		//$this->assertEquals('Here is &#8220;<a href="http://example.com">a test with a link</a>&#8221;', wptexturize('Here is "<a href="http://example.com">a test with a link</a>"'));
84
		//$this->assertEquals('Here is &#8220;<a href="http://example.com">a test with a link and a period</a>&#8221;.', wptexturize('Here is "<a href="http://example.com">a test with a link and a period</a>".'));
85
		$this->assertEquals('Here is &#8220;<a href="http://example.com">a test with a link</a>&#8221; and a space.', wptexturize('Here is "<a href="http://example.com">a test with a link</a>" and a space.'));
86
		$this->assertEquals('Here is &#8220;<a href="http://example.com">a test with a link</a> and some text quoted&#8221;', wptexturize('Here is "<a href="http://example.com">a test with a link</a> and some text quoted"'));
87
		//$this->assertEquals('Here is &#8220;<a href="http://example.com">a test with a link</a>&#8221;, and a comma.', wptexturize('Here is "<a href="http://example.com">a test with a link</a>", and a comma.'));
88
		//$this->assertEquals('Here is &#8220;<a href="http://example.com">a test with a link</a>&#8221;; and a semi-colon.', wptexturize('Here is "<a href="http://example.com">a test with a link</a>"; and a semi-colon.'));
89
		//$this->assertEquals('Here is &#8220;<a href="http://example.com">a test with a link</a>&#8221;- and a dash.', wptexturize('Here is "<a href="http://example.com">a test with a link</a>"- and a dash.'));
90
		//$this->assertEquals('Here is &#8220;<a href="http://example.com">a test with a link</a>&#8221;&#8230; and ellipses.', wptexturize('Here is "<a href="http://example.com">a test with a link</a>"... and ellipses.'));
91
		//$this->assertEquals('Here is &#8220;a test <a href="http://example.com">with a link</a>&#8221;.', wptexturize('Here is "a test <a href="http://example.com">with a link</a>".'));
92
		//$this->assertEquals('Here is &#8220;<a href="http://example.com">a test with a link</a>&#8221;and a work stuck to the end.', wptexturize('Here is "<a href="http://example.com">a test with a link</a>"and a work stuck to the end.'));
93
		$this->assertEquals('A test with a finishing number, &#8220;like 23&#8221;.', wptexturize('A test with a finishing number, "like 23".'));
94
		$this->assertEquals('A test with a number, &#8220;like 62&#8221;, is nice to have.', wptexturize('A test with a number, "like 62", is nice to have.'));
95
	}
96
97
	/**
98
	 * @ticket 4539
99
	 */
100
	function test_quotes_before_s() {
101
		$this->assertEquals('test&#8217;s', wptexturize("test's"));
102
		$this->assertEquals('&#8216;test&#8217;s', wptexturize("'test's"));
103
		$this->assertEquals('&#8216;test&#8217;s&#8217;', wptexturize("'test's'"));
104
		$this->assertEquals('&#8216;string&#8217;', wptexturize("'string'"));
105
		$this->assertEquals('&#8216;string&#8217;s&#8217;', wptexturize("'string's'"));
106
	}
107
108
	/**
109
	 * @ticket 4539
110
	 */
111
	function test_quotes_before_numbers() {
112
		$this->assertEquals('Class of &#8217;99', wptexturize("Class of '99"));
113
		$this->assertEquals('Class of &#8217;99&#8217;s', wptexturize("Class of '99's"));
114
		$this->assertEquals('&#8216;Class of &#8217;99&#8217;', wptexturize("'Class of '99'"));
115
		$this->assertEquals('&#8216;Class of &#8217;99&#8217; ', wptexturize("'Class of '99' "));
116
		$this->assertEquals('&#8216;Class of &#8217;99&#8217;.', wptexturize("'Class of '99'."));
117
		$this->assertEquals('&#8216;Class of &#8217;99&#8217;, she said', wptexturize("'Class of '99', she said"));
118
		$this->assertEquals('&#8216;Class of &#8217;99&#8217;:', wptexturize("'Class of '99':"));
119
		$this->assertEquals('&#8216;Class of &#8217;99&#8217;;', wptexturize("'Class of '99';"));
120
		$this->assertEquals('&#8216;Class of &#8217;99&#8217;!', wptexturize("'Class of '99'!"));
121
		$this->assertEquals('&#8216;Class of &#8217;99&#8217;?', wptexturize("'Class of '99'?"));
122
		$this->assertEquals('&#8216;Class of &#8217;99&#8217;s&#8217;', wptexturize("'Class of '99's'"));
123
		$this->assertEquals('&#8216;Class of &#8217;99&#8217;s&#8217;', wptexturize("'Class of '99&#8217;s'"));
124
		$this->assertEquals('&#8220;Class of 99&#8221;', wptexturize("\"Class of 99\""));
125
		$this->assertEquals('&#8220;Class of &#8217;99&#8221;', wptexturize("\"Class of '99\""));
126
		$this->assertEquals('{&#8220;Class of &#8217;99&#8221;}', wptexturize("{\"Class of '99\"}"));
127
		$this->assertEquals(' &#8220;Class of &#8217;99&#8221; ', wptexturize(" \"Class of '99\" "));
128
		$this->assertEquals(' &#8220;Class of &#8217;99&#8221;.', wptexturize(" \"Class of '99\"."));
129
		$this->assertEquals(' &#8220;Class of &#8217;99&#8221;, she said', wptexturize(" \"Class of '99\", she said"));
130
		$this->assertEquals(' &#8220;Class of &#8217;99&#8221;:', wptexturize(" \"Class of '99\":"));
131
		$this->assertEquals(' &#8220;Class of &#8217;99&#8221;;', wptexturize(" \"Class of '99\";"));
132
		$this->assertEquals(' &#8220;Class of &#8217;99&#8221;!', wptexturize(" \"Class of '99\"!"));
133
		$this->assertEquals(' &#8220;Class of &#8217;99&#8221;?', wptexturize(" \"Class of '99\"?"));
134
		$this->assertEquals('}&#8221;Class of &#8217;99&#8243;{', wptexturize("}\"Class of '99\"{")); // Not a quotation, may be between two other quotations.
135
	}
136
137
	function test_quotes_after_numbers() {
138
		$this->assertEquals('Class of &#8217;99', wptexturize("Class of '99"));
139
	}
140
141
	/**
142
	 * @ticket 4539
143
	 * @ticket 15241
144
	 */
145
	function test_other_html() {
146
		$this->assertEquals('&#8216;<strong>', wptexturize("'<strong>"));
147
		//$this->assertEquals('&#8216;<strong>Quoted Text</strong>&#8217;,', wptexturize("'<strong>Quoted Text</strong>',"));
148
		//$this->assertEquals('&#8220;<strong>Quoted Text</strong>&#8221;,', wptexturize('"<strong>Quoted Text</strong>",'));
149
	}
150
151
	function test_x() {
152
		$this->assertEquals('14&#215;24', wptexturize("14x24"));
153
	}
154
155 View Code Duplication
	function test_minutes_seconds() {
156
		$this->assertEquals('9&#8242;', wptexturize('9\''));
157
		$this->assertEquals('9&#8243;', wptexturize("9\""));
158
159
		$this->assertEquals('a 9&#8242; b', wptexturize('a 9\' b'));
160
		$this->assertEquals('a 9&#8243; b', wptexturize("a 9\" b"));
161
162
		$this->assertEquals('&#8220;a 9&#8242; b&#8221;', wptexturize('"a 9\' b"'));
163
		$this->assertEquals('&#8216;a 9&#8243; b&#8217;', wptexturize("'a 9\" b'"));
164
	}
165
166
	/**
167
	 * @ticket 8775
168
	 */
169
	function test_wptexturize_quotes_around_numbers() {
170
		$this->assertEquals('&#8220;12345&#8221;', wptexturize('"12345"'));
171
		$this->assertEquals('&#8216;12345&#8217;', wptexturize('\'12345\''));
172
		$this->assertEquals('&#8220;a 9&#8242; plus a &#8216;9&#8217;, maybe a 9&#8242; &#8216;9&#8217;&#8221;', wptexturize('"a 9\' plus a \'9\', maybe a 9\' \'9\'"'));
173
		$this->assertEquals('<p>&#8217;99<br />&#8216;123&#8217;<br />&#8217;tis<br />&#8216;s&#8217;</p>', wptexturize('<p>\'99<br />\'123\'<br />\'tis<br />\'s\'</p>'));
174
	}
175
176
	/**
177
	 * @ticket 8912
178
	 */
179
	function test_wptexturize_html_comments() {
180
		$this->assertEquals('<!--[if !IE]>--><!--<![endif]-->', wptexturize('<!--[if !IE]>--><!--<![endif]-->'));
181
		$this->assertEquals('<!--[if !IE]>"a 9\' plus a \'9\', maybe a 9\' \'9\' "<![endif]-->', wptexturize('<!--[if !IE]>"a 9\' plus a \'9\', maybe a 9\' \'9\' "<![endif]-->'));
182
		$this->assertEquals('<ul><li>Hello.</li><!--<li>Goodbye.</li>--></ul>', wptexturize('<ul><li>Hello.</li><!--<li>Goodbye.</li>--></ul>'));
183
	}
184
185
	/**
186
	 * @ticket 4539
187
	 * @ticket 15241
188
	 */
189
	function test_entity_quote_cuddling() {
190
		$this->assertEquals('&nbsp;&#8220;Testing&#8221;', wptexturize('&nbsp;"Testing"'));
191
		//$this->assertEquals('&#38;&#8220;Testing&#8221;', wptexturize('&#38;"Testing"'));
192
	}
193
194
	/**
195
	 * @ticket 22823
196
	 */
197
	function test_apostrophes_before_primes() {
198
		$this->assertEquals( 'WordPress 3.5&#8217;s release date', wptexturize( "WordPress 3.5's release date" ) );
199
	}
200
201
	/**
202
	 * @ticket 23185
203
	 */
204
	function test_spaces_around_hyphens() {
205
		$nbsp = "\xC2\xA0";
206
207
		$this->assertEquals( ' &#8211; ', wptexturize( ' - ' ) );
208
		$this->assertEquals( '&nbsp;&#8211;&nbsp;', wptexturize( '&nbsp;-&nbsp;' ) );
209
		$this->assertEquals( ' &#8211;&nbsp;', wptexturize( ' -&nbsp;' ) );
210
		$this->assertEquals( '&nbsp;&#8211; ', wptexturize( '&nbsp;- ') );
211
		$this->assertEquals( "$nbsp&#8211;$nbsp", wptexturize( "$nbsp-$nbsp" ) );
212
		$this->assertEquals( " &#8211;$nbsp", wptexturize( " -$nbsp" ) );
213
		$this->assertEquals( "$nbsp&#8211; ", wptexturize( "$nbsp- ") );
214
215
		$this->assertEquals( ' &#8212; ', wptexturize( ' -- ' ) );
216
		$this->assertEquals( '&nbsp;&#8212;&nbsp;', wptexturize( '&nbsp;--&nbsp;' ) );
217
		$this->assertEquals( ' &#8212;&nbsp;', wptexturize( ' --&nbsp;' ) );
218
		$this->assertEquals( '&nbsp;&#8212; ', wptexturize( '&nbsp;-- ') );
219
		$this->assertEquals( "$nbsp&#8212;$nbsp", wptexturize( "$nbsp--$nbsp" ) );
220
		$this->assertEquals( " &#8212;$nbsp", wptexturize( " --$nbsp" ) );
221
		$this->assertEquals( "$nbsp&#8212; ", wptexturize( "$nbsp-- ") );
222
	}
223
224
	/**
225
	 * @ticket 31030
226
	 */
227 View Code Duplication
	function test_hyphens_at_start_and_end() {
228
		$this->assertEquals( '&#8211; ', wptexturize( '- ' ) );
229
		$this->assertEquals( '&#8211; &#8211;', wptexturize( '- -' ) );
230
		$this->assertEquals( ' &#8211;', wptexturize( ' -' ) );
231
232
		$this->assertEquals( '&#8212; ', wptexturize( '-- ' ) );
233
		$this->assertEquals( '&#8212; &#8212;', wptexturize( '-- --' ) );
234
		$this->assertEquals( ' &#8212;', wptexturize( ' --' ) );
235
	}
236
237
	/**
238
	 * Test spaces around quotes.
239
	 *
240
	 * These should never happen, even if the desired output changes some day.
241
	 *
242
	 * @ticket 22692
243
	 */
244
	function test_spaces_around_quotes_never() {
245
		$nbsp = "\xC2\xA0";
246
247
		$problem_input  = "$nbsp\"A";
248
		$problem_output = "$nbsp&#8221;A";
249
250
		$this->assertNotEquals( $problem_output, wptexturize( $problem_input ) );
251
	}
252
253
	/**
254
	 * Test spaces around quotes.
255
	 *
256
	 * These are desirable outputs for the current design.
257
	 *
258
	 * @ticket 22692
259
	 * @dataProvider data_spaces_around_quotes
260
	 */
261
	function test_spaces_around_quotes( $input, $output ) {
0 ignored issues
show
Documentation introduced by
The return type could not be reliably inferred; please add a @return annotation.

Our type inference engine in quite powerful, but sometimes the code does not provide enough clues to go by. In these cases we request you to add a @return annotation as described here.

Loading history...
262
		return $this->assertEquals( $output, wptexturize( $input ) );
263
	}
264
265
	function data_spaces_around_quotes() {
266
		$nbsp = "\xC2\xA0";
267
		$pi   = "\xCE\xA0";
268
269
		return array(
270
			array(
271
				"stop. $nbsp\"A quote after 2 spaces.\"",
272
				"stop. $nbsp&#8220;A quote after 2 spaces.&#8221;",
273
			),
274
			array(
275
				"stop.$nbsp$nbsp\"A quote after 2 spaces.\"",
276
				"stop.$nbsp$nbsp&#8220;A quote after 2 spaces.&#8221;",
277
			),
278
			array(
279
				"stop. $nbsp'A quote after 2 spaces.'",
280
				"stop. $nbsp&#8216;A quote after 2 spaces.&#8217;",
281
			),
282
			array(
283
				"stop.$nbsp$nbsp'A quote after 2 spaces.'",
284
				"stop.$nbsp$nbsp&#8216;A quote after 2 spaces.&#8217;",
285
			),
286
			array(
287
				"stop. &nbsp;\"A quote after 2 spaces.\"",
288
				"stop. &nbsp;&#8220;A quote after 2 spaces.&#8221;",
289
			),
290
			array(
291
				"stop.&nbsp;&nbsp;\"A quote after 2 spaces.\"",
292
				"stop.&nbsp;&nbsp;&#8220;A quote after 2 spaces.&#8221;",
293
			),
294
			array(
295
				"stop. &nbsp;'A quote after 2 spaces.'",
296
				"stop. &nbsp;&#8216;A quote after 2 spaces.&#8217;",
297
			),
298
			array(
299
				"stop.&nbsp;&nbsp;'A quote after 2 spaces.'",
300
				"stop.&nbsp;&nbsp;&#8216;A quote after 2 spaces.&#8217;",
301
			),
302
			array(
303
				"Contraction: $pi's",
304
				"Contraction: $pi&#8217;s",
305
			),
306
		);
307
	}
308
309
	/**
310
	 * Apostrophe before a number always becomes &#8217 (apos);
311
	 *
312
	 * Checks all baseline patterns. If anything ever changes in wptexturize(), these tests may fail.
313
	 *
314
	 * @ticket 22692
315
	 * @dataProvider data_apos_before_digits
316
	 */
317
	function test_apos_before_digits( $input, $output ) {
0 ignored issues
show
Documentation introduced by
The return type could not be reliably inferred; please add a @return annotation.

Our type inference engine in quite powerful, but sometimes the code does not provide enough clues to go by. In these cases we request you to add a @return annotation as described here.

Loading history...
318
		return $this->assertEquals( $output, wptexturize( $input ) );
319
	}
320
321 View Code Duplication
	function data_apos_before_digits() {
322
		return array(
323
			array(
324
				"word '99 word",
325
				"word &#8217;99 word",
326
			),
327
			array(
328
				"word'99 word",
329
				"word&#8217;99 word",
330
			),
331
			array(
332
				"word '99word",
333
				"word &#8217;99word",
334
			),
335
			array(
336
				"word'99word",
337
				"word&#8217;99word",
338
			),
339
			array(
340
				"word '99&#8217;s word", // Appears as a separate but logically superfluous pattern in 3.8.
341
				"word &#8217;99&#8217;s word",
342
			),
343
			array(
344
				"according to our source, '33 students scored less than 50' on the test.", // Apostrophes and primes have priority over quotes
345
				"according to our source, &#8217;33 students scored less than 50&#8242; on the test.",
346
			),
347
		);
348
	}
349
350
	/**
351
	 * Apostrophe after a space or ([{<" becomes &#8216; (opening_single_quote)
352
	 *
353
	 * Checks all baseline patterns. If anything ever changes in wptexturize(), these tests may fail.
354
	 *
355
	 * @ticket 22692
356
	 * @dataProvider data_opening_single_quote
357
	 */
358
	function test_opening_single_quote( $input, $output ) {
0 ignored issues
show
Documentation introduced by
The return type could not be reliably inferred; please add a @return annotation.

Our type inference engine in quite powerful, but sometimes the code does not provide enough clues to go by. In these cases we request you to add a @return annotation as described here.

Loading history...
359
		return $this->assertEquals( $output, wptexturize( $input ) );
360
	}
361
362
	function data_opening_single_quote() {
363
		return array(
364
			array(
365
				"word 'word word",
366
				"word &#8216;word word",
367
			),
368
			array(
369
				"word ('word word",
370
				"word (&#8216;word word",
371
			),
372
			array(
373
				"word ['word word",
374
				"word [&#8216;word word",
375
			),
376
			array(
377
				"word <'word word", // Invalid HTML
378
				"word <'word word",
379
			),
380
			array(
381
				"word &lt;'word word", // Valid HTML input makes curly quotes.
382
				"word &lt;&#8216;word word",
383
			),
384
			array(
385
				"word {'word word",
386
				"word {&#8216;word word",
387
			),
388
			array(
389
				"word \"'word word",
390
				"word &#8220;&#8216;word word", // Two opening quotes
391
			),
392
			array(
393
				"'word word",
394
				"&#8216;word word",
395
			),
396
			array(
397
				"word('word word",
398
				"word(&#8216;word word",
399
			),
400
			array(
401
				"word['word word",
402
				"word[&#8216;word word",
403
			),
404
			array(
405
				"word<'word word",
406
				"word<'word word",
407
			),
408
			array(
409
				"word&lt;'word word",
410
				"word&lt;&#8216;word word",
411
			),
412
			array(
413
				"word{'word word",
414
				"word{&#8216;word word",
415
			),
416
			array(
417
				"word\"'word word",
418
				"word&#8221;&#8216;word word", // Closing quote, then opening quote
419
			),
420
			array(
421
				"word ' word word",
422
				"word &#8216; word word",
423
			),
424
			array(
425
				"word (' word word",
426
				"word (&#8216; word word",
427
			),
428
			array(
429
				"word [' word word",
430
				"word [&#8216; word word",
431
			),
432
			array(
433
				"word <' word word",
434
				"word <' word word",
435
			),
436
			array(
437
				"word &lt;' word word",
438
				"word &lt;&#8216; word word",
439
			),
440
			array(
441
				"word {' word word",
442
				"word {&#8216; word word",
443
			),
444
			array(
445
				"word \"' word word",
446
				"word &#8220;&#8216; word word", // Two opening quotes
447
			),
448
			array(
449
				"' word word",
450
				"&#8216; word word",
451
			),
452
			array(
453
				"word(' word word",
454
				"word(&#8216; word word",
455
			),
456
			array(
457
				"word[' word word",
458
				"word[&#8216; word word",
459
			),
460
			array(
461
				"word<' word word",
462
				"word<' word word",
463
			),
464
			array(
465
				"word&lt;' word word",
466
				"word&lt;&#8216; word word",
467
			),
468
			array(
469
				"word{' word word",
470
				"word{&#8216; word word",
471
			),
472
			array(
473
				"word\"' word word",
474
				"word&#8221;&#8216; word word", // Closing quote, then opening quote
475
			),
476
		);
477
	}
478
479
	/**
480
	 * Double quote after a number becomes &#8243; (double_prime)
481
	 *
482
	 * Checks all baseline patterns. If anything ever changes in wptexturize(), these tests may fail.
483
	 *
484
	 * @ticket 22692
485
	 * @dataProvider data_double_prime
486
	 */
487
	function test_double_prime( $input, $output ) {
0 ignored issues
show
Documentation introduced by
The return type could not be reliably inferred; please add a @return annotation.

Our type inference engine in quite powerful, but sometimes the code does not provide enough clues to go by. In these cases we request you to add a @return annotation as described here.

Loading history...
488
		return $this->assertEquals( $output, wptexturize( $input ) );
489
	}
490
491 View Code Duplication
	function data_double_prime() {
492
		return array(
493
			array(
494
				'word 99" word',
495
				'word 99&#8243; word',
496
			),
497
			array(
498
				'word 99"word',
499
				'word 99&#8243;word',
500
			),
501
			array(
502
				'word99" word',
503
				'word99&#8243; word',
504
			),
505
			array(
506
				'word99"word',
507
				'word99&#8243;word',
508
			),
509
		);
510
	}
511
512
	/**
513
	 * Apostrophe after a number becomes &#8242; (prime)
514
	 *
515
	 * Checks all baseline patterns. If anything ever changes in wptexturize(), these tests may fail.
516
	 *
517
	 * @ticket 22692
518
	 * @dataProvider data_single_prime
519
	 */
520
	function test_single_prime( $input, $output ) {
0 ignored issues
show
Documentation introduced by
The return type could not be reliably inferred; please add a @return annotation.

Our type inference engine in quite powerful, but sometimes the code does not provide enough clues to go by. In these cases we request you to add a @return annotation as described here.

Loading history...
521
		return $this->assertEquals( $output, wptexturize( $input ) );
522
	}
523
524 View Code Duplication
	function data_single_prime() {
525
		return array(
526
			array(
527
				"word 99' word",
528
				"word 99&#8242; word",
529
			),
530
			array(
531
				"word 99'word", // Not a prime anymore. Apostrophes get priority.
532
				"word 99&#8217;word",
533
			),
534
			array(
535
				"word99' word",
536
				"word99&#8242; word",
537
			),
538
			array(
539
				"word99'word", // Not a prime anymore.
540
				"word99&#8217;word",
541
			),
542
		);
543
	}
544
545
	/**
546
	 * Apostrophe "in a word" becomes &#8217; (apos)
547
	 *
548
	 * Checks all baseline patterns. If anything ever changes in wptexturize(), these tests may fail.
549
	 *
550
	 * @ticket 22692
551
	 * @dataProvider data_contractions
552
	 */
553
	function test_contractions( $input, $output ) {
0 ignored issues
show
Documentation introduced by
The return type could not be reliably inferred; please add a @return annotation.

Our type inference engine in quite powerful, but sometimes the code does not provide enough clues to go by. In these cases we request you to add a @return annotation as described here.

Loading history...
554
		return $this->assertEquals( $output, wptexturize( $input ) );
555
	}
556
557 View Code Duplication
	function data_contractions() {
558
		return array(
559
			array(
560
				"word word's word",
561
				"word word&#8217;s word",
562
			),
563
			array(
564
				"word'[ word", // Apostrophes are never followed by opening punctuation.
565
				"word'[ word",
566
			),
567
			array(
568
				"word'( word",
569
				"word'( word",
570
			),
571
			array(
572
				"word'{ word",
573
				"word'{ word",
574
			),
575
			array(
576
				"word'&lt; word",
577
				"word'&lt; word",
578
			),
579
			array(
580
				"word'< word", // Invalid HTML input does trigger the apos pattern.
581
				"word&#8217;< word",
582
			),
583
		);
584
	}
585
586
	/**
587
	 * Double quote after a space or ([-{< becomes &#8220; (opening_quote) if not followed by spaces
588
	 *
589
	 * Checks all baseline patterns. If anything ever changes in wptexturize(), these tests may fail.
590
	 *
591
	 * @ticket 22692
592
	 * @dataProvider data_opening_quote
593
	 */
594
	function test_opening_quote( $input, $output ) {
0 ignored issues
show
Documentation introduced by
The return type could not be reliably inferred; please add a @return annotation.

Our type inference engine in quite powerful, but sometimes the code does not provide enough clues to go by. In these cases we request you to add a @return annotation as described here.

Loading history...
595
		return $this->assertEquals( $output, wptexturize( $input ) );
596
	}
597
598 View Code Duplication
	function data_opening_quote() {
599
		return array(
600
			array(
601
				'word "word word',
602
				'word &#8220;word word',
603
			),
604
			array(
605
				'word ("word word',
606
				'word (&#8220;word word',
607
			),
608
			array(
609
				'word ["word word',
610
				'word [&#8220;word word',
611
			),
612
			array(
613
				'word <"word word', // Invalid HTML
614
				'word <"word word',
615
			),
616
			array(
617
				'word &lt;"word word',
618
				'word &lt;&#8220;word word',
619
			),
620
			array(
621
				'word {"word word',
622
				'word {&#8220;word word',
623
			),
624
			array(
625
				'word -"word word',
626
				'word -&#8220;word word',
627
			),
628
			array(
629
				'word-"word word',
630
				'word-&#8220;word word',
631
			),
632
			array(
633
				'"word word',
634
				'&#8220;word word',
635
			),
636
			array(
637
				'word("word word',
638
				'word(&#8220;word word',
639
			),
640
			array(
641
				'word["word word',
642
				'word[&#8220;word word',
643
			),
644
			array(
645
				'word<"word word',
646
				'word<"word word',
647
			),
648
			array(
649
				'word&lt;"word word',
650
				'word&lt;&#8220;word word',
651
			),
652
			array(
653
				'word{"word word',
654
				'word{&#8220;word word',
655
			),
656
			array(
657
				'word "99 word',
658
				'word &#8220;99 word',
659
			),
660
		);
661
	}
662
663
	/**
664
	 * Double quote becomes &#8221; (closing_quote) unless it is already converted to double_prime or opening_quote.
665
	 *
666
	 * Checks all baseline patterns. If anything ever changes in wptexturize(), these tests may fail.
667
	 *
668
	 * @ticket 22692
669
	 * @dataProvider data_closing_quote
670
	 */
671
	function test_closing_quote( $input, $output ) {
0 ignored issues
show
Documentation introduced by
The return type could not be reliably inferred; please add a @return annotation.

Our type inference engine in quite powerful, but sometimes the code does not provide enough clues to go by. In these cases we request you to add a @return annotation as described here.

Loading history...
672
		return $this->assertEquals( $output, wptexturize( $input ) );
673
	}
674
675 View Code Duplication
	function data_closing_quote() {
676
		return array(
677
			array(
678
				'word word" word',
679
				'word word&#8221; word',
680
			),
681
			array(
682
				'word word") word',
683
				'word word&#8221;) word',
684
			),
685
			array(
686
				'word word"] word',
687
				'word word&#8221;] word',
688
			),
689
			array(
690
				'word word"} word',
691
				'word word&#8221;} word',
692
			),
693
			array(
694
				'word word"> word', // Invalid HTML input?
695
				'word word&#8221;> word',
696
			),
697
			array(
698
				'word word"&gt; word', // Valid HTML should work
699
				'word word&#8221;&gt; word',
700
			),
701
			array(
702
				'word word"',
703
				'word word&#8221;',
704
			),
705
			array(
706
				'word word"word',
707
				'word word&#8221;word',
708
			),
709
			array(
710
				'word"word"word',
711
				'word&#8221;word&#8221;word',
712
			),
713
			array(
714
				'test sentence".',
715
				'test sentence&#8221;.',
716
			),
717
			array(
718
				'test sentence",',
719
				'test sentence&#8221;,',
720
			),
721
			array(
722
				'test sentence":',
723
				'test sentence&#8221;:',
724
			),
725
			array(
726
				'test sentence";',
727
				'test sentence&#8221;;',
728
			),
729
			array(
730
				'test sentence"!',
731
				'test sentence&#8221;!',
732
			),
733
			array(
734
				'test sentence"?',
735
				'test sentence&#8221;?',
736
			),
737
			array(
738
				'test sentence."',
739
				'test sentence.&#8221;',
740
			),
741
			array(
742
				'test sentence". word',
743
				'test sentence&#8221;. word',
744
			),
745
			array(
746
				'test sentence." word',
747
				'test sentence.&#8221; word',
748
			),
749
		);
750
	}
751
752
	/**
753
	 * Test that single quotes followed by a space or .,-)}]> become &#8217; (closing_single_quote)
754
	 *
755
	 * Checks all baseline patterns. If anything ever changes in wptexturize(), these tests may fail.
756
	 *
757
	 * @ticket 22692
758
	 * @dataProvider data_closing_single_quote
759
	 */
760
	function test_closing_single_quote( $input, $output ) {
0 ignored issues
show
Documentation introduced by
The return type could not be reliably inferred; please add a @return annotation.

Our type inference engine in quite powerful, but sometimes the code does not provide enough clues to go by. In these cases we request you to add a @return annotation as described here.

Loading history...
761
		return $this->assertEquals( $output, wptexturize( $input ) );
762
	}
763
764 View Code Duplication
	function data_closing_single_quote() {
765
		return array(
766
			array(
767
				"word word' word",
768
				"word word&#8217; word",
769
			),
770
			array(
771
				"word word'. word",
772
				"word word&#8217;. word",
773
			),
774
			array(
775
				"word word'.word",
776
				"word word&#8217;.word",
777
			),
778
			array(
779
				"word word', she said",
780
				"word word&#8217;, she said",
781
			),
782
			array(
783
				"word word': word",
784
				"word word&#8217;: word",
785
			),
786
			array(
787
				"word word'; word",
788
				"word word&#8217;; word",
789
			),
790
			array(
791
				"word word'! word",
792
				"word word&#8217;! word",
793
			),
794
			array(
795
				"word word'? word",
796
				"word word&#8217;? word",
797
			),
798
			array(
799
				"word word'- word",
800
				"word word&#8217;- word",
801
			),
802
			array(
803
				"word word') word",
804
				"word word&#8217;) word",
805
			),
806
			array(
807
				"word word'} word",
808
				"word word&#8217;} word",
809
			),
810
			array(
811
				"word word'] word",
812
				"word word&#8217;] word",
813
			),
814
			array(
815
				"word word'&gt; word",
816
				"word word&#8217;&gt; word",
817
			),
818
			array(
819
				"word word'",
820
				"word word&#8217;",
821
			),
822
			array(
823
				"test sentence'.",
824
				"test sentence&#8217;.",
825
			),
826
			array(
827
				"test sentence.'",
828
				"test sentence.&#8217;",
829
			),
830
			array(
831
				"test sentence'. word",
832
				"test sentence&#8217;. word",
833
			),
834
			array(
835
				"test sentence.' word",
836
				"test sentence.&#8217; word",
837
			),
838
		);
839
	}
840
841
	/**
842
	 * Tests multiplication.
843
	 *
844
	 * Checks all baseline patterns. If anything ever changes in wptexturize(), these tests may fail.
845
	 *
846
	 * @ticket 22692
847
	 * @dataProvider data_multiplication
848
	 */
849
	function test_multiplication( $input, $output ) {
0 ignored issues
show
Documentation introduced by
The return type could not be reliably inferred; please add a @return annotation.

Our type inference engine in quite powerful, but sometimes the code does not provide enough clues to go by. In these cases we request you to add a @return annotation as described here.

Loading history...
850
		return $this->assertEquals( $output, wptexturize( $input ) );
851
	}
852
853
	function data_multiplication() {
854
		return array(
855
			array(
856
				"9x9",
857
				"9&#215;9",
858
			),
859
			array(
860
				"12x34",
861
				"12&#215;34",
862
			),
863
			array(
864
				"-123x1=-123",
865
				"-123&#215;1=-123",
866
			),
867
			// @ticket 30445
868
			array(
869
				"-123x-1",
870
				"-123x-1",
871
			),
872
			array(
873
				"0.675x1=0.675",
874
				"0.675&#215;1=0.675",
875
			),
876
			array(
877
				"9 x 9",
878
				"9 x 9",
879
			),
880
			array(
881
				"0x70",
882
				"0x70",
883
			),
884
			array(
885
				"3x2x1x0",
886
				"3x2x1x0",
887
			),
888
		);
889
	}
890
891
	/**
892
	 * Test ampersands. & always becomes &#038; unless it is followed by # or ;
893
	 *
894
	 * Checks all baseline patterns. If anything ever changes in wptexturize(), these tests may fail.
895
	 *
896
	 * @ticket 22692
897
	 * @dataProvider data_ampersand
898
	 */
899
	function test_ampersand( $input, $output ) {
0 ignored issues
show
Documentation introduced by
The return type could not be reliably inferred; please add a @return annotation.

Our type inference engine in quite powerful, but sometimes the code does not provide enough clues to go by. In these cases we request you to add a @return annotation as described here.

Loading history...
900
		return $this->assertEquals( $output, wptexturize( $input ) );
901
	}
902
903 View Code Duplication
	function data_ampersand() {
904
		return array(
905
			array(
906
				"word & word",
907
				"word &#038; word",
908
			),
909
			array(
910
				"word&word",
911
				"word&#038;word",
912
			),
913
			array(
914
				"word &nbsp; word",
915
				"word &nbsp; word",
916
			),
917
			array(
918
				"word &#038; word",
919
				"word &#038; word",
920
			),
921
			array(
922
				"word &#xabc; word",
923
				"word &#xabc; word",
924
			),
925
			array(
926
				"word &#X394; word",
927
				"word &#X394; word",
928
			),
929
			array(
930
				"word &# word",
931
				"word &#038;# word",
932
			),
933
			array(
934
				"word &44; word",
935
				"word &44; word",
936
			),
937
			array(
938
				"word &&amp; word",
939
				"word &#038;&amp; word",
940
			),
941
			array(
942
				"word &!amp; word",
943
				"word &#038;!amp; word",
944
			),
945
			array(
946
				"word &#",
947
				"word &#038;#",
948
			),
949
			array(
950
				"word &",
951
				"word &#038;",
952
			),
953
		);
954
	}
955
956
	/**
957
	 * Test "cockney" phrases, which begin with an apostrophe instead of an opening single quote.
958
	 *
959
	 * Checks all baseline patterns. If anything ever changes in wptexturize(), these tests may fail.
960
	 *
961
	 * @ticket 22692
962
	 * @dataProvider data_cockney
963
	 */
964
	function test_cockney( $input, $output ) {
0 ignored issues
show
Documentation introduced by
The return type could not be reliably inferred; please add a @return annotation.

Our type inference engine in quite powerful, but sometimes the code does not provide enough clues to go by. In these cases we request you to add a @return annotation as described here.

Loading history...
965
		return $this->assertEquals( $output, wptexturize( $input ) );
966
	}
967
968 View Code Duplication
	function data_cockney() {
969
		return array(
970
			array(
971
				"word 'tain't word",
972
				"word &#8217;tain&#8217;t word",
973
			),
974
			array(
975
				"word 'twere word",
976
				"word &#8217;twere word",
977
			),
978
			array(
979
				"word 'twas word",
980
				"word &#8217;twas word",
981
			),
982
			array(
983
				"word 'tis word",
984
				"word &#8217;tis word",
985
			),
986
			array(
987
				"word 'twill word",
988
				"word &#8217;twill word",
989
			),
990
			array(
991
				"word 'til word",
992
				"word &#8217;til word",
993
			),
994
			array(
995
				"word 'bout word",
996
				"word &#8217;bout word",
997
			),
998
			array(
999
				"word 'nuff word",
1000
				"word &#8217;nuff word",
1001
			),
1002
			array(
1003
				"word 'round word",
1004
				"word &#8217;round word",
1005
			),
1006
			array(
1007
				"word 'cause word",
1008
				"word &#8217;cause word",
1009
			),
1010
			array(
1011
				"word 'em word",
1012
				"word &#8217;em word",
1013
			),
1014
		);
1015
	}
1016
1017
	/**
1018
	 * Test smart dashes.
1019
	 *
1020
	 * Checks all baseline patterns. If anything ever changes in wptexturize(), these tests may fail.
1021
	 *
1022
	 * @ticket 22692
1023
	 * @dataProvider data_smart_dashes
1024
	 */
1025
	function test_smart_dashes( $input, $output ) {
0 ignored issues
show
Documentation introduced by
The return type could not be reliably inferred; please add a @return annotation.

Our type inference engine in quite powerful, but sometimes the code does not provide enough clues to go by. In these cases we request you to add a @return annotation as described here.

Loading history...
1026
		return $this->assertEquals( $output, wptexturize( $input ) );
1027
	}
1028
1029
	function data_smart_dashes() {
1030
		return array(
1031
			array(
1032
				"word --- word",
1033
				"word &#8212; word",
1034
			),
1035
			array(
1036
				"word---word",
1037
				"word&#8212;word",
1038
			),
1039
			array(
1040
				"word -- word",
1041
				"word &#8212; word",
1042
			),
1043
			array(
1044
				"word--word",
1045
				"word&#8211;word",
1046
			),
1047
			array(
1048
				"word - word",
1049
				"word &#8211; word",
1050
			),
1051
			array(
1052
				"word-word",
1053
				"word-word",
1054
			),
1055
			array(
1056
				"word xn&#8211; word",
1057
				"word xn&#8211; word",
1058
			),
1059
			array(
1060
				"wordxn&#8211;word",
1061
				"wordxn&#8211;word",
1062
			),
1063
			array(
1064
				"wordxn--word",
1065
				"wordxn--word",
1066
			),
1067
		);
1068
	}
1069
1070
	/**
1071
	 * Test miscellaneous static replacements.
1072
	 *
1073
	 * Checks all baseline patterns. If anything ever changes in wptexturize(), these tests may fail.
1074
	 *
1075
	 * @ticket 22692
1076
	 * @dataProvider data_misc_static_replacements
1077
	 */
1078
	function test_misc_static_replacements( $input, $output ) {
0 ignored issues
show
Documentation introduced by
The return type could not be reliably inferred; please add a @return annotation.

Our type inference engine in quite powerful, but sometimes the code does not provide enough clues to go by. In these cases we request you to add a @return annotation as described here.

Loading history...
1079
		return $this->assertEquals( $output, wptexturize( $input ) );
1080
	}
1081
1082
	function data_misc_static_replacements() {
1083
		return array(
1084
			array(
1085
				"word ... word",
1086
				"word &#8230; word",
1087
			),
1088
			array(
1089
				"word...word",
1090
				"word&#8230;word",
1091
			),
1092
			array(
1093
				"word `` word",
1094
				"word &#8220; word",
1095
			),
1096
			array(
1097
				"word``word",
1098
				"word&#8220;word",
1099
			),
1100
			array(
1101
				"word '' word",
1102
				"word &#8221; word",
1103
			),
1104
			array(
1105
				"word''word",
1106
				"word&#8221;word",
1107
			),
1108
			array(
1109
				"word (tm) word",
1110
				"word &#8482; word",
1111
			),
1112
			array(
1113
				"word (tm)word",
1114
				"word &#8482;word",
1115
			),
1116
			array(
1117
				"word(tm) word",
1118
				"word(tm) word",
1119
			),
1120
			array(
1121
				"word(tm)word",
1122
				"word(tm)word",
1123
			),
1124
		);
1125
	}
1126
1127
	/**
1128
	 * Numbers inside of matching quotes get curly quotes instead of apostrophes and primes.
1129
	 *
1130
	 * @ticket 8775
1131
	 * @dataProvider data_quoted_numbers
1132
	 */
1133
	function test_quoted_numbers( $input, $output ) {
0 ignored issues
show
Documentation introduced by
The return type could not be reliably inferred; please add a @return annotation.

Our type inference engine in quite powerful, but sometimes the code does not provide enough clues to go by. In these cases we request you to add a @return annotation as described here.

Loading history...
1134
		return $this->assertEquals( $output, wptexturize( $input ) );
1135
	}
1136
1137 View Code Duplication
	function data_quoted_numbers() {
1138
		return array(
1139
			array(
1140
				'word "42.00" word',
1141
				'word &#8220;42.00&#8221; word',
1142
			),
1143
			array(
1144
				'word "42.00"word',
1145
				'word &#8220;42.00&#8221;word',
1146
			),
1147
			array(
1148
				"word '42.00' word",
1149
				"word &#8216;42.00&#8217; word",
1150
			),
1151
			array(
1152
				"word '42.00'word",
1153
				"word &#8216;42.00&#8217;word",
1154
			),
1155
			array(
1156
				'word "42" word',
1157
				'word &#8220;42&#8221; word',
1158
			),
1159
			array(
1160
				'word "42,00" word',
1161
				'word &#8220;42,00&#8221; word',
1162
			),
1163
			array(
1164
				'word "4,242.00" word',
1165
				'word &#8220;4,242.00&#8221; word',
1166
			),
1167
			array(
1168
				"word '99's word",
1169
				"word &#8217;99&#8217;s word",
1170
			),
1171
			array(
1172
				"word '99'samsonite",
1173
				"word &#8217;99&#8217;samsonite",
1174
			),
1175
		);
1176
	}
1177
1178
	/**
1179
	 * Quotations should be allowed to have dashes around them.
1180
	 *
1181
	 * @ticket 20342
1182
	 * @dataProvider data_quotes_and_dashes
1183
	 */
1184
	function test_quotes_and_dashes( $input, $output ) {
0 ignored issues
show
Documentation introduced by
The return type could not be reliably inferred; please add a @return annotation.

Our type inference engine in quite powerful, but sometimes the code does not provide enough clues to go by. In these cases we request you to add a @return annotation as described here.

Loading history...
1185
		return $this->assertEquals( $output, wptexturize( $input ) );
1186
	}
1187
1188 View Code Duplication
	function data_quotes_and_dashes() {
1189
		return array(
1190
			array(
1191
				'word---"quote"',
1192
				'word&#8212;&#8220;quote&#8221;',
1193
			),
1194
			array(
1195
				'word--"quote"',
1196
				'word&#8211;&#8220;quote&#8221;',
1197
			),
1198
			array(
1199
				'word-"quote"',
1200
				'word-&#8220;quote&#8221;',
1201
			),
1202
			array(
1203
				"word---'quote'",
1204
				"word&#8212;&#8216;quote&#8217;",
1205
			),
1206
			array(
1207
				"word--'quote'",
1208
				"word&#8211;&#8216;quote&#8217;",
1209
			),
1210
			array(
1211
				"word-'quote'",
1212
				"word-&#8216;quote&#8217;",
1213
			),
1214
			array(
1215
				'"quote"---word',
1216
				'&#8220;quote&#8221;&#8212;word',
1217
			),
1218
			array(
1219
				'"quote"--word',
1220
				'&#8220;quote&#8221;&#8211;word',
1221
			),
1222
			array(
1223
				'"quote"-word',
1224
				'&#8220;quote&#8221;-word',
1225
			),
1226
			array(
1227
				"'quote'---word",
1228
				"&#8216;quote&#8217;&#8212;word",
1229
			),
1230
			array(
1231
				"'quote'--word",
1232
				"&#8216;quote&#8217;&#8211;word",
1233
			),
1234
			array(
1235
				"'quote'-word",
1236
				"&#8216;quote&#8217;-word",
1237
			),
1238
		);
1239
	}
1240
1241
	/**
1242
	 * Test HTML and shortcode avoidance.
1243
	 *
1244
	 * @ticket 12690
1245
	 * @dataProvider data_tag_avoidance
1246
	 */
1247
	function test_tag_avoidance( $input, $output ) {
0 ignored issues
show
Documentation introduced by
The return type could not be reliably inferred; please add a @return annotation.

Our type inference engine in quite powerful, but sometimes the code does not provide enough clues to go by. In these cases we request you to add a @return annotation as described here.

Loading history...
1248
		return $this->assertEquals( $output, wptexturize( $input ) );
1249
	}
1250
1251
	function data_tag_avoidance() {
1252
		return array(
1253
			array(
1254
				'[ ... ]',
1255
				'[ &#8230; ]',
1256
			),
1257
			array(
1258
				'[ is it wise to <a title="allow user content ] here? hmm"> maybe </a> ]',
1259
				'[ is it wise to <a title="allow user content ] here? hmm"> maybe </a> ]',
1260
			),
1261
			array(
1262
				'[is it wise to <a title="allow user content ] here? hmm"> maybe </a> ]',
1263
				'[is it wise to <a title="allow user content ] here? hmm"> maybe </a> ]',
1264
			),
1265
			array(
1266
				'[caption - is it wise to <a title="allow user content ] here? hmm"> maybe </a> ]',
1267
				'[caption &#8211; is it wise to <a title="allow user content ] here? hmm"> maybe </a> ]',
1268
			),
1269
			array(
1270
				'[ photos by <a href="http://example.com/?a[]=1&a[]=2"> this guy & that guy </a> ]',
1271
				'[ photos by <a href="http://example.com/?a[]=1&#038;a[]=2"> this guy &#038; that guy </a> ]',
1272
			),
1273
			array(
1274
				'[photos by <a href="http://example.com/?a[]=1&a[]=2"> this guy & that guy </a>]',
1275
				'[photos by <a href="http://example.com/?a[]=1&#038;a[]=2"> this guy &#038; that guy </a>]',
1276
			),
1277
			array(
1278
				'& <script>&&</script>',
1279
				'&#038; <script>&&</script>'
1280
			),
1281
			array(
1282
				'[gallery ...]',
1283
				'[gallery ...]',
1284
			),
1285
			array(
1286
				'[[gallery ...]', // This tag is still valid.
1287
				'[[gallery ...]',
1288
			),
1289
			array(
1290
				'[gallery ...]]', // This tag is also valid.
1291
				'[gallery ...]]',
1292
			),
1293
			array(
1294
				'[/gallery ...]', // This would actually be ignored by the shortcode system.  The decision to not texturize it is intentional, if not correct.
1295
				'[/gallery ...]',
1296
			),
1297
			array(
1298
				'[[gallery]]...[[/gallery]]', // Shortcode parsing will ignore the inner ]...[ part and treat this as a single escaped shortcode.
1299
				'[[gallery]]&#8230;[[/gallery]]',
1300
			),
1301
			array(
1302
				'[[[gallery]]]...[[[/gallery]]]', // Again, shortcode parsing matches, but only the [[gallery] and [/gallery]] parts.
1303
				'[[[gallery]]]&#8230;[[[/gallery]]]',
1304
			),
1305
			array(
1306
				'[gallery ...',
1307
				'[gallery &#8230;',
1308
			),
1309
			array(
1310
				'[gallery <br ... /> ...]', // This tag is still valid. Shortcode 'attributes' are not considered in the initial parsing of shortcodes, and HTML is allowed.
1311
				'[gallery <br ... /> ...]',
1312
			),
1313
			array(
1314
				'<br [gallery ...] ... />',
1315
				'<br [gallery ...] ... />',
1316
			),
1317
			array(
1318
				'<br [gallery ...] ... /',
1319
				'<br [gallery ...] ... /',
1320
			),
1321
			array(
1322
				'<br ... />',
1323
				'<br ... />',
1324
			),
1325
			array(
1326
				'<br ... />...<br ... />',
1327
				'<br ... />&#8230;<br ... />',
1328
			),
1329
			array(
1330
				'[gallery ...]...[gallery ...]',
1331
				'[gallery ...]&#8230;[gallery ...]',
1332
			),
1333
			array(
1334
				'[[gallery ...]]',
1335
				'[[gallery ...]]',
1336
			),
1337
			array(
1338
				'[[gallery ...]',
1339
				'[[gallery ...]',
1340
			),
1341
			array(
1342
				'[gallery ...]]',
1343
				'[gallery ...]]',
1344
			),
1345
			array(
1346
				'[/gallery ...]]',
1347
				'[/gallery ...]]',
1348
			),
1349
			array(
1350
				'[[gallery <br ... /> ...]]', // This gets parsed as an escaped shortcode with embedded HTML.  Brains may explode.
1351
				'[[gallery <br ... /> ...]]',
1352
			),
1353
			array(
1354
				'<br [[gallery ...]] ... />',
1355
				'<br [[gallery ...]] ... />',
1356
			),
1357
			array(
1358
				'<br [[gallery ...]] ... /',
1359
				'<br [[gallery ...]] ... /',
1360
			),
1361
			array(
1362
				'[[gallery ...]]...[[gallery ...]]',
1363
				'[[gallery ...]]&#8230;[[gallery ...]]',
1364
			),
1365
			array(
1366
				'[[gallery ...]...[/gallery]]',
1367
				'[[gallery ...]&#8230;[/gallery]]',
1368
			),
1369
			array(
1370
				'<!-- ... -->',
1371
				'<!-- ... -->',
1372
			),
1373
			array(
1374
				'<!--...-->',
1375
				'<!--...-->',
1376
			),
1377
			array(
1378
				'<!-- ... -- > ...',
1379
				'<!-- ... -- > ...',
1380
			),
1381
			array(
1382
				'<!-- ...', // An unclosed comment is still a comment.
1383
				'<!-- ...',
1384
			),
1385
			array(
1386
				'a<!-->b', // Browsers seem to allow this.
1387
				'a<!-->b',
1388
			),
1389
			array(
1390
				'a<!--->b',
1391
				'a<!--->b',
1392
			),
1393
			array(
1394
				'a<!---->b',
1395
				'a<!---->b',
1396
			),
1397
			array(
1398
				'a<!----->b',
1399
				'a<!----->b',
1400
			),
1401
			array(
1402
				'a<!-- c --->b',
1403
				'a<!-- c --->b',
1404
			),
1405
			array(
1406
				'a<!-- c -- d -->b',
1407
				'a<!-- c -- d -->b',
1408
			),
1409
			array(
1410
				'a<!-- <!-- c --> -->b<!-- close -->',
1411
				'a<!-- <!-- c --> &#8211;>b<!-- close -->',
1412
			),
1413
			array(
1414
				'<!-- <br /> [gallery] ... -->',
1415
				'<!-- <br /> [gallery] ... -->',
1416
			),
1417
			array(
1418
				'...<!-- ... -->...',
1419
				'&#8230;<!-- ... -->&#8230;',
1420
			),
1421
			array(
1422
				'[gallery ...]...<!-- ... -->...<br ... />',
1423
				'[gallery ...]&#8230;<!-- ... -->&#8230;<br ... />',
1424
			),
1425
			array(
1426
				'<ul><li>Hello.</li><!--<li>Goodbye.</li>--></ul>',
1427
				'<ul><li>Hello.</li><!--<li>Goodbye.</li>--></ul>',
1428
			),
1429
			array(
1430
				'word <img src="http://example.com/wp-content/uploads/2014/06/image-300x216.gif" /> word', // Ensure we are not corrupting image URLs.
1431
				'word <img src="http://example.com/wp-content/uploads/2014/06/image-300x216.gif" /> word',
1432
			),
1433
			array(
1434
				'[ do texturize "[quote]" here ]',
1435
				'[ do texturize &#8220;[quote]&#8221; here ]',
1436
			),
1437
			array(
1438
				'[ regex catches this <a href="[quote]">here</a> ]',
1439
				'[ regex catches this <a href="[quote]">here</a> ]',
1440
			),
1441
			array(
1442
				'[ but also catches the <b>styled "[quote]" here</b> ]',
1443
				'[ but also catches the <b>styled &#8220;[quote]&#8221; here</b> ]',
1444
			),
1445
			array(
1446
				'[Let\'s get crazy<input>[caption code="<a href=\'?a[]=100\'>hello</a>"]</input>world]', // caption shortcode is invalid here because it contains [] chars.
1447
				'[Let&#8217;s get crazy<input>[caption code=&#8221;<a href=\'?a[]=100\'>hello</a>&#8220;]</input>world]',
1448
			),
1449
			array(
1450
				'<> ... <>',
1451
				'<> &#8230; <>',
1452
			),
1453
			array(
1454
				'<> ... <> ... >',
1455
				'<> &#8230; <> &#8230; >',
1456
			),
1457
			array(
1458
				'<> ... < ... > ... <>',
1459
				'<> &#8230; < ... > &#8230; <>',
1460
			),
1461
		);
1462
	}
1463
1464
	/**
1465
	 * Year abbreviations consist of exactly two digits.
1466
	 *
1467
	 * @ticket 26850
1468
	 * @dataProvider data_year_abbr
1469
	 */
1470
	function test_year_abbr( $input, $output ) {
0 ignored issues
show
Documentation introduced by
The return type could not be reliably inferred; please add a @return annotation.

Our type inference engine in quite powerful, but sometimes the code does not provide enough clues to go by. In these cases we request you to add a @return annotation as described here.

Loading history...
1471
		return $this->assertEquals( $output, wptexturize( $input ) );
1472
	}
1473
1474 View Code Duplication
	function data_year_abbr() {
1475
		return array(
1476
			array(
1477
				"word '99 word",
1478
				"word &#8217;99 word",
1479
			),
1480
			array(
1481
				"word '99. word",
1482
				"word &#8217;99. word",
1483
			),
1484
			array(
1485
				"word '99, word",
1486
				"word &#8217;99, word",
1487
			),
1488
			array(
1489
				"word '99; word",
1490
				"word &#8217;99; word",
1491
			),
1492
			array(
1493
				"word '99' word", // For this pattern, prime doesn't make sense.  Should get apos and a closing quote.
1494
				"word &#8217;99&#8217; word",
1495
			),
1496
			array(
1497
				"word '99'. word",
1498
				"word &#8217;99&#8217;. word",
1499
			),
1500
			array(
1501
				"word '99', word",
1502
				"word &#8217;99&#8217;, word",
1503
			),
1504
			array(
1505
				"word '99.' word",
1506
				"word &#8217;99.&#8217; word",
1507
			),
1508
			array(
1509
				"word '99",
1510
				"word &#8217;99",
1511
			),
1512
			array(
1513
				"'99 word",
1514
				"&#8217;99 word",
1515
			),
1516
			array(
1517
				"word '999 word", // Does not match the apos pattern, should be opening quote.
1518
				"word &#8216;999 word",
1519
			),
1520
			array(
1521
				"word '99% word",
1522
				"word &#8216;99% word",
1523
			),
1524
			array(
1525
				"word '9 word",
1526
				"word &#8216;9 word",
1527
			),
1528
			array(
1529
				"word '99.9 word",
1530
				"word &#8216;99.9 word",
1531
			),
1532
			array(
1533
				"word '999",
1534
				"word &#8216;999",
1535
			),
1536
			array(
1537
				"word '9",
1538
				"word &#8216;9",
1539
			),
1540
			array(
1541
				"in '4 years, 3 months,' Obama cut the deficit",
1542
				"in &#8216;4 years, 3 months,&#8217; Obama cut the deficit",
1543
			),
1544
			array(
1545
				"testing's '4' through 'quotes'",
1546
				"testing&#8217;s &#8216;4&#8217; through &#8216;quotes&#8217;",
1547
			),
1548
		);
1549
	}
1550
1551
	/**
1552
	 * Make sure translation actually works.
1553
	 *
1554
	 * Also make sure apostrophes and closing quotes aren't being confused by default.
1555
	 *
1556
	 * @ticket 27426
1557
	 * @dataProvider data_translate
1558
	 */
1559 View Code Duplication
	function test_translate( $input, $output ) {
0 ignored issues
show
Documentation introduced by
The return type could not be reliably inferred; please add a @return annotation.

Our type inference engine in quite powerful, but sometimes the code does not provide enough clues to go by. In these cases we request you to add a @return annotation as described here.

Loading history...
1560
		add_filter( 'gettext_with_context', array( $this, 'filter_translate' ), 10, 4 );
1561
1562
		$result = wptexturize( $input, true );
1563
1564
		remove_filter( 'gettext_with_context', array( $this, 'filter_translate' ), 10, 4 );
1565
		wptexturize( 'reset', true );
1566
1567
		return $this->assertEquals( $output, $result );
1568
	}
1569
1570 View Code Duplication
	function filter_translate( $translations, $text, $context, $domain ) {
0 ignored issues
show
Documentation introduced by
The return type could not be reliably inferred; please add a @return annotation.

Our type inference engine in quite powerful, but sometimes the code does not provide enough clues to go by. In these cases we request you to add a @return annotation as described here.

Loading history...
1571
		switch ($text) {
1572
			case '&#8211;' : return '!endash!';
1573
			case '&#8212;' : return '!emdash!';
1574
			case '&#8216;' : return '!openq1!';
1575
			case '&#8217;' :
1576
				if ( 'apostrophe' == $context ) {
1577
					return '!apos!';
1578
				} else {
1579
					return '!closeq1!';
1580
				}
1581
			case '&#8220;' : return '!openq2!';
1582
			case '&#8221;' : return '!closeq2!';
1583
			case '&#8242;' : return '!prime1!';
1584
			case '&#8243;' : return '!prime2!';
1585
			case '&#8217;tain&#8217;t,&#8217;twere,&#8217;twas,&#8217;tis,&#8217;twill,&#8217;til,&#8217;bout,&#8217;nuff,&#8217;round,&#8217;cause,&#8217;em' : 
1586
				return '!apos!tain!apos!t,!apos!twere,!apos!twas,!apos!tis,!apos!twill,!apos!til,!apos!bout,!apos!nuff,!apos!round,!apos!cause,!apos!em';
1587
			default : return $translations;
1588
		}
1589
	}
1590
1591
	function data_translate() {
1592
		return array(
1593
			array(
1594
				"word '99 word",
1595
				"word !apos!99 word",
1596
			),
1597
			array(
1598
				"word'99 word",
1599
				"word!apos!99 word",
1600
			),
1601
			array(
1602
				"word 'test sentence' word",
1603
				"word !openq1!test sentence!closeq1! word",
1604
			),
1605
			array(
1606
				"'test sentence'",
1607
				"!openq1!test sentence!closeq1!",
1608
			),
1609
			array(
1610
				'word "test sentence" word',
1611
				'word !openq2!test sentence!closeq2! word',
1612
			),
1613
			array(
1614
				'"test sentence"',
1615
				'!openq2!test sentence!closeq2!',
1616
			),
1617
			array(
1618
				"word 'word word",
1619
				"word !openq1!word word",
1620
			),
1621
			array(
1622
				"word ('word word",
1623
				"word (!openq1!word word",
1624
			),
1625
			array(
1626
				"word ['word word",
1627
				"word [!openq1!word word",
1628
			),
1629
			array(
1630
				'word 99" word',
1631
				'word 99!prime2! word',
1632
			),
1633
			array(
1634
				'word 99"word',
1635
				'word 99!prime2!word',
1636
			),
1637
			array(
1638
				'word99" word',
1639
				'word99!prime2! word',
1640
			),
1641
			array(
1642
				'word99"word',
1643
				'word99!prime2!word',
1644
			),
1645
			array(
1646
				"word 99' word",
1647
				"word 99!prime1! word",
1648
			),
1649
			array(
1650
				"word99' word",
1651
				"word99!prime1! word",
1652
			),
1653
			array(
1654
				"word word's word",
1655
				"word word!apos!s word",
1656
			),
1657
			array(
1658
				"word word'. word",
1659
				"word word!closeq1!. word",
1660
			),
1661
			array(
1662
				"word ]'. word",
1663
				"word ]!closeq1!. word",
1664
			),
1665
			array(
1666
				'word "word word',
1667
				'word !openq2!word word',
1668
			),
1669
			array(
1670
				'word ("word word',
1671
				'word (!openq2!word word',
1672
			),
1673
			array(
1674
				'word ["word word',
1675
				'word [!openq2!word word',
1676
			),
1677
			array(
1678
				'word word" word',
1679
				'word word!closeq2! word',
1680
			),
1681
			array(
1682
				'word word") word',
1683
				'word word!closeq2!) word',
1684
			),
1685
			array(
1686
				'word word"] word',
1687
				'word word!closeq2!] word',
1688
			),
1689
			array(
1690
				'word word"',
1691
				'word word!closeq2!',
1692
			),
1693
			array(
1694
				'word word"word',
1695
				'word word!closeq2!word',
1696
			),
1697
			array(
1698
				'test sentence".',
1699
				'test sentence!closeq2!.',
1700
			),
1701
			array(
1702
				'test sentence."',
1703
				'test sentence.!closeq2!',
1704
			),
1705
			array(
1706
				'test sentence." word',
1707
				'test sentence.!closeq2! word',
1708
			),
1709
			array(
1710
				"word word' word",
1711
				"word word!closeq1! word",
1712
			),
1713
			array(
1714
				"word word'. word",
1715
				"word word!closeq1!. word",
1716
			),
1717
			array(
1718
				"word word'.word",
1719
				"word word!closeq1!.word",
1720
			),
1721
			array(
1722
				"word word'",
1723
				"word word!closeq1!",
1724
			),
1725
			array(
1726
				"test sentence'.",
1727
				"test sentence!closeq1!.",
1728
			),
1729
			array(
1730
				"test sentence.'",
1731
				"test sentence.!closeq1!",
1732
			),
1733
			array(
1734
				"test sentence'. word",
1735
				"test sentence!closeq1!. word",
1736
			),
1737
			array(
1738
				"test sentence.' word",
1739
				"test sentence.!closeq1! word",
1740
			),
1741
			array(
1742
				"word 'tain't word",
1743
				"word !apos!tain!apos!t word",
1744
			),
1745
			array(
1746
				"word 'twere word",
1747
				"word !apos!twere word",
1748
			),
1749
			array(
1750
				'word "42.00" word',
1751
				'word !openq2!42.00!closeq2! word',
1752
			),
1753
			array(
1754
				"word '42.00' word",
1755
				"word !openq1!42.00!closeq1! word",
1756
			),
1757
			array(
1758
				"word word'. word",
1759
				"word word!closeq1!. word",
1760
			),
1761
			array(
1762
				"word word'.word",
1763
				"word word!closeq1!.word",
1764
			),
1765
			array(
1766
				"word word', she said",
1767
				"word word!closeq1!, she said",
1768
			),
1769
		);
1770
	}
1771
1772
	/**
1773
	 * Extra sanity checks for _wptexturize_pushpop_element()
1774
	 *
1775
	 * @ticket 28483
1776
	 * @dataProvider data_element_stack
1777
	 */
1778
	function test_element_stack( $input, $output ) {
0 ignored issues
show
Documentation introduced by
The return type could not be reliably inferred; please add a @return annotation.

Our type inference engine in quite powerful, but sometimes the code does not provide enough clues to go by. In these cases we request you to add a @return annotation as described here.

Loading history...
1779
		return $this->assertEquals( $output, wptexturize( $input ) );
1780
	}
1781
1782 View Code Duplication
	function data_element_stack() {
1783
		return array(
1784
			array(
1785
				'<span>hello</code>---</span>',
1786
				'<span>hello</code>&#8212;</span>',
1787
			),
1788
			array(
1789
				'</code>hello<span>---</span>',
1790
				'</code>hello<span>&#8212;</span>',
1791
			),
1792
			array(
1793
				'<code>hello</code>---</span>',
1794
				'<code>hello</code>&#8212;</span>',
1795
			),
1796
			array(
1797
				'<span>hello</span>---<code>',
1798
				'<span>hello</span>&#8212;<code>',
1799
			),
1800
			array(
1801
				'<span>hello<code>---</span>',
1802
				'<span>hello<code>---</span>',
1803
			),
1804
			array(
1805
				'<code>hello<span>---</span>',
1806
				'<code>hello<span>---</span>',
1807
			),
1808
			array(
1809
				'<code>hello</span>---</span>',
1810
				'<code>hello</span>---</span>',
1811
			),
1812
			array(
1813
				'<span><code>hello</code>---</span>',
1814
				'<span><code>hello</code>&#8212;</span>',
1815
			),
1816
			array(
1817
				'<code>hello</code>world<span>---</span>',
1818
				'<code>hello</code>world<span>&#8212;</span>',
1819
			),
1820
		);
1821
	}
1822
1823
	/**
1824
	 * Test disabling shortcode texturization.
1825
	 *
1826
	 * @ticket 29557
1827
	 * @dataProvider data_unregistered_shortcodes
1828
	 */
1829
	function test_unregistered_shortcodes( $input, $output ) {
0 ignored issues
show
Documentation introduced by
The return type could not be reliably inferred; please add a @return annotation.

Our type inference engine in quite powerful, but sometimes the code does not provide enough clues to go by. In these cases we request you to add a @return annotation as described here.

Loading history...
1830
		add_filter( 'no_texturize_shortcodes', array( $this, 'filter_shortcodes' ), 10, 1 );
1831
	
1832
		$output = $this->assertEquals( $output, wptexturize( $input ) );
1833
	
1834
		remove_filter( 'no_texturize_shortcodes', array( $this, 'filter_shortcodes' ), 10, 1 );
1835
		return $output;
1836
	}
1837
	
1838
	function filter_shortcodes( $disabled ) {
1839
		$disabled[] = 'audio';
1840
		return $disabled;
1841
	}
1842
1843 View Code Duplication
	function data_unregistered_shortcodes() {
1844
		return array(
1845
			array(
1846
				'[a]a--b[audio]---[/audio]a--b[/a]',
1847
				'[a]a&#8211;b[audio]---[/audio]a&#8211;b[/a]',
1848
			),
1849
			array(
1850
				'[code ...]...[/code]', // code is not a registered shortcode.
1851
				'[code &#8230;]&#8230;[/code]',
1852
			),
1853
			array(
1854
				'[hello ...]...[/hello]', // hello is not a registered shortcode.
1855
				'[hello &#8230;]&#8230;[/hello]',
1856
			),
1857
			array(
1858
				'[...]...[/...]', // These are potentially usable shortcodes.
1859
				'[&#8230;]&#8230;[/&#8230;]',
1860
			),
1861
			array(
1862
				'[gal>ery ...]',
1863
				'[gal>ery &#8230;]',
1864
			),
1865
			array(
1866
				'[randomthing param="test"]',
1867
				'[randomthing param=&#8221;test&#8221;]',
1868
			),
1869
			array(
1870
				'[[audio]...[/audio]...', // These are potentially usable shortcodes.  Unfortunately, the meaning of [[audio] is ambiguous unless we run the entire shortcode regexp.
1871
				'[[audio]&#8230;[/audio]&#8230;',
1872
			),
1873
			array(
1874
				'[audio]...[/audio]]...', // These are potentially usable shortcodes.  Unfortunately, the meaning of [/audio]] is ambiguous unless we run the entire shortcode regexp.
1875
				'[audio]...[/audio]]...', // This test would not pass in 3.9 because the extra brace was always ignored by texturize.
1876
			),
1877
			array(
1878
				'<span>hello[/audio]---</span>',
1879
				'<span>hello[/audio]&#8212;</span>',
1880
			),
1881
			array(
1882
				'[/audio]hello<span>---</span>',
1883
				'[/audio]hello<span>&#8212;</span>',
1884
			),
1885
			array(
1886
				'[audio]hello[/audio]---</span>',
1887
				'[audio]hello[/audio]&#8212;</span>',
1888
			),
1889
			array(
1890
				'<span>hello</span>---[audio]',
1891
				'<span>hello</span>&#8212;[audio]',
1892
			),
1893
			array(
1894
				'<span>hello[audio]---</span>',
1895
				'<span>hello[audio]---</span>',
1896
			),
1897
			array(
1898
				'[audio]hello<span>---</span>',
1899
				'[audio]hello<span>---</span>',
1900
			),
1901
			array(
1902
				'[audio]hello</span>---</span>',
1903
				'[audio]hello</span>---</span>',
1904
			),
1905
		);
1906
	}
1907
1908
	/**
1909
	 * Ensure primes logic is not too greedy at the end of a quotation.
1910
	 *
1911
	 * @ticket 29256
1912
	 * @dataProvider data_primes_vs_quotes
1913
	 */
1914
	function test_primes_vs_quotes( $input, $output ) {
0 ignored issues
show
Documentation introduced by
The return type could not be reliably inferred; please add a @return annotation.

Our type inference engine in quite powerful, but sometimes the code does not provide enough clues to go by. In these cases we request you to add a @return annotation as described here.

Loading history...
1915
		return $this->assertEquals( $output, wptexturize( $input ) );
1916
	}
1917
1918
	function data_primes_vs_quotes() {
1919
		return array(
1920
			array(
1921
				"George's porch is 99' long.",
1922
				"George&#8217;s porch is 99&#8242; long.",
1923
			),
1924
			array(
1925
				'The best year "was that time in 2012" when everyone partied, he said.',
1926
				'The best year &#8220;was that time in 2012&#8221; when everyone partied, he said.',
1927
			),
1928
			array(
1929
				"I need 4 x 20' = 80' of trim.", // Works only with a space before the = char.
1930
				"I need 4 x 20&#8242; = 80&#8242; of trim.",
1931
			),
1932
			array(
1933
				'"Lorem ipsum dolor sit amet 1234"',
1934
				'&#8220;Lorem ipsum dolor sit amet 1234&#8221;',
1935
			),
1936
			array(
1937
				"'Etiam eu egestas dui 1234'",
1938
				"&#8216;Etiam eu egestas dui 1234&#8217;",
1939
			),
1940
			array(
1941
				'according to our source, "33% of all students scored less than 50" on the test.',
1942
				'according to our source, &#8220;33% of all students scored less than 50&#8221; on the test.',
1943
			),
1944
			array(
1945
				"The doctor said, 'An average height is between 5' and 6' in study group 7'.  He then produced a 6' chart of averages.  A man of 7', incredibly, is very possible.",
1946
				"The doctor said, &#8216;An average height is between 5&#8242; and 6&#8242; in study group 7&#8217;.  He then produced a 6&#8242; chart of averages.  A man of 7&#8242;, incredibly, is very possible.",
1947
			),
1948
			array(
1949
				'Pirates have voted on "The Expendables 3" with their clicks -- and it turns out the Sylvester Stallone-starrer hasn\'t been astoundingly popular among digital thieves, relatively speaking.
1950
1951
As of Sunday, 5.12 million people worldwide had pirated "Expendables 3" since a high-quality copy hit torrent-sharing sites July 23, according to piracy-tracking firm Excipio.
1952
1953
That likely contributed to the action movie\'s dismal box-office debut this weekend. But over the same July 23-Aug. 18 time period, the movie was No. 4 in downloads, after "Captain America: The Winter Soldier" (7.31 million), "Divergent" (6.29 million) and "The Amazing Spider-Man 2" (5.88 million). Moreover, that\'s despite "Expendables 3" becoming available more than three weeks prior to the film\'s U.S. theatrical debut.
1954
1955
String with a number followed by a single quote \'Expendables 3\' vestibulum in arcu mi.',
1956
1957
				'Pirates have voted on &#8220;The Expendables 3&#8221; with their clicks &#8212; and it turns out the Sylvester Stallone-starrer hasn&#8217;t been astoundingly popular among digital thieves, relatively speaking.
1958
1959
As of Sunday, 5.12 million people worldwide had pirated &#8220;Expendables 3&#8221; since a high-quality copy hit torrent-sharing sites July 23, according to piracy-tracking firm Excipio.
1960
1961
That likely contributed to the action movie&#8217;s dismal box-office debut this weekend. But over the same July 23-Aug. 18 time period, the movie was No. 4 in downloads, after &#8220;Captain America: The Winter Soldier&#8221; (7.31 million), &#8220;Divergent&#8221; (6.29 million) and &#8220;The Amazing Spider-Man 2&#8221; (5.88 million). Moreover, that&#8217;s despite &#8220;Expendables 3&#8221; becoming available more than three weeks prior to the film&#8217;s U.S. theatrical debut.
1962
1963
String with a number followed by a single quote &#8216;Expendables 3&#8217; vestibulum in arcu mi.',
1964
			),
1965
		);
1966
	}
1967
1968
	/**
1969
	 * Make sure translation actually works.
1970
	 *
1971
	 * Also make sure opening and closing quotes are allowed to be identical.
1972
	 *
1973
	 * @ticket 29256
1974
	 * @dataProvider data_primes_quotes_translation
1975
	 */
1976 View Code Duplication
	function test_primes_quotes_translation( $input, $output ) {
0 ignored issues
show
Documentation introduced by
The return type could not be reliably inferred; please add a @return annotation.

Our type inference engine in quite powerful, but sometimes the code does not provide enough clues to go by. In these cases we request you to add a @return annotation as described here.

Loading history...
1977
		add_filter( 'gettext_with_context', array( $this, 'filter_translate2' ), 10, 4 );
1978
1979
		$result = wptexturize( $input, true );
1980
1981
		remove_filter( 'gettext_with_context', array( $this, 'filter_translate2' ), 10, 4 );
1982
		wptexturize( 'reset', true );
1983
1984
		return $this->assertEquals( $output, $result );
1985
	}
1986
1987 View Code Duplication
	function filter_translate2( $translations, $text, $context, $domain ) {
0 ignored issues
show
Documentation introduced by
The return type could not be reliably inferred; please add a @return annotation.

Our type inference engine in quite powerful, but sometimes the code does not provide enough clues to go by. In these cases we request you to add a @return annotation as described here.

Loading history...
1988
		switch ($text) {
1989
			case '&#8211;' : return '!endash!';
1990
			case '&#8212;' : return '!emdash!';
1991
			case '&#8216;' : return '!q1!';
1992
			case '&#8217;' :
1993
				if ( 'apostrophe' == $context ) {
1994
					return '!apos!';
1995
				} else {
1996
					return '!q1!';
1997
				}
1998
			case '&#8220;' : return '!q2!';
1999
			case '&#8221;' : return '!q2!';
2000
			case '&#8242;' : return '!prime1!';
2001
			case '&#8243;' : return '!prime2!';
2002
			default : return $translations;
2003
		}
2004
	}
2005
2006
	function data_primes_quotes_translation() {
2007
		return array(
2008
			array(
2009
				"George's porch is 99' long.",
2010
				"George!apos!s porch is 99!prime1! long.",
2011
			),
2012
			array(
2013
				'The best year "was that time in 2012" when everyone partied, he said.',
2014
				'The best year !q2!was that time in 2012!q2! when everyone partied, he said.',
2015
			),
2016
			array(
2017
				"I need 4 x 20' = 80' of trim.", // Works only with a space before the = char.
2018
				"I need 4 x 20!prime1! = 80!prime1! of trim.",
2019
			),
2020
			array(
2021
				'"Lorem ipsum dolor sit amet 1234"',
2022
				'!q2!Lorem ipsum dolor sit amet 1234!q2!',
2023
			),
2024
			array(
2025
				"'Etiam eu egestas dui 1234'",
2026
				"!q1!Etiam eu egestas dui 1234!q1!",
2027
			),
2028
			array(
2029
				'according to our source, "33% of all students scored less than 50" on the test.',
2030
				'according to our source, !q2!33% of all students scored less than 50!q2! on the test.',
2031
			),
2032
			array(
2033
				"The doctor said, 'An average height is between 5' and 6' in study group 7'.  He then produced a 6' chart of averages.  A man of 7', incredibly, is very possible.",
2034
				"The doctor said, !q1!An average height is between 5!prime1! and 6!prime1! in study group 7!q1!.  He then produced a 6!prime1! chart of averages.  A man of 7!prime1!, incredibly, is very possible.",
2035
			),
2036
			array(
2037
				'Pirates have voted on "The Expendables 3" with their clicks -- and it turns out the Sylvester Stallone-starrer hasn\'t been astoundingly popular among digital thieves, relatively speaking.
2038
2039
As of Sunday, 5.12 million people worldwide had pirated "Expendables 3" since a high-quality copy hit torrent-sharing sites July 23, according to piracy-tracking firm Excipio.
2040
2041
That likely contributed to the action movie\'s dismal box-office debut this weekend. But over the same July 23-Aug. 18 time period, the movie was No. 4 in downloads, after "Captain America: The Winter Soldier" (7.31 million), "Divergent" (6.29 million) and "The Amazing Spider-Man 2" (5.88 million). Moreover, that\'s despite "Expendables 3" becoming available more than three weeks prior to the film\'s U.S. theatrical debut.
2042
2043
String with a number followed by a single quote \'Expendables 3\' vestibulum in arcu mi.',
2044
2045
				'Pirates have voted on !q2!The Expendables 3!q2! with their clicks !emdash! and it turns out the Sylvester Stallone-starrer hasn!apos!t been astoundingly popular among digital thieves, relatively speaking.
2046
2047
As of Sunday, 5.12 million people worldwide had pirated !q2!Expendables 3!q2! since a high-quality copy hit torrent-sharing sites July 23, according to piracy-tracking firm Excipio.
2048
2049
That likely contributed to the action movie!apos!s dismal box-office debut this weekend. But over the same July 23-Aug. 18 time period, the movie was No. 4 in downloads, after !q2!Captain America: The Winter Soldier!q2! (7.31 million), !q2!Divergent!q2! (6.29 million) and !q2!The Amazing Spider-Man 2!q2! (5.88 million). Moreover, that!apos!s despite !q2!Expendables 3!q2! becoming available more than three weeks prior to the film!apos!s U.S. theatrical debut.
2050
2051
String with a number followed by a single quote !q1!Expendables 3!q1! vestibulum in arcu mi.',
2052
			),
2053
		);
2054
	}
2055
2056
	/**
2057
	 * Automated performance testing of the main regex.
2058
	 *
2059
	 * @dataProvider data_whole_posts
2060
	 */
2061
	function test_pcre_performance( $input ) {
0 ignored issues
show
Documentation introduced by
The return type could not be reliably inferred; please add a @return annotation.

Our type inference engine in quite powerful, but sometimes the code does not provide enough clues to go by. In these cases we request you to add a @return annotation as described here.

Loading history...
2062
		global $shortcode_tags;
2063
2064
		// With Shortcodes Disabled
2065
		$regex = _get_wptexturize_split_regex( );
2066
		$result = benchmark_pcre_backtracking( $regex, $input, 'split' );
2067
		$this->assertLessThan( 200, $result );
2068
2069
		// With Shortcodes Enabled
2070
		$shortcode_regex = _get_wptexturize_shortcode_regex( array_keys( $shortcode_tags ) );
2071
		$regex = _get_wptexturize_split_regex( $shortcode_regex );
2072
		$result = benchmark_pcre_backtracking( $regex, $input, 'split' );
2073
		return $this->assertLessThan( 200, $result );
2074
	}
2075
2076
	/**
2077
	 * Ensure that a trailing less-than symbol doesn't cause a PHP warning.
2078
	 *
2079
	 * @ticket 35864
2080
	 */
2081
	function test_trailing_less_than() {
2082
		$this->assertEquals( 'F&#8211;oo<', wptexturize( 'F--oo<', true ) );
2083
	}
2084
2085
	function data_whole_posts() {
2086
		require_once( DIR_TESTDATA . '/formatting/whole-posts.php' );
2087
		return data_whole_posts();
2088
	}
2089
}