![]() |
Articles Feed |
Categories
Archives
- December 2008 (3)
- November 2008 (5)
- October 2008 (4)
- September 2008 (6)
- August 2008 (4)
- July 2008 (5)
- June 2008 (5)
- May 2008 (4)
- April 2008 (2)
- February 2008 (4)
- January 2008 (2)
- December 2007 (2)
- November 2007 (2)
- October 2007 (2)
- September 2007 (1)
- August 2007 (3)
- July 2007 (1)
- June 2007 (4)
- May 2007 (7)
- April 2007 (2)
- February 2007 (3)
- January 2007 (3)
- November 2006 (3)
- October 2006 (3)
- September 2006 (17)
- November 2004 (1)
Clean as You Code
by: micah | January 29th, 2007 | 0 comments »
In my younger days I was a Line Cook at the Olive Garden. In case you’ve never worked in the food industry, Line Cooks are the guys putting meals together as fast as customers order them. At times, it’s nearly impossible to keep up.
Among the most fundamental of the Line Cook’s principles was Clean as you go. I can remember clearly the manager walking regally down the line chanting, “Clean as you go Javier. Clean as you go Micah. Clean as you go Brian.” Cooks would remind each other from time to time too, “Clean as you go!”.
As you’re realizing, it’s import to keep your station clean when you’re a cook. Keeping things clean is not easy. Food gets EVERYWHERE when you’re putting together hundreds of meals an hour. Why is it important to keep it clean? Simple. When your station is dirty, the system breaks down and it slows you down. Utensils are dirty or missing, ingredients get mixed together, cooking surfaces are soiled… Combine this with all the fire, boiling water, and sharp knives, it’s dangerous too! Worse, other cooks are not able to help out. Uncleanliness on the line is a vicious cycle with positive feedback. Every experienced cook keeps their station spotless at all times and unexperienced cooks learn fast.
Dirtiness is a sign of trouble too. Let’s say that it’s the middle of a dinner rush. You look down the line and notice that Javier’s station is becoming cluttered. It’s near certainty that in five minutes Javier’s system will break down. Food will be burnt, orders will get lost, and servers will get vocal. Don’t get servers mad! Line Cooks work as a team though. So when you see that Javier’s station is getting cluttered, you jump over and give Javier a hand every moment you can spare.
This principle, “Clean as you go”, is well applied to software, “Clean as you code”. The analogy is fairly straight forward. Although I’ve applied the principle to software for years, it was only recently that I recalled the mantra “Clean as you go”. I’m sure my teammates will soon grow tired of hearing me chant… “Clean as you code!”
Three Reasons to Use FitNesse
by: micah | January 19th, 2007 | 3 comments »
1. You find your self delivering software to your customer who says “That’s not what I asked for.”
Using FitNesse allows you to communicate with the customer up front. Before a line of code is written, you can have all the behavior expressed in an executable format. Make sure the customer helps to write these tests. Once your FitNesse test is in place, all you need to do it make it pass. Due to the cut-and-dry aspect of executable specifications (FitNesse test), one the spec is passing, you have delivered precisely what your customer asked for.
2. Bugs sneak into your system as development progresses and these bugs takes weeks to find and remove.
FitNesse is a tools to help you drive development with tests. When practices with discipline, test driven development will insure that you have a FitNesse test for each and every feature in your system. The moment a bug is introduced, you will know about it because a FitNesse test will fail.
3. It is difficult to create documentation for your system and it is constantly out of date because the system is changing.
FitNesse offers a unique documentation solution. When ever you write a FitNesse test, you are in fact describing how the system works. In other words you’re documenting it. The web/wiki based nature of FitNesse makes documentation simple and convenient. The best part is that the documentation in FitNesse can never go out of date. Since you’re keeping your test passing, and your tests are documentation, it’s impossible for them to lie.
There is an article I wrote about FitNesse for Windows Developer Power Tools. This book, just released today, includes articles on dozens of free tools that .NET developers might benefit from. If you write .NET code, check it out. If not, keep in mind that FitNesse will work for almost any language.
Getting started with Rails and FitNesse
by: paul | January 15th, 2007 | 36 comments »
This is intended to be a tutorial to get you started using FitNesse with ruby on Rails. There is some explanation needed about FitNesse, Fit, and Rails. Smart people have written about such things, I will leave you to google them as interested. Two good references are listed at the bottom of this tutorial.So lets get started. Our customer has just written a test that looks like this:
|vending machine| |check|amount|$0.00| |enter|currency|$.35| |press|add change| |check|amount|$.35| |enter|selection|juicy fruit| |press|vend| |check|amount|$0.00|
This would be a common first fixture for a product, as it is limited in scope, it is a very specific example from which to build a conversation about requirements about. Anyway, the first thing to making this pass is getting some of the FitNesse infrastructure in place around your rails app.
First, lets create a rails app for our vending machine
$rails vending_machine
We see all the normal rails stuff, all the creates.
Lets download FitNesse and place it in our vending_machine root directory. FitNesse can be downloaded at http://fitnesse.org. And start the FitNesse server.
So, now we go to the FitNesse main page and create the page for our acceptance test. Then put the test from the customer into the page and try to run it. Failures? We need to set up the environment to run with ruby fit. Follow the instructions here (http://fitnesse.org/FitServers.RubyFit) to set up the right test runner for ruby.
Lets write our first fixture in a fixtures directory we create in the root folder.
Our new test with the path and test runner set up looks like this
!define COMMAND_PATTERN {ruby -I%p ruby/bin/FitServer.rb}
!path
!3 Make one transaction with a vending machine
!|fixtures.VendingMachine|
|check|amount|$0.00|
|enter|currency|$.35|
|press|add change|
|check|amount|$.35|
|enter|selection|juicy fruit|
|press|vend|
|check|amount|$0.00|
There are a few things to notice about the changes.* The path is the rails root dir.
* Fixtures.VendingMachine is mapping to the folder name/module name of where the fixutures are located. In this instance it is a folder in the rails directory called fixtures.
* If you run the test, you will get all sorts of exceptions, because the fixture code is not written yet.
Note: If the table is not even showing up when you run the fixture go here.
Now it is time to write a fixture to make this test fail without any exceptions. In the fixtures directory, create a file called vending_machine.rb. The naming of your fixtures maps with the name of your file, which it will require. Lets make a stub file to make the test fail without exceptions.
require 'ruby/lib/fit_helper'
module Fixtures
class VendingMachineFixture < Fit::ActionFixture
attr_accessor :currency, :selection
def initialize
super
@@actor = self
end
def add_change
end
def vend
end
end
end
Now we should have failures with the amount not changing.
Lets create our controller for the vending machine and start to implement the code. I am going to leave out the specs I use to write the controller, just show the code. Here is the first version of the controller. Note it has the same stubbed methods the fixture has.
class VendingMachineController < ApplicationController def add_change end def vend end end
Lets hook up the fixture to the imaginary controller. There is a fair amount of set up which is rails related.
First, we need to load up the environment and the controllers. Add these lines to the beginning of your fixture.
require File.expand_path(File.dirname(__FILE__) + "/config/environment") require File.expand_path(File.dirname(__FILE__) + ' /app/controllers/application')
Which should allow us to change the initialize method to:
def initialize
super
@@actor = self
@controller = VendingMachineController.new
@controller.params = {}
end
Which creates the controller, and initializes its params to an empty dictionary. There are other ways to do this, like creating test params, but for simplicity, we are going to create our own for now.
Next, we set up the values in the params and call the controller methods.
def add_change
@controller.params[:amount] = @currency
@controller.add_change
end
def vend
@controller.params[:selection] = @selection
@controller.vend
end
Now, we make the test pass by implementing the controller.
class VendingMachineController < ApplicationController
def initialize
@items = {"juicy fruit" => 35 , "doublemint" => 45 }
@session = {} if not @session
@session[:amount_entered] = 0.0;
end
def add_change
@session[:amount_entered] += params[:amount].to_f
end
def vend
@items.each_pair do |key, value|
if(params[:selection] == key)
@session[:amount_entered] = 0.0
end
end
end
end
