WordPress (as CMS) Hacking Tips

Note: this is one of a series of posts about the creation of the King Design web site.

I knew the WordPress back-end pretty well up through version 1.2.x, but I was so busy during the 1.5 development cycle that I wasn’t able to contribute much to the 1.5 development.1 Because of this, I had to spend a little time with the new version before I fully understood all the changes. Some changes are fairly fundamental, but they are pretty easy to understand when you get into the code.

In response to my WordPress as a CMS post, several people had questions about how to handle a web site home page with WordPress. For me the answer is quite simple. You need to tell WordPress how to behave, not try to work around what WordPress does by default.

Here is the code I use to show my ‘Home’ page on the King Design web site:

if ($_SERVER['REQUEST_URI'] == '/' ||
$_SERVER['REQUEST_URI'] == '/index.php') {
$_GET['pagename'] = 'home';
}

I put that above this line:

require('wp-blog-header.php');

and that takes care of the home page.

On my home page I have some standard static content and I also have a list of recent news items. This list of recent news items is simply a list of posts within a category. I created a function for displaying the news items, and call it from within the post content using the RunPHP plugin.

When adding customizations to any software package, I find that it is best to make as few changes in the package code as possible. To do this, I generally put all of my code into a single file that I can then include as needed. This also means that instead of having to add several lines of code to accomplish something, you can just call a function you’ve defined in your include file.

My function to show the recent news on the home page is quite simple:

function the_news($limit) {
global $wpdb, $post;
$temp = $wpdb;
query_posts('category_name=news&showposts='.$limit);
print(' <ul class="news">'."\n");
if (have_posts()) {
while (have_posts()) {
the_post();
print('<li><a href="/news/'
.get_the_time("Y/m/d/")
.$post->post_name.'/">'
.get_the_title().'</a><br /><span>'
.get_the_time("F j, Y")
.'</span></li>'."\n"
);
}
}
print(' </ul>'."\n");
$wpdb = $temp;
}

Here is what the code does:

  1. Put the current data in $wpdb and stick it in a $temp variable so I can get it back later.
  2. Use WordPress’s query_posts function to get the data for the news items.
  3. Use standard WP functionality to start a loop with the news item data.
  4. Print out my list of news items (I have to create my own links due to my custom URL scheme).
  5. Now take the original $wpdb data from $temp and stick it back into the $wpdb variable so the rest of the page will behave as expected.

As you can see, this is just a little detour in the standard WP page display. Then I just add this code:

<php the_news(6); ?>

to my RunPHP enabled ‘page’ and that’s it. I used this technique quite a bit for retrieving post data as needed throughout the site. It adds a little overhead, but using a caching hack like Staticize Reloaded can help out there.

Note, RunPHP does have it’s limitations. For example, I couldn’t get this type of code to work:

<php if (1 == 1) { ?>
Show this text.
<php } ?>

however, this worked fine:

<php
if (1 == 1) {
print('Show this text.');
}
?>

While the auto-formatting in WordPress works great 90% of the time, there are times when it just gets in the way. Try as I could to make the code for my contact forms play nicely with WordPress’s auto-formatting, I finally had to give up. Luckily, I’d already written the WP Unformatted plug-in which allows you to disable ‘autop’ and ‘wptexturize’ on a per-post (and per-page) basis. For those pages, I had to turn off the auto-formatting so that I could use my own.

It’s pretty easy to build your own permalink structure if you need to. I did that for both my news items and for my support FAQs. The news items have a URL like this:

/news/2005/03/23/news-item-title/

To create this link manually from within the loop, use the following code:

print('<a href="/news/'
.get_the_time("Y/m/d/")
.$post->post_name.'/">'
.get_the_title().'</a>'
);

Then in your .htaccess file, create the following rewrite rule (should be all one line):

RewriteRule ^news/([0-9]{4})/
([0-9]{1,2})/([0-9]{1,2})/
([^/]+)/?$ /index.php?
category_name=news&
year=$1&monthnum=$2&
day=$3&name=$4

The FAQs use this URL structure:

/support/faq/faq-title/

To create this link manually from within the loop, use the following code:

print('<a href="/support/faq/<?php
print($post->post_name); ?>/"><?php
the_title(); ?></a>'
);

Then in your .htaccess file, create the following rewrite rule (should be all one line):

RewriteRule ^support/faq/
([^/]+)/?$ /index.php?
category_name=faq&name=$1

That should give you an idea of how to grab the information you need to create custom permalinks. If you need a piece of post information and you aren’t sure what it is called, you can always print_r($post) to see all the data and property names in the current $post.

  1. One of the other reasons I haven’t been as active in helping with the WordPress development recently is due to disagreements I’ve had with the way certain features have been implemented and how certain code is structured in the backend. However, you don’t have to agree with every decision made in a project to support it and enjoy using it. :) [back]