Writing Technical Design Documents
One great mechanism for improving the planning process among distributed teams is writing technical design documents. Design docs spell out what you’re going to build, how you’re going to build it, and why you’re building it the way you are. Because design docs involve clearly communicating your plan in writing, they serve a nice forcing function in verifying that you have a solid plan. As you’re building the system and after it’s built, the design also provides an artifact into the intent and considerations that went into key decisions.
There are several great resources out there for folks who are getting started writing technical designs. I’d especially recommend Malte Ubl’s “Design Docs at Google.” While I largely agree with much of the content there, I wanted to take some time here to reflect the key recommendations I’d offer to someone who’s getting started writing this type of document.
Err on the side of writing. A common question in the literature is what sort of efforts merit a design doc. It’s good to establish clear guidelines, and to assure that you properly scope work before committing resources to execution. That said, it normally doesn’t hurt to write things down. If you’re on the fence about whether or not a given change requires a design doc, consider just going ahead and writing something. Perhaps you’ll discover that the change doesn’t merit it, and you don’t have to share out. You’ll still benefit from surveying the landscape and thinking clearly about the problem. Take opportunities to practice writing things down whenever you have an inkling that greater explanation may be warranted, and you can grow your muscle in designing nontrivial systems.
Don’t start by writing a design doc. A corollary to the above is that lots of efforts that merit writing things down don’t necessarily justify a full fledged technical design, which often includes painstaking detail and peripheral concerns (monitoring/alerting strategies, privacy/security implications, timeline estimates, etc). It can be helpful to “grow” a technical design from a series of smaller documents. Perhaps you can start by capturing your idea in a one-pager. Share that with a few close confidants and see if it has legs. If so, maybe you expand out to several pages and seek feedback from a larger group of reviewers. You can save the effort that would go into writing a comprehensive design doc until it’s clear that the payoff is there.
Focus on the “why.” A natural instinct when writing design docs is to focus on how you’re going to build the system. These details are critical, and it makes sense to put great care into defining them - if for no other reason than to prove that the goals you’re setting out to accomplish are actually achievable. That said, answering questions about why you’re building the system the way you are is as much if not more important, for several reasons:
- Logically prior. How you build your system may flow directly from a critical decision that narrows your options. For example, your data model will be impacted by whether you choose a SQL vs NoSQL data store. If your data model is premised on an underlying data store that you haven’t justified in the first place, then your design is incomplete. The “why” comes before the “how.”
- Lasting impact. Low level details of your design will change over time, as you encounter unexpected blockers, new or changing requirements, and so forth. Less likely to change are the major decisions. Indeed, these decisions will constrain how you can adapt in a dynamic environment. Focusing on why you made those decisions pays dividends deep into the future, since it surfaces the tradeoffs and intent behind your constraints.
- Digestible. The details about how you’ll build a complex system are bound to be lengthy, so that they can stand up to close scrutiny. But the reality is that some of your most valuable feedback will come from folks whose time is at a premium. These folks may not have the bandwidth to deep dive on all of the implementation details, but are well suited to assess your key decisions and tradeoffs. Spotlighting the “why” gets maximum value from all reviewers.
Let it go. Ideally, you should write a design and then execute it. In reality, you’ll likely find that the implementation starts to drift from the design over time. In some cases, it may make sense to go back and update the design. But, it can also be perfectly reasonable to let the doc grow old and outdated. Design docs are a guide to early execution and a historical record of intent; they are not the systems they describe. It’s ok if code or other documentation starts to fill a greater role in explaining the system, and you should focus your time/effort in the place where it delivers the most value to the business.
Take all of the above with a grain of salt, and probe for the expectations around technical designs in your specific organizational context. At the end of the day, the measure of a design’s worth is its value to the team - and you need to understand what your team values to build a valuable technical design.
Design docs are a tool like any other; they may not always be suited to the task at hand. But when they are, they can play a huge role in unlocking and facilitating efficient execution at scale. Writing is a critical means of communication in any field, and software is no exception. By practicing, iterating, and refining our writing, we can produce higher quality software.