Ajax in Austin

  • Posted By Stuart Halloway on June 27, 2007
I will be giving three JavaScript and Ajax talks this Friday, June 29, at the Lone Star Software Symposium in Austin. Stop by if you're in town.

Rails Edge coming up again

  • Posted By Justin Gehtland on June 15, 2007

Stu and I are speaking at what has become one of our favorite events, Rails Edge, this time in Chicago on August 23-25. The lineup is a little different this time, with a bunch of new (and updated) talks and even a workshop on web design presented the day before by Jenifer Hanen.

As speakers, we love this event and its format. Since it is a single track, we get to see what everybody else is up to, and help out through the “choose a random co-speaker” application. We really get to know the attendants (great to see everyone up at RailsConf, by the way). Early bird signup lasts until July 1, so get your seat now!

With great power comes great responsibility

  • Posted By Stuart Halloway on June 13, 2007

The Hpricot library allows the following syntax:

Hpricot(my_document)

This is not idiomatic Ruby, and a novice programmer might not know what it did, or how. UrbanHonking explains how, but James Robertson takes issue over why.

If you are going to bend a language's idiomatic usage, you should have a compelling reason, and I share James' view that this example is not compelling.

But other examples are compelling. In Ruby, I could say this:

class Person < ActiveRecord::Base
  has_many = ["opinions"]
  validates_presence_of("first_name")
end

Yuck. Better:

class Person < ActiveRecord::Base
  has_many :opinions
  validates_presence_of :first_name
end

That's how it would look in Rails today. But I could do even more exotic things:

# no base-class, but has_many triggers mixin
class Person
  has_many :opinions
end

Or

Person = Model :has_many=>:opinions, :validates_presence_of=>:first_name

Or

# creates a Person class!!
person {has_many :opinions; validates_presence_of :first_name}

Or how about:

# creates MyDB::Person, MyDB::Opinion, & other classes automatically
module MyDB
  tables :all
  naming_conventions :capitalized, :singular
end

One of these choices is clearly better than all the others. (Which one?)

The unconventional wisdom here is that your syntax should be chosen for the domain, not by the language. In order for this to work, you must be able to think creatively about the domain you are working in.

The classic counter-argument is "our developers aren't smart/skilled/experienced enough to take advantage of this." Riiight. If your developers aren't skilled enough to think creatively about the domain you are working in, you have way bigger problems.

(Updated to fix typo in example five, thanks Scott!)

Ruby on Rails with Large Teams

  • Posted By Stuart Halloway on June 11, 2007

After my recent series on Ruby vs. Java myths, many people have asked for some real-world evidence about Ruby on Rails with large teams. You are in luck. My friend Muness Alrubaie is giving exactly that talk at erubycon.

Justin and I will be there too, talking about refactoring, keeping tests DRY, Microsoft and the DLR, CAS, and OpenID.

Refactoring in NetBeans

  • Posted By Stuart Halloway on June 06, 2007

If you aren't watching Tor Norbye add Ruby features to NetBeans, you should be. Most recently, refactoring support.

You will need to get some prerelease bits to try it yourself.

Ruby vs. Java Myth #5: It's a zero-sum game

  • Posted By Stuart Halloway on June 06, 2007

Previous Myths:

  1. Project Size
  2. Ruby feature X makes code unmaintainable
  3. Ruby is too hard
  4. It is easy to copy Rails' good ideas

Ruby is a great language, Java is a great platform. With Ruby running on a Java Virtual Machine, you get the best of both worlds.

As a language, Ruby is superior to Java for most general purpose programming tasks, as implied here, here, and here. (Some people disagree, mostly for reasons I have already covered under myths one, two, and three.)

As a platform, Java wins hands down. Until recently, Ruby's platform was simply the interpreter (MRI). Want to know how it works? Read the source code. Java provides a much better platform, including

  • a byte code instruction set
  • a portable class file format
  • powerful threading support
  • a thorough security model
  • lots of proven deployment options

Plus Java has more implementations than you can shake a stick at, running everywhere you want to be.

So can't we all just get along? I want to live in a world where language preference does not define a programmer. We'll write code in Ruby, or Scheme, or Scala, or Erlang. And we can all live in harmony on a JVM anywhere.

Want to help create this world? Here are some steps you can take:

  • Contribute to the JRuby project.
  • Write some parts of your next Java application in JRuby. Your dependency injection framework should make this trivial to integrate. If it doesn't, get a new one. You can even get a static typing methadone shot by making your JRuby code conform to a Java interface.
  • Manage your Java application with rake instead of ant (and contribute some code to help others do the same). I have yet to meet a single developer who prefers ant to rake. As I often say, WWJDDD?
  • Unit test some Java code in JRuby Test::Unit.

Happy coding!

How to build a development team

  • Posted By Stuart Halloway on June 05, 2007

Good teams: The platform provides power, agile process provides restraint, and paperwork is optional.

Weak teams: The platform provides restraint, process provides paperwork, and success is optional.

Ruby vs. Java Myth #4: It is easy to copy Rails' good ideas

  • Posted By Stuart Halloway on June 05, 2007

Previous Myths:

  1. Project Size
  2. Ruby feature X makes code unmaintainable
  3. Ruby is too hard

Rails enthusiasts and detractors seem to agree on one thing: Rails embodies a lot of good ideas about web development, and other frameworks are changing to be more Rails-like. If my Java web framework of choice is already adopting Rails' good ideas, why should I bother looking at Rails itself?

This myth is a tricky one, because it is partially true. Many of Rails' good ideas can be copied into any language. But some of Rails' good ideas require a language as open as Ruby--so much so that the good ideas in Ruby become bad ideas in other languages. If you copy Rails' good ideas into Java, you will get somewhat less that half of the total value. And if you do not understand Ruby, you will not even know what you are missing. Let's consider some examples.

Some of Rails' good ideas can easily be copied into almost any framework. Take convention over configuration. There is nothing language-specific about this idea, and it is great to see other frameworks moving in this direction.

Other good ideas depend on specific Ruby features. Rails uses open classes to make better, more readable object models. For example, you can say x.blank? instead of StringUtilities.isBlank(x). Individually, such differences do not matter much, but hundreds of them add up to a significant improvement in readability.

A more important use of open classes is creating simple, domain-specific languages (DSLs), such as ActiveRecord's declarative relationships and validations:

class Poet < ActiveRecord::Base
  has_many :poems
  validates_presence_of :name
end

DSLs often use open classes twice: first to create new declarative "statements" that are legal at class definition time, and second to add new methods depending on the options chosen. You could simulate some of this with Java annotations, but it would take more work. How much more work? Look at the source code for Rails validations side-by-side with Hibernate or Spring validations.

A few of Rails' most controversial ideas are good only in the context of Ruby, and would be bad ideas in Java. For example, many Java web applications have a clean, layered separation of business logic and persistence. This is good idea in Java, in case the application has to change. Rails applications seem to compromise this separation, choosing instead to emphasize simplicity and ease of development. This is a good idea in Ruby, because it is easy enough to add this separation when and only if you need it. (I will say more about this in a subsequent post.)

Finally, we come to the best idea in Rails: Flexible, open languages enable rapid innovation and exploration. What languages will we use to think the big software ideas of 2008?

Ruby vs. Java Myth #3: Ruby is too hard

  • Posted By Stuart Halloway on June 04, 2007

Previous Myths:

  1. Project Size
  2. Ruby feature X makes code unmaintainable

Welcome to Myth #3: "Ruby is too hard." Honest, I am not making this up. People do seriously argue that Ruby is too hard for the average developer. This is problematic in many ways.

1. Programming itself is hard. It is not for dummies, and you cannot learn to do it in 21 days. Programming languages may have a gentle learning curve, but hard problems will require hard thinking in any language.

2. In what serious discipline is "It's too hard" a legitimate excuse? I have never seen a bank that eschews multiplication: "We use repeated addition here--multiplication was too hard for our junior staffers." And I would be uncomfortable if my surgeon said "I refuse to perform procedures developed in the last 10 years--it is just too hard for me to learn new techniques."

3. Java and Ruby are both hard. I have heard the same argument made about which features to use within Java: "We don't use reflection, it is too hard to understand."

4. "We use idiot-proof tools and save money by hiring the cheapest idiots" is simply not true because there are no idiot-proof tools. Even as wishful thinking this idea sucks. It won't impress customers, and the effect on morale is easy to imagine.

5. You cannot wish away difficulty by limiting language features. If a language omits a feature that developers need, they will find a way to simulate it. This can happen on a small scale: Start without blocks, and you end up with anonymous inner classes. Or on a medium scale: Start without implementation mixins, and you end up with design patterns as code smells. Or even on a grand scale: Start with no trivial way to compose dynamic systems, and you will end up with an enormous framework that requires a second language for tedious, error-prone configuration.

This last point leads to the circular framework argument:

  1. We cannot use language Hund. We need simple language Blub that everyone can understand.
  2. Ruh-roh. Blub is not powerful enough. We must build an elaborate framework for enterprise work.
  3. Blub doesn't have an elaborate framework! How can we possibly use it for enterprise development?!

More than half of the code in every Java enterprise framework exists purely to work around well-known, deliberately chosen limitations at the language level. Smart Java developers have paid a staggering price to prop up the illusion that the Java language is easy.

Perhaps this is all water under the bridge. The price has been paid, and Java works. Expert Java developers can do incredible things. Those of us in the Java community should be proud of the great code we have written, in spite of the incredible difficulty of Java development.

But we shouldn't, in the next breath, say "Ruby is too hard." I for one would have trouble holding a straight face.

Ruby vs. Java Myth #2: Ruby feature X makes code unmaintainable

  • Posted By Stuart Halloway on June 03, 2007

Welcome to the second installment. You can catch the first myth here.

Ruby includes a variety of features that lead to compact, expressive code, e.g. open classes, dynamic evaluation, soft encapsulation rules, easy metaprogramming, and closures. These features demo well, but developers who have not used them fear that they will lead to unmaintainable code.

In reality, Ruby's powerful features make code more maintainable, when used correctly. (Learning to use these features correctly will be the subject of another myth.)

What makes code maintainable? You should be able to easily

  • Understand the overall design of an application or module
  • Find code you are looking for
  • Read the code
  • Make changes to the code
  • Verify that the changes work

Given these criteria, how do Java and Ruby stack up? I believe that the responsibility for maintainable code lies 80% with the programmer, and only 20% language and tools. With that caveat in mind, let's look at each point in turn.

Understand overall design. Advantage: Neither. In my experience, no language is very helpful here. Good abstractions help. Java and Ruby share many abstractions in common: implementation inheritance, classes, polymorphism, encapsulation, etc. The Java world has much better support for navigating these abstractions, via IDEs such as IntelliJ IDEA. On the other hand, Ruby has some useful constructs that Java lacks. Mixins help keep code more organized. Ruby makes it easy to create DSLs that accurately reflect and document your design.

Find the code you are looking for. Advantage: Java. Java's IDE support wins hands down. (It is worth remembering that many of us adopted Java when this IDE support was nonexistent.)

Read the code. Advantage: Ruby. Now we are down to the level of individual classes and methods. At this level, Ruby code is easier to keep DRY, and therefore easier to read. If you do not believe that Ruby is easier to keep DRY, then read about the Blub paradox.

Change the code. Advantage: Ruby. When you change code, you often move past the uses anticipated by the original author. At this point the compiler gets in your way, because some of the original author's assumptions need to be bent or broken. Change is much easier in a dynamic language.

Verify that the changes work. Advantage: Neither. If you are serious about quality, then you need to test. Manual testing is infeasible, so you need automated testing: unit tests, acceptance tests, continuous integration, the works. Both Java and Ruby provide good support for these.

Neither Ruby nor Java can make your code maintainable. I propose that we replace the old myth (feature X makes code unmaintainable) with no myth at all. If your primary argument for choosing a language is a presumption that language X will cause people to write maintainable code, then you have either a bad presumption, or the wrong people. You would be better off to pick a language at random, and change either the presumption or the people.

Ruby vs. Java Myth #1: Project Size

  • Posted By Stuart Halloway on June 02, 2007

This week, I abruptly switched gears from working on a green-field Ruby project to pitching in on a well-established Java project. Revisiting Java provided a good chance for me to set down in words how we at Relevance think about platform choice. This week I will be posting a series of five myths that often misinform platform choices for new projects.

Myth #1: Ruby is suitable for small projects, and Java is better for large, complex projects.

This is exactly backwards. In fact, Java is more suitable for small, well-defined projects, while Ruby is better for large, complex, open-ended projects. There are several reasons Java wins for small projects:

  • On small projects, finding the right open-source library often means you have nothing to do. Java has more libraries than anyone. Advantage: Java.
  • The budget for a small project can be blown by a few gotchas that require unexpected development effort. Java is much better known and documented than Ruby. Advantage: Java.
  • On small projects, teams don't have time or budget to acquire new skills. Most teams already know Java. Advantage: Java.

On a large project, all the factors above get reversed:

  • There is a lot of new work to be done, so language productivity matters more than having libraries to choose from. Advantage: Ruby.
  • Large projects are sure to have many gotchas, so you need maximum flexibility in responding to change. Advantage: Ruby.
  • On a large project, retraining pays for itself. Companies grossly underestimate this. A five-week(!) training course on a technology that makes a developer 10% more productive would pay for itself in about a year. Advantage: Ruby.

If the myth is so backwards, why does anybody believe it? Ruby is, at present, exceptionally good at one specific kind of small project: database-backed web applications. Ruby on Rails counteracts all of Ruby's small-project disadvantages:

  • Rails is the library you need.
  • Rails eliminates the gotchas (for small projects!)
  • Rails has a great out-of-box experience, so web developers need little retraining (for small projects!)

For web applications, Advantage: Rails.

People see the success of Rails and draw exactly the wrong conclusions. There are lots of visible, successful, small Ruby on Rails projects. There are lots of visible, successful, large Java projects. Look at these facts without broader context, and you get Myth #1.

Object Models: Not What, But Who

  • Posted By Stuart Halloway on June 01, 2007

The important thing about an object model is not "what is in it," but "who can change it." Charles Nutter provides a nice demonstration of this with his field-initializing new method. Open classes empower library writers, and make it easier to keep code DRY.

When languages are tightly controlled at the expense of library developers, you end up with the bad side of design patterns.