Rewriting corfield.org using Fusebox

Update: 5/7/2006 - The site is currently running Fusebox 5 Alpha 3. I am the lead developer for Fusebox 5 and plan to release it publicly at CFUNITED - read what's new in Fusebox 5.

Update: 11/23/2004 - The site is back to being Fusebox-based, this time using Fusebox 4.1 - read about the conversion.

Update: 9/4/2004 - At the beginning of September 2004, I moved the site to a new host that provides ColdFusion MX on a LAMP platform. I subsequently converted the site from PHP to CFML - read about that experience.

Update: 1/12/2004 - On New Year's Eve I rewrote this site using Mach II. Read about my experience converting from Fusebox 3 to Mach II.

Update: 5/17/2003 - I put a Fusebox wrapper around my blog. See below for notes on that experience.

I promised to write up my experience with Fusebox for PHP when I rewrote my site to use it. I know it's been a long time coming and I apologize for that but after the lull in early November that allowed me space to rewrite the site, I was kinda busy working on macromedia.com until we launched the new site recently!

First, a little background. The site was hosted by Hurricane Electric, a small but extremely good ISP based in Fremont, CA (I moved to SmarterLinux.com at the beginning of September 2004). They provide LAMP (Linux, Apache, MySQL and PHP) for just under ten bucks a month. When I decided to move my former (static) site from the UK to America, they were exactly what I was looking for, even tho' I'd never seen PHP in my life. Most of the site remained static although I took advantage of PHP's include() function to provide a uniform look'n'feel with standard headers and footers and, over time, changed a few sections to have a 'main' page which was invoked with an argument to indicate which content to load. Those pages looked like:

<? include('header.php'); ?>
<table border="0">
<tr><td>
<? include('leftnav.php'); ?>
</td><td>
<? include($content.'.php'); ?>
</td><tr>
</table>
<? include('footer.php'); ?>

The URLs looked like /{section}.php?content={page} and, overall, it was fairly easy to figure out the physical page location behind each URL.

Second, my background has been software engineering for about twenty years and for the last decade I've been working in an Object-Oriented environment with C++ and Java and more recently with ColdFusion MX. Consequently, when I first started reading about Fusebox, I was less than complimentary about it, to say the least. My early postings about Fusebox on various mailing lists garnered a lot of heated responses and it became clear to me that the Fusebox community was extremely passionate about their framework. I figured that I owed them a fair trial and promised to rewrite my site to use Fusebox and then write up my experience. The rewrite was completed in November, 2002, and I've just this week given the site a complete overhaul. I figured now was a good time to write it up...

First Impressions

As I said in my blog back in November, there's a fair bit of machinery to learn. I'd read Jeff and Nat's book once, cover-to-cover, and I'd read everything on the Fusebox site. Then I'd downloaded Fusebox for PHP. I don't remember the "Getting Started" guide being available back then - if it was, I obviously chose not to download it.

My first task was to plan the circuits my rewritten site would have. That was pretty straightforward - I figured I'd have a circuit for each of the main sections of the site: home, sean, technical, personal, weddings, bookstore, links. Then I hit my first piece of cognitive dissonance: fbx_Circuits.php. It took me a while to realize that the root directory of the site needed to map to a name so that circuits in directories could be mapped:

$Fusebox["circuits"]["root"] = "home";
$Fusebox["circuits"]["{cname}"] = "home/{directory}";

The home/{directory} thing just looked really weird to me. I guess I couldn't see why it didn't use either /or . to represent the root directory on the site. Once I'd gotten over that, I decided to add circuits for cplusplus, coldfusion and java and nest those within the technical circuit (figuring I'd take advantage of nested layouts if I could). [4/28/2003: Tony Hillerson pointed out on the Fusebox forums that instead of "home" I could indeed have used "." but I guess I was led by the comments in the PHP core files to thinking I had to use "home" -thanx Tony!]

The next piece of cognitive dissonance was that I was so used to a page linking directly to another page that I found it annoying to have to add entries to fbx_Switch.php in the appropriate circuit for every page that I wanted to link to (since most of the pages were static and hence the fuseaction mapped to a simple dsp_xxx.php file). In the end I worked that to my advantage in the C++ section, where I had a lot of pre-existing content files, by having the default fuseaction simply include dsp_action.php for every action. Downside: give it a bad fuseaction and you get a "missing include" error. Upside: saved me a lot of typing! I used Dreamweaver's regular expression pattern replace to change all the old links to use the new URLs and I was mostly done with that part of the site. [1/12/2004: this was a really bad decision with hindsight! I should've done what I did in the BroadVision section and had fuseaction=cplusplus.section/section/xxx and, when I rewrote the site in Mach II, that's exactly what I ended up doing!]

Nested Layouts

I used the basic layout mechanism in Fusebox to 'wrap' my pages in a standard header and footer and took the opportunity to tidy up some of the HTML by using style sheets instead of font tags. Fusebox was encouraging me to separate presentation from actual content since it was forcing me to think about layout separately from pages. Even before the rewrite, I had separate include files for the header and footer (and leftnav) but it was all 'content'. An interesting little glitch was then that I previously had code in my header file that set values used in some of my pages. Since Fusebox executes the layout after the page, that meant moving that code elsewhere. Again, it was one of those cases where I was mixing presentation and logic and simply hadn't noticed. Fusebox made me think about it and move the code to the correct place, the fbx_Settings.php file.

Two sections of the site have left navigation menus: weddings and technical, the latter including cplusplus, coldfusion and java [1/12/2004: I've since dropped the Java section and expanded the ColdFusion section to provide separate Fusebox and Mach II sections] Fusebox provides a fairly clean way to separate out that additional layout by allowing you to nest layouts. I was fairly impressed by how easy that was - each circuit can have its own layout and if circuits are physically nested (in subdirectories) then the layouts automatically nest. Overall, my site has just three layouts: a root layout and a nested layout in each of the technical and weddings circuits. [9/23/2004: As a sidenote, Fusebox 4 abandoned nested layout in favor of the more flexible 'content variables' mechanism. When I rewrote the site to Mach II I had to switch from nested layouts to content variables anyway since Mach II and Fusebox 4 use a similar approach to layouts.]

URL Structure

I mentioned earlier that it was pretty easy to figure out the mapping between URLs and the files on the website in my old site. Fusebox allows you to mask that completely by having a series of circuits that map to any directories you want and all URLs begin with index.php. This sort of abstraction can be a good thing: it allows you to move files around without breaking anyone's bookmarks; it potentially improves security since folks can't see your directory structure. The downside is that the URLs aren't as easy to remember. I liked having URLs like /coldfusion/ and /weddings/ much better than having URLs like index.php?fuseaction=coldfusion.main and index.php?fuseaction=weddings.main so I created directories for some of the circuits anyway and had simple index pages that just redirected to the appropriate Fusebox URL instead... which somewhat defeats the purpose I suppose. Of course, if I was hosting my own server instead of using an ISP, I'd probably add some rewrite rules to Apache and have it map the high-level URLs directly.

Overall, I think the Fusebox URL structure is a bit unwieldy but the abstraction it provides can be useful. [9/23/2004: Mach II suffers from a similar problem since it expects URLs like index.php?event=something and a lot of folks stick to the dot-separated naming to 'group' Mach II events together. I did the same when I rewrote from Fusebox 3 to Mach II]

Ongoing Maintenance

Over time, I've added a few new pages (sorry, 'fuses') and having to update the fbx_Switch.php file no longer annoys me the way it did at first. I've also just given the site a full overhaul and removed a number of tables that were used for layout, replacing them with divs instead. Working on a Fusebox site isn't as bad as I thought it would be although there's still many things about it I don't like, including the file naming convention, but I can live with it. The fairly rigid conventions of Fusebox make you think more carefully about presentation, logic and content which is a good habit to get into. Some of the machinery is unwieldy but it does the job it was designed to do. In the same way that ColdFusion MX has moved toward a more Object-Oriented style and the forthcoming Fusebox MX is following that, I'd like to see how Fusebox for PHP evolves given the OO support in PHP. I have fewer reservations about Fusebox 4 & Fusebox MX but I will have more to say once I've used them for specific projects. [1/12/2004: Fusebox MX became Mach II - this site is now implemented with Mach II for PHP; 5/7/2007: then I converted it from PHP to ColdFusion and later from Mach II to Fusebox 4.1; this site is now running Fusebox 5 Alpha 3!]

Wrapping my Blog

I just finished putting a Fusebox wrapper around my blog, partly to provide some more consistency with the rest of the site and partly because I was curious as to how difficult it would be. The blog is generated by Movable Type and it's plain HTML. [9/23/2004: My blog is powered by Ray Camden's Blog CFC now and is not currently wrapped in a framework; 5/7/2006: and then I wrote a Fusebox wrapper for Blog CFC!] The 'lightbulb moment' was when I realised that HTML pages can be treated as display fuses that provide their own layout. The Fusebox switch simply decides which display fuse to include so the only design issue was how to name the fuseactions. I initially had fuseaction=blog.category&id=xxx for the category archives but then the logical choice for the monthly archives was fuseaction=blog.month&month=yyyy_mm which seemed redundant so I settled on fuseaction=blog.archive&category=xxx and fuseaction=blog.archive&month=yyyy_mm which seemed more generic and will allow me to add other archive types in the future. It also allows the default archives page to be shown for fuseaction=blog.archive which, again, feels 'right'. The other puzzle was the fact that the blog pages are full layouts that do not need the header and footer used on the rest of the site. The approach I took was to change the default layout for the site to allow for fuses to say that they don't additional layout, by using a boolean flag. Somehow this doesn't feel very Fuseboxy so I may experiment to see how to avoid the automatic nesting of layouts in this particular situation.

Overall

So, my opinion has mellowed somewhat but hasn't entirely changed: Fusebox 3 provides a good framework for folks who have no software engineering background because it forces them to think about abstraction and encapsulation in some important ways. For experienced software engineers, I still think Fusebox gets in the way at times and feels a bit clunky. On the other hand, I'm not going to rewrite my site just to get away from Fusebox - I'll keep using it and expanding the site unless I have a compelling reason to change all the URL structure (again!). [1/12/2004: That compelling reason turned out to be Mach II - I didn't initially change the URL structure although I have since adopted event= instead of fuseaction=; 5/7/2006: and then I rewrote the site again, back to Fusebox, but release 4.1!]

Beyond Fusebox 3

9/23/2004: As I indicated above, I had fewer reservations about Fusebox 4 and 4.1 removes even more of my objections. The combination of MVC, full support for CFCs and an expressive XML grammar is very compelling - especially with the promise of an extensible lexicon for Fusebox 4.2. [5/7/2006: Fusebox 4.2 never appeared but we're getting Fusebox 5 this year which has full support for extensible lexicons]