Today, many software projects rely on some form of iterative software development lifecycle (SDLC) to incrementally deliver features to their users. A feature is identified, analyzed, designed, scoped, implemented, tested, and ultimately shipped to users – and this cycle is repeated for all features throughout a project’s lifetime.
These types of methodologies are especially useful when developing web applications, where evolution happens at a rapid pace and time to market is often paramount. Keeping iterations short helps get features in front of users as soon as possible, allowing them to give feedback on key areas that provide them the most value. Using this feedback to prioritize work within subsequent SDLC iterations helps in turn with increasing customer engagement and satisfaction, as well as reducing waste by avoiding features that do not provide as much benefit to the users.
If such well-established SDLC practices exist, why do many teams struggle to deliver value on a consistent basis?
Reaching an Ideal SDLC Structure
A good software development lifecycle should include certain key phases that are delineated and engage all required stakeholders. The ordering of these phases is important – they typically form a natural order in terms of how a feature goes from idea to working software in front of users. However, iteration should be happening within every phase, as well as across phases – phases will often overlap within the broader project plan, so some parallelization should also be happening.
Key phases are:
- Ideation and analysis – defining a vision of what a valuable feature would be, and discovering what the requirements are to realize the vision. Answering the “what?” and the “why?”.
- Design and architecture – beginning to detail what an implementation of the vision may look like in terms of user experience and broad-brush technology implementations. Answering the “how?”.
- Planning and prioritization – working out dependencies and ordering to deliver multiple features in the most effective way, given all constraints. Answering the “when?”.
- Development and testing – the actual implementation of a verifiably-robust feature that delivers the vision.
Identifying Pain Points
If you are involved with software delivery you will know projects rarely run smoothly. And even for those that do, there are inevitably areas that can be improved.
A good first step in improving software delivery is articulating what your current SDLC actually is, end-to-end. How does an idea go from a thought in the mind of a product owner to working production software in front of active users? If this definition already exists and matches with reality, you are off to a good start. Although even if you are defining your lifecycle for the first time, looking at every step required will likely highlight areas that are problematic or outright lacking. These are ideal areas for some concerted improvement.
Hidden Costs of Feature Thrashing
As a feature moves through the development lifecycle, it incurs more and more cost. There is the intrinsic labor cost in all the work that goes into designing and implementing the feature – this cost is (for the most part) estimable, made visible, and planned for ahead of time via story point estimations or similar mechanisms.
However, features also begin incurring hidden potential costs that are realized as actual costs through a suboptimal SDLC. These extra costs are typically incurred through “feature thrashing”, where a single feature is revisited time and time again. Some minor revisitation can be expected in every project – especially once user feedback starts being factored into the project – but unnecessary or excessive revisitation may mean an SDLC is not working as well as it should.
One such hidden potential cost is if any significant changes need to be made to a feature. Perhaps the feature was entirely wrong to begin with and whatever implementation already completed for it now needs to be thrown away. Perhaps the feature is complex and was not sufficiently prototyped before development started, leading to horrific bugs, poor performance, or developmental dead ends. Or perhaps the feature may be endlessly tweaked every iteration as priority-givers are unable to establish where the real value lies, or when the feature is at least “good enough” to ship in whatever state it may be.
Another hidden potential cost is that of ramp-up and context switching for someone new getting up to speed with an existing feature. This cost is even present for the original implementer of the feature, if they revisit the feature after having not worked on it for some time. Every time a feature is revisited this cost is realized.
Feature thrashing incurs and compounds these hidden costs, ultimately taking away valuable budget from the rest of the project. For small features this may not be an issue – and some of these costs are inevitable in every project – but for larger features in enterprise systems these costs can eat up much of a project’s overall budget. Having a robust SDLC is a good way of combating these unnecessary costs.
What causes feature thrashing? Typically there are a few major pain point areas that are often the root cause:
- Insufficient (or excessive) analysis, planning, architecting or design
- Ineffective prioritization
- Ineffective stakeholder engagement
Identifying and resolving these are key to establishing good SDLC health.
Finding the Goldilocks Zone
Know where you’re going, and the steps to get there
Timeline horizons are important when analyzing what makes software projects successful. Many problems can arise if teams are overstretched and the only visible horizon is the end of the current iteration. Vision and scope become too narrow, meaning teams may end up going in circles, developing and tweaking and redeveloping and rewriting from scratch a single feature – the worst type of feature thrashing.
Conversely, if the focus is only on the full picture and scope is too broad, the project can stray further away from the goal of constant, iterative value delivery. This can also induce feature thrashing where features are insufficiently defined before being implemented, leading to rework once more detailed analysis becomes available (far later than it should have been). There is also the other end of the scale – analysis paralysis, where too much up-front analysis, design, or architecture work is attempted, ultimately stalling any attempts at delivery.
Healthy projects typically have a good handle on multiple timeline horizons and can jump between macro- and micro-level granularities as needs dictate. These projects can state “that is enough, for now”, where sufficient work is done at a given detail level to allow the next phases of the SDLC to start. Other lower-priority decisions can be deferred until they need to be answered – and there’s a good chance in retrospect that many such decisions will never be needed.
A high-level view of the total project should be visible to all stakeholders, but may not provide much detail beyond major milestones or feature areas. The primary purposes here are setting the overall vision, and serving to plan overall timeline and budget requirements for the project.
When looking at more immediate term horizons, detailed feature analysis, design, and architecture should become visible. This is most relevant for features in the current development iteration, as well as the next couple of upcoming iterations. The entire stakeholder team can then work across and refine information within as many of these horizon ranges as needed to best meet continued project success.
Minimize Feature Thrashing
Insufficient (or excessive) analysis, planning, architecting or design
Given all the costs that are accrued the longer a feature progresses through the SDLC, there should be an active effort from all stakeholders to “shift left” or “shift earlier” the activities of feature analysis, design, and architecture. By this, we mean that these activities should occur as early in the overall SDLC pipeline as possible – i.e. at the point where they are cheapest to accomplish and where the cost of any rework is minimized. It is far quicker and cheaper to change a set of requirements in a ticket or an architectural blueprint before implementation has started.
Work with product owners in establishing what “good enough” looks like for the current iteration, while keeping an ever-present eye on the bigger picture. Avoid descending into rabbit holes, and be confident in taking a step back to identify when you are currently in a rabbit hole. On balance, also try to identify potential problem areas ahead of time – complex or contentious areas that will require much more detailed upfront analysis, user experience design, or areas that may require prototyping to select the best possible way forward before implementation begins. Here, prototyping can mean wireframing and user testing in terms of UX, as well as proof-of-concept implementations in terms of technology. Ensure time is allocated to support this work, but think about using timeboxing to avoid yet another rabbit hole.
There is a tendency in modern software delivery to delay decision making until the last possible point in time – but it is easy to cross this line and proceed with implementing something that does not meet expected requirements. An unforeseen delay in obtaining those expectations typically causes this – critical decisions that involve multiple stakeholders should be assessed on an ongoing basis to allow for variations in stakeholder availability. Leaving such decisions until the last possible moment will likely fail given some key person being unavailable at that time. Ensure decisions that need to be made, are made – software delivery should not involve guesswork. Be empowered to defer features with outstanding decision points – and be confident in the robustness of your iteration planning and prioritization processes that deferring one or two items will not cause havoc with the wider project delivery schedule.
Ineffective Prioritization
Ensure a single primary product owner can be identified – or if dealing with a team, ensure there are mechanisms in place to reach quorum when decisions need to be made.
Ensure decision outcomes are documented and have procedures in place to manage any required changes in decisions. Ensure costs of such change management are known and agreed to by all parties ahead of time, to avoid any nasty surprises down the line.
Keep timeline horizons in mind when making prioritization decisions – ensure these decisions are not exclusively based on the immediate term. Allocate a budget for each iteration that allows for the capacity to handle extra work that underpins pure product features. Budgets can also support buffers for unplanned work (critical bug fixing) or allow for stretch goals if all committed features are delivered ahead of schedule. Pure feature delivery should not occupy 100% of every iteration’s budget – if this is happening, it may be a sign that your SDLC needs a health check.
Ineffective Stakeholder Engagement
Know who the product’s intended users are. Everything that flows through an SDLC should be justifiable in terms of providing value to these users. The best SDLC in the world will not help a product achieve success if such “success” cannot be defined.
Ensure effective communication lines are open between all stakeholder groups, where problems can be raised and managed as soon as they are identified. Good communication should also be more than just a channel to raise problems, however; it should also allow for negotiation, as well as providing justifications and reasonings behind contentious decisions. A decision may seem problematic or unnecessary at first glance but there may be good business or technological justification backing it up. If insufficient justification is available, the feature in question may be a candidate for deprioritization; effort should not be wasted on analysis, design, or implementation of features that attempt to guess underlying justifications.
Ensure all teams are empowered and can raise concerns when problem areas are identified. Try to ensure time is given to fix these areas before they become even more problematic – or at least get an estimate of their scale and priority in relation to other problems also being dealt with.
SDLC Technology Choices
While much of what forms an SDLC is simple process definitions, there are areas where technology is key to reach any form of efficient delivery cadence. This can be thought of as all the supporting technology that goes into shipping working features to end users, but is not directly responsible for feature implementations themselves. Areas such as toolchains (the languages and frameworks that features are implemented with), automated delivery pipelines (building, testing, releasing & shipping working software), infrastructure definitions, etc.
These areas are challenging in their own right and may need a lot of attention before a project reaches the goal of a robust, automated SDLC that can ship a product to end users on a repeatable basis. However, these are comparably easier to solve than other SDLC pain points as they are under more direct control of the technology delivery teams – plus the software development industry is producing more and more automated tooling and infrastructure to take such burdens off individual project teams. These SDLC areas are now commodities, for the most part – but still require some investment to fully integrate into a project.
Conclusion
If any of these problems sound familiar, it may be useful to reassess whether your SDLC is working for or against you by giving it a much-needed health checkup. Spending time improving an SDLC to reach a more optimal balance will provide tangible lasting benefits to any project.
At SitePen, our team provides end-to-end application development solutions including the establishment of effective SDLCs that allow us to deliver fantastic products, together.
Get in touch with us to find out how SitePen can help you improve your software delivery effectiveness or help you develop your next application.