Sunday, September 19, 2010

Thoughts from Code Retreat - St. Louis

Yesterday was the St. Louis Code Retreat and I wanted to capture my experiences and observations. I hadn't heard of Game of Life before reading about Corey Haines' code retreats last year. My field of study in college was life sciences so I missed out on things like Conway's game of life that mathematicians and CS majors are probably exposed to. In prep for the event, I gave Game of Life a try for myself. It was a great experience! I felt totally sucked into the elegance and simplicity of the problem. But enough about that.

On organizing it

IMG_0007 DSC_0008

We were fortunate to have great sponsors. Microsoft provided the venue, a large space with ample capacity for the 40 people who were signed-up for the event. Oasis Digital funded the breakfast (fantastic pastries, fruit, and coffees) and Object Computing, Inc. (my employer) paid for the sumptuous buffet lunch from Mayuri.

The event was announced back in July and within a week of the free tickets becoming available, all were taken by eager developers from various technical backgrounds. However, of the 40 who signed up to attend, only 26 made it to the event. I had read accounts of previously held code retreats that warned to expect people signing up for the event but canceling at the last minute; given how hard it is to coordinate with a large group of people, this is not surprising. But to have only 65% attendance was, honestly, a disappointment. Given the size of the turn out, though, I was very happy with the range of technical interests among the folks that were there to learn, experiment, and enjoy programming.

Languages, Tools & Format

At the beginning of the day, I said a few words about how the day would be organized. We were to have 3 40-minute pair-programming sessions before lunch, with developers implementing the Game of Life problem in their preferred language or technology, and doing it test-first. Then switching pairs at the end of each session, deleting the last sessions effort and starting over.

DSC_0004

The point of the event was practice. Through exploring new languages and experimenting with different approaches to a common problem, all those who made it that day would get a chance to improve on some skill they already had or work with someone who could teach them something they were interested in learning. Attendees took on the game of life problem using a number of different languages and tools.

  • Eclipse
  • Emacs
  • IntelliJ IDEA
  • TextMate
  • Visual Studio
  • C#
  • Clojure
  • F#
  • Java
  • JavaScript
  • Objective-C
  • Ruby
  • SQL

A common reaction to the 40 minute time limit was that it was far too short to get a working implementation of Game of Life. The time constraint led to some sessions that scrapped testing altogether in the interests of getting a working implementation as quickly as possible. For others, it meant only being able to implement a partial, test-backed solution. Personally, I appreciated peering into the lightning-like minds of some of St. Louis' most talented software professionals. I liked what I saw in the clojure implementations that I watched and paired on and found myself inspired to take clojure on as my next language of study.

Organizing this event was a learning experience for me. Several people asked whether there would be another one next year. I really hope so ;-) It wasn't a crazy level of effort to organize (nothing on the scale of a major conference). I am curious whether I'd set the date for the event too far in the future and whether that was why there were so many people that cancelled their tickets. Next year, if the stars align like they did this year for venue and food sponsors, St. Louis will see another Code Retreat.

Interesting implementations

I have found a number of Game of Life implementations on the web that I think are pretty cool. Here are just a few.

Sunday, July 18, 2010

module_function (where have you been all my life?)

I recently discovered a feature of Ruby that surprised me. Really, I was surprised that I hadn't heard of it before (for as long as I have been a fan of the language).

module_function can be used to make one or more Module methods accessible as type-scoped methods (in the same way that declaring them as self methods would). For example:

In this form, the methods of the module must be declared before the line containing module_function. You can pass one or more method names (as symbols) in the call. In fact, you can even re-write this as follows:

This form makes all methods declared after module_function behave as type-scoped functions (callable in the form of: Foo.bar or Foo::bar). You can "turn-off" the behavior of what is given type-scoped calling access by declaring a visibility modifier after the last method you want to expose in this way.

Now the Foo functions can be called either as type-scoped functions or Foo can be included in a class or added to an object.

One thing you now can't do, though, is refer to the module_function scoped methods as instance methods of classes or objects into which the Foo module is included. IOW, trying to call: Something.new.foo in the above sample code blows up with a warning about trying to access a 'private' scoped variable.

Saturday, May 15, 2010

Regex riff (for words not containing a string)

I had the need to figure out how to parse a string and pull out any words that didn't contain "Foo" in them. After a lot of cursing, I came up with something that works. For the string "Which BarFoo Is It Foo Bar":

Yields: "Which", "Is", "It", "Bar"

Regular expressions are diabolical.

Sunday, December 27, 2009

My dot-Autotest

Among the things that make me ga-ga for Ruby testing libraries is the ZenTest gem, which includes a super handy utility called 'autotest'. Autotest is meant to be run from the top of your project directory and it will search through your /test directory and run all test files it finds there (and report passes/failures on the console). My own development preference is writing specifications for my software using RSpec, which includes a tiny utility script called 'autospec' that enables 'autotest' to run anything it finds under the /spec directory of your project environment. As well, setting an environment variable called AUTOFEATURE=true tells autotest to search through your /features directory and run all your Cucumber features after file-system changes (this capability is added by Cucumber and not actually part of the ZenTest gem).

I have been running autospec nonstop as I tinker with a Sinatra app I have been writing. The normal behavior for autospec is that it runs all specs & features and then stops, watching the filesystem for any file changes that trigger it to run specs again. Recently, though, I noticed that the specs would start running and then go into an infinite loop of running and running and running... At first I thought that I'd updated a gem in the vendor directory of my Sinatra app that broke autospec somehow. After doing a lot of tinkering, I tracked it down to a Webrat log file that gets updated each time my Cucumber specs make it all the way through the login feature of my web app.

Autotest includes a configuration capability that lets you specify which file updates it should ignore (i.e. which files can be updated without triggering an execution of all the specs for your project). These exceptions can be declared in a .autotest file that needs to reside in the home directory of your development environment. I think I have covered all the bases for things that I want to keep from triggering my autospec runs. Here is what my file looks like:

The 'autotest/growl' require is so that I can see growl popups when my specs pass or fail. The gem for this is 'autotest-growl'.

UPDATE - 12/28/09: The 'autotest' script supports a '-v' flag which will cause it to report what file it saw changed to trigger your last test run. I only learned about this flag thanks to a comment on this original post by the great Ryan Davis.

Sunday, November 08, 2009

Calculator Kata revisited

Just as a follow-on, I went back to the Calculator Kata and applied a functional Ruby approach with the rule of no mutable state allowed. I was inspired by Tom Stuart's Thinking Functionally in Ruby talk.

This time I create a reusable Proc for scanning the expression according to the regex that extracts [left_operand, operator, right_operand] arrays. I evaluate the expression with reduce, using the evaluation of the first equation in the expression as the initial value, and then applying that as the left hand side of all other equations in the expression. The drop(1) call removes the first element of the parsed expression so that the reduce call can operate on the second and all subsequent equations in the expression. Since the initial value passed to reduce is the evaluation of the first equation, the memo passed to all evaluations in the reduce block is the last evaluated result.

The above code passes the same spec as I included in the previous post

Monday, October 26, 2009

Strange Passions Confusion

A funny thing happened to me on Friday. I was scheduled to present at one of the Strange Passions events for the first Strange Loop conference. Earlier in the morning, I practiced a code kata I was planning on showing when it was my turn to present. The kata was an exercise I use when I do tech interviews of prospective candidates for developer positions at the consulting firm where I work. It calls for building a calculator that can parse a string expression and return the result of the expression as a string. This is an exercise that I have used for years, one that I have done many times in Java as well as in Ruby. The problem is ideal for observing test-first habits in programmers because it is a very easy problem for which to write tests.

When the time came for me to present, I gave a few minutes of introduction to the exercise and dove in. The first test took less than a minute to write, and I switched over to writing just enough to pass the first test. And then I froze. My mind went completely blank. This is an exercise that can be solved many different ways, and at that moment, in front of a decent crowd, I couldn't think of a single one. It was a totally unnerving experience. So I sat there for a minute or two, struggling to remember how I had solved this before. The audience grew impatient. I can only imagine that it was like watching a train wreck. Then, after what felt like an eternity, something unclogged in my brain and I started up again.

The next day, I thought a lot about it. I remembered that something similar happened to me on the night of my wedding. My wife and I took Tango lessons for 4 months prior to our wedding because we wanted our first dance to be a Tango. We had a routine that the dance instructor helped us work out and we practiced and practiced. On the night of the reception, the music started and I began the routine. Then, mid-way through, everything went blank. It was a two-part routine, and the lights went out in my head at the end of the first part. I panicked and led my wife through the first part of the moves we had practiced.

These lapses in memory to execute something that is almost second nature while in front of a crowd is generally thought of as stage fright. It may very well be that I have sporadic bouts of this phobia, and what happened Friday at Strange Loop was just another occurrence. I teach classes and had presented the day before at the conference, so it is not unusual for me to be presenting something in front of an audience. It was, however, disappointing to leave the crowd twiddling their thumbs while the wheels in my head spun for traction and I am unsure what to do to prevent this same episode from happening again.

I have written several variations of the calculator kata, that I present here to anyone interested in picking this up as an exercise for their own practice. The exercise is as follows: create a simple calculator that accepts a String arithmetic expression and returns the result of the expression, also as a String.

The Spec


Solution 1

This is the ugliest of the bunch. Split the expression at each space character, then add the parts of the expression into an array until there are 3 elements in the array, at which time I figure out which operator should be applied to the left and right sides of the expression, and then calculate and store the result as the left side of the expression to be evaluated next. On line 7, I am also adding a convenience method to the array to reduce some code duplication. This solution is readable but wordy.

Solution 2

This next approach greatly simplifies the strategy for calculating a binary expression. I still split on spaces and add each part of the expression string to an array, but instead of figuring out the operator for the expression, I take advantage of the operators existing as methods on the Fixnum class. This solution turns the left and right operands into integers, passing the right operand and the operator to the 'send' method of the left operand integer, and storing the result of the evaluation back in the parts array.

Solution 3

This one is a variation on Solution 2. Instead of splitting on spaces, I use a regular expression and capture groups to extract out the operands and operators for each part of the expression contained in the string. This solution still takes advantage of arithmetic operations existing as methods on the Fixnum class, so the difference from Solution 2 is primarily in the way that the parts of the expression are extracted.

Solution 4 -- Updated - 10/27/09

This final solution is defers to the Ruby interpreter to solve components of the equation. This approach can't simply rely on the Ruby interpreter to evaluate the entire expression because the arithmetic operators have different precedence order in Ruby. I use capture groups and positive lookahead (?=(\d+)) to get the three parts of the binary expression, thereby ensuring left-to-right expression evaluation (which is how I wanted the Calculator to work).

Special thanks to Michael Easter for pointing out the flaw in the original version of solution 4, which actually did just hand the expression over to the interpreter. I hadn't included a test that combined all four operators, which exposes the order precedence issue in Ruby. That has been remedied in the spec above.

Saturday, August 22, 2009

Handy RubyMine feature - Open Current File in Browser

I just discovered a little feature in RubyMine that I think is very cool and useful. Editing a view file causes a little overlay to appear in the corner of the editor pane showing icons for Firefox, Safari, and Opera. Clicking any of these will open the currently edited file in the browser of your choosing (assuming you are working in development mode and have a server running).
Neat!

Sunday, July 26, 2009

My Code Review Criteria

As a Scrum Master, I do code reviews. Recently, someone on my team asked whether what I look for in a code review was documented anywhere. This post is my starting point for documenting what I look for. I am hopeful that someone reading this may point out things that I haven't thought of that would be good to add to the list.

Backed by automated test
This should be self explanatory. No conditional logic or otherwise observable behavior should be added to the system without an automated test that confirms the predicable flow of the code.

Reinvents the Wheel
Does the code recreate some function that exists in a library included in the code base (or perhaps something from a utility library)? The chances of this are higher if you are reviewing code written by a developer new to the team. Does the code recreate a micro-framework or design pattern for which supporting types already exist and can be reused?

Doppelganger
Does the code contain logic duplication from elsewhere in the source file or from other files in the code base? Are there refactoring opportunities to extract code under review into a block reusable within the source file?

Maintains Harmony
Does the code under review look like it was written by the same hands as the rest of the code in the source file? In my mind, all source should read as if it was written by a single diligent developer, no matter the size of the team responsible for the system. That said, a projects' code style is an issue for teams to agree on internally and be ever vigilant for its application.

Says what it is / Says what it does
Are variables, constants, methods, and types descriptively named? Are any names inappropriately abbreviated or otherwise confusing?

Tell, don't ask
Classes and other types should accept their dependencies (through injection) rather than calling out for them (either via instantiation or other means). Accepting dependencies simplifies the ability to test code as well as change implementations of the types supplied at runtime. Does the code provide some means for external dependencies to be handed to the object? Are those external dependencies specified as interfaces or other non-concrete type declarations?

Too many notes
Are there any obvious opportunities for refactoring to simplify or reduce the size of the code under review? Does each method fit entirely within the view screen? The Single Responsibility Principle says that each type in a system should have one and only one reason to change. Are any methods, functions, or types written with multiple responsibilities?

Does it work?
Finally and most importantly, does running the system or related tests demonstrate that the code under review functions as expected?

Wednesday, February 18, 2009

Git tab completion from Cygwin

I have been a fan of Git since starting to use it regularly and am going to give a talk on it at a tech lunch for my company in April. For the last two weeks, I have been using Git as an SVN front-end (my company has a backed-up SVN repo that I am using for SCM) while developing for a Windows target platform application. So far the experience with Git from cygwin has been a bit mixed. Another developer I am working with ran into problems with Git from cygwin (as opposed to msysgit) that I was unable to reproduce. His problem prevented him from being able to do simple commits on staged files. Bummer.

The little tidbit I wanted to document here is related to getting tab-completion of git commands working from the Cygwin bash shell. There are plenty of posts that already document how to do this, but cygwin kept complaining about having extra tokens in the shell scripts I was sourcing from my .bash_profile. After a little bit of forensic googling, I saw a post explaining that Windows line feed characters inserted by the text editor I was using on my shell scripts was causing my problem and that I should run the scripts through the d2u utility. Problem solved!

So for Windows folks running git from cygwin, here's how you get the awesomeness of tab-completion for git:

  1. Download the source for the version of git you have installed from http://www.kernel.org/pub/software/scm/git/
  2. Copy the git-completion.bash file from the contrib/ directory and paste it into your home dir -- (I renamed my file .git-completion.bash).
  3. Run that file through dlu: $:> d2u .git-completion.bash
  4. Source the file from your .bash_profile (in your cygwin home directory):
    if [ -e "${HOME}/.git-completion.bash" ] ; then
    source "${HOME}"/.git-completion.bash
    fi
  5. Restart your cygwin shell and you should be have git tab completion working. I can't say enough about how helpful tab completion is for git (or how smart the shell script is - truly is teh awesome)

Saturday, January 10, 2009

Learning Ruby

I began learning the Ruby programming language by using a problem I had already solved one way and rewriting the solution in Ruby. Taking a domain that I had great experience in and fitting Ruby into it made the process of exploring the syntax and rules of the language a comfortable one. To use a sports metaphor, it gave me home field advantage.

I blogged about it. In fact, the blog entry was another Ruby learning opportunity for me. The pretty syntax highlighting for the Ruby source code I included in my blog was colored by a Ruby library (gem) called syntax. I found it helpful to create a Ruby script to take the source code I had written and generate syntax-highlighted HTML (yet another learning experience).

At some point early on, I got a great reference book and dove into it as needed. Other books followed, as well as adding *many* blogs to my blogroll. As I learned, my appreciation of the language grew and I spent time working on things that would help me write Ruby.

Over time, I wrote more Ruby code as well as more about Ruby and sought opportunities to learn Ruby by teaching it. I have also been fortunate to have a patient and knowledgeable mentor to ask questions to and learn from.

The learning stage changes eventually in to the doing stage. Much like a fusion chef, I discovered ways of mixing expertise I had in other areas with Ruby. An ingenious Ruby & Swing library (or is it a framework... you decide) called Monkeybars reignited my passion for rich-client user interfaces. I dug-in and started contributing to the project and later recorded a screencast demonstrating how to use it.

Fool that I am for the fun I have writing Ruby, I wrote a Rails website to host the screencast (as well as another I recorded for yet another Ruby/Swing library). All this is to say that learning something (like Ruby) can be a rewarding and enjoyable journey. Though I have travelled a fair distance, there are still so many new directions to go. As I write this, I stand at the beginning of a new trail. At my side I have the project I will re-write, a trusty reference book on the delivery truck and a patient mentor (who doesn't blog -- looking at you, Dave Giovannini) to hold my hand when I need it. And what do you know (I think I have seen this picture before...) there is even a fusion restaurant that makes stuff I have a feeling I will like.

<broad-grin/>

Saturday, December 27, 2008

Noche Buena 2008

Christmas Eve has always been the most special day of the year for me. Memories from my childhood include Noche Buena dinner parties full of family and friends dressed very nicely and a house permeated with the smells of a Cuban kitchen. Sometimes ham, sometimes pork, always black beans and rice, yuca, some vegetables, desserts, and lots of booze. A joyous occasion that usually ended with bodies laid out on the floor in front of the tree or by the fire, watching snowflakes fall and telling stories of adventures past.

Since becoming a father, it has been a priority for me to try my best to recreate the memorable experience for my kids that was my own warm memory of Christmas Eve.


Noche Buena 2008 from Mario Aquino on Vimeo.

Epilogue

We had prepared for a dinner party to seat 11 adults and 2 kids. The pig was so late in being ready to eat that the Noche Buena dinner was effectively ruined. All our guests had gone home with little more than hors d'oeuvres and some wine in their bellies. Despite all our efforts, there is no rushing a pig in a Caja China in December in St. Louis. At times I felt like Icarus... at times, like Captain Ahab. The regret was palpable and the expense of the day, substantial.

My opinion of the Caja China is that it is an extremely inefficient apparatus for roasting pigs. As you can see from the video, the heat source is above the meat, which lies in a metal-lined plywood box. This guarantees that the meat will be cooked slowly. However, the documentation for the Caja China says that a pig should take between 3 & 4 hours to cook, but our experience was that it took over 10 hours to cook the pig. Perhaps in Miami, where the temperature usually stays above 65 °F, the cook-time for a pig stays within the 3 - 4 hour window. Sadly, that was not our experience.

Tuesday, December 23, 2008

Habemus Porcus

Battling rotten weather this afternoon, we travelled out to Kenricks Meat Market to pick up our Noche Buena pig. My Dad brought the biggest cooler he had for taking the pig from the market back to my house. Once back home, the Yak Shaving commenced. We had to clean the pig, find a big enough plastic container to marinate it in, wash a bunch of things to mix the brine with the mojo we had prepared earlier, transfer the pig down to the kitchen, move a bunch of things around, keep the dog in the office, etc.

Two hours after getting it back to our house, the pig was finally juiced-up and bagged neatly for overnight marinading. It's out on our enclosed porch and the forecast calls for an overnight low of just above freezing. My Dad was concerned that wild creatures might break-in to our porch in the night and start to munch on our pig once the divine scent of the mojo gets carried into the backyard. I am not concerned.

Monday, December 22, 2008

Caja China Chicken Test

In preparation for the most important dinner of the year (the Noche Buena pig roast), I decided to test the cooking performance of the Caja China that we bought recently. I used self-starting coals to get the grill hot, though didn't use enough coals to cover the top of the box (mistake #1). After the coals were white-hot, I added Kingsford charcoals using roughly the same amount I had started with, and once again waited for them to be hot enough to spread and get more coverage of the top of the box.

By 5:15, I was ready to add the roaster chicken I had purchased for the test. This chicked was still quite cold for having sat in the trunk of my car in 15 °F weather for most of the day. The Caja China instructions advise adding meat that has been warmed to room temperature, but I decided to go for it anyway (mistake #2).

At the end of the first hour of cooking, we flipped the chicken. I could hear that the skin on the bottom of the bird (which had been facing the heat from above) was crispy as we flipped it over. I thought this was a good sign and that the chicken would soon be done and ready to eat. After flipping it, I recovered the tray of coals on top of the box and added a nominal amount of charcoals to the tray (mistake #3). The instructions say to add roughly 1/2 bag (8 lbs.) of charcoal after flipping the bird, but I didn't added that much.

Forty-five minutes later, I peaked into the box to see if I could read the meat thermometer we had added to the bird. The top was not as brown and crispy looking as I had expected it would. I realize now that I should have followed the charcoal amount recommendations to the letter. This will definitely happen when we cook on the afternoon of Noche Buena.

As you can see from the video, the chicken is a good shade of brown near the neck of the bird, but much less so near the bottom. The ambient temperature for the entire cooking episode was roughly 20 °F and the forecast for the day of Noche Buena calls for similar weather. I expect to post more details after we get the pig and start the prep. This is the first time I have ever roasted a whole pig and am really excited about it!

Saturday, December 20, 2008

Caja China - Pig Box

My Dad and I have split the cost of a Caja China so we can do a tradition Cuban extravaganza for Noche Buena (Christmas Eve), the most special night of the year for Cubans. Here is what the box looks like setup in my garage.

We have the pig on order from a butcher in Arnold, MO., for pickup on 12/23. If you are looking for a friendly place to eat surrounded by happy people eating the most delicious pork north of Miami, please come by
:-)

Thursday, December 11, 2008

Sublimewire...

Since August, I have been working with the highly-talented development team that supports LimeWire, a P2P file-sharing application that leverages the Gnutella network for passing bits around to other clients. While LimeWire has been around since 2000, it has been our efforts in this latest release (which just became publicly available yesterday, albeit as an alpha build) that has finally given it a clean, stylish, modern look. I have been working in Swing application development for more years than I'd like to admit and I have to say that 6 months ago I wouldn't have believed what we have created was possible with the venerable toolkit. 

The team I have been working with is made up of a mix of designers and developers who each brought focus to different aspects of the application. The designers have sweated over the look of the UI, obsessing on clean lines, separating areas of visual focus, colors and whitespace. It has been an iterative effort, following their design mock-ups for implementing the UI of new features, kicking the implementation back to them to evaluate and then revisiting the layout with new ideas for improvement. It has reminded me of the often heard quote about Michelangelo recognizing that great works of art were already present in blocks of marble and that all he needed to do was brush away the right bits from the stone so you could view them.

My own focus has been on implementing aspects of the UI, while the heavy lifting on the back-end was shouldered by other folks on the team. This has been a pleasant shift of focus for me because it has provided the opportunity to dive deeper into some of the murkier corners of Swing and the SwingX library, which (most unfortunately) recently had its funding cut-off by Sun.

My favorite new features in this release are private sharing lists and chat. I can't count the number of times I have wanted to send something to someone (maybe some software I was working on or pictures or whatever) that was just too big to fit as an email attachment. That problem is solved for me by being able to share whatever I want with only who I specify via the private share lists.

LimeWire_Alpha Uploaded with plasq's Skitch!

Give the tires a kick and keep your eyes peeled for the beta, which should be out shortly.

Sunday, December 07, 2008

Pecan Mini-Tarts (Favorite Holiday Recipe Meme)

Following on from Eric's blog post about Grizzlenuckles, here is a recipe for a pecan mini-tart dessert that my Mom has made at Christmas time for the last thousand years. These little things are crack, big time!

Pecan Tarts

1 stick unsalted butter
3 oz. cream cheese
1 cup flour, shifted
Mix ingredients until well blended. Make an oblong ball and wrap in wax paper. Put in refrigerator for at least 20 minutes.

Make little balls shaping the insides of the pans.

Filling:
¾ cup brown sugar
1 egg
2 tablespoons melted butter
¾ cup or more pecans, chopped

Mix these ingredients and fill the “cups”. Bake in a 350 minutes [pre-heated] oven for 18-20 minutes. [Keep an eye the first time because I am more or less guessing the time]
When cool sprinkle powdered sugar on top.
Makes 24 tarts.

I am tagging the following folks to pass-on their favorite recipes:
Dan
Dean
Justin
Jeff
Lance

Friday, November 28, 2008

Developing for the Android Platform

I attended an excellent talk Eric Burke gave last week on developing for the Android platform. The first half of the talk has been posted on YouTube. Enjoy!

Tuesday, October 14, 2008

Tuesday morning Ruby quiz

Last night, myself and the local Ruby group started down the path of preparation for the Ruby certification exam (after being inspired by Fabio Kung to go for it). One of the things we covered was here docs, a facility for creating multi-line strings in Ruby. We came across two funky cases (or at least I thought they were funky) that seemed good enough for quiz questions. Given the following here docs, what would you expect to print for the values of v1 & v2:

Friday, October 03, 2008

Me Meme


  1. Take a picture of yourself right now.
  2. Don’t change your clothes, don’t fix your hair…just take a picture. (should be super-easy with Photobooth)
  3. Post that picture with NO editing.
  4. Post these instructions with your picture
Carrying on from Dave

Friday, September 26, 2008

Rails Rumble

I've got to say that Rails Rumble is one of the things that I LOVE about the Rails community. Ultra time-boxed web application development is a great way to demonstrate enthusiasm for the technology as well as what can be accomplished in a short time by truly gifted developer/designer teams.

Respek!