Tuesday, December 19, 2006

Mac OS X & Windows in Parallel

The first most natural reaction for a Mac guy like me is "Ick! Windows on my Mac?!". And yeah, it is a bit disgusting. After all we all know that Mac OS X is obviously the superior operating system, right?

Well even if you don't necessarily agree with that assertion, you have to agree that if you're any kind of web developer you can't ignore Internet Explorer. Despite all its warts and laughable standards adherence, it is the browser that most people use. So if you care about giving those users the best experience when visiting your site you need to view it in IE.

My solution was to use Windows 2000 (with SP4 and IE6 installed) within Parallels and I've been pretty happy. W2K runs very well and being able to seamlessly run my webapps in IE while continuing to work in Mac OS X gives me exactly what I need. So here's the recipe:
  1. Install Parallels (get a demo from Parallels to try it out). You might also want to give the beta 3036 version a try (I did). It has some great features like the "coherence" view that lets you mix the W2K windows in with your Mac OS X windows.
  2. Create a Windows virtual machine and install Windows (take a deep breath its a little surreal)
  3. Once you have the VM open go to the Parallels Action menu and choose "Install Parallels Tools...". This improves performance, mouse support, the graphics capabilities and lets you drag files to the Windows desktop (and probably a bunch of other stuff too).
  4. Set Windows' screen resolution, colour depth, font antialiasing, and be sure to set "Show window contents while dragging". The last option is important if you use Parallels' coherence view.
  5. Start up your web server in Mac OS X, and be sure to open the necessary ports in your built-in Mac OS X firewall to let Windows see your server (e.g., Tomcat is 8080 by default and WEBrick is 3000 by default).
  6. Type in your Mac's IP address in IE and enjoy! (Well hopefully enjoy, IE has a tendency of frustrating a lot of developers).

Wednesday, December 06, 2006

Passionate Development

A lot of people seem to have a real passion for developing software. So why is it that we have so much bad code? Well I have my own theories. So without further ado I present my most-wanted list of culprits, in no-particular order:

New coders

New developers are great. They're happy to have a job and are excited and keen and want to change the world. But they don't really know what they're doing. Hey sorry, but I've been there, I know. You can always do better the second time. And when you're new you write a lot of code. You do the first thing that pops into your head. That's not usually a good recipe for creating good code. I've said it before and I'll say it again, mentor these people and give them training. They don't mind learning and usually take constructive feedback well.

Gung ho Project Managers

Project deadlines are very rarely made with developer input and even if they are, deadlines are never adjusted to account for unanticipated problems or changing requirements. The usual solution is to throw more coders at the problem. To write code under the obligation to create software to help someone do their job is one thing. To do it under duress is completely another. Project Managers love to be "under budget" and "on-time". A lot of them don't care what it takes to get there. Tie some of their compensation to creating maintable systems and they'll help do the right thing.

Heroes

You know who I'm talking about. Every place has at least one of them. An environment that routinely has ridiculous productivity expectations seems to attract the evil genius who works his ass off to produce a solution. Like the new coder, this guy writes a lot of code and lives for the pat-on-the-back and the "attaboy". But he isn't really interested in producing an elegant bit of code. Rather he lives for the hack that will make things work at the last minute and "save the company". The problem with this guy is that he perpetuates the bad productivity expectations and increases the brittleness of the environment. Keep some kryptonite handy to slow him down.

The Architect

You know that fat dude from the Matrix who talks in riddles that nobody understands (says shit like "vis a vis" and "ergo"). Picture that guy and make him an IT architect and you'll get my drift. Architecture is a good thing and somebody needs to think about it, but a lot of these enterprise architects have no accountability to anyone and dream up all kinds of crazy impractical things to do. Take for instance all this SOA, Web Service stuff... Good Lord what a mess! But talk to an "architect" and he'll have tears in his eyes when he explains the world he sees through his rose colored glasses. If you're gonna have people called "architects" (regardless of how bad that analogy is for software development) then assign them to projects and make them responsible for something. (btw: I was a technical architect once so save your hate mail. I know what I'm talking about, vis a vis)

The Academic

These guys are aspiring architects. They love to look for the next great solution and somehow work it into their latest projects. There is such a thing as the progression of technology and you should upgrade the technology in your project so that it doesn't become a backwater for discarded frameworks. But you need to be careful. If you blindly adopt the latest and greatest all the time then you'll spend more of your time working the bugs out of these frameworks than you will actually developing your own software. The elusive silver bullet will often shoot you in the foot.

Support Developers

A lot of places I've been devote some developers to supporting the applications in production. They're motivated by the desire to fix bugs and enhance the application to meet ongoing user demand. So while that's a good thing, they usually have to support 20 applications simultaneously, don't really understand how any of them are put together, and only have to touch the code every so often. So what happens is that the application code (no matter how lovingly crafted during development) slowly decays over time. The solution? Make sure the people who developed the application are resonsible for maintaining them. There's nothing like knowing your own code may come back to haunt you, to keep you focussed on writing good code.

DBAs

These characters live in an alternate universe of sets, joins and intersections and they rule this kingdom. They institute all kinds of rules that don't always make sense from all perspectives. Understandably, they want to enforce certain conventions so that things are consistent and easier to maintain. But every once in a while these guys need to stop defending the battlements and adopt the prevailing wisdom of the land. For example, DBA purists will usually get pretty hostile if you talk about using surrogate primary keys to ease the object relational mapping burden. They'll get all academic about composite natural keys. And while their argument may make absolute sense from their perspective, they need to undertand that their unreasonable rules can result in less elegant code. Don't even get me started on the "law" about only updating tables through stored procedures.

Summary

Nobody sets out to create nasty tangles of code. Most people are at least somewhat passionate about what they do. They want to have pride in their work. Now it's easy to fall into the trap of negativity and start believing in the futility of trying to make things better. (Lord knows I've fallen in there once or twice). But in the end that's what you have to work with. Greenfield development seems to be a rare commodity. So recognize the poor behaviors, try to understand the motivations behind them, state your opinion, make good decisions (or at least try to influence the decision makers) and do what you can to make your coding world better. And for god sakes, stop writing crap code! ;-)


Digg!

Monday, December 04, 2006

Java Compiler Woes

To cut a long story short, I lost a couple days of effort to discover that you should always use the version of the Java compiler that matches your production environment. Take for example this little piece of Java code:

import java.math.BigDecimal;

public class BigDecimalTest {
public static void main(String[] args) {
BigDecimal big = new BigDecimal(100);
System.out.println(big);
}
}

Compile it and run it in Java 1.4 and it prints out "100". Compile it and run it in Java 5 and it prints out "100". But now take that Java 5 compiled class (e.g., javac -target 1.4 -source 1.4 BigDecimalTest.java) and run it in Java 1.4 and you get:

Exception in thread "main" java.lang.NoSuchMethodError:
java.math.BigDecimal.(I)V
at BigDecimalTest.main(BigDecimalTest.java:5)

The problem is that Java 5 introduced a new constructor for BigDecimal that takes an int. So once compiled in Java 5, the class expects to find a constructor to match that signature and when run in Java 1.4, it blows up spectacularly. Nasty little mess.

Sunday, December 03, 2006

Airmiles with that?

The latest edition to my family of computers is slowly making it's way around the world. It started its life in China, then Anchorage, then flew straight overhead to Memphis, and is now getting acquainted with Canadian customs in Mississauga. Unfortunately, more than half the shipping time has been spent there waiting for some customs official to give it the green light to move on. If only I could get air miles for the trip perhaps I'd have a little more patience for this delay. C'mon you guys, get a move on!

P.S., Ain't Google Maps cool?!

Wednesday, November 22, 2006

Enterprise Software? You gotta be kidding me!

If you create truly mediocre software for a vertical market in a mainstream technology like .NET, fill it with buzzwords like "web services", then the truly ignorant will shower you with bags of money. Apparently that's the recipe to becoming a success. Hard to believe isn't it? Well I wish it weren't true but it must be. Otherwise I have no explanation for the project that I'm working on.

Recommendation #1. Make it real ugly.
I commented earlier this year about the ugly UI, and since then things haven't gotten much better as I've started to dig around under the covers. The entire UI is driven via metadata. Nobody actually designs this interface to help the user solve his problem. Hell no! That's way too much work. Instead, tell it there's a new column and it just adds it the the grid. Wow. That's brilliant. Yeah it's ultimately flexible and configurable by every single client but then you end up with one ugly generic UI. Where's the dialogue between designer, developer, and user about what's critical?

Recommendation #2. Use .NET specific types in your Web Services
Because this is largely an integration project we tried to follow the vendor's recommendation to use their "platform-neutral, next-generation, SOA compliant", web services. Well that turned out to be a bust because their crappy implementation simply returns a serialized Microsoft .NET DataSet that no other toolset (including AXIS for Java) seems to be able to understand it. We ended up using a TCP/IP monitor to reverse engineer this abomination just so that we could figure out how to call it. And if you've ever looked at the XML of a serialized dataset you'd know immediately that this isn't something you should be exposing to your clients in the first place. It basically opens the kimono and says "here's my data model". So now there's zero abstraction from the database. If it changes then so does the web service. I can see that being nice and stable. Not!

Recommendation #3. Release often and change your external API.
Trying to write some code on top of something that changes all the time is like building a house on mud. Just yesterday, we discovered that their latest version of the app has a subtle change in the URLs for the web services. Suddenly none of our code worked. (BTW: I argued that we should test this thing before just dumping it on our servers but nobody listened).

Recommendation #4. Make ridiculous claims and milk your clients for consulting fees.
The vendor said it works with Oracle to make the sale but their consultant, who came onsite for a week to troubleshoot the performance problem, made the astounding pronouncement: "it works faster with SQL Server". What? What about the promises you made before and are you sure that'll fix anything? During our load testing we discovered that the CPU utilization on the database server is minimal regardless of database flavor. It's the application server that's pinned! How come they didn't mention that?

Conclusion Make crappy software for a niche market whose users are dumb enough to get dazzled by a flashy demo. Then sell a license for some exorbitant fee and just start milking them with expensive consulting served up by people who don't have a clue what they're talking about. Sure your users and their pathetic IT staff will grow to loathe you, but hey you already have their money and there's always another sucker knocking on your door just dying to buy your "enterprise software".

Or you could just Get Real...

Ruby on Rails demo

Yesterday I gave my co-workers a lunch time presentation about Ruby on Rails. Since these guys haven't even seen Ruby, never mind Rails, I kept it pretty basic and loosely based it on DHH's build-a-blog-in-15-minutes screencast at RubyOnRails.org. I coded live and in person and even the mistakes I made were good because they highlighted not only Rails' good error reporting but also the quick edit-and-refresh-the-browser style of coding. No Ant scripts, no compiling, no restarting the app server, no waiting for the VM, etc.

In the end I think I made the impact I wanted. I showed people some other ways of developing web applications that are fundamentally more productive than the endless configuration hell we Java developers tend to work in. Unfortunately, I also heard unfortunate statements like "that's cool but we're a Java shop and we'd never be able to deploy something like that". While that was disappointing, I kept my composure and plugged JRuby as a possible future solution (I can't wait to be able to a build a Rails app into a WAR and deploy it in WebLogic).

I planted the seed. Now all I have to do is continue to nurture the idea of Rails development, continue the education and hope for a brighter future.

Saturday, November 11, 2006

Tim Bray: PHP, Rails, & Java


Tim Bray, of Sun Microsystems, set off a little bombshell with one slide from a presentation he gave at the International PHP Conference. The slide in question compares PHP, Rails, & Java on four separate criteria: Scaling, Dev Speed, Dev Tools, & Maintainability. Rails won on Dev Speed and Maintainability and PHP won the scaling contest!

The presentation even goes on to talk about the WS-* specs being too complex (he even borrowed DHH's WS-Deathstar slide). Who would have thought things like this would be coming out of the mouths of people at Sun? Can't say that I disagree... Fewer lines of more readable code should mean greater productivity and better maintenance. That seems like a no-brainer.

Monday, November 06, 2006

Code Generation with Ruby

I just watched some parts of a Google Tech Talk Video about code generation. It was a videotaped presentation by Jack Harrington, the author of "Code Generation in Action" to some of the developers at Google. I didn't find most of the presentation to be that interesting, but there was one snippet of Ruby code that I liked. It looked something like this:

require 'erb'

File.open('./test.txt', 'w+') do |f|
name='Darcy'
erb = ERB.new(File.new('template').read)
f.write(erb.result(binding))
end

My template file was a single line that contained this: "Hello <%=name%>". I think you can probably figure out what the result would look like ;-)

The real example he used in his presentation was slightly more elaborate in that he had a source of data, an XML file, and he used REXML (a great XML library in Ruby) to read the source to generate a SQL file.

I'm not a big advocate of code generation but if you find yourself in the unenviable position of needing to do it then this is a great place to sprinkle in a little Ruby magic.

Wednesday, November 01, 2006

Sucking the Fun Out of Software Development

Last week I found myself being subjected to one of the worst fates known to the North American cubicle dweller... the dreaded team building meeting. Acckkkk!!!

But even worse was that the typical mind-numbing "personality profiling exercise" was replaced with the excruciating "enterprise architecture presentation".

Where do these guys come from anyway? Who uses words like "end user vision", "long range target architecture", "governance board" and garbage like that?

Quite frankly I don't have the patience for it. If you get a thrill trying to out-merriam-webster a bunch of other like minded architecture zombies then all the power to you, but don't come to my precious team-building meeting and make things worse by spouting that meaningless drivel at me.

I tried to pay attention in order to show some respect for my fellow man, but before I knew it I felt like Charlie Brown listening to his teacher, mwah-mwah-mwah...

So I first started sketching to try and relieve the tedium but soon found myself writing down a bunch of words to describe the corporate architecture team and this crap presentation. Here's what I wrote:
  • bureaucratic
  • roadblocks
  • undemocratic (appointed)
  • not a meritocracy
  • unrealistic
  • double talk
  • expensive
Does that list remind you of anything else? Well I dunno about you but my mind goes straight to several branches of the government. Uh oh...

Anyway, my point goes back to the stuff that DHH talks about all the time:
  1. Beauty leads to happiness
  2. Happiness leads to productivty
  3. (therefore) Beauty leads to productivity
Maybe, just maybe, if these IT departments would just stop sucking the fun out of software development, then maybe, just maybe, we could get back to actually delivering some real value to our clients. I'm not saying that we should completely ignore architecture or good design, but if you've somehow let your focus shift from delivering value to your customers to creating Powerpoint presentations full of words that nobody understands just in order to try and sound important then please find someone who cares and get out of my face so that I can get back to what really matters!


Digg!

Sunday, October 22, 2006

RadRails Refresher

So I started working a bit harder on a rails project this past weekend (several hours a day) and discovered a few things about Ruby/Rails and my IDE that I thought I'd share (in no particular order):
  1. RadRails has the ability to automatically run your unit tests whenever you modify certain files. The AutoTest functionality is great but only if you realize it's there. I had been staring at a big red 'X' in the toolbar occassionally wondering "I wonder what that's for" and then suddenly saw a nice big green checkmark after I fixed a bunch of tests. Duh!
  2. ctrl-space is your friend. In the absence of any true "intellisense"-like functionality, RadRails' templates will save you a bunch of typing. In fact if you're a TextMate refugee then try Corban Brook's textmate-like templates for RadRails.
  3. Rake is cool, but I always forget all the tasks I can run. Yes even the simple ones like "rake migrate VERSION=3" or "rake db:fixtures:load" seem to continually elude me. Well RadRails has a Rake view. Just make sure you're in a Rails project and then Bob's your uncle.
  4. I like watching the development log. And lo and behold RadRails allows me to right click on the .log file in the Rails Navigator and select "Tail". This allows me to watch the end of the file in a console window. I recommend creating a new console view, displaying the tailed log file, and then pinning it. Then drag it somewhere where you can always see it.
  5. The servers view allows me to set up a mongrel view and then start, stop, and restart it with the click of a button. It also has a handy little globe button for opening a browser within RadRails that goes to your default URL. The browser's functionality is a bit anemic, but it's still a nice touch.
  6. Autotest is awesome but if you want to run a single unit test, just open it in an editor, right click and select "Run As -> Test::Unit Test"
  7. When I use Eclipse to do Java editing I often like to click the button in the toolbar that only shows me the selected element in my editor. That way I can focus on a single method at a time. RadRails has this button too but it seems to be permanently disabled. But if you have the outline view kicking around, try clicking on a method and watch what happens.
  8. I like to keep the Data Navigator view around to see the table structures. Comes in handy when I can't remember some detail about my data model.
  9. My console view doesn't work. Something abut the readline library on Mac OS X I think... Regardless, if it works for you either use it or keep a terminal window open. The console rocks.
  10. Thanks to the "has_many :through" blog I discovered that I can add a block to associations in ActiveRecord classes and add methods to these associations. For example, I added a find method to one of my has_many relationships. The cool thing is that the find method is scoped by its outer has_many definition. Not sure if I really understand what's going on under the covers (still figuring this Ruby thing out) but it seems like an elegant way to express something like this: user.blog_entries.find_all_by_tag( tag ).
  11. Now if I could only remember what the RadRails shortcut keys were for navigating between models and tests and navigating between controllers and views I'd be happy...(UPDATE: CTRL-SHIFT-V to go between controller and view, CTRL-ALT-T to go between model/controller and test)

Digg!

Saturday, October 14, 2006

Google Reader

News Readers have been around for several years and like many other people I have my own collection of feeds to which I subscribe. The only problem was synchronization from computer to computer. It was fairly common for me to read through a list of published articles at work and then come home to do it all over again. It wasn't as time consuming the second time because I could just skip over the ones I'd already read but it was still annoying.

So finally, Google's listened to its users and upgraded its previously weak Google Reader and added the features I needed to use it full time. It's amazing to me what they can accomplish with a browser application. It's making me rethink what can be done with a web app.

Wednesday, September 27, 2006

Digg, Ruby, & Cocoa

I recently discovered that Digg allows you to simplify story submission for readers by placing a "digg this" link on your website. That sounded like a reasonable thing to do for my blog entries and after reading Guy Kawasaki's blog about it, I decided to give it a whirl. It wasn't long before I found myself wanting to automate the generation of the anchor tag. So I immediately ran off to my Ruby editor and generated a little script:

require "erb"
include ERB::Util

title, description, url, topic = ARGV[0], ARGV[1], ARGV[2], ARGV[3]
puts <<EOS

<a href="http://adigg.com/submit?phase=2

&url=#{url_encode(url)}

&title=#{url_encode(title)}

&bodytext=#{url_encode(description)}

&topic=#{url_encode(topic)}">

<img src="http://digg.com/img/badges/91x17-digg-button.gif"

width="91" height="17" alt="Digg!" border="0" />

</a>

EOS


That worked reasonably well, but then I started thinking back to all the stuff I learned about Mac OS X software development with Cocoa and decided that I should really wrap up my cute little Ruby script with a Cocoa GUI!

So I immediately opened XCode, generated a Cocoa application, and started messing around with Interface Builder. Here's what I came up with:



From Interface Builder I stubbed out my controller class (MVC after all!) and wired the button to an action method. I also decided to use Cocoa Bindings to wire the text fields to NSString properties in my model without any code. Now since my model only needed to expose four string properties (one for each field in my window) I chose to cheat a bit and just added the four properties to the controller.

Since Objective-C doesn't have automatic memory management, you typically manage the memory allocation and deallocation in the accessors. Fortunately Accessorizor came to my rescue and generated that code for me. So the only thing left for me to code was to pass my four text values to my Ruby script. A simple Google search resulted in this page on Cocoa Dev Central that describes how to call the 'ls' unix command from Cocoa. I quickly adapted it for calling my Ruby script. The one change I made was that I added my Ruby script to my XCode project as a resource so that it would be included in the application bundle at build time. So I added this line for finding it:

NSString *path = [[NSBundle mainBundle] pathForResource:@"digg" ofType:@"rb"];


Finally I decided it would be nice to just put the generated anchor tag on the clipboard when I click on the "Digg It" button. So I perused my "Cocoa Programming For Mac OS X" book and added these three lines:

NSPasteboard *pb = [NSPasteboard generalPasteboard];
[pb declareTypes:[NSArray arrayWithObject:NSStringPboardType] owner:self];
[pb setString:string forType:NSStringPboardType];


and voila:


Digg!

Sunday, September 24, 2006

Rethinking the car



Here are two extraordinary cars that I discovered through the magic of the internet. One is the Tesla Roadster. The Tesla is fascinating because it redefines what an electric car can be. How does 0 to 60mph in about 4 seconds and 135mpg equivalent all wrapped up in a gorgeous sports car package sound? Nikola Tesla would be proud.

Then you have the Ariel Atom. A stripped down minimal sports car with a phenomenal power to weight ratio but no windshield. You have to see this one to believe it. It's amazing.

I'll take one of each. ;-)

Wednesday, September 20, 2006

Ruby User Group Meeting

Last night I attended my first Ruby user group meeting. I've been a member of a lot of user groups and so my expectations were (perhaps unreasonably) high. My initial impressions weren't that great and I left the meeting unsure whether or not I'd return the following month.

But then I started to think about it:
  1. Here were a bunch of geeks (me included) getting together to talk about a nascent technology in a city largely dominated by Java and .NET. The fact that these people cared enough about fostering the growth of the language and framework to set all this up is commendable.
  2. The presentation was actually quite good. I came out of there knowing something about Capistrano that I didn't know before I went in there. It inspired me enough to go looking at the Capistrano and Mongrel websites.
  3. The group was roughly 20-25 people. Not bad when you consider very few of us are actually getting paid for writing Ruby.
  4. There were door prizes (a couple books from O'Reilly and no, I didn't win). The people in charge are trying to entice people to come and learn and share.
So I reconsidered. I'll probably continue to attend and hope to see the technology and user group flourish. Only with growth (and perhaps some corporate sponsorship) can we eliminate poor first impressions like the one I had. In the interim, I'll continue to learn, make contacts, and maybe if I learn enough I'll be able to give a presentation one day too.

Thursday, September 14, 2006

Set phasers to stun...

The last couple days have been a bit painful for me as I've endured exposure to the white hot burning effects of crappy UI design. My crap-block was only at an SPF level of 20 and I really should have just got the all-over environmental suit and properly protected myself.

Seriously, I don't understand why so many people undervalue good user interface design. At the very least, people should expect some consistency. Love 'em or hate 'em Apple set some pretty good keyboard conventions with:

Command-S == Save
Command-A == Select All
Command-X == Cut
Command-C == Copy
etc.

Even Microsoft's Windows 95 decided to copy Apple's Command key combinations with the likes of CTRL-S and CTRL-A (they even figured out CTRL-X, CTRL-C, CTRL-V for Cut, Copy, & Paste instead of that abomination that was Shift-Del, Ctrl-Ins, Shift-Ins in Windows 3.1).

Apple's human interface design was also heavily copied. For example, potentially destructive user actions were met with a nice little dialog box asking the user to confirm their action.

So imagine my surprise and frustration today when I pressed Ctrl-S to save my work and this ridiculous application promptly threw away my data and selected (as in SQL select) the data from the database again! What I don't understand is that a committee of people reviewed a number of these vertical market candidate applications and chose this one as the best. Good lord I can only imagine what the others looked like!

Thursday, September 07, 2006

JRuby on Rails


It was only a week ago I was waxing philosophically about Enterprise Software and mentioned that Ruby was in the early stages of running on the JVM and .NET CLR and just today Sun announced that they're hiring the JRuby developers to continue their work full time at Sun. Wow! That's big news. Maybe mainstream Ruby on Rails development won't be far behind... Ahh the winds of change.

P.S. I tried JRuby a few weeks ago after Rails went to 1.1.6. The Gem system actually worked to fetch rails and I was able to create a skeleton rails app and start webbrick. It didn't work much more than that (which was still very impressive) and it was definitely slow but that proof of concept gives my high hopes for this project.

Tuesday, September 05, 2006

User Interface Development

Given the same amount of time, who is more productive... a small team of multi-talented developers? or a large team of specialists? Since I think the answer lies with the multi-talented crew, I took stock of my own skills and decided it was time again to strengthen my ability to create web user interfaces.

So here was my plan: design a web page or two in a graphics tool of some sort and then translate it to an xhtml/css implementation that I can then make dynamic at some later date with something like rails.

I started by perusing the css zen garden for inspiration. Then while keeping the goal of simplicity and efficiency in the back of my mind, I opened OmniGraffle and threw together some nice curves, a healthy amount of translucency, a decent colour palette and quickly had a design.

I then moved onto creating the browser implementation. It was simple enough to create the bare-bones xhtml to represent he text of my fictitious website. But then I ran into my biggest skill deficit, a weak understanding of css. I've read books and coded a lot of this stuff in the past, I just didn't have the big picture. I couldn't make the html tags do what I wanted. I even got so desperate that I almost resorted to the the evil "table" tag. Fortunately I stumbled across Mike Hall's BrainJar website.

He has some great descriptions (with diagrams!) of css positioning, the box model, selectors, etc. After absorbing some of that good information I was soon off and running again.

But no sooner had I started coding than I found myself in the nasty world of css standard unconformity. You see I wanted to take advantage of some of the css3 enhancements I was reading about and unfortunately they weren't working.

In the past I've always relied on Firefox to be the standards compliant browser, but I discovered that the nightly build of Safari/webkit has support for just the properties I needed (i.e., border-radius and multiple background-image properties). For the Firefox fans you probably know that it also supports -moz-border-radius, but Safari's anti-aliased rendering without artifacts is definitely superior.

So a couple "float:right;" properties here, a "-webkit-border-radius:15px;" there and I pretty much got what I wanted. I did discover however that content and style are not as cleanly separated as a I thought they would be. I still ended up nesting a couple div tags and placing content in a certain order so that the float property would do what I wanted but regardless I'm pretty happy with the end result. Next will be dealing with the various browser differences. And I bet Windows IE will be the big pain... PNG support sucks, CSS support is spotty, I'll let you know...

Thursday, August 31, 2006

What is Enterprise Software?

What is "enterprise software"? And the follow up question what is an "enterprise software developer"?

The reason I ask is that I've been thinking about the Java vs Rails question again and the reaction I get from my fellow Java developers when I talk about Ruby and Rails. Generally, they turn their noses up. Ruby doesn't have the breadth they say, it's immature, it's slow, it doesn't scale, it's not an "enterprise" solution. So what exactly are they talking about?

"Breadth": Java has it and Ruby doesn't. There I said it. And quite frankly I agree with it. If I need some oddball service in my app, I can probably find an open source Java framework to help me out. I may not be so lucky in Ruby. But on the other hand do I care? Not really. If I'm building a web app (which describes nearly every single Java project I've worked on) then I don't really give a hoot about most of the stuff that's in Java. As a matter of fact Ruby's ability to create domain specific languages (DSLs) is the power that Rails exploits in its framework, allowing me to express the complexities of my projects very succinctly. It's not about writing gobs of code it's about efficiently expressing a maintainable solution to a problem in as few lines of code as possible. And this is where Ruby and Rails succeeds.

"Ruby/Rails is immature/slow": While it's true that Ruby's been around a long time it certainly hasn't had the commercial success that Java enjoyed and therefore it hasn't received the research dollars to improve it's language runtime. However Rails is getting a lot of attention and by extension so is Ruby. Ruby is in the early stages of running within the .NET CLR and Java Virtual Machine and by the sounds of things Ruby 2.0 has some virtual machine tricks of its own. So at that point at least the discussion of performance can be evenly leveled at all the virtual machines of the world.

Immaturity has also been expressed to me in terms of a lack of an IDE. While I lament the inability to easily refactor my Ruby code as easily as I refactor my Java code with the assistance of something like Eclipse, I console myself with the knowledge that refactoring tools in the Java world are relatively new too. It wasn't that many years ago that I was doing this the hard way in Java. Personally I think this particular complaint is pretty weak. I think developers who are clutching on to this one are doing themselves a real disservice. If nothing else they are depriving themselves of a fresh perspective to object relational mapping and web development because they don't have all the fancy tools.

"Scalability": Well that's a tough one to tackle because of the differences in strategy between Java and Rails. Java likes distributed shared caching (think EJB). Rails likes a Shared Nothing Architecture (SNA). So which is better? Well both have their successes. But to me, the SNA architecture is simpler to understand, simpler to implement and well-proven by the Googles of the world. Fewer moving parts certainly attracts me. There's less to go wrong.

"Enterprisy": Well I dunno how to address that one at all. Because first of all, I don't know what the term "Enterprise" means. I've developed a lot of applications for a lot of users who believe their apps are critical to the success of their business. So does that mean I've developed "enterprise" applications and as a result am an "enterprise developer". Maybe? So am I qualified to say whether or not Rails is ready for the enterprise? Maybe... maybe not. But in any case I can say that I think the IT shops I work for could definitely benefit from Ruby and Rails. I've seen a lot of crazy Java solutions. They tend to be overly-complicated and inconsistently designed and constructed. There is way to much configuration, way too much thinking about "what-if" and not enough thinking about keeping it DRY. Rails comes with a lot of opinions about how things ought to be done and if you can just accept them and go with the flow, you can be very productive.

But it's funny, the "enterprises" that could benefit the most from this technology are probably the people who will be the last to adopt it. Enterprises are big and difficult to steer. Once they get some momentum in one direction, it's hard to get them off that path. Take for example my latest attempt to move from Java 1.4 to Java 1.5. You wouldn't believe the number of departments and the amount of bureaucracy I have to cut through to try and get this approved. All I want to do is use the latest version of Java that was released two years ago so I can take advantage of it's language features so I can write cleaner, more maintainable code. What are the chances that this particular enterprise will ever use Rails? And they claim they're an agile development shop too. LOL.

Thursday, August 24, 2006

Watch that SQL!

Long before I used object relational mapping tools like Hibernate or Toplink in Java or ActiveRecord in Ruby on Rails I used to write a fair amount of SQL (some real nasty queries too!). And in a lot of the shops where I worked it was standard practice to create an explain plan just to make sure that the database could execute the SQL efficiently. If it couldn't, I would dutifully restructure the query, add indexes, or go ask for some DBA help.

But nowadays in this wonderful land of ORMs people just let the framework crank out the queries and never ever look at them. To me, that's just plain wrong. If you're using Hibernate turn on the logging. If you're using Rails just go take a look at the development.log file and go watch what's going on! You may be surprised.

I started a new job a few weeks ago and just wanted to see what Hibernate was doing. And lo and behold, a JSP page was causing 69 queries to run in order to generate a simple list of rows from a table. The main problem was that every lazily instantiated relationship for each object in the collection was being traversed after the initial fetch.

So what could have been done? Well in this case, Hibernate has several options:

  1. Hibernate's query language is quite expressive and something like select e from Employee e left outer join fetch e.department d would have caused both objects to be fetched in a single query.
  2. The fetch keyword I used in the first example has one limitation (for good reason too). It can only be used to fetch one collection. So take advantage of Hibernate's caching to prefetch related objects instead. Hibernate will associate any newly instantiated objects with objects that already exist in cache. Even if you're not using something like EHCache you still have some caching built into your session so don't discount this tip right away.
  3. Use a DTO-like object and go old-school and only select the fields you need with something like: select new EmployeeListDTO( e.firstName, e.lastName, d.name) from Employee e left outer join e.department d
Now if you're using ActiveRecord you don't have the double edged sword of a cache so the second option I described above isn't available, but the other two are possibilities:

  1. Employee.find :all :include => :department
  2. Employee.find_by_sql "select e.first_name, e.last_name, d.name from employees e left outer join departments d on e.department_id = d.id"
The second option shows one distinct design difference between Hibernate and ActiveRecord. Hibernate gives you a SQL-like query language but does away with having to specify join constraints because that information is in the mapping metadata. Whereas ActiveRecord says why reinvent SQL and just let's you have at it. Oddly enough I like both approaches...

Finally, be sure to use the ad-hoc query tools at your disposal to try out your queries before you embed them in your app. If you're using Hibernate 2.x then go get a copy of Hibernate Console (part of the Hibernate Tools). It can be a bit of a pain to get it setup but I really appreciate being able to work out the query before running it as part of my app. If you're using Hibernate 3.x and Eclipse then go get the Hibernate Tools plugin. If you're using Ruby on Rails then you already have all the tools you need. Simply drop to the command line, cd to your project directory and then type script/console. Open up a second shell window (if you're running unix) and type tail -f log/development.log from your project directory and you can instantly watch what SQL Rails generates when you execute those find methods.

Now go out there and watch what you're doing for database access! Don't let all that ORM goodness make you lazy.

Tuesday, August 15, 2006

Should Rails come with a Warning Sticker?

I've been a Java Developer for about 9 years, and maybe my interest is finally waning or maybe the lack of productivity is starting to get to me but maybe, just maybe, something else is has come along that has shown me a better way... I suspect that something is Ruby on Rails.

Now I'm not saying Rails is perfect or that Rails is an appropriate solution for every problem but as I said to someone else last week, it amazes me how many of the things that I've written these past 9 years would be appropriate for Rails.

One of the things that tends to annoy me is that every Java development shop is maddeningly different. They all have a different combination of open source and commercial frameworks. I've dealt with Struts, Hibernate, Spring, JSF, Tomcat, OC4J, Spring, JBoss, Weblogic, TopLink, EJB, JSP, JSTL, DOM4J, JAXB, Swing, Tiles, Facelets, etc, etc. Now while some will say (and yes I'm sure I've used this argument in the past) that the Java community is vibrant and constantly pushing the state of the art, sometimes I wish there wasn't so much choice. Some consistency would be quite nice.

Secondly, why does each shop have to have its own collection of "clever" Java developers who feel they need to endow the poor developers that follow them with some fascinatingly weird framework of their own? Why can't these guys just build a straightforward solution with the frameworks they've chosen? They all seem to feel this overwhelming urge to hide what they're doing behind layers and layers of abstraction, abstraction that usually involves one implementation. For crying out loud if you're going to abstract away Hibernate's API behind your own, you better have a darn good reason and it better not be "just in case".

Rails is a breath of fresh air. David Heinemeir Hannson has said he's very "opinionated" and that may tend to put some people off, but the strength of his character has allowed a single vision to shine through. Rails isn't littered with a pile of abstraction because it's not needed. It's simple, it's straightforward and it's productive. As a Java developer someone should have told me that Rails was so revolutionary. Now when I write Java web applications I'm constantly thinking about how much better it could be with Rails. Is the grass just greener on the other side? Maybe, but either way Rails should have come with a warning sticker. It's addictive.

Tuesday, August 08, 2006

Rails and Apple together in Leopard

David Heinemeier Hannson notes in his blog that Ruby on Rails will ship with the next major release of the Mac OS, Leopard (a.k.a., Mac OS 10.5). As a Mac user and Rails admirer I have to say that these two seem to go so well together... Not sure how to explain that... It's just that they both have a great aesthetic, and are two of the most elegant software products I've used in years.

Saturday, July 29, 2006

Cool Reception

A friend of mine, who works at a Java shop, recently gave a Ruby on Rails presentation and was surprised and dissapointed by the people who didn't come to the presentation. In his blog he discussed some of his theories about why one person in particular didn't show up...

I have a simpler theory, one that was presented by Bruce Tate in the Ruby on Rails Podcast back in March of this year. He said:
You can either look at a programming language as a means or as an end. And if you're looking at a programming language as a means it's just a tool to get a job done and religion just falls out of it. But once a language is entrenched and that language becomes a meal-ticket then the language becomes the end. And when that happens you're gonna get passions stirred up whether you want to or not, because now when you threaten a language you're threatening somebody's ability to feed their family...

I wouldn't present it quite so dramatically as being unable to feed one's family, afterall Java isn't about to be replaced any time soon, but I think his position is probably correct. Java is a meal-ticket for a lot of people. Many have worked their way up to nice lofty "architect" or "senior lead" positions. Most of them through hard work. They know Java and the frameworks and tools that go with it (JSF, Hibernate, Struts, Spring, Eclipse, IntelliJ, Tomcat, JBoss, JUnit, etc). They've made a significant investment and may quite naturally feel threatened by something like Rails whether they realize it or not. It challenges their position and knowledge.

Andy Hunt, one of the authors of "The Pragmatic Programmer" said:
Languages and frameworks come and go, but your habits--your practices--stay with you for your whole career.

Unfortunately, most people don't understand that. They look only at what's directly in front of them and don't check the horizon to see what's coming. Today Java can be a morass of complexity and it's only by looking at things like Rails do we challenge our preconceptions and make our day-to-day Java development positions better.

Keep giving the presentations, continue to push the boundaries. People don't like to be pushed but constant gentle persuasion will eventually leave its mark.

Thursday, July 20, 2006

SOA and APP

During a recent job interview they told me that one of their new technical directions is Service Oriented Architecture (SOA). So I'm thinking okay, Web Services probably figures into that somehow... But unfortunatley (or maybe fortunately) the last time I touched any of that stuff (UDDI, WSDL, SOAP) was at least a couple years ago. So I started Googling to get up to speed again...

All the regular Web Services stuff is still out there but I found a couple other articles/blog entries/presentations by Joe Gregorio that are much more profound:
In the meantime I also watched a presentation by David Heinemeir Hansson called "Discovering a world of resources" (slides, video) where he describes something obviously influenced by the Atom Publishing Protocol (APP).

My interpretation of all this is that we tend to naively use just the GET and POST methods of the HTTP protocol and tend to be fairly inconsistent and sloppy in how we choose our URIs. These articles suggest that we can more wisely and efficiently use all of HTTP's methods to provide basic CRUD functionality:

CREATE - POST
READ - GET
UPDATE - PUT
DELETE - DELETE

Rather than reinventing the wheel with SOAP and all the WS-* standards we can just keep it simple with HTTP. Sounds pretty smart to me.

Monday, July 10, 2006

MacCallisto

Even with a few weeks off from work I still like to keep up-to-date with what's going on in the Java world. And the biggest news so far has been the release of Eclipse 3.2 and the various other Eclipse based projects. So I downloaded 3.2 and then went on to install these other projects:
  • Visual Editor (VE)
  • Java EE and Web Tools (WTP)
  • Test and Performance Tools (TPTP)
  • Reporting Tools(BIRT)
  • Data Tools (DTP)
I was happy to see that VE is now supported on Mac OS X. I was able to quickly create a very simple Swing app in just a couple minutes. I can't say too much about stability of the tool at the moment but it worked first time!

Then I moved onto the Data Tools. It was pretty easy to connect to PostgreSQL (my preferred local database) even though PostgreSQL wasn't one of the predefined driver types. I browsed my schema and then quickly learned that you need to create a SQL editor and then connect it to a database before you can issue ad-hoc queries. In the end it's nice to see these tools in Eclipse but the implementation is still pretty weak compared to something like Aqua Data Studio whose code completion features are more comprehensive.

Then because I haven't really messed around with Web Services before I figured I'd take the Eclipse web tools for a spin. Now I know why David Heinemeier Hansson calls the Web Services collection of standards, which usually sports the abbreviation WS-*, as WS-death-star! Yikes! But in the end I was able to use the wizards to create a bottom-up web service from a simple JavaBean method that returned a String and then deploy that web service in Tomcat 5.5 and then use the generated web service client, also deployed in Tomcat, to execute the method and return my String. It sure is a lot of plumbing to do something so simple but maybe for large heterogeneous enterprise IT shops the benefits for integration outweigh the overhead...

So I still have the reporting tools and the test and monitoring tools to look at but so far everything looks good in the latest Eclipse offering. But I must admit I was suffering some nasty Eclipse crashes at first with the rather nebulous "Out of Memory" exception. After a bit of monkeying around I discovered that the following changes/additions to my eclipse.ini file (within the Eclipse bundle on Mac OS X) made everything happy again:

-Xms256M
-Xmx768M
-XX:PermSize=128M

The last one in particular made the biggest difference. Let me know if you discover anything interesting...

Friday, June 16, 2006

Just Say No to Specialization

One of the topics of our standup meeting this morning was the communication problems with the database group. At the eleventh hour they wanted to change the names of tables, columns and constraints. While I suppose there's nothing too much wrong with caring about consistent naming conventions, I question a lot of the specialization that happens in larger IT shops nowadays.

I read this quote on Apple's Pro site:

Where these big shops have tiers and tiers of people focused on something specific and get bogged down by their infrastructures, we can win a huge campaign with just two artists and a Mac.

...and I can't help but see the parallels with IT development. The last few shops I've worked in (with one exception) have had Business Analysts, System Analysts, Technical Architects, Senior Java Developers, Junior Java Developers, Product Managers, Software Project Managers, HTML developers, Art directors, DBAs, QA managers, QA testers, Release Engineers, etc. etc.

As a result, even the simplest project ends up involving at least 10 to 15 people. If you then consider the communication overhead this introduces, there's not much wonder that productivity suffers. The funny thing is that all these shops actually think that they're agile.

Anyway, back to the database group's requests for change. WTF!? I've long since come to the view that the database model and the object model are just two perspectives on the same thing. But in a lot of circumstances I see the DB design and the object model design begin to drastically diverge as the product evolves. And naming conventions tend to be the worst offenders.

Usually a glossary of terms is developed (even informally) as the dev team and the business people talk about the business problem, and usually the object model's class, attribute and method names are changed to better reflect the real world problem space. But for one reason or another, the database is left to decay. And then when the all-knowing database group comes along to make the problem worse and suggests/enforces naming conventions, I just give my head a shake...

For me it's all this skill specialization that is destroying the holistic view of the software systems that we build. Smaller teams of people with a broader set of skills and responsibilities are what we need to get the job done.

Wednesday, June 07, 2006

That is just so awful...

I was watching a video about Django, a Python powered web framework, when the presenter, Jacob Kaplan-Moss, made the following comment (at around 29:22):
I've actually seen a system, I shit you not, that has every single URL on the site calls a stored procedure in an Oracle database that generates html in the stored procedure and returns it to the web for display. I'm not joking! That is just so awful I can't even start to begin...
That comment took me back a few years where I encountered just such a mess. I was brought into the organization to introduce Java and J2EE but the developers that lived there already had this Oracle solution in place. For reasons that I still don't understand to this day, they couldn't see that this was one incredibly awful idea. In any case, the next time you find yourself looking at some ugly bit of Java or Ruby or whatever, just remember it could be a lot worse!

Sunday, May 28, 2006

Billion Dollar Boondoggle

The "Canadian Firearms Program" more widely known as the "Canadian Gun Registry" was a program instituted by the former Liberal government of Canada under Prime Minister Jean Chretian to license and register certain types of firearms across Canada. Bill C-68 was introduced in February 1995 and has been controversial ever since for a number of reasons but undoubtedly the issue that has caught everyone's attention has been the cost of the program, now over $1,000,000,000, and growing.

So leaving the politics behind, I was interested in the technical details behind this program from a software developer's perspective. What exactly did these guys do wrong that would result in such astronomical cost overruns? What technologies did they use and what could be learned from their mistakes?

Well it was surprisingly difficult to find information but finally I came upon a two-year-old article in eWeek titled "Canada Firearms: Armed Robbery". The system was originally comprised of an Oracle 7 database and a PowerBuilder application built by EDS. Given what I know about those technologies, I doubt that the problem was the technology. Instead, it appears that the biggest problem was incorrect initial assumptions and ballooning, ever-changing requirements.

But after eight years of mismanagement what was the solution? That's right! They decided to rebuild the application with a different set of technology and consulting resources (CGI)! Maybe the implementation really was poor, but I suspect some incompetent management types were deftly pointing fingers elsewhere and some unwitting bureaucrat believed them. Ahhh that old story...

Tuesday, May 23, 2006

DAOs and ORMs

The discussion that this article on the ServerSide generated reminds me of an article I wrote a little while ago. The original poster gets a bit confused about the problem because he assume the use of an ORM means that you need to use the "Open Session In View" pattern. But if you get by that and read some of the comments, you discover that many people (like me) don't believe that the DAO pattern is necessary when using an ORM solution.

A valid concern about ditching DAOs is the coupling that may happen between your domain objects and your persistence mechanism. But if you like ActiveRecord or Rich Domain Models or Annotations or XDoclet then you've already made the choice of productivity over ultimate framework plugability and should just get over it.

But if the coupling is still nagging you and you're concerned about sprinkling framework API calls throughout your code then maybe you want to consider looking at EJB3. Instead of using the vendor's API (e.g., Hibernate, Toplink, etc.) you can reference standard annotations and classes that are free of implementation specifics. At least that way you've provided some hope of switching out implementations.

In the end, question why you're using the DAO pattern and then ask yourself if you've already done something in your code that has violated that pattern. Think about your use of OpenSessionInView filters or the navigation of lazily instantiated collections in your view layer. Maybe DAO and ORM really don't mix...

Saturday, May 13, 2006

XML Glue


When I discovered XDoclet I quickly stopped editing my hibernate mapping documents by hand. From the XDoclet website:

XDoclet lets you apply Continuous Integration in component-oriented development. Developers should concentrate their editing work on only one Java source file per component.

This approach has several benefits:

  1. You don't have to worry about out dating deployment meta-data whenever you touch the code. The deployment meta-data is continuously integrated.
  2. Working with only one file per component gives you a better overview of what you're doing. If your component consists of several files, it's easy to lose track. If you have ever written an Enterprise Java Bean, you know what we mean. A single EJB can typically consists of 7 or more files. With XDoclet you only maintain one of them, and the rest is generated.
  3. You dramatically reduce development time, and can concentrate on business logic, while XDoclet generates 85% of the code for you.
But unfortunately I still find myself editing a ridiculous amount of Spring XML by hand. Spring sounds nice in theory but after using it for awhile I don't think there's anything wrong with the factory and singleton patterns. This unholy quest for ultimate flexbility by gluing components together with XML has to stop. Most of the time you simply don't need it.

Friday, April 21, 2006

MS Mac Lab

A friend of mine just sent me a link to a tour of Microsoft's Mac lab. Thanks Aaron... Thought I'd file it here under the category of "Holy Macs!".

Monday, April 17, 2006

Embracing Change

When I consider the "agile software development methodology", a key principle that comes to mind is "embrace change". The theory is that users don't really know what they want. They'll only be able to steer you to the goal once they see something working. So get ready for change. They'll change their minds a bunch of times as the software evolves. In the end they'll appreciate your flexibility to adapt the software to their changing vision and you'll be a happy developer because you've created something that will actually be used and appreciated by the end users.

But what happens when it's your team leader who keeps changing the technologies under your feet? Is it just another kind of change to be embraced? Let's see...

The elaboration phase of the unified process can be defined as: "This phase attempts to create an executable architecture that realizes architecturally significant use cases." In other words, we should select the appropriate technologies that will be needed to create a solution for the most difficult known use-cases and then actually prove that our chosen technologies will do the job by creating executable software. Then during the construction phase, we should be ready to tackle the problems (known and yet to be discovered) with the technologies in hand.

A second core principle of the "agile software development methodology" is "You aren't going to need it", which means you shouldn't overengineer something because you think you might need it in the future. Keep it simple. The idea is that you save time by not doing it now and you make your code better and more maintainable because it's simpler. If someone ever says to you "if we build it in now, it'll save us time later" and you already have too much other work to do right now, then tell them to forget it.

I'm currently in an environment where every "senior" resource is on a mission to turn the management spotlight on themselves and the way they try to achieve that goal is to way overengineer the solution with as many Java frameworks as possible. By doing so they can prove their technical merit with a complex solution. To give you an idea of what I mean consider this:

We have a framework for dependency injection, we have one for database persistence, we have one for role based security, and one for binding XML, we have one, no wait two (or maybe three) for doing UI. We're in the process of adding yet another Java web container (without retiring the previous two) and have added every conceivable open source code measurement and style checking software. We have two continuous integration servers and in addition to the JUnit testing framework, we're adding Ruby/Watir testing too...

Individually and maybe with some intelligent selection I don't have anything against most of these frameworks (except for Spring) but after six weeks of development with 9 programmers with only a login screen to show for it, I say enough is enough. Java web development may not be as productive as it is with Ruby on Rails, but it's not this tough!! Come on! Look at the requirements and choose proven frameworks that address problems you've identified and don't cost more to implement, learn and maintain than it would cost to create a custom solution. For example, if you have to spend more than a couple weeks implementing a role based security framework when nobody has actually said you need to worry about different roles, then you're probably doing something very wrong. Keep it elegant, efficient and simple.

Wednesday, April 05, 2006

Apple Listens to Customers

Well don't ever let it be said that Apple doesn't listen to its customers.  They released a new beta piece of software called "Boot Camp" that will allow people to dual boot Windows XP and Mac OS X on Intel based Macs.  I can't imagine that many self-respecting Mac owners would prefer to use Windows over Mac OS X, but there are undoubtedly occasions when it would be beneficial to do so.

Now Apple isn't being completely selfless here of course.  They make a lot of money selling hardware and if they can convince Windows users to buy a Mac instead of a Dell they'll be more than happy to accomodate them.  Maybe this is like a Trojan horse to get people to experience a good OS.

Next thing I'd like to see is the ability to run Windows in some kind of virtualization environment within Mac OS X...

Thursday, March 30, 2006

Fast and Furious

I'm sure I have goofy speech patterns and favourite catch phrases of my own but I also have a talent for picking these colloquialisms out of someone else's speech as well. I have discovered over the years that the best time to capture these beauties within an IT environment is during the inevitable "status meeting". It's almost like a freestyle rap battle where two or more contenders try to outdo each other for status meeting supremacy. Fortunately for me, the agile process inspired daily standup meetings on my new project have become a veritable gold mine for these things. We have a few people on the project who are black-belt kung-fu masters of the colloquialism spinning these out with speed and grace... Here's a sample of the ones I've captured so far:

up to speedhigh level design
make it realsnapshot
visionary thinganecdotal evidence
identify the needlay the groundwork
cycles availabledisparate user experience
bottom feederlook and feel
production capacitynebulous
contextnumerous permutations
driversshock effect
more or lessimpact
grease the skidsfresh set of eyes
steer going forwardengage you
take forwardexternalize
put the spin on itsocializing it
draft rollout planshow stopper
iterative processmitigate risk
right hand manextra pair of hands
duck is cookedmessaging protocol
key artifactsvalidation effect
verbagesooner rather than later
put lipstick on ittechnical components
bring to the tableconsider the options
test bedfull meal deal
iterative cyclelock it down in stone
instant gratification

Wednesday, March 29, 2006

Misplaced Priorities

I've worked on quite a few software projects in my career and I always wonder at the people who get hung up on their favorite features regardless of importance to the actual users of the system.

A few years back I worked with a developer who became analyst. At some point in one of his past projects he had created a feature for allowing a user to press some key combinations to "hot jump" from screen to screen. Although he never really elaborated I suspect this feature was more than just the typical shortcut keys you see in most desktop applications. But that's not the point. He became convinced this was THE feature to add to our app. Over the next few weeks he became fixated on "hot jumps". We kept hearing about "hot jumps" over and over. This was going to be the "most used feature" in the system.

But the other developers and I didn't agree with him... We felt "hot jumps" had absolutely no value unless the destinations of these hot jumps actually worked! And that was the problem and the point of this blog entry. We had tight deadlines, and a lot of actual business functionality to develop long before features like "hot jumps" should ever have entered anyone's mind. I'm not saying "hot jumps" would have been completely worthless, but at the time, it was undoubtedly a misplaced priority.

So it's with some surprise (and frustration) that I find myself in a similar situation today, only it's not "hot jumps", it's directory structures, eclipse project files, and (lord help me) Ant scripts. Under normal circumstances I would definitely say these things all have some importance, but what about actually developing the application? We're three weeks into development with five developers but under the direction of our "leader", I find myself spending my entire day renaming things and begging the "gods of Ant" to actually let me get this damn build.xml file right so it will do what I want. And gentle reader this is not just your regular run of the mill ant script. This is the mother of all ant scripts, utilizing every possible ant task available. And let me clarify, I did not write it. I inherited it and have been instructed to "make it work".

But my point again is this, what good is this "hot jump", oops, I mean Ant script if it doesn't have anything to build? At the end of the day, will the users be impressed with the quintessential Ant script or would they actually like to have the features they asked for?

Saturday, March 18, 2006

DHH Interview

I just found a SYS-CON.TV interview with David Heinemeier Hansson that had some real quotable moments:

In his description of Ruby On Rails:
...we like to consider ourselves the Apple of open source web application development...

...it's extremely conventional. Most of the ideas in Ruby on Rails are the same ideas people have been building web applications on for the last ten years. They just hurt a lot less...
On Convention over configuration:
...In Java we call it XML sittups. You can produce just as much XML configuration as application code and that's just insane in our mind...
Does it scale?
...unquestionably yes. simply because Ruby doesn't invent a new architecture. We use exactly the same architecture as people who have been building the biggest sites on the internet.... shared nothing...
On the value of Rails.
[People think] it's so valuable to have extreme performance when there are tones of other attributes that are more valuable: programmer productivity, how maintainable your application is over time, ...

Sunday, March 12, 2006

Ruby jEdit Plugin

I've been a big fan of jEdit for quite a few years now and I just downloaded a new plugin that I just simply felt compelled to write about, the jEdit Ruby Plugin. It's not the simplest thing to install but the integrated code completion and documentation features (including Ruby on Rails) are quite good. For example, when I'm editing a model object I can type in "has", hit ctrl-space and get a popup with the options "has_one", "has_and_belongs_to_many", and "has_many" options, and if I'm displaying the Ruby Docs window (currently docked to the right side of my jEdit window), it will display the documentation for each option as I select each one. Very nice. Perhaps some competition for RadRails?

Saturday, March 11, 2006

Agile or Traditional?

I was recently speaking with a friend I haven't seen in months and she mentioned that she was reading a book I had lent to her. The book is called "Balancing Agility and Discipline" by B. Boehm and R. Turner. The book's main theme is the attempt to balance agile software development methods with traditional methods. The idea is to try and assess your project by looking at several different characteristics and then choose the processes from each method that will allow you to best manage it.

So that idea got me thinking about my most recent project, a Java rewrite of an existing application, and how desperately we were trying to use a pure agile methodology when it didn't really fit.

Here's a quote from a presentation available on the "American Institute of Aeronautics and Astronautics" website:

Problems characterized by change, speed, and turbulence are best solved by agility.
  • Accelerated time schedule combined with significant risk and uncertainty that generate constant change during the project.
Is your project more like drilling for oil or like managing a production line?
  • Oil exploration projects need Agile processes.
  • Production-line projects are often well-served by rigorous methodologies.
Our project was undoubtedly a production-line application with very low risk:
  • Although I didn't really like the technology we used on this project, it was being used to some degree of success on two other projects. So while it was undoubtedly not very productive, it was usable.
  • The database design and user interface design were to be lifted untouched from the existing application.
  • We were mandated with reproducing an existing production application so the requirements were well known if not well documented.
  • Business users were not co-located and not easily reached for consultation (during the entire project I never spoke to a single person who would actually use it).
So what drove us to try and use an agile methodology? Well.... it's trendy. Agile is "in" and waterfall is "out". IT people would like to live in a world of absolutes, where we can say with certainty that A is better than B. But the reality is that we live in a world of spectrums where things are classified in terms of a position on a scale between two extreme or opposite points. Just like we shouldn't try to develop a simple project using every conceivable J2EE technology and framework available, maybe we shouldn't try to apply every agile process available where it just doesn't fit. Sometimes it's okay to create a plan and to write down requirements. Sometimes it's the best thing to do.

Tuesday, March 07, 2006

Suffering

One of the Pragmatic Programmer tips is:
"select" Isn't Broken.
Which means that's it is rare to find a bug in the OS or the compiler, or even a third-party product or library. The bug is most likely in the application, i.e., my code.

The problem with the project that I'm working on is that there is so many layers of code and abstraction that I don't even work with the framework anymore but some class ten times removed.

For example I have a JSP calling a JSF configured backing bean, calling a Spring configured service, calling another Spring configured EJB in a different process, calling another Spring configured service calling another Spring configured DAO which is (eventually) a subclass of Spring's HibernateDaoSupport class which attempts to hide Hibernate's API altogether.

So while I try to take the tip seriously and not blame the framework, there is so much stuff happening before it even gets to Hibernate (and let's not forget all that XML goo that glues everything together) that I can't help but lay some blame at the feet of these frameworks that encourage so much obfuscation.

To get real geeky I'll quote C3PO from the original Star Wars movie:
We seem to be made to suffer. It's our lot in life.

Monday, March 06, 2006

Bruce Eckel on Ruby and Rails

I just listened to the latest podcast by the Java Posse; an interview with Bruce Eckel.  Since it's the "Java" Posse there's a fair amount of discussion about Java, but the second part of the interview dives into Bruce's thoughts on Python, Ruby and Rails.  Although he gets some things wrong, like attributing the creation of Ruby to David Heinemeir Hannson (DHH) instead of Yukihiro Matsumoto (Matz), he largely says a lot of good things about Ruby and Rails and admits where he lacks sufficient knowledge to comment.

The one part in particular I agreed with was his assesment of the Rails supporters as being "loud", as in "loud-mouthed".  He says it's a lot like the early Java days.  As a matter of fact, my first taste of Rails was a presentation by DHH.  His rhetoric in that speech was a bit much to bear, but if you can see your way past the hyperbole, and just see that the guy is truly passionate about creating "beautiful" code, you get a good idea of why Rails is the way it is.

Monday, February 27, 2006

Rails is Boring and Ruby is a Toy

Chad Fowler did a presentation last month that I happen to be listening to at the moment. He's talking about his "evolution" from a Java developer to a Ruby developer. He talks about the various XML files you have to edit when doing J2EE, the number of lines of code that's needed to do just the simplest things in Java, etc.

What I find so surprising is that some of my recent comments seem to be echoing his statements. Unlike him however I was already on the path to trying to simplify my Java development and Rails has simply dropped in a great big exclamation point. Web application development doesn't need to be the morass we suffer through in Java. Ruby can make it fun and Rails can make it so easy to do. Geez now I'm starting to sound like an evangelist too! Oh well I use a Mac too... maybe it's in my DNA...

Sunday, February 26, 2006

Hibernate vs ActiveRecord

Over the last 2+ years I've grown quite accustomed to the facilities of Hibernate (one of the most popular Java object-relational persistence frameworks). And before that I used TopLink for a couple of years. So now when it comes to my work with Ruby on Rails I have some pretty high expectations.

The out-of-box experience with Rails' persistence framework is undoubtedly different but similar enough to Hibernate to make life fairly comfortable. But recently I started watching the SQL that gets generated from Rails and decided I'd like to optimize them a bit. But unfortunately that isn't as easy as everything else in Rails. I found this article at TheServerSide that sums things up pretty well. I think Rails comes out on the losing end. Now the question becomes, are the things you lose worth the things you gain?

Monday, February 20, 2006

What I don't have to know

I was thinking recently about how someone with no knowledge of Java or Rails web development would choose which of the two technology stacks to learn. Then I started comparing the lists of technologies on both sides.
  1. For the View you have JSP (Java Server Pages) vs ERb (Embedded Ruby). (We'll assume that (X)HTML, CSS, & Javascript are a given knowledge requirement regardless of framework choice.)
  2. For the Controller you have JSF (Java Server Faces) vs ActionPack
  3. For the Model you have Hibernate vs ActiveRecord. (Since both of these technologies are Object Relational Frameworks we'll assume that relational database knowledge, including SQL is a given requirement regardless of framework.)
So on the surface things look pretty similar. But let's dig a bit deeper.

First let's start at the View: In Rails we take standard HTML and embed Ruby to dynamically generate the content. In JSF-flavoured JSPs on the other hand we substitute HTML tags with custom JSF tags. You must also know JSF EL (Java Server Faces Expression Language) because it is used heavily in the JSF tags.

Secondly, the Controller: In Rails, controllers are written in Ruby. In JSF the controllers are thankfully written in Java but in order to make them work you have to configure the dependency injection framework with XML. Your JSF XML file must conform to a particular DTD. Now if you also believe in the value of dependency injection frameworks you may want to use Spring. Spring isn't mandatory, but it's popular enough to be part of a typical Java stack of technologies. Unfortunately it requires it's own XML DTD.

Finally let's move onto the Model: In Rails we use Ruby to define our model. The naming convention is usually sufficient to allow ActiveRecord to determine what classes map to which tables. We typically use snippets of SQL to tell ActiveRecord how to fetch data from the database. In Java, Hibernate is the common persistence framework choice. In Hibernate another XML DTD tells the framework how to map the classes to the tables. But since people grew tired of maintaining so much XML they turned to XDoclet. And since that became so popular there are now Java 5 annotations that allow you to annotate your domain model wth mapping metadata. Currently you can use any of the three choices. Hibernate also uses its own query language, HQL, to instantiate objects from the database. This query language is based on SQL and has quite a few benefits but is yet another syntactically different language to learn.

So let's add it all up. To do Rails web development you need to learn:
  1. Ruby
  2. the various Rails APIs (e.g., ActiveRecord & ActionPack).
To do Java web development you need to learn:
  1. Java
  2. JSF tag libraries
  3. JSF EL
  4. JSF's XML DTD
  5. Spring's XML DTD
  6. Hibernate's HQL
  7. Hibernate's mapping DTD or XDoclet or Hibernate Java 5 annotations (and the DTD for configuring the framework)
  8. The DTD for web.xml.
  9. The APIs for Spring and Hibernate and JSF
  10. (And I didn't even mention EJBs)
People may look at this list and say "wait a sec, you're being unfair, XML is XML and you're counting four different types of XML in the Java stack". Well all I can say is that when I have to edit one of these things I have to take my eyes off the code that I'm currently working with and make a contextual switch to something that looks very different. That switch is enough for me to penalize the Java list with a bullet point for each one. But even if you collapse the four XML items into one, my point still stands: there seems to be an awful lot more things you have to be comfortable with when developing Java web applications. Perhaps that's why I'm beginning to favor Ruby on Rails so much more. It's the Simplicity.

Thursday, February 16, 2006

Manifesto

Everyone has a manifesto nowadays. I just read an interesting entry at the "Creating Passionate Users" blog that pointed to the the 37signals manifesto. Both recommended reading.

Sunday, February 05, 2006

Patterns

Christopher Alexander says:
Each pattern describes a problem which occurs over and over again in our environment, and then describes the core of the solution to that problem, in such a way that you can use this solution ...
So why is it so commonplace to use patterns where a problem doesn't exist?

Example 1. The Data Access Object was originally created to hide various data access APIs (LDAP, RDBMS, ODBMS, XML, EJB, etc.) behind an interface. But in reality most applications use a single data access API, and it's usually a relational database. So if you already use something like Hibernate as your data access framework, is it really necessary to wrap the data access in yet another class? Hibernate already abstracts you from the specifics of the target database (e.g., SQL Server, Oracle, PostgreSQL, etc.) Your queries are usually created in HQL and are written in the terms of your object model not the data model, so why add another layer that just delegates to Hibernate? Think about it, how many of your DAO methods look like "return session.getNamedQuery("someName").list();".

Example 2. The Data Transfer Object was originally conceived when Entity EJBs were in vogue. Because you wanted to use course grained data access and eliminate network traffic you'd package up your data and pass it over the wire in a DTO. But in a world where you're using something like Hibernate in the same VM why incur the overhead of DTOs and the marshalling they require. Hibernate can give you a domain object that you can disconnect from the Hibernate session and work with independently. Secondly DTOs are horribly brittle. If you change a domain object chances are pretty good you'll have to change a DTO.

I'm not saying the two patterns I used above are necessarily bad, it's just that they don't need to be used in every single case. People should look to patterns when they discover a problem with the way things are being coded. Remember the old agile mantra "Do the simplest thing that could possibly work". Don't try to build the most complex solution with every conceivable pattern. Instead think of building the simplest most elegant solution with the fewest lines of code. The people who have to maintain your code will thank you. Well okay, they might not thank you, but maybe they won't be cursing you every hour either ;-)

Friday, January 27, 2006

RadRails 0.5.3

In the rails community it would appear that the majority of developers use Macs and the text editor TextMate. (What is it about Rails that seems to attract so many Mac people? I'm not arguing, I'm a Mac guy too, but it's an interesting question to ponder) But coming from a Java background I've grown fairly accustomed to Eclipse and so the RadRails and RDT Eclipse plugin projects caught my attention. But they each have their own strengths that made me wish I could take the best of both worlds. Well version 0.5.3 of RadRails shows the benefits of those two teams collaborating. RadRails is now using RDT for editing Ruby. It also means you get all the other nice features of RDT like a visual Test::Unit runner, the RI view, etc. I'm also pretty excited to hear where the developers of RadRails want to take RadRails. In short:
The focus of RadRails is going to move towards achieving dynamic content assist.
Rails development gets better all the time and the future looks bright.

Tuesday, January 17, 2006

Snakes and Rubies

Over on the Django website you can find a video of presentations made in Chicago on December 3rd, 2005 by two leaders in web application development. Adrian Holovaty, one of the Django creators, and David Heinemeier Hansson, the creator of Ruby on Rails, present their respective frameworks and then take some questions from the audience. Naturally I was curious about the Ruby on Rails presentation. David quotes Richad Feynman:
You can recognize truth by its beauty and simplicity. When you get it right, it is obvious that it is right.
and then goes on to make the assertion:
Beauty leads to happiness, happiness leads to productivty, thus Beauty leads to productivity.
and that Ruby on Rails is part of his search for beauty. He may be on to something. It's also fun to hear him curse out Windows a few times, "this is ugliness" :-)

Sunday, January 15, 2006

Rewrites

System rewrites must be extraordinarily popular because I've worked on my fair share of them throughout my career. And usually the story is the same...

Poorly-trained developers in an IT department or startup slowly build a system over the course of a few years and then eventually come to the realization that the system needs a rewrite. Here are some of the most common reasons:
  1. The database design is bad (Usually it's atrocious. It's very rare to find good data models)
  2. The code for the business logic or UI is a hopeless tangle of procedural code (You'd be lucky if thy UI and business logic are separate. I've even seen one implementation of a web application where data access, business logic, and even HTML markup was generated by Oracle stored procedures.)
  3. Performance issues have cropped up (Most applications are bound by the performance of the data access code. Good data model design is crucial in this respect, but bad queries (easier to make with object relational tools btw) are the usual culrits and are a good place to start.)
  4. The technology is obsolete. (Unfortunately this is a fact of life in IT and it is common for this old code to be the only "documentation". Keep the developers of the future in mind when writing your code and make it readable.)
  5. It's just so fragile that implementing new functionality takes way too long. (If you see gigantic nested if-then statements, run away now before you run away screaming later.)
  6. The new IT manager doesn't like his/her predecessor's legacy (It's sad but true. The "wiping out all vestiges of that 'bad' manager who was the harbinger of all things evil" is a bit of a spectator sport among developers.)
  7. It's a combination of some of the above. (And if you've really arrived at the precipice and are gaping into the abyss it'll be all of the above.)
Eventually the decision to rewrite is approved and someone must make the decision about how to redevelop the system. People usually see these two paths:
  1. They can redevelop the entire thing, affectionately dubbed the "big-bang approach"
  2. They can incrementally replace the subsystems one at a time.
Usually the incremental approach is the most attractive because it's seen as having less risk. And of course managers who like their jobs like less risk. But this "lower-risk" decision usually comes with one very difficult problem: "How do you integrate the new code with the old and keep them both running at the same time?" Well the typical decision is to just leave the database alone and build the new application on top of it. While this seems to be an easy choice (look at all the stuff you can reuse and no data migration activities to endure), this is one of the worst things you can do.

No matter how good the database may appear at first glance and no matter how much faith you have in your object relational mapping (ORM) tool's ability to "abstract away the ugly parts", you are always going to compromise your object model. It is extraordinarily difficult to design the best domain model you can without repeating the design decisions made in the database. It's like trying to hum a tune while listening to another song on the radio, you inevitably end up singing the song on the radio.

For several years I believed that ORM really gave me an abstraction from the physical database, that the two were independent and it was meta data that glued them together. But after some real experience, I learned the hard way that was a fantasy. If you want to be productive and want to work with an object oriented domain model that you can easily refactor you really need to be able to change the data model just as easily. I now consider the domain model and the relational data model to be two perspectives on the same thing. If you don't believe me, I ask you to consider the following trends:

  • In EJB3, the relational view of the domain model is becoming part of the domain model through Java 5 annotations. The main reason for this is practicality. It embraces the DRY principle (Don't Repeat Yourself): every piece of knowledge should have a single, authoratitive, and unambiguous representation in a system. It's an acknowledgment that the attribute oriented programming model advocated by XDoclet so many years ago is a good one. I suggest that you should even generate your database from this metadata, keep it DRY.
  • In Ruby on Rails, much of the domain model is generated at runtime by querying the database meta data. The database can't express everything in a object model so the rest of the picture exists in the Ruby domain classes. This practical approach that intrinsically marries relational and object views is one of the many features of Ruby on Rails that make its supporters claim such high productivity benefits.
You may also want to consider what data warehousing people have been doing for years. They always treat the transactional databases as sources of data but they always stage that data somewhere else and "cleanse" it before making it part of their warehouse. So while they're dependent on that data model for ongoing feeds they have a real abstraction from it and none of their cubes or reports are impacted by a change in the data source.

Rewrites appear to be inevitable. Even if the reasons for doing it are dubious you'll probably find yourself in one of these projects sooner or later. But if you going to get involved, make sure it's a complete rewrite. Don't take shortcuts. The most successful rewrite project I worked on created a new domain model and new data model for the new application and used database technologies to keep the new and old data model synchronized. We got the productivity of not being bound by the old (and very scary database) and we kept everything else that was dependent on that old database running by keeping the old database alive. The most aggravating projects have been the ones that tie you down by saying "leave the database alone". Then there are the ones that say "leave the UI alone" too. Ugh! But that can be the subject of another article...