PluginProbe ʕ •ᴥ•ʔ
Contact Form 7 / 5.8.1
Contact Form 7 v5.8.1
6.1.6 5.0.2 5.0.3 5.0.4 5.0.5 5.1 5.1.1 5.1.2 5.1.3 5.1.4 5.1.5 5.1.6 5.1.7 5.1.8 5.1.9 5.2 5.2.1 5.2.2 5.3 5.3.1 5.3.2 5.4 5.4.1 5.4.2 5.5 5.5.1 5.5.2 5.5.3 5.5.4 5.5.5 5.5.6 5.5.6.1 5.6 5.6.1 5.6.2 5.6.3 5.6.4 5.7 5.7.1 5.7.2 5.7.3 5.7.4 5.7.5 5.7.5.1 5.7.6 5.7.7 5.8 5.8.1 5.8.2 5.8.3 5.8.4 5.8.5 5.8.6 5.8.7 5.9 5.9.2 5.9.3 5.9.4 5.9.5 5.9.6 5.9.7 5.9.8 6.0 6.0.1 6.0.2 6.0.3 6.0.4 6.0.5 6.0.6 6.1 6.1.1 6.1.2 6.1.3 6.1.4 6.1.5 trunk 1.1 1.10 1.10.0.1 1.10.1 1.2 1.3 1.3.1 1.3.2 1.4 1.4.1 1.4.2 1.4.3 1.4.4 1.5 1.6 1.6.1 1.7 1.7.1 1.7.2 1.7.4 1.7.5 1.7.6 1.7.6.1 1.7.7 1.7.7.1 1.7.8 1.8 1.8.0.1 1.8.0.2 1.8.0.3 1.8.0.4 1.8.1 1.8.1.1 1.9 1.9.1 1.9.2 1.9.2.1 1.9.2.2 1.9.3 1.9.4 1.9.5 1.9.5.1 2.0 2.0-beta 2.0.1 2.0.2 2.0.3 2.0.4 2.0.5 2.0.6 2.0.7 2.1 2.1.1 2.1.2 2.2 2.2.1 2.3 2.3.1 2.4 2.4.1 2.4.2 2.4.3 2.4.4 2.4.5 2.4.6 3.0 3.0-beta 3.0.1 3.0.2 3.0.2.1 3.1 3.1.1 3.1.2 3.2 3.2.1 3.3 3.3.1 3.3.2 3.3.3 3.4 3.4.1 3.4.2 3.5 3.5.1 3.5.2 3.5.3 3.5.4 3.6 3.7 3.7.1 3.7.2 3.8 3.8.1 3.9 3.9-beta 3.9.1 3.9.2 3.9.3 4.0 4.0.1 4.0.2 4.0.3 4.1 4.1-beta 4.1.1 4.1.2 4.2 4.2-beta 4.2.1 4.2.2 4.3 4.3.1 4.4 4.4.1 4.4.2 4.5 4.5.1 4.6 4.6.1 4.7 4.8 4.8.1 4.9 4.9.1 4.9.2 5.0 5.0.1
contact-form-7 / includes / formatting.php
contact-form-7 / includes Last commit date
block-editor 2 years ago config-validator 2 years ago css 3 years ago js 3 years ago swv 2 years ago capabilities.php 7 years ago contact-form-functions.php 2 years ago contact-form-template.php 2 years ago contact-form.php 2 years ago controller.php 3 years ago file.php 3 years ago form-tag.php 2 years ago form-tags-manager.php 3 years ago formatting.php 2 years ago functions.php 2 years ago html-formatter.php 3 years ago integration.php 3 years ago l10n.php 3 years ago mail.php 2 years ago pipe.php 3 years ago pocket-holder.php 3 years ago rest-api.php 2 years ago shortcodes.php 3 years ago special-mail-tags.php 2 years ago submission.php 3 years ago upgrade.php 2 years ago validation-functions.php 2 years ago validation.php 3 years ago
formatting.php
559 lines
1 <?php
2
3 /**
4 * Replaces double line breaks with paragraph elements.
5 *
6 * @param string $input The text which has to be formatted.
7 * @param bool $br Optional. If set, this will convert all remaining
8 * line breaks after paragraphing. Default true.
9 * @return string Text which has been converted into correct paragraph tags.
10 */
11 function wpcf7_autop( $input, $br = true ) {
12 $placeholders = array();
13
14 // Replace non-HTML embedded elements with placeholders.
15 $input = preg_replace_callback(
16 '/<(math|svg).*?<\/\1>/is',
17 static function ( $matches ) use ( &$placeholders ) {
18 $placeholder = sprintf(
19 '<%1$s id="%2$s" />',
20 WPCF7_HTMLFormatter::placeholder_inline,
21 sha1( $matches[0] )
22 );
23
24 list( $placeholder ) =
25 WPCF7_HTMLFormatter::normalize_start_tag( $placeholder );
26
27 $placeholders[$placeholder] = $matches[0];
28
29 return $placeholder;
30 },
31 $input
32 );
33
34 $formatter = new WPCF7_HTMLFormatter( array(
35 'auto_br' => $br,
36 ) );
37
38 $chunks = $formatter->separate_into_chunks( $input );
39
40 $output = $formatter->format( $chunks );
41
42 // Restore from placeholders.
43 $output = str_replace(
44 array_keys( $placeholders ),
45 array_values( $placeholders ),
46 $output
47 );
48
49 return $output;
50 }
51
52
53 /**
54 * Newline preservation help function for wpcf7_autop().
55 *
56 * @deprecated 5.7 Unnecessary to use any more.
57 *
58 * @param array $matches preg_replace_callback() matches array.
59 * @return string Text including newline placeholders.
60 */
61 function wpcf7_autop_preserve_newline_callback( $matches ) {
62 return str_replace( "\n", '<WPPreserveNewline />', $matches[0] );
63 }
64
65
66 /**
67 * Sanitizes the query variables.
68 *
69 * @param string $text Query variable.
70 * @return string Text sanitized.
71 */
72 function wpcf7_sanitize_query_var( $text ) {
73 $text = wp_unslash( $text );
74 $text = wp_check_invalid_utf8( $text );
75
76 if ( false !== strpos( $text, '<' ) ) {
77 $text = wp_pre_kses_less_than( $text );
78 $text = wp_strip_all_tags( $text );
79 }
80
81 $text = preg_replace( '/%[a-f0-9]{2}/i', '', $text );
82 $text = preg_replace( '/ +/', ' ', $text );
83 $text = trim( $text, ' ' );
84
85 return $text;
86 }
87
88
89 /**
90 * Strips quote characters surrounding the input.
91 *
92 * @param string $text Input text.
93 * @return string Processed output.
94 */
95 function wpcf7_strip_quote( $text ) {
96 $text = trim( $text );
97
98 if ( preg_match( '/^"(.*)"$/s', $text, $matches ) ) {
99 $text = $matches[1];
100 } elseif ( preg_match( "/^'(.*)'$/s", $text, $matches ) ) {
101 $text = $matches[1];
102 }
103
104 return $text;
105 }
106
107
108 /**
109 * Navigates through an array, object, or scalar, and
110 * strips quote characters surrounding the each value.
111 *
112 * @param mixed $input The array or string to be processed.
113 * @return mixed Processed value.
114 */
115 function wpcf7_strip_quote_deep( $input ) {
116 if ( is_string( $input ) ) {
117 return wpcf7_strip_quote( $input );
118 }
119
120 if ( is_array( $input ) ) {
121 $result = array();
122
123 foreach ( $input as $key => $text ) {
124 $result[$key] = wpcf7_strip_quote_deep( $text );
125 }
126
127 return $result;
128 }
129 }
130
131
132 /**
133 * Normalizes newline characters.
134 *
135 * @param string $text Input text.
136 * @param string $to Optional. The newline character that is used in the output.
137 * @return string Normalized text.
138 */
139 function wpcf7_normalize_newline( $text, $to = "\n" ) {
140 if ( ! is_string( $text ) ) {
141 return $text;
142 }
143
144 $nls = array( "\r\n", "\r", "\n" );
145
146 if ( ! in_array( $to, $nls ) ) {
147 return $text;
148 }
149
150 return str_replace( $nls, $to, $text );
151 }
152
153
154 /**
155 * Navigates through an array, object, or scalar, and
156 * normalizes newline characters in the each value.
157 *
158 * @param mixed $input The array or string to be processed.
159 * @param string $to Optional. The newline character that is used in the output.
160 * @return mixed Processed value.
161 */
162 function wpcf7_normalize_newline_deep( $input, $to = "\n" ) {
163 if ( is_array( $input ) ) {
164 $result = array();
165
166 foreach ( $input as $key => $text ) {
167 $result[$key] = wpcf7_normalize_newline_deep( $text, $to );
168 }
169
170 return $result;
171 }
172
173 return wpcf7_normalize_newline( $input, $to );
174 }
175
176
177 /**
178 * Strips newline characters.
179 *
180 * @param string $text Input text.
181 * @return string Processed one-line text.
182 */
183 function wpcf7_strip_newline( $text ) {
184 $text = (string) $text;
185 $text = str_replace( array( "\r", "\n" ), '', $text );
186 return trim( $text );
187 }
188
189
190 /**
191 * Canonicalizes text.
192 *
193 * @param string $text Input text.
194 * @param string|array|object $args Options.
195 * @return string Canonicalized text.
196 */
197 function wpcf7_canonicalize( $text, $args = '' ) {
198 // for back-compat
199 if ( is_string( $args ) and '' !== $args
200 and false === strpos( $args, '=' ) ) {
201 $args = array(
202 'strto' => $args,
203 );
204 }
205
206 $args = wp_parse_args( $args, array(
207 'strto' => 'lower',
208 'strip_separators' => false,
209 ) );
210
211 static $charset = null;
212
213 if ( ! isset( $charset ) ) {
214 $charset = get_option( 'blog_charset' );
215
216 $is_utf8 = in_array(
217 $charset,
218 array( 'utf8', 'utf-8', 'UTF8', 'UTF-8' )
219 );
220
221 if ( $is_utf8 ) {
222 $charset = 'UTF-8';
223 }
224 }
225
226 $text = html_entity_decode( $text, ENT_QUOTES | ENT_HTML5, $charset );
227
228 if ( function_exists( 'mb_convert_kana' ) ) {
229 $text = mb_convert_kana( $text, 'asKV', $charset );
230 }
231
232 if ( $args['strip_separators'] ) {
233 $text = preg_replace( '/[\r\n\t ]+/', '', $text );
234 } else {
235 $text = preg_replace( '/[\r\n\t ]+/', ' ', $text );
236 }
237
238 if ( 'lower' == $args['strto'] ) {
239 if ( function_exists( 'mb_strtolower' ) ) {
240 $text = mb_strtolower( $text, $charset );
241 } else {
242 $text = strtolower( $text );
243 }
244 } elseif ( 'upper' == $args['strto'] ) {
245 if ( function_exists( 'mb_strtoupper' ) ) {
246 $text = mb_strtoupper( $text, $charset );
247 } else {
248 $text = strtoupper( $text );
249 }
250 }
251
252 $text = trim( $text );
253 return $text;
254 }
255
256
257 /**
258 * Sanitizes Contact Form 7's form unit-tag.
259 *
260 * @param string $tag Unit-tag.
261 * @return string Sanitized unit-tag.
262 */
263 function wpcf7_sanitize_unit_tag( $tag ) {
264 $tag = preg_replace( '/[^A-Za-z0-9_-]/', '', $tag );
265 return $tag;
266 }
267
268
269 /**
270 * Converts a file name to one that is not executable as a script.
271 *
272 * @param string $filename File name.
273 * @return string Converted file name.
274 */
275 function wpcf7_antiscript_file_name( $filename ) {
276 $filename = wp_basename( $filename );
277
278 $filename = preg_replace( '/[\r\n\t -]+/', '-', $filename );
279 $filename = preg_replace( '/[\pC\pZ]+/iu', '', $filename );
280
281 $parts = explode( '.', $filename );
282
283 if ( count( $parts ) < 2 ) {
284 return $filename;
285 }
286
287 $script_pattern = '/^(php|phtml|pl|py|rb|cgi|asp|aspx)\d?$/i';
288
289 $filename = array_shift( $parts );
290 $extension = array_pop( $parts );
291
292 foreach ( (array) $parts as $part ) {
293 if ( preg_match( $script_pattern, $part ) ) {
294 $filename .= '.' . $part . '_';
295 } else {
296 $filename .= '.' . $part;
297 }
298 }
299
300 if ( preg_match( $script_pattern, $extension ) ) {
301 $filename .= '.' . $extension . '_.txt';
302 } else {
303 $filename .= '.' . $extension;
304 }
305
306 return $filename;
307 }
308
309
310 /**
311 * Masks a password with asterisks (*).
312 *
313 * @param int $right Length of right-hand unmasked text. Default 0.
314 * @param int $left Length of left-hand unmasked text. Default 0.
315 * @return string Text of masked password.
316 */
317 function wpcf7_mask_password( $text, $right = 0, $left = 0 ) {
318 $length = strlen( $text );
319
320 $right = absint( $right );
321 $left = absint( $left );
322
323 if ( $length < $right + $left ) {
324 $right = $left = 0;
325 }
326
327 if ( $length <= 48 ) {
328 $masked = str_repeat( '*', $length - ( $right + $left ) );
329 } elseif ( $right + $left < 48 ) {
330 $masked = str_repeat( '*', 48 - ( $right + $left ) );
331 } else {
332 $masked = '****';
333 }
334
335 $left_unmasked = $left ? substr( $text, 0, $left ) : '';
336 $right_unmasked = $right ? substr( $text, -1 * $right ) : '';
337
338 $text = $left_unmasked . $masked . $right_unmasked;
339
340 return $text;
341 }
342
343
344 /**
345 * Returns an array of allowed HTML tags and attributes for a given context.
346 *
347 * @param string $context Context used to decide allowed tags and attributes.
348 * @return array Array of allowed HTML tags and their allowed attributes.
349 */
350 function wpcf7_kses_allowed_html( $context = 'form' ) {
351 static $allowed_tags = array();
352
353 if ( isset( $allowed_tags[$context] ) ) {
354 return apply_filters(
355 'wpcf7_kses_allowed_html',
356 $allowed_tags[$context],
357 $context
358 );
359 }
360
361 $allowed_tags[$context] = wp_kses_allowed_html( 'post' );
362
363 if ( 'form' === $context ) {
364 $additional_tags_for_form = array(
365 'button' => array(
366 'disabled' => true,
367 'name' => true,
368 'type' => true,
369 'value' => true,
370 ),
371 'datalist' => array(),
372 'fieldset' => array(
373 'disabled' => true,
374 'name' => true,
375 ),
376 'input' => array(
377 'accept' => true,
378 'alt' => true,
379 'capture' => true,
380 'checked' => true,
381 'disabled' => true,
382 'list' => true,
383 'max' => true,
384 'maxlength' => true,
385 'min' => true,
386 'minlength' => true,
387 'multiple' => true,
388 'name' => true,
389 'placeholder' => true,
390 'readonly' => true,
391 'size' => true,
392 'step' => true,
393 'type' => true,
394 'value' => true,
395 ),
396 'label' => array(
397 'for' => true,
398 ),
399 'legend' => array(),
400 'meter' => array(
401 'value' => true,
402 'min' => true,
403 'max' => true,
404 'low' => true,
405 'high' => true,
406 'optimum' => true,
407 ),
408 'optgroup' => array(
409 'disabled' => true,
410 'label' => true,
411 ),
412 'option' => array(
413 'disabled' => true,
414 'label' => true,
415 'selected' => true,
416 'value' => true,
417 ),
418 'output' => array(
419 'for' => true,
420 'name' => true,
421 ),
422 'progress' => array(
423 'max' => true,
424 'value' => true,
425 ),
426 'select' => array(
427 'disabled' => true,
428 'multiple' => true,
429 'name' => true,
430 'size' => true,
431 ),
432 'textarea' => array(
433 'cols' => true,
434 'disabled' => true,
435 'maxlength' => true,
436 'minlength' => true,
437 'name' => true,
438 'placeholder' => true,
439 'readonly' => true,
440 'rows' => true,
441 'spellcheck' => true,
442 'wrap' => true,
443 ),
444 );
445
446 $additional_tags_for_form = array_map(
447 static function ( $elm ) {
448 $global_attributes = array(
449 'aria-atomic' => true,
450 'aria-checked' => true,
451 'aria-describedby' => true,
452 'aria-details' => true,
453 'aria-disabled' => true,
454 'aria-hidden' => true,
455 'aria-invalid' => true,
456 'aria-label' => true,
457 'aria-labelledby' => true,
458 'aria-live' => true,
459 'aria-relevant' => true,
460 'aria-required' => true,
461 'aria-selected' => true,
462 'class' => true,
463 'data-*' => true,
464 'id' => true,
465 'inputmode' => true,
466 'role' => true,
467 'style' => true,
468 'tabindex' => true,
469 'title' => true,
470 );
471
472 return array_merge( $global_attributes, (array) $elm );
473 },
474 $additional_tags_for_form
475 );
476
477 $allowed_tags[$context] = array_merge(
478 $allowed_tags[$context],
479 $additional_tags_for_form
480 );
481 }
482
483 return apply_filters(
484 'wpcf7_kses_allowed_html',
485 $allowed_tags[$context],
486 $context
487 );
488 }
489
490
491 /**
492 * Sanitizes content for allowed HTML tags for the specified context.
493 *
494 * @param string $input Content to filter.
495 * @param string $context Context used to decide allowed tags and attributes.
496 * @return string Filtered text with allowed HTML tags and attributes intact.
497 */
498 function wpcf7_kses( $input, $context = 'form' ) {
499 $output = wp_kses(
500 $input,
501 wpcf7_kses_allowed_html( $context )
502 );
503
504 return $output;
505 }
506
507
508 /**
509 * Returns a formatted string of HTML attributes.
510 *
511 * @param array $atts Associative array of attribute name and value pairs.
512 * @return string Formatted HTML attributes.
513 */
514 function wpcf7_format_atts( $atts ) {
515 $atts_filtered = array();
516
517 foreach ( $atts as $name => $value ) {
518 $name = strtolower( trim( $name ) );
519
520 if ( ! preg_match( '/^[a-z_:][a-z_:.0-9-]*$/', $name ) ) {
521 continue;
522 }
523
524 static $boolean_attributes = array(
525 'checked',
526 'disabled',
527 'inert',
528 'multiple',
529 'readonly',
530 'required',
531 'selected',
532 );
533
534 if ( in_array( $name, $boolean_attributes ) and '' === $value ) {
535 $value = false;
536 }
537
538 if ( is_numeric( $value ) ) {
539 $value = (string) $value;
540 }
541
542 if ( null === $value or false === $value ) {
543 unset( $atts_filtered[$name] );
544 } elseif ( true === $value ) {
545 $atts_filtered[$name] = $name; // boolean attribute
546 } elseif ( is_string( $value ) ) {
547 $atts_filtered[$name] = trim( $value );
548 }
549 }
550
551 $output = '';
552
553 foreach ( $atts_filtered as $name => $value ) {
554 $output .= sprintf( ' %1$s="%2$s"', $name, esc_attr( $value ) );
555 }
556
557 return trim( $output );
558 }
559