Archive for May, 2009

Creating Search Engine Friendly URLS in PHP and MySQL

So, I’ve been playing around a lot with Search Engine Optimization for the website that I maintain at http://advicescene.com/. We have a directory of lawyers that is slowing being updated to include 7000+ lawyers across Canada, and it would be nicer if when people search for a lawyer, the result page doesn’t look something like http://somedomain.com/lawyers.php?id=4.  Instead, it would look much nicer like this:http://advicescene.com/lawyer/BC/Victoria/l-john-alexander.php where search engines and humans can both understand what they are looking at, in this case a Lawyer in Victoria, British Columbia, by the name of L. John Alexander.

There are several ways of tackling this problem. The first one, is to use Apache’s mod_rewrite capabilities to create rules around your URL. This can be very complicated and confusing for long URLs and varied topics. Not always easy to do and can require some relatively extensive database changes and complicated rewrite rules. There is, however, another way to do it that is much easier, requires only 1 additional database field and can adapt very easily to any situation.

Let’s address the URL a little chunk at a time starting with the ending string or file name.

Part of Search Engine Optimization is to create as much of an English-like URL as possible. Search engines, Google in particular, prefer hyphens for word breaks in strings as opposed to underscores or individual word capitalization or other techniques. To create a hyphenated string based on your topic, or in my case, the name of the individual, you need to create a string substitution function, like so:


function friendlyURL($string){
	$string = preg_replace("`\[.*\]`U","",$string);
	$string = preg_replace('`&(amp;)?#?[a-z0-9]+;`i','-',$string);
	$string = htmlentities($string, ENT_COMPAT, 'utf-8');
	$string = preg_replace( "`&([a-z])(acute|uml|circ|grave|ring|cedil|slash|tilde|caron|lig|quot|rsquo);`i","\\1", $string );
	$string = preg_replace( array("`[^a-z0-9]`i","`[-]+`") , "-", $string);
	return strtolower(trim($string, '-'));
}

Once you have the string, store it in your database table where you want to do the query. I created a field called ‘perma’ in my database to handle the string and I added a ‘.php’ extension to it to look more like a file name instead of a directory. You can do it either way, I don’t think there is one way that is better from a SEO standpoint.

Ok, now let’s get to the real trick of creating the URL. I found this from a sitepoint article while doing some research. While the article is out of date and uses an old PHP methodology, I adjusted to make it work with PHP5. The basic idea is that Apache has a lookback feature when parsing a URL. So, the first item after the domain name in the URL can just as easily be a file instead of a directory. We just have to tell Apache that it is indeed a file and handle it accordingly. You do this with Apache’s ForceType directive in a .htaccess file, like so:


<Files article>
ForceType application/x-httpd-php
</Files>

This directive tells Apache to handle the file “articles” as if it were a php file.  Place the .htaccess file in the same location as “articles“. Now, all the processing of the URL can take place in that one file. One such processing that needs to occur is breaking apart the URL into the chunks we need using PHP’s explode() function.

// parse the URL path to retrieve the appropriate information
$details = explode("/", $_SERVER['REQUEST_URI']);

How large the $details array is depends on how long your URL is you need to create and what parts of it you need for your database query, which we can now do. Assuming we have a blog type URL like so: http://somewhere.com/blog/2009/10/12/seo/search-engine-urls.php, we have the following information: year, month, day, category, and title of an article. We then use that information to create a MySQL Query like so:

$result = mysql_query("SELECT * from blog where year='$details[2]' and month='$details[3]' and day='$details[4]' and category='$details[5] and perma='$details[6]'");
// handle result here

I did some extensive tests with the database, and compared looking up a row in the table based on the id number, and using multiple criteria like that above, and the difference in speed is negligible. I do recommend good indexing in your database and index any field where you do lookups to keep your database speedy.

I hope this excerpt was useful to you. I’m always interested in feedback but abhor spam, so please feel free to email me at:

email address if you are human

Stay tuned for part 2, coming soon.

Tags: , , , , , ,

No Comments

Star Trek Boldly Goes

So some friends of mine and I went to see the new Star Trek film. We’ve heard from all sources that it was a great film and we had been chomping at the bit to go. You see, one friend of mine and I are pretty avid Trekies. The movie did not disappoint, and would appeal to both the hard core trekies and the new trekies to be. However, for us old folks, we have something completely new.

At the risk of providing spoilers, forget everything you know about the Star Trek franchise, because this movie changes everything. J.J. Abrams has seen fit to re-write history, or maybe re-write the future with this movie as the beginning. If you want to appeal to a whole new generation, this was the way to do it because the current timeline that you all know and love is completely shot and twisted so much as to be unrecognizable.

I truely enjoyed the new actor’s take on characters such as Scotty, McCoy, Spock, and of course James T. Kirk. We still had some of the great one liners of the original cast, though I was waiting for a “He’s dead Jim” to no avail. In the end, what happens with the timeline doesn’t matter as the movie preserves the core values and characters of the original. But be prepared to be wowed and courted into new movies based on these interpretations of the original characters. I for one, look forward to it.

No Comments