C:\xampp\htdocs\landing\wp-content\plugins\amp\includes\options\class-amp-options-manager.php


1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481
482
483
484
485
486
487
488
489
490
491
492
493
494
495
496
497
498
499
500
501
502
503
504
505
506
507
508
509
510
511
512
513
514
515
516
517
518
519
520
521
522
523
524
525
526
527
528
529
530
531
532
533
534
535
536
537
538
539
540
541
542
543
544
545
546
547
548
549
550
551
552
553
554
555
556
557
558
559
<?php
/**
 * Class AMP_Options_Manager.
 *
 * @package AMP
 */

use AmpProject\AmpWP\Admin\ReaderThemes;
use 
AmpProject\AmpWP\Option;

/**
 * Class AMP_Options_Manager
 *
 * @internal
 */
class AMP_Options_Manager {

    
/**
     * Option name.
     *
     * @var string
     */
    
const OPTION_NAME 'amp-options';

    
/**
     * Default option values.
     *
     * @var array
     */
    
protected static $defaults = [
        
Option::THEME_SUPPORT           => AMP_Theme_Support::READER_MODE_SLUG,
        
Option::SUPPORTED_POST_TYPES    => [ 'post''page' ],
        
Option::ANALYTICS               => [],
        
Option::ALL_TEMPLATES_SUPPORTED => true,
        
Option::SUPPORTED_TEMPLATES     => [ 'is_singular' ],
        
Option::VERSION                 => AMP__VERSION,
        
Option::READER_THEME            => ReaderThemes::DEFAULT_READER_THEME,
        
Option::PLUGIN_CONFIGURED       => false,
    ];

    
/**
     * Sets up hooks.
     */
    
public static function init() {
        
add_action'admin_notices', [ __CLASS__'render_php_css_parser_conflict_notice' ] );
        
add_action'admin_notices', [ __CLASS__'insecure_connection_notice' ] );
        
add_action'admin_notices', [ __CLASS__'reader_theme_fallback_notice' ] );
    }

    
/**
     * Register settings.
     */
    
public static function register_settings() {
        
register_setting(
            
self::OPTION_NAME,
            
self::OPTION_NAME,
            [
                
'type'              => 'array',
                
'sanitize_callback' => [ __CLASS__'validate_options' ],
            ]
        );

        
add_action'update_option_' self::OPTION_NAME, [ __CLASS__'maybe_flush_rewrite_rules' ], 10);
    }

    
/**
     * Flush rewrite rules if the supported_post_types have changed.
     *
     * @since 0.6.2
     *
     * @param array $old_options Old options.
     * @param array $new_options New options.
     */
    
public static function maybe_flush_rewrite_rules$old_options$new_options ) {
        
$old_post_types = isset( $old_optionsOption::SUPPORTED_POST_TYPES ] ) ? $old_optionsOption::SUPPORTED_POST_TYPES ] : [];
        
$new_post_types = isset( $new_optionsOption::SUPPORTED_POST_TYPES ] ) ? $new_optionsOption::SUPPORTED_POST_TYPES ] : [];
        
sort$old_post_types );
        
sort$new_post_types );
        if ( 
$old_post_types !== $new_post_types ) {
            
// Flush rewrite rules.
            
add_rewrite_endpointamp_get_slug(), EP_PERMALINK );
            
flush_rewrite_rulesfalse );
        }
    }

    
/**
     * Get plugin options.
     *
     * @return array Options.
     */
    
public static function get_options() {
        
$options get_optionself::OPTION_NAME, [] );
        if ( empty( 
$options ) ) {
            
$options = []; // Ensure empty string becomes array.
        
}

        
$defaults      self::$defaults;
        
$theme_support AMP_Theme_Support::get_theme_support_args();

        
// Make sure the plugin is marked as being already configured if there saved options.
        
if ( ! empty( $options ) ) {
            
$defaultsOption::PLUGIN_CONFIGURED ] = true;
        }

        
// Migrate legacy method of specifying the mode.
        
if ( ! isset( $optionsOption::THEME_SUPPORT ] ) && $theme_support ) {
            
$template   get_template();
            
$stylesheet get_stylesheet();
            if (
                
// If theme support was probably explicitly added by the theme (since not core).
                
in_array$templateAMP_Core_Theme_Sanitizer::get_supported_themes(), true )
                ||
                
// If it is a core theme no child theme is being used (which likely won't be AMP-compatible by default).
                
$template === $stylesheet
            
) {
                if ( empty( 
$theme_supportAMP_Theme_Support::PAIRED_FLAG ] ) ) {
                    
$defaultsOption::THEME_SUPPORT ] = AMP_Theme_Support::STANDARD_MODE_SLUG;
                } else {
                    
$defaultsOption::THEME_SUPPORT ] = AMP_Theme_Support::TRANSITIONAL_MODE_SLUG;
                }
            }
        }

        
// Migrate legacy amp post type support to be reflected in the default supported_post_types value.
        
if ( ! isset( $optionsOption::SUPPORTED_POST_TYPES ] ) ) {
            
$defaultsOption::SUPPORTED_POST_TYPES ] = array_merge(
                
$defaultsOption::SUPPORTED_POST_TYPES ],
                (array) 
get_post_types_by_support'amp' )
            );
        }

        
// Migrate legacy method of specifying all_templates_supported.
        
if ( ! isset( $optionsOption::ALL_TEMPLATES_SUPPORTED ] ) && isset( $theme_support['templates_supported'] ) ) {
            
$defaultsOption::ALL_TEMPLATES_SUPPORTED ] = ( 'all' === $theme_support['templates_supported'] );
        }

        
// Migrate legacy amp theme support to be reflected in the default supported_templates value.
        
if ( ! isset( $optionsOption::SUPPORTED_TEMPLATES ] ) && isset( $theme_support['templates_supported'] ) && is_array$theme_support['templates_supported'] ) ) {
            
$defaultsOption::SUPPORTED_TEMPLATES ] = array_merge(
                
$defaultsOption::SUPPORTED_TEMPLATES ],
                
array_keysarray_filter$theme_support['templates_supported'] ) )
            );
            
$defaultsOption::SUPPORTED_TEMPLATES ] = array_diff(
                
$defaultsOption::SUPPORTED_TEMPLATES ],
                
array_keys(
                    
array_filter(
                        
$theme_support['templates_supported'],
                        static function ( 
$supported ) {
                            return ! 
$supported;
                        }
                    )
                )
            );
        }

        
$options array_merge(
            
$defaults,
            
/**
             * Filters default options.
             *
             * @internal
             * @param array $defaults Default options.
             */
            
(array) apply_filters'amp_default_options'$defaults ),
            
$options
        
);

        
// Ensure current template mode.
        
if (
            
AMP_Theme_Support::READER_MODE_SLUG === $optionsOption::THEME_SUPPORT ]
            &&
            
get_stylesheet() === $optionsOption::READER_THEME ]
            &&
            ! isset( 
$_GETamp_get_slug() ] ) // phpcs:ignore WordPress.Security.NonceVerification.Recommended
        
) {
            
/*
             * When Reader mode is selected and a Reader theme has been chosen, if the active theme switches to be the
             * same as the Reader theme, then transparently switch the mode from Reader to Transitional while the
             * active theme and the Reader theme are the same. Remember that Reader mode means having two separate
             * templates for AMP and non-AMP, whereas Transitional mode means using the same templates. Otherwise, there
             * is no difference whatsoever between Reader and Transitional modes, as they are both Paired AMP modes.
             * By dynamically changing the mode from Reader to Transitional in the options getter here, if the active
             * theme is switched again to be different than what was selected as the Reader theme, then the site will
             * go back to being in Reader mode as opposed to Transitional.
             * @todo It would be preferable to rather invoke methods of ReaderThemeLoader here, but that risks an infinite loop and is a circular dependency.
             */
            
$optionsOption::THEME_SUPPORT ] = AMP_Theme_Support::TRANSITIONAL_MODE_SLUG;
        } elseif ( 
'native' === $optionsOption::THEME_SUPPORT ] ) {
            
// The slug 'native' is the old term for 'standard'.
            
$optionsOption::THEME_SUPPORT ] = AMP_Theme_Support::STANDARD_MODE_SLUG;
        } elseif ( 
'paired' === $optionsOption::THEME_SUPPORT ] ) {
            
// The slug 'paired' is the old term for 'transitional.
            
$optionsOption::THEME_SUPPORT ] = AMP_Theme_Support::TRANSITIONAL_MODE_SLUG;
        } elseif ( 
'disabled' === $optionsOption::THEME_SUPPORT ] ) {
            
/*
             * Prior to 1.2, the theme support slug for Reader mode was 'disabled'. This would be saved in options for
             * themes that had 'amp' theme support defined. Also prior to 1.2, the user could not switch between modes
             * when the theme had 'amp' theme support. The result is that a site running 1.1 could be AMP-first and then
             * upon upgrading to 1.2, be switched to Reader mode. So when migrating the old 'disabled' slug to the new
             * value, we need to make sure we use the default theme support slug as it has been determined above. If the
             * site has non-paired 'amp' theme support and the theme support slug is 'disabled' then it should here be
             * set to 'standard' as opposed to 'reader', and the same goes for paired 'amp' theme support, as it should
             * become 'transitional'. Otherwise, if the theme lacks 'amp' theme support, then this will become the
             * default 'reader' mode.
             */
            
$optionsOption::THEME_SUPPORT ] = $defaultsOption::THEME_SUPPORT ];
        }

        
// Migrate options from 1.5 to 2.0.
        
if ( isset( $options['version'] ) && version_compare$options['version'], '2.0''<' ) ) {

            
// It used to be that the themes_supported flag overrode the options, so make sure the option gets updated to reflect the theme support.
            
if ( isset( $theme_support['templates_supported'] ) ) {
                if ( 
'all' === $theme_support['templates_supported'] ) {
                    
$optionsOption::ALL_TEMPLATES_SUPPORTED ] = true;
                } elseif ( 
is_array$theme_support['templates_supported'] ) ) {
                    
$optionsOption::ALL_TEMPLATES_SUPPORTED ] = false;

                    
$optionsOption::SUPPORTED_TEMPLATES ] = array_merge(
                        
$optionsOption::SUPPORTED_TEMPLATES ],
                        
array_keysarray_filter$theme_support['templates_supported'] ) )
                    );

                    
$optionsOption::SUPPORTED_TEMPLATES ] = array_diff(
                        
$optionsOption::SUPPORTED_TEMPLATES ],
                        
array_keys(
                            
array_filter(
                                
$theme_support['templates_supported'],
                                static function ( 
$supported ) {
                                    return ! 
$supported;
                                }
                            )
                        )
                    );
                }
            }

            
// Make sure programmatic post type support is persisted in the DB, as from now on the DB option is the source of truth.
            
$optionsOption::SUPPORTED_POST_TYPES ] = array_merge(
                
$optionsOption::SUPPORTED_POST_TYPES ],
                (array) 
get_post_types_by_supportAMP_Post_Type_Support::SLUG )
            );

            
// Make sure that all post types get enabled if all templates were supported since they are now independently controlled. This only applies to non-Reader mode.
            
if ( ! empty( $optionsOption::ALL_TEMPLATES_SUPPORTED ] ) && AMP_Theme_Support::READER_MODE_SLUG !== $optionsOption::THEME_SUPPORT ] ) {
                
$optionsOption::SUPPORTED_POST_TYPES ] = array_merge(
                    
$optionsOption::SUPPORTED_POST_TYPES ],
                    
AMP_Post_Type_Support::get_eligible_post_types()
                );
            }
        }

        unset(
            
/**
             * Remove 'auto_accept_sanitization' option.
             *
             * @since 1.4.0
             */
            
$optionsOption::AUTO_ACCEPT_SANITIZATION ],
            
/**
             * Remove Story related options.
             *
             * Option::ENABLE_AMP_STORIES was added in 1.2-beta and later migrated into the `experiences` option.
             *
             * @since 1.5.0
             */
            
$optionsOption::STORY_TEMPLATES_VERSION ],
            
$optionsOption::STORY_EXPORT_BASE_URL ],
            
$optionsOption::STORY_SETTINGS ],
            
$optionsOption::ENABLE_AMP_STORIES ],
            
/**
             * Remove 'experiences' option.
             *
             * @since 1.5.0
             */
            
$optionsOption::EXPERIENCES ],
            
/**
             * Remove 'enable_response_caching' option.
             *
             * @since 1.5.0
             */
            
$optionsOption::ENABLE_RESPONSE_CACHING ]
        );

        return 
$options;
    }

    
/**
     * Get plugin option.
     *
     * @param string $option  Plugin option name.
     * @param bool   $default Default value.
     *
     * @return mixed Option value.
     */
    
public static function get_option$option$default false ) {
        
$amp_options self::get_options();

        if ( ! isset( 
$amp_options$option ] ) ) {
            return 
$default;
        }

        return 
$amp_options$option ];
    }

    
/**
     * Validate options.
     *
     * @param array $new_options Plugin options.
     * @return array Options.
     */
    
public static function validate_options$new_options ) {
        
$options self::get_options();

        if ( ! 
current_user_can'manage_options' ) ) {
            return 
$options;
        }

        
// Theme support.
        
$recognized_theme_supports = [
            
AMP_Theme_Support::READER_MODE_SLUG,
            
AMP_Theme_Support::TRANSITIONAL_MODE_SLUG,
            
AMP_Theme_Support::STANDARD_MODE_SLUG,
        ];
        if ( isset( 
$new_optionsOption::THEME_SUPPORT ] ) && in_array$new_optionsOption::THEME_SUPPORT ], $recognized_theme_supportstrue ) ) {
            
$optionsOption::THEME_SUPPORT ] = $new_optionsOption::THEME_SUPPORT ];
        }

        
// Validate post type support.
        
if ( isset( $new_optionsOption::SUPPORTED_POST_TYPES ] ) && is_array$new_optionsOption::SUPPORTED_POST_TYPES ] ) ) {
            
$optionsOption::SUPPORTED_POST_TYPES ] = [];
            foreach ( 
$new_optionsOption::SUPPORTED_POST_TYPES ] as $post_type ) {
                if ( 
post_type_exists$post_type ) ) {
                    
$optionsOption::SUPPORTED_POST_TYPES ][] = $post_type;
                }
            }
            
$optionsOption::SUPPORTED_POST_TYPES ] = array_valuesarray_unique$optionsOption::SUPPORTED_POST_TYPES ] ) );
        }

        
// Update all_templates_supported.
        
if ( isset( $new_optionsOption::ALL_TEMPLATES_SUPPORTED ] ) ) {
            
$optionsOption::ALL_TEMPLATES_SUPPORTED ] = rest_sanitize_boolean$new_optionsOption::ALL_TEMPLATES_SUPPORTED ] );
        }

        
// Validate supported templates.
        
if ( isset( $new_optionsOption::SUPPORTED_TEMPLATES ] ) && is_array$new_optionsOption::SUPPORTED_TEMPLATES ] ) ) {
            
$supportable_templates                  AMP_Theme_Support::get_supportable_templates();
            
$optionsOption::SUPPORTED_TEMPLATES ] = [];
            foreach ( 
$new_optionsOption::SUPPORTED_TEMPLATES ] as $template_id ) {
                if ( 
array_key_exists$template_id$supportable_templates ) ) {
                    
$optionsOption::SUPPORTED_TEMPLATES ][] = $template_id;
                }
            }
            
$optionsOption::SUPPORTED_TEMPLATES ] = array_valuesarray_unique$optionsOption::SUPPORTED_TEMPLATES ] ) );
        }

        
// Validate wizard completion.
        
if ( isset( $new_optionsOption::PLUGIN_CONFIGURED ] ) ) {
            
$optionsOption::PLUGIN_CONFIGURED ] = (bool) $new_optionsOPTION::PLUGIN_CONFIGURED ];
        }

        
// Validate analytics.
        
if ( isset( $new_optionsOption::ANALYTICS ] ) && $new_optionsOption::ANALYTICS ] !== $optionsOption::ANALYTICS ] ) {
            
$new_analytics_option = [];

            foreach ( 
$new_optionsOption::ANALYTICS ] as $id => $data ) {
                if ( empty( 
$data['config'] ) || ! AMP_HTML_Utils::is_valid_json$data['config'] ) ) {
                    
// Bad JSON or missing config.
                    
continue;
                }

                
$new_analytics_optionsanitize_key$id ) ] = [
                    
'type'   => ! empty( $data['type'] ) ? preg_replace'/[^a-zA-Z0-9_\-]/'''$data['type'] ) : '',
                    
'config' => trim$data['config'] ),
                ];
            }

            
$optionsOPTION::ANALYTICS ] = $new_analytics_option;
        }

        if ( isset( 
$new_optionsOption::READER_THEME ] ) ) {
            
$reader_theme_slugs wp_list_pluck( ( new ReaderThemes() )->get_themes(), 'slug' );
            if ( 
in_array$new_optionsOption::READER_THEME ], $reader_theme_slugstrue ) ) {
                
$optionsOption::READER_THEME ] = $new_optionsOption::READER_THEME ];
            }
        }

        if ( 
array_key_existsOption::DISABLE_CSS_TRANSIENT_CACHING$new_options ) && true === $new_optionsOption::DISABLE_CSS_TRANSIENT_CACHING ] ) {
            
$optionsOption::DISABLE_CSS_TRANSIENT_CACHING ] = true;
        } else {
            unset( 
$optionsOption::DISABLE_CSS_TRANSIENT_CACHING ] );
        }

        
/**
         * Filter the options being updated, so services can handle the sanitization and validation of
         * their respective options.
         *
         * @internal
         *
         * @param array $options     Existing options with already-sanitized values for updating.
         * @param array $new_options Unsanitized options being submitted for updating.
         */
        
$options apply_filters'amp_options_updating'$options$new_options );

        
// Store the current version with the options so we know the format.
        
$optionsOption::VERSION ] = AMP__VERSION;

        return 
$options;
    }

    
/**
     * Update plugin option.
     *
     * @param string $option Plugin option name.
     * @param mixed  $value  Plugin option value.
     *
     * @return bool Whether update succeeded.
     */
    
public static function update_option$option$value ) {
        
$amp_options self::get_options();

        
$amp_options$option ] = $value;
        return 
update_optionself::OPTION_NAME$amp_optionsfalse );
    }

    
/**
     * Update plugin options.
     *
     * @param array $options Plugin option name.
     * @return bool Whether update succeeded.
     */
    
public static function update_options$options ) {
        
$amp_options array_merge(
            
self::get_options(),
            
$options
        
);

        return 
update_optionself::OPTION_NAME$amp_optionsfalse );
    }

    
/**
     * Render PHP-CSS-Parser conflict notice.
     *
     * @return void
     */
    
public static function render_php_css_parser_conflict_notice() {
        
$current_screen get_current_screen();
        if ( ! ( 
$current_screen instanceof WP_Screen ) || 'toplevel_page_' self::OPTION_NAME !== $current_screen->id ) {
            return;
        }

        if ( 
AMP_Style_Sanitizer::has_required_php_css_parser() ) {
            return;
        }

        try {
            
$reflection = new ReflectionClass'Sabberworm\CSS\CSSList\CSSList' );
            
$source_dir str_replace(
                
trailingslashitWP_CONTENT_DIR ),
                
'',
                
preg_replace'#/vendor/sabberworm/.+#'''$reflection->getFileName() )
            );

            
printf(
                
'<div class="notice notice-warning"><p>%s</p></div>',
                
wp_kses(
                    
sprintf(
                        
/* translators: %s: path to the conflicting library */
                        
__'A conflicting version of PHP-CSS-Parser appears to be installed by another plugin or theme (located in %s). Because of this, CSS processing will be limited, and tree shaking will not be available.''amp' ),
                        
'<code>' esc_html$source_dir ) . '</code>'
                    
),
                    [ 
'code' => [] ]
                )
            );
        } catch ( 
ReflectionException $e ) {
            
printf(
                
'<div class="notice notice-warning"><p>%s</p></div>',
                
esc_html__'PHP-CSS-Parser is not available so CSS processing will not be available.''amp' )
            );
        }
    }

    
/**
     * Outputs an admin notice if the site is not served over HTTPS.
     *
     * @since 1.3
     *
     * @return void
     */
    
public static function insecure_connection_notice() {
        
$current_screen get_current_screen();

        
// is_ssl() only tells us whether the admin backend uses HTTPS here, so we add a few more sanity checks.
        
$uses_ssl = (
            
is_ssl()
            &&
            ( 
strposget_bloginfo'wpurl' ), 'https' ) === )
            &&
            ( 
strposget_bloginfo'url' ), 'https' ) === )
        );

        if ( ! 
$uses_ssl && $current_screen instanceof WP_Screen && 'toplevel_page_' self::OPTION_NAME === $current_screen->id ) {
            
printf(
                
'<div class="notice notice-warning"><p>%s</p></div>',
                
wp_kses(
                    
sprintf(
                        
/* translators: %s: "Why should I use HTTPS" support URL */
                        
__'Your site is not being fully served over a secure connection (using HTTPS).<br>As some AMP functionality requires a secure connection, you might experience degraded performance or broken components.<br><a href="%s">More details</a>''amp' ),
                        
esc_url__'https://wordpress.org/support/article/why-should-i-use-https/''amp' ) )
                    ),
                    [
                        
'br' => [],
                        
'a'  => [ 'href' => true ],
                    ]
                )
            );
        }
    }

    
/**
     * Outputs an admin notice if the AMP Legacy Reader theme is used as a fallback.
     */
    
public static function reader_theme_fallback_notice() {
        
$current_screen get_current_screen();

        if ( ! ( 
$current_screen instanceof WP_Screen ) || ! in_array$current_screen->id, [ 'themes''toplevel_page_' self::OPTION_NAME ], true ) ) {
            return;
        }

        
$reader_themes = new ReaderThemes();

        if ( 
$reader_themes->using_fallback_theme() && current_user_can'manage_options' ) ) {
            
$selected_theme self::get_optionOption::READER_THEME );
            
$error_message  sprintf(
                
/* translators: 1: slug of the Reader theme, 2: the URL for the reader theme selection UI */
                
__'The AMP Reader theme %1$s cannot be found. Your site is currently falling back to using the Legacy templates for AMP pages. Please <a href="%2$s">re-select</a> the desired Reader theme.''amp' ),
                
"<code>{$selected_theme}</code>",
                
esc_urladd_query_arg'page'self::OPTION_NAMEadmin_url'admin.php' ) ) . '#reader-themes' )
            );
            
?>
            <div class="notice notice-warning">
                <p>
                    <?php
                    
echo wp_kses(
                        
$error_message,
                        [
                            
'code' => [],
                            
'a'    => [
                                
'href' => true,
                            ],
                        ]
                    );
                    
?>
                </p>
            </div>
            <?php
        
}
    }
}
x

Windows NT KPTV 6.2 build 9200 (Windows Server 2012 Datacenter Edition) i586