by Sean Johnson
According to the world’s brain (by which I mean Wikipedia in this case, not Google), abstraction in the context of computer programming is “to reduce and factor out details so that one can focus on a few concepts at a time.” I’ll explain how abstraction is so useful in software development with an analogy. Products that are electrical almost always have a power switch. We have abstracted this concept so we know to look for a power button, slider, switch or toggle on these devices. We don’t have to rediscover the concept of on/off and how it is implemented for every electrical device we encounter. This is the same type of abstraction software developers like to harness. Good software developers treat the like aspects of similar things in the same way and avoid exposing details of one area of their software to all the other areas of their software. Abstractions shield us from details that are not important at the time. Abstractions are productivity enhancing tools and they free us to focus on more important issues at a higher level in the system.
Yet all is not perfectly rosy with using abstraction. One problem with abstractions and software development has been identified by Joel Spolsky and he calls it the Law of Leaky Abstractions. A second problem with abstractions is that they aren’t always useful for our product’s users. When an abstraction is used to develop software it can then seem natural to expose the abstraction to users of the product. This is often times a very bad idea. In an homage to Joel, I’ll christen this the Law of Overexposed Abstractions.
Law of Overexposed Abstractions – the users of your software don’t benefit from the same abstractions that benefited you in building the software
Excess abstraction is a leading cause of complexity in software products. The developers know that the product is built in such a way that certain details of the system have been abstracted, and that the system is thus very flexible. They get excited about this and are eager to expose this flexibility to users so that they can benefit from it too. This rarely works because of the Law of Overexposed Abstractions. In exposing your abstraction to your users, the flexibility you are trying to provide simply becomes added complexity, configuration work, and cognitive load. This stems from, among other things, the need to translate between the abstract terms and concepts of your software and the concrete terms and concepts of the user’s world.
Why is there such a temptation to overexpose abstractions? Because the abstraction becomes real in the developer’s mind when it becomes real in the software’s code. Developers start talking and thinking in terms of the abstractions they’ve created and can quickly lose sight of the fact that the abstraction is entirely their own creation and is not something that users are familiar with and understand.
Another temptation comes in the form of a question that inevitably arises, “why have this useful abstraction and not take advantage of it?” The counsel here is patience. Take advantage of the flexibility in your software by creating new products for new markets based on your existing code base and by evolving your software to meet the changing needs of the marketplace over time. Trying to capitalize on your software abstractions by exposing them directly to your users will only frustrate them.
Here are four signs that you may have let your abstractions get overexposed:
- Users must learn a new vocabulary of abstract terms and how they map on to their own language in order to use your product.
- Your product exposes any sort of type system for users and administrators to define the types of objects that exist in the system
- Your product exposes any sort of workflow system for users and administrators to define processes
- Your product requires significant up front configuration before it can be used rather than supporting moderate adjustments once real world use has shown the user that they need to make an adjustment
I’ll illustrate some of these warnings with a great product that may have lost its way due to the Law of Overexposed Abstraction. Mingle is a project management and team collaboration product for agile software development teams from ThoughtWorks. I’ve been using Mingle for a couple of releases now and I have talked to other developers that use or have used or evaluated Mingle. A consistent view is that Mingle does many things right (its flexible user interface is a big plus) but it exposes too much abstraction. I’ve struggled with the resulting complexity myself and I’ve witnessed other development teams struggle with it.
Every item in Mingle is a card with a user defined sub-type.
Once defined, card types are ordered into a user defined containment hierarchy.
User defined transitions in Mingle take the form of a state machine.
Mingle is a very flexible and abstract system. Without an existing template of card types, card properties, card tree hierarchies and state transitions, getting it configured is a daunting task that can at times feel like programming. ThoughtWorks has done a good job of providing some ready made templates with Mingle that can remove some of this burden. However, even when using a template users must come to grips with the abstractions to make the small configuration changes that are needed. Mingle would benefit from a more opinionated view of how an agile product management tool should function. Then the flexibility that has been developed in the system could remain under the covers but be leveraged to create different versions of Mingle for different development methodologies, or could be released in a high end version of the product for the largest development teams that can justify the cost of learning and configuring a complex tool.
Remember, smart developers will use abstraction, and this is not itself a problem. Abstractions go wrong when a strong barrier is not erected between useful abstractions in the software and the real world problems of your customers. Your software must interact with its users in a concrete and opinionated way. Use the vocabulary of your users, not the vocabulary of your own abstract creations. Even though your software is flexible and is therefore capable of supporting many different opinions, you must pick the one way you think is best for your customers and then defend the hell out of it.
Keep the abstractions where they belong, under the covers. Benefit from your abstractions over time, both by responding to the changing market faster and by creating new products from your existing code. And with each product release, remember to keep it real.
Sean Johnson is a voice in the field of product development, management and design. He works for IBM and has brought numerous products to market for startups, for IBM and for himself. His blog on product design is called Art of the Product.