WordPress as CMS – More Than Just “Pretty” (Permalinks)

By Sol in Lab

I had a feeling that the biggest challenge of this little experiment would be finagling proper CMS permalinks out of WordPress. Simply put, I was not let down. Today was my first major foray into the world of WP_Rewrite (the class in WordPress that handles all the URL rewriting), and I feel fortunate to have made it back out to tell the world about it. It is a world full of twists and turns, dead ends, and cliffs of confusion. Haha, nah, actually it was pretty enlightening to look over the class and see where all the URL “magic” happens. I still wouldn’t assume myself to be an expert on the subject, but at least now the depths of WordPress’ inner-workings seem a little less dark and mysterious.

The truth is, I spent most of the day researching just how to manipulate the rewrite rules. Unfortunately, the official documentation was of little help in this matter. Sure, they’ve got a whole bunch of filters and hooks to get at the rewrite rules, but with little to no documentation on the vast majority of them, I can’t say I found much help there. As an aside, though sparse in some areas, the WordPress’ documentation is quite useful. Also, I do realize that the documentation is a community-driven effort, and that I have no place to complain unless I’m willing to do something about it myself (which I am). Anyway, I found some discussion on the subject of rewrite rules in a few places, but a step-by-step rundown of the required steps was not be found. As such, I spent most of the day feeling like I was going in circles, all the while missing the “key” to tying it all together.

Ultimately, it turns out I was looking in the wrong place (sorta) for a solution. WP_Rewrite mainly kept track of the rewrite rules and how WordPress handles fancy URL’s, but it seems to have little part in actually generating the permalinks. For that, we lneed ook to the function, get_permalink() (and its buddies in wp-includes/template-functions-links.php). This function takes the permalink structure defined by WP_Rewrite and generates the link for a post. In order to get the output of this function before it gets to the browser, you’ve got to use the post_link filter, which passes the URL to whatever function you call with the filter. I’ll admit, I spent a certain amount of time playing with the rewrite_rules_array filter, and wondering why nothing was happening to my links. After some more research, I came upon the aforementioned post_link filter, which finally enabled me to access the generated URL and manipulate it like so:
add_filter('post_link','url_magic_time') where url_magic_time is the name of the function that will process the URL before it gets to the browser. With a little bit of hair-pulling (mostly from the big hole in the documentation in this area), I got it working and WordPress is now (mostly) giving me Beautiful Permalinks (not just “Pretty Permalinks”!) 🙂

However, even though I was getting WordPress to generate the URLs of my dreams, the utility of WP_Rewrite remained a mystery to me. Why was everything I read talking about having to make new rewrite rules? Yesterday, I had tested my rewrite rules in my .htaccess file, and everything seemed to be working swimmingly (I tested the rules by manually typing in different URL’s, all of which worked just fine). I was under the impression that I wouldn’t even need to mess with WP_Rewrite to accomplish my goals. In the end, I was (half) right. It seems that when permalinks are turned off, the rewrite rules in .htaccess are enough to redirect a request to the proper destination (e.g. /section_name/post_name/ redirects to /index.php?name=post_name). However, when I turned permalinks on I was getting 404’s all over the place on URL’s that had worked seconds ago. I found it surprising that WordPress had any control over the redirecting of requests, but upon adding a new rewrite rule to WP_Rewrite to recognize my customized permalink structure (with add_filter('rewrite_rules_array','my_fancy_rewrite_rules')), the permalinks were once again in working order! Surely, more testing in this area is required on my part.

I’m glad I got that beast out of the way today. Now comes the fun part: endless tweaking, incremental refinement, and (dread) testing! 🙁 I’m expecting this is where progress slows somewhat. But at least a got I good amount done during these past 3 days!