- Published on
JavaScript Optional Chaining
Table of Contents
The execution of your code may be interrupted by errors that result from intermediary properties that are frequently null or undefined. The innovative optional chaining operator (?.) was added by JavaScript in ECMAScript 2020 (ES2020) to address this issue. With the confidence that this operator gives you, you can code with greater ease and stability.
The Problem Without Optional Chaining
Before we start exploring let's consider a common scenario where nested property access can lead to errors:
Consider the following JavaScript object representing a user with nested address information:
const user = {
name: 'John',
address: {
city: 'New York',
zipcode: '10001',
},
}
The traditional approach to access the city
involves multiple checks to ensure that the properties exist and are not null or undefined:
let city
if (user && user.address && user.address.city) {
city = user.address.city
} else {
city = 'Unknown'
}
console.log('Traditional Approach:', city) // Output: New York
This code checks if the user
object exists, if it has an address
property, and if the address
property has a city
property. If any of these conditions fail, the city variable is set to “Unknown.” this is the kind of problem Optional Chaining solves
Understanding Optional Chaining
Optional chaining (?.) is your hero in JavaScript when dealing with nested objects that might have missing properties (null or undefined). It lets you access properties gracefully, preventing errors and keeping your code clean.
Here's how it works:
object?.property1?.property2?.method()
- Start with an object (
object
). - Use
?.
to access properties (property1
,property2
). - Call methods (
method()
). - If any part is null/undefined, evaluation stops, returning
undefined
(no errors!).
With optional chaining, accessing the nested city
property from the above becomes much simpler:
const city = user?.address?.city || 'Unknown'
console.log('Optional Chaining Approach:', city) // Output: New York
The ?.
operator is used to access the city
property of the user’s address
. If any intermediate property (user
or address
) is null
or undefined
, the expression short-circuits, and the result is immediately set to “Unknown.”
How to Call Nested Methods
In addition to accessing properties, optional chaining also works with nested methods. Let’s consider a user object with a method getAddress()
that returns the user’s address:
const user = {
name: 'Alice',
getAddress() {
return {
city: 'Los Angeles',
zipcode: '90001',
}
},
}
Traditionally, calling the getAddress()
method involves similar checks:
let city
if (user && user.getAddress && typeof user.getAddress === 'function') {
const address = user.getAddress()
if (address && address.city) {
city = address.city
} else {
city = 'Unknown'
}
} else {
city = 'Unknown'
}
console.log('Traditional Method Call:', city) // Output: Los Angeles
Using optional chaining, we can simplify the method call:
const city = user?.getAddress?.()?.city || 'Unknown'
console.log('Optional Chaining Method Call:', city) // Output: Los Angeles
Optional Chaining Arrays
Consider the following code snippet
const arr = [1, 2, 3, 4, 5]
// Using logical AND operator
const firstElement = arr && arr[4]
console.log(firstElement) // Output: 5
This code checks that arr is truthy before attempting to access the element at the forth index. However, we can simplify this using the optional chaining operator
const arr = [1, 2, 3, 4, 5]
// Using optional chaining operator
const firstElement = arr?.[4]
console.log(firstElement) // Output: 5
Conclusion
With ES2020, optional chaining (?.) was added as a potent technique to the JavaScript toolkit. It makes it easier to access nested object and array properties and methods, especially when working with possibly null or undefined data. Optional chaining improves code readability and maintainability and lowers error risk by doing away with the requirement for frequent null checks. Use optional chaining to build more readable code.