Add custom URLs to WordPress’s XML sitemap

My WordPress site also incorporates some external non-WP content that is dynamically pulled into the page via shortcode. The content shown depends on a query string parameter. So from WP’s point of view, index is just a single page containing a shortcode; but in reality, when you visit index?x=1, index?x=2, index?x=3, etc. you get different page content depending on the x value. (It’s a primary key ID into a large external database.)

This works fine, and avoids creating thousands of separate pages in WP, though I do have to filter get_canonical_url to ensure that the canonical URL retains the query string with the x value (which would otherwise be stripped out by WP).

Now I want to include all of these pages in WP’s auto-generated sitemap (/wp-sitemap.xml), which, again, currently only lists the single bare URL with no x value. I need the sitemap to include index?x=1, index?x=2, index?x=3, etc. to cover every extant ID value.

I can easily write PHP code to generate a list of these URLs, but how do I hook into the sitemap generation process to add them to the default list produced by WP?

1 Answer
1

Sitemap Provider

It’s possible to create a so called custom sitemap provider and register it with wp_register_sitemap_provider().

It’s helpful to look at the core setup, e.g. for the WP_Sitemaps_Posts provider and also the dev notes.

Basic Example – Sitemap with custom URLs

Here’s a very basic example that adds the wpse provider that extends WP_Sitemaps_Provider, through an anonymous class:

add_action ( 'init', function () {  
    wp_register_sitemap_provider( 
        'wpse', 
        new class extends \WP_Sitemaps_Provider {
            public function __construct() {
                $this->name="wpse"; // public-facing name in URLs says parent class.
            }
            public function get_url_list( $page_num, $post_type="" ) {
                return array(
                    array(
                        'loc' => add_query_arg( 'x', 1, home_url() ),
                    ),
                    array(
                        'loc' => add_query_arg( 'x', 2, home_url() ),
                    ),
                );
            }
            public function get_max_num_pages( $subtype="" ) {
                return 1;
            }
        }
    );
} );

It will generate wp-sitemap-wpse-{PAGE NUMBER <= get_max_num_pages()}.xml or wp-sitemap-wpse-1.xml:

enter image description here

that contains these two custom urls:

enter image description here

External DB

For an external DB you can adjust the get_max_num_pages() and get_url_list() methods above, with the help of e.g.:

  • overall number of x values from the external DB
  • paginated chunk of x values from the external DB
  • wp_sitemaps_get_max_urls() that’s 2000 by default
  • current page number $page_num

ps: looking around there is a great article on wp-kama that will probably help a lot regarding the external DB.

Leave a Comment