Perfect vs. Shipped

I overheard an amusing comment in my team-room the other day, I think it might have been Kris Kemper who said it – “Anyone who knows Ruby On Rails has a half-done personal project that’s going nowhere”. How true. I have at-least three.

The thing is, in my mind I’m always envisioning these grand cathedrals, and even when I do start work on any one of them, I never seem to quite finish them. Or I don’t complete everything properly (or quite enough to be production-ready), and the application is never quite done.

I think it has to do with a lack of focus. I find myself thrashing between the hundreds of things that interest me, and I end up with a ton of unfinished work. I’m very much into lean software methods, and I know that all I’m doing by operating this way is creating a lot of inventory. I seem to be able to use lean and other workflow management techniques at work, but in the world of my personal projects, I seem to be at a loss.

Sometimes, it has to do with trying to get everything perfect. After all, since it is a personal project, I feel like I don’t have a delivery dead-line, so I can take the time to get it right. Which leads me down the rabbit-hole of perfection and cathedral building, with no real end. Cause there probably ain’t anything called perfection.

When consulting for our various clients, I’ve a clear idea in my mind about the compromises and trade-offs needed between design, architecture, refactoring, and delivery. And I aggressively do whatever might be needed to prod the folks along (be they developers, or product-owners) to get the thing done and into production. After all, there’s always another iteration coming up, and there’s always a next release.

So why the heck can’t I seem to do the same thing when I’m working on a nights-and-weekends project?

Ruby, managing global variables, and dynamic scope

Everyone knows that global variables are bad. However, they are quite unavoidable. Java’s System.out is an example.

Globals, sometimes offer a certain kind of flexibility. They offer a way to tweak the behavior of the entire (or a subset of) the system. For instance, one can redirect System.out to a different stream (into a file, say) and capture all the messages a program spits out.

This kind of stuff works nicely. Except when someone else goes and changes the same variable to something else in another part of the code, and you’ve no idea where.

What is needed, is something like optional dynamic scope, so that the globals can be used when needed, but can be managed better. After all, from the above example, what seems to be needed is a way for a piece of code to say – for my purposes, and for all code that runs when I’m called, I want the value of this global(s) to be _something_, and when I return, these globals should be reset.

This can be done manually, by saving the existing value of a global before setting it to something else, and then resetting it back when the code block completes running. Perl and Common Lisp have had a mechanism to do this type of stuff for a long time, built into the language.

Here’s a hacky (and probably naive) way to implement this in Ruby, to illustrate how this might work –


module Let
def let(bindings, &block)
old_bindings = capture_existing_bindings_for(bindings)
block.call
rehydrate_old_bindings_with(old_bindings)
end
def capture_existing_bindings_for(bindings)
old_bindings = { }
bindings.each do |k, v|
old_bindings[k] = eval "@"+k.to_s
create_binding k, v
end
return old_bindings
end
def create_binding(var_name, value)
instance_eval "@#{var_name}=value"
end
def rehydrate_old_bindings_with(old_bindings)
old_bindings.each do |k, v|
create_binding k, v
end
end
end

And the way you would use this, would look something like this –


require 'let_module'
include Let
@num_var = 1
@char_var = 'a'
class Car
attr_reader :name
def initialize(name)
@name = name
end
end
@obj_var = Car.new("hyundai")
def do_something
puts "num_var is " + @num_var.to_s + ", char_var is '" + @char_var.to_s + "', obj_var is " + @obj_var.name
puts "returning"
end
do_something
puts "changing num_var to 2, char_var to b, obj_var to 'kia'"
let :num_var => 2, :char_var => 'b', :obj_var => Car.new("kia") do
do_something
puts "changing num_var to 3, char_var to c, obj_var to 'toyota'"
let :num_var => 3, :char_var => 'c', :obj_var => Car.new("toyota") do
do_something
end
do_something
end
do_something

And when run, would produce this –

num_var is 1, char_var is 'a', obj_var is hyundai
returning
changing num_var to 2, char_var to b, obj_var to 'kia'
num_var is 2, char_var is 'b', obj_var is kia
returning
changing num_var to 3, char_var to c, obj_var to 'toyota'
num_var is 3, char_var is 'c', obj_var is toyota
returning
num_var is 2, char_var is 'b', obj_var is kia
returning
num_var is 1, char_var is 'a', obj_var is hyundai
returning

This could be one way to control unruly global variables in Ruby.

Lean Software Development and the Theory of Constraints

I’ve been trying to apply lean software development principles on my project for a little over a year now. So, when I recently re-read Mary Poppendieck’s Lean Software Development – An Agile Toolkit, I thoroughly enjoyed it and found I was nodding to myself a lot. I highly recommend reading this book because it explains in very simple terms what this whole lean process thing is about, and how it relates to software development. A knowledge of why Agile processes work and what they’re aimed at would help, but is not essential.

For those who don’t have the patience (or time) to read the full book – here’s my version of a summary –

– Strive to eliminate waste. Waste comes in many forms in the world of software development, all of these is waste – partially done work, extra processes that add no value, extra features that have little impact on business value, task switching because of multiple objectives or other reasons, waiting for something, having to go somewhere (to meet someone or fetch something) to get information, defects, and ‘management’ activities.

– Use a technique called value-stream mapping to understand where the process you’re using delivers value and (more importantly) to determine where it adds none.

– Amplify learning through feedback. This is easily done through short iterations and negotiating scope for each of them.

– Think about set-based development techniques.

– Delay commitment – decide as late as possible. At the same time, think about concurrent development.

– Deliver as fast as possible – this enhances learning, and delivers value at the same time. Use concepts from pull-systems and queuing theory.

– Understand the cost of delay – use a product model. Have an accountant on your team who can help with this, and make trade-off decisions in light of what the model says.

– Empower the team!

– Think about integrity – both conceptual integrity, and perceived integrity.

– Testing – TDD, automated functional testing, continuous integration – is key. Refactoring is key.

– Always optimize at a level higher than the perceived issue. Employ systems thinking.

– Embrace the idea of Customer Collaboration vs. Contract Negotiation.

I’ve found that as I started to apply lean software development methods, our processes started to become more and more natural, and that the team became more and more effective. As expected, the team members themselves began to look for new and innovative ways to optimize their workflow, and my job as a project manager became easier and easier from that perspective.

Speaking of optimization, I recall being introduced to the writings of Eli Goldratt by a really smart project manager I worked with in the past – Matt Gelbwaks. Goldratt writes about the Theory of Constraints – his books The Goal and Critical Chain are a really good start to the whole discipline. He has a really simple algorithm to optimize a system, based on throughput accounting

1. IDENTIFY the system’s constraint(s)
2. Describe how to EXPLOIT the system’s constraint(s)
3. SUBORDINATE everything else to the above decision
4. ELEVATE the system’s constraint(s)
5. If in the above process, a constraint has been broken, GO BACK to step 1 but do not allow inertia to cause a system’s constraint.

Applying the Theory of Constraints to improve my teams’ processes, while using lean software development ideas to drive agile practices has proved absolutely invaluable to me over the past year.

I’d be happy to hear from you if you tried similar things on your project… and about how they worked out…

Java Micro Edition development – annoying emulator error

After a long time, I recently started playing with the Java Micro Edition again. Many years ago, I had downloaded and installed the Wireless Toolkit from Sun’s website (then in beta), and had hacked together common mobile games – snake, hangman, and the like.

So, when I downloaded the toolkit this time (v2.5 now), it was annoying to find that I couldn’t even seem to run a basic midlet without the emulator barfing at start up time, with an inexplicable ‘Uncaught exception java/lang/ArrayIndexOutOfBoundsException’ – no line numbers, nothing. The emulator screen wouldn’t list the midlet name either, so clicking on the soft button would simply print the same exception message again.

Google was of limited help. More annoying.

Finally, I just played around with different configurations during launching the midlet, and when running it in “class” mode (you have to specify the midlet class), it seems to work.

So there’s a work-around for you.

CruiseControl.rb – Continuous integration for ruby projects

cruisecontrol.rb

I downloaded and installed CruiseControl.rb today – from the ThoughtWorks website. Well, I suppose ‘install’ is not quite the right word as it comprised entirely of running a couple of commands, and took all of 30 seconds.

It works beautifully, right out of the box! The example on the website didn’t have any reference to the situation where you connect to your subversion server over ssh, so when I went ahead and tried it, it succeeded and then gave me the following message –

IMPORTANT!!! – It looks like you are connecting to your repository with an svn+ssh connection. For cruise to build this project, you need to have set up authentication caching for ssh, see this article
http://subversion.tigris.org/faq.html#ssh-auth-cache

What a pleasant surprise! I like software that was designed with users in mind. The information above for setting up ssh authentication works like a charm, btw.

Using mind maps to start planning a project

As you might have read earlier, I recently started a new team that has been chartered with building a suite of new products from scratch. The business folks have been working in the domain for a long time and have built similar products before. Despite that, requirements for the new products have not all been nailed down yet, making this project somewhat of an ideal situation to start a new team. We’re using Agile (Scrum with XP practices) methods, and I’m infusing several ideas from Lean Software Development into the mix.

I used a new tool to kick-ff the high-level planning sessions this time. I’ve been using mind maps (FreeMind, Mindjet Manager, and NovaMind) for a while now: for various things – keeping track of to-dos, planning my personal projects, thinking about high-level goals, brainstorming and brain-dumping, and so on and so forth. I’ve always felt that such an intuitive tool might make for a great way to facilitate work sessions, especially when the work at hand is fairly high-level. An example might be – early stages of planning.

In my opinion, using the tool turned out to be quite a good idea. The first meeting lasted three hours (including coffee and a 10 minute break), and had about 12 participants with me facilitating using a whiteboard and sticky flip-charts. I ended up with several mind-maps including one for the overall project layout, one for training requirements, and another that detailed a particular module. The whole team was able to participate in building it as it was merely a form of a brainstorming exercise, with some extra structure.

Here’s a mock-up of one of these mind maps that got produced at this session –

projectX.png

One possible next step is to pick up the area which needs to be worked on first (actually this will probably be more than one – for example, the architecture-spike and config-management piece will need to be done in the beginning regardless of what else gets picked up) and continue to drill-down into its details. When sufficient granularity has been achieved, the leaf nodes of the mind map can be translated into backlog items (or phrase-level user-stories). Of course, this will mean that the brainstorming will need to be done with an eye towards this end goal – and all the guidelines around writing good user-story phrases will need to be kept in mind.

Overall, it was a good exercise – it was interactive and fun. More importantly, it was a visual way of representing the project and its potential scope – and was a great start at arriving at a shared mental-model of the system. Having all members of the team present (developers, QA, BA, and sponsors) helped a lot as well.

Note: I didn’t use the actual software in the meeting, instead, I chose to draw on the whiteboard and one of the participants (the sponsor!) volunteered to scribe. This let the session be more about the content than about formating and word-smithing. I later converted the notes to soft-copies using FreeMind.

Pay incentives vs. motivation

I’m sure you’ve had many conversations with people about what motivates people, and how to get them to work smarter or harder or to get them to do the right thing. Compensation – money, stock options, bonuses, and other similar perks quite often figure in these discussions. Yet, there is usually a thread about how these don’t really seem to work that well, or perhaps not at all.

Here’s expert commentary from someone who has spent many years studying management practices – including what kinds of incentives work – such that people are intrinsically motivated to do the right thing towards the end goal. This testimony was given to congress, no less.

[Originally from Esther Derby]