JavaScript guard clauses – how you can refactor conditional logic

Originally published at medium.freecodecamp.org.

Learn about guard clauses in JavaScript and how to use them to refactor your code.

This short refactoring tutorial will explain how you can write guard clauses for your if statements, rather than using nested if .. else conditional logic. This can help you to create clean and easy to read code. It will give examples using JavaScript, but the same programming style can apply to other languages.

Avoid nested if .. else logic

What may start off as one set of conditions managed by an if .. else block can easily become difficult to understand when more and more if .. elselogic is added to manage various conditions.

function userIsAdmin(user) {
 if (user.role == 'admin') {
  if (user.manager == true) {
   return true;
  }
  else {
  return false;
  }
 }
 else {
  return false;
 }
}

This can result in code in which it is challenging for developers to follow the flow of logic. It can also be time consuming to maintain or amend code later on. An alternative programming style is to use guard clauses, which achieve the same outcomes but can be easier to read.

The guard clause

This structure guards the flow of logic from continuing if certain conditions are met, or not met.

if (user.role != 'admin') return false
...

Guard clauses can reduce the number of lines in your functions, classes, and so on. A result of using multiple guard clauses is that you can see what conditions trigger certain code to be executed.

Here is the above example refactored using guard clauses.

function userIsAdmin(user) {
 if (user.role != 'admin') return false
 if (user.manager != true) return false
 return true
}

Note how the number of lines of code has reduced from 13 to 5!

Further refactoring using code extractions

A further way to develop this refactoring strategy is to extract code to other functions, classes, or modules, which are then called within guard clauses. It means you can use more complex conditional logic for an if statement within a guard clause. Here is a simple example of code extracted to separate functions.

function userHasAdminRole(user) {
 return (user.role == 'admin')
}
function userIsSeniorManager(user) {
 return (user.manager == 'senior')
}

Now you have extracted key logic, you can unit test these independently from the original code. This can help you to identify, isolate, and iron out bugs within a large code base.

Here are the extracted functions applied to the original example.

function userIsAdmin(user) {
 if (userHasAdminRole(user) && userIsSeniorManager(user)) return true
 return false
}

It can even be refactored down to 3 lines for the original method.

function userIsAdmin(user) {
 return (userHasAdminRole(user) && userIsSeniorManager(user))
}

En conclusion!

Applying this strategy to a complex code block can help you gain control of your code logic in way that makes code maintainable and scalable. Refactoring is an art form, and there are always ways to keep refining this skill as a developer.

Source: dev