Wewite Wules:
What & Why

About Jim

Time for Jim to Embarass Himself

What is a Rewrite Rule?

Apache's mod_rewrite

Despite the tons of examples and docs, mod_rewrite is voodoo. Damned cool voodoo, but still voodoo.

-- Brian Moore

				
# BEGIN WordPress
<IfModule mod_rewrite.c>
	RewriteEngine On
	RewriteBase /
	RewriteRule ^index\.php$ - [L]
	RewriteCond %{REQUEST_FILENAME} !-f
	RewriteCond %{REQUEST_FILENAME} !-d
	RewriteRule . /index.php [L]
</IfModule>
# END WordPress
				
			

Nginx rewrite

Stored within the site host config file

				
server {
	# ...
	rewrite ^(/download/.*)/media/(\w+)\.?.*$ $1/mp3/$2.mp3 last;
	rewrite ^(/download/.*)/audio/(\w+)\.?.*$ $1/mp3/$2.ra  last;
	return  403;
	# ...
}
				
			

Rewrite vs. Redirect

Within WordPress

WordPress Codex: Using Permalinks
					
# BEGIN WordPress
<IfModule mod_rewrite.c>
	RewriteEngine On
	RewriteBase /
	RewriteRule ^index\.php$ - [L]
	RewriteCond %{REQUEST_FILENAME} !-f
	RewriteCond %{REQUEST_FILENAME} !-d
	RewriteRule . /index.php [L]
</IfModule>
# END WordPress
					
				

Regular Expressions (regex)

				preg_match( '#([0-9]{4})/([0-9]{1,2})/([0-9]{1,2})/([^/]+)(?:/([0-9]+))?#', $url, $matches );
			

Example 1: Regex 101

Example 2: STAT Series Permalink

				
/**
 * Rewrite rules for urls that have been changed
 */
public function action_rewrite_rules( $rewrite ) {
	$series_rules = $rewrite->generate_rewrite_rules( '/series/%postname%/', EP_ALL, true, true, false, false, true );
	$rewrite->rules = array_merge( $series_rules, (array) $rewrite->rules );
}
add_action( 'generate_rewrite_rules', 'action_rewrite_rules' );
				
			

Example 2 cont.

Rewrite Rules Inspector

Example 2 cont.

				
/**
* Filter that will override certain url types.
*/
public function filter_post_link( $permalink, $post, $leavename ) {
	$series_overrides = array(
		'series-one',
		'series-2',
	);
	/*
	* For posts that have been flagged as a series we want to get rid of the
	* date stamp and substitute it with the word 'series'.
	* Since we only need the slug, array key 4 from matches will provide.
	*/
	if ( in_array( $post->post_name, $series_overrides, true )  && 'publish' === get_post_status( $post->ID ) ) {
		preg_match( '#([0-9]{4})/([0-9]{1,2})/([0-9]{1,2})/([^/]+)(?:/([0-9]+))?#', $url, $matches );
		if ( is_array( $matches ) && ! empty( $matches ) && 5 === count( $matches ) ) {
			$permalink = home_url() . '/series/' . $matches[4] . '/';
		}
	}
	return $permalink;
}
add_filter( 'post_link', 'filter_post_link', 10, 3 );
				
			

Precautions

Resources

Thank You

Jim Reevior

@hirozed
jim@jimreevior.com