1

Update: I read that a custom rewrite rule might be overridden and drop any parameter variables, when the custom rewrite rule is used on a child/parent page/post. The post my custom rewrite rule is meant for, is not a child/parent but it is part of a custom post type. Could this be causing similar rewrite issues (dropped parameter variables)?

Update 2 (Problem Solved): As mentioned in the update above, the fact that it concerns a rewrite rule for a custom post type post, was indeed causing the issue. Please see my anwer for the solution.

My question

When using the code below, the actual post rewrite seems to work, as it correctly leads to the post with ID 160. And it does this even when using a pretty parameter URL. But once the pretty parameter URL is redirected, to the post with ID 160, all parameter values are gone.

How can I get WP to not drop the custom parameter, when using a pretty parameter URL?

So an URL like:

site.com/post/parameter-value/

Should redirect (to the post with ID 160) as follows:

site.com/custom-post-type-slug/post-title-of-160/parameter-value/ (parameter value is not dropped)

The code I'm using

function add_custom_query_vars($vars) {
    $vars[] = 'member_view';
    return $vars;
}
add_filter('query_vars', 'add_custom_query_vars');

function add_rewrite_rules($rules) {
$newrules = array('page/([^/]+)/?$' => 'index.php?page_id=158&member_view=$matches[1]',
                  'post/([^/]+)/?$' => 'index.php?p=160&member_view=$matches[1]');
$rules = $newrules + $rules;
return $rules;
}
add_filter('rewrite_rules_array', 'add_rewrite_rules');

The details

I'm using the code above to rewrite URLs to pretty URLs, ending with pretty custom parameter values. Here's what works and what does not work:

For Pages (this works)

The rewrite rule for pages works. An URL like:

site.com/page/parameter-value/

Redirects (to the page with ID 158) as follows:

site.com/page-title-of-158/parameter-value/

And get_query_var('member_view') returns parameter-value.

For Posts (using non-pretty URL) (this works)

For posts the parameters only stick when using "non-pretty" URLs:

site.com/?p=160&member_view=parameter-value

Or:

site.com/custom-post-type-slug/post-title-of-160/?member_view=parameter-value

Both redirect (to the post with ID 160) as follows:

site.com/custom-post-type-slug/post-title-of-160/?member_view=parameter-value

And the member_view value can be retrieved.

For Posts (using pretty URL) (this does not work)

When using a pretty parameter URL, the custom parameter is dropped after the canonical.php redirect process is completed. So, an URL that looks like:

site.com/post/parameter-value/

Redirects (to the post with ID 160) as follows:

site.com/custom-post-type-slug/post-title-of-160/ (parameter value is gone)

And both get_query_var('member_view') and $_GET['member_view'] return nothing.

  • Neither should redirect if the rewrite rules are working properly, canonical only kicks in when the requested object isn't found. Have you flushed rewrite rules? – Milo Nov 27 '14 at 14:13
  • The rewrite rules were flushed several times. I've added an update to my question, explaining the post is part of a custom post type. Could this be causing the issue? – Ralph Nov 27 '14 at 14:18
  • Your page rule isn't working either, you've got issues with both that aren't immediately apparent. Not sure offhand what the query var should be for cpt id, possibly the cpt slug, but I imagine that only works with post slug, not id. – Milo Nov 27 '14 at 14:34
  • What's wrong with the page rewrite rule? Please note that I've simplified the rewrite rules a bit, as that made it easier to explain the actual problem (parameters not working for post rewrites). But perhaps you've spotted a page rewrite issue that's also in the original code, hence my question. Re the post rewrite: should the slug be added to the query vars? – Ralph Nov 27 '14 at 14:55
  • If it's redirecting, its not working. Rewritten paths should not redirect anywhere. Cpt slug is already in query vars. – Milo Nov 27 '14 at 15:00
1

Well, I found the solution. It seems that, when applying a rewrite rule on a custom post type post, one needs to tell WP the custom post type's name within the rewrite rule itself.

Here's the code that does NOT work (redirects and drops parameter variables instead of rewrite):

function add_rewrite_rules($rules) {
    $newrules = array('cpt-slug/([^/]+)/([^/]+)/?$' => 'index.php?p=$matches[1]&member_view=$matches[2]');
    $rules = $newrules + $rules;
    return $rules;
}
add_filter('rewrite_rules_array', 'add_rewrite_rules');

Here's the code that DOES work (rewrites and keeps parameter variables):

function add_rewrite_rules($rules) {
    $newrules = array('cpt-slug/([^/]+)/([^/]+)/?$' => 'index.php?p=$matches[1]&post_type=cpt_name&member_view=$matches[2]');
    $rules = $newrules + $rules;
    return $rules;
}
add_filter('rewrite_rules_array', 'add_rewrite_rules');

The rewrite worked once &post_type=cpt_name was added to its rule. I'm amazed that this isn't/wasn't explicitly pointed out in any of the rewrite rules-related info I found and read (and I searched for 2 days) :)

An URL that looks as follows:

site.com/cpt-slug/INSERT-ID-OF-CPT-POST/INSERT-PARAMETER-VARIABLE/

Will now rewrite properly and the parameter variables will not be dropped. The parameter variable can now be retrieved using get_query_var('member_view').

0

Search for the add_rewrite_tag function. You have to add a tag to catch up any variable in a rewrite; or it'll be dropped

In your case, this should do the trick:

add_rewrite_tag( '%ps-cpt-parameter%', '([^/]+)');
add_rewrite_rule('post/([^/]+)/([^/]+)/?', 'index.php?p=$matches[1]&ps-cpt-parameter=$matches[2]', 'top' );

// And then you could get the variable with

get_query_var('ps-cpt-parameter');

By the way, with add_rewrite_rule you can set if you want your custom rewrite rules before or after any other rule

  • How does adding a rewrite tag differ from adding to query vars array in this case? – Milo Nov 27 '14 at 14:56
  • I have tried adding a rewrite tag yesterday, but somehow WP keeps dropping the parameter. Sorry for not mentioning this in my question. – Ralph Nov 27 '14 at 14:59
  • @PotterSys: Thank you for your input! I managed to get it working by adding the CPT's name to the rewrite rule. Please see my answer for details. – Ralph Nov 27 '14 at 16:20

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.