Thursday, September 15, 2005

Is Ruby Better Than…?

As I speak about Ruby with folks around the world, a question comes up with depressing regularity: “is Ruby better than Xyz?”, where Xyz is the questioner’s current language du jour.


The simple answer is “no.”


But then let’s ask the same question differently. Is Xyz better that Ruby?


The simple answer is “no.”


The longer answer is that the question falls into the same category as “have you stopped beating your wife?”—it makes an implicit and (hopefully) incorrect assumption. In this case, it assumes that it’s possible to compare two languages and come up with some kind of binary A trumps B evaluation.


Is your chisel better than my hammer? If I’m forming dovetail joints, yes. If I’m nailing two-by-fours, no.


Is my Ruby better than your Java (or C#, or …)? It depends.


So, over the next few weeks I’ll try to post some answers. I’ll look at areas of Ruby which seem to be hot buttons for folks when making language comparisons.


Let’s start with a big one:


Performance


Ruby is probably slower than Java or C# in most real-world situations. Does that worry me? Not normally.


Think about your average web application. An incoming request appears on an Ethernet interface. The packets make their way up through the IP and TCP stacks, then get queued up as a data buffer. The web server receives the data, decodes some of the content and passes it off to your application server. There the information is massaged into some kind of request object, and your application is invoked. Your code hits the database a couple of times, probably using an OR mapping layer such as Hibernate to sanitize the access. It then constructs response data before calling some kind of templating library to format a response. The response heads back through the application server, and possibly through the web server, before being deconstructed into packets and sent over the network.


Whew! There’s a bunch of processing going on there. Millions and millions of machine instructions being executed. There’s latency while packets are queued, processes are scheduled, threads are dispatched, and disk heads seek to the right track.


How much of this processing is done in code that you write? How much of the total time spend handling the request is spend executing the actual instructions corresponding to your code?


Zip.


I’m guessing maybe 5% on a really bad day, with a complex application. Let’s face it: you average commercial application isn’t burning CPU cycles solving NP-complete problems. We typically write code that moves chunks of data about and adds up a couple of numbers.


In these scenarios, is it worth worrying about the relative performance of the language used to do the moving and adding? Not in my book.


Instead, I’d rather write in a language that let’s me focus on the application, and which lets me express myself clearly and effectively. And, if I can do those two things, I believe that sometimes I’ll be able to write code which is cleverer than something I’d write in a lower-level language. A better algorithm will easily gain back any marginal performance hit I take for using a slower language.


Justin Ghetland experienced this recently on a Rails project. Having coded the same application twice, once in Java and once using Ruby on Rails, he was surprised to discover that the Rails application outperformed the Java one. Why? Justin believes it’s because Rails does smarter caching. The Rails framework contains some very high-level abstractions, and that allows the folks writing the framework to be smart about what they do. They accepted the linear hit of writing in a language that executes more slowly because they got a non-linear increase in speed from being able to write better code.


Clearly there’ll be times where you need to squeeze the most out of your CPU, where your application itself is the bottleneck and it’s CPU bound. In these cases, Ruby might be a bad choice. You probably want to look at a high-performance language such as OCAML. But even then, the choice isn’t always clear. Ruby with a good parallizing matrix library would probably beat Java or C# code which inlines the same operations.


So, is Ruby fast enough for your application?


I don’t know. But I do know that I wouldn’t assume that I can’t use Ruby for performance reasons. There are plenty of sites out there pumping high transaction volumes through a Ruby application. The real answer, as always, is it depends. If you’re concerned about performance as you start to develop a new application, it doesn’t matter if you’re writing Ruby, Java, C#, or assembler. It’s prudent to spend a small amount of time doing some rough tests on your proposed architecture before you start laying down the code.

Thursday, September 8, 2005

Is Rails Ready for Prime Time?

I give talks on Rails and Ruby to Java developers on average once every two weeks. I’ve probably spoken to thousands of folks over the last year. And I don’t think I’ve ever had a talk that didn’t end with someone asking “that’s all very nice, but is Rails ready to be used in my company? Can I stop writing Java and start writing Ruby?”


As with most good questions, there’s no one simple answer. Here’s what I tell people.


First, Ask the Right Question


One of the main selling points for Java in the late 90’s was the idea of having a language, runtime, and library set that could be used everywhere. Use Java to code your cell phone, and use Java to code your largest enterprise application. To some extent that thinking has insinuated itself into the mind sets of many developers—they are looking for one solution, one framework, and one language to solve all their problems.


That’s silly. Some situations need one tool, other situations another tool. Using the full might of a J2EE stack to write a small stand-alone application is using a sledgehammer to crack a nut. But I keep hearing the sound of nuts being pulverized as developers seem to think that using anything other than J2EE is somehow unprofessional.


At the same time, there are situations that call for the shock and awe that is J2EE. Some applications need to make use of facilities rolled into the stack, and it would be crazy to reinvent the wheel.


So when people ask “should I be using Rails instead of Java?”, the answer has to be “not exclusively: you’re likely to want to use Rails as well as Java.” Why? Because I’m a firm believer in having a bag of tools at your disposal, tools that you know how and—most importantly—when to use. When Rails is appropriate, you’re going to be hard pressed to find a more productive environment.


And, even if Rails is the clear winner for a particular application, developers face a second challenge. They have to convince their companies to let them use it.


So the real questions are “when is Rails appropriate?”, and “how can I introduce it where I work?”


Let’s start by looking at some of the hurdles Rails has to clear to make it an appropriate choice where you work.


Next, Make Sure It’s Possible


When shouldn’t you use Rails?



  • If you need to handle transactions across multiple databases. Rails/Ruby doesn’t have two phase commit (yet).




  • If you have really strange database schemas. ActiveRecord beats Hibernate when the schemas are fairly well structured. Hibernate wins when you have to map the schema-from-hell before using it inside your application.




  • If you’re adding small chunks of functionality to an existing, large application. OK, this is contentious. If I was reading this, I’d probably fire up my mail client and complain that this is exactly when you should use Rails. Integrate to the monster using web services, and add new functionality in something more malleable, such as Rails.


    Except… most monstrously large applications I’ve come across got there over time. They’re messy, hard to work with, and tightly coupled. If you wanted to expose parts of them via web services, you’d first have to restructure them to make those parts callable from the outside, and that probably isn’t worth the effort (if it’s possible at all).




  • The developers don’t want to. If the rest of the developers don’t want to use Rails, then forcing them to help you create a pilot project is a simple recipe for embarrassment. Pull, don’t push, when it comes to change.



Then, Make it Realistic


Companies are all different, and there’s no one road to Rails adoption.


In some environments, there may be no resistance to using Rails. I’ve even heard of some places where the managers are working to persuade the development staff to give Rails a try. Typically, it’s the small and medium size businesses that have this kind of flexibility. Companies such as Odeo and VitalSourceembraced Rails as a key component of their business plan.


Other companies, including most large ones, have a more conservative approach when adopting new technologies. So how can a developer who’s convinced that Rails would benefit their company get it into production?


In general, I suggest an incremental approach. Start with small, developer-focused applications. For example, a new table may have been added to the database. Developers need to be able to maintain test data in it, so they can continue to write parts of the larger (Java) application. Whip up a quick Rails application in 20 minutes and leave it running on a Webrick server somewhere. Folks will notice how easy it seemed to be.


Maybe at some point the development group might need a web application for their own use (change request trqcking, for example). Suggest writing it in Rails. Mention that not only will it take less time (and hence cost less in terms of overhead dollars), but it will also allow the group to get some experience with the technology. This is where you get to show off. First deliver a solid solution, then add stuff such as Ajax support to show them how things might be (if only they used Rails in all their applications…).


Then the time might come to roll out an inward-facing corporate application. If the development team are now comfortable with the technology, propose a Rails application. Now you’ll get experience running Rails in a production environment.


Finally, once everyone is comfortable, think about rolling out an externally-facing Rails application.


Easing the Transition


Here are three suggestions for making the transition to Rails applications less extreme:



  • Start using Rails Conventions in Your Java Applications. Maybe you aren’t in a position to make the switch now. Even so, think about using some of the Rails conventions when you do things such as add new tables to your Java applications. Using the Rails naming schemes won’t make any difference to Hibernate, and you’ll be in a stronger position to write Rails applications against that schema. Even though the external application is still J2EE, you can write internal, ancillary applications in Rails. And if the schema is Rails friendly, the effort will be less.




  • Do parallel developments. The jury is still out on the productivity increases that come from using Rails, but I see some very credible people talking about numbers in the 5-15x range. So if Rails really does let you write applications in 10-20% of the time you’d otherwise take, why not do a Rails development in parallel with the real one? If the main project is slated to take 5 months using J2EE, and after a month you have a working Rails version, your company gets to make a decision.



    • They can use the Rails version, having invested 2 months of effort (one month for Rails, one month for the parallel Java team). This is a net saving of 3 months over the original 5 month estimate.




    • They can choose not to use the Rails version. In this case they’ve spent an extra month, and learned something valuable. Is that extra month significant? Probably not—it seems to me that any project that comes in within 20% of its estimate is a raging (and unusual) success, so this extra time just gets swallowed by the general budget slop that surrounds all software development.





  • Make sure you know what you’re doing before leaping into an ambitious project. As the cliché says, you only get one chance to make a first impression. If you want to show that Rails is viable in your company, then you need to make sure that all the folks doing the work on your first visible Rails project know what they’re doing. Think hard about the deployment and maintenance issues before committing. Choose something simple, and implement it well.



What do you think? Is all this realistic? Have you already introduced Rails to your company? How’d it go?Let me know.

Thursday, September 1, 2005

Mining Build Statistics

Mike Clark’s been posting some interesting views of CruiseControl build statistics (here and here). These are cool pictures, and I suspect there’s a bunch of information to be gleaned from them:


  • what’s the blob density (how frequently do folks check in)?

  • are they mostly red or mostly blue (red is broken builds)?

  • after a red blob, how many more red blobs do you see before you get a blue one?

That last statistic is one I think might be interesting. If you were to plot a histogram of the number of sequences of red blobs of length one, length two, length three, and so on, what would it look like? If it is heavily weighted to the low end, then you’re looking at a team that fixes broken windows.


I’m sure that there’s a lot more cool stuff in these pictures, but I’m impressed at how quickly things jump out at you, and just how much tacit information they convey. Maybe project tea-leaf reading will become a sought-after discipline…