We often hear that because we are working on complex systems we cannot have full coverage of what to look for. Our view is just the opposite. Because we are working on complex systems we must have complete coverage.
Complex systems are characterized by dynamic relationships between their related components. One cannot understand the system by individually looking at any one or two or three components alone. The system is not merely the sum of the components but rather it is the integration of the components, their relationships and the interconnections between them. Systems thinking starts with understanding this. You must recognize that you cannot investigate or learn about a system by decomposing it into its components. Rather, to learn how the system behaves, and more importantly, how to improve it, you must take a holistic view of the system. A system thinker can investigate components of a system, recognizing that the sum of the components is not the system and that investigating the system while ignoring certain components that make it up will leave a faulty understanding of the system.
One of the salient characteristics of systems thinking is that it is the system within which people find themselves contributes greatly to their success or failure. While we respect people, attention to the system is paramount. In fact, it is precisely because we respect the people that we must strive for good systems. Management must make this a priority and the people in the system, who typically know more about how it affects them than anyone else, need to be looking to continuously improve it.
The validity of this is easy to confirm. Consider the job of a programmer who works side by side with a tester. Further, suppose the two of them work with their product owner doing acceptance test-driven development. As the programmer writes code, he not only can run his own tests, but the tester can run any additional tests he created. The synergy improves understanding of what to do and the teamwork enables coding and testing to happen virtually simultaneously.
Now let’s look at a more prevalent system for coding and testing – a group of programmers who have a group of testers validate their work. Let’s further suppose the test team tests the programmers’ code a week after it is written. Whereas before, within a system of virtual simultaneous code and test, fixing discovered bugs is very quick, it will now be much harder and more time-consuming. Yet the programmer is the same. Why the lower productivity and lower quality of resulting code. The answer is obvious – the system.
Once we recognize the importance of systems, we understand that to achieve improvement of our methods we must improve the system we operate in. But, if we remember that complex systems are interrelated, we must attend to all aspects of the system. We cannot just say “create teams” while ignoring flow (or vice versa). When we start we won’t be able to attend to every aspect in detail. And we don’t need to. Part of our attention should be to ask – “which parts of the system do I need to attend to at the beginning?”
We appear to be in a dilemma. Systems thinking requires us to look at the whole, while our limitations on beginning new things mean we can’t look at everything. So what do we do? We need to be at least aware of the forces present to attend to. There really aren’t that many and most of the ones we need to start looking at center on delays in the workflow and in feedback cycles. These types of delays are caused primarily by:
- Too many things being introduced into development
- What is being introduced into development is too large
- Collocated, cross-functional teams do not exist forcing people to wait on others
- There are too many things in play at any one time
- Teams are not coordinating well so that they work on related things at different times causing integration errors later
- Developers and testers are not coordinating well
Note how these interact with each other. It’s important to note that the common practice of limiting WIP directly only addresses two of the above. It’s a bit naive (dogmatic?) to suggest we should always start by addressing one particular issue. Virtually every one of the above issues will have an adverse effect on the others – making for a downward spiral. Instead, we must look at a variety of potential solutions (these relate to the prior list):
- Institute a pull system by development where work does not get to the team except when it pulls it from a sequenced queue
- Use minimum business increments to work on the most important items. Create collocated cross-functional teams to the extent possible.
- Set WIP limits on each stage of the workflow (including queues).
- Teams coordinating with each other should pull the work in a coordinated fashion so that work does not begin until all the necessary people and resources are available.
- Use acceptance test-driven development.
We don’t need to address all of these issues at the beginning, of course. But we should be aware that they exist. We can ask a series of questions to see where we should start (these relate to the prior list):
- Will management cooperate to restrict work hitting the team?
- Can we convince stakeholders to use MBIs?
- To what extent possible is it to make committed, cross-functional teams without adversely impacting the rest of the organization
- Do we have a stable enough system where setting WIP limits will do us some good?
- Do we have teams that are working together? Can we use common backlogs so that they work on things in a coordinated fashion
Are our product owners/BAs, programmers and testers willing to use ATDD?
By recognizing we need to consider all aspects of the system yet knowing we must phase them in, we start at a high level and drill down only when there appears to be benefit.