At Olio Apps, we use the technical design process to understand a problem, and to formally articulate a solution that is possible to validate with oneself and with one's collaborators.
Whereas pull requests and code reviews are reactive, technical design allows review and guidance to happen proactively.
Most importantly, the technical design process allows us to think through a problem carefully before jumping straight in, avoiding potentially expensive pitfalls and dead ends.
Applications
Technical design can be applied in the small, where the behaviors of discrete functions and their interactions within one or more modules are described. Technical design techniques are also applicable in the large where the interactions within multiple coordinating systems are explored, diving into details of the internals of those systems in the small as necessary. In short, its always applicable!
How it fits in the Software Development Life Cycle
Technical design is an iterative process that happens roughly after the requirements and functional design have been worked out. Its broken into roughly 3 phases:
- High level design
- Detailed Design
- Review
Each of these steps are described in detail below. Upon successful completion, the regular coding and pull request peer review cycles commence, dipping back into the technical design if peer reviews reveal that addition design is required.
Phase 1: High Level Design (HLD)
The HLD phase is where the functional design is discussed and a general solution approach is agreed upon. Typical decisions made during this phase include:
- What frameworks or languages are required, and the rationale for using them
- Build or buy decisions
- Identification of the major technical risks & research activities
- The modules that require modification or creation, and a general description of what is needed to be done
- Outlining the interactions between modules or even functions over time (using UML interaction diagrams for example)
- Division of labor between individual contributors
- Integration planning and timelines
What isn't typically discussed at this level are the exact changes to particular functions. The conversation is left intentionally less specific in order to provide room for creativity and exploration for individuals undertaking the next phase. The HLD represents the phase of technical design where the strategy of the solution is proposed.
Senior engineers/architects usually seed the ideas in the HLD, encouraging junior members to dialog and refine the solution.
Phase 2: Detailed Design
This phase is where specific changes to the code are proposed in support of the High Level Design. Furthermore, the detailed design should identify any impacts of those changes to other parts of the system that are not being directly modified.
Typical activities performed during the phase could include:
- Description of the algorithms to be created and their application in specific modules
- The creation or modification of specific functions, describing the impact within the system being changed
- Exact schema changes if a datastore is being changed (eg. sql upgrades)
- Entity relationship diagrams showing the changes to the composition of entities if required
- Identification of any performance related impacts and mitigations
- Identification of areas in the code where backwards compatibility is threatened by changes
- Description of what automated and manual tests are needed as result of the change
- Identification of changes to external facing resources such as documentation
- Identification of any weaknesses in functional design or high level design
This phase is usually performed by the folks who will actually be writing the code. The process typically involves:
- analyzing any existing code
- documenting any thoughts that arise during the analysis
- transforming those thoughts into a coherent solution that resembles English much more than a specific coding language
Just enough detail should be provided so that the proposed changes are specific enough to be challengeable. However, code snippets should be avoided if possible, as it could derail the conversation. It is easy to get bogged down in, for example, the specifics of language syntax & coding conventions.
If necessary, the engineer may do some prototyping and other short-lived coding activity which is ideally not shared but instead documented only as far as to share the conclusions gleaned from the prototype.
Phase 3: Review
Once an engineer has documented their technical design, they should regroup with the original team to discuss the degree to which the high level design is served by the detailed design.
The reviewers may find the detailed analysis to be insufficient in some way, and the detailed design could at that point be amended. On the other hand, the detailed design may also reveal weaknesses in the original high level design. In this case the high level design should be rethought, and revisions be made to the analysis (eg. go back to step 2).
Agreement & Post Technical Design
Once the detailed design has been agreed upon by all parties involved, any actionable points in the analysis should be turned into work items (eg. trello tickets) and the regular coding - peer review cycle can commence!