Amazon’s tabs are a classic example of product design debt and the refactoring process to pay it down
Incrementalism creates Technical Debt, and also Product Design Debt
Most startups these days build products using the various philosophies of agile – both in the formal sense but also the informal sayings of “deploy early and often,” “fail fast,” “ship and iterate,” etc. Coupled with A/B testing, customer development, and thinking through business problems in a scientific, hypothesis-driven way, you end up with a powerful cocktail of techniques to build a modern startup in the most iterative way possible. This kind of incrementalism is mostly great, and people should generally do more of it.
The interesting part is when you get a couple months into your product cycle. You often end up with lots of half-done experiments lying around, an infrastructure that isn’t built to scale, and a mishmash of code that needs to be refactored. Most engineers know that in this kind of a case, the best practice is NOT to rewrite your code, but rather refactor it continually and take down the so-called “Technical debt” so that it’s always under control.
However, there’s the other side of the coin, which is the product design. After you’ve added a ton of new features and stuck them all on the homepage, you create Product Design debt. The Amazon tabs at the top are a great example of this – you have a design philosophy built around tabs, you scale it as far as you can, and then you have to refactor your design.
Arguably, MySpace is a company that never paid down their product design debt, and their traffic has been impacted as a result.
Anyway, let’s dive into this topic more, starting with technical debt.
Technical debt
Most of my readers are probably familiar with the concept of technical debt, but just to re-summarize from this great article on the topic:
The first kind of technical debt is the kind that is incurred unintentionally. For example, a design approach just turns out to be error-prone or a junior programmer just writes bad code. This technical debt is the non-strategic result of doing a poor job. In some cases, this kind of debt can be incurred unknowingly, for example, your company might acquire a company that has accumulated significant technical debt that you don’t identify until after the acquisition. Sometimes, ironically, this debt can be created when a team stumbles in its efforts to rewrite a debt-laden platform and inadvertently creates more debt. We’ll call this general category of debt Type I.
The second kind of technical debt is the kind that is incurred intentionally. This commonly occurs when an organization makes a conscious decision to optimize for the present rather than for the future. “If we don’t get this release done on time, there won’t be a next release” is a common refrain—and often a compelling one. This leads to decisions like, “We don’t have time to reconcile these two databases, so we’ll write some glue code that keeps them synchronized for now and reconcile them after we ship.” Or “We have some code written by a contractor that doesn’t follow our coding standards; we’ll clean that up later.” Or “We didn’t have time to write all the unit tests for the code we wrote the last 2 months of the project. We’ll right those tests after the release.” (We’ll call this Type II.)
Of course, we are mostly interested in the second type. Eric Ries has a great article advocating for why it’s OK to Embrace Technical Debt. Another great article is from Joel on Software called Duct Tape Programmer. All of these articles are worth reading.
I won’t focus too much on the definition since those other posts do such a great job – instead, I think it’s worth talking about why an iterative approach tends to produce technical debt. I don’t think it happens all the time, but there’s always a temptation for it to happen.
Ultimately, the problem is that if you are trying to learn something about the business, and your technology is meant just to support that experiment, 99% of the time it’s not worth it to do things the “right way.” The reason is that you don’t know if something is going to work, and as a result, you don’t want to invest in scale or perturbing your entire codebase for something that might be disposable. So instead, you just put a 10% or 25% version of the product out there (now commonly referred to as the Minimum Viable Product) and do as little coding as possible to get there.
The problem is, when the feature is successful, very rarely is a team going to then go back and rewrite it – every experiment creates more questions, and the temptation is to move on to the next question.
Product design debt
A similar problem to this is Product Design debt, which impacts the user experience rather than the underlying technology. The same temptations that lead to technical debt also lead to product design debt, because it’s always harder to do things the “right way” and it’s almost never a rational investment of resources. Show me a site that has great visual appeal, and I’ll guarantee that they don’t A/B test.
Product design debt happens because of scenarios like the following:
- “I want to test this new feature, where should we put it? How about the tabs?”
- “Can we throw this experiment on the homepage and see if people click on it?”
- “Our navigation is kind of getting out of control, but if we fix it, most of the site’s features will lose a ton of traffic”
- “We just added a Lists feature and we want to promote it, can we just add a button next to everyone’s name?”
- “Yahoo just bought our startup and they are going to stick us on their homepage!”
(just kidding on the last one)
The point is, as a product experience grows deeper, at some point the initial design philosophy of just adding more links to a page or more tabs or more buttons just stops scaling. Yet it’s often hard to reorganize the whole site, especially if it means taking a short-term dip on traffic, so the “safe” thing to do becomes to incrementally add things until the user experience is horrible.
Kudos to Facebook for looking at their product and deciding that they needed to refactor everything first into a big newsfeed stream of “stuff,” and then all their features into a generic container of apps. They’ve also done a lot to actually remove options from the menu and navigation.
Why homepages becomes a Las Vegas visual experience
Incrementally-developed UIs that are never refactored often turn into a Las Vegas visual experience over time. Ya know, something that looks like this:
Why does Vegas look this way? I’d speculate that all these buildings are ultimately infringing on the public good of aesthetics, and light pollution becomes a tragedy of the commons. If all of those buildings were to power down, it may be that the relative distribution of business would remain the same, but we’ll never know since that will never happen :-)
Important navigational areas like homepages, inboxes, notifications, etc are all the same way. Each incremental menu item is not a big deal, and provides a lot of value downstream, but a slight incremental cost. But do this enough times, and you’ll start to pollute the overall design aesthetic, which is a public good that all features share.
For startups, this shouldn’t be a huge problem because you should have a product person who manages the whole experience and can resolve the public good problem. But there’s a danger in bottoms-up startup cultures where anyone can throw up an A/B experiment, which on one hand is great, but on the other hand creates UX pollution. The other class of cultures where this becomes a problem is short-term optimizing cultures, which may have a “feature of the week!” they want to focus on, which they need to exaggerate each feature each week.
For established companies with multiple teams competing with each other, this may become a key problem because then it really is a public good within the company.
Product types that are most susceptible to design debt
Ultimately, I think product experiences that provide a million little features are the ones that need to watch out the most.
This means:
- Social networking and Community sites that want to unify chat, forums, polls, videos, blogs, etc.
- Portals that want to unify news, communication, tools, etc.
- Games that want to unify lots of different missions, communication, characters, revenue-generating activities
- Retail products that want to unify lots of product categories and SKUs
- Classifieds sites that want to sell lots of different services, products, people, etc
All of the above products are hard to design for because they are meant to be open and support lots of diverse activities, but refactoring the UI constantly becomes a strong need as the initial navigation paradigms probably will not scale.
I wrote an article a while back specifically on social community sites, called Social Design Explosion.
Ideas for when and how to pay down product design debt?
For entrepreneurs out there who are building metrics-driven products but also committed to a great user experience, I would love to hear when and how you pay down the product design debt. Please comment!
Want more?
If you liked this post, please subscribe or follow me on Twitter. You can also find more essays here.