Make WordPress Core

Opened 7 years ago

#41680 new defect (bug)

Added rewrite tags using add_rewrite_tag() not working on static front-page

Reported by: asgaros's profile Asgaros Owned by:
Milestone: Awaiting Review Priority: normal
Severity: normal Version: 4.8.1
Component: Rewrite Rules Keywords:
Focuses: Cc:

Description

Hello everyone,

the following ticket is a little bit similar to the issue described here: #25143

Introduction

I am working on a plugin which provides a shortcode. This shortcode generates some content/output on a page where it is placed on. The shown output depends on optional URL-parameters. For example those two URLs result in different outputs:

  • my-site.com/my-page
  • my-site.com/my-page?foo=bar

In preparation for pretty URLs I have to register a new rewrite-tag foo:

add_rewrite_tag('%foo%', '([^/]*)');

This allows me (in combination with the corresponding rewrite rules) to use pretty URLs like this:

  • my-site.com/my-page/foo/bar

As expected you can access the assigned value bar of foo with the following code:

$value_of_foo = get_query_var('foo'); // returns: bar

Problem

This all works fine as long as the page which includes the shortcode is not set as the sites static front-page. In this case your URLs will usually look like that:

  • my-site.com (the content of the static page is shown)
  • my-site.com/?foo=bar (from here it is broken)

So, whats happening? Instead of generating and showing the content based on the URL parameter, the second URL loads the front-page but instead of showing the content of the static page, it acts like the blog page and shows the list of the latest posts.

The problem is that is_home is improperly set to true because we now have a custom query-var in our URL which basically makes the content of a static page not static anymore. But this fact shouldnt let WordPress showing the list of the latest posts-page instead. This problem makes it impossible for users to place and show the content of a shortcode - which is based on (prettyfied) URL-parameters - on their static front-page.

At the moment I am using the following code as a workaround but I think this is not an optimal long-term solution for this problem:

function fix_query_vars_on_front_page($query) {
    // Dont do this workaround when we are in the administration area or when we are not inside the main query.
    if (is_admin() || !$query->is_main_query()) {
        return;
    }

    // Cache the actual query vars first.
    $queryVarCache = $query->query;

    // Only continue when our query vars are not already empty.
    if (!empty($queryVarCache)) {
        // Remove our query vars from the cache when they are set.
        if (isset($queryVarCache['foo'])) {
            unset($queryVarCache['view']);
        }

        // When our cache is empty, we are on a front-page (is_home() or is_front_page()). Ensure that the following filtering only happens on a static front page.
        if (empty($queryVarCache) && get_option('show_on_front') === 'page') {
            // Get the ID of the front page and add it to the query vars.
            $query->query['page_id'] = get_option('page_on_front');

            // Reparse the query.
            $query->parse_query($query->query);
        }
    }
}

add_action('pre_get_posts', 'fix_query_vars_on_front_page');

Maybe some way to add custom rewrite tags without adding them as a query var would be a possible solution for this. Of course there would be a need to add a function to access them, for example get_rewrite_var('foo') instead of get_query_var('foo').

I am looking forward that WordPress will make this possible in a future version. :-)

Change History (0)

Note: See TracTickets for help on using tickets.