A creative way to have required arguments in JavaScript

A creative way to have required arguments in JavaScript

ยท

3 min read

Have you ever received an error because you forgot to pass an argument to the function? This is a common situation.

Unfortunately, JavaScript does not require passing parameters that have been declared in the function, and this results in a possible later error.

Let's see an example. Consider we've got a function that must receive a string and return if that string contains de letter "G".

file.js

function includesG(string) {
  return string.includes('G')
}

console.log(includesG('Gabriel Rufino')) // true

This works fine! But there's a problem: what happens if I call the function includesG without an argument?

file.js

function includesG(string) {
  return string.includes('G')
}

console.log(includesG())

Let's execute using Node:

$ node file.js
/home/gabrielrufino/Desktop/file.js:2
  return string.includes('G')
                ^

TypeError: Cannot read property 'includes' of undefined
    at includesG (/home/gabrielrufino/Desktop/lab/lab.js:2:17)
    at Object.<anonymous> (/home/gabrielrufino/Desktop/lab/lab.js:5:13)
    at Module._compile (internal/modules/cjs/loader.js:1063:30)
    at Object.Module._extensions..js (internal/modules/cjs/loader.js:1092:10)
    at Module.load (internal/modules/cjs/loader.js:928:32)
    at Function.Module._load (internal/modules/cjs/loader.js:769:14)
    at Function.executeUserEntryPoint [as runMain] (internal/modules/run_main.js:72:12)
    at internal/main/run_main_module.js:17:47

It seems to be a pretty violent error ๐Ÿ˜…

There's a much better way to report the absence of an argument to the developer: we can combine the power of the default params with the throw of a more descriptive error.

Let's do it step by step. First, we define the function responsible for throw the error. I'm gonna call it isRequired.

file.js

function isRequired(argument) {
  throw new Error(`The argument ${argument} is required`)
}

function includesG(string) {
  return string.includes('G')
}

console.log(includesG())

The function isRequired is nothing more than a function that throws a custom error based on the name of the argument.

Now that we have this function, we can use it as the default param of the required argument or arguments.

Wait for it...

file.js

function isRequired(argument) {
  throw new Error(`The argument ${argument} is required`)
}

function includesG(string = isRequired('string')) {
  return string.includes('G')
}

console.log(includesG())

Now, always we forget to pass the argument string, the default value will be assumed and the default value is the throw of an error.

Let's run the code:

$ node file.js
/home/gabrielrufino/Desktop/file.js:2
  throw new Error(`The argument ${argument} is required`)
  ^

Error: The argument string is required
    at isRequired (/home/gabrielrufino/Desktop/lab/lab.js:2:9)
    at includesG (/home/gabrielrufino/Desktop/lab/lab.js:5:29)
    at Object.<anonymous> (/home/gabrielrufino/Desktop/lab/lab.js:9:13)
    at Module._compile (internal/modules/cjs/loader.js:1063:30)
    at Object.Module._extensions..js (internal/modules/cjs/loader.js:1092:10)
    at Module.load (internal/modules/cjs/loader.js:928:32)
    at Function.Module._load (internal/modules/cjs/loader.js:769:14)
    at Function.executeUserEntryPoint [as runMain] (internal/modules/run_main.js:72:12)
    at internal/main/run_main_module.js:17:47

And now, we've got a more descriptive error saying that we forgot the parameter string.

"Ok, Gabriel! But don't we replace one error with another? How does it help me?"

Errors were created to help us! They must tell us what specifically is wrong. The first error doesn't help us to find out what is the problem, it only says that the value undefined doesn't have the method includes. It's so much generic to find the problem. The error we've created says explicitly that we forgot the argument ๐Ÿ˜„

Thank you!

Did you find this article valuable?

Support Gabriel Rufino's Blog by becoming a sponsor. Any amount is appreciated!

ย