There are no solutions, only trade-offs


“There are no solutions, there are only trade-offs; and you try to get the best trade-off you can get, that’s all you can hope for.” – Thomas Sowell

In software, we don’t often articulate trade-offs when we make a decision. We may make a pros/cons list and consider the options, but then when we make a decision, we just articulate the decision. Why do we do this?

For example, many companies at some point decide that they need to break up their monolith into microservices. Most people would agree that it wouldn’t make sense for a small early-stage startup to have a lot of microservices, and it wouldn’t make sense for a massive company to have one monolithic system. At some point in the growth of a company, you get to the point where this is a 50/50 tradeoff.

These are the most painful kinds of change because you’re trading off one set of problems for an equally painful set of problems, usually because you think it’s better in the long term. Making the change takes a lot of painful work, and big change is hard for people. If you decide to stick with the status quo, you’re still feeling a lot of pain. Either way, you’re likely to have many dissenters that think that the other way is better.

This is why you often see companies decide to switch from a monolith to microservices and then walk back the decision shortly after. Was it the wrong decision the first time? Maybe yes, maybe no, or maybe a new leader saw the 50/50 tradeoff as more of a 40/60 tradeoff. Changing your mind might be the best decision, but it still ends up costing a lot of time and money.

There are many non-technical examples I could talk about here as well, such as changes to planning processes, re-orgs, project prioritization decisions, headcount allocation decisions, etc. I’m sure you could think of many examples from your own company.

I think we can do better

1. Be aware of the negative trade-offs that you accept when you make a decision and make sure you have mitigations in place.

For example, you may decide to start using serverless compute because you want the ability to scale up quickly when you have spikes in traffic. The trade-off is that now your costs can explode unless you mitigate the risk by putting observability and controls in place to ensure that doesn’t happen. If all you focus on is solving the problem of handling spiky traffic, you could create a bigger problem.

2. When you’re articulating a decision, also include the counter-arguments, why you’re choosing to accept the trade-off that you chose, and any steps you’re taking to mitigate the risk.

This gives more context to the listener – if they have the opposite view, at least they know that you considered their side of the argument, are aware of it, and are potentially going to do something to mitigate the risk. There may still be disagreement, but you’ve shifted the discussion to whether we’re accepting the right trade-offs, which forces the dissenters to consider trade-offs as well.

3. When faced with a 50/50 tradeoff, consider keeping the status quo in place until the right choice is more obvious.

This may sound like a cop out, but it gives you more time to make the right decision and reduces the risk that a small change in some external factor forces you to change your mind. There are three typical outcomes to a decision like this:

  • You make the right change and it ends up working out.
  • You make the wrong change, and then you either have to spend more time to undo the decision or continue to march forward down a path that you know is worse, but the cost to go back is too high.
  • You wait to make a change and make the right change a little late.

The cost of making the wrong decision can be extremely high. The cost of choosing slightly incrementally better trade-offs may incur a cost of change that far exceeds the benefits of the change. I would rather accept the pain of making the right decision a little late if it increases my chance of making the right decision.