Modern JS Features You Should Use
JavaScript has evolved massively over the past few years. If you haven't explored features from ES2020+ yet, you're missing out on cleaner, safer, and more expressive code. In this article, we'll walk through some of the top modern JS features that you should be using today, with examples and real-world scenarios.
1. Optional Chaining (?.)
Optional chaining allows you to safely access deeply nested properties without having to check each level manually. Imagine you are fetching user data from an API:
// Before optional chaining
const city = user && user.address && user.address.city;
// With optional chaining
const city = user?.address?.city;
This prevents runtime errors when some property along the chain is undefined. It’s a small syntax addition that makes your code much safer and more readable.
2. Nullish Coalescing (??)
Sometimes you want to provide default values only when a variable is null or undefined, but not when it’s falsy like 0 or an empty string:
const input = "";
const username = input ?? "Guest"; //username will be "" instead of "Guest"
const userAge = undefined ?? 18; // userAge will be 18
Combined with optional chaining, this feature is incredibly handy when dealing with optional API responses.
3. Dynamic Imports
Dynamic imports let you load JavaScript modules on-demand instead of at the initial load. This is particularly useful in large apps or React/Next.js projects where you want to reduce bundle size:
// Lazy load a module only when needed
async function loadFeature() {
const { feature } = await import("./feature.js");
feature();
}
// In React
const LazyComponent = React.lazy(() => import('./MyComponent'));
Dynamic imports are key for modern performance optimization and code-splitting.
4. Top Modern JS Patterns
Besides language features, there are patterns that take advantage of modern JS:
- Destructuring: Clean extraction of values from objects and arrays.
- Spread / Rest Operators: Easy merging and immutability.
- Optional Chaining + Nullish Coalescing: Safe defaults and less boilerplate.
- Modules (import/export): Keep code modular and maintainable.
These patterns help maintain readable, maintainable, and safe code, which is critical for professional-grade applications.
5. Real-World Example
Let’s combine optional chaining, nullish coalescing, and dynamic imports in a single scenario:
async function displayUserInfo(user) {
const person = user?.profile?.name ?? "Anonymous";
const age = user?.profile?.age ?? "Unknown";
if (!user?.settings?.loaded) {
const { loadSettings } = await import("./settings.js");
await loadSettings(user.id);
}
console.log(`\${person}, \${age}`);
}
Here we safely access deeply nested data, provide defaults, and lazily load a module only when needed—all modern JS best practices in one small example.
Conclusion
Modern JavaScript is more than just syntax sugar; it empowers you to write cleaner, safer, and more maintainable code. If you haven’t embraced ES2020+ features yet, start incorporating into your projects the following:
- Optional chaining (?.)
- Nullish coalescing (??)
- Dynamic imports
- Modern patterns like destructuring and spread/rest operators
These small changes will save hours of debugging, make your code safer, and improve readability. They are must-learn for any JavaScript or Node.js developer.
