Tag pages and WordPress 2.7

I run the latest version of WordPress from svn, currently “WordPress 2.7-hemorrhage revision 9123”. Usually that’s interesting because it allows me to see the latest patches and fixes on the tool. Basically I do not care that it is not “production” since this is just my personal weblog and it’s actually a breeze to just do exactly the things you wouldn’t do when developing a website for a company. Who cares.

However, in this state of svn I noticed that my tag pages (check the WordPress template hierachy for more information) are not working anymore. They somehow revert to a default page template.

Normally it works like this:


Suppose that I have a tag called “xbox” (which I have applied to all postings about my X-Box 360).

When I then create a php file called “tag-xbox.php” and place this in my template directory, this php page will handle the layout for my tag page on the X-Box. E.g. I could give it a specific side bar, it’s own header, it’s own RSS feed and anything else you can think of.

If this file does not exist WordPress will try to look for “tag.php” and only if that does not exist it will use the default “index.php”.

In the default WordPress installation the first part of the url is “/tag/” followed by the tag, but I changed it in the permalink settings to become “/about/” (because it’s kind of funny to read: “Edward de Leau about xbox” (…):


Well… as you can see on http://edward.de.leau.net/about/xbox it does not work anymore. the tag-xbox.php file is still in my template directory but somehow it’s not being picked up anymore. So I entered a question in the WP Forums, which, in my experience is many times a sort of void box. But who knows who will give an answer to it.

I’m not 100% sure either that it is caused by 2.7 because I did change some things, luckily all my changes are on my home svn server so I can doublecheck those changes.

So let’s get off my lazy b. and (yawn, stretches fingers) dive into the php code again of WordPress to see what has changed.

First things first. Let’s see if someone has already entered an issue about it on trac. Hmm… as far as I can see noone has reported this issue yet.

hypothesis 1: My first guess would be that something has changed in “/include/template-loader.php” and as far as I can see something has changed, but merely the move of one of the checks a few steps down (I love Total Commander…).


So let’s take the lazy route and revert back to the old version, clean the wp-cache and see what happens…nothing… would be too simple..

hypothesis 2: So, maybe something has changed in the “is_tag()” check which is in “query.php” which has changed A LOT. Wow, how beautiful, all these nice informative comments and instaed of “The Big Query” it is now the “WordPress Query API”. Let’s take some time to enjoy the code and then jump to is_tag.


Well.. there were absolutely some interesting things in there to read but as far as I can see the code for the tag check hasn’t been touched.

hypothesis 3: So maybe its the get_tag_template() function that has been changed, which is in “/includes/theme.php”.


This has changed also a lot! Apparently the locate_template function now does the hard work of looking for the tag page. Maybe this new function is still incorrect. Let’s be lazy again and just comment this one out and use the old code.

BINGO! Now my tag pages appear again:


Now let’s see if we can write a patch for it and submit it to WP 2.7 before they release it…


Since they are still testing it, it is more or less a unit test result. Let’s see if I can find out what is wrong with the new function:

   1: /**
   2:  * Returns the name of the highest priority template file that exists
   3:  * 
   4:  * Searches in the STYLESHEETPATH before TEMPLATEPATH so that themes which
   5:  * inherit from a parent theme can just overload one file.
   6:  * @since 2.7
   7:  *
   8:  * @param array $template_names Array of template files to search for in priority order
   9:  * @param bool $load If true the template file will be loaded if it is found.
  10:  * @return string The template filename if one is located.
  11:  */
  12: function locate_template($template_names, $load = false) {
  13:     if (!is_array($template_names))
  14:         return '';
  15:     $located = '';
  16:     foreach($template_names as $template_name) {
  17:         if ( file_exists(STYLESHEETPATH . '/' . $template_name)) {
  18:             $located = STYLESHEETPATH . '/' . $template_name;
  19:             break;
  20:         } else if ( file_exists(TEMPLATEPATH . '/' . $template_name) ) {
  21:             $located = TEMPLATEPATH . '/' . $template_name;
  22:             break;
  23:         }
  24:     }
  25:     if ($load && '' != $located)
  26:         load_template($located);
  27:     return $located;
  28: } 

update (see issue #7685)

Westi writes:

“Nothing is wrong with locate_template.  The fact is that the code in 2.6.x allows for textual tag templates 2.7 for some reason expects them to be numeric tag ids. The change is in get_tag_template() which now wraps an absint around the result of get_query_var ”

Tagged with