JavaScript Quick Tip: Make Function Arguments Required With Default Parameters

JavaScript Quick Tip: Make Function Arguments Required With Default Parameters

How to mark arguments as required without bloating your function body

Have you ever written code like this?

const myFunction = (argument) => {
  if (argument == null) {
    throw new Error('argument is a required argument');
  }
}

Guarding against invalid arguments is perfectly fine. It's way better than failing at some random point in your function with a usually pretty obscure error message. But writing guard statements over and over again can bloat code pretty fast.

You could, of course, write a helper function for this, like the one below, which is already better.

const assertPresent = (value, name) => {
  if (value == null) throw new Error(`${name} is a required argument`);
};

You can then assert the presence of a parameter on the first lines of your function like this:

const myFunction = (argument) => {
  assertPresent(argument, 'argument');
  // further processing...
};

In my opinion, however, this still drives the reader away from the most important part of your function: its actual logic. Gladly, there is another way that moves assertions from the body of your function to its parameter list.

The Code

You can use default parameters to make function arguments required. For this to work, you first need a helper function that immediately throws an error:

const required = (parameterName) => throw new Error(`${parameterName} is a required argument`);

And you can then integrate this function like this:

const myFunction = (argument = required('argument')) => {
  // processing...
};

From now on, when users call your functions like this:

myFunction(); // => Error: argument is a required argument

an error is thrown because not providing the argument triggers the required function, which immediately throws a readable error message.

This way prevents that your function body gets bloated with assertions you can move to the function's head. And it preserves semantics way better.

One Caveat

This solution is not fully functionally equivalent to the original code. Default parameters don't catch null because it's an explicitly set reference. If you need to handle null properly, you won't be able to do it with the default parameter solution.

The Whole Tip As An Image

If you like visual content more, or if you want to store it for later, I put all this into one single image for you. I hope you like it!

A picture showcasing the above code

Before You Leave

If you would love to read even more content like this, feel free to visit me on Twitter or LinkedIn.

I'd love to count you as my ever-growing group of awesome friends!