This is definitely not the first question regarding the issue. I have read a lot and tried, even more, but without success.
I want to do the following: rewrites URLs from: example.com/cars/lambo to: example.com/index.php?p=42&model=lambo
The p parameter corresponds to a fixed page ID I have created.
I have a custom plugin in which I use the plugins_loaded
hook to load the method setupFrontendRewrites
from my CarUrlRewrite
class.
The class looks like that:
class CarUrlRewrite{
const regex = 'cars/(.+?)/?$';
const param = 'model';
const pageId = 42;
// this method is called with the plugins_loaded hook
public static function setupFrontendRewrites(){
add_action('wp_loaded', array(__CLASS__, 'flushRulesIfNecessary'));
add_filter('query_vars', array(__CLASS__, 'addQueryVariables'));
add_action('init', array(__CLASS__, 'rewriteRules'));
add_action('template_redirect', array(__CLASS__, 'rewriteCatchesToInjectContent'));
}
public static function flushRulesIfNecessary(){
$wpRewriteRules = get_option( 'rewrite_rules' );
if (!isset($wpRewriteRules[self::regex])){ // if my regex is missing, flush rules!
global $wp_rewrite;
$wp_rewrite->flush_rules();
}
}
public static function addQueryVariables($vars){
$vars[] = self::param;
return $vars; // this is a filter after all
}
public static function rewriteRules() {
// from: example.com/cars/lambo
// into: example.com/index.php?p=42&model=lambo
add_rewrite_rule(
self::regex,
'index.php?p='.self::pageId.'&'.self::param.'=$matches[1]',
'top'
);
}
// Catch the URL and redirect it to a template file
public static function rewriteCatchesToInjectContent() {
global $wp_query;
$model = array_key_exists('model', $wp_query->query_vars) ? $wp_query->query_vars['model'] : null;
// would expect to see the model parameter filled here, but don't :-(
// do something with the model variable
}
}
I did some error_log
outputs to see that all class methods get called.
What is happening is that the rewrite works in that it forwards me to the page (page ID 42). The URL is then example.com/myslug (where myslug is the permalink from the page). There is no model parameter however. What I need is example.com/myslug?model=lambo