<?php class WP_Sitemaps { public $index; public $registry; public $renderer; public function __construct() { $this->registry = new WP_Sitemaps_Registry(); $this->renderer = new WP_Sitemaps_Renderer(); $this->index = new WP_Sitemaps_Index($this->registry); } public function init() { $this->register_rewrites(); add_action('template_redirect', array($this, 'render_sitemaps')); if (!$this->sitemaps_enabled()) { return; } $this->register_sitemaps(); add_filter('pre_handle_404', array($this, 'redirect_sitemapxml'), 10, 2); add_filter('robots_txt', array($this, 'add_robots'), 0, 2); } public function sitemaps_enabled() { $is_enabled = (bool) get_option('blog_public'); return (bool) apply_filters('wp_sitemaps_enabled', $is_enabled); } public function register_sitemaps() { $providers = array('posts' => new WP_Sitemaps_Posts(), 'taxonomies' => new WP_Sitemaps_Taxonomies(), 'users' => new WP_Sitemaps_Users()); foreach ($providers as $name => $provider) { $this->registry->add_provider($name, $provider); } } public function register_rewrites() { add_rewrite_tag('%sitemap%', '([^?]+)'); add_rewrite_tag('%sitemap-subtype%', '([^?]+)'); add_rewrite_rule('^wp-sitemap\\.xml$', 'index.php?sitemap=index', 'top'); add_rewrite_tag('%sitemap-stylesheet%', '([^?]+)'); add_rewrite_rule('^wp-sitemap\\.xsl$', 'index.php?sitemap-stylesheet=sitemap', 'top'); add_rewrite_rule('^wp-sitemap-index\\.xsl$', 'index.php?sitemap-stylesheet=index', 'top'); add_rewrite_rule('^wp-sitemap-([a-z]+?)-([a-z\\d_-]+?)-(\\d+?)\\.xml$', 'index.php?sitemap=$matches[1]&sitemap-subtype=$matches[2]&paged=$matches[3]', 'top'); add_rewrite_rule('^wp-sitemap-([a-z]+?)-(\\d+?)\\.xml$', 'index.php?sitemap=$matches[1]&paged=$matches[2]', 'top'); } public function render_sitemaps() { global $wp_query; $sitemap = sanitize_text_field(get_query_var('sitemap')); $object_subtype = sanitize_text_field(get_query_var('sitemap-subtype')); $stylesheet_type = sanitize_text_field(get_query_var('sitemap-stylesheet')); $paged = absint(get_query_var('paged')); if (!($sitemap || $stylesheet_type)) { return; } if (!$this->sitemaps_enabled()) { $wp_query->set_404(); status_header(404); return; } if ($stylesheet_type) { $stylesheet = new WP_Sitemaps_Stylesheet(); $stylesheet->render_stylesheet($stylesheet_type); exit; } if ('index' === $sitemap) { $sitemap_list = $this->index->get_sitemap_list(); $this->renderer->render_index($sitemap_list); exit; } $provider = $this->registry->get_provider($sitemap); if (!$provider) { return; } if (empty($paged)) { $paged = 1; } $url_list = $provider->get_url_list($paged, $object_subtype); if (empty($url_list)) { $wp_query->set_404(); status_header(404); return; } $this->renderer->render_sitemap($url_list); exit; } public function redirect_sitemapxml($bypass, $query) { if ($bypass) { return $bypass; } if ('sitemap-xml' === $query->get('pagename') || 'sitemap-xml' === $query->get('name')) { wp_safe_redirect($this->index->get_index_url()); exit; } return $bypass; } public function add_robots($output, $public) { if ($public) { $output .= "\nSitemap: " . esc_url($this->index->get_index_url()) . "\n"; } return $output; } }