Monday 29 June 2015

Too Much Typing


One of the most dangerous tools available to a developer is Ctrl+C Ctrl+V, with those two short-cuts a developer can do a lot of damage to a code base.
The duplication it causes reduces the readability, maintainability and the integrity of the code, we should implement things once and only once and not repeat ourselves because who enjoys typing.
Don't Repeat Functionality
For every piece of functionality their should be a single authoritative implementation within the code base.
Don't duplicate functionality by implementing your own function or method to provide functionality already available in the code. If the current implementation doesn't quite fit your needs consider how it could be re-factored to meet your requirements.
Remember that if you need this functionality the chances are someone else will need it in the future too.
If we all implement functionality ourselves soon the code base will be nothing but date formatting functions and string utilities.
If you can't adapt the method to do what you want this should be conceded a smell, it could be that the code you need hasn't been built for change or could be that what you want to do with it just isn't practical or desirable. 
Don't Duplicate Implementation
Don't duplicate implementation by copy and pasting code from one location to another.
If you can't just call the code that already exists the chances are something is structured badly, either your code or the code you need to call. It could be behind a bad abstraction, tied up with too many other concerns or it could be that your code is trying to do something it really shouldn't be doing and sticking its nose in where its not wanted.
Either way the solution to the problem isn't to duplicate the mistake into multiple locations in the code.
Once again if you've encountered this problem at some point someone else will, help them out by dealing with the situation not by replicating the problem.
Don't Duplicate Information
Make sure every piece of information within your system is stored in only one place, this should apply to dynamic data and constants alike, their should be a single source of truth for all data.
Once again if you can't get to the data you need the chances are either you shouldn't need to know that data or its being stored in the wrong place. The class that exposes the data should have a close association with that data, this is how we ensure the code makes sense and that we abstracting things properly.
Having data defined in multiple places creates the possibility that the different sources won't agree on the value of the data, this creates a situation that isn't easily solved, you shouldn't have to decide which source of data you trust more.
Just Don't Duplicate
What I'm trying to get across is that when duplication appears to be the answer your probably solving the wrong problem.
This is nearly always indicative of a structural problem in the code base, it is these structural issues that should be addressed.
Every time something is duplicated in a system your not only duplicating the code, your duplicating the effort required to maintain the code, the likelihood of bugs and the amount of code a reader has to understand.
Because of its need to be maintained and fixed code is a liability we should be looking to end up with as little of it as is practically possible, duplicating it does the opposite.
Writing classes isn't about providing example source code documenting to someone this is a solution for this problem, its about providing a structure so that they don't have to care how the machine is working they just trust you and make use of the implementation you've already provided.
Now its not always possible to know all the variations of a piece of functionality that may be needed in the future, but its for exactly this reason that good code is built for change, so when tweaking is necessary its clear how that can be achieved and we don't just start again by duplicating.
A good developer is a lazy developer who doesn't want to type the same thing over and over again, he or she likes to do a really good job of it once and then stop their. 

Wednesday 24 June 2015

Debt Management

We've all been in the position where we've been asked to cut a corner to hit a deadline, we don't want to do it but its part of the commercial reality of having to ship something out of the door.
Providing this is done in an Agile way by defining an MVP and leaving future enhancements for subsequent iterations this doesn't have to be a bad thing.
But every time we take an action that is sub-optimal we accrue a piece of technical debt, again this doesn't have to be disastrous but it does need to be properly managed.
Buy Now Pay Later
The first thing to realise about technical debt is that its effect isn't felt at the time its accrued, the pain comes when its time to pay it back.
The definition of technical debt is taking an action that is sub-optimal and will make future changes to a system harder to achieve, eventually this can build up to a point where no further change is possible, development grinds to a halt, and you can bet this will happen just in time for the next urgent release.
Very often a code base that is riddled with technical debt will be beyond saving, a re-write is the only cure.
For this reason its important to document technical debt both at the point its accrued and every time it impacts a future change. Quite often the sin isn't in accruing the technical debt its in letting it fester and not addressing it until its too late.
Be careful you don't buy a release with so much debt that your credit card is rejected when you next need to ship, instead be sure you have a payment plan.
Technical debt is like any other debt, your accruing interest all the time you haven't paid off the balance.
Credit Score
In an ideal world no technical debt would ever be accrued but the reality is you can't avoid it, but you can make sure you are responsible borrowers.
Martin Fowler describes technical debt as being a mixture of prudent/reckless, and deliberate/inadvertent, this gives rise to four possible groups who can accrue technical debt.
Reckless and Inadvertent = Bad Developers Just Doing It Wrong
This is less about technical debt and more about simply never having any hope of producing quality code, this team doesn't even realise there accruing technical debt and will undoubtedly end up insolvent.
They aren't cutting corners they are simply making bad design choices at every turn, there is no excuse for being in this group.
Reckless and Deliberate = Hacking It Up
This group might know how to do things properly but are happy to just "get it working". They don't appreciate the benefits of a good design and don't write code that is built to cope with change.
The first few releases will be fine but soon the stack of hacks will come crashing down with a wave of defects.
To not end up in this group you simply need to realise that your code working is the minimum requirement not the point at which you say "job done". 
Prudent and Inadvertent = Not Fully Understanding The Problem
This kind of debt is very difficult to avoid especially on a new project. This is what Agile is trying to teach us that anticipating and meeting the demands of users is difficult, that's why we ship early, fail fast and iterate.
The most important aspect of this kind of debt is to anticipate that you are probably accruing it and be sure to recognise early when certain design choices are causing issues and start thinking about a plan to make changes and pay the debt back.
Prudent and Deliberate = Being Realistic
This is the team that's on top of their game, they understand the system they are trying to build and they are realists who know that at some point you have to ship something. They fully understand which decisions are causing the debt to be accrued and they have an appreciation for the likely consequences and may even have some idea what the resolution will look like.
Don't be too hard on yourself if your not in this group, they are probably experienced developers working on a mature product.
Forewarned is forearmed, understanding the concept of technical debt and its consequences is half the battle, monitoring your debt levels and acting early to avoid bankruptcy will see that you can continually ship software and continue to iterate and add value for the user.  
Try and make the debt work in your favour by using it to buy the time to make the release but paying it off before the interest payments cripple you.

Sunday 21 June 2015

Defending Your Honour


As much as we might want to we can't always write everything ourselves, sometimes we have to use someone else's code, an old adage quoted in many forms is
"Good developers write good code, great developers use somebody else's"
Re-using existing proven solutions to problems should always be preferred but utilising someone else's code should not be done without a healthy measure of distrust.
Never assume that everyone else has the same high standards that you do, some people "do it wrong".
Everything Is Tainted Until Proven Otherwise
When writing a class or a method all data that is passed from the rest of the code base into you should be distrusted by default and should be validated before any damage can be done.
If someone passes rubbish then they should receive an error, not just to protect your code but also to inform them that your code cannot work with what they have provided and this is what they should do to fix it.
This does mean that the APIs you write must be clear about what is acceptable and what isn't, as much as possible this should be enforced by type safety. As an example if your API accepts an integer an error shouldn't be thrown if that integer is greater than 173, as the caller how was I supposed to know that? 
This distrust should also extend to data you receive from the methods you are calling, for example a method may not state that it could return null/nil but if that would cause your code problems then this should be checked for.
Not all developers document their code well, if you cannot see the source who knows what is happening under the hood, assume the worst and protect yourself against it.
Assumption Is Mother Of All Disasters
When performing a post-mortem on a problem you will quite often here things like
"I assumed that couldn't happen"
"I assumed that method wouldn't do that" 
"I assumed no-one would do that"
If you can see a potential problem never assume anything about the likelihood of it happening, this is especially true if the resolution to that problem is straight-forward.
A good example of this is the unchecked use of size constrained variables, consider the following example in C,
void DoSomethingWithAString(char *aString) {
   char someNewString[100];
   // Do some stuff
   // Copy the result and hope we don't overflow the stack!
   strcpy(someNewString, aString);
}
The nature of this function maybe that it would be unexpected for a string longer than 100 character to be passed in, but never assume.
A better solution to this problem would be to explicitly copy only 99 characters leaving room for a null terminator. 
The only assumption you should make is that someone at sometime will do something stupid, make sure your code isn't made to misbehave because of it.
Help The Next Guy Out
Another aspect to defensive programming relates to trying to prevent accidental damage being done by the next person who touches the code.
The first defence against this is achieved by simply having a good design in the first place, well written code is designed to deal with change and as such there are less likely to be mistakes made when it needs to be updated.
But sometime subtle changes can help the next guy out, an example of this is Yoda Programming,
if (10 == x)  {
   // Do some stuff
}
This may look strange but it prevents anyone editing this line from accidentally turning equality into assignment, notice also how we are still using curly braces even though the if statement is a single line, this prevents anyone who needs to add extra lines in the future from accidentally placing them outside the if statement.
A large proportion of those annoying niggly bugs are caused by accidental mistakes when editing an existing code base, this kind of defensive programming can go a long way towards making sure that doesn't happen.
When writing a new piece of code you should see a clear boundary between the code your writing and the code written by others that you're utilising. Everything on the other side of the line should be viewed with suspicion and is guilty until proven innocent.
We should distrust black boxes, defending our codes honour against being made to look foolish because of someone else's mistakes. Just because you're paranoid doesn't mean the other guy isn't doing it wrong. 

Thursday 18 June 2015

Rewarding Good Behaviour


As developers these days we are very driven people, there are numerous xDD philosophies that we can chose to become followers of.
One such philosophy is Test Driven Development (TDD).
In essence TDD involves writing the tests before writing the code, this focus on what functionality a piece of code should offer and how you should interface with it before you actually produce the code brings many advantages.
But TDD tends to be a tool of a developer, he or she applies it when writing unit tests concentrating specifically on a single class.
What if we could apply the same thinking to an entire system? And what if we could bring these benefits to everybody and not suggest those of us that are conceded "techy"?
This leads us to the idea of Behaviour Driven Development (BDD).
Given, When, Then
Much like TDD, BDD attempts to define the specification of a system before it is written, the key difference being that this specification is by example and is phrased in a ubiquitous language that everyone who has a stake in the outcome of the system agrees upon and understands.
These examples of the desired outcomes for the system are not technical because there not concerned with implementation, remember the system hasn't been implemented yet, the ubiquitous language should be understood by developer, tester, business analyst, product owner and even the end-user of the system alike.
Everybody can agree that you need to be able to login into our system and everyone can agree that Given that I enter the correct username and password, When I select login, Then I should be logged in.
Because we are simply providing examples of the expected behaviour of the system irrespective of implementation we create a living document that grows as the system grows and can be used by anyone to understand what the system is and what it does.
When the system regresses and no longer conforms to this specification it is clear for all to see.
The Three Amigos
The move away from technical detail in defining the behaviour of a system lies at the heart of BDD, the definition of the specification should have input from all sides.
Developer
Tester
Domain Expert
Between these three amigos all aspects of a potential system can be covered, what is technically possible, what quality looks like and what makes sense within the domain that the system will operate. 
Producing a specification is as much about clear communication between these members of the team as it is about specifying the tests a system must pass in order to be fit for purpose.
The Story We Want To Hear
BDD has a clear alignment with Agile development, the concentration on telling the story of the user and the system means the testing output of BDD should inspire great confidence that what was required had been delivered.
Specification by example also allows only the minimum set of requirements to be defined that represent value and produce a viable product.
The living document allows rapid iteration of the story we want the system to fulfil as well as clearly defining the work required to get their.
The ability to have a ubiquitous language and narrative from the project starting to the first iteration rolling of the production line is a very powerful tool.
The What Not The How
The cause of many projects getting caught in quicksand is getting overly bogged down with the "how" and not the "what" in the initial inception.
BDD as with Agile should help focus the mind that providing we will be able to supply an answer to "how" the much more important questions are "what" and even "why", failure to be able to supply answers to those two questions means your doomed to fail.
Difficulty in writing the features of a system should be a clear sign that you don't have a clear vision for what you are trying to achieve, don't just start building something work out the right thing and build that. 
The most important feature you every right should be Given We produce a system that does this, When Users get there hands on it, Then They will wonder how they ever lived without it. 

Sunday 14 June 2015

Recognising The Enemy


We're all familiar with software design patterns and we apply them when we recognise a common problem as our collective experience has taught us that they are effective solutions.
But not all patterns are born equal, sometimes they can be misused, this leads us to the concept of anti-patterns.
Generally anti-patterns can be described as being ineffectual solutions, on the surface they may appear to fix the problem but they usually are just converting one type of problem for another.
So how can we recognise an anti-pattern?
Square Peg In A Round Hole
Anti-patterns can sometimes be born by applying a well known pattern to a situation that requires a different solution, quite often this is caused by attempting to fix the wrong problem.
An example of this would be the over zealous use of the singleton pattern.
There are valid use cases for singletons but their automatic use in situations where allowing multiple instances of a class is problematic can make it become an anti-pattern.
Turning a class into a singleton may solve a problem your having related to multiple instances but singletons,
  • Hide dependencies.
  • Decrease Testability.
  • Decrease the opportunities for code re-use.
This is a good example of an anti-pattern, the solution to a problem in one class has now spread to several problems in every class that comes into contact with it.
When applying a design pattern we should be looking to satisfy the greater good, whenever the application of a pattern causes undesirable side-effects such as these the question must be asked are we fixing the right problem? How much impact does our solution have on the rest of the code base?
Fix For A Fix
Another symptom of an anti-pattern is rigidity and a general lack of adaptability, they often fix a specific problem in a specific way. This leads to you re-visiting an area of the code over and over again coming up with ever more inventive ways to keep the plates spinning and keep the pattern in place.
An example of this would be the inappropriate use of the template method pattern.
Again there are valid use cases for this pattern but its use of abstract classes and inheritance places restrictions on how the code base operates, this means you must be sure that all potential future uses of the functionality will fit the abstraction.
This is another trait of an anti-pattern, it doesn't fix the problem for very long, you end up returning to that area of the code base frequently and each time the original pattern used seems less appropriate for the situation.
I Thought It'd Be Easier Than This
Applying an anti-pattern often doesn't provide the benefits that you are lead to believe will follow, an example of this is the service locator pattern.
The service locator pattern is a necessary part of implementing dependency injection, however it is only part of the story.
The key aspect of implementing DI is the inversion of control where classes clearly state their dependencies and pass over control of providing them to the code constructing the class. Use of the service locator pattern inside the class doesn't provide this inversion and therefore doesn't reap all the benefits that DI should bring especially in relation to testing.
This is one more symptom of an anti-pattern, they do not provide well rounded or complete solutions to the problem at hand. They hint at the correct solution but have something missing.
You will on occasion end up coding an anti-pattern, software development is complicated not always getting it right is not a sin. The key is to recognise early on that something isn't right before the side effects permeate to far.
When you've decide on a pattern to use ask yourself if this leaves the code base in better shape than when you found it,
  • Can I think of way where the problem I'm trying to solve will still exist?
  • Can I think of a new problem I'll be creating if I use this pattern?
  • How far reaching are the consequences of using this pattern?
  • Is it clear how I will be able to test this code?
  • Is it clear how the code base will grow around the use of this pattern?
Satisfactory answers to these questions should give you a warm feeling inside, unsatisfactory answers will leave a niggling doubt in the back of your mind.
Do not ignore this doubt, its the product of experiencing and the surest way to recognise the presence of the enemy. 

Wednesday 10 June 2015

Don't Talk To Strangers


In ancient Greek mythology Demeter was the goddess of the harvest who presided over grains and the fertility of the earth.
In 1987 at Northeastern University in Boston as part of the Demeter project the Law of Demeter was formed, this law states that classes should,
  • Have only limited knowledge about other classes: only classes "closely" related to the current unit.
  • Only talk to friends; don't talk to strangers.
  • Only talk to immediate friends.
The purpose of the law is to promote loose coupling and information hiding by re-enforcing the idea that a class should have as little knowledge as possible about the workings of the larger system it is a part of, for this reason the law also goes by the name of the principle of least knowledge.
A Bit Of A Train Wreck
Code that breaks this law is most often identifiable by looking for long chains of function calls, each one taking another step down the rabbit hole of dependencies.
Consider two classes A and B and the following snippet,
var someData = A.GetB().SomeMethod();
When we spot code like this we should be asking ourselves questions like,
  • Why does A expose its dependency on B to perform this operation?
  • Why do we know about the existence of B?
  • Why do we know that SomeMethod() needs to be called on B?
By reaching through A to get to B we have exposed ourselves to future changes in both classes.
If code like this is found in multiple areas what happens if A no longer uses B to fulfil this dependency or the signature of SomeMethod() changes? The answer of course is that we've set ourselves up for a lot of re-factoring.
These long chains of function calls are sometimes referred to as train-wrecks, keep an eye out for them and be sure to ask yourself what has happened to the encapsulation here?
Why Have I Got To Do That?
A good approach to identifying and fixing these issues is to be lazy, to see a function call as taking some physical or mental effort.
In the previous example we should see A as slacking off, why do we have to do A's job for it, isn't that what you were coded for? I don't want to have to know about B and I certainly don't want to call SomeMethod().
In general the interface a class presents should be capable of fulfilling the functionality it is stated to offer without you as the caller taking further action on another class returned from the API. By class A returning class B we now have a dependency on B that isn't easily inverted, its won't be stated in our classes constructor but the dependency is there none the less.
This is essentially the essence of encapsulation, its the reason we write classes in the first place to gradually one step at a time move ourselves away from the detail.
Being Anti-Social
Its important when we write code that we give some thought to how it will be maintained, what will be the impact of this area of the code changing? Because its a pretty sure thing that at some point in the lifetime of the code change will be necessary.
The most effective way to ease this potential maintenance headache is to effectively manage who knows what, everything should be on a need to know basis.
The reasons a class has to change is directly related to its knowledge of the system its in, the greater the knowledge the more detail the class is exposed to and detail can change.
Encapsulation is the cloak we use to hide this information.
Write your classes to be shy, to not want to expose their internal structure and implementation to others.
Write your classes to be slightly anti-social, to not want a wide circle of friends, to be fearful of strangers.
Your classes should only be friends with classes that share a common interest, "we're friends because we all work with the database, we don't want to be friends with anyone that works with the UI".
Don't Go Breaking My Heart
This is not to say that classes should be tightly coupled, classes that are friends should enjoy a loose relationship, this is about the fact that these circle of friends should be clearly identifiable and obvious to anyone with only a passing knowledge of the system.
This isn't Facebook, every time your class gains a friend it could at some point be let down by that friend and need re-factoring to fix the relationship, more friends in this context is not better.
So whenever your introduce two classes to each other ask yourself the question "does it make sense that these two are friends?"  

Sunday 7 June 2015

The Best Laid Plans


Should we be saying we DO Agile or that we ARE Agile?
I fear that many of us go with the first option, it may seem like pedantry but I think there is an important distinction between these two phrasings.
To say you DO Agile indicates a mind-set that Agile is a process, a set of rules that can be used to run a project that will deliver a favourable outcome.
To say you ARE Agile indicates that Agile is a state of mind, a practical outlook on the world, a realistic view of the trials and tribulations of software development.
A Dose Of Realism
In 2001 17 software developers produced the Manifesto For Agile Software Development.
We are uncovering better ways of developing software by doing it and helping others do it. Through this work we have come to value:
Individuals and interactions over Processes and tools
Working software over Comprehensive documentation
Customer collaboration over Contract negotiation
Responding to change over Following a plan
That is, while there is value in the items on the right, we value the items on the left more.
No mention of sprints, stand-ups or Scrum Masters, instead four view points on what we should value when developing software.
Many looking at this for the first time may get quite scared about the apparent disregard for the items on the right, but in my opinion this is not the aim of these statements.
Instead this is about realism, we would all prefer to have a rock-solid plan built on extensive and complete documentation and be delivering to a customer who is in no doubt about what they want, but has anyone reading this ever worked on a project like that?
To say you ARE Agile is to admit the world isn't like that, to move on and not be frightened to deliver something imperfect but instead to concentrate on continually delivering something viable with the expectation that it will need to change with every iteration.
All The Right Notes But Not The Right Tune
Mostly when we say we DO Agile we mean we use the terminology of Scrum. We have a Scrum Master, a Product Owner and our developers work in sprints, but is that Agile?
Scrum is a methodology designed to help the adoption of an Agile state of mind but its possible and all too common for Scrum to become just another project management technique where we still cling to all the items on the right hand side of the manifesto either through fear or through force of habit.
The word Agile is defined as being quick in movement; nimble, it could also equally be defined as anticipating and being ready for change, embracing the imprecise nature of requirements and having a desire to ship a quality if minimal product.
When we decide to adopt Scrum we have to be prepared to embrace these ways of thinking, other wise I fear were just discovering new ways to repeat the same mistakes. 
It is better to have written code and got some features slightly wrong than to never have shipped at all, the best laid plans of analysts and developers often go awry.




Tuesday 2 June 2015

Smart Coded


We are developers we like to write code, we like to write a lot of code, we see code as the solution to all of life's ills.
The uncomfortable reality for all of us is, sometimes code isn't the answer.
We've all been in the position, especially early on in a project, where our imagination is sparked, our geeky sense starts tingling as we see a potential new feature starting to be mapped out in our mind.
My message is, do NOT code that feature, if its not on the list its not going in.
You Aint Gonna Need It
Whenever were trying to decide on a solution to a problem with been presented with we should be seeking to get away with doing as little as possible, we should be trying to do the simplest thing that can possibly work.
Its a harsh reality but code is a liability not an asset, we should be in the business of ensuring we need as little of it as possible.
Code has to be maintained, code has to be tested, code has to be integrated with other pieces of code. It has to be documented and it has to be understood by anyone new that comes into contact with it.
All of those tasks take time and effort, the only way to effectively reduce both is to write just enough code to implement the required features and to implement them as simply as possible.
We'll I Didn't See That Coming
What may seem like a time saver at first, "I reckon where going to need this at some point", can end up costing a lot further down the road when the code has gone in a direction we didn't anticipate and the code that implements a feature that no-one asked for or is using still needs to be maintained.
One of the fundamental things an agile methodology tells us is that things are guaranteed to change and the intentions and behaviour of users is difficult to anticipate.
When we decide to implement a feature no-one asked for we are unlikely to have properly defined what it is were trying to achieve by adding it, remember allowing you to write a cool piece of code isn't the end goal.
Implementing one feature often leads to other features before long if were not careful we've created a whole mass of stuff no-one actually wants but we have to keep the plates spinning.
An agile code base is a small code base that is as simple as it can realistically be to meet what's being asked of it. Good engineering solves problems and believe me there are enough of those to go around we only need to concentrate on the one were being asked to solve now.
Coding Smart
So we write a really simple piece of code and then rip it up and start again when we need to solve a new problem or implement a new feature? Well no, we write simple but SOLID code so that we never need to start again we just refactor, change and adapt.
Although it sounds slightly strange to say SOLID code is flexible code, those five principles will ensure that when you do get the inevitable tap on the shoulder asking for a change the new road ahead will be clear.
When your writing some code and you do get the itch, "we could easily add in something that does this as well", the battle is already won the fact that you can see how that would be done is enough to prove you've solved the problem in the right way, what your really seeing is flexibility. 
The chances are the thing your anticipating won't actually be required in exactly the way your envisioning it but if your code base is flexible and built for change then it doesn't really matter, it'll be able to cope with whatever the world throws at it.
Keeping it simple and holding back the urge to churn out more code isn't easy but there is no more valuable skill a developer can learn than becoming adept at knowing when not to write code, its not laziness its smart.