For the past two weeks I have been working on a major upgrade to my web site, and here it is! Please let me know if you find any problems on the new site. This post talks about the problems I solved during the upgrade.
I have wanted to upgrade my site for a while. I was happy with the content but it needed a better look and feel. There were also some bugs in the simple web store I was using. For example it didn’t force selection of a shipping option so I kept getting orders with no shipping. Bart from the Flusko project suggested using WordPress, as it has nice themes and a bunch of plugins for various stores. Key advantages are a unified look and feel across the blog and static pages, easier navigation, and finding the Store is now much easier.
As I was already using WordPress for my blog this sounded like a good idea. With a bit of encouragement from Rosemary (she cracked up laughing when she saw the old web site) I was off. Like a lot of jobs we put off I actually started enjoying the work after a few days.
Managing Projects by Risk
Like all projects there were some major challenges. My style of project management is to work on the riskiest tasks first. If you nail the riskiest tasks there is much less to go wrong later and the schedule becomes more predictable.
WordPress Look and Feel
The first challenge was to get my head around the WordPress 3.0 and select a theme to get the look and feel I wanted. To get started I installed WordPress 3.0 on a local test machine. I fooled around with themes for a few days before settling on Atahualpa. I checked browser compatibility. I found a bug with the default WordPress 3.0 Twenty Ten theme on Firefox 2.0 – the body text on pages is offset way to the right. Atahualpa renders just fine on Firefox 2.0 and 3.x so Atahualpa is it.
Being a very geeky and not very arty person this phase was actually quite intimidating for me. I didn’t trust my judgement to come up with a good looking site. Where do I start? But like any project a good approach is to break it down into little steps, try a few things, make a few mistakes, and ask questions. I am content with the result and particularly happy with the banner. Fortunately I have lots of cool photos from 4 years of open source work.
The next challenge was the shopping cart.
I had to find a web store that could handle my weird shipping rules. For IP0X sales I don’t have per item shipping, just one fee for an entire shipment. However this is not a flat fee – I have several different shipping options (Air Mail and EMS Courier). For some products I don’t charge for shipping. I also need dual currency support at the same time on the same page. Most store applications support just one currency across the site at any one time.
Anyway my shipping rules and currency support were strange enough that none of the free WordPress shopping carts plug-ins seemed suitable. After playing with different cart plug-ins for a few days I chose to hack the WordPress Simple Paypal Shopping Cart. This was easy to use and was simple (one 700 line PHP source file), which made it easily hackable. So over a couple of days I added options for shipping and multiple currency support that exactly suited the needs of my store. The modified PHP file is here.
To add a store item to a page you insert a “short code” to the WordPress page:
[ wp_cart:IP04 IP-PBX with 0 modules:price:399.00:currency:AUD:needs_shipping:1:anchor:#cart:end ]
This is the entry that creates the “Add to Cart” button for the IP04, like this:
I added new PHP code to support the “currency”, “needs_shipping” and “anchor:” fields. The anchor field tells the cart where on the page to return after an item is added to the cart, for example “store.html#cart”. The default behaviour for this cart is to return to the top of the page which gets annoying when adding multiple products. I use the anchor to return to the shopping cart after each product is added.
The “needs_shipping” flag needs more explanation. When one item in the cart has “needs_shipping” set the checkout button is disabled until a shipping item is added to the cart. You can see various shipping items on the IP0X Store Page. Each shipping item is just like a regular product in the store. Here is the EMS Courier short code:
[ wp_cart:EMS Courier:price:60.00:shipping:0:currency:USD:is_shipping:1:anchor:#cart:end ]
The “is_shipping” flags tells the cart this item is a shipping item which then enables the checkout button. Until a shipping item is selected the customer cannot proceed to the checkout. For items that have shipping included I just don’t include a “needs_shipping” flag in the item short code. I think it’s cool I can hack an store app just for my specific needs. Open source e-business.
Migrating Static Pages from ASCIIDOC
The V1.0 web site used ASCIIDOC to render the static pages. This was actually quite a nice system. I could edit my pages using my favourite editor on my laptop, then use a Makefile to render the pages and automatically upload them. Writing web pages in ASCIIDOC is quick and easy, and the source is human readable even before rendering.
However this meant I had a bunch of web pages in ASCIIDOC markup format that I needed to convert to plain html so I could post them into the new WordPress pages. So I wrote a simple interpreter in Perl to partially render all the pages, called a2h.pl. The output was pasted into the WordPress editor and with a few manual tweaks to the HTML I was happy with the results. I like writing little Perl scripts for these sorts of jobs. Saves a lot of time and prevents many errors that I would make with manual markup. Also some coding work made the web site migration project more interesting. But I do miss using emacs to edit my web site, these web based editors are just not the same.
One not so nice thing about database-driven web sites is the use of page numbers like “/blog/?page_id=434” rather than “about.html”. You can get around this with the WordPress permalinks feature but this involves some .htaccess magic on the server. Not sure if I can do that on my hosted web site so I chickened out and just used some redirect pages like “about.html” below:
This means all my existing links like /ucasterisk/index.html won’t break.
Integrating Static Pages with Existing Blog Pages
Next step was to integrate my static pages with the existing blog posts. Of which there are many. My first attempt was to export the posts from the live rowetel.com/blog and then import them to the test machine using the WordPress Import/Export feature. This worked but all the post IDs were messed up after the import. So a post that had been “?p=1” was now “?p=450”. That wouldn’t do as it would break a bunch of my links.
So after some head scratching I tried another approach. I used phpMyAdmin to dump the live blog database (just like a regular wordpress backup). I then installed this data into a new database on my test machine using phpMyAdmin and fired up a fresh copy of WordPress 3.0. Which unfortunately just sat there and displayed nothing. I guess it doesn’t like starting up with a populated database, especially one from an earlier version of WordPress. I found a few ways around this:
1. Create a fresh database with nothing in it then start up WordPress 3.0. Then use phpMyAdmin to restore all of the database tables from the live site except wp_options.
2. Manually point your browser at the admin login page, “http://localhost/wordpress/wp-admin/. For some reason this would work when the index page of the blog wouldn’t come up.
3. It’s also possible to edit the wp_options table using phpMyAdmin to change any options (like the site URL) that might be messing up WordPress when you install the database on a test machine with a different URL. Using phpMyAdmin is also handy for resetting your password when the blog won’t display.
Anyway the above approaches gave me a working WordPress 3.0 test machine that had all of my old blog posts with the correct post IDs. From there I could import my new static pages into WordPress to get the final merged site. The page_ids of the static pages were also changed during the import but as they were new it didn’t really matter – no one was linking to them yet. I wrote a bunch or little redirect files (as above) to handle redirection of the static pages.
Doing a complete install on a test machine was also great practice. As I built the test site I wrote a check list which I used when I worked on the actual live site. When it takes you 10 minutes to find some obscure theme option it’s a good idea to write it down!
Command Line e-business
When some one places an order on my store I get a PayPal email. I save the email to a file the use a Perl script called paypal2invoice.pl that slurps up this email and converts it into an itemised invoice. Yes, I really do use the Linux command line to generate invoices!
[david@bunny invoices]$ ./paypal2invoice.pl DRR-PO-577-Luke.txt
found postal address
qty_ip04: 1 shipping: cart_total: $540.00 AUD