I’ve talked a lot in the last few posts about the concept of a Story without actually ever saying what one of those is – so here goes. A story in this context is an independent, vertical slice through the code. It is the smallest unit which can independently be developed and deployed to add value to our business users. It is a narrative that takes a user through some process that results in a valuable outcome. The story MUST result in something of value – in an ideal world of continuously integrated and deployed software (and calorie-free cake), the story would be implemented straightaway, and implementing/deploying something of no value to the user is a bit of a waste of development time.

How To Write Stories

A very common way to write out stories is the following:

asA

For example:
saverStory1

Note that we require the “TO” in “I NEED TO” to make it functional so we know exactly what work this story needs to do. Instead of “I need a screen to see my bank balance”, we would have “I need to be able to view my bank balance” – how we show you this bank balance is then up to us as developers.

Hollub proposes a change to this:
inOrderTo

The above would become:
saverStory2

Aside from being 2 lines instead of 3 (and we like minimalist documentation) this states the value of the story up front, the first thing we know about this requirement is how it’s helping the users which is always the most important part of any story.

Stories should be written in the language of the domain, a user should be able to understand or even write the story without knowing any technical jargon. There should be no mention of technical concepts, or implementation details. Stories describe WHAT needs to be done, for us as developers to come in and decide the HOW of implementation based on WHY it’s required. Stories do NOT describe technical features.

The EPIC – splitting down into stories

Agile has the concept of an EPIC. I always write EPIC in upper case because it makes clear what it is – a big story which hasn’t yet been split into smaller chunks. Every EPIC needs to be taken and split into vertical slices – each of which is as thin as possible, whilst still delivering value. One way to split the EPIC is to split on if statements – as these are separate flows that can be implemented independently. I’ll explain what I mean through an example:
Let’s go back to the wonderful world of Hogwarts, and examples we’ve seen before. Suppose, as developers, we are given this requirement from our users – in this case the staff at Hogwarts.

“We need a way to award and deduct points from each individual student at Hogwarts. When points are added or deducted, we need this to be done in the following ways:

  • For a Gryffindor student, the points should be added and deducted as awarded (for example, if 10 points are awarded to Gryffindor, then they get 10 points, and similarly for deductions.
  • For a Slytherin student, the points added should be double what they are actually awarded, and the points deducted should be half the actual points deducted. If the actual points deducted is an odd number, then take 1 away from the value and then halve it.
  • For a Hufflepuff student, they can only add or deduct points in multiples of 5. If a member of staff tries to award points in increments of less than 5, then they should be warned that the balance will be rounded UP to the nearest 5.
  • If the student belongs to Ravenclaw, they can also only add or deduct points in multiples of 5. If a member of staff tries to award a number of points that is not a multiple of 5, automatically round UP OR DOWN to the nearest 5, i.e. 23 would round up to 25, but 37 would round down to 35.

Once the points have been added or deducted, the new total needs to be calculated and displayed in the Great Hall. At the end of the year, the house with the highest points is awarded the House Cup.”

Let’s break this down into individual stories. We see that there are immediately 4 distinct cases – 1 per house. However, as we will see, it is possible to split some of these cases even further.
Let’s start with Gryffindor, as it is the simplest case. We’ll use Hollub’s modified way of writing the story:

Next, we look at the Slytherin case, because, sneaky as it is, it is the next simplest scenario

slytherin3

Next, we look at Hufflepuff:

And finally, Ravenclaw:

To finish our backlog, we take the final requirement into account:
houseCup

Note a few important things about these stories:

  • They are independent – we could pick up any one of these first and be able to deliver it. There may be some overlap – the first story we picked up would involve creating a means for the user to view the points balance – and this would then be used in future stories – but that in itself is not a separate story. Therefore, no one story is dependent on another. (Implementation order is NOT equal to dependency).
  • They are written in user friendly language. There is no mention of how we will store the points balance, or how we will display the points in the great hall. The warning given would probably involve some sort of exception being raised in the code – but there is no mention of that in the stories, and that is how it should be.
  • The stories go right through the application. Each one is demonstrable to the user because each one displays something for them to see – i.e. the points balance in the Great Hall. They can see the story having an effect on the UI they have access to.
  • The stories all independently add value. This maybe should have come first, and is obvious but often overlooked when writing stories of your own.
  • They are all small, which makes them seem more manageable and makes estimating them easier.
  • They are all testable. It’s easy to test that they do what is intended – check the balance that is displayed at the end and see if it is what is expected.
  • They make no assumptions about architectural decisions – which means those types of decisions can be made at the time of taking on the story.

The story is only DONE when it is implemented with acceptance criteria having been met, AND HAS BEEN TESTED.

How do we get from these stories to our code?

We should use the concepts defined in our stories to form a system metaphor for our design, and use the language of the metaphor in our code. Every system needs a metaphor – this is commonly directly provided by the domain of your system. Stories exist within this metaphor, and names commonly used in the metaphor can be used without definition – e.g. Hufflepuff, House, House Cup. Your metaphor can exist without a computer! The computer is brought in to model the people/components of the metaphor, but that comes later. The computer is brought in to make what people could be doing more efficient (in the above example, we could have people following around every Hogwarts staff member and, when they award points, manually running to the Great Hall and writing the new points balance onto a whiteboard. Whilst this would solve the problem at hand, it is a waste of time for the “runners” and inefficient when computers could do this so much better. However, the point is that the stories as they are written could be implemented without a computer).

When reading the code, then, it should be easy to see what we are doing. For example, in our instance, we would end up with classes for HousePoints, HouseCup and RavenclawStudents, we would have methods called isMultipleOfFive, punishBadBehaviour, awardHousePoints, roundDownToNearestFive, etc. Our code will read as a narrative of our story – it reflects the language of the domain accurately. Therefore, for future stories (even in the same backlog), it becomes obvious where to modify the code.

Disclaimer: A lot of the material of this post is based on a talk given by Allen Hollub entitled “From Stories To Code” at the SDD conference in London.

<<<<Moving Towards Being Agile – Planning

Advertisements

2 thoughts on “Moving Towards Being Agile – Stories

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s