snippetjavascriptTip
Boolean traps and how to avoid them
Viewed 0 times
javascriptandhowtrapsavoidthemboolean
Problem
I recently came across the concept of Boolean traps and it instantly resonated with me due to the volume of Google searches I've performed because of it. In this article, I'll try to explain what it is, why it's somewhat of an anti-pattern, how to spot it in your code and ways to refactor around it.
While the name Boolean trap might be unfamiliar to some, I'm pretty certain the concept it represents isn't. The simplest form of a boolean trap is a function that takes a boolean argument.
The trap in the name might throw you off if you stick to this definition, but it serves its purpose. Let's look at two simple examples to get a better grasp of things:
The first example suffers in terms of readability due to an obvious contradiction. A function named
The second example is also hard to decipher without looking at some documentation. Here, the constructor expects a boolean argument that might mean literally anything. Would you have guessed that it's a flag indicating if the user should have administrative privileges? Probably not. The point is there is no way to tell what this argument means without looking at the documentation.
While the name Boolean trap might be unfamiliar to some, I'm pretty certain the concept it represents isn't. The simplest form of a boolean trap is a function that takes a boolean argument.
The trap in the name might throw you off if you stick to this definition, but it serves its purpose. Let's look at two simple examples to get a better grasp of things:
The first example suffers in terms of readability due to an obvious contradiction. A function named
reload expects a boolean argument. false in this context must surely mean that no reloading should happen. Except that might not be the case. This argument might be anything from performing the operation immediately (i.e. immediate) to some side effect such as animation to even the no-op we suspected. I've stumbled upon similar cases of ambiguous arguments in many libraries in the past.The second example is also hard to decipher without looking at some documentation. Here, the constructor expects a boolean argument that might mean literally anything. Would you have guessed that it's a flag indicating if the user should have administrative privileges? Probably not. The point is there is no way to tell what this argument means without looking at the documentation.
Solution
// What does `false` stand for?
results.reload(false);
// What does `true` stand for?
const user = new User(true);The trap in the name might throw you off if you stick to this definition, but it serves its purpose. Let's look at two simple examples to get a better grasp of things:
The first example suffers in terms of readability due to an obvious contradiction. A function named
reload expects a boolean argument. false in this context must surely mean that no reloading should happen. Except that might not be the case. This argument might be anything from performing the operation immediately (i.e. immediate) to some side effect such as animation to even the no-op we suspected. I've stumbled upon similar cases of ambiguous arguments in many libraries in the past.The second example is also hard to decipher without looking at some documentation. Here, the constructor expects a boolean argument that might mean literally anything. Would you have guessed that it's a flag indicating if the user should have administrative privileges? Probably not. The point is there is no way to tell what this argument means without looking at the documentation.
At this point, you might be asking yourself why this is actually bad. Reading through the documentation is expected. After all, that's what it's there for. Except this starts to become a waste of time on return visits. If you're working with a library and look up a boolean argument over and over because it's not obvious, it becomes a bit of a hassle.
Moreover, code is read many times by many people. The author might be familiar with the library and API and have no need for documentation altogether. But the next person who comes along will have to visit the same documentation and figure it out for themselves. That harms readability and wastes tons of time in the long run, due to a single boolean argument.
A bonus point here is the potential of further reducing readability by increasing cognitive load. There are valid use-cases for boolean arguments, but there are situations where the name of the function, being in itself a negative, with a negative (i.e. falsy) value makes the reader stop and pause to parse what's happening. For example:
Code Snippets
// What does `false` stand for?
results.reload(false);
// What does `true` stand for?
const user = new User(true);// Real quick: Is this valid or invalid?
input.setInvalid(false);// It should be obvious that `true` makes the element disabled
element.setProperty('disabled', true);
// Could be equivalent to `element.disabled = true;`Context
From 30-seconds-of-code: boolean-trap
Revisions (0)
No revisions yet.