- December 30, 2006
- 22 comments
We’re migrating our corporate site to Wordpress. Our first article in the series discussed why we’re doing this. Our second article established project scope. This article will dive into some specific strategies and tactics.
We’re a paid search marketing agency. Our people and our technology are top-notch at search. However, we’re WordPress beginners, not experts. Other impediments: we are new to blogging; we develop in Perl, not PHP; and we’re working on this intermittently, just a few afternoons here and there.
So please read our suggestions with all those warnings in mind. We hope this series helps others implementing WordPress as a CMS. And, hopefully, we’ll benefit from comments from real WordPress experts out there.
This process seems to be working for us. Your mileage may vary.
- Install WP2.x.
Don’t waste your time trying to work with an older version. Many of the plugins you’ll need will require WP2. If you’re building a fresh site, use a fresh modern WordPress install.
- Use one WP install for your CMS; use another for your blog.
You’ll be playing enough games with your templates and plugins to coerce WP to look like a CMS. Don’t make your life more complicated by trying to use one install for both your blog and your core site — you’ll end up with conditionals everywhere. Easier to have two installs.
- Set up a Technorati account for just for this project.
Install the little browser widget (we use the FireFox version) so you can tag pages with a single click. You’ll be bouncing across the web reading documentation. It saves a time to tag every useful page you encounter so you can find it again later. It also helps share knowledge between the different folks working on the migration.
- Use pages, not posts, for your static content.
That is WP wants you to do and it works better.
- Start with a sitemap.
Use Visio, Excel, Denim, or good old pen and paper, but start by sketching out the static pages you’ll need. We thought our corporate site was small — it is — but we ended up with over 40 distinct pages nonetheless.
-
Map your sitemap onto a WP page hierarchy.
With your sitemap in hand, create empty pages for every page on the site. Try to write decent titles and post slugs, but don’t obsess over them at this point. What is important is to make sure the pages are organized intelligently into subpages and, if needed, subsubpages. If you’ve already planned your hierarchy, this should take 10 or 20 minutes of rote button punching. For a huge site, one could script this by pumping data directly into the WP database tables.
Here’s an example of our site hierarchy from earlier in the week. Following WP conventions, a leading dash indicates a subpage, a leading double dash indicates a subsub page, and so on. (Note the dashes aren’t part of the titles; they’re presentation chrome put on by wp-admin/edit-pages.php.)
ID Title
27 About RKG
29 — Management Team
25 — — Alan Rimm-Kaufman
26 — — George Michie
57 — — Larry Becker
62 — — Greg Brennan
28 — Retailer Background
30 — Affiliations
37 — Guarantee
19 — Jobs
50 — — IT
51 — — — About IT
53 — — — IT Intern, Summer ‘07
21 — — — Senior Developer
63 — — — Developer
52 — — About RKG
49 — — CS
20 — — — Analyst, Client Services
54 — — — Marketing Internship, Summer ‘07
55 — — Job Footer
31 Search Marketing
46 — Paid Search
32 — — Brand Versus Non-Brand
33 — — Search Technology
34 — — Shopping Feeds
35 — — Client Service
36 — — Pricing
38 — Natural Search
39 Web Effectiveness
40 Speaking & Writing
41 — Articles
42 — Speaking
47 — — Slides
43 — Studies
44 — Press Center
45 Contact Us
48 — Driving Directions
65 — Privacy Policy
66 — — Compact Privacy Policy
64 Home
- Use a /home for your homepage.
You have several choices on how to handle your homepage. One option is having simple html or php page entirely outside of WP, served directly by Apache. We dismissed this option because (a) you then have hassles keeping the header and footers consistent, and (b) site maintainers can’t edit the homepage through WP. Another option is putting homepage content in the index.php (aka Main) template. We did this until we figured out it is a bad idea, as it violates the keep content and presentation apart rule, generating confusion and unhappiness. The best option, in our opinion, is to place your static homepage content in a page called /home, and use static homepage plugin. This keeps all the standard top and bottom nav out of the /home page, and instead in the page.php template.
- Breadcrumbs, if desired.
At this point, the Breadcrumb Navigation XT plugin should get you nice bread crumbs, if you want ‘em. We made small tweaks, supressing crumbs on the home page (as they are redundant and confusing there) and using the » symbol as our crumb delimiter. (Note: we installed the code markup plugin on both our CMS wordpress install and on our blog wordpress install to display code snippets.)
Use
is_home()to turn off crumbs and unwanted nav on the homepage. - Contextual nav, if desired.
Many sites show a sitemap in the left or right nav, with sections “folding” in and out. Typically, contextual nav trees show the ancestors of the current page, the siblings of the current page, the immediate children of the current page, as well as all top level pages.
Here are two examples. When someone is viewing our ‘Paid Search’ page, the nav should look like this:
* About RKG
* Search Marketing
oo Paid Search
+++ Brand Versus Non-Brand
+++ Search Technology
+++ Shopping Feeds
+++ Client Service
+++ Pricing
oo Natural Search
* Web Effectivess
* Speaking & Writing
* Contact Us
And when they’re on our ‘Contact us’ page, the contextual nav should fold to look like this:
* About RKG
* Search Marketing
* Web Effectivess
* Speaking & Writing
* Contact Us
oo Driving Directions
oo Privacy Policy
While this is hard to explain, it makes sense in practice. This nav folding is easily accomplished by the well-written Fold Page List plugin. If you want contextual nav, this is the plugin for you.
As a good usability rule of thumb, try to make sure pages never link to themselves . Jakob Nielsen named this the tenth of the Top Ten Web Design Mistakes of 2003. It is still often violated today. The never-self-link rule applies to top nav, breadcrumbs, bottom nav, contextual nav, the homepage logo, everything. If you can’t easily omit the self-links, at least fake it by rendering them as non-links using CSS. (Sorry to the purists for that suggestion.)
- Don’t hard-code permalinks in pages.
Your static pages will reference one another, and it is tempting to just cut-and-paste internal links via their permalinks like this:
href="http://myblog.com/some-other-page". We suggest avoiding this, as it makes your content brittle to any changes in your permalinks.As we described in our second post in this series, our WP CMS lives at rimmkaufman.com/wp for the time being. We’ll later hide all the /wp stuff through heavy rewrite rules, to be described later. If we embed links to, say “/wp/search-marketing” in our top nav, we don’t want to have to go back and edit this to remove the “wp”, nor do we want the site issuing 301 redirects on every internal site click to remove the “wp”.
Our solution is to reference every page by number in posts and on pages. Page IDs should never change, even when page slugs and/or permalink structures change. For aesthetics and SEO benefit, we can remap these numbers to permalinks on the fly using a filter, so outsiders never need see the ugly IDs. Thanks, Wordpress, for offering so many nice hooks.
Here’s a tiny 8 line plugin that accomplishes this remapping across the site:
/*
Plugin Name: RKG Page Permalinks
Plugin URI: none
Description: change “/index.php?page_id=\d+” links into permalinks
Version: 0.1
Author: RKG
Author URI: http://www.rimmkaufman.com/rkgblog
*/
// changing permalinks breaks links embedded in pages.
// to avoid this, we’ll use the “/index.php?page_id=25″ syntax to reference
// wp pages from other wp pages and wp posts.
// we install a filter to modify all these links into permalinks on-the-fly
// thus, these keep working when we modify permalink structure.
// note this strategy fails gracefully in the absence of this plugin or if the regexp
// doesn’t match correctly (in contrast to inventing our own page-link-by-number
// syntax) because WP accepts “/index.php?page_id=25″ as valid syntax to reference a page by number
//
// see also: http://codex.wordpress.org/Filters
// see also: http://codex.wordpress.org/Template_Tags/get_permalink
// see also: http://codex.wordpress.org/Linking_Posts_Pages_and_Categories
function quoted_permalink ($num) {return ‘”‘ . get_permalink($num) . ‘”‘;}
function rkg_pagepermalinks($content) {
// case one: relative index link (so by definition is on our site)
$pattern = ‘/”\/index.php\?page_id=(\d+)”/e’;
$content = preg_replace($pattern, ‘quoted_permalink(${1})’, $content);
// case two: absolute index link (must make sure is on our site)
$pattern = ‘/”http:\S*rimmkaufman\.com\S*\/index.php\?page_id=(\d+)”/e’;
$content = preg_replace($pattern, ‘quoted_permalink(${1})’, $content);
return $content;
}
add_filter(’the_content’, ‘rkg_pagepermalinks’);
?>
Make sure to modify the ‘rimmkaufman’ in ‘case two’ to match your domain.
- Use safe-includes to put code in content.
It is easy to put php code in a template — indeed, php code is all a template is. For security, and to separate code from content, WP makes it hard for you place php code in posts. There are times, though, when you need a smidgen of php on a page. For example, we place the current date atop our jobs page to indicate the page is fresh. (It is; we’re hiring.)
While there are several plugs which allow php in pages and on posts, we opted to use the Safe Include plugin. Rather than allow arbritrary code in posts and pages — which could be a major security hole — Safe Include makes you define a chunks of text via external files which are then be included via double braces:. This offers more protection from user mistakes and from bad guys than the php exec plugin. - Use subpages and the page hierarchy to include common content.
Some areas of the site have common chunks of content. For example, we end each job posting with a common slug of benefits:
RKG benefits include 17 paid vacation days; 9 paid holidays, including your birthday; profit sharing plan;
401k plan with company match; health insurance; great weather; blah blah blahWe don’t want to repeat this slug manually on each post, as they’ll get out of sync. We don’t want to mangle the page template, as (1) this slug is content, not presentation; and (2) we want site maintainers to be able to edit the slug easily. Likewise, we don’t want to use the Static Include plugin for such slugs, as site maintainers couldn’t edit them through the WP interface.
Our engineers proposed including chunks of content by exploiting subpages and the page hierarchy. The following snippet lives in the page.php template. Here’s their trick:
if (!is_home()) {
// here’s how we do page includes
// include page 55 on page 19 and all of 19s descendents
$footers = array(’19′ => 55);$p = $post;
while ($p) {
// dont include page on itself
if (array_key_exists($p->ID,$footers) && $post != $p->ID) {
$f = get_post($footers[$p->ID]);
echo “\n”;
break;
}
$p = $p->post_parent;
}
}
?>What this code does is insert page 55 (”Job Footer”) on page 19 (”Jobs”) and on all of page 19’s subpages. Slick. We could easily add other pages to other parts of the hierarchy as well. As example, changing
$footers = array('19' => 55);to
$footers = array('19' => 55, '29'=>66);would also place our compact privacy policy on the bottom of all our management team bio pages. That’s not something we’d ever want to do, but it illustrates the point.
- Put more important content higher in the source.
For modest SEO benefit, it is helpful to place core page content above generic page content. We’ve opted to place our right contextual nav at the bottom of the source, versus the more customary place at the beginning. We’ll use CSS to render this element where it belongs, on the top right of each page.
Well, that’s about all for this installment in the series.
With the page framework of the site in place, we’ll next be turning our attention to tweaking our marketing content.
And, as described in a previous post, we’re also working finishing up the code to use WP posts (not WP pages) to handle our “upcoming” and “recently occurred” events, as well as the date issues involved in our print articles in the trades.
A very happy New Years to all — may 2007 be full of health, peace, and success for you and your family. See you next year!
If you like this post, consider subscribing to our RSS feed. You can also have new posts sent to you via email.
Similar Posts
- Tips For Using WordPress As A Content Management System (CMS)
- WordPress as CMS: Scope and Initial Progress
- Excellent 404 Handling
- More Tips For Using WordPress As A Web Content Management System
- Home Page Usability and Credibility Survey
Trackback
http://www.rimmkaufman.com/rkgblog/2006/12/30/wordpress-cms-breadcrumbs-nav-plugins/trackback/Blogs Citing This Post
- Pingback: The no money, no talent website on November 9, 2007
- Pingback: My del.icio.us bookmarks for January 18th : Discovering my World… on January 18, 2008
- Pingback: Can I use WordPress as a Content Management System? A WordPress as CMS resource list. | Independent Digital on February 12, 2008
- Pingback: Ressourcen um Wordpress als CMS zu nutzen « Wordpress, Plugins, Reasons, Beispiel, Five, Themes, Available, “CMS « Volderette on March 7, 2008
- Pingback: Powerfull List of WordPress Lifesavers Plugins on March 30, 2008
- Pingback: Skylog » Blog Archive » links for 2008-04-15 on April 15, 2008
- Pingback: Powerfull List of WordPress Lifesavers Plugins | SEO & Web Design on May 6, 2008


Great post! I am working on a similar project and this has been a great help. I was unsure about using WP to power an entire site, but after 2.1 I feel its really ready.
One thing I am confused about though… I am using the same bread crumb plugin and dont quite under stand is_home() in order to remove it from the home page. Any advice? Thanks!
Hi Ethan — Thanks for the kind words — Not quite following you r.e. the code — post some code or drop an email and our engineering folks will try to help — Cheers — Alan
Alan… Thanks for the response.
Under #8 you mention -
“Use is_home() to turn off crumbs and unwanted nav on the homepage.”
Where withing the
Ethan:
Something like this (untested!)
<div class="breadcrumb">
<?php
if (class_exists(’breadcrumb_navigation_xt’) && !is_home() ) {
// new breadcrumb object, skip if homepage
$mybreadcrumb = new breadcrumb_navigation_xt;
$mybreadcrumb->opt[’separator’] = ‘ » ‘;
$mybreadcrumb->opt[’static_frontpage’] = TRUE;
$mybreadcrumb->display();
}
?>
</div>
Great article. I have also used Wordpress as a CMS on a number of projects. While it certainly isn’t as robust as Drupal, it’s also not as complicated to use. Generally speaking, the admin. assistant at company X doesn’t want to know what a ‘node’ is.
The other area where wordpress really shines is in the use of templates. Using specific templates for different sections of the website reduces the need to for conditionals and allows for different parts of the website to have a completely different look and feel than others. Not always essential, but an important tool to have in your back pocket.
Thanks again for the Breadcrumb tip, but it didn’t seem to take. Maybe it is because I am on 2.1
Alan!
You mention that one should use 2 installations- one for the CMS and another for the Blog.
However you haven’t (yet?!?) indicated what one can do to integrate the 2 parts. What do you suggest?
Also, you mention “heavy rewrite rules” to hide the “wp” in section 10… are you going to elaborate?
Thanks for this great series. I can’t wait for the next exciting episode.
Peter
PeterL: We gained a great burst of new business and so our team’s work on our own site slowed to a complete standstill. I need to get our gang reenergenized on that! The two sites wouldn’t be integrated per se. They’d live on the same domain, they’d cross link, but as we want such different functionality and look between the corp site and the corp blog, we opted for two distinct WP installs.
Yes, the heavy rewrite post is coming — I think that’s an important issue and we’ll blog it.
Cheers –
Alan
I am very new to WordPress, so forgive me if this is a silly question, but I was under the impression that creating new page templates within WP would solve the issues you mentioned in points 11 and 12.
Thanks for the plugin at point 10; it solved a problem for me which I didn’t know could be solved :)
Alex
PS: I’ve just been bounced back here because I assumed that “three plus eight plus nine” was “twenty” rather than “20″. Whoops.
Hi Alex: As for 11, we needed arbitrary CODE inserted, eg PHP to execute, so templates wouldn’t do that for us. As for 12, we’re lazy and belive in DRY (don’t repeat yourself) code, so we took the approach of auto-including snippets. Again, this is a work in progress, and not yet live — more to come!
thanks for the comment
A
Hello ALl
This is a very useful post and gives tips and information on Pages, Nav, Crumbs and Pluging. It also explains how the Wordpress is to be used But there are number of points that needs to be explained and understood. For eg. As Alan said you should use 2 installations but he needs the explaination how these 2 can be integrated?
Overall it has been very useful.
You talk about using the page fold list to display your navigation and I noticed that in some cases you are using 3 levels. Can you provide the code you used to do this? I have been having real trouble getting mine to work, I can go down to 2 levels fine, but as soon I reach 3, my nav dissapears:-(
Hi David — We’re no longer using the exact code listed here. And I notice we mangled the CSS on this page. Let me try to get this page cleaned up, and post a new entry on how we handled nav. This post was from 12/06, by the time we launched the site (11/07), we took a diff route. More to come on this shortly.
Hi Dean — Sure, let me follow up on the double WP issue in a diff post (see note to David above).
Cheers
Alan
This is very nice. I’ve just gotten into Blogging and WordPress. I have used a lot of .php code on my sites, and have added one test blog. Trying to get a better coordination between blog and site seems ideal. This article really helps describe some of the ways to do this from scratch and some ideas for me to use on an existing site. Thanks Again. Now I need to find the second part of this post.
A great post. I´m working in similar proyect based on wordpress and this post is very usefull for make it.
Thank you!